Ticket #3000: heropanel2.patch
File heropanel2.patch, 8.6 KB (added by , 8 years ago) |
---|
-
binaries/data/mods/public/gui/session/session.js
const g_GameSpeeds = prepareForDropdown( 6 6 */ 7 7 const g_DefaultPopulationColor = "white"; 8 8 const g_PopulationAlertColor = "orange"; 9 9 10 10 /** 11 * Maximum number of heroes to display (must stay in sync with hero_icon.xml). 12 */ 13 const g_HeroPanelCount = 10; 14 15 /** 11 16 * A random file will be played. TODO: more variety 12 17 */ 13 18 const g_Ambient = [ "audio/ambient/dayscape/day_temperate_gen_03.ogg" ]; 14 19 15 20 /** … … var g_ShowGuarded = false; 143 148 var g_AdditionalHighlight = []; 144 149 145 150 /** 146 151 * Blink the hero selection if that entity has lost health since the last turn. 147 152 */ 148 var g_PreviousHero HitPoints;153 var g_PreviousHeroes = []; 149 154 150 155 /** 151 156 * Unit classes to be checked for the idle-worker-hotkey. 152 157 */ 153 158 var g_WorkerTypes = ["Female", "Trader", "FishingBoat", "CitizenSoldier", "Healer"]; … … function updateGUIObjects() 710 715 recalculateStatusBarDisplay(); 711 716 712 717 if (g_ShowGuarding || g_ShowGuarded) 713 718 updateAdditionalHighlight(); 714 719 715 updateHero ();720 updateHeroes(); 716 721 updateGroups(); 717 722 updateDebug(); 718 723 updatePlayerDisplay(); 719 724 updateResearchDisplay(); 720 725 updateSelectionDetails(); … … function updateGUIStatusBar(nameOfBar, p 786 791 787 792 statusBar.size = healthSize; 788 793 } 789 794 790 795 791 function updateHero ()796 function updateHeroes() 792 797 { 793 798 let unitHeroPanel = Engine.GetGUIObjectByName("unitHeroPanel"); 794 let heroButton = Engine.GetGUIObjectByName("unitHeroButton");795 796 799 let playerState = GetSimState().players[g_ViewedPlayer]; 797 800 if (!playerState || playerState.heroes.length <= 0) 798 801 { 799 g_PreviousHero HitPoints = undefined;802 g_PreviousHeroes = []; 800 803 unitHeroPanel.hidden = true; 801 804 return; 802 805 } 803 804 let heroImage = Engine.GetGUIObjectByName("unitHeroImage");805 let heroState = GetExtendedEntityState(playerState.heroes[0]);806 let template = GetTemplateData(heroState.template);807 heroImage.sprite = "stretched:session/portraits/" + template.icon;808 let hero = playerState.heroes[0];809 810 heroButton.onpress = function()811 {812 if (!Engine.HotkeyIsPressed("selection.add"))813 g_Selection.reset();814 g_Selection.addList([hero]);815 };816 heroButton.ondoublepress = function() { selectAndMoveTo(getEntityOrHolder(hero)); };817 806 unitHeroPanel.hidden = false; 818 807 808 let usedSlots = new Array(g_HeroPanelCount).fill(false); 809 810 let mapped = playerState.heroes.map(ent => { 811 812 // Map to current button, if available. 813 if (g_PreviousHeroes[ent]) 814 return { 815 "ent": ent, 816 "index": g_PreviousHeroes[ent].displayIndex, 817 "previous": g_PreviousHeroes[ent] 818 }; 819 820 // Place new heroes at the end of the list. 821 return { 822 "ent": ent, 823 "index": g_HeroPanelCount 824 }; 825 }).sort((l, r) => l.index == r.index ? l.ent - r.ent : l.index - r.index); 826 827 let heroes = []; 828 for (let displayIndex = 0; displayIndex < Math.min(g_HeroPanelCount, mapped.length); ++displayIndex) 829 { 830 let hero = mapped[displayIndex]; 831 832 // Find the first unused one if new, otherwise reuse previous. 833 let buttonSlot = hero.previous ? 834 hero.previous.button : 835 usedSlots.findIndex(slot => !slot); 836 837 usedSlots[buttonSlot] = true; 838 839 let heroButton = Engine.GetGUIObjectByName("unitHeroButton[" + buttonSlot + "]"); 840 let heroState = GetExtendedEntityState(hero.ent); 841 let template = GetTemplateData(heroState.template); 842 843 if (hero.previous === undefined) 844 { 845 heroButton.onPress = function() 846 { 847 if (!Engine.HotkeyIsPressed("selection.add")) 848 g_Selection.reset(); 849 850 g_Selection.addList([hero.ent]); 851 }; 852 853 heroButton.onDoublePress = function() { 854 selectAndMoveTo(getEntityOrHolder(hero.ent)); 855 }; 856 857 heroButton.hidden = false; 858 859 // Ensure no pre-existing animations. 860 stopColorFade("heroHitOverlay[" + buttonSlot + "]"); 861 862 let heroImage = Engine.GetGUIObjectByName("unitHeroImage[" + buttonSlot + "]"); 863 heroImage.sprite = "stretched:session/portraits/" + template.icon; 864 } 865 866 heroButton.tooltip = createHeroTooltip(heroState, template); 867 868 updateGUIStatusBar("heroHealthBar[" + buttonSlot + "]", 869 heroState.hitpoints, heroState.maxHitpoints); 870 871 setPanelObjectPosition(heroButton, displayIndex, g_HeroPanelCount); 872 873 // If the health of the hero changed since the last update, trigger the animation. 874 if (hero.previous && hero.previous.player == g_ViewedPlayer && 875 hero.previous.hitpoints > heroState.hitpoints) 876 { 877 startColorFade("heroHitOverlay[" + buttonSlot + "]", 100, 0, 878 colorFade_attackUnit, true, smoothColorFadeRestart_attackUnit); 879 } 880 881 heroes[hero.ent] = { 882 "displayIndex": displayIndex, 883 "button": buttonSlot, 884 "hitpoints": heroState.hitpoints, 885 "player": g_ViewedPlayer 886 }; 887 } 888 889 // In case heroes were removed and their slot/button was freed, hide it. 890 for (let hero of g_PreviousHeroes.filter(prev => !usedSlots[prev.button])) 891 Engine.GetGUIObjectByName("unitHeroButton[" + hero.button + "]").hidden = true; 892 893 g_PreviousHeroes = heroes; 894 } 895 896 function createHeroTooltip(heroState, template) 897 { 819 898 // Setup tooltip 820 899 let tooltip = "[font=\"sans-bold-16\"]" + template.name.specific + "[/font]"; 821 let healthLabel = "[font=\"sans-bold-13\"]" + translate("Health:") + "[/font]"; 822 tooltip += "\n" + sprintf(translate("%(label)s %(current)s / %(max)s"), { 823 "label": healthLabel, 900 tooltip += "\n" + sprintf(translate("%(label)s %(current)s / %(max)s"), { 901 "label": "[font=\"sans-bold-13\"]" + translate("Health:") + "[/font]", 824 902 "current": Math.ceil(heroState.hitpoints), 825 903 "max": Math.ceil(heroState.maxHitpoints) 826 904 }); 827 905 if (heroState.attack) 828 906 tooltip += "\n" + getAttackTooltip(heroState); 829 907 830 908 tooltip += "\n" + getArmorTooltip(heroState.armour); 831 909 if (template.tooltip) 832 910 tooltip += "\n" + template.tooltip; 833 834 heroButton.tooltip = tooltip; 835 836 // update heros health bar 837 updateGUIStatusBar("heroHealthBar", heroState.hitpoints, heroState.maxHitpoints); 838 839 let heroHP = { 840 "hitpoints": heroState.hitpoints, 841 "player": g_ViewedPlayer 842 }; 843 844 if (!g_PreviousHeroHitPoints) 845 g_PreviousHeroHitPoints = heroHP; 846 847 // if the health of the hero changed since the last update, trigger the animation 848 if (g_PreviousHeroHitPoints.player == heroHP.player && g_PreviousHeroHitPoints.hitpoints > heroHP.hitpoints) 849 startColorFade("heroHitOverlay", 100, 0, colorFade_attackUnit, true, smoothColorFadeRestart_attackUnit); 850 851 g_PreviousHeroHitPoints = heroHP; 911 return tooltip; 852 912 } 853 913 854 914 function updateGroups() 855 915 { 856 916 let guiName = "Group"; -
binaries/data/mods/public/gui/session/session_objects/hero_icon.xml
2 2 <object 3 3 name="unitHeroPanel" 4 4 size="0 36 50 93" 5 5 hidden="true" 6 6 > 7 <object name="unitHeroButton" size="0 0 50 50" type="button" style="iconButton" 8 tooltip_style="sessionToolTip"> 9 <object name="unitHeroImage" size="5 5 100%-5 100%-5" type="image" ghost="true"/> 10 <object name="heroHitOverlay" hidden="true" type="image" ghost="true" size="5 5 100%-5 100%-5"/> 11 </object> 12 <!-- Hero Health bar --> 13 <object size="3 100%-7 100%-3 100%-2" name="heroHealthSection" ghost="true"> 14 <object size="0 0 100% 5" name="heroHealth" type="image" ghost="true"> 15 <object type="image" sprite="barBorder" ghost="true" size="-1 -1 100%+1 100%+1"/> 16 <object type="image" sprite="healthBackground" ghost="true"/> 17 <object type="image" sprite="healthForeground" ghost="true" name="heroHealthBar"/> 18 <object type="image" sprite="statsBarShaderHorizontal" ghost="true"/> 7 <repeat count="10" var="n"> 8 <object name="unitHeroButton[n]" size="0 0 50 50" type="button" hidden="true" style="iconButton" tooltip_style="sessionToolTip"> 9 <object name="unitHeroImage[n]" size="5 5 100%-5 100%-5" type="image" ghost="true"/> 10 <object name="heroHitOverlay[n]" hidden="true" type="image" ghost="true" size="5 5 100%-5 100%-5"/> 11 <!-- Hero Health bar --> 12 <object size="3 100%-7 100%-3 100%-2" name="heroHealthSection[n]" ghost="true"> 13 <object size="0 0 100% 5" name="heroHealth[n]" type="image" ghost="true"> 14 <object type="image" sprite="barBorder" ghost="true" size="-1 -1 100%+1 100%+1"/> 15 <object type="image" sprite="healthBackground" ghost="true"/> 16 <object type="image" sprite="healthForeground" ghost="true" name="heroHealthBar[n]"/> 17 <object type="image" sprite="statsBarShaderHorizontal" ghost="true"/> 18 </object> 19 </object> 19 20 </object> 20 </ object>21 </repeat> 21 22 </object>