1 // _________ __ __ 2 // / _____// |_____________ _/ |______ ____ __ __ ______ 3 // \_____ \\ __\_ __ \__ \\ __\__ \ / ___\| | \/ ___/ 4 // / \| | | | \// __ \| | / __ \_/ /_/ > | /\___ | 5 // /_______ /|__| |__| (____ /__| (____ /\___ /|____//____ > 6 // \/ \/ \//_____/ \/ 7 // ______________________ ______________________ 8 // T H E W A R B E G I N S 9 // Stratagus - A free fantasy real time strategy game engine 10 // 11 /**@name ui.h - The user interface header file. */ 12 // 13 // (c) Copyright 1999-2019 by Lutz Sammer, Jimmy Salmon and Andrettin 14 // 15 // This program is free software; you can redistribute it and/or modify 16 // it under the terms of the GNU General Public License as published by 17 // the Free Software Foundation; only version 2 of the License. 18 // 19 // This program is distributed in the hope that it will be useful, 20 // but WITHOUT ANY WARRANTY; without even the implied warranty of 21 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 22 // GNU General Public License for more details. 23 // 24 // You should have received a copy of the GNU General Public License 25 // along with this program; if not, write to the Free Software 26 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 27 // 02111-1307, USA. 28 // 29 30 #ifndef __UI_H__ 31 #define __UI_H__ 32 33 //@{ 34 35 /// @todo this only the start of the new user interface 36 /// @todo all user interface variables should go here and be configurable 37 38 /*---------------------------------------------------------------------------- 39 -- Includes 40 ----------------------------------------------------------------------------*/ 41 42 #include <vector> 43 #include <string> 44 #include <map> 45 46 #include "color.h" 47 #include "cursor.h" 48 #include "map/minimap.h" 49 #include "script.h" 50 #include "viewport.h" 51 #include "ui/interface.h" 52 #include "ui/statusline.h" 53 #include "ui/uitimer.h" 54 55 /*---------------------------------------------------------------------------- 56 -- Declarations 57 ----------------------------------------------------------------------------*/ 58 59 class CContentType; 60 class CFile; 61 class CFont; 62 class CMapLayer; 63 class CPopup; 64 class CUnit; 65 class LuaActionListener; 66 67 /*---------------------------------------------------------------------------- 68 -- Definitions 69 ----------------------------------------------------------------------------*/ 70 71 enum TextAlignment { 72 TextAlignUndefined, 73 TextAlignCenter, 74 TextAlignLeft, 75 TextAlignRight 76 }; 77 78 class ButtonStyleProperties 79 { 80 public: ButtonStyleProperties()81 ButtonStyleProperties() : Sprite(nullptr), Frame(0), BorderColor(0), 82 BorderSize(0), TextAlign(TextAlignUndefined), 83 TextPos(0, 0) 84 {} 85 86 CGraphic *Sprite; 87 int Frame; 88 CColor BorderColorRGB; 89 IntColor BorderColor; 90 int BorderSize; 91 TextAlignment TextAlign; /// Text alignment 92 PixelPos TextPos; /// Text location 93 std::string TextNormalColor; /// Normal text color 94 std::string TextReverseColor; /// Reverse text color 95 }; 96 97 class ButtonStyle 98 { 99 public: ButtonStyle()100 ButtonStyle() : Width(0), Height(0), Font(nullptr), 101 TextAlign(TextAlignUndefined), TextX(0), TextY(0) {} 102 103 int Width; /// Button width 104 int Height; /// Button height 105 CFont *Font; /// Font 106 std::string TextNormalColor; /// Normal text color 107 std::string TextReverseColor; /// Reverse text color 108 TextAlignment TextAlign; /// Text alignment 109 int TextX; /// Text X location 110 int TextY; /// Text Y location 111 ButtonStyleProperties Default; /// Default button properties 112 ButtonStyleProperties Hover; /// Hover button properties 113 ButtonStyleProperties Clicked; /// Clicked button properties 114 }; 115 116 /// buttons on screen themselves 117 class CUIButton 118 { 119 public: 120 //Wyrmgus start 121 // CUIButton() : X(0), Y(0), Style(nullptr), Callback(nullptr) {} CUIButton()122 CUIButton() : X(0), Y(0), Clicked(false), HotkeyPressed(false), Style(nullptr), Callback(nullptr) {} 123 //Wyrmgus end ~CUIButton()124 ~CUIButton() {} 125 126 bool Contains(const PixelPos &screenPos) const; 127 128 public: 129 int X; /// x coordinate on the screen 130 int Y; /// y coordinate on the screen 131 //Wyrmgus start 132 bool Clicked; /// whether the button is currently clicked or not 133 bool HotkeyPressed; /// whether the button's hotkey is currently pressed or not 134 //Wyrmgus end 135 std::string Text; /// button text 136 ButtonStyle *Style; /// button style 137 LuaActionListener *Callback; /// callback function 138 }; 139 140 #define MAX_NUM_VIEWPORTS 8 /// Number of supported viewports 141 142 /** 143 ** Enumeration of the different predefined viewport configurations. 144 ** 145 ** @todo this should be later user configurable 146 */ 147 enum ViewportModeType { 148 VIEWPORT_SINGLE = 0, /// Old single viewport 149 VIEWPORT_SPLIT_HORIZ, /// Two viewports split horizontal 150 VIEWPORT_SPLIT_HORIZ3, /// Three viewports split horiontal 151 VIEWPORT_SPLIT_VERT, /// Two viewports split vertical 152 VIEWPORT_QUAD, /// Four viewports split symmetric 153 NUM_VIEWPORT_MODES /// Number of different viewports. 154 }; 155 156 class CMapArea 157 { 158 public: CMapArea()159 CMapArea() : X(0), Y(0), EndX(0), EndY(0), 160 ScrollPaddingLeft(0), ScrollPaddingRight(0), 161 ScrollPaddingTop(0), ScrollPaddingBottom(0) {} 162 163 bool Contains(const PixelPos &screenPos) const; 164 165 public: 166 int X; /// Screen pixel left corner x coordinate 167 int Y; /// Screen pixel upper corner y coordinate 168 int EndX; /// Screen pixel right x coordinate 169 int EndY; /// Screen pixel bottom y coordinate 170 int ScrollPaddingLeft; /// Scrollable area past the left of map 171 int ScrollPaddingRight; /// Scrollable area past the right of map 172 int ScrollPaddingTop; /// Scrollable area past the top of map 173 int ScrollPaddingBottom; /// Scrollable area past the bottom of map 174 }; 175 176 /** 177 ** Condition to show panel content. 178 */ 179 class ConditionPanel 180 { 181 public: ConditionPanel()182 ConditionPanel() : ShowOnlySelected(false), HideNeutral(false), 183 HideAllied(false), ShowOpponent(false), ShowIfCanCastAnySpell(false), BoolFlags(nullptr), 184 //Wyrmgus start 185 Affixed(0), Unique(0), Replenishment(0), 186 //Wyrmgus end 187 Variables(nullptr) {} ~ConditionPanel()188 ~ConditionPanel() 189 { 190 delete[] BoolFlags; 191 delete[] Variables; 192 } 193 194 bool ShowOnlySelected; /// if true, show only for selected unit. 195 196 bool HideNeutral; /// if true, don't show for neutral unit. 197 bool HideAllied; /// if true, don't show for allied unit. (but show own units) 198 bool ShowOpponent; /// if true, show for opponent unit. 199 bool ShowIfCanCastAnySpell; /// if true, show only if the unit can cast any spell 200 201 //Wyrmgus start 202 char Affixed; /// check if the button's unit has an affix 203 char Unique; /// check if the button's unit is unique 204 char Replenishment; /// check if the button's unit has resource replenishment 205 //Wyrmgus end 206 char *BoolFlags; /// array of condition about user flags. 207 char *Variables; /// array of variable to verify (enable and max > 0) 208 }; 209 210 /** 211 ** Info for the panel. 212 */ 213 class CUnitInfoPanel 214 { 215 public: CUnitInfoPanel()216 CUnitInfoPanel() : PosX(0), PosY(0), DefaultFont(0), 217 Contents(), Condition(nullptr) {} 218 ~CUnitInfoPanel(); 219 220 public: 221 std::string Name; /// Ident of the panel. 222 int PosX; /// X coordinate of the panel. 223 int PosY; /// Y coordinate of the panel. 224 CFont *DefaultFont; /// Default font for content. 225 226 std::vector<CContentType *>Contents; /// Array of contents to display. 227 228 ConditionPanel *Condition; /// Condition to show the panel; if null, no condition. 229 }; 230 231 232 class CFiller 233 { 234 struct bits_map { bits_mapbits_map235 bits_map() : Width(0), Height(0), bstore(nullptr) {} 236 ~bits_map(); 237 238 void Init(CGraphic *g); 239 TransparentPixelbits_map240 bool TransparentPixel(int x, int y) 241 { 242 if (bstore) { 243 const unsigned int x_index = x / 32; 244 y *= Width; 245 y /= 32; 246 x -= (x_index * 32); 247 return ((bstore[y + x_index] & (1 << x)) == 0); 248 } 249 return false; 250 }; 251 252 int Width; 253 int Height; 254 unsigned int *bstore; 255 }; 256 257 bits_map map; 258 public: CFiller()259 CFiller() : G(nullptr), X(0), Y(0) {} 260 261 void Load(); 262 OnGraphic(int x,int y)263 bool OnGraphic(int x, int y) 264 { 265 x -= X; 266 y -= Y; 267 if (x >= 0 && y >= 0 && x < map.Width && y < map.Height) { 268 return !map.TransparentPixel(x, y); 269 } 270 return false; 271 } 272 CGraphic *G; /// Graphic 273 int X; /// X coordinate 274 int Y; /// Y coordinate 275 }; 276 277 class CButtonPanel 278 { 279 public: CButtonPanel()280 CButtonPanel() : G(nullptr), X(0), Y(0), ShowCommandKey(true) 281 {} 282 283 void Draw(); 284 void Update(); 285 void DoClicked(int button); 286 int DoKey(int key); 287 288 private: 289 void DoClicked_SelectTarget(int button); 290 291 void DoClicked_Unload(int button); 292 void DoClicked_SpellCast(int button); 293 void DoClicked_Repair(int button); 294 void DoClicked_Return(); 295 void DoClicked_Stop(); 296 void DoClicked_StandGround(); 297 void DoClicked_Button(int button); 298 void DoClicked_CancelUpgrade(); 299 void DoClicked_CancelTrain(); 300 void DoClicked_CancelBuild(); 301 void DoClicked_Build(int button); 302 void DoClicked_Train(int button); 303 void DoClicked_UpgradeTo(int button); 304 void DoClicked_Research(int button); 305 void DoClicked_CallbackAction(int button); 306 void DoClicked_LearnAbility(int button); 307 void DoClicked_ExperienceUpgradeTo(int button); 308 void DoClicked_RallyPoint(int button); 309 void DoClicked_Faction(int button); 310 void DoClicked_Quest(int button); 311 void DoClicked_Buy(int button); 312 void DoClicked_ProduceResource(int button); 313 void DoClicked_SellResource(int button); 314 void DoClicked_BuyResource(int button); 315 void DoClicked_Salvage(); 316 void DoClicked_EnterMapLayer(); 317 318 319 public: 320 CGraphic *G; 321 int X; 322 int Y; 323 std::vector<CUIButton> Buttons; 324 CColor AutoCastBorderColorRGB; 325 bool ShowCommandKey; 326 }; 327 328 class CPieMenu 329 { 330 public: CPieMenu()331 CPieMenu() : G(nullptr), MouseButton(NoButton) 332 { 333 memset(this->X, 0, sizeof(this->X)); 334 memset(this->Y, 0, sizeof(this->Y)); 335 } 336 337 CGraphic *G; /// Optional background image 338 int MouseButton; /// Which mouse button pops up the piemenu, deactivate with NoButton 339 int X[9]; /// X position of the pies 340 int Y[9]; /// Y position of the pies 341 SetRadius(int radius)342 void SetRadius(int radius) 343 { 344 const int coeffX[] = { 0, 193, 256, 193, 0, -193, -256, -193, 0}; 345 const int coeffY[] = { -256, -193, 0, 193, 256, 193, 0, -193, 0}; 346 for (int i = 0; i < 9; ++i) { 347 this->X[i] = (coeffX[i] * radius) >> 8; 348 this->Y[i] = (coeffY[i] * radius) >> 8; 349 } 350 } 351 }; 352 353 class CResourceInfo 354 { 355 public: CResourceInfo()356 CResourceInfo() : G(nullptr), IconFrame(0), IconX(0), IconY(0), IconWidth(-1), 357 Font(nullptr), TextX(-1), TextY(-1) {} 358 359 CGraphic *G; /// icon graphic 360 int IconFrame; /// icon frame 361 int IconX; /// icon X position 362 int IconY; /// icon Y position 363 int IconWidth; /// icon W size 364 CFont *Font; /// Font 365 std::string Text; /// text 366 int TextX; /// text X position 367 int TextY; /// text Y position 368 }; 369 #define MaxResourceInfo MaxCosts + 4 /// +4 for food and score and mana and free workers count 370 371 class CInfoPanel 372 { 373 public: CInfoPanel()374 CInfoPanel() : G(nullptr), X(0), Y(0) {} 375 376 void Draw(); 377 378 CGraphic *G; 379 int X; 380 int Y; 381 }; 382 383 class CUIUserButton 384 { 385 public: CUIUserButton()386 CUIUserButton() : Clicked(false) {} 387 388 bool Clicked; // true if button is clicked, false otherwise 389 CUIButton Button; // User button 390 }; 391 392 /** 393 ** Defines the user interface. 394 */ 395 class CUserInterface 396 { 397 public: 398 CUserInterface(); 399 ~CUserInterface(); 400 401 void Load(); 402 403 bool MouseScroll; /// Enable mouse scrolling 404 bool KeyScroll; /// Enable keyboard scrolling 405 /// Key Scroll Speed 406 int KeyScrollSpeed; 407 /// Mouse Scroll Speed (screenpixels per mousepixel) 408 int MouseScrollSpeed; 409 /// Middle-Mouse Scroll Speed (screenpixels per mousepixel) 410 int MouseScrollSpeedDefault; 411 /// Middle-Mouse Scroll Speed with Control pressed 412 int MouseScrollSpeedControl; 413 414 PixelPos MouseWarpPos; /// Cursor warp screen position 415 416 std::string NormalFontColor; /// Color for normal text displayed 417 std::string ReverseFontColor; /// Color for reverse text displayed 418 419 std::vector<CFiller> Fillers; /// Filler graphics 420 421 CResourceInfo Resources[MaxResourceInfo]; /// Icon+Text of all resources 422 423 CInfoPanel InfoPanel; /// Info panel 424 CResourceInfo TimeOfDayPanel; /// Time of day panel 425 CResourceInfo SeasonPanel; /// Season panel 426 CResourceInfo DatePanel; /// Date panel 427 CResourceInfo AgePanel; /// Age panel 428 std::vector<CUnitInfoPanel *> InfoPanelContents; /// Info panel contents 429 430 std::vector<CPopup *> ButtonPopups; /// Popup windows for buttons 431 432 CUIButton *SingleSelectedButton; /// Button for single selected unit 433 434 std::vector<CUIButton> SelectedButtons; /// Selected buttons 435 CFont *MaxSelectedFont; /// Font type to use 436 int MaxSelectedTextX; /// position to place '+#' text 437 int MaxSelectedTextY; /// if > maximum units selected 438 439 CUIButton *SingleTrainingButton; /// Button for single training 440 std::string SingleTrainingText; /// Text for single training 441 CFont *SingleTrainingFont; /// Font for single traning 442 int SingleTrainingTextX; /// X text position single training 443 int SingleTrainingTextY; /// Y text position single training 444 445 std::vector<CUIButton> TrainingButtons;/// Training buttons 446 std::string TrainingText; /// Multiple Training Text 447 CFont *TrainingFont; /// Multiple Training Font 448 int TrainingTextX; /// Multiple Training X Text position 449 int TrainingTextY; /// Multiple Training Y Text position 450 451 CUIButton *UpgradingButton; /// Button info for upgrade 452 453 CUIButton *ResearchingButton; /// Button info for researching 454 455 std::vector<CUIButton> TransportingButtons;/// Button info for transporting 456 457 CUIButton *IdleWorkerButton; /// Button for the idle worker notification 458 CUIButton *LevelUpUnitButton; /// Button for the level up unit notification 459 std::vector<CUIButton> HeroUnitButtons; /// Button for the hero units 460 std::vector<CUIButton> InventoryButtons; /// Button info for inventory items 461 462 // Completed bar 463 CColor CompletedBarColorRGB; /// color for completed bar 464 IntColor CompletedBarColor; /// color for completed bar 465 bool CompletedBarShadow; /// should complete bar have shadow 466 467 // Button panel 468 CButtonPanel ButtonPanel; 469 470 // Pie Menu 471 CPieMenu PieMenu; 472 473 // Map area 474 ViewportModeType ViewportMode; /// Current viewport mode 475 CViewport *MouseViewport; /// Viewport containing mouse 476 CViewport *SelectedViewport; /// Current selected active viewport 477 int NumViewports; /// # Viewports currently used 478 CViewport Viewports[MAX_NUM_VIEWPORTS]; /// Parameters of all viewports 479 CMapArea MapArea; /// geometry of the whole map area 480 CFont *MessageFont; /// Font used for messages 481 int MessageScrollSpeed; /// Scroll speed in seconds for messages 482 483 CMapLayer *CurrentMapLayer; 484 CMapLayer *PreviousMapLayer; 485 486 // Menu buttons 487 CUIButton MenuButton; /// menu button 488 //Wyrmgus start 489 // CUIButton NetworkMenuButton; /// network menu button 490 //Wyrmgus end 491 CUIButton NetworkDiplomacyButton; /// network diplomacy button 492 493 //Wyrmgus start 494 std::vector<CUIButton> PlaneButtons; /// Button info for plane map layer buttons 495 std::vector<CUIButton> WorldButtons; /// Button info for world map layer buttons 496 std::vector<CUIButton> SurfaceLayerButtons; /// Button info for surface layer map layer buttons 497 //Wyrmgus end 498 499 // Used defined buttons 500 std::vector<CUIUserButton> UserButtons; /// User buttons 501 502 // The minimap 503 CMinimap Minimap; /// minimap 504 IntColor ViewportCursorColor; /// minimap cursor color 505 506 // The status line 507 CStatusLine StatusLine; /// status line 508 509 // Game timer 510 CUITimer Timer; /// game timer 511 512 // Offsets for 640x480 center used by menus 513 int Offset640X; /// Offset for 640x480 X position 514 int Offset480Y; /// Offset for 640x480 Y position 515 516 // 517 // Cursors used. 518 // 519 CursorConfig Point; /// General pointing cursor 520 CursorConfig Glass; /// HourGlass, system is waiting 521 CursorConfig Cross; /// Multi-select cursor. 522 CursorConfig YellowHair; /// Yellow action,attack cursor. 523 CursorConfig GreenHair; /// Green action,attack cursor. 524 CursorConfig RedHair; /// Red action,attack cursor. 525 CursorConfig Scroll; /// Cursor for scrolling map around. 526 527 CursorConfig ArrowE; /// Cursor pointing east 528 CursorConfig ArrowNE; /// Cursor pointing north east 529 CursorConfig ArrowN; /// Cursor pointing north 530 CursorConfig ArrowNW; /// Cursor pointing north west 531 CursorConfig ArrowW; /// Cursor pointing west 532 CursorConfig ArrowSW; /// Cursor pointing south west 533 CursorConfig ArrowS; /// Cursor pointing south 534 CursorConfig ArrowSE; /// Cursor pointing south east 535 536 /// @todo could use different sounds/speech for the errors 537 /// Is in gamesounds? 538 /// SoundConfig PlacementError; /// played on placements errors 539 /// SoundConfig PlacementSuccess; /// played on placements success 540 /// SoundConfig Click; /// click noice used often 541 542 CGraphic *VictoryBackgroundG; /// Victory background graphic 543 CGraphic *DefeatBackgroundG; /// Defeat background graphic 544 }; 545 546 extern std::vector<ButtonAction> CurrentButtons; /// Current Selected Buttons 547 548 /*---------------------------------------------------------------------------- 549 -- Variables 550 ----------------------------------------------------------------------------*/ 551 552 extern CUserInterface UI; /// The user interface 553 554 extern std::string ClickMissile; /// Missile to show when you click 555 extern std::string DamageMissile; /// Missile to show damage caused 556 557 558 /// Hash table of all the button styles 559 extern std::map<std::string, ButtonStyle *> ButtonStyleHash; 560 561 extern bool RightButtonAttacks; /// right button attacks 562 563 extern const char DefaultGroupKeys[]; /// Default group keys 564 extern std::string UiGroupKeys; /// Up to 11 keys used for group selection 565 566 extern bool FancyBuildings; /// Mirror buildings 1 yes, 0 now. 567 568 // only exported to save them 569 570 /*---------------------------------------------------------------------------- 571 -- Functions 572 ----------------------------------------------------------------------------*/ 573 574 /// Initialize the ui 575 extern void InitUserInterface(); 576 /// Save the ui state 577 extern void SaveUserInterface(CFile &file); 578 /// Clean up the ui module 579 extern void CleanUserInterface(); 580 //Wyrmgus start 581 void CleanUserInterfaceFillers(); 582 extern void UpdateSurfaceLayerButtons(); 583 //Wyrmgus end 584 585 extern void FreeButtonStyles(); 586 587 /// Register ccl features 588 extern void UserInterfaceCclRegister(); 589 590 /// return popup by ident string 591 extern CPopup *PopupByIdent(const std::string &ident); 592 593 /// Find a button style 594 extern ButtonStyle *FindButtonStyle(const std::string &style); 595 596 /// Called if the mouse is moved in Normal interface state 597 extern void UIHandleMouseMove(const PixelPos &pos); 598 /// Called if any mouse button is pressed down 599 extern void UIHandleButtonDown(unsigned button); 600 /// Called if any mouse button is released up 601 extern void UIHandleButtonUp(unsigned button); 602 603 /// Restrict mouse cursor to viewport 604 extern void RestrictCursorToViewport(); 605 /// Restrict mouse cursor to minimap 606 extern void RestrictCursorToMinimap(); 607 608 /// Get viewport for screen pixel position 609 extern CViewport *GetViewport(const PixelPos &screenPos); 610 /// Cycle through all available viewport modes 611 extern void CycleViewportMode(int); 612 /// Select viewport mode 613 extern void SetViewportMode(ViewportModeType mode); 614 extern void SetNewViewportMode(ViewportModeType mode); 615 extern void CheckViewportMode(); 616 617 /// Check if mouse scrolling is enabled 618 extern bool GetMouseScroll(); 619 /// Enable/disable scrolling with the mouse 620 extern void SetMouseScroll(bool enabled); 621 /// Check if keyboard scrolling is enabled 622 extern bool GetKeyScroll(); 623 /// Enable/disable scrolling with the keyboard 624 extern void SetKeyScroll(bool enabled); 625 /// Check if mouse grabbing is enabled 626 extern bool GetGrabMouse(); 627 /// Enable/disable grabbing the mouse 628 extern void SetGrabMouse(bool enabled); 629 /// Check if scrolling stops when leaving the window 630 extern bool GetLeaveStops(); 631 /// Enable/disable leaving the window stops scrolling 632 extern void SetLeaveStops(bool enabled); 633 634 extern int AddHandler(lua_State *l); 635 extern void CallHandler(unsigned int handle, int value); 636 637 /// Show load progress 638 extern void ShowLoadProgress(const char *fmt, ...) PRINTF_VAARG_ATTRIBUTE(1, 2); 639 /// Update load progress 640 extern void UpdateLoadProgress(); 641 642 extern void CalculateItemsToLoad(); 643 extern void UpdateLoadingBar(); 644 extern void IncItemsLoaded(); 645 extern void ResetItemsToLoad(); 646 647 //@} 648 649 #endif // !__UI_H__ 650