Full support for custom PC graphics as well as monster graphics on PCs

This commit is contained in:
2015-06-23 14:12:51 -04:00
parent ef36e901de
commit f0f3994b98
7 changed files with 105 additions and 38 deletions

View File

@@ -348,10 +348,23 @@ void draw_startup_stats() {
pc_rect.offset(60 + 232 * (i / 3) - 9,95 + 45 * (i % 3));
if(univ.party[i].main_status != eMainStatus::ABSENT) {
from_rect = calc_rect(2 * (univ.party[i].which_graphic / 8), univ.party[i].which_graphic % 8);
to_rect = party_to,
to_rect = party_to;
to_rect.offset(pc_rect.left,pc_rect.top);
rect_draw_some_item(pc_gworld,from_rect,to_rect,ul,sf::BlendAlpha);
pic_num_t pic = univ.party[i].which_graphic;
if(pic >= 1000) {
sf::Texture* gw;
graf_pos_ref(gw, from_rect) = spec_scen_g.find_graphic(pic % 1000, pic >= 10000);
rect_draw_some_item(*gw,from_rect,to_rect,ul,sf::BlendAlpha);
} else if(pic >= 100) {
pic -= 100;
// Note that we assume it's a 1x1 graphic.
// PCs can't be larger than that, but we leave it to the scenario designer to avoid assigning larger graphics.
from_rect = get_monster_template_rect(pic, 0, 0);
rect_draw_some_item(monst_gworld[m_pic_index[pic].i / 20],from_rect,to_rect,ul,sf::BlendAlpha);
} else {
from_rect = calc_rect(2 * (pic / 8), pic % 8);
rect_draw_some_item(pc_gworld,from_rect,to_rect,ul,sf::BlendAlpha);
}
style.pointSize = 14;
pc_rect.offset(35,0);

View File

@@ -224,7 +224,6 @@ void play_see_monster_str(unsigned short m, location monst_loc) {
//short mode; // 0 - put pcs in gworld 1 - only rectangle around active pc
void draw_pcs(location center,short mode) {
short i;
rectangle source_rect,active_pc_rect;
location where_draw;
@@ -233,23 +232,41 @@ void draw_pcs(location center,short mode) {
if(!can_draw_pcs)
return;
for(i = 0; i < 6; i++)
// Draw current pc on top
int pcs[6] = {0,1,2,3,4,5};
if(current_pc < 6)
std::swap(pcs[5], pcs[current_pc]);
for(int j = 0; j < 6; j++) {
int i = pcs[j];
if(univ.party[i].main_status == eMainStatus::ALIVE)
if(point_onscreen(center, univ.party[i].combat_pos) &&
(cartoon_happening || party_can_see(univ.party[i].combat_pos) < 6)){
where_draw.x = univ.party[i].combat_pos.x - center.x + 4;
where_draw.y = univ.party[i].combat_pos.y - center.y + 4;
sf::Texture* from_gw;
if(univ.party[i].which_graphic >= 1000) {
bool isParty = univ.party[i].which_graphic >= 10000;
pic_num_t need_pic = univ.party[i].which_graphic % 1000;
pic_num_t pic = univ.party[i].which_graphic;
if(pic >= 1000) {
bool isParty = pic >= 10000;
pic_num_t need_pic = pic % 1000;
if(univ.party[i].direction >= 4)
need_pic++;
if(combat_posing_monster == i)
need_pic += 2;
graf_pos_ref(from_gw, source_rect) = spec_scen_g.find_graphic(need_pic, isParty);
} else if(pic >= 100) {
// Note that we assume it's a 1x1 graphic.
// PCs can't be larger than that, but we leave it to the scenario designer to avoid assigning larger graphics.
pic_num_t need_pic = pic - 100;
int mode = 0;
if(univ.party[current_pc].direction >= 4)
mode++;
if(combat_posing_monster == i)
mode += 10;
source_rect = get_monster_template_rect(need_pic, mode, 0);
from_gw = &monst_gworld[m_pic_index[need_pic].i / 20];
} else {
source_rect = calc_rect(2 * (univ.party[i].which_graphic / 8), univ.party[i].which_graphic % 8);
source_rect = calc_rect(2 * (pic / 8), pic % 8);
if(univ.party[i].direction >= 4)
source_rect.offset(28,0);
if(combat_posing_monster == i)
@@ -271,19 +288,6 @@ void draw_pcs(location center,short mode) {
frame_roundrect(mainPtr, active_pc_rect, 8, sf::Color::Magenta);
}
}
// Draw current pc on top
if(point_onscreen(center, univ.party[current_pc].combat_pos) && univ.party[current_pc].main_status == eMainStatus::ALIVE) {
where_draw.x = univ.party[current_pc].combat_pos.x - center.x + 4;
where_draw.y = univ.party[current_pc].combat_pos.y - center.y + 4;
source_rect = calc_rect(2 * (univ.party[current_pc].which_graphic / 8), univ.party[current_pc].which_graphic % 8);
if(univ.party[current_pc].direction >= 4)
source_rect.offset(28,0);
if(combat_posing_monster == current_pc)
source_rect.offset(0,288);
if(mode == 0)
Draw_Some_Item(pc_gworld, source_rect, terrain_screen_gworld, where_draw, 1, 0);
}
}
@@ -449,14 +453,24 @@ void draw_party_symbol(location center) {
if((univ.party.in_boat < 0) && (univ.party.in_horse < 0)) {
i = first_active_pc();
sf::Texture* from_gw;
if(univ.party[i].which_graphic >= 1000) {
bool isParty = univ.party[i].which_graphic >= 10000;
pic_num_t need_pic = univ.party[i].which_graphic % 1000;
pic_num_t pic = univ.party[i].which_graphic;
if(pic >= 1000) {
bool isParty = pic >= 10000;
pic_num_t need_pic = pic % 1000;
if(univ.party[i].direction >= 4)
need_pic++;
graf_pos_ref(from_gw, source_rect) = spec_scen_g.find_graphic(need_pic, isParty);
} else if(pic >= 100) {
// Note that we assume it's a 1x1 graphic.
// PCs can't be larger than that, but we leave it to the scenario designer to avoid assigning larger graphics.
pic_num_t need_pic = pic - 100;
int mode = 0;
if(univ.party[current_pc].direction >= 4)
mode++;
source_rect = get_monster_template_rect(need_pic, mode, 0);
from_gw = &monst_gworld[m_pic_index[need_pic].i / 20];
} else {
source_rect = calc_rect(2 * (univ.party[current_pc].which_graphic / 8), univ.party[i].which_graphic % 8);
source_rect = calc_rect(2 * (pic / 8), pic % 8);
if(univ.party[current_pc].direction >= 4)
source_rect.offset(28,0);
from_gw = &pc_gworld;
@@ -485,7 +499,6 @@ void draw_party_symbol(location center) {
// Give the position of the monster graphic in the template in memory
//mode; // 0 - left 1 - right +10 - combat mode
rectangle get_monster_template_rect (pic_num_t picture_wanted,short mode,short which_part) {
rectangle store_rect = {0,0,36,28};
short adj = 0;
if(mode >= 10) {

View File

@@ -530,7 +530,10 @@ static void display_pc_info(cDialog& me, const short pc) {
me["skp"].setTextToNum(univ.party[pc].skill_pts);
store = univ.party[pc].level * univ.party[pc].get_tnl();
me["progress"].setTextToNum(store);
dynamic_cast<cPict&>(me["pic"]).setPict(univ.party[pc].which_graphic,PIC_PC); // TODO: Was adding 800 needed, or a relic?
pic_num_t pic = univ.party[pc].which_graphic;
if(pic >= 100 && pic < 1000)
dynamic_cast<cPict&>(me["pic"]).setPict(pic - 100,PIC_MONST);
else dynamic_cast<cPict&>(me["pic"]).setPict(pic,PIC_PC);
// Fight bonuses
for(i = 0; i < 24; i++)

View File

@@ -499,7 +499,10 @@ static void put_item_graphics(cDialog& me, size_t& first_item_shown, short& curr
if(univ.party[i].main_status == eMainStatus::ALIVE) {
std::ostringstream sout;
sout << "pc" << i + 1 << "-g";
dynamic_cast<cPict&>(me[sout.str()]).setPict(univ.party[i].which_graphic);
pic_num_t pic = univ.party[i].which_graphic;
if(pic >= 100 && pic < 1000)
dynamic_cast<cPict&>(me[sout.str()]).setPict(pic - 100,PIC_MONST);
else dynamic_cast<cPict&>(me[sout.str()]).setPict(pic,PIC_PC);
}
}

View File

@@ -5,7 +5,7 @@
#include <list>
#include "boe.global.hpp"
#include "boe.graphutil.hpp"
#include "universe.hpp"
#include "boe.text.hpp"
#include "boe.locutils.hpp"
@@ -55,7 +55,7 @@ extern location center;
extern sf::Texture tiny_obj_gworld,invenbtn_gworld,status_gworld;
extern cCustomGraphics spec_scen_g;
extern sf::Texture pc_gworld;
extern sf::Texture pc_gworld, monst_gworld[NUM_MONST_SHEETS];
extern sf::RenderTexture pc_stats_gworld, item_stats_gworld, text_area_gworld;
extern sf::RenderTexture terrain_screen_gworld;
@@ -505,9 +505,25 @@ void place_item_bottom_buttons() {
item_bottom_button_active[i] = true;
to_rect = item_screen_button_rects[i];
rect_draw_some_item(invenbtn_gworld, but_from_rect, item_stats_gworld, to_rect, sf::BlendAlpha);
pc_from_rect = calc_rect(2 * (univ.party[i].which_graphic / 8), univ.party[i].which_graphic % 8);
pic_num_t pic = univ.party[i].which_graphic;
sf::Texture* from_gw;
if(pic >= 1000) {
bool isParty = pic >= 10000;
pic_num_t need_pic = pic % 1000;
graf_pos_ref(from_gw, pc_from_rect) = spec_scen_g.find_graphic(need_pic, isParty);
} else if(pic >= 100) {
// Note that we assume it's a 1x1 graphic.
// PCs can't be larger than that, but we leave it to the scenario designer to avoid assigning larger graphics.
pic_num_t need_pic = pic - 100;
int mode = 0;
pc_from_rect = get_monster_template_rect(need_pic, mode, 0);
from_gw = &monst_gworld[m_pic_index[need_pic].i / 20];
} else {
pc_from_rect = calc_rect(2 * (pic / 8), pic % 8);
from_gw = &pc_gworld;
}
to_rect.inset(2,2);
rect_draw_some_item(pc_gworld, pc_from_rect, item_stats_gworld, to_rect, sf::BlendAlpha);
rect_draw_some_item(*from_gw, pc_from_rect, item_stats_gworld, to_rect, sf::BlendAlpha);
}
else item_bottom_button_active[i] = false;
}

View File

@@ -1018,7 +1018,7 @@ void cUniverse::exportGraphics() {
// The party sheet can contain the following types of graphics:
// - Monster graphics for monsters summoned by custom items or captured in the party's soul crystal
// - Item graphics for custom items that the party has in their possession or in their saved item rectangles
// - Custom PC graphics - TODO: Rendering support for custom PC graphics
// - Custom PC graphics
// TODO: Missile graphics for custom monsters
// So basically, almost all the graphics are linked to items.
used_graphics.clear();

View File

@@ -206,6 +206,10 @@ void Set_up_win () {
dlogpics_gworld.loadFromImage(*ResMgr::get<ImageRsrc>("dlogpics"));
buttons_gworld.loadFromImage(*ResMgr::get<ImageRsrc>("pcedbuttons"));
pc_gworld.loadFromImage(*ResMgr::get<ImageRsrc>("pcs"));
for(int i = 0; i < NUM_MONST_SHEETS; i++) {
std::string id = "monst" + std::to_string(i + 1);
monst_gworld[i].loadFromImage(*ResMgr::get<ImageRsrc>(id));
}
}
static void draw_main_screen();
@@ -357,7 +361,7 @@ void draw_items() {
//short clear_first; // 1 - redraw over what's already there, 0 - don't redraw over
void display_party() {
short i,k,string_num, cur_rect=0;
rectangle from_base = {0,0,36,28},from_rect,no_party_rect,temp_rect;
rectangle from_rect,no_party_rect,temp_rect;
TextStyle style;
style.lineHeight = 10;
@@ -386,10 +390,25 @@ void display_party() {
// pc_record_type is the records that contains chaarcters
// main_status determins 0 - not exist, 1 - alive, OK, 2 - dead, 3 - stoned, 4 - dust
if(univ.party[i].main_status != eMainStatus::ABSENT) { // PC exists?
from_rect = from_base;
// draw PC graphic
from_rect.offset(56 * (univ.party[i].which_graphic / 8),36 * (univ.party[i].which_graphic % 8));
rect_draw_some_item(pc_gworld,from_rect,mainPtr,pc_area_buttons[i][1],sf::BlendAlpha);
pic_num_t pic = univ.party[i].which_graphic;
sf::Texture* from_gw;
if(pic >= 1000) {
bool isParty = pic >= 10000;
pic_num_t need_pic = pic % 1000;
graf_pos_ref(from_gw, from_rect) = spec_scen_g.find_graphic(need_pic, isParty);
} else if(pic >= 100) {
// Note that we assume it's a 1x1 graphic.
// PCs can't be larger than that, but we leave it to the scenario designer to avoid assigning larger graphics.
pic_num_t need_pic = pic - 100;
pic_num_t picture_wanted = m_pic_index[need_pic].i % 20;
from_rect = calc_rect(2 * (picture_wanted / 10), picture_wanted % 10);
from_gw = &monst_gworld[m_pic_index[need_pic].i / 20];
} else {
from_rect = calc_rect(2 * (pic / 8), pic % 8);
from_gw = &pc_gworld;
}
rect_draw_some_item(*from_gw,from_rect,mainPtr,pc_area_buttons[i][1],sf::BlendAlpha);
//frame_dlog_rect(GetWindowPort(mainPtr),pc_area_buttons[i][1],0);
// draw name