static void JKG_DrawFiringMode( menuDef_t *menuHUD ) { // Menu ain't used...yet. float x, y, w; char *text; int textWidth; weaponData_t *wp = BG_GetWeaponDataByIndex(cg.predictedPlayerState.weaponId); unsigned char firingMode = cg.predictedPlayerState.firingMode; vec4_t opacity; if( cg.predictedPlayerState.weapon == WP_SABER ) { // Sabers don't have firing modes, loel return; } if( cg.jkg_WHUDOpacity < 1.0f ) { MAKERGBA(opacity, 1,1,1, cg.jkg_WHUDOpacity); } else { MAKERGBA(opacity, 1,1,1, cg.jkg_HUDOpacity); } if(!wp) { return; } if(wp->numFiringModes <= 1) { return; } #ifndef NO_SP_STYLE_AMMO if(cg.lastFiringModeTime > cg.time) { vec4_t colorCopy = { 0.2, 0.72, 0.86, 1 }; Q_RGBCopy(&opacity, colorCopy); } #endif // Set us some basic defaults (for now. these will be replaced by the jkg_hud.menu) x = 500.0f; y = 448.0f; w = 120.0f; // Right. Now let's get the display string. // FIXME: Localize this text --eez text = va("Mode: %s", CG_GetStringEdString2(wp->visuals.visualFireModes[firingMode].displayName)); if(!text || !text[0]) { // ok maybe this isn't realistic at all but i'm paranoid return; } textWidth = trap_R_Font_StrLenPixels(text, cgDC.Assets.qhSmall3Font, 0.4f); //trap_R_Font_DrawString(focusItem->window.rect.x + ((focusItem->window.rect.w/2) - (width/2)), focusItem->window.rect.y, text, opacity, cgDC.Assets.qhSmall3Font, -1, 0.5f); trap_R_Font_DrawString(x + ((w/2) - (textWidth/2)), y, text, opacity, cgDC.Assets.qhSmall3Font, -1, 0.4f); }
static void CG_DrawBottomRightHUD ( menuDef_t *menuHUD, centity_t *cent, vec4_t opacity ) { itemDef_t *focusItem; if (!menuHUD) { return; } focusItem = Menu_FindItemByName(menuHUD, "framebg"); if (focusItem) { vec4_t tmp; MAKERGBA(tmp,0,0,0, cg.jkg_HUDOpacity); trap_R_SetColor( tmp ); CG_DrawPic( focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w, focusItem->window.rect.h, cgs.media.whiteShader ); } // Draw the bars (temp) CG_DrawJetpackCloak(menuHUD); focusItem = Menu_FindItemByName(menuHUD, "frame"); if (focusItem) { trap_R_SetColor(opacity); CG_DrawPic( focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w, focusItem->window.rect.h, focusItem->window.background ); } // Draw ammo tics or saber style if ( cent->currentState.weapon == WP_SABER ) { CG_DrawSaberStyle(cent,menuHUD); } else { CG_DrawAmmo(cent,menuHUD); } }
void JKG_Slice_DrawGridSummary(int slot, float x, float y, float w, float h) { static const vec4_t topcol = {.2, 1, .2, 0.2f}; static const vec4_t botcol = {1, 0.2, 0.2, 0.2f}; int orientation = (slot >> 3) & 1; // 0 = Columns, 1 = Rows int index = slot & 7; vec4_t color; const char *text; float w2; if ((orientation == 0 && index >= sliceData.width) || (orientation == 1 && index >= sliceData.height) ) { UI_DrawRect(x, y, w, h, disabled); return; } else { UI_FillRect(x, y, w, h/2, topcol); UI_FillRect(x, y + (0.5f * h), w, h/2, botcol); if (sliceData.inputState == INPUTSTATE_AWAITINGLINE) { float phase = 0.7f + sin((float)trap->Milliseconds() / 150.0f) * 0.1f; MAKERGBA(color, phase, phase, phase, 1.0f); UI_DrawRect(x, y, w, h, color); } else { UI_DrawRect(x, y, w, h, black); } } if (sliceData.summariesKnown) { text = va("%i", sliceData.summaries[slot].value); w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y-1, 0.4f, const_cast<float *>(white), text, 0, 0, 0, 0 ); text = va("%i", sliceData.summaries[slot].alarms); w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y+(h*0.5f)-1, 0.4f, const_cast<float *>(white), text, 0, 0, 0, 0 ); } else { text = "?"; w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y-1, 0.4f, const_cast<float *>(white), text, 0, 0, 0, 0 ); w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y+(h*0.5f)-1, 0.4f, const_cast<float *>(white), text, 0, 0, 0, 0 ); } }
/* ================ CG_DrawArmor ================ */ static void CG_DrawArmor( menuDef_t *menuHUD ) { //vec4_t calcColor; vec4_t glowColor; playerState_t *ps; int armor, maxArmor; itemDef_t *focusItem; double percentage, factor ; //quarterArmor; //int i,currValue,inc; const char *text; int x; static double fcurrent = 0; vec4_t fadecolor = {1, 1, 1, 0.5f}; static vec4_t draincolor = {1, 0.4f, 0.4f, 1}; static vec4_t fillcolor = {0.4f, 1, 0.4f, 1}; vec4_t opacity; int state = 0; MAKERGBA(opacity, 1, 1, 1, cg.jkg_HUDOpacity); //ps = &cg.snap->ps; ps = &cg.predictedPlayerState; // Can we find the menu? if (!menuHUD) { return; } armor = ps->stats[STAT_ARMOR]; maxArmor = ps->stats[STAT_MAX_ARMOR]; // TEST: just render the whole thing for now, we'll fix it later focusItem = Menu_FindItemByName(menuHUD, "shieldbar"); if (focusItem) { percentage = (double)armor / (double)maxArmor; if (percentage > 1) { percentage = 1; } else if (percentage < 0) { percentage = 0; } factor = /*0.6171875f **/ percentage /*+ 0.34375f*/; /*if(factor > 0.95f) { factor = 1.0f; //eezstreet - mega hack }*/ // Fade our fcurrent to this factor if (fcurrent < factor) { // Raise it fcurrent += (cg.frameDelta * .0003); // Go up 30% per second if (fcurrent > factor) { // We passed it fcurrent = factor; } } else if (fcurrent > factor) { // Lower it fcurrent -= (cg.frameDelta * .0003); // Go up 30% per second if (fcurrent < factor) { fcurrent = factor; } } if (fcurrent != 0) { if (fcurrent < factor) { state = 1; // We're filling up, draw up to fcurrent solid, and up to factor translucent trap_R_SetColor(opacity); trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * fcurrent, focusItem->window.rect.h, 0, 0, fcurrent, 1, focusItem->window.background); fadecolor[3] *= cg.jkg_HUDOpacity; trap_R_SetColor(fadecolor); trap_R_DrawStretchPic(focusItem->window.rect.x + focusItem->window.rect.w * fcurrent, focusItem->window.rect.y, focusItem->window.rect.w * (factor - fcurrent), focusItem->window.rect.h, fcurrent, 0, factor, 1, focusItem->window.background); trap_R_SetColor(opacity); } else if (fcurrent > factor) { state = 2; // We're draining, draw up to factor solid, and up to fcurrent translucent trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * factor, focusItem->window.rect.h, 0, 0, factor, 1, focusItem->window.background); fadecolor[3] *= cg.jkg_HUDOpacity; trap_R_SetColor(fadecolor); trap_R_DrawStretchPic(focusItem->window.rect.x + focusItem->window.rect.w * factor, focusItem->window.rect.y, focusItem->window.rect.w * (fcurrent - factor), focusItem->window.rect.h, factor, 0, fcurrent, 1, focusItem->window.background); trap_R_SetColor(opacity); } else { state = 0; // Just solid trap_R_SetColor(opacity); trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * factor, focusItem->window.rect.h, 0, 0, factor, 1, focusItem->window.background); } } } if (!armor) { return; } focusItem = Menu_FindItemByName(menuHUD, "shieldtext"); if (focusItem) { if (state == 1) { VectorCopy4(fillcolor, glowColor); } else if (state == 2) { VectorCopy4(draincolor, glowColor); } else { VectorCopy4(colorWhite, glowColor); } glowColor[3] *= cg.jkg_HUDOpacity; // Center and draw the text, positioning will be finetuned later on :P text = va("%i / %i", armor, maxArmor); x = ((focusItem->window.rect.w/2) - (trap_R_Font_StrLenPixels(text, cgs.media.hudfont1, 0.6f) / 2)) + focusItem->window.rect.x; trap_R_Font_DrawString( x, focusItem->window.rect.y, text, glowColor, cgs.media.hudfont1, -1, 0.6f); trap_R_SetColor(NULL); } }
/* ================ CG_DrawHealth ================ */ static void CG_DrawHealth( menuDef_t *menuHUD ) { vec4_t glowColor; playerState_t *ps; int healthAmt, maxAmt; //int i,currValue,inc; double percentage, factor; itemDef_t *focusItem; const char *text; int x; static double fcurrent = 0; vec4_t fadecolor = {1, 1, 1, 0.5f}; static vec4_t draincolor = {1, 0.4f, 0.4f, 1}; static vec4_t fillcolor = {0.4f, 1, 0.4f, 1}; vec4_t opacity; int state = 0; MAKERGBA(opacity, 1, 1, 1, cg.jkg_HUDOpacity); // Can we find the menu? if (!menuHUD) { return; } ps = &cg.snap->ps; // What's the health? healthAmt = ps->stats[STAT_HEALTH]; maxAmt = ps->stats[STAT_MAX_HEALTH]; //if (healthAmt > ps->stats[STAT_MAX_HEALTH]) //{ // healthAmt = ps->stats[STAT_MAX_HEALTH]; //} focusItem = Menu_FindItemByName(menuHUD, "healthbar"); if (focusItem) { percentage = (double)healthAmt / (double)maxAmt; if (percentage > 1) { percentage = 1; } else if (percentage < 0) { percentage = 0; } factor = /*0.62109375f **/ percentage /*+ 0.330078125f*/; /*if(factor > 0.95f) { factor = 1.0f; //eezstreet - mega hack }*/ if (fcurrent < factor) { // Raise it fcurrent += (cg.frameDelta * .0003); // Go up 30% per second if (fcurrent > factor) { // We passed it fcurrent = factor; } } else if (fcurrent > factor) { // Lower it fcurrent -= (cg.frameDelta * .0003); // Go up 30% per second if (fcurrent < factor) { fcurrent = factor; } } else { //Stay the same } if (fcurrent != 0) { if (fcurrent < factor) { state = 1; // We're filling up, draw up to fcurrent solid, and up to factor translucent trap_R_SetColor(opacity); trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * fcurrent, focusItem->window.rect.h, 0, 0, fcurrent, 1, focusItem->window.background); fadecolor[3] *= cg.jkg_HUDOpacity; trap_R_SetColor(fadecolor); trap_R_DrawStretchPic(focusItem->window.rect.x + focusItem->window.rect.w * fcurrent, focusItem->window.rect.y, focusItem->window.rect.w * (factor - fcurrent), focusItem->window.rect.h, fcurrent, 0, factor, 1, focusItem->window.background); trap_R_SetColor(NULL); } else if (fcurrent > factor) { state = 2; // We're draining, draw up to factor solid, and up to fcurrent translucent trap_R_SetColor(opacity); trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * factor, focusItem->window.rect.h, 0, 0, factor, 1, focusItem->window.background); fadecolor[3] *= cg.jkg_HUDOpacity; trap_R_SetColor(fadecolor); trap_R_DrawStretchPic(focusItem->window.rect.x + focusItem->window.rect.w * factor, focusItem->window.rect.y, focusItem->window.rect.w * (fcurrent - factor), focusItem->window.rect.h, factor, 0, fcurrent, 1, focusItem->window.background); trap_R_SetColor(NULL); } else { state = 0; // Just solid trap_R_SetColor(opacity); trap_R_DrawStretchPic(focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * factor, focusItem->window.rect.h, 0, 0, factor, 1, focusItem->window.background); } } } focusItem = Menu_FindItemByName(menuHUD, "healthtext"); if (focusItem) { // Center and draw the text, apply glow if needed if (state == 1) { VectorCopy4(fillcolor, glowColor); } else if (state == 2) { VectorCopy4(draincolor, glowColor); } else { VectorCopy4(colorWhite, glowColor); if (healthAmt < 25) { // Glow the text from red to white float fade = 0.5f + cos((float)cg.time/250) *.5; glowColor[1] = glowColor[2] = fade; } } glowColor[3] *= cg.jkg_HUDOpacity; text = va("%i / %i", healthAmt, maxAmt); x = ((focusItem->window.rect.w/2) - (trap_R_Font_StrLenPixels(text, cgs.media.hudfont1, 0.6f) / 2)) + focusItem->window.rect.x; trap_R_Font_DrawString( x, focusItem->window.rect.y, text, glowColor, cgs.media.hudfont1, -1, 0.6f); trap_R_SetColor(NULL); } }
/* ================ CG_DrawForcePower ================ */ static void CG_DrawForcePower( menuDef_t *menuHUD ) { // This goes in the lower bar on the hud const int maxForcePower = 100; vec4_t calcColor; float percent; qboolean flash=qfalse; itemDef_t *focusItem; vec4_t opacity; MAKERGBA( opacity, 1, 1, 1, 1*cg.jkg_HUDOpacity ); if (!menuHUD) { return; } // Make the hud flash by setting forceHUDTotalFlashTime above cg.time if (cg.forceHUDTotalFlashTime > cg.time ) { flash = qtrue; if (cg.forceHUDNextFlashTime < cg.time) { cg.forceHUDNextFlashTime = cg.time + 400; trap_S_StartSound (NULL, 0, CHAN_LOCAL, cgs.media.noforceSound ); if (cg.forceHUDActive) { cg.forceHUDActive = qfalse; } else { cg.forceHUDActive = qtrue; } } } else // turn HUD back on if it had just finished flashing time. { cg.forceHUDNextFlashTime = 0; cg.forceHUDActive = qtrue; } // if (!cg.forceHUDActive) // { // return; // } if (flash) { MAKERGBA(calcColor, 1, 1, 1, 0.6f*cg.jkg_HUDOpacity); } else { MAKERGBA(calcColor, 1, 1, 1, 1*cg.jkg_HUDOpacity); } /*focusItem = Menu_FindItemByName(menuHUD, "bar2ico"); if (focusItem) { calcColor[3] *= cg.jkg_HUDOpacity; trap_R_SetColor( calcColor ); CG_DrawPic( focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w, focusItem->window.rect.h, trap_R_RegisterShader("gfx/jkghud/ico_stamina.png") // TODO: Precache this ); }*/ // Work out the bar now percent = (float)cg.predictedPlayerState.forcePower / (float)maxForcePower; //percent *= 0.75f; // Range of the bar is 0 to 0.75f focusItem = Menu_FindItemByName(menuHUD, "staminabar"); if (focusItem) { trap_R_SetColor( opacity ); trap_R_DrawStretchPic( focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w * percent, focusItem->window.rect.h, 0, 0, percent, 1, focusItem->window.background ); } { char *Force = va("%i / %i", cg.predictedPlayerState.forcePower, maxForcePower); trap_R_Font_DrawString( focusItem->window.rect.x + (focusItem->window.rect.w / 2) - (trap_R_Font_StrLenPixels(Force, 1, 0.4)/2), focusItem->window.rect.y - 2/* + (trap_R_Font_HeightPixels(1, 1.0)*0.4)*/, Force, colorWhite, 1, -1, 0.4f ); } }
/* ================ CG_DrawAmmo ================ */ static void CG_DrawAmmo( centity_t *cent,menuDef_t *menuHUD) { playerState_t *ps; int ammo; itemDef_t *focusItem; float width; const char *text; vec4_t opacity; const weaponInfo_t *weaponInfo; if( cg.jkg_WHUDOpacity < 1.0f ) { MAKERGBA(opacity, 1,1,1, cg.jkg_WHUDOpacity); } else { MAKERGBA(opacity, 1,1,1, cg.jkg_HUDOpacity); } ps = &cg.snap->ps; // Can we find the menu? if (!menuHUD) { return; } if (!cent->currentState.weapon ) // We don't have a weapon right now { return; } #ifndef NO_SP_STYLE_AMMO // Figure out whether or not we want to do the thing where we highlight the text whenever we consume ammo or change firing mode (or, change weapon) if (cg.lastAmmo != cg.predictedPlayerState.stats[STAT_AMMO] || cg.lastAmmoGun != cg.predictedPlayerState.weaponId) { cg.lastAmmo = cg.predictedPlayerState.stats[STAT_AMMO]; cg.lastAmmoTime = cg.time + 200; // matches SP 1:1 cg.lastAmmoGun = cg.predictedPlayerState.weaponId; } if(cg.lastAmmoTime > cg.time) { vec4_t colorCopy = { 0.2, 0.72, 0.86, 1 }; Q_RGBCopy(&opacity, colorCopy); } #endif weaponInfo = CG_WeaponInfo (cent->currentState.weapon, cent->currentState.weaponVariation); if ( GetWeaponData( cent->currentState.weapon, cent->currentState.weaponVariation )->firemodes[0].cost == 0 && GetWeaponData( cent->currentState.weapon, cent->currentState.weaponVariation )->firemodes[1].cost == 0) { //just draw "infinite" text = "Ammo: Infinite"; } else { if ( GetWeaponAmmoClip( cent->currentState.weapon, cent->currentState.weaponVariation )) { ammo = ps->stats[STAT_AMMO]; } else { ammo = ps->ammo; } if ( GetWeaponAmmoClip( cent->currentState.weapon, cent->currentState.weaponVariation )) { // Display the amount of clips too float temp; temp = ceil(( float ) ps->ammo / ( float ) GetWeaponAmmoClip( cent->currentState.weapon, cent->currentState.weaponVariation )); text = va( "Ammo: %i (%i)", ammo, ( int ) temp ); } else { text = va( "Ammo: %i", ammo ); } } // Now then, lets render this text ^_^ width = (float)trap_R_Font_StrLenPixels(text, cgDC.Assets.qhSmallFont, 1) * 0.6f; focusItem = Menu_FindItemByName(menuHUD, "infobar"); if (focusItem) { trap_R_Font_DrawString(focusItem->window.rect.x + ((focusItem->window.rect.w/2) - (width/2)), focusItem->window.rect.y, text, opacity, cgDC.Assets.qhSmall3Font, -1, 0.5f); } focusItem = Menu_FindItemByName(menuHUD, "weapicon"); if (focusItem) { trap_R_SetColor( opacity ); CG_DrawPic( focusItem->window.rect.x, focusItem->window.rect.y, focusItem->window.rect.w, focusItem->window.rect.h, weaponInfo->hudIcon ); } }
/* ================ CG_DrawHUD ================ */ void CG_DrawHUD(centity_t *cent) { menuDef_t *menuHUD = NULL; vec4_t opacity = {1, 1, 1, 1}; AdjustOpacityLevels(); MAKERGBA(opacity, 1, 1, 1, cg.jkg_HUDOpacity); if (cg.captureFlagPercent > 0 && cg.captureFlagPercent < 100 && cg.capturingFlag) {// For attack/defence/scenario gametype flag captures... int x = 600; int y = 154; vec3_t color; if (cg.captureFlagPercent > 100) cg.captureFlagPercent = 100; FlagCaptureBar(); VectorSet(color, 250, 100, 1); if (next_color_update < cg.time) { // Cycle writing color... if (color_forwards) { if (color_selector >= 250) { color_forwards = qfalse; color_selector--; } else { color_selector++; } } else { if (color_selector <= 50) { color_forwards = qtrue; color_selector++; } else { color_selector--; } } next_color_update = cg.time + 10; } color[0] = color_selector; color[1] = color_selector; color[2] = 1; if (cg.recaptureingFlag) { x-=15; UI_DrawScaledProportionalString(x, y, va("Consolidating Control Point"), UI_RIGHT|UI_DROPSHADOW, color, 0.4); } else UI_DrawScaledProportionalString(x, y, va("Capturing Control Point"), UI_RIGHT|UI_DROPSHADOW, color, 0.4); } else if (cg.captureFlagPercent >= 100 && cg.capturingFlag) {// For attack/defence/scenario gametype flag captures... int x = 600; int y = 154; vec3_t color; if (cg.captureFlagPercent > 100) cg.captureFlagPercent = 100; FlagCaptureBar(); VectorSet(color, 250, 250, 0); UI_DrawScaledProportionalString(x, y, va("^3Control Point Captured!"), UI_RIGHT|UI_DROPSHADOW, color, 0.4); } if (cgs.gametype >= GT_TEAM) { // tint the hud items based on team if (cg.snap->ps.persistant[PERS_TEAM] == TEAM_RED ) hudTintColor = redhudtint; else if (cg.snap->ps.persistant[PERS_TEAM] == TEAM_BLUE ) hudTintColor = bluehudtint; else // If we're not on a team for whatever reason, leave things as they are. hudTintColor = colorTable[CT_WHITE]; } else { // tint the hud items white (dont' tint) hudTintColor = colorTable[CT_WHITE]; } // Jedi Knight Galaxies -- Put in our own HUD components here // Render the top-left stuff menuHUD = Menus_FindByName("hud_topleft"); CG_DrawTopLeftHUD (menuHUD, opacity); // Render the minimap menuHUD = Menus_FindByName("hud_minimap"); CG_DrawMiniMap (menuHUD, opacity); // Render the hotkey bar menuHUD = Menus_FindByName("hud_hotkey"); CG_DrawHotkeyBar (menuHUD, opacity); menuHUD = Menus_FindByName("hud_bottomright"); CG_DrawBottomRightHUD (menuHUD, cent, opacity); }
void JKG_Slice_DrawGridSlot(int slot, float x, float y, float w, float h) { vec4_t color; vec4_t color2; int row = slot >> 3; int col = slot & 7; const char *text = NULL; float w2; if (row >= sliceData.height || col >= sliceData.width) { UI_DrawRect(x, y, w, h, disabled); } else { if (sliceData.grid[row][col].active) { // Determine the color to show switch (sliceData.grid[row][col].type) { case 0: // Alarm node VectorCopy4M(red, color2); text = NULL; break; case 1: // Relay node VectorCopy4M(orange, color2); text = NULL; break; case 2: // Reset node VectorCopy4M(yellow, color2); text = "R"; break; case 3: // Access level 1 case 4: // Access level 2 case 5: // Access level 3 case 6: // Access level 4 case 7: // Access level 5 VectorCopy4M(green, color2); text = va("%i", sliceData.grid[row][col].type - 2); break; } if (sliceData.grid[row][col].revealTime) { float phase = (float)(trap->Milliseconds() - sliceData.grid[row][col].revealTime) / 250.0f; if (phase > 1.0f) phase = 1.0f; if (trap->Milliseconds() > sliceData.grid[row][col].revealTime + 250) { sliceData.grid[row][col].revealTime = 0; } LerpColor((float *)white, color2, color, phase); UI_FillRect(x, y, w, h, color); if (text) { color[0] = color[1] = color[2] = 1.0f; color[3] = phase; w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y+(h*0.2f), 0.4f, color, text, 0, 0, 0, 0 ); } } else { UI_FillRect(x, y, w, h, color2); if (text) { w2 = trap->R_Font_StrLenPixels(text, MenuFontToHandle(0), 1.0f) * 0.4f; DC->drawText(x + (w/2) - (w2/2), y+(h*0.2f), 0.4f, (float *)(white), text, 0, 0, 0, 0 ); } } } else { if (sliceData.grid[row][col].blinkTime) { int delta = trap->Milliseconds() - sliceData.grid[row][col].blinkTime; float phase; if (delta > 2350) { // ~(7.5 * PI)*100, so the node blinks 4 times and stops when faded out sliceData.grid[row][col].blinkTime = 0; } phase = 0.5f + (sin((float)delta / 100.0f) * 0.5); if (sliceData.grid[row][col].blinkColor) { LerpColor((float *)offcolor, (float *)green, color, phase); } else { LerpColor((float *)offcolor, (float *)red, color, phase); } UI_FillRect(x, y, w, h, color); } else { if (sliceData.grid[row][col].marked) { if (sliceData.grid[row][col].marked == 1) { MAKERGBA(color, 0.3f, 0.3f, 1.0f, 0.7f + sin((float)trap->Milliseconds() / 150.0f) * 0.1f); } else { MAKERGBA(color, 1.0f, 0.3f, .3f, 0.7f + sin((float)trap->Milliseconds() / 150.0f) * 0.1f); } UI_FillRect(x, y, w, h, color); } else { UI_FillRect(x, y, w, h, offcolor); } } } if (sliceData.inputState == INPUTSTATE_AWAITINGNODE || (sliceData.inputState == INPUTSTATE_AWAITINGINACTIVENODE && !sliceData.grid[row][col].active)) { float phase = 0.7f + sin((float)trap->Milliseconds() / 150.0f) * 0.1f; MAKERGBA(color, phase, phase, phase, 1.0f); UI_DrawRect(x, y, w, h, color); } else { UI_DrawRect(x, y, w, h, black); } } }