From: Clyne Sullivan Date: Mon, 21 Mar 2016 12:49:48 +0000 (-0400) Subject: cleaning up ui code X-Git-Url: https://code.bitgloo.com/?a=commitdiff_plain;h=afdbe5de31c9ae1009d36710eb2b1c31ec44a9f5;p=clyne%2Fgamedev.git cleaning up ui code --- afdbe5de31c9ae1009d36710eb2b1c31ec44a9f5 diff --cc Changelog index fbef63e,05ac163..546ded4 --- a/Changelog +++ b/Changelog @@@ -779,13 -779,3 +779,22 @@@ - planned ahead ~ set finish date for game engine: 3/31 + +3/17/2016: +========== + + - cleaned up ui stuff (more std::strings) + - worlds load adjacent worlds for faster loading + - fixed world fall-through error + - (WIP) made ui options dynamic (boxes can have 'infinite' options) + - can scroll through inventory with mouse wheel + - added text transparency support ++ ++3/18/2016: ++========== ++ ++ - worked on keeping multiple-sizes fonts in memory (importantText lag) ++ - c++'d more ui stuff ++ - game can run on *BSD systems.. ++ - fixed abort bug on exit ++ - added light that follows player diff --cc main.cpp index acbc4f6,e7494a9..0b3984e --- a/main.cpp +++ b/main.cpp @@@ -417,9 -415,8 +417,8 @@@ int main(int argc, char *argv[]) //currentWorld->mob.back()->followee = player; gameRunning = true; -- - while(gameRunning)mainLoop(); + while ( gameRunning ) + mainLoop(); /************************** **** CLOSE PROGRAM **** diff --cc src/ui.cpp index 9ed941d,245f1d7..458e797 --- a/src/ui.cpp +++ b/src/ui.cpp @@@ -38,30 -38,23 +38,26 @@@ extern unsigned int tickCount static FT_Library ftl; static FT_Face ftf; --static GLuint ftex[93]; - /*static vec2 ftexwh[93]; -static vec2 ftexwh[93]; --static vec2 ftexbl[93]; - static vec2 ftexad[93];*/ -static vec2 ftexad[93]; + +typedef struct { + vec2 wh; + vec2 bl; + vec2 ad; +} FT_Info; + - static FT_Info ftdat[93]; ++static std::vector ftdat ( 93, { { 0, 0 }, { 0, 0 }, { 0, 0 } } ); ++static std::vector ftex ( 93, 0 ); - static unsigned char fontColor[3] = {255,255,255}; + static unsigned char fontColor[4] = {255,255,255,255}; /* * Variables for dialog boxes / options. --*/ ++ */ - static std::string dialogBoxText; -static char dialogBoxText[512]; -static char *dialogOptText[4]; -static float merchAOptLoc[2][3]; -static float dialogOptLoc[4][3]; -static unsigned char dialogOptCount = 0; -static bool typeOutDone = true; +static std::vector> dialogOptText; - static float merchAOptLoc[2][3]; - static float dialogOptLoc[4][3]; - static bool typeOutDone = true; ++static std::string dialogBoxText; ++static vec3 merchArrowLoc[2]; ++static bool typeOutDone = true; /* * Menu-related objects @@@ -76,12 -69,12 +72,12 @@@ static Mix_Chunk *dialogClick extern void mainLoop(void); /* -- * Toggled by pressing 'q', disables some controls when true. --*/ ++ * Fade effect flags ++ */ bool fadeEnable = false; --bool fadeWhite = false; --bool fadeFast = false; ++bool fadeWhite = false; ++bool fadeFast = false; unsigned int fadeIntensity = 0; bool inBattle = false; @@@ -161,8 -155,8 +158,7 @@@ namespace ui std::cout<<"Error! Couldn't initialize freetype."<glyph->bitmap.width * ftf->glyph->bitmap.rows * 4]; - for(j=0;jglyph->bitmap.width*ftf->glyph->bitmap.rows;j++){ - buf[j*4 ]=255;//fontColor[0]; - buf[j*4+1]=255;//fontColor[1]; - buf[j*4+2]=255;//fontColor[2]; - buf[j*4+3]=ftf->glyph->bitmap.buffer[j] ? 255 : 0; - //buf[j*4+3]=ftf->glyph->bitmap.buffer[j]; - } + std::vector buf ( ftf->glyph->bitmap.width * ftf->glyph->bitmap.rows, 0 ); - ftexwh[i-33].x=ftf->glyph->bitmap.width; - ftexwh[i-33].y=ftf->glyph->bitmap.rows; - ftexbl[i-33].x=ftf->glyph->bitmap_left; - ftexbl[i-33].y=ftf->glyph->bitmap_top; - ftexad[i-33].x=ftf->glyph->advance.x>>6; - ftexad[i-33].y=ftf->glyph->advance.y>>6; + for( j = 0; j < buf.size(); j++ ) + buf[j] = 0x00FFFFFF | (ftf->glyph->bitmap.buffer[j] ? (0xFF << 24) : 0); - glTexImage2D(GL_TEXTURE_2D,0,GL_RGBA,ftf->glyph->bitmap.width,ftf->glyph->bitmap.rows,0,GL_RGBA,GL_UNSIGNED_BYTE,buf); + ftdat[i-33].wh.x=ftf->glyph->bitmap.width; + ftdat[i-33].wh.y=ftf->glyph->bitmap.rows; + ftdat[i-33].bl.x=ftf->glyph->bitmap_left; + ftdat[i-33].bl.y=ftf->glyph->bitmap_top; + ftdat[i-33].ad.x=ftf->glyph->advance.x>>6; + ftdat[i-33].ad.y=ftf->glyph->advance.y>>6; - delete[] buf; //free(buf); + glTexImage2D(GL_TEXTURE_2D,0,GL_RGBA,ftf->glyph->bitmap.width,ftf->glyph->bitmap.rows,0,GL_RGBA,GL_UNSIGNED_BYTE,buf.data()); } + mtx.unlock(); } /* @@@ -442,48 -460,78 +447,47 @@@ /* * Handle the formatted string, printing it to the buffer. - */ + */ va_start(args,str); - vsnprintf(buf,512,str,args); + vsnprintf(buf.get(),512,str,args); va_end(args); - /* - * Draw the string, free resources, return the width of the string. - */ - - width=putString(x,y,buf); - delete[] buf; //free(buf); - - return width; + // draw the string and return the width + return putString( x, y, buf.get() ); } - void dialogBox(const char *name,const char *opt,bool passive,const char *text,...){ - textWrapLimit = 110; + + void dialogBox( const char *name, const char *opt, bool passive, const char *text, ... ) { va_list dialogArgs; - unsigned int len; - char *sopt,*soptbuf; + std::unique_ptr printfbuf (new char[512]); + textWrapLimit = 110; dialogPassive = passive; - /* - * Set up the text buffer. - */ - - memset(dialogBoxText,0,512); - - /* - * Get the text ready for rendering. - */ - - len=strlen(name); - strcpy(dialogBoxText ,name); - strcpy(dialogBoxText+len,": "); - len+=2; + // reset & add speaker prefix + dialogBoxText.clear(); + dialogBoxText = (std::string)name + ": "; + // handle the formatted string va_start(dialogArgs,text); - vsnprintf(dialogBoxText+len,512-len,text,dialogArgs); + vsnprintf(printfbuf.get(),512,text,dialogArgs); va_end(dialogArgs); + dialogBoxText += printfbuf.get(); - /* - * Set up option text. - */ - - while(dialogOptCount){ - if(dialogOptText[dialogOptCount]){ - delete[] dialogOptText[dialogOptCount]; //free(dialogOptText[dialogOptCount]); - dialogOptText[dialogOptCount] = NULL; - } - dialogOptCount--; - }; + // setup option text + dialogOptText.clear(); - dialogOptCount = 0; dialogOptChosen = 0; -- memset(&dialogOptLoc,0,sizeof(float)*12); - if(opt != NULL){ + if ( opt ) { + std::string soptbuf = opt; + char *sopt = strtok(&soptbuf[0], ":"); - soptbuf = new char[strlen(opt)+1]; - strcpy(soptbuf,opt); - - sopt=strtok(soptbuf,":"); - while(sopt != NULL){ - dialogOptText[dialogOptCount] = new char[strlen(sopt)+1]; //(char *)malloc(strlen(sopt)); - strcpy(dialogOptText[dialogOptCount++],sopt); - sopt=strtok(NULL,":"); + // cycle through options + while(sopt){ + dialogOptText.push_back(std::make_pair((std::string)sopt, vec3 {0,0,0}) ); + sopt = strtok(NULL,":"); } - - delete[] soptbuf; - } /* @@@ -510,19 -557,30 +514,19 @@@ merchTrade = trade; // clear the buffer - memset(dialogBoxText, '\0', 512); + dialogBoxText.clear(); + dialogBoxText = (std::string)name + ": "; - // create the string - strcpy(dialogBoxText, name); - strcat(dialogBoxText, ": "); - - len=strlen(dialogBoxText); va_start(dialogArgs,text); - vsnprintf(dialogBoxText + len, 512 - len, text, dialogArgs); + vsnprintf(printfbuf.get(),512,text,dialogArgs); va_end(dialogArgs); + dialogBoxText += printfbuf.get(); // free old option text - while(dialogOptCount){ - if(dialogOptText[dialogOptCount]){ - delete[] dialogOptText[dialogOptCount]; - dialogOptText[dialogOptCount] = NULL; - } - - dialogOptCount--; - }; + dialogOptText.clear(); dialogOptChosen = 0; - memset(&dialogOptLoc, 0, sizeof(float) * 12); + merchOptChosen = 0; - memset(&dialogOptLoc, 0, sizeof(float) * 12); // handle options if desired if(opt){ @@@ -709,26 -759,26 +714,26 @@@ glEnd(); glDisable(GL_TEXTURE_2D); -- merchAOptLoc[0][0] = offset.x - (SCREEN_WIDTH / 8.5) - 16; -- merchAOptLoc[1][0] = offset.x + (SCREEN_WIDTH / 8.5) + 16; -- merchAOptLoc[0][1] = offset.y + (SCREEN_HEIGHT *.2); -- merchAOptLoc[1][1] = offset.y + (SCREEN_HEIGHT *.2); -- merchAOptLoc[0][2] = offset.x - (SCREEN_WIDTH / 8.5); -- merchAOptLoc[1][2] = offset.x + (SCREEN_WIDTH / 8.5); ++ merchArrowLoc[0].x = offset.x - (SCREEN_WIDTH / 8.5) - 16; ++ merchArrowLoc[1].x = offset.x + (SCREEN_WIDTH / 8.5) + 16; ++ merchArrowLoc[0].y = offset.y + (SCREEN_HEIGHT *.2); ++ merchArrowLoc[1].y = offset.y + (SCREEN_HEIGHT *.2); ++ merchArrowLoc[0].z = offset.x - (SCREEN_WIDTH / 8.5); ++ merchArrowLoc[1].z = offset.x + (SCREEN_WIDTH / 8.5); for(i = 0; i < 2; i++){ -- if(((merchAOptLoc[i][0] < merchAOptLoc[i][2]) ? -- (mouse.x > merchAOptLoc[i][0] && mouse.x < merchAOptLoc[i][2]) : -- (mouse.x < merchAOptLoc[i][0] && mouse.x > merchAOptLoc[i][2])) && -- mouse.y > merchAOptLoc[i][1] - 8 && mouse.y < merchAOptLoc[i][1] + 8){ ++ if(((merchArrowLoc[i].x < merchArrowLoc[i].z) ? ++ (mouse.x > merchArrowLoc[i].x && mouse.x < merchArrowLoc[i].z) : ++ (mouse.x < merchArrowLoc[i].x && mouse.x > merchArrowLoc[i].z) ) && ++ mouse.y > merchArrowLoc[i].y - 8 && mouse.y < merchArrowLoc[i].y + 8 ) { glColor3ub(255,255, 0); }else{ glColor3ub(255,255,255); } glBegin(GL_TRIANGLES); -- glVertex2f(merchAOptLoc[i][0],merchAOptLoc[i][1]); -- glVertex2f(merchAOptLoc[i][2],merchAOptLoc[i][1]-8); -- glVertex2f(merchAOptLoc[i][2],merchAOptLoc[i][1]+8); ++ glVertex2f(merchArrowLoc[i].x,merchArrowLoc[i].y); ++ glVertex2f(merchArrowLoc[i].z,merchArrowLoc[i].y-8); ++ glVertex2f(merchArrowLoc[i].z,merchArrowLoc[i].y+8); glEnd(); } @@@ -738,18 -788,18 +743,18 @@@ setFontColor(255, 255, 255); // draw option - tmp = putStringCentered(offset.x, dialogOptLoc[i][1], dialogOptText[i].first); - tmp = putStringCentered(offset.x, dialogOptLoc[i][1], dialogOptText[i]); ++ tmp = putStringCentered(offset.x, dialogOptText[i].second.y, dialogOptText[i].first); // get coordinate information on option -- dialogOptLoc[i][2] = offset.x + tmp; -- dialogOptLoc[i][0] = offset.x - tmp; -- dialogOptLoc[i][1] = y - SCREEN_HEIGHT / 2 - (fontSize + HLINE) * (i + 1); ++ dialogOptText[i].second.z = offset.x + tmp; ++ dialogOptText[i].second.x = offset.x - tmp; ++ dialogOptText[i].second.y = y - SCREEN_HEIGHT / 2 - (fontSize + HLINE) * (i + 1); // make text yellow if the mouse hovers over the text -- if(mouse.x > dialogOptLoc[i][0] && mouse.x < dialogOptLoc[i][2] && -- mouse.y > dialogOptLoc[i][1] && mouse.y < dialogOptLoc[i][1] + 16 ){ ++ if(mouse.x > dialogOptText[i].second.x && mouse.x < dialogOptText[i].second.z && ++ mouse.y > dialogOptText[i].second.y && mouse.y < dialogOptText[i].second.y + 16 ){ setFontColor(255, 255, 0); - putStringCentered(offset.x, dialogOptLoc[i][1], dialogOptText[i].first); - putStringCentered(offset.x, dialogOptLoc[i][1], dialogOptText[i]); ++ putStringCentered(offset.x, dialogOptText[i].second.y, dialogOptText[i].first); } } @@@ -777,18 -827,18 +782,18 @@@ putString(x+HLINE,y-fontSize-HLINE,rtext); - for(i=0;i dialogOptLoc[i][0] && -- mouse.x < dialogOptLoc[i][2] && -- mouse.y > dialogOptLoc[i][1] && -- mouse.y < dialogOptLoc[i][1] + 16 ){ // fontSize ++ tmp = putStringCentered(offset.x,dialogOptText[i].second.y,dialogOptText[i].first); ++ dialogOptText[i].second.z = offset.x + tmp; ++ dialogOptText[i].second.x = offset.x - tmp; ++ dialogOptText[i].second.y = y - SCREEN_HEIGHT / 4 + (fontSize + HLINE) * (i + 1); ++ if(mouse.x > dialogOptText[i].second.x && ++ mouse.x < dialogOptText[i].second.z && ++ mouse.y > dialogOptText[i].second.y && ++ mouse.y < dialogOptText[i].second.y + 16 ){ // fontSize setFontColor(255,255,0); - putStringCentered(offset.x,dialogOptLoc[i][1],dialogOptText[i].first); - putStringCentered(offset.x,dialogOptLoc[i][1],dialogOptText[i]); ++ putStringCentered(offset.x,dialogOptText[i].second.y,dialogOptText[i].first); } } setFontColor(255,255,255); @@@ -1185,17 -1252,34 +1207,35 @@@ typeOutDone = true; return; } - for(i=0;i dialogOptLoc[i][0] && - mouse.x < dialogOptLoc[i][2] && - mouse.y > dialogOptLoc[i][1] && - mouse.y < dialogOptLoc[i][1] + 16 ){ // fontSize + + for(i=0;i dialogOptLoc[i][0] && - mouse.x < dialogOptLoc[i][2] && - mouse.y > dialogOptLoc[i][1] && - mouse.y < dialogOptLoc[i][1] + 16 ){ // fontSize ++ if(mouse.x > dialogOptText[i].second.x && ++ mouse.x < dialogOptText[i].second.z && ++ mouse.y > dialogOptText[i].second.y && ++ mouse.y < dialogOptText[i].second.y + 16 ){ // fontSize dialogOptChosen = i + 1; - goto DONE; + goto EXIT; + } + } + if(dialogMerchant){ + for(i=0;i<2;i++){ - if(((merchAOptLoc[i][0] < merchAOptLoc[i][2]) ? - (mouse.x > merchAOptLoc[i][0] && mouse.x < merchAOptLoc[i][2]) : - (mouse.x < merchAOptLoc[i][0] && mouse.x > merchAOptLoc[i][2])) && - mouse.y > merchAOptLoc[i][1] - 8 && mouse.y < merchAOptLoc[i][1] + 8){ // fontSize ++ if(((merchArrowLoc[i].x < merchArrowLoc[i].z) ? ++ (mouse.x > merchArrowLoc[i].x && mouse.x < merchArrowLoc[i].z) : ++ (mouse.x < merchArrowLoc[i].x && mouse.x > merchArrowLoc[i].z) && ++ mouse.y > merchArrowLoc[i].y - 8 && mouse.y < merchArrowLoc[i].y + 8)){ + merchOptChosen = i + 1; + goto EXIT; + } } } - DONE: + + - EXIT: ++EXIT: + //if(!dialogMerchant)closeBox(); + dialogBoxExists = false; + dialogMerchant = false; + + //DONE: // handle important text if(dialogImportant){ diff --cc src/world.cpp index 2c7e06d,b1eb12e..1a7322f --- a/src/world.cpp +++ b/src/world.cpp @@@ -783,9 -783,9 +782,10 @@@ singleDetect( Entity *e /* * Handle gravity if the entity is above the line. - */ + */ + + } else { + - }else{ if(e->type == STRUCTURET && e->loc.y > 2000){ e->loc.y = worldData[i].groundHeight; e->vel.y = 0;