44 const std::string &ip,
46 unsigned int windowWidth,
47 unsigned int windowHeight,
49 bool windowFullscreen,
50 const std::string &windowTitle,
53 const std::string &windowCursorIcon,
57 unsigned int spriteWidth,
58 unsigned int spriteHeight,
59 unsigned int frameLimit,
60 const std::string &configFilePath,
63 const std::string &player
65_windowWidth(windowWidth),
66_windowHeight(windowHeight),
67_windowCursor(windowCursor),
68_windowFullscreen(windowFullscreen),
69_windowTitle(windowTitle),
72_imageIsSprite(imageIsSprite),
73_spriteStartTop(spriteStartTop),
74_spriteStartLeft(spriteStartLeft),
75_spriteWidth(spriteWidth),
76_configFilePath(configFilePath),
77_spriteHeight(spriteHeight),
86 PRETTY_DEBUG <<
"The debug section of the log is enabled" << std::endl;
88 if (_isIpInRange(ip) ==
true) {
94 if (_isPortCorrect(port) ==
true) {
99 PRETTY_INFO <<
"Processing cursor icon" << std::endl;
100 std::string windowText = _lowerText(windowCursorIcon);
101 if (windowText.empty() || windowText ==
"null" || windowText ==
"none") {
102 _windowCursorIcon =
"";
103 }
else if (_isFilePresent(windowCursorIcon) ==
true) {
104 _windowCursorIcon = windowCursorIcon;
108 PRETTY_INFO <<
"Processing frame limit" << std::endl;
109 if (_isFrameLimitCorrect(frameLimit)) {
110 _windowFrameLimit = frameLimit;
114 PRETTY_INFO <<
"Initialising the network manager" << std::endl;
115 _networkManager = std::make_shared<GUI::Network::ThreadCapsule>(_baseId);
117 PRETTY_INFO <<
"Setting the player name" << std::endl;
118 _networkManager->setPlayerName(_player);
139std::string Main::_lowerText(
const std::string &text)
141 std::string lowerText = text;
142 if (lowerText.empty()) {
149 [](
unsigned char c) {
150 return std::tolower(c);
164const bool Main::_isIpInRange(
const std::string &ip)
const
166 std::istringstream iss(ip);
170 while (std::getline(iss, segment,
'.')) {
175 int octet = std::stoi(segment);
176 if (octet < 0 || octet > 255) {
197const bool Main::_isPortCorrect(
const unsigned int port)
const
199 return port >= 0 && port <= 65535;
210const bool Main::_isFilePresent(
const std::string &filepath)
const
212 return std::ifstream(filepath).good();
223const bool Main::_isFrameLimitCorrect(
const unsigned int frameLimit)
const
225 if (frameLimit < 10 || frameLimit > 1000) {
239const bool Main::_isFontConfigurationCorrect(
const TOMLLoader &node)
const
242 !_isKeyPresentAndOfCorrectType(node,
"name", toml::node_type::string) ||
243 !_isKeyPresentAndOfCorrectType(node,
"path", toml::node_type::string)
259const bool Main::_isIconConfigurationCorrect(
const TOMLLoader &node)
const
262 !_isKeyPresentAndOfCorrectType(node,
"name", toml::node_type::string) ||
263 !_isKeyPresentAndOfCorrectType(node,
"path", toml::node_type::string)
278const bool Main::_isMusicConfigurationCorrect(
const TOMLLoader &node)
const
281 !_isKeyPresentAndOfCorrectType(node,
"name", toml::node_type::string) ||
282 !_isKeyPresentAndOfCorrectType(node,
"path", toml::node_type::string) ||
283 !_isKeyPresentAndOfCorrectType(node,
"loop", toml::node_type::boolean) ||
284 !_isKeyPresentAndOfCorrectType(node,
"volume", toml::node_type::integer)
299const bool Main::_isSpriteConfigurationCorrect(
const TOMLLoader &node)
const
302 !_isKeyPresentAndOfCorrectType(node,
"name", toml::node_type::string) ||
303 !_isKeyPresentAndOfCorrectType(node,
"path", toml::node_type::string) ||
304 !_isKeyPresentAndOfCorrectType(node,
"sprite_width", toml::node_type::integer) ||
305 !_isKeyPresentAndOfCorrectType(node,
"sprite_height", toml::node_type::integer) ||
306 !_isKeyPresentAndOfCorrectType(node,
"start_left", toml::node_type::boolean) ||
307 !_isKeyPresentAndOfCorrectType(node,
"start_top", toml::node_type::boolean)
322const bool Main::_isBackgroundConfigurationCorrect(
const TOMLLoader &node)
const
325 !_isKeyPresentAndOfCorrectType(node,
"name", toml::node_type::string) ||
326 !_isKeyPresentAndOfCorrectType(node,
"path", toml::node_type::string)
343const bool Main::_isKeyPresentAndOfCorrectType(
const TOMLLoader &node,
const std::string &key,
const toml::node_type &valueType)
const
359void Main::_initialiseConnection()
361 std::string address = _ip +
":" + std::to_string(_port);
362 PRETTY_DEBUG <<
"Connecting to the server at " << address << std::endl;
363 _networkManager->initialize();
364 _networkManager->setAddress(_ip, _port);
365 _networkManager->startGame();
366 _connectionInitialised = _networkManager->isConnected();
367 if (_connectionInitialised) {
370 PRETTY_WARNING <<
"We are not connected to the server" << std::endl;
378void Main::_closeConnection()
380 _networkManager->stopThread();
381 _connectionInitialised = _networkManager->isConnected();
389std::uint32_t Main::_initialiseAudio()
391 const std::string tomlPath = _tomlContent.
getTOMLPath();
392 const std::string musicKey =
"music";
393 const std::string musicKeyAlt =
"musics";
394 std::vector<std::string> audios;
395 std::unordered_map<std::string, TOMLLoader> loadedAudios;
397 const TOMLLoader audio = _getTOMLNodeContent<CustomExceptions::InvalidConfigurationMusicType, CustomExceptions::NoMusicInConfigFile>(_tomlContent, musicKey, musicKeyAlt);
401 audios.push_back(
"mainMenu");
402 audios.push_back(
"bossFight");
403 audios.push_back(
"gameLoop");
404 audios.push_back(
"shooting");
405 audios.push_back(
"damage");
406 audios.push_back(
"dead");
407 audios.push_back(
"button");
408 audios.push_back(
"gameOver");
409 audios.push_back(
"success");
411 const std::string &expectedStringType = _tomlContent.
getTypeAsString(toml::node_type::table);
413 PRETTY_INFO <<
"Getting the music configuration chunks" << std::endl;
415 for (std::string &iterator : audios) {
416 _updateLoadingText(
"Processing music '" + iterator +
"'...");
417 if (!audio.
hasKey(iterator)) {
420 loadedAudios[iterator] = tempNode;
421 if (audio.
getValueType(iterator) != toml::node_type::table) {
424 loadedAudios[iterator].update(audio.
getTable(iterator));
425 if (!_isMusicConfigurationCorrect(loadedAudios[iterator])) {
426 std::string userConfig = loadedAudios[iterator].getTOMLString();
429 _updateLoadingText(
"Processing music '" + iterator +
"'...[OK]");
432 PRETTY_INFO <<
"Initialising the musics" << std::endl;
434 for (std::unordered_map<std::string, TOMLLoader>::iterator it = loadedAudios.begin(); it != loadedAudios.end(); ++it) {
435 std::string application = it->first;
436 std::string name = it->second.getValue<std::string>(
"name");
437 std::string path = it->second.getValue<std::string>(
"path");
441 _updateLoadingText(
"Loading music '" + name +
"'...");
443 if (_isKeyPresentAndOfCorrectType(it->second,
"volume", toml::node_type::integer)) {
444 volume = it->second.getValue<
int>(
"volume");
446 if (_isKeyPresentAndOfCorrectType(it->second,
"loop", toml::node_type::boolean)) {
447 loop = it->second.getValue<
bool>(
"loop");
449 std::shared_ptr<GUI::ECS::Components::MusicComponent> node = std::make_shared<GUI::ECS::Components::MusicComponent>(_baseId, path, name, application, volume, loop);
452 _updateLoadingText(
"Loading music '" + name +
"'...[OK]");
456 PRETTY_INFO <<
"Value of the base id: " << std::to_string(_baseId) << std::endl;
465std::uint32_t Main::_initialiseFonts()
467 const std::string tomlPath = _tomlContent.
getTOMLPath();
468 const std::string fontKey =
"font";
469 const std::string fontKeyAlt =
"fonts";
470 const TOMLLoader font = _getTOMLNodeContent<CustomExceptions::InvalidConfigurationFontType, CustomExceptions::NoFontInConfigFile>(_tomlContent, fontKey, fontKeyAlt);
471 std::unordered_map<std::string, TOMLLoader> loadedFonts;
473 const std::string titleFontNode =
"title";
474 const std::string bodyFontNode =
"body";
475 const std::string defaultFontNode =
"default";
476 const std::string buttonFontNode =
"button";
478 if (!font.
hasKey(titleFontNode)) {
481 if (!font.
hasKey(bodyFontNode)) {
484 if (!font.
hasKey(defaultFontNode)) {
487 if (!font.
hasKey(buttonFontNode)) {
493 loadedFonts[
"title"] = tempNode;
494 loadedFonts[
"body"] = tempNode;
495 loadedFonts[
"default"] = tempNode;
496 loadedFonts[
"button"] = tempNode;
499 loadedFonts[
"body"].update(font.
getTable(titleFontNode));
500 loadedFonts[
"title"].update(font.
getTable(bodyFontNode));
501 loadedFonts[
"default"].update(font.
getTable(defaultFontNode));
502 loadedFonts[
"button"].update(font.
getTable(buttonFontNode));
504 if (!_isFontConfigurationCorrect(loadedFonts[
"title"])) {
505 const std::string userConfig = loadedFonts[
"title"].getTOMLString();
506 const std::string fontName = titleFontNode;
509 if (!_isFontConfigurationCorrect(loadedFonts[
"body"])) {
510 const std::string userConfig = loadedFonts[
"body"].getTOMLString();
511 const std::string fontName = bodyFontNode;
514 if (!_isFontConfigurationCorrect(loadedFonts[
"default"])) {
515 const std::string userConfig = loadedFonts[
"default"].getTOMLString();
516 const std::string fontName = defaultFontNode;
519 if (!_isFontConfigurationCorrect(loadedFonts[
"button"])) {
520 const std::string userConfig = loadedFonts[
"button"].getTOMLString();
521 const std::string fontName = buttonFontNode;
526 for (std::unordered_map<std::string, TOMLLoader>::iterator it = loadedFonts.begin(); it != loadedFonts.end(); ++it) {
527 std::string application = it->first;
528 PRETTY_INFO <<
"Font application = '" + application +
"'" << std::endl;
529 std::string name = it->second.getValue<std::string>(
"name");
530 std::string path = it->second.getValue<std::string>(
"path");
531 int defaultSize = 50;
535 if (_isKeyPresentAndOfCorrectType(it->second,
"default_size", toml::node_type::integer)) {
536 defaultSize = it->second.getValue<
int>(
"default_size");
538 if (_isKeyPresentAndOfCorrectType(it->second,
"bold", toml::node_type::boolean)) {
539 bold = it->second.getValue<
bool>(
"bold");
541 if (_isKeyPresentAndOfCorrectType(it->second,
"italic", toml::node_type::boolean)) {
542 italic = it->second.getValue<
bool>(
"italic");
544 PRETTY_DEBUG <<
"Loading font '" << application <<
"' ... [LOADING]" << std::endl;
545 std::shared_ptr<GUI::ECS::Systems::Font> node = std::make_shared<GUI::ECS::Systems::Font>(_baseId, name, path, defaultSize, application, bold, italic);
546 PRETTY_DEBUG <<
"Font '" << application <<
"' [LOADED]" << std::endl;
549 if (application == titleFontNode) {
552 if (application == bodyFontNode) {
555 if (application == defaultFontNode) {
558 if (application == buttonFontNode) {
564 PRETTY_INFO <<
"Value of the base id: " << std::to_string(_baseId) << std::endl;
569std::uint32_t Main::_initialiseIcon()
571 const std::string iconKey =
"icon";
572 const std::string iconKeyAlt =
"icons";
573 const TOMLLoader sprites = _getTOMLNodeContent<CustomExceptions::InvalidIconConfiguration, CustomExceptions::NoIconInConfigFile>(_tomlContent, iconKey, iconKeyAlt);
574 std::unordered_map<std::string, TOMLLoader> loadedSprites;
576 PRETTY_INFO <<
"Getting the icon configuration chunks" << std::endl;
578 if (!_isIconConfigurationCorrect(sprites)) {
579 std::string iconName =
"";
580 if (_isKeyPresentAndOfCorrectType(sprites,
"name", toml::node_type::string)) {
581 iconName = sprites.
getValue<std::string>(
"name");
586 _updateLoadingText(
"Getting icon information...");
587 const std::string name = sprites.
getValue<std::string>(
"name");
588 const std::string path = sprites.
getValue<std::string>(
"path");
594 if (_isKeyPresentAndOfCorrectType(sprites,
"width", toml::node_type::integer)) {
595 const int tmpWidth = sprites.
getValue<
int>(
"width");
600 if (_isKeyPresentAndOfCorrectType(sprites,
"height", toml::node_type::integer)) {
601 const int tmpHeight = sprites.
getValue<
int>(
"height");
606 if (_isKeyPresentAndOfCorrectType(sprites,
"x", toml::node_type::integer)) {
607 const int tmpX = sprites.
getValue<
int>(
"x");
612 if (_isKeyPresentAndOfCorrectType(sprites,
"y", toml::node_type::integer)) {
613 const int tmpY = sprites.
getValue<
int>(
"y");
618 _updateLoadingText(
"Getting icon information...[OK]");
619 _updateLoadingText(
"Loading icon...");
620 std::shared_ptr<GUI::ECS::Components::ImageComponent> icon = std::make_shared<GUI::ECS::Components::ImageComponent>(_baseId, path, name);
621 icon->setDimension({ width, height });
622 icon->setPosition({ x,y });
626 _updateLoadingText(
"Loading icon...[OK]");
636std::uint32_t Main::_initialiseSprites()
638 const std::string spriteSheetKey =
"spritesheets";
639 const std::string spriteSheetKeyAlt =
"spritesheet";
640 const TOMLLoader sprites = _getTOMLNodeContent<CustomExceptions::InvalidConfigurationSpritesheetType, CustomExceptions::NoSpritesInConfigFile>(_tomlContent, spriteSheetKey, spriteSheetKeyAlt);
641 const std::string tomlPath = _tomlContent.
getTOMLPath();
642 std::unordered_map<std::string, TOMLLoader> loadedSprites;
646 PRETTY_INFO <<
"Getting the sprite configuration chunks" << std::endl;
648 unsigned int counter = 1;
649 std::string data =
"Processed Sprites: \n";
650 const std::string &expectedStringType = _tomlContent.
getTypeAsString(toml::node_type::table);
652 for (std::string &it : sprites.
getKeys()) {
653 _updateLoadingText(
"Processing '" + it +
"'...");
654 data +=
"\t" + std::to_string(counter) +
" : " +
"'" + it +
"'\n";
655 PRETTY_INFO <<
"Processing sprite: '" << it <<
"'" << std::endl;
656 if (!sprites.
hasKey(it)) {
659 loadedSprites[it] = tempNode;
660 if (sprites.
getValueType(it) != toml::node_type::table) {
663 loadedSprites[it].update(sprites.
getTable(it));
664 if (!_isSpriteConfigurationCorrect(loadedSprites[it])) {
665 std::string userConfig = loadedSprites[it].getTOMLString();
669 _updateLoadingText(
"Processing '" + it +
"'...[OK]");
673 PRETTY_INFO <<
"Initialising the sprites" << std::endl;
675 for (std::unordered_map<std::string, TOMLLoader>::iterator it = loadedSprites.begin(); it != loadedSprites.end(); ++it) {
676 std::string application = it->first;
677 std::string name = it->second.getValue<std::string>(
"name");
678 std::string path = it->second.getValue<std::string>(
"path");
679 int spriteWidth = it->second.getValue<
int>(
"sprite_width");
680 int spriteHeight = it->second.getValue<
int>(
"sprite_height");
681 bool startLeft = it->second.getValue<
bool>(
"start_left");
682 bool startTop = it->second.getValue<
bool>(
"start_top");
683 int initialFrame = 0;
685 int frameDelay = 100;
687 if (it->second.hasKey(
"initial_frame")) {
688 initialFrame = it->second.getValue<
int>(
"initial_frame");
690 if (it->second.hasKey(
"end_frame")) {
691 endFrame = it->second.getValue<
int>(
"end_frame");
693 if (it->second.hasKey(
"frame_delay")) {
694 frameDelay = it->second.getValue<
int>(
"frame_delay");
695 if (frameDelay < 0) {
696 std::string errMsg =
"<A number between 0 and 2147483647 was expected, however, you entered: '";
703 _updateLoadingText(
"Loading sprite '" + name +
"'...");
704 PRETTY_INFO <<
"Loading sprite '" << name <<
"' [LOADING]" << std::endl;
709 "name='" << name <<
"', " <<
710 "path='" << path <<
"', " <<
719 std::shared_ptr<GUI::ECS::Components::AnimationComponent> animationPointer = std::make_shared<GUI::ECS::Components::AnimationComponent>(_baseId, path, spriteWidth, spriteHeight, startLeft, startTop, initialFrame, endFrame);
723 animationPointer->setDelay(frameDelay);
724 PRETTY_INFO <<
"Animation component info: " << *animationPointer << std::endl;
727 PRETTY_DEBUG <<
"Setting animation, animation id: '" <<
Recoded::myToString(animationPointer->getEntityNodeId()) <<
"', sprite entity id: '" << _baseId <<
"'" << std::endl;
728 std::shared_ptr<GUI::ECS::Components::SpriteComponent> spriteEntity = std::make_shared<GUI::ECS::Components::SpriteComponent>(_baseId, name, *animationPointer);
729 PRETTY_SUCCESS <<
"Sprite entity added to sprite '" << name <<
"'" << std::endl;
731 spriteEntity->setApplication(application);
732 PRETTY_INFO <<
"Storing " << name <<
" into the ecs" << std::endl;
734 PRETTY_SUCCESS << name <<
" stored into the ecs entity" << std::endl;
737 PRETTY_SUCCESS <<
"Sprite '" << name <<
"' [LOADED]" << std::endl;
738 _updateLoadingText(
"Loading sprite '" + name +
"'...[OK]");
740 PRETTY_INFO <<
"buffer line1 between two sprite loads" << std::endl;
741 PRETTY_INFO <<
"buffer line2 between two sprite loads" << std::endl;
742 PRETTY_INFO <<
"buffer line3 between two sprite loads" << std::endl;
743 PRETTY_INFO <<
"buffer line4 between two sprite loads" << std::endl;
747 PRETTY_INFO <<
"Value of the base id: " << std::to_string(_baseId) << std::endl;
756std::uint32_t Main::_initialiseBackgrounds()
758 const std::string iconKey =
"backgrounds";
759 const std::string iconKeyAlt =
"background";
760 const std::string path = _tomlContent.
getTOMLPath();
761 const TOMLLoader backgrounds = _getTOMLNodeContent<CustomExceptions::InvalidBackgroundConfiguration, CustomExceptions::NoBackgroundInConfigFile>(_tomlContent, iconKey, iconKeyAlt);
762 std::unordered_map<std::string, TOMLLoader> loadedBackgrounds;
763 std::vector<std::string> systemBackgrounds;
765 systemBackgrounds.push_back(
"mainMenu");
766 systemBackgrounds.push_back(
"settings");
767 systemBackgrounds.push_back(
"gameOver");
768 systemBackgrounds.push_back(
"connectionFailed");
770 PRETTY_INFO <<
"Getting the background configuration chunks" << std::endl;
772 for (std::string &item : backgrounds.
getKeys()) {
773 std::string checkMsg =
"Checking for the presence of '" + item +
"' in the config file...";
774 _updateLoadingText(checkMsg);
775 if (std::find(systemBackgrounds.begin(), systemBackgrounds.end(), item) != systemBackgrounds.end() && !backgrounds.
hasKey(item)) {
776 PRETTY_CRITICAL <<
"No TOML key '" << item <<
"' in the file path '" << path <<
"'." << std::endl;
779 if (!_isKeyPresentAndOfCorrectType(backgrounds, item, toml::node_type::table)) {
780 PRETTY_CRITICAL <<
"The key '" << item <<
"' is not a table in the file." << std::endl;
783 loadedBackgrounds[item] = backgrounds.
getTable(item);
784 _updateLoadingText(checkMsg +
"[OK]");
787 std::unordered_map<std::string, TOMLLoader>::iterator it;
789 for (it = loadedBackgrounds.begin(); it != loadedBackgrounds.end(); it++) {
790 PRETTY_INFO <<
"Loading background: " << it->first << std::endl;
791 _updateLoadingText(
"Loading background '" + it->first +
"'...");
792 std::string name = it->second.getValue<std::string>(
"name");
793 std::string path = it->second.getValue<std::string>(
"path");
796 bool allowAsLevelBackground =
false;
797 if (_isKeyPresentAndOfCorrectType(it->second,
"x", toml::node_type::integer)) {
798 int tmpX = it->second.getValue<
int>(
"x");
800 PRETTY_CRITICAL <<
"The value of 'x' for the background '" << name <<
"'." << std::endl;
805 if (_isKeyPresentAndOfCorrectType(it->second,
"y", toml::node_type::integer)) {
806 int tmpY = it->second.getValue<
int>(
"y");
808 PRETTY_CRITICAL <<
"The value of 'y' for the background '" << name <<
"'." << std::endl;
813 if (_isKeyPresentAndOfCorrectType(it->second,
"allow_as_level_background", toml::node_type::boolean)) {
814 bool allowAsLevelBackground = it->second.getValue<
bool>(
"allow_as_level_background");
816 std::shared_ptr<GUI::ECS::Components::ImageComponent> node = std::make_shared<GUI::ECS::Components::ImageComponent>(_baseId, path, name, it->first);
818 node->setPosition({ x, y });
819 node->setLevelBackgroundCompatible(allowAsLevelBackground);
821 _updateLoadingText(
"Loading background '" + it->first +
"'...[OK]");
822 PRETTY_INFO <<
"buffer line1 between two background loads" << std::endl;
823 PRETTY_INFO <<
"buffer line2 between two background loads" << std::endl;
824 PRETTY_INFO <<
"buffer line3 between two background loads" << std::endl;
825 PRETTY_INFO <<
"buffer line4 between two background loads" << std::endl;
835void Main::_initialiseRessources()
837 std::uint32_t _baseId = 0;
838 _ecsEntities.clear();
840 PRETTY_INFO <<
"========================== Displaying loaded toml data. ==========================" << std::endl;
842 PRETTY_SUCCESS <<
"========================== Displayed loaded toml data. ==========================" << std::endl;
844 std::shared_ptr<GUI::ECS::Systems::Window> window = std::make_shared<GUI::ECS::Systems::Window>(_baseId, _windowWidth, _windowHeight, _windowTitle);
845 PRETTY_DEBUG <<
"Setting the window position to : " << std::pair<int, int>({ _windowX, _windowY }) << std::endl;
846 window->setPosition({ _windowX, _windowY });
848 std::shared_ptr<GUI::ECS::Systems::EventManager>
event = std::make_shared<GUI::ECS::Systems::EventManager>(_baseId);
851 window->setFullScreen(_windowFullscreen);
852 window->setFramerateLimit(_windowFrameLimit);
861 _baseId = _initialiseFonts();
864 PRETTY_CRITICAL <<
"There are no fonts that were loaded in the program, aborting." << std::endl;
868 PRETTY_INFO <<
"Fetching loaded font for displaying a loading text on screen." << std::endl;
870 if (!firstFontCapsule.has_value()) {
878 window->draw(*loading);
883 std::shared_ptr<SoundLib> soundLib = std::make_shared<SoundLib>(_baseId, _ecsEntities);
884 _ecsEntities[
typeid(
SoundLib)].push_back(soundLib);
888 _baseId = _initialiseIcon();
889 _baseId = _initialiseBackgrounds();
890 _baseId = _initialiseSprites();
891 _baseId = _initialiseAudio();
892 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
893 std::cout <<
"Sound is empty" << std::endl;
894 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
898 if (!(internalSoundLib.has_value())) {
899 std::cout <<
"Sound lib not found" << std::endl;
900 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
903 internalSoundLib.value()->updateSoundLib(_ecsEntities);
904 PRETTY_INFO <<
"Final value of the base Id: " << std::to_string(_baseId) << std::endl;
907void Main::_updateLoadingText(
const std::string &detail)
909 PRETTY_DEBUG <<
"Updating loading display" << std::endl;
914 if (_mainWindowIndex > windows.size()) {
919 if (!windowCapsule.has_value()) {
923 std::shared_ptr<GUI::ECS::Systems::Window> window = windowCapsule.value();
925 if (_mainEventIndex > eventManagers.size()) {
930 if (!eventManagerCapsule.has_value()) {
934 std::shared_ptr<GUI::ECS::Systems::EventManager>
event = eventManagerCapsule.value();
936 if (_loadingIndex > textComponents.size()) {
941 if (!textCapsule.has_value()) {
945 std::shared_ptr<GUI::ECS::Components::TextComponent> text = textCapsule.value();
947 if (!window->isOpen()) {
950 event->processEvents(*window);
951 if (!window->isOpen()) {
955 text->update(event->getMouseInfo());
956 text->setText(detail);
965 PRETTY_INFO <<
"Updating mouse information for renderable components." << std::endl;
972 for (
unsigned int index = 0; index < sprites.size(); index++) {
973 PRETTY_INFO <<
"Processing index for sprite : " << std::to_string(index) << std::endl;
975 std::shared_ptr<GUI::ECS::Components::SpriteComponent> sprite = std::any_cast<std::shared_ptr<GUI::ECS::Components::SpriteComponent>>(sprites[index]);
976 sprite->update(mouse);
978 catch (std::bad_any_cast &e) {
979 PRETTY_ERROR <<
"Error casting sprite component, system error: " + std::string(e.what()) << std::endl;
982 for (
unsigned int index = 0; index < texts.size(); index++) {
983 PRETTY_INFO <<
"Processing index for text : " << std::to_string(index) << std::endl;
985 std::shared_ptr<GUI::ECS::Components::TextComponent> text = std::any_cast<std::shared_ptr<GUI::ECS::Components::TextComponent>>(texts[index]);
988 catch (std::bad_any_cast &e) {
989 PRETTY_ERROR <<
"Error casting text component, system error: " + std::string(e.what()) << std::endl;
992 for (
unsigned int index = 0; index < buttons.size(); index++) {
993 PRETTY_INFO <<
"Processing index for button : " << std::to_string(index) << std::endl;
995 std::shared_ptr<GUI::ECS::Components::ButtonComponent> button = std::any_cast<std::shared_ptr<GUI::ECS::Components::ButtonComponent>>(buttons[index]);
996 button->update(mouse);
998 catch (std::bad_any_cast &e) {
999 PRETTY_ERROR <<
"Error casting button component, system error: " + std::string(e.what()) << std::endl;
1002 for (
unsigned int index = 0; index < shapes.size(); index++) {
1003 PRETTY_INFO <<
"Processing index for shape : " << std::to_string(index) << std::endl;
1005 std::shared_ptr<GUI::ECS::Components::ShapeComponent> shape = std::any_cast<std::shared_ptr<GUI::ECS::Components::ShapeComponent>>(shapes[index]);
1006 shape->update(mouse);
1008 catch (std::bad_any_cast &e) {
1009 PRETTY_ERROR <<
"Error casting shape component, system error: " + std::string(e.what()) << std::endl;
1012 for (
unsigned int index = 0; index < images.size(); index++) {
1013 PRETTY_INFO <<
"Processing index for image : " << std::to_string(index) << std::endl;
1015 std::shared_ptr<GUI::ECS::Components::ImageComponent> image = std::any_cast<std::shared_ptr<GUI::ECS::Components::ImageComponent>>(images[index]);
1016 image->update(mouse);
1018 catch (std::bad_any_cast &e) {
1019 PRETTY_ERROR <<
"Error casting shape component, system error: " + std::string(e.what()) << std::endl;
1022 PRETTY_SUCCESS <<
"Updated mouse information for renderable components." << std::endl;
1030void Main::_sendAllPackets()
1032 PRETTY_DEBUG <<
"Sending any packets that have been buffered and not sent" << std::endl;
1050void Main::_processIncommingPackets()
1052 PRETTY_DEBUG <<
"Getting the buffer from the incoming packets" << std::endl;
1053 _bufferPackets.clear();
1054 const bool connected = _networkManager->isConnected();
1057 _bufferPackets = _networkManager->getReceivedMessages();
1060 PRETTY_DEBUG <<
"Out of _processIncommingPackets" << std::endl;
1090const std::string Main::_getIpChunk(
const unsigned int index,
const std::string &defaultValue)
const
1094 PRETTY_DEBUG <<
"Handling edge case when the _ip is empty" << std::endl;
1096 PRETTY_DEBUG <<
"_ip is empty, returning defaultValue" << std::endl;
1097 return defaultValue;
1101 size_t startPos = 0;
1103 unsigned int currentIndex = 0;
1105 PRETTY_DEBUG <<
"Looping through the dots in the IP address." << std::endl;
1108 dotPos = _ip.find(
'.', startPos);
1109 if (dotPos == std::string::npos) {
1110 PRETTY_DEBUG <<
"No more dots found, returning the rest of the string" << std::endl;
1114 if (currentIndex == index) {
1115 resp = _ip.substr(startPos, dotPos - startPos);
1116 PRETTY_DEBUG <<
"Found node at index " << index <<
": " << resp << std::endl;
1120 PRETTY_DEBUG <<
"Moving to the next segment after the current dot" << std::endl;
1121 startPos = dotPos + 1;
1125 if (currentIndex == index) {
1126 PRETTY_DEBUG <<
"Returning the content after the last dot if any" << std::endl;
1127 PRETTY_DEBUG <<
"Getting the part after the last dot" << std::endl;
1128 resp = _ip.substr(startPos);
1129 PRETTY_DEBUG <<
"Found node at last index: " << resp << std::endl;
1131 PRETTY_DEBUG <<
"Returning the defaultValue because resp is empty" << std::endl;
1132 return defaultValue;
1137 PRETTY_DEBUG <<
"No dot was found or index was too large, returning the default value.\n"
1138 <<
"Content of defaultValue: " << defaultValue << std::endl;
1139 return defaultValue;
1158const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> Main::_getTextComponent(
const std::string &textComponentKey)
1164 for (std::any node : texts) {
1166 if (node.has_value()) {
1167 PRETTY_DEBUG <<
"node type: '" << node.type().name() <<
"'" << std::endl;
1169 if (!chunk.has_value()) {
1170 PRETTY_DEBUG <<
"Text component is empty" << std::endl;
1173 if (chunk.value()->getApplication() == textComponentKey || chunk.value()->getName() == textComponentKey) {
1174 PRETTY_DEBUG <<
"Found node with key: " << chunk.value()->getApplication() << std::endl;
1178 PRETTY_DEBUG <<
"No matching text component found" << std::endl;
1179 return std::nullopt;
1199const std::string Main::_incrementIpV4Node(
const std::string &v4Node)
1201 if (v4Node ==
"0" || v4Node ==
"000") {
1205 const unsigned int v4int = std::max({ std::stoi(v4Node), 0 });
1207 return std::to_string(v4int + 1);
1212 catch (std::invalid_argument &e) {
1213 PRETTY_WARNING <<
"The argument passed is not a number, you entered: '"
1214 << v4Node <<
"', stoi error: '" << std::string(e.what()) <<
"'"
1215 <<
", defaulting to: '0'"
1238const std::string Main::_decrementIpV4Node(
const std::string &v4Node)
1241 const unsigned int v4int = std::max({ std::stoi(v4Node), 0 });
1243 return std::to_string(v4int - 1);
1248 catch (std::invalid_argument &e) {
1249 PRETTY_WARNING <<
"The argument passed is not a number, you entered: '"
1250 << v4Node <<
"', stoi error: '" << std::string(e.what()) <<
"'"
1251 <<
", defaulting to: '0'"
1272const std::string Main::_incrementPortCounter(
const std::string &portSection)
1274 if (portSection ==
"0" || portSection ==
"000") {
1278 const unsigned int port = std::max({ std::stoi(portSection), 0 });
1279 if (port < _maximumPortRange) {
1280 return std::to_string(port + 1);
1285 catch (std::invalid_argument &e) {
1286 PRETTY_WARNING <<
"The argument passed is not a number, you entered: '"
1287 << portSection <<
"', stoi error: '" << std::string(e.what()) <<
"'"
1288 <<
", defaulting to: '0'"
1309const std::string Main::_decrementPortCounter(
const std::string &portSection)
1312 const unsigned int port = std::max({ std::stoi(portSection), 0 });
1314 return std::to_string(port - 1);
1316 return std::to_string(_maximumPortRange);
1319 catch (std::invalid_argument &e) {
1320 PRETTY_WARNING <<
"The argument passed is not a number, you entered: '"
1321 << portSection <<
"', stoi error: '" << std::string(e.what()) <<
"'"
1322 <<
", defaulting to: '0'"
1334void Main::_incrementIpChunkOne()
1336 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1338 events->flushEvents();
1339 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4FirstChunkKey);
1340 if (!text.has_value()) {
1341 PRETTY_ERROR <<
"Could not find the text component for the first IP chunk." << std::endl;
1344 const std::string currentChunk = text.value()->getText();
1345 const std::string newChunk = _incrementIpV4Node(currentChunk);
1346 text.value()->setText(newChunk);
1347 PRETTY_DEBUG <<
"The first chunk has it's value that has been set to: '"
1348 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1358void Main::_incrementIpChunkTwo()
1360 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1362 events->flushEvents();
1363 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4SecondChunkKey);
1364 if (!text.has_value()) {
1365 PRETTY_ERROR <<
"Could not find the text component for the second IP chunk." << std::endl;
1368 const std::string currentChunk = text.value()->getText();
1369 const std::string newChunk = _incrementIpV4Node(currentChunk);
1370 text.value()->setText(newChunk);
1371 PRETTY_DEBUG <<
"The second chunk has it's value that has been set to: '"
1372 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1382void Main::_incrementIpChunkThree()
1384 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1386 events->flushEvents();
1387 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4ThirdChunkKey);
1388 if (!text.has_value()) {
1389 PRETTY_ERROR <<
"Could not find the text component for the third IP chunk." << std::endl;
1392 const std::string currentChunk = text.value()->getText();
1393 const std::string newChunk = _incrementIpV4Node(currentChunk);
1394 text.value()->setText(newChunk);
1395 PRETTY_DEBUG <<
"The third chunk has it's value that has been set to: '"
1396 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1406void Main::_incrementIpChunkFour()
1408 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1410 events->flushEvents();
1411 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4FourthChunkKey);
1412 if (!text.has_value()) {
1413 PRETTY_ERROR <<
"Could not find the text component for the fourth IP chunk." << std::endl;
1416 const std::string currentChunk = text.value()->getText();
1417 const std::string newChunk = _incrementIpV4Node(currentChunk);
1418 text.value()->setText(newChunk);
1419 PRETTY_DEBUG <<
"The fourth chunk has it's value that has been set to: '"
1420 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1431void Main::_incrementPortChunk()
1433 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1435 events->flushEvents();
1436 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_portV4ChunkKey);
1437 if (!text.has_value()) {
1438 PRETTY_ERROR <<
"Could not find the text component for the port chunk." << std::endl;
1441 const std::string currentChunk = text.value()->getText();
1442 const std::string newChunk = _incrementPortCounter(currentChunk);
1443 text.value()->setText(newChunk);
1444 PRETTY_DEBUG <<
"The port chunk has it's value that has been set to: '"
1445 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1456void Main::_decrementIpChunkOne()
1458 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1460 events->flushEvents();
1461 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4FirstChunkKey);
1462 if (!text.has_value()) {
1463 PRETTY_ERROR <<
"Could not find the text component for the first IP chunk." << std::endl;
1466 const std::string currentChunk = text.value()->getText();
1467 const std::string newChunk = _decrementIpV4Node(currentChunk);
1468 text.value()->setText(newChunk);
1469 PRETTY_DEBUG <<
"The first chunk has it's value that has been set to: '"
1470 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1480void Main::_decrementIpChunkTwo()
1482 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1484 events->flushEvents();
1485 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4SecondChunkKey);
1486 if (!text.has_value()) {
1487 PRETTY_ERROR <<
"Could not find the text component for the second IP chunk." << std::endl;
1490 const std::string currentChunk = text.value()->getText();
1491 const std::string newChunk = _decrementIpV4Node(currentChunk);
1492 text.value()->setText(newChunk);
1493 PRETTY_DEBUG <<
"The second chunk has it's value that has been set to: '"
1494 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1504void Main::_decrementIpChunkThree()
1506 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1508 events->flushEvents();
1509 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4ThirdChunkKey);
1510 if (!text.has_value()) {
1511 PRETTY_ERROR <<
"Could not find the text component for the third IP chunk." << std::endl;
1514 const std::string currentChunk = text.value()->getText();
1515 const std::string newChunk = _decrementIpV4Node(currentChunk);
1516 text.value()->setText(newChunk);
1517 PRETTY_DEBUG <<
"The third chunk has it's value that has been set to: '"
1518 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1528void Main::_decrementIpChunkFour()
1530 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1532 events->flushEvents();
1533 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_ipV4FourthChunkKey);
1534 if (!text.has_value()) {
1535 PRETTY_ERROR <<
"Could not find the text component for the fourth IP chunk." << std::endl;
1538 const std::string currentChunk = text.value()->getText();
1539 const std::string newChunk = _decrementIpV4Node(currentChunk);
1540 text.value()->setText(newChunk);
1541 PRETTY_DEBUG <<
"The fourth chunk has it's value that has been set to: '"
1542 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1553void Main::_decrementPortChunk()
1555 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1557 events->flushEvents();
1558 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> text = _getTextComponent(_portV4ChunkKey);
1559 if (!text.has_value()) {
1560 PRETTY_ERROR <<
"Could not find the text component for the port chunk." << std::endl;
1563 const std::string currentChunk = text.value()->getText();
1564 const std::string newChunk = _decrementPortCounter(currentChunk);
1565 text.value()->setText(newChunk);
1566 PRETTY_DEBUG <<
"The port chunk has it's value that has been set to: '"
1567 << newChunk <<
"', the previous value was: '" << currentChunk <<
"'"
1583const std::shared_ptr<GUI::ECS::Systems::EventManager> Main::_getEventManager()
1585 PRETTY_DEBUG <<
"Getting the event manager component" << std::endl;
1587 if (!event_ptr.has_value()) {
1591 return event_ptr.value();
1613 std::shared_ptr<GUI::ECS::Components::TextComponent> textNode = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, font, text, size);
1614 textNode->setApplication(application);
1615 textNode->setName(name);
1616 textNode->setNormalColor(normal);
1617 textNode->setHoverColor(hover);
1618 textNode->setClickedColor(clicked);
1643const std::shared_ptr<GUI::ECS::Components::ButtonComponent> Main::_createButton(
const std::string &application,
const std::string &title, std::function<
void()> callback,
const std::string &callbackName,
const int width,
const int height,
const int textSize,
const GUI::ECS::Systems::Colour &bg,
const GUI::ECS::Systems::Colour &normal,
const GUI::ECS::Systems::Colour &hover,
const GUI::ECS::Systems::Colour &clicked,
const std::shared_ptr<GUI::ECS::Systems::Font> &textFont)
1645 const std::string errMsgFont =
"<Required font not found for the text of the button>, system error: ";
1646 std::optional<std::shared_ptr<GUI::ECS::Systems::Font>> fontInstance;
1647 if (textFont ==
nullptr) {
1649 if (!fontInstance.has_value()) {
1650 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the body text of the unknown screen screen." << std::endl;
1654 fontInstance.emplace(textFont);
1656 std::shared_ptr<GUI::ECS::Components::ShapeComponent> shapeItem = std::make_shared<GUI::ECS::Components::ShapeComponent>(_baseId);
1658 shapeItem->setShape(std::pair<float, float>(width, height));
1659 shapeItem->setNormalColor(bg);
1660 shapeItem->setHoverColor(bg);
1661 shapeItem->setClickedColor(bg);
1662 shapeItem->setApplication(std::string(application +
"Shape"));
1664 std::shared_ptr<GUI::ECS::Components::TextComponent> textItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(fontInstance.value()), title, textSize, normal, hover, clicked);
1665 textItem->setApplication(std::string(application +
"Text"));
1667 std::shared_ptr<GUI::ECS::Components::ButtonComponent> buttonItem = std::make_shared<GUI::ECS::Components::ButtonComponent>(_baseId, *shapeItem, *textItem);
1668 buttonItem->setCallback(callback, callbackName);
1669 buttonItem->setApplication(application);
1676 PRETTY_DEBUG <<
"Inserting a TextComponent with key: " << title << std::endl;
1678 PRETTY_DEBUG <<
"Inserting a ShapeComponent with key: " << application << std::endl;
1697const unsigned int Main::_getScreenCenterX()
1700 if (!win.has_value()) {
1704 PRETTY_DEBUG <<
"Setting the icon at the top center of the main menu." << std::endl;
1705 const std::pair<int, int> windowDimensions = win.value()->getDimensions();
1706 if (windowDimensions.first <= 0.0) {
1707 PRETTY_CRITICAL <<
"Skipping calculations and rendering because the window is smaller or equal to 0." << std::endl;
1710 PRETTY_DEBUG <<
"Calculating the y-coordinate (center of the window)." << std::endl;
1711 return static_cast<unsigned int>(windowDimensions.first / 2);
1722const unsigned int Main::_getScreenCenterY()
1725 if (!win.has_value()) {
1729 PRETTY_DEBUG <<
"Setting the icon at the top center of the main menu." << std::endl;
1730 const std::pair<int, int> windowDimensions = win.value()->getDimensions();
1731 if (windowDimensions.second <= 0.0) {
1732 PRETTY_CRITICAL <<
"Skipping calculations and rendering because the window is smaller or equal to 0." << std::endl;
1735 PRETTY_DEBUG <<
"Calculating the y-coordinate (center of the window)." << std::endl;
1736 return static_cast<unsigned int>(windowDimensions.second / 2);
1739void Main::_gameScreen()
1744 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
1746 if (!win.has_value()) {
1752 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1753 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
1755 if (!_networkClassSet) {
1756 PRETTY_DEBUG <<
"The online brain does not have the network class, providing" << std::endl;
1758 PRETTY_DEBUG <<
"The brain now has the network class" << std::endl;
1761 if (!_onlineInitialised) {
1762 PRETTY_DEBUG <<
"The online brain is not initialised, initialising" << std::endl;
1764 _onlineInitialised =
true;
1765 _onlineStarted =
false;
1766 PRETTY_DEBUG <<
"The brain has been initialised" << std::endl;
1769 if (!_onlineStarted) {
1770 PRETTY_DEBUG <<
"The online has not started, starting" << std::endl;
1771 _onlineBrain.
reset();
1772 _onlineBrain.
start();
1773 _onlineStarted =
true;
1778 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
1779 _onlineBrain.
reset();
1780 _onlineBrain.
stop();
1781 _onlineStarted =
false;
1788 PRETTY_DEBUG <<
"The online is over, resetting" << std::endl;
1789 _onlineBrain.
reset();
1790 _onlineBrain.
stop();
1791 _onlineStarted =
false;
1793 PRETTY_DEBUG <<
"The online has been reset" << std::endl;
1794 PRETTY_DEBUG <<
"The user has lost, going to the game over screen" << std::endl;
1796 PRETTY_DEBUG <<
"The game over screen has been set to play next" << std::endl;
1801 PRETTY_DEBUG <<
"The online has been won, resetting" << std::endl;
1802 _onlineBrain.
reset();
1803 _onlineBrain.
stop();
1804 _onlineStarted =
false;
1806 PRETTY_DEBUG <<
"The online has been reset" << std::endl;
1807 PRETTY_DEBUG <<
"The user has won, going to the game won screen" << std::endl;
1809 PRETTY_DEBUG <<
"The game won screen has been set to play next" << std::endl;
1813 if (!_connectionInitialised) {
1814 PRETTY_INFO <<
"Initialising the connection with the server" << std::endl;
1815 _initialiseConnection();
1816 PRETTY_SUCCESS <<
"Connection with ther server initialised" << std::endl;
1817 _connectionInitialised = _networkManager->isConnected();
1820 PRETTY_DEBUG <<
"Ticking the online brain" << std::endl;
1821 _onlineBrain.
tick(_bufferPackets);
1824 PRETTY_DEBUG <<
"Ticked and rendered content" << std::endl;
1827void Main::_demoScreen()
1832 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
1834 if (!win.has_value()) {
1840 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1841 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
1843 if (!_demoInitialised) {
1844 PRETTY_DEBUG <<
"The demo brain is not initialised, initialising" << std::endl;
1846 _demoInitialised =
true;
1847 _demoStarted =
false;
1848 PRETTY_DEBUG <<
"The brain has been initialised" << std::endl;
1851 if (!_demoStarted) {
1852 PRETTY_DEBUG <<
"The demo has not started, starting" << std::endl;
1855 _demoStarted =
true;
1860 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
1863 _demoStarted =
false;
1869 PRETTY_DEBUG <<
"The demo is over, resetting" << std::endl;
1872 _demoStarted =
false;
1873 PRETTY_DEBUG <<
"The demo has been reset" << std::endl;
1874 PRETTY_DEBUG <<
"The user has lost, going to the game over screen" << std::endl;
1876 PRETTY_DEBUG <<
"The game over screen has been set to play next" << std::endl;
1881 PRETTY_DEBUG <<
"The demo has been won, resetting" << std::endl;
1884 _demoStarted =
false;
1885 PRETTY_DEBUG <<
"The demo has been reset" << std::endl;
1886 PRETTY_DEBUG <<
"The user has won, going to the game won screen" << std::endl;
1888 PRETTY_DEBUG <<
"The game won screen has been set to play next" << std::endl;
1896 PRETTY_DEBUG <<
"Ticked and rendered content" << std::endl;
1899void Main::_settingsMenu()
1902 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
1904 if (!win.has_value()) {
1910 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
1911 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
1913 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
1917 PRETTY_DEBUG <<
"Getting the sound library if present" << std::endl;
1918 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
1919 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
1923 if (!soundLib.has_value()) {
1924 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
1927 PRETTY_DEBUG <<
"Fetched the sound library" << std::endl;
1929 PRETTY_DEBUG <<
"Declaring size customisation options" << std::endl;
1930 const unsigned int titleTextSize = 40;
1931 const unsigned int bodyTextSize = 20;
1932 const unsigned int soundTextSize = 20;
1933 const unsigned int musicTextSize = 20;
1934 const unsigned int soundButtonTextSize = 20;
1935 const unsigned int soundButtonWidth = 50;
1936 const unsigned int soundButtonHeight = 20;
1937 const unsigned int musicButtonTextSize = 20;
1938 const unsigned int musicButtonWidth = 50;
1939 const unsigned int musicButtonHeight = 20;
1940 PRETTY_DEBUG <<
"Declared size customisation options" << std::endl;
1942 PRETTY_DEBUG <<
"Declaring colour customisation options" << std::endl;
1963 PRETTY_DEBUG <<
"Declared colour customisation options" << std::endl;
1965 PRETTY_DEBUG <<
"Declaring required item keys" << std::endl;
1966 const std::string titleTextKey =
"settingsMenuTitleTextKey";
1967 const std::string bodyTextKey =
"settingsMenuBodyTextKey";
1968 const std::string soundTextKey =
"settingsMenuSoundTextKey";
1969 const std::string musicTextKey =
"settingsMenuMusicTextKey";
1970 const std::string soundButtonKey =
"settingsMenuSoundButtonKey";
1971 const std::string musicButtonKey =
"settingsMenuMusicButtonKey";
1972 PRETTY_DEBUG <<
"Declared required item keys" << std::endl;
1974 PRETTY_DEBUG <<
"Getting the lists of ressources we want" << std::endl;
1986 PRETTY_DEBUG <<
"Got the list of ressources we want" << std::endl;
1988 PRETTY_DEBUG <<
"Declaring the ressources required for the settings menu (for the texts)" << std::endl;
1989 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> bodyTextItem;
1990 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> titleTextItem;
1991 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> musicTextItem;
1992 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> soundTextItem;
1993 PRETTY_DEBUG <<
"Declared the ressources required for the settings menu (for the texts)" << std::endl;
1995 PRETTY_DEBUG <<
"Declaring the ressources required for the settings menu (for the buttons)" << std::endl;
1996 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> musicButtonItem;
1997 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> soundButtonItem;
1998 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> mainMenuButtonItem;
1999 PRETTY_DEBUG <<
"Declared the ressources required for the settings menu (for the buttons)" << std::endl;
2001 PRETTY_DEBUG <<
"Declaring font holder instances" << std::endl;
2002 std::optional<std::shared_ptr<GUI::ECS::Systems::Font>> defaultFont;
2003 std::optional<std::shared_ptr<GUI::ECS::Systems::Font>> titleFont;
2004 std::optional<std::shared_ptr<GUI::ECS::Systems::Font>> bodyFont;
2005 std::optional<std::shared_ptr<GUI::ECS::Systems::Font>> buttonFont;
2006 PRETTY_DEBUG <<
"Declared font holder instances" << std::endl;
2008 PRETTY_DEBUG <<
"Declaring the ressource required for the settings menu to have a background" << std::endl;
2009 std::optional<std::shared_ptr<GUI::ECS::Components::ImageComponent>> backgroundItem;
2010 PRETTY_DEBUG <<
"Declared the ressource required for the settings menu to have a background" << std::endl;
2013 for (std::any textCast : texts) {
2015 if (textCapsule.has_value()) {
2018 std::string application = textCapsule.value()->getApplication();
2019 std::string name = textCapsule.value()->getName();
2020 if (application == titleTextKey || name == titleTextKey) {
2021 titleTextItem.emplace(textCapsule.value());
2022 }
else if (application == bodyTextKey || name == bodyTextKey) {
2023 bodyTextItem.emplace(textCapsule.value());
2024 }
else if (application == soundTextKey || name == soundTextKey) {
2025 soundTextItem.emplace(textCapsule.value());
2026 }
else if (application == musicTextKey || name == musicTextKey) {
2027 musicTextItem.emplace(textCapsule.value());
2033 for (std::any buttonCast : buttons) {
2035 if (buttonCapsule.has_value()) {
2038 std::string application = buttonCapsule.value()->getApplication();
2039 std::string name = buttonCapsule.value()->getName();
2040 if (application == soundButtonKey || name == soundButtonKey) {
2041 soundButtonItem.emplace(buttonCapsule.value());
2042 }
else if (application == _mainMenuKey) {
2043 mainMenuButtonItem.emplace(buttonCapsule.value());
2044 }
else if (application == musicButtonKey || name == musicButtonKey) {
2045 musicButtonItem.emplace(buttonCapsule.value());
2051 for (std::any backgroundCast : backgrounds) {
2053 if (!backgroundCapsule.has_value()) {
2057 backgroundCapsule.value()->getApplication() ==
"settings" || backgroundCapsule.value()->getName() ==
"settings" ||
2058 backgroundCapsule.value()->getApplication() ==
"Settings" || backgroundCapsule.value()->getName() ==
"Settings"
2060 backgroundItem.emplace(backgroundCapsule.value());
2064 if (!titleTextItem.has_value() || !bodyTextItem.has_value() || !soundTextItem.has_value() || !musicButtonItem.has_value() || !soundButtonItem.has_value() || !mainMenuButtonItem.has_value()) {
2065 PRETTY_DEBUG <<
"Fetching the fonts that will be used in the window" << std::endl;
2066 unsigned int index = 0;
2067 unsigned int titleFontIndex = 0;
2068 unsigned int bodyFontIndex = 0;
2069 unsigned int defaultFontIndex = 0;
2070 unsigned int buttonFontIndex = 0;
2071 for (std::any fontCast : fonts) {
2073 if (!fontCapsule.has_value()) {
2076 std::string applicationContext = fontCapsule.value()->getApplication();
2077 if (applicationContext ==
"title") {
2078 titleFontIndex = index;
2079 }
else if (applicationContext ==
"body") {
2080 bodyFontIndex = index;
2081 }
else if (applicationContext ==
"default") {
2082 defaultFontIndex = index;
2083 }
else if (applicationContext ==
"button") {
2084 buttonFontIndex = index;
2095 if (!defaultFontCapsule.has_value()) {
2096 PRETTY_DEBUG <<
"No default font found, aborting program" << std::endl;
2099 defaultFont.emplace(defaultFontCapsule.value());
2100 titleFont.emplace(defaultFontCapsule.value());
2101 bodyFont.emplace(defaultFontCapsule.value());
2102 buttonFont.emplace(defaultFontCapsule.value());
2103 if (titleFontCapsule.has_value()) {
2104 PRETTY_SUCCESS <<
"Title font found, not defaulting to the default font." << std::endl;
2105 titleFont.emplace(titleFontCapsule.value());
2107 if (bodyFontCapsule.has_value()) {
2108 PRETTY_SUCCESS <<
"Body font found, not defaulting to the default font." << std::endl;
2109 bodyFont.emplace(bodyFontCapsule.value());
2111 if (buttonFontCapsule.has_value()) {
2112 PRETTY_SUCCESS <<
"Button font found, not defaulting to the default font." << std::endl;
2113 buttonFont.emplace(buttonFontCapsule.value());
2115 PRETTY_DEBUG <<
"Fetched the fonts that will be used in the window" << std::endl;
2118 PRETTY_DEBUG <<
"Checking is title text component exists" << std::endl;
2119 if (!titleTextItem.has_value()) {
2120 PRETTY_DEBUG <<
"Title text component does not exist, creating" << std::endl;
2121 if (!titleFont.has_value()) {
2122 PRETTY_ERROR <<
"No font found in title font." << std::endl;
2125 PRETTY_DEBUG <<
"Creating title text component" << std::endl;
2126 titleTextItem = _createText(
2130 *(titleFont.value()),
2136 PRETTY_DEBUG <<
"Created title text component" << std::endl;
2138 PRETTY_DEBUG <<
"Checked if title text component existed" << std::endl;
2140 PRETTY_DEBUG <<
"Checking is body text component exists" << std::endl;
2141 if (!bodyTextItem.has_value()) {
2142 PRETTY_DEBUG <<
"Body text component does not exist, creating" << std::endl;
2143 if (!bodyFont.has_value()) {
2144 PRETTY_ERROR <<
"No font found in body font." << std::endl;
2147 PRETTY_DEBUG <<
"Creating body text component" << std::endl;
2148 bodyTextItem = _createText(
2151 "Comme and customise your user experience!",
2152 *(bodyFont.value()),
2158 PRETTY_DEBUG <<
"Created body text component" << std::endl;
2160 PRETTY_DEBUG <<
"Checked if body text component existed" << std::endl;
2162 PRETTY_DEBUG <<
"Checking is sound text component exists" << std::endl;
2163 if (!soundTextItem.has_value()) {
2164 PRETTY_DEBUG <<
"Sound text component does not exist, creating" << std::endl;
2165 if (!defaultFont.has_value()) {
2166 PRETTY_ERROR <<
"No font found in body font." << std::endl;
2169 PRETTY_DEBUG <<
"Creating sound text component" << std::endl;
2170 soundTextItem = _createText(
2174 *(defaultFont.value()),
2180 PRETTY_DEBUG <<
"Created sound text component" << std::endl;
2182 PRETTY_DEBUG <<
"Checked if sound text component existed" << std::endl;
2184 PRETTY_DEBUG <<
"Checking is music text component exists" << std::endl;
2185 if (!musicTextItem.has_value()) {
2186 PRETTY_DEBUG <<
"Music text component does not exist, creating" << std::endl;
2187 if (!defaultFont.has_value()) {
2188 PRETTY_ERROR <<
"No font found in body font." << std::endl;
2191 PRETTY_DEBUG <<
"Creating music text component" << std::endl;
2192 musicTextItem = _createText(
2196 *(defaultFont.value()),
2202 PRETTY_DEBUG <<
"Created music text component" << std::endl;
2204 PRETTY_DEBUG <<
"Checked if music text component existed" << std::endl;
2206 PRETTY_DEBUG <<
"Checking if the sound button is created" << std::endl;
2207 if (!soundButtonItem.has_value()) {
2208 PRETTY_DEBUG <<
"Sound button component does not exist, creating" << std::endl;
2209 if (!defaultFont.has_value()) {
2210 PRETTY_ERROR <<
"No font found in default font." << std::endl;
2213 std::string soundStatus =
"OFF";
2218 if (soundLib.has_value() && soundLib.value()->isEnabled()) {
2220 soundButtonBackgroundColour = playingSoundButtonBackgroundColour;
2221 soundButtonNormalColour = playingSoundButtonNormalColour;
2222 soundButtonHoverColour = playingSoundButtonHoverColour;
2223 soundButtonClickedColour = playingSoundButtonClickedColour;
2225 PRETTY_DEBUG <<
"Creating sound button component" << std::endl;
2226 soundButtonItem = _createButton(
2229 std::bind(&Main::_toggleSound,
this),
2233 soundButtonTextSize,
2234 soundButtonBackgroundColour,
2235 soundButtonNormalColour,
2236 soundButtonHoverColour,
2237 soundButtonClickedColour,
2240 PRETTY_DEBUG <<
"sound button component created" << std::endl;
2242 PRETTY_DEBUG <<
"Checked if the sound button was created" << std::endl;
2244 PRETTY_DEBUG <<
"Checking if the music button is created" << std::endl;
2245 if (!musicButtonItem.has_value()) {
2246 PRETTY_DEBUG <<
"Sound button component does not exist, creating" << std::endl;
2247 if (!defaultFont.has_value()) {
2248 PRETTY_ERROR <<
"No font found in default font." << std::endl;
2251 std::string musicStatus =
"OFF";
2258 musicButtonBackgroundColour = stoppedMusicButtonBackgroundColour;
2259 musicButtonNormalColour = stoppedMusicButtonNormalColour;
2260 musicButtonHoverColour = stoppedMusicButtonHoverColour;
2261 musicButtonClickedColour = stoppedMusicButtonClickedColour;
2263 PRETTY_DEBUG <<
"Creating music button component" << std::endl;
2264 musicButtonItem = _createButton(
2267 std::bind(&Main::_toggleMusic,
this),
2271 musicButtonTextSize,
2272 musicButtonBackgroundColour,
2273 musicButtonNormalColour,
2274 musicButtonHoverColour,
2275 musicButtonClickedColour,
2278 PRETTY_DEBUG <<
"music button component created" << std::endl;
2280 PRETTY_DEBUG <<
"Checked if the music button was created" << std::endl;
2282 PRETTY_DEBUG <<
"Checking if the home button exists" << std::endl;
2283 if (!mainMenuButtonItem.has_value()) {
2284 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
2285 mainMenuButtonItem = _createButton(
2288 std::bind(&Main::_goHome,
this),
2300 PRETTY_DEBUG <<
"Checked if the home button existed" << std::endl;
2304 backgroundItem.value()->setDimension(win.value()->getDimensions());
2305 backgroundItem.value()->setPosition({ 0, 0 });
2309 const float step = 10;
2311 titleTextItem.value()->setPosition({ posX, posY });
2312 posY += step + titleTextSize;
2313 bodyTextItem.value()->setPosition({ posX, posY });
2314 posY += step + bodyTextSize;
2315 soundTextItem.value()->setPosition({ posX, posY });
2316 posX = _getScreenCenterX();
2317 soundButtonItem.value()->setPosition({ posX, posY });
2319 posY += step + soundTextSize;
2320 musicTextItem.value()->setPosition({ posX, posY });
2321 posX = _getScreenCenterX();
2322 musicButtonItem.value()->setPosition({ posX, posY });
2324 posY += step + musicTextSize;
2325 mainMenuButtonItem.value()->setPosition({ posX, posY });
2328 PRETTY_DEBUG <<
"Setting the text of the buttons" << std::endl;
2329 std::string soundStatus =
"OFF";
2330 if (soundLib.has_value() && soundLib.value()->isEnabled()) {
2333 soundButtonItem.value()->setTextString(soundStatus);
2334 std::string musicStatus =
"OFF";
2338 musicButtonItem.value()->setTextString(musicStatus);
2339 PRETTY_DEBUG <<
"The text of the buttons has been set" << std::endl;
2341 PRETTY_DEBUG <<
"Setting the colour of the buttons" << std::endl;
2343 if (soundLib.has_value() && soundLib.value()->isEnabled()) {
2344 soundButtonItem.value()->setNormalColor(playingSoundButtonBackgroundColour);
2345 soundButtonItem.value()->setHoverColor(playingSoundButtonBackgroundColour);
2346 soundButtonItem.value()->setClickedColor(playingSoundButtonBackgroundColour);
2347 soundButtonItem.value()->setTextNormalColor(playingSoundButtonNormalColour);
2348 soundButtonItem.value()->setTextHoverColor(playingSoundButtonHoverColour);
2349 soundButtonItem.value()->setTextClickedColor(playingSoundButtonClickedColour);
2351 soundButtonItem.value()->setNormalColor(stoppedSoundButtonBackgroundColour);
2352 soundButtonItem.value()->setHoverColor(stoppedSoundButtonBackgroundColour);
2353 soundButtonItem.value()->setClickedColor(stoppedSoundButtonBackgroundColour);
2354 soundButtonItem.value()->setTextNormalColor(stoppedSoundButtonNormalColour);
2355 soundButtonItem.value()->setTextHoverColor(stoppedSoundButtonHoverColour);
2356 soundButtonItem.value()->setTextClickedColor(stoppedSoundButtonClickedColour);
2360 musicButtonItem.value()->setNormalColor(playingMusicButtonBackgroundColour);
2361 musicButtonItem.value()->setHoverColor(playingMusicButtonBackgroundColour);
2362 musicButtonItem.value()->setClickedColor(playingMusicButtonBackgroundColour);
2363 musicButtonItem.value()->setTextNormalColor(playingMusicButtonNormalColour);
2364 musicButtonItem.value()->setTextHoverColor(playingMusicButtonHoverColour);
2365 musicButtonItem.value()->setTextClickedColor(playingMusicButtonClickedColour);
2367 musicButtonItem.value()->setNormalColor(stoppedMusicButtonBackgroundColour);
2368 musicButtonItem.value()->setHoverColor(stoppedMusicButtonBackgroundColour);
2369 musicButtonItem.value()->setClickedColor(stoppedMusicButtonBackgroundColour);
2370 musicButtonItem.value()->setTextNormalColor(stoppedMusicButtonNormalColour);
2371 musicButtonItem.value()->setTextHoverColor(stoppedMusicButtonHoverColour);
2372 musicButtonItem.value()->setTextClickedColor(stoppedMusicButtonClickedColour);
2374 PRETTY_DEBUG <<
"The colour of the buttons has been set" << std::endl;
2376 PRETTY_DEBUG <<
"Displaying elements on the screen" << std::endl;
2377 win.value()->draw(*(backgroundItem.value()));
2379 win.value()->draw(*(titleTextItem.value()));
2380 win.value()->draw(*(bodyTextItem.value()));
2381 PRETTY_DEBUG <<
"Title and body text rendered" << std::endl;
2382 win.value()->draw(*(soundTextItem.value()));
2383 win.value()->draw(*(soundButtonItem.value()));
2384 PRETTY_DEBUG <<
"Sound button and text rendered" << std::endl;
2385 win.value()->draw(*(musicTextItem.value()));
2386 win.value()->draw(*(musicButtonItem.value()));
2387 PRETTY_DEBUG <<
"Music button and text rendered" << std::endl;
2388 win.value()->draw(*(mainMenuButtonItem.value()));
2390 PRETTY_DEBUG <<
"Displayed elements on the screen" << std::endl;
2393void Main::_unknownScreen()
2395 bool bodyTextFound =
false;
2396 bool titleTextFound =
false;
2397 bool homeButtonFound =
false;
2399 const std::string titleKey =
"unknownScreenTitle";
2400 const std::string bodyKey =
"unknownScreenBody";
2402 const unsigned int titleTextSize = 40;
2403 const unsigned int bodyTextSize = 20;
2407 std::shared_ptr<GUI::ECS::Components::TextComponent> bodyItem;
2408 std::shared_ptr<GUI::ECS::Components::TextComponent> titleItem;
2409 std::shared_ptr<GUI::ECS::Components::ButtonComponent> homeItem;
2414 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
2416 if (!win.has_value()) {
2422 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
2423 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
2425 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
2430 for (std::any textCast : texts) {
2433 if (textCapsule.value()->getApplication() == titleKey) {
2434 titleTextFound =
true;
2435 titleItem = textCapsule.value();
2436 titleItem->setSize(titleTextSize);
2437 }
else if (textCapsule.value()->getApplication() == bodyKey) {
2438 bodyTextFound =
true;
2439 bodyItem = textCapsule.value();
2440 bodyItem->setSize(bodyTextSize);
2447 for (std::any buttonCast : buttons) {
2449 if (buttonCapsule) {
2450 if (buttonCapsule.value()->getApplication() == _mainMenuKey) {
2451 homeButtonFound =
true;
2452 homeItem = buttonCapsule.value();
2457 if (!titleTextFound) {
2459 if (!titleFont.has_value()) {
2460 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the title text of the unknown screen screen." << std::endl;
2463 titleItem = _createText(
2467 *(titleFont.value()),
2475 if (!bodyTextFound) {
2477 if (!bodyFont.has_value()) {
2478 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the body text of the unknown screen screen." << std::endl;
2481 bodyItem = _createText(
2484 "It seems like you have landed on an unknown page.",
2485 *(bodyFont.value()),
2493 if (!homeButtonFound) {
2494 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
2495 homeItem = _createButton(
2498 std::bind(&Main::_goHome,
this),
2511 unsigned int posx = _getScreenCenterX();
2512 unsigned int posy = _getScreenCenterY();
2514 const unsigned int titleOffest = (2 * titleTextSize);
2515 const unsigned int titleLength = (titleItem->getSize() + 1) / 2 + titleOffest;
2516 const unsigned int bodyLength = ((bodyItem->getSize() + 1) / 2) + (17 * bodyTextSize);
2517 const unsigned int homeItemLength = (homeItem->getTextSize() + 1) / 2 + titleOffest;
2519 PRETTY_DEBUG <<
"Lengths:\n- titleLength: '" << titleLength <<
"'\n- bodyLength: '" << bodyLength <<
"'\n- homeItemLength: '" << homeItemLength <<
"'" << std::endl;
2520 PRETTY_DEBUG <<
"Positions:\n- posx: '" << posx <<
"'\n- posy: '" << posy <<
"'" << std::endl;
2523 titleItem->setPosition({ posx - titleLength, posy });
2524 bodyItem->setPosition({ posx - bodyLength, posy + 60 });
2525 homeItem->setPosition({ posx - homeItemLength, posy + 100 });
2526 PRETTY_DEBUG <<
"Component's positions updated for the current screen." << std::endl;
2527 win.value()->draw(*titleItem);
2528 win.value()->draw(*bodyItem);
2529 win.value()->draw(*homeItem);
2530 PRETTY_SUCCESS <<
"Component's positions drawn successfully." << std::endl;
2533void Main::_gameOverScreen()
2536 PRETTY_DEBUG <<
"In the _gameOverScreen function." << std::endl;
2538 bool bodyTextFound =
false;
2539 bool titleTextFound =
false;
2540 bool homeButtonFound =
false;
2541 bool backgroundFound =
false;
2543 const std::string titleKey =
"GameOverScreenTitle";
2544 const std::string bodyKey =
"GameOverScreenBody";
2545 const std::string backgroundKey =
"gameOver";
2549 std::shared_ptr<GUI::ECS::Components::TextComponent> bodyItem;
2550 std::shared_ptr<GUI::ECS::Components::TextComponent> titleItem;
2551 std::shared_ptr<GUI::ECS::Components::ButtonComponent> homeItem;
2552 std::shared_ptr<GUI::ECS::Components::ImageComponent> backgroundItem;
2558 PRETTY_DEBUG <<
"vector texts size: " << texts.size() << std::endl;
2559 PRETTY_DEBUG <<
"vector buttons size: " << buttons.size() << std::endl;
2560 PRETTY_DEBUG <<
"vector backgrounds size: " << backgrounds.size() << std::endl;
2562 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
2564 if (!win.has_value()) {
2570 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
2571 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
2573 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
2577 PRETTY_DEBUG <<
"Fetching the text components if present." << std::endl;
2578 for (std::any textCast : texts) {
2580 if (textCapsule.has_value()) {
2581 if (textCapsule.value()->getApplication() == titleKey) {
2582 titleTextFound =
true;
2583 titleItem = textCapsule.value();
2585 }
else if (textCapsule.value()->getApplication() == bodyKey) {
2586 bodyTextFound =
true;
2587 bodyItem = textCapsule.value();
2594 PRETTY_DEBUG <<
"Fetched the text components that were present." << std::endl;
2596 PRETTY_DEBUG <<
"Attempting to fetch content for the button." << std::endl;
2597 for (std::any buttonCast : buttons) {
2599 if (buttonCapsule.has_value() && buttonCapsule.value()->getApplication() == _mainMenuKey) {
2600 homeButtonFound =
true;
2601 homeItem = buttonCapsule.value();
2605 PRETTY_DEBUG <<
"Fetched the button content." << std::endl;
2607 PRETTY_DEBUG <<
"Attempting to fetch content for the background." << std::endl;
2608 for (std::any backgroundCast : backgrounds) {
2610 if (backgroundCapsule.has_value() && backgroundCapsule.value()->getApplication() == backgroundKey) {
2611 backgroundFound =
true;
2612 backgroundItem = backgroundCapsule.value();
2616 PRETTY_DEBUG <<
"Fetched the background content." << std::endl;
2620 PRETTY_DEBUG <<
"Checking the text for the title." << std::endl;
2621 if (!titleTextFound) {
2622 PRETTY_WARNING <<
"No title text instance found, creating instance." << std::endl;
2624 if (!titleFont.has_value()) {
2625 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the title text of the game over screen screen." << std::endl;
2628 titleItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(titleFont.value()),
"Game Over!");
2629 titleItem->setApplication(titleKey);
2630 titleItem->setNormalColor(textColour);
2631 titleItem->setHoverColor(textColour);
2632 titleItem->setClickedColor(textColour);
2636 PRETTY_DEBUG <<
"Checked the text for the title." << std::endl;
2638 PRETTY_DEBUG <<
"Checking text content for the body." << std::endl;
2639 if (!bodyTextFound) {
2640 PRETTY_WARNING <<
"No body text instance found, creating instance." << std::endl;
2642 if (!bodyFont.has_value()) {
2643 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the body text of the game over screen screen." << std::endl;
2646 bodyItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(bodyFont.value()),
"You have died!", 20);
2647 bodyItem->setApplication(bodyKey);
2648 bodyItem->setNormalColor(textColour);
2649 bodyItem->setHoverColor(textColour);
2650 bodyItem->setClickedColor(textColour);
2654 PRETTY_DEBUG <<
"Checked the text content for the body." << std::endl;
2656 PRETTY_DEBUG <<
"Checking if the Home button exists." << std::endl;
2657 if (!homeButtonFound) {
2658 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
2659 homeItem = _createButton(
2662 std::bind(&Main::_goHome,
this),
2674 PRETTY_DEBUG <<
"Checked if the home button existed." << std::endl;
2676 if (!backgroundFound) {
2677 PRETTY_WARNING <<
"Background not found, changing the text components" << std::endl;
2679 titleItem->setNormalColor(defaultColourForNoBackground);
2680 titleItem->setHoverColor(defaultColourForNoBackground);
2681 titleItem->setClickedColor(defaultColourForNoBackground);
2682 bodyItem->setNormalColor(defaultColourForNoBackground);
2683 bodyItem->setHoverColor(defaultColourForNoBackground);
2684 bodyItem->setClickedColor(defaultColourForNoBackground);
2687 PRETTY_DEBUG <<
"Checking the coordinates for the center of the x and y axis." << std::endl;
2688 unsigned int posx = _getScreenCenterX();
2689 unsigned int posy = _getScreenCenterY();
2690 PRETTY_DEBUG <<
"Center of the screen is at (" << posx <<
", " << posy <<
")" << std::endl;
2692 PRETTY_DEBUG <<
"The items that are currently loaded, are:\n- " << *titleItem <<
"\n- " << *bodyItem <<
"\n- " << *homeItem << std::endl;
2694 PRETTY_DEBUG <<
"Setting the position of the components." << std::endl;
2695 titleItem->setPosition({ posx, posy });
2696 PRETTY_DEBUG <<
"Position for the title item is set." << std::endl;
2697 bodyItem->setPosition({ posx, posy + 40 });
2698 PRETTY_DEBUG <<
"Position for the body item is set." << std::endl;
2699 homeItem->setPosition({ posx, posy + 100 });
2700 PRETTY_DEBUG <<
"Position for the home item is set." << std::endl;
2701 if (backgroundFound) {
2702 backgroundItem->setDimension({ _windowWidth, _windowHeight });
2703 win.value()->draw(*backgroundItem);
2705 PRETTY_DEBUG <<
"Component's positions updated for the current screen." << std::endl;
2706 win.value()->draw(*titleItem);
2708 win.value()->draw(*bodyItem);
2710 win.value()->draw(*homeItem);
2712 PRETTY_SUCCESS <<
"Component's positions drawn successfully." << std::endl;
2715void Main::_gameWonScreen()
2718 PRETTY_DEBUG <<
"In the _gameWonScreen function." << std::endl;
2720 bool bodyTextFound =
false;
2721 bool titleTextFound =
false;
2722 bool homeButtonFound =
false;
2723 bool backgroundFound =
false;
2725 const std::string titleKey =
"GameWonScreenTitle";
2726 const std::string bodyKey =
"GameWonScreenBody";
2727 const std::string backgroundKey =
"gameWon";
2731 std::shared_ptr<GUI::ECS::Components::TextComponent> bodyItem;
2732 std::shared_ptr<GUI::ECS::Components::TextComponent> titleItem;
2733 std::shared_ptr<GUI::ECS::Components::ButtonComponent> homeItem;
2734 std::shared_ptr<GUI::ECS::Components::ImageComponent> backgroundItem;
2740 PRETTY_DEBUG <<
"vector texts size: " << texts.size() << std::endl;
2741 PRETTY_DEBUG <<
"vector buttons size: " << buttons.size() << std::endl;
2742 PRETTY_DEBUG <<
"vector backgrounds size: " << backgrounds.size() << std::endl;
2744 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
2746 if (!win.has_value()) {
2752 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
2753 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
2755 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
2759 PRETTY_DEBUG <<
"Fetching the text components if present." << std::endl;
2760 for (std::any textCast : texts) {
2762 if (textCapsule.has_value()) {
2763 if (textCapsule.value()->getApplication() == titleKey) {
2764 titleTextFound =
true;
2765 titleItem = textCapsule.value();
2767 }
else if (textCapsule.value()->getApplication() == bodyKey) {
2768 bodyTextFound =
true;
2769 bodyItem = textCapsule.value();
2776 PRETTY_DEBUG <<
"Fetched the text components that were present." << std::endl;
2778 PRETTY_DEBUG <<
"Attempting to fetch content for the button." << std::endl;
2779 for (std::any buttonCast : buttons) {
2781 if (buttonCapsule.has_value() && buttonCapsule.value()->getApplication() == _mainMenuKey) {
2782 homeButtonFound =
true;
2783 homeItem = buttonCapsule.value();
2787 PRETTY_DEBUG <<
"Fetched the button content." << std::endl;
2789 PRETTY_DEBUG <<
"Attempting to fetch content for the background." << std::endl;
2790 for (std::any backgroundCast : backgrounds) {
2792 if (backgroundCapsule.has_value() && backgroundCapsule.value()->getApplication() == backgroundKey) {
2793 backgroundFound =
true;
2794 backgroundItem = backgroundCapsule.value();
2798 PRETTY_DEBUG <<
"Fetched the background content." << std::endl;
2802 PRETTY_DEBUG <<
"Checking the text for the title." << std::endl;
2803 if (!titleTextFound) {
2804 PRETTY_WARNING <<
"No title text instance found, creating instance." << std::endl;
2806 if (!titleFont.has_value()) {
2807 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the title text of the game won screen screen." << std::endl;
2810 titleItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(titleFont.value()),
"Game Won!");
2811 titleItem->setApplication(titleKey);
2812 titleItem->setNormalColor(textColour);
2813 titleItem->setHoverColor(textColour);
2814 titleItem->setClickedColor(textColour);
2818 PRETTY_DEBUG <<
"Checked the text for the title." << std::endl;
2820 PRETTY_DEBUG <<
"Checking text content for the body." << std::endl;
2821 if (!bodyTextFound) {
2822 PRETTY_WARNING <<
"No body text instance found, creating instance." << std::endl;
2824 if (!bodyFont.has_value()) {
2825 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the body text of the game won screen screen." << std::endl;
2828 bodyItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(bodyFont.value()),
"You have won!", 20);
2829 bodyItem->setApplication(bodyKey);
2830 bodyItem->setNormalColor(textColour);
2831 bodyItem->setHoverColor(textColour);
2832 bodyItem->setClickedColor(textColour);
2836 PRETTY_DEBUG <<
"Checked the text content for the body." << std::endl;
2838 PRETTY_DEBUG <<
"Checking if the Home button exists." << std::endl;
2839 if (!homeButtonFound) {
2840 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
2841 homeItem = _createButton(
2844 std::bind(&Main::_goHome,
this),
2856 PRETTY_DEBUG <<
"Checked if the home button existed." << std::endl;
2858 if (!backgroundFound) {
2859 PRETTY_WARNING <<
"Background not found, changing the text components" << std::endl;
2861 titleItem->setNormalColor(defaultColourForNoBackground);
2862 titleItem->setHoverColor(defaultColourForNoBackground);
2863 titleItem->setClickedColor(defaultColourForNoBackground);
2864 titleItem->setNormalColor(defaultColourForNoBackground);
2865 titleItem->setHoverColor(defaultColourForNoBackground);
2866 titleItem->setClickedColor(defaultColourForNoBackground);
2869 PRETTY_DEBUG <<
"Checking the coordinates for the center of the x and y axis." << std::endl;
2870 unsigned int posx = _getScreenCenterX();
2871 unsigned int posy = _getScreenCenterY();
2872 PRETTY_DEBUG <<
"Center of the screen is at (" << posx <<
", " << posy <<
")" << std::endl;
2874 PRETTY_DEBUG <<
"The items that are currently loaded, are:\n- " << *titleItem <<
"\n- " << *bodyItem <<
"\n- " << *homeItem << std::endl;
2876 PRETTY_DEBUG <<
"Setting the position of the components." << std::endl;
2877 titleItem->setPosition({ posx, posy });
2878 PRETTY_DEBUG <<
"Position for the title item is set." << std::endl;
2879 bodyItem->setPosition({ posx, posy + 40 });
2880 PRETTY_DEBUG <<
"Position for the body item is set." << std::endl;
2881 homeItem->setPosition({ posx, posy + 100 });
2882 PRETTY_DEBUG <<
"Position for the home item is set." << std::endl;
2883 if (backgroundFound) {
2884 backgroundItem->setDimension({ _windowWidth, _windowHeight });
2885 win.value()->draw(*backgroundItem);
2887 PRETTY_DEBUG <<
"Component's positions updated for the current screen." << std::endl;
2888 win.value()->draw(*titleItem);
2890 win.value()->draw(*bodyItem);
2892 win.value()->draw(*homeItem);
2894 PRETTY_SUCCESS <<
"Component's positions drawn successfully." << std::endl;
2897void Main::_mainMenuScreen()
2899 const std::string startGameKey =
"MainMenuStartGame";
2900 const std::string onlineGameKey =
"MainMenuOnlineGame";
2901 const std::string settingsKey =
"MainMenuSettings";
2902 const std::string exitMenuKey =
"MainMenuexitMenu";
2904 const unsigned int textSize = 20;
2905 const unsigned int buttonWidth = 200;
2906 const unsigned int buttonHeight = 30;
2916 std::shared_ptr<GUI::ECS::Components::ImageComponent> background;
2917 std::shared_ptr<GUI::ECS::Components::ImageComponent> icon;
2919 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> startGame;
2920 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> onlineGame;
2921 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> settings;
2922 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> exitWindow;
2924 unsigned int heightPos = 0;
2925 const unsigned int heightStep = 40;
2928 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
2930 if (!win.has_value()) {
2936 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
2937 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
2939 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
2943 for (
const std::any node : images) {
2945 if (!nodeCapsule.has_value()) {
2946 PRETTY_WARNING <<
"The uncasting of an image component has failed." << std::endl;
2950 nodeCapsule.value()->getName() ==
"mainMenu" ||
2951 nodeCapsule.value()->getApplication() ==
"mainMenu" ||
2952 nodeCapsule.value()->getName() ==
"Main Menu" ||
2953 nodeCapsule.value()->getApplication() ==
"Main Menu"
2955 PRETTY_INFO <<
"Background found, assinning to variable" << std::endl;
2956 background = nodeCapsule.value();
2958 nodeCapsule.value()->getName() ==
"icon" ||
2959 nodeCapsule.value()->getApplication() ==
"icon" ||
2960 nodeCapsule.value()->getName() ==
"Main Icon" ||
2961 nodeCapsule.value()->getApplication() ==
"Main Icon" ||
2962 nodeCapsule.value()->getName() ==
"R-type" ||
2963 nodeCapsule.value()->getApplication() ==
"R-type"
2965 PRETTY_INFO <<
"Icon found, assinning to variable" << std::endl;
2966 icon = nodeCapsule.value();
2970 for (
const std::any node : buttons) {
2972 if (!nodeCapsule.has_value()) {
2973 PRETTY_WARNING <<
"The uncasting of a button component has failed." << std::endl;
2977 nodeCapsule.value()->getName() == startGameKey ||
2978 nodeCapsule.value()->getApplication() == startGameKey
2980 PRETTY_INFO <<
"Start Game found, assinning to variable" << std::endl;
2981 startGame.emplace(nodeCapsule.value());
2983 nodeCapsule.value()->getName() == onlineGameKey ||
2984 nodeCapsule.value()->getApplication() == onlineGameKey
2986 PRETTY_INFO <<
"Online Game found, assinning to variable" << std::endl;
2987 onlineGame.emplace(nodeCapsule.value());
2989 nodeCapsule.value()->getName() == settingsKey ||
2990 nodeCapsule.value()->getApplication() == settingsKey
2992 PRETTY_INFO <<
"Settings found, assinning to variable" << std::endl;
2993 settings.emplace(nodeCapsule.value());
2995 nodeCapsule.value()->getName() == exitMenuKey ||
2996 nodeCapsule.value()->getApplication() == exitMenuKey
2998 PRETTY_INFO <<
"Exit Menu found, assinning to variable" << std::endl;
2999 exitWindow.emplace(nodeCapsule.value());
3004 PRETTY_DEBUG <<
"Setting the icon at the top center of the main menu." << std::endl;
3005 const std::pair<int, int> windowDimensions = win.value()->getDimensions();
3006 PRETTY_DEBUG <<
"The window dimensions are: " << windowDimensions << std::endl;
3007 if (windowDimensions.first == 0.0 || windowDimensions.second == 0.0) {
3008 PRETTY_CRITICAL <<
"Skipping calculations and rendering because the window is smaller or equal to 0." << std::endl;
3012 PRETTY_DEBUG <<
"Getting the icon dimensions" << std::endl;
3013 const std::pair<float, float> iconDimensions = icon->getDimension();
3014 PRETTY_DEBUG <<
"The icon dimensions are : " << iconDimensions << std::endl;
3015 if (iconDimensions.first <= 0 || iconDimensions.second <= 0) {
3016 PRETTY_WARNING <<
"Icon dimensions are zero, skipping position adjustment." << std::endl;
3020 PRETTY_DEBUG <<
"Calculating the center of the window based on the image and the window dimensions." << std::endl;
3021 const float xCenter = windowDimensions.first / 2.0f;
3022 const int x = xCenter - (iconDimensions.first / 2);
3024 PRETTY_DEBUG <<
"Calculating the y-coordinate (for the top position)." << std::endl;
3025 const int y = (windowDimensions.second / 10);
3026 PRETTY_DEBUG <<
"The adjusted coordinates for the icon are: " << std::pair<int, int>(x, y) << std::endl;
3027 PRETTY_DEBUG <<
"The coordinates are: " << std::pair<int, int>(x, y) << std::endl;
3028 icon->setPosition({ x, y });
3030 PRETTY_DEBUG <<
"Setting the size of the background to that of the window" << std::endl;
3031 background->setPosition({ 0, 0 });
3032 background->setDimension({ windowDimensions.first, windowDimensions.second });
3033 PRETTY_DEBUG <<
"Background position set" << std::endl;
3035 int verticalIconHeight = 0;
3036 if (iconDimensions.second < 1) {
3037 verticalIconHeight =
static_cast<int>(std::round(iconDimensions.second * 1000)) + 100;
3038 PRETTY_DEBUG <<
"Calculated converted icon height's value is: " << verticalIconHeight << std::endl;
3040 verticalIconHeight = iconDimensions.second;
3042 heightPos = y + verticalIconHeight;
3044 PRETTY_DEBUG <<
"Checking if the Start game button exists." << std::endl;
3045 if (!startGame.has_value()) {
3046 PRETTY_WARNING <<
"Start Game button not found, creating" << std::endl;
3049 startGameKey,
"Start Game", std::bind(&Main::_goDemo,
this),
"_goDemo", buttonWidth, buttonHeight, textSize, bg, normal, hover, clicked
3054 startGame.value()->setPosition({ x, heightPos });
3055 heightPos += heightStep;
3057 PRETTY_DEBUG <<
"Checking if the Online game button exists." << std::endl;
3058 if (!onlineGame.has_value()) {
3059 PRETTY_WARNING <<
"Online Game button not found, creating" << std::endl;
3062 onlineGameKey,
"Online Game", std::bind(&Main::_goConnectionAddress,
this),
"_goConnectionAddress", buttonWidth, buttonHeight, textSize, bg, normal, hover, clicked
3067 onlineGame.value()->setPosition({ x, heightPos });
3068 heightPos += heightStep;
3070 PRETTY_DEBUG <<
"Checking if the settings button exists." << std::endl;
3071 if (!settings.has_value()) {
3072 PRETTY_WARNING <<
"Settings button not found, creating" << std::endl;
3075 settingsKey,
"Settings", std::bind(&Main::_goSettings,
this),
"_goSettings", buttonWidth, buttonHeight, textSize, bg, normal, hover, clicked
3080 settings.value()->setPosition({ x, heightPos });
3081 heightPos += heightStep;
3083 PRETTY_DEBUG <<
"Checking if the exit window game button exists." << std::endl;
3084 if (!exitWindow.has_value()) {
3085 PRETTY_WARNING <<
"Exit Window button not found, creating" << std::endl;
3088 exitMenuKey,
"Exit Window", std::bind(&Main::_goExit,
this),
"_goExit", buttonWidth, buttonHeight, textSize, bg, normal, hover, clicked
3093 exitWindow.value()->setPosition({ x, heightPos });
3094 heightPos += heightStep;
3096 PRETTY_DEBUG <<
"Drawing the elements required for the main menu to be displayed." << std::endl;
3097 win.value()->draw(*background);
3099 win.value()->draw(*icon);
3101 win.value()->draw(*(startGame.value()));
3103 win.value()->draw(*(onlineGame.value()));
3105 win.value()->draw(*(settings.value()));
3107 win.value()->draw(*(exitWindow.value()));
3111void Main::_bossFightScreen()
3114 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
3116 if (!win.has_value()) {
3122 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
3123 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
3125 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
3130void Main::_connectionFailedScreen()
3133 PRETTY_DEBUG <<
"In the _connectionFailedScreen function." << std::endl;
3135 bool bodyTextFound =
false;
3136 bool titleTextFound =
false;
3137 bool homeButtonFound =
false;
3138 bool backgroundFound =
false;
3139 bool connectButtonFound =
false;
3141 const std::string bodyKey =
"ConnectionFailedScreenBody";
3142 const std::string titleKey =
"ConnectionFailedScreenTitle";
3143 const std::string backgroundKey =
"connectionFailed";
3144 const std::string connectionButtonKey =
"ConnectionFailedScreenConnectButton";
3148 std::shared_ptr<GUI::ECS::Components::TextComponent> bodyItem;
3149 std::shared_ptr<GUI::ECS::Components::TextComponent> titleItem;
3150 std::shared_ptr<GUI::ECS::Components::ButtonComponent> homeItem;
3151 std::shared_ptr<GUI::ECS::Components::ButtonComponent> connectItem;
3152 std::shared_ptr<GUI::ECS::Components::ImageComponent> backgroundItem;
3158 PRETTY_DEBUG <<
"vector texts size: " << texts.size() << std::endl;
3159 PRETTY_DEBUG <<
"vector buttons size: " << buttons.size() << std::endl;
3160 PRETTY_DEBUG <<
"vector backgrounds size: " << backgrounds.size() << std::endl;
3162 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
3164 if (!win.has_value()) {
3170 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
3171 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
3173 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
3177 PRETTY_DEBUG <<
"Fetching the text components if present." << std::endl;
3178 for (std::any textCast : texts) {
3180 if (textCapsule.has_value()) {
3181 if (textCapsule.value()->getApplication() == titleKey) {
3182 titleTextFound =
true;
3183 titleItem = textCapsule.value();
3185 }
else if (textCapsule.value()->getApplication() == bodyKey) {
3186 bodyTextFound =
true;
3187 bodyItem = textCapsule.value();
3194 PRETTY_DEBUG <<
"Fetched the text components that were present." << std::endl;
3196 PRETTY_DEBUG <<
"Attempting to fetch content for the button." << std::endl;
3197 for (std::any buttonCast : buttons) {
3199 if (buttonCapsule.has_value()) {
3200 if (buttonCapsule.value()->getApplication() == _mainMenuKey) {
3201 homeButtonFound =
true;
3202 homeItem = buttonCapsule.value();
3204 }
else if (buttonCapsule.value()->getApplication() == connectionButtonKey) {
3205 connectButtonFound =
true;
3206 connectItem = buttonCapsule.value();
3207 PRETTY_DEBUG <<
"Connection button found" << std::endl;
3211 PRETTY_DEBUG <<
"Fetched the button content." << std::endl;
3213 PRETTY_DEBUG <<
"Attempting to fetch content for the background." << std::endl;
3214 for (std::any backgroundCast : backgrounds) {
3216 if (backgroundCapsule.has_value() && backgroundCapsule.value()->getApplication() == backgroundKey) {
3217 backgroundFound =
true;
3218 backgroundItem = backgroundCapsule.value();
3222 PRETTY_DEBUG <<
"Fetched the background content." << std::endl;
3226 PRETTY_DEBUG <<
"Checking the text for the title." << std::endl;
3227 if (!titleTextFound) {
3228 PRETTY_WARNING <<
"No title text instance found, creating instance." << std::endl;
3230 if (!titleFont.has_value()) {
3231 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the title text of the game won screen screen." << std::endl;
3234 titleItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(titleFont.value()),
"Connection failed!");
3235 titleItem->setApplication(titleKey);
3236 titleItem->setNormalColor(textColour);
3237 titleItem->setHoverColor(textColour);
3238 titleItem->setClickedColor(textColour);
3242 PRETTY_DEBUG <<
"Checked the text for the title." << std::endl;
3244 PRETTY_DEBUG <<
"Checking text content for the body." << std::endl;
3245 if (!bodyTextFound) {
3246 PRETTY_WARNING <<
"No body text instance found, creating instance." << std::endl;
3248 if (!bodyFont.has_value()) {
3249 PRETTY_CRITICAL <<
"There is no font to be extracted for creating the body text of the game won screen screen." << std::endl;
3252 bodyItem = std::make_shared<GUI::ECS::Components::TextComponent>(_baseId, *(bodyFont.value()),
"You are not connected to the server!", 20);
3253 bodyItem->setApplication(bodyKey);
3254 bodyItem->setNormalColor(textColour);
3255 bodyItem->setHoverColor(textColour);
3256 bodyItem->setClickedColor(textColour);
3260 PRETTY_DEBUG <<
"Checked the text content for the body." << std::endl;
3262 PRETTY_DEBUG <<
"Checking if the Home button exists." << std::endl;
3263 if (!homeButtonFound) {
3264 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
3265 homeItem = _createButton(
3268 std::bind(&Main::_goHome,
this),
3280 PRETTY_DEBUG <<
"Checked if the home button existed." << std::endl;
3282 PRETTY_DEBUG <<
"Checking if the Connect button exists." << std::endl;
3283 if (!connectButtonFound) {
3284 PRETTY_WARNING <<
"Connect button not found, creating" << std::endl;
3285 connectItem = _createButton(
3286 connectionButtonKey,
3287 "Connection address",
3288 std::bind(&Main::_goConnectionAddress,
this),
3289 "_goConnectionAddress",
3300 PRETTY_DEBUG <<
"Checked if the home button existed." << std::endl;
3302 if (!backgroundFound) {
3303 PRETTY_WARNING <<
"Background not found, changing the text components" << std::endl;
3305 titleItem->setNormalColor(defaultColourForNoBackground);
3306 titleItem->setHoverColor(defaultColourForNoBackground);
3307 titleItem->setClickedColor(defaultColourForNoBackground);
3308 bodyItem->setNormalColor(defaultColourForNoBackground);
3309 bodyItem->setHoverColor(defaultColourForNoBackground);
3310 bodyItem->setClickedColor(defaultColourForNoBackground);
3313 PRETTY_DEBUG <<
"Checking the coordinates for the center of the x and y axis." << std::endl;
3314 unsigned int posx = 40;
3315 unsigned int posy = 30;
3316 PRETTY_DEBUG <<
"Center of the screen is at (" << posx <<
", " << posy <<
")" << std::endl;
3318 PRETTY_DEBUG <<
"The items that are currently loaded, are:\n- " << *titleItem <<
"\n- " << *bodyItem <<
"\n- " << *homeItem << std::endl;
3320 PRETTY_DEBUG <<
"Setting the position of the components." << std::endl;
3321 titleItem->setPosition({ posx, posy });
3322 PRETTY_DEBUG <<
"Position for the title item is set." << std::endl;
3323 bodyItem->setPosition({ posx, posy + 40 });
3324 PRETTY_DEBUG <<
"Position for the body item is set." << std::endl;
3325 homeItem->setPosition({ posx, posy + 100 });
3326 PRETTY_DEBUG <<
"Position for the home item is set." << std::endl;
3327 connectItem->setPosition({ posx, posy + 160 });
3328 PRETTY_DEBUG <<
"Position for the connect item is set." << std::endl;
3329 if (backgroundFound) {
3330 backgroundItem->setDimension({ _windowWidth, _windowHeight });
3331 win.value()->draw(*backgroundItem);
3333 PRETTY_DEBUG <<
"Component's positions updated for the current screen." << std::endl;
3334 win.value()->draw(*titleItem);
3336 win.value()->draw(*bodyItem);
3338 win.value()->draw(*homeItem);
3340 win.value()->draw(*connectItem);
3342 PRETTY_SUCCESS <<
"Component's positions drawn successfully." << std::endl;
3345void Main::_connectionAddressScreen()
3350 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
3352 if (!win.has_value()) {
3358 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
3359 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
3361 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
3366 PRETTY_DEBUG <<
"In the _connectionAddressScreen" << std::endl;
3369 const std::string homeKey =
"connectionAddressScreenHome";
3370 const std::string bodyKey =
"connectionAddressScreenBody";
3371 const std::string titleKey =
"connectionAddressScreenTitle";
3372 const std::string connectKey =
"connectionAddressScreenConnect";
3374 const std::string backgroundKey =
"connectionAddress";
3376 const std::string ipV4FirstDotKey =
"connectionAddressScreenIpV4FirstDot";
3377 const std::string ipV4SecondDotKey =
"connectionAddressScreenIpV4SecondDot";
3378 const std::string ipV4ThirdDotKey =
"connectionAddressScreenIpV4ThirdDot";
3380 const std::string portV4ColumnKey =
"connectionAddressScreenPortV4ColumnKey";
3382 const std::string ipChunkOneUpKey =
"connectionAddressScreenIpChunkOneUp";
3383 const std::string ipChunkOneDownKey =
"connectionAddressScreenIpChunkOneDown";
3384 const std::string ipChunkTwoUpKey =
"connectionAddressScreenIpChunkTwoUp";
3385 const std::string ipChunkTwoDownKey =
"connectionAddressScreenIpChunkTwoDown";
3386 const std::string ipChunkThreeUpKey =
"connectionAddressScreenIpChunkThreeUp";
3387 const std::string ipChunkThreeDownKey =
"connectionAddressScreenIpChunkThreeDown";
3388 const std::string ipChunkFourUpKey =
"connectionAddressScreenIpChunkFourUp";
3389 const std::string ipChunkFourDownKey =
"connectionAddressScreenIpChunkFourDown";
3391 const std::string portChunkUpKey =
"connectionAddressScreenPortChunkUpKey";
3392 const std::string portChunkDownKey =
"connectionAddressScreenPortChunkDownKey";
3395 PRETTY_DEBUG <<
"Fetching component lists from the entity list" << std::endl;
3400 PRETTY_DEBUG <<
"Fetched component lists from the entity list" << std::endl;
3402 PRETTY_DEBUG <<
"Setting the default colour for the text that will displayed" << std::endl;
3406 PRETTY_DEBUG <<
"Setting the ip colour for the text that will displayed" << std::endl;
3413 PRETTY_DEBUG <<
"Setting the size of the title" << std::endl;
3414 const unsigned int titleSize = 40;
3417 PRETTY_DEBUG <<
"Setting the size of the body text" << std::endl;
3418 const unsigned int bodySize = 20;
3421 PRETTY_DEBUG <<
"Setting the size for the text that will manage the ip and port display" << std::endl;
3422 const unsigned int ipTextSize = 20;
3423 const unsigned int portTextSize = 20;
3424 const unsigned int ipTextDotSize = ipTextSize;
3425 const unsigned int portTextColumnSize = portTextSize;
3426 const unsigned int buttonUpSize = 40;
3427 const unsigned int buttonUpBoxWidth = 30;
3428 const unsigned int buttonUpBoxHeight = 30;
3429 const unsigned int buttonDownSize = 40;
3430 const unsigned int buttonDownBoxWidth = 30;
3431 const unsigned int buttonDownBoxHeight = 30;
3432 PRETTY_DEBUG <<
"Text size set for ip and port display" << std::endl;
3434 PRETTY_DEBUG <<
"Setting the ip and port colour for the buttons that will displayed" << std::endl;
3454 PRETTY_DEBUG <<
"Ip and port button colour set" << std::endl;
3456 PRETTY_DEBUG <<
"Setting the customisation information for the general buttons" << std::endl;
3461 PRETTY_DEBUG <<
"General button customisation set" << std::endl;
3463 PRETTY_DEBUG <<
"Fetching the fonts that will be used in the window" << std::endl;
3464 unsigned int index = 0;
3465 unsigned int titleFontIndex = 0;
3466 unsigned int bodyFontIndex = 0;
3467 unsigned int defaultFontIndex = 0;
3468 unsigned int buttonFontIndex = 0;
3469 for (std::any fontCast : fonts) {
3471 if (!fontCapsule.has_value()) {
3474 std::string applicationContext = fontCapsule.value()->getApplication();
3475 if (applicationContext ==
"title") {
3476 titleFontIndex = index;
3477 }
else if (applicationContext ==
"body") {
3478 bodyFontIndex = index;
3479 }
else if (applicationContext ==
"default") {
3480 defaultFontIndex = index;
3481 }
else if (applicationContext ==
"button") {
3482 buttonFontIndex = index;
3493 if (!defaultFontCapsule.has_value()) {
3494 PRETTY_DEBUG <<
"No default font found, aborting program" << std::endl;
3497 const std::shared_ptr<GUI::ECS::Systems::Font> defaultFont = defaultFontCapsule.value();
3498 std::shared_ptr<GUI::ECS::Systems::Font> titleFont = defaultFontCapsule.value();
3499 std::shared_ptr<GUI::ECS::Systems::Font> bodyFont = defaultFontCapsule.value();
3500 std::shared_ptr<GUI::ECS::Systems::Font> buttonFont = defaultFontCapsule.value();
3501 if (titleFontCapsule.has_value()) {
3502 PRETTY_SUCCESS <<
"Title font found, not defaulting to the default font." << std::endl;
3503 titleFont = titleFontCapsule.value();
3505 if (bodyFontCapsule.has_value()) {
3506 PRETTY_SUCCESS <<
"Body font found, not defaulting to the default font." << std::endl;
3507 bodyFont = bodyFontCapsule.value();
3509 if (buttonFontCapsule.has_value()) {
3510 PRETTY_SUCCESS <<
"Button font found, not defaulting to the default font." << std::endl;
3511 buttonFont = buttonFontCapsule.value();
3513 PRETTY_DEBUG <<
"Fetched the fonts that will be used in the window" << std::endl;
3515 PRETTY_DEBUG <<
"Holder for the background initialising" << std::endl;
3516 std::optional<std::shared_ptr<GUI::ECS::Components::ImageComponent>> backgroundItem;
3517 PRETTY_DEBUG <<
"Background holder initialised" << std::endl;
3519 PRETTY_DEBUG <<
"Holders for the title and body initialising" << std::endl;
3520 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> titleItem;
3521 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> bodyItem;
3522 PRETTY_DEBUG <<
"Holders for the title and body initialised" << std::endl;
3524 PRETTY_DEBUG <<
"Holders for the home and connect buttons initialising" << std::endl;
3525 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> homeItem;
3526 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> connectItem;
3527 PRETTY_DEBUG <<
"Holders for the home and connect buttons initialised" << std::endl;
3529 PRETTY_DEBUG <<
"Holders for the ip text chunks initialising" << std::endl;
3530 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4FirstChunkItem;
3531 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4FirstDotItem;
3532 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4SecondChunkItem;
3533 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4SecondDotItem;
3534 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4ThirdChunkItem;
3535 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4ThirdDotItem;
3536 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> ipV4FourthChunkItem;
3537 PRETTY_DEBUG <<
"Holders for the ip text chunks initialised" << std::endl;
3539 PRETTY_DEBUG <<
"Holders for the port text chunks initialising" << std::endl;
3540 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> portV4ColumnItem;
3541 std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> portV4ChunkItem;
3542 PRETTY_DEBUG <<
"Holders for the port text chunks initialised" << std::endl;
3544 PRETTY_DEBUG <<
"Holders for the ip button chunks initialising" << std::endl;
3545 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkOneUpItem;
3546 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkOneDownItem;
3547 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkTwoUpItem;
3548 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkTwoDownItem;
3549 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkThreeUpItem;
3550 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkThreeDownItem;
3551 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkFourUpItem;
3552 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> ipChunkFourDownItem;
3553 PRETTY_DEBUG <<
"Holders for the ip button chunks initialised" << std::endl;
3555 PRETTY_DEBUG <<
"Holders for the port button chunks initialising" << std::endl;
3556 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> portChunkUpItem;
3557 std::optional<std::shared_ptr<GUI::ECS::Components::ButtonComponent>> portChunkDownItem;
3558 PRETTY_DEBUG <<
"Holders for the port button chunks initialised" << std::endl;
3560 PRETTY_DEBUG <<
"Attempting to fetch content for the background." << std::endl;
3561 for (std::any backgroundCast : backgrounds) {
3563 if (backgroundCapsule.has_value() && backgroundCapsule.value()->getApplication() == backgroundKey) {
3564 backgroundItem.emplace(backgroundCapsule.value());
3568 PRETTY_DEBUG <<
"Fetched the background content." << std::endl;
3571 PRETTY_DEBUG <<
"Fetching the text components if present." << std::endl;
3572 unsigned int textIndex = 0;
3573 for (std::any textCast : texts) {
3577 if (!textCapsule.has_value()) {
3581 std::string applicationContext = textCapsule.value()->getApplication();
3582 if (applicationContext == titleKey) {
3584 << titleKey <<
"' found and assigned to the correct item."
3586 titleItem.emplace(textCapsule.value());
3587 }
else if (applicationContext == bodyKey) {
3589 << bodyKey <<
"' found and assigned to the correct item."
3591 bodyItem.emplace(textCapsule.value());
3592 }
else if (applicationContext == _ipV4FirstChunkKey) {
3594 << _ipV4FirstChunkKey <<
"' found and assigned to the correct item."
3596 ipV4FirstChunkItem.emplace(textCapsule.value());
3597 }
else if (applicationContext == _ipV4SecondChunkKey) {
3599 << _ipV4SecondChunkKey <<
"' found and assigned to the correct item."
3601 ipV4SecondChunkItem.emplace(textCapsule.value());
3602 }
else if (applicationContext == _ipV4ThirdChunkKey) {
3604 << _ipV4ThirdChunkKey <<
"' found and assigned to the correct item."
3606 ipV4ThirdChunkItem.emplace(textCapsule.value());
3607 }
else if (applicationContext == _ipV4FourthChunkKey) {
3609 << _ipV4FirstChunkKey <<
"' found and assigned to the correct item."
3611 ipV4FourthChunkItem.emplace(textCapsule.value());
3612 }
else if (applicationContext == _portV4ChunkKey) {
3614 << _portV4ChunkKey <<
"' found and assigned to the correct item."
3616 portV4ChunkItem.emplace(textCapsule.value());
3617 }
else if (applicationContext == ipV4FirstDotKey) {
3619 << ipV4FirstDotKey <<
"' found and assigned to the correct item."
3621 ipV4FirstDotItem.emplace(textCapsule.value());
3622 }
else if (applicationContext == ipV4SecondDotKey) {
3624 << ipV4SecondDotKey <<
"' found and assigned to the correct item."
3626 ipV4SecondDotItem.emplace(textCapsule.value());
3627 }
else if (applicationContext == ipV4ThirdDotKey) {
3629 << ipV4ThirdDotKey <<
"' found and assigned to the correct item."
3631 ipV4ThirdDotItem.emplace(textCapsule.value());
3632 }
else if (applicationContext == portV4ColumnKey) {
3634 << portV4ColumnKey <<
"' found and assigned to the correct item."
3636 portV4ColumnItem.emplace(textCapsule.value());
3639 PRETTY_DEBUG <<
"Text application context: " << applicationContext << std::endl;
3643 PRETTY_DEBUG <<
"Fetched the text components that were present." << std::endl;
3645 PRETTY_DEBUG <<
"Attempting to fetch content for the button." << std::endl;
3646 unsigned int buttonIndex = 0;
3647 for (std::any buttonCast : buttons) {
3651 if (!buttonCapsule.has_value()) {
3655 std::string applicationContext = buttonCapsule.value()->getApplication();
3656 if (applicationContext == _mainMenuKey) {
3657 homeItem.emplace(buttonCapsule.value());
3659 }
else if (applicationContext == connectKey) {
3660 connectItem.emplace(buttonCapsule.value());
3662 }
else if (applicationContext == ipChunkOneUpKey) {
3663 ipChunkOneUpItem.emplace(buttonCapsule.value());
3664 PRETTY_DEBUG <<
"IP chunk one up button found" << std::endl;
3665 }
else if (applicationContext == ipChunkTwoUpKey) {
3666 ipChunkTwoUpItem.emplace(buttonCapsule.value());
3667 PRETTY_DEBUG <<
"IP chunk two up button found" << std::endl;
3668 }
else if (applicationContext == ipChunkThreeUpKey) {
3669 ipChunkThreeUpItem.emplace(buttonCapsule.value());
3670 PRETTY_DEBUG <<
"IP chunk three up button found" << std::endl;
3671 }
else if (applicationContext == ipChunkFourUpKey) {
3672 ipChunkFourUpItem.emplace(buttonCapsule.value());
3673 PRETTY_DEBUG <<
"IP chunk four up button found" << std::endl;
3674 }
else if (applicationContext == ipChunkOneDownKey) {
3675 ipChunkOneDownItem.emplace(buttonCapsule.value());
3676 PRETTY_DEBUG <<
"IP chunk one down button found" << std::endl;
3677 }
else if (applicationContext == ipChunkTwoDownKey) {
3678 ipChunkTwoDownItem.emplace(buttonCapsule.value());
3679 PRETTY_DEBUG <<
"IP chunk two down button found" << std::endl;
3680 }
else if (applicationContext == ipChunkThreeDownKey) {
3681 ipChunkThreeDownItem.emplace(buttonCapsule.value());
3682 PRETTY_DEBUG <<
"IP chunk three down button found" << std::endl;
3683 }
else if (applicationContext == ipChunkFourDownKey) {
3684 ipChunkFourDownItem.emplace(buttonCapsule.value());
3685 PRETTY_DEBUG <<
"IP chunk four down button found" << std::endl;
3686 }
else if (applicationContext == portChunkUpKey) {
3687 portChunkUpItem.emplace(buttonCapsule.value());
3688 PRETTY_DEBUG <<
"Port chunk up button found" << std::endl;
3689 }
else if (applicationContext == portChunkDownKey) {
3690 portChunkDownItem.emplace(buttonCapsule.value());
3691 PRETTY_DEBUG <<
"Port chunk down button found" << std::endl;
3694 PRETTY_DEBUG <<
"Unknown button found with context: " << applicationContext << std::endl;
3698 PRETTY_DEBUG <<
"Fetched the button content." << std::endl;
3700 PRETTY_DEBUG <<
"Checking if the Home button exists." << std::endl;
3701 if (!homeItem.has_value()) {
3702 PRETTY_WARNING <<
"Home button not found, creating" << std::endl;
3703 homeItem = _createButton(
3706 std::bind(&Main::_goHome,
this),
3711 buttonGeneralColourBackground,
3712 buttonGeneralColourNormal,
3713 buttonGeneralColourHover,
3714 buttonGeneralColourClicked
3718 PRETTY_DEBUG <<
"Checked if the home button existed." << std::endl;
3720 PRETTY_DEBUG <<
"Checking text content for the body." << std::endl;
3721 if (!bodyItem.has_value()) {
3722 PRETTY_WARNING <<
"No body text instance found, creating instance." << std::endl;
3723 bodyItem = _createText(
3726 "Please set the ip for the server",
3734 PRETTY_DEBUG <<
"Checked the text content for the body." << std::endl;
3736 PRETTY_DEBUG <<
"Checking if the title item is set" << std::endl;
3737 if (!titleItem.has_value()) {
3738 PRETTY_DEBUG <<
"Title item is not set, setting the title component" << std::endl;
3739 titleItem = _createText(
3750 PRETTY_DEBUG <<
"Checked if the title item is set" << std::endl;
3752 PRETTY_DEBUG <<
"Checking if the Connect button exists." << std::endl;
3753 if (!connectItem.has_value()) {
3754 PRETTY_WARNING <<
"Connect button not found, creating" << std::endl;
3755 connectItem = _createButton(
3758 std::bind(&Main::_goConnect,
this),
3763 buttonGeneralColourBackground,
3764 buttonGeneralColourNormal,
3765 buttonGeneralColourHover,
3766 buttonGeneralColourClicked
3770 PRETTY_DEBUG <<
"Checked if the Connect button existed." << std::endl;
3772 PRETTY_DEBUG <<
"Checking if the ipV4FirstChunk item is set" << std::endl;
3773 if (!ipV4FirstChunkItem.has_value()) {
3774 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4FirstChunk component" << std::endl;
3775 ipV4FirstChunkItem = _createText(
3778 _getIpChunk(0,
"127"),
3786 PRETTY_DEBUG <<
"Checked if the ipV4FirstChunk item is set" << std::endl;
3788 PRETTY_DEBUG <<
"Checking if the ipV4FirstDot item is set" << std::endl;
3789 if (!ipV4FirstDotItem.has_value()) {
3790 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4FirstDot component" << std::endl;
3791 ipV4FirstDotItem = _createText(
3802 PRETTY_DEBUG <<
"Checked if the ipV4FirstDot item is set" << std::endl;
3804 PRETTY_DEBUG <<
"Checking if the ipV4SecondChunk item is set" << std::endl;
3805 if (!ipV4SecondChunkItem.has_value()) {
3806 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4SecondChunk component" << std::endl;
3807 ipV4SecondChunkItem = _createText(
3808 _ipV4SecondChunkKey,
3809 _ipV4SecondChunkKey,
3810 _getIpChunk(1,
"0"),
3818 PRETTY_DEBUG <<
"Checked if the ipV4SecondChunk item is set" << std::endl;
3820 PRETTY_DEBUG <<
"Checking if the ipV4SecondDot item is set" << std::endl;
3821 if (!ipV4SecondDotItem.has_value()) {
3822 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4SecondDot component" << std::endl;
3823 ipV4SecondDotItem = _createText(
3834 PRETTY_DEBUG <<
"Checked if the ipV4SecondDot item is set" << std::endl;
3836 PRETTY_DEBUG <<
"Checking if the ipV4ThirdChunk item is set" << std::endl;
3837 if (!ipV4ThirdChunkItem.has_value()) {
3838 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4ThirdChunk component" << std::endl;
3839 ipV4ThirdChunkItem = _createText(
3842 _getIpChunk(2,
"0"),
3850 PRETTY_DEBUG <<
"Checked if the ipV4ThirdChunk item is set" << std::endl;
3852 PRETTY_DEBUG <<
"Checking if the ipV4ThirdDot item is set" << std::endl;
3853 if (!ipV4ThirdDotItem.has_value()) {
3854 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4ThirdDot component" << std::endl;
3855 ipV4ThirdDotItem = _createText(
3866 PRETTY_DEBUG <<
"Checked if the ipV4ThirdDot item is set" << std::endl;
3868 PRETTY_DEBUG <<
"Checking if the ipV4FourthChunk item is set" << std::endl;
3869 if (!ipV4FourthChunkItem.has_value()) {
3870 PRETTY_DEBUG <<
"Title item is not set, setting the ipV4FourthChunk component" << std::endl;
3871 ipV4FourthChunkItem = _createText(
3872 _ipV4FourthChunkKey,
3873 _ipV4FourthChunkKey,
3874 _getIpChunk(3,
"1"),
3882 PRETTY_DEBUG <<
"Checked if the ipV4FourthChunk item is set" << std::endl;
3884 PRETTY_DEBUG <<
"Checking if the portV4Column item is set" << std::endl;
3885 if (!portV4ColumnItem.has_value()) {
3886 PRETTY_DEBUG <<
"Title item is not set, setting the portV4Column component" << std::endl;
3887 portV4ColumnItem = _createText(
3893 textColourPortColumn,
3894 textColourPortColumn,
3895 textColourPortColumn
3898 PRETTY_DEBUG <<
"Checked if the portV4Column item is set" << std::endl;
3900 PRETTY_DEBUG <<
"Checking if the portV4Chunk item is set" << std::endl;
3901 if (!portV4ChunkItem.has_value()) {
3902 PRETTY_DEBUG <<
"Title item is not set, setting the portV4Chunk component" << std::endl;
3903 portV4ChunkItem = _createText(
3906 std::to_string(_port),
3914 PRETTY_DEBUG <<
"Checked if the portV4Chunk item is set" << std::endl;
3916 PRETTY_DEBUG <<
"Checking if the ipChunkOneUp button exists." << std::endl;
3917 if (!ipChunkOneUpItem.has_value()) {
3918 PRETTY_WARNING <<
"ipChunkOneUp button not found, creating" << std::endl;
3919 ipChunkOneUpItem = _createButton(
3922 std::bind(&Main::_incrementIpChunkOne,
this),
3923 "_incrementIpChunkOne",
3927 buttonUpColourIpBackground,
3928 buttonUpColourIpNormal,
3929 buttonUpColourIpHover,
3930 buttonUpColourIpClicked,
3935 PRETTY_DEBUG <<
"Checked if the ipChunkOneUp button existed." << std::endl;
3937 PRETTY_DEBUG <<
"Checking if the ipChunkOneDown button exists." << std::endl;
3938 if (!ipChunkOneDownItem.has_value()) {
3939 PRETTY_WARNING <<
"ipChunkOneDown button not found, creating" << std::endl;
3940 ipChunkOneDownItem = _createButton(
3943 std::bind(&Main::_decrementIpChunkOne,
this),
3944 "_decrementIpChunkOne",
3946 buttonDownBoxHeight,
3948 buttonDownColourIpBackground,
3949 buttonDownColourIpNormal,
3950 buttonDownColourIpHover,
3951 buttonDownColourIpClicked,
3956 PRETTY_DEBUG <<
"Checked if the ipChunkOneDown button existed." << std::endl;
3958 PRETTY_DEBUG <<
"Checking if the ipChunkTwoUp button exists." << std::endl;
3959 if (!ipChunkTwoUpItem.has_value()) {
3960 PRETTY_WARNING <<
"ipChunkTwoUp button not found, creating" << std::endl;
3961 ipChunkTwoUpItem = _createButton(
3964 std::bind(&Main::_incrementIpChunkTwo,
this),
3965 "_incrementIpChunkTwo",
3969 buttonUpColourIpBackground,
3970 buttonUpColourIpNormal,
3971 buttonUpColourIpHover,
3972 buttonUpColourIpClicked,
3977 PRETTY_DEBUG <<
"Checked if the ipChunkTwoUp button existed." << std::endl;
3979 PRETTY_DEBUG <<
"Checking if the ipChunkTwoDown button exists." << std::endl;
3980 if (!ipChunkTwoDownItem.has_value()) {
3981 PRETTY_WARNING <<
"ipChunkTwoDown button not found, creating" << std::endl;
3982 ipChunkTwoDownItem = _createButton(
3985 std::bind(&Main::_decrementIpChunkTwo,
this),
3986 "_decrementIpChunkTwo",
3988 buttonDownBoxHeight,
3990 buttonDownColourIpBackground,
3991 buttonDownColourIpNormal,
3992 buttonDownColourIpHover,
3993 buttonDownColourIpClicked,
3998 PRETTY_DEBUG <<
"Checked if the ipChunkTwoDown button existed." << std::endl;
4000 PRETTY_DEBUG <<
"Checking if the ipChunkThreeUp button exists." << std::endl;
4001 if (!ipChunkThreeUpItem.has_value()) {
4002 PRETTY_WARNING <<
"ipChunkThreeUp button not found, creating" << std::endl;
4003 ipChunkThreeUpItem = _createButton(
4006 std::bind(&Main::_incrementIpChunkThree,
this),
4007 "_incrementIpChunkThree",
4011 buttonUpColourIpBackground,
4012 buttonUpColourIpNormal,
4013 buttonUpColourIpHover,
4014 buttonUpColourIpClicked,
4019 PRETTY_DEBUG <<
"Checked if the ipChunkThreeUp button existed." << std::endl;
4021 PRETTY_DEBUG <<
"Checking if the ipChunkThreeDown button exists." << std::endl;
4022 if (!ipChunkThreeDownItem.has_value()) {
4023 PRETTY_WARNING <<
"ipChunkThreeDown button not found, creating" << std::endl;
4024 ipChunkThreeDownItem = _createButton(
4025 ipChunkThreeDownKey,
4027 std::bind(&Main::_decrementIpChunkThree,
this),
4028 "_decrementIpChunkThree",
4030 buttonDownBoxHeight,
4032 buttonDownColourIpBackground,
4033 buttonDownColourIpNormal,
4034 buttonDownColourIpHover,
4035 buttonDownColourIpClicked,
4038 PRETTY_SUCCESS <<
"ipChunkThreeDown Button created" << std::endl;
4040 PRETTY_DEBUG <<
"Checked if the ipChunkThreeDown button existed." << std::endl;
4042 PRETTY_DEBUG <<
"Checking if the ipChunkFourUp button exists." << std::endl;
4043 if (!ipChunkFourUpItem.has_value()) {
4044 PRETTY_WARNING <<
"ipChunkFourUp button not found, creating" << std::endl;
4045 ipChunkFourUpItem = _createButton(
4048 std::bind(&Main::_incrementIpChunkFour,
this),
4049 "_incrementIpChunkFour",
4053 buttonUpColourIpBackground,
4054 buttonUpColourIpNormal,
4055 buttonUpColourIpHover,
4056 buttonUpColourIpClicked,
4061 PRETTY_DEBUG <<
"Checked if the ipChunkFourUp button existed." << std::endl;
4063 PRETTY_DEBUG <<
"Checking if the ipChunkFourDown button exists." << std::endl;
4064 if (!ipChunkFourDownItem.has_value()) {
4065 PRETTY_WARNING <<
"ipChunkFourDown button not found, creating" << std::endl;
4066 ipChunkFourDownItem = _createButton(
4069 std::bind(&Main::_decrementIpChunkFour,
this),
4070 "_decrementIpChunkFour",
4072 buttonDownBoxHeight,
4074 buttonDownColourIpBackground,
4075 buttonDownColourIpNormal,
4076 buttonDownColourIpHover,
4077 buttonDownColourIpClicked,
4082 PRETTY_DEBUG <<
"Checked if the ipChunkFourDown button existed." << std::endl;
4084 PRETTY_DEBUG <<
"Checking if the portChunkUp button exists." << std::endl;
4085 if (!portChunkUpItem.has_value()) {
4086 PRETTY_WARNING <<
"portChunkUp button not found, creating" << std::endl;
4087 portChunkUpItem = _createButton(
4090 std::bind(&Main::_incrementPortChunk,
this),
4091 "_incrementPortChunk",
4095 buttonUpColourPortBackground,
4096 buttonUpColourPortNormal,
4097 buttonUpColourPortHover,
4098 buttonUpColourPortClicked,
4103 PRETTY_DEBUG <<
"Checked if the portChunkUp button existed." << std::endl;
4105 PRETTY_DEBUG <<
"Checking if the portChunkDown button exists." << std::endl;
4106 if (!portChunkDownItem.has_value()) {
4107 PRETTY_WARNING <<
"portChunkDown button not found, creating" << std::endl;
4108 portChunkDownItem = _createButton(
4111 std::bind(&Main::_decrementPortChunk,
this),
4112 "_decrementPortChunk",
4114 buttonDownBoxHeight,
4116 buttonDownColourPortBackground,
4117 buttonDownColourPortNormal,
4118 buttonDownColourPortHover,
4119 buttonDownColourPortClicked,
4124 PRETTY_DEBUG <<
"Checked if the portChunkDown button existed." << std::endl;
4126 PRETTY_DEBUG <<
"Checking if background exists" << std::endl;
4127 if (!backgroundItem.has_value()) {
4128 PRETTY_WARNING <<
"Background not found, changing the text components" << std::endl;
4130 titleItem.value()->setNormalColor(defaultColourForNoBackground);
4131 titleItem.value()->setHoverColor(defaultColourForNoBackground);
4132 titleItem.value()->setClickedColor(defaultColourForNoBackground);
4133 bodyItem.value()->setNormalColor(defaultColourForNoBackground);
4134 bodyItem.value()->setHoverColor(defaultColourForNoBackground);
4135 bodyItem.value()->setClickedColor(defaultColourForNoBackground);
4136 ipV4FirstChunkItem.value()->setNormalColor(defaultColourForNoBackground);
4137 ipV4FirstChunkItem.value()->setHoverColor(defaultColourForNoBackground);
4138 ipV4FirstChunkItem.value()->setClickedColor(defaultColourForNoBackground);
4139 ipV4SecondChunkItem.value()->setNormalColor(defaultColourForNoBackground);
4140 ipV4SecondChunkItem.value()->setHoverColor(defaultColourForNoBackground);
4141 ipV4SecondChunkItem.value()->setClickedColor(defaultColourForNoBackground);
4142 ipV4ThirdChunkItem.value()->setNormalColor(defaultColourForNoBackground);
4143 ipV4ThirdChunkItem.value()->setHoverColor(defaultColourForNoBackground);
4144 ipV4ThirdChunkItem.value()->setClickedColor(defaultColourForNoBackground);
4145 ipV4FourthChunkItem.value()->setNormalColor(defaultColourForNoBackground);
4146 ipV4FourthChunkItem.value()->setHoverColor(defaultColourForNoBackground);
4147 ipV4FourthChunkItem.value()->setClickedColor(defaultColourForNoBackground);
4148 portV4ColumnItem.value()->setNormalColor(defaultColourForNoBackground);
4149 portV4ColumnItem.value()->setHoverColor(defaultColourForNoBackground);
4150 portV4ColumnItem.value()->setClickedColor(defaultColourForNoBackground);
4152 PRETTY_DEBUG <<
"Checked if the background existed." << std::endl;
4154 PRETTY_DEBUG <<
"Getting the center y of the screen" << std::endl;
4155 const unsigned int centerY = _getScreenCenterY();
4156 const unsigned int centerX = _getScreenCenterX();
4157 PRETTY_DEBUG <<
"Center Y of the screen is " << centerY << std::endl;
4160 const unsigned int padX = 10;
4162 const unsigned int padY = 10;
4163 PRETTY_DEBUG <<
"Setting the X line tracker" << std::endl;
4164 unsigned int posX = padX;
4166 const unsigned int ipXStep = 20;
4167 PRETTY_DEBUG <<
"Setting the Y column tracker" << std::endl;
4168 unsigned int posY = padY;
4170 const unsigned int yStep = 40;
4173 titleItem.value()->setPosition({ posX, posY });
4175 posY += yStep + titleSize;
4176 bodyItem.value()->setPosition({ posX, posY });
4178 posY += yStep + bodySize;
4179 PRETTY_DEBUG <<
"Setting the positions for the increment arrows" << std::endl;
4180 ipChunkOneUpItem.value()->setPosition({ posX, posY });
4182 posX += ipXStep + ipTextSize;
4183 posX += ipTextDotSize;
4184 ipChunkTwoUpItem.value()->setPosition({ posX, posY });
4186 posX += ipXStep + ipTextSize;
4187 posX += ipTextDotSize;
4188 ipChunkThreeUpItem.value()->setPosition({ posX, posY });
4190 posX += ipXStep + ipTextSize;
4191 posX += ipTextDotSize;
4192 ipChunkFourUpItem.value()->setPosition({ posX, posY });
4194 posX += ipXStep + ipTextSize;
4195 posX += portTextColumnSize;
4196 portChunkUpItem.value()->setPosition({ posX, posY });
4198 PRETTY_DEBUG <<
"Setting the positions for the texts representing the address" << std::endl;
4200 posY += yStep + ipTextSize;
4202 ipV4FirstChunkItem.value()->setPosition({ posX, posY });
4204 posX += ipXStep + ipTextSize;
4205 ipV4FirstDotItem.value()->setPosition({ posX, posY });
4207 posX += ipTextDotSize;
4208 ipV4SecondChunkItem.value()->setPosition({ posX, posY });
4210 posX += ipXStep + ipTextSize;
4211 ipV4SecondDotItem.value()->setPosition({ posX, posY });
4213 posX += ipTextDotSize;
4214 ipV4ThirdChunkItem.value()->setPosition({ posX, posY });
4216 posX += ipXStep + ipTextSize;
4217 ipV4ThirdDotItem.value()->setPosition({ posX, posY });
4219 posX += ipTextDotSize;
4220 ipV4FourthChunkItem.value()->setPosition({ posX, posY });
4222 posX += ipXStep + ipTextSize;
4223 portV4ColumnItem.value()->setPosition({ posX, posY });
4225 posX += portTextColumnSize;
4226 portV4ChunkItem.value()->setPosition({ posX, posY });
4231 ipChunkOneDownItem.value()->setPosition({ posX, posY });
4233 posX += ipXStep + ipTextSize;
4234 posX += ipTextDotSize;
4235 ipChunkTwoDownItem.value()->setPosition({ posX, posY });
4237 posX += ipXStep + ipTextSize;
4238 posX += ipTextDotSize;
4239 ipChunkThreeDownItem.value()->setPosition({ posX, posY });
4241 posX += ipXStep + ipTextSize;
4242 posX += ipTextDotSize;
4243 ipChunkFourDownItem.value()->setPosition({ posX, posY });
4245 posX += ipXStep + ipTextSize;
4246 posX += portTextColumnSize;
4247 portChunkDownItem.value()->setPosition({ posX, posY });
4252 PRETTY_DEBUG <<
"Setting the position of the connect button" << std::endl;
4253 connectItem.value()->setPosition({ posX, posY });
4255 posX += ipXStep * 10;
4257 PRETTY_DEBUG <<
"Setting the position of the home button" << std::endl;
4258 homeItem.value()->setPosition({ posX, posY });
4263 if (backgroundItem.has_value()) {
4264 win.value()->draw(*(backgroundItem.value()));
4267 win.value()->draw(*(titleItem.value()));
4269 win.value()->draw(*(bodyItem.value()));
4271 win.value()->draw(*(homeItem.value()));
4273 win.value()->draw(*(connectItem.value()));
4275 win.value()->draw(*(ipV4FirstChunkItem.value()));
4276 PRETTY_DEBUG <<
"Rendered ipV4FirstChunk item" << std::endl;
4277 win.value()->draw(*(ipV4FirstDotItem.value()));
4278 PRETTY_DEBUG <<
"Rendered ipV4FirstDot item" << std::endl;
4279 win.value()->draw(*(ipV4SecondChunkItem.value()));
4280 PRETTY_DEBUG <<
"Rendered ipV4SecondChunk item" << std::endl;
4281 win.value()->draw(*(ipV4SecondDotItem.value()));
4282 PRETTY_DEBUG <<
"Rendered ipV4SecondDotItem" << std::endl;
4283 win.value()->draw(*(ipV4ThirdChunkItem.value()));
4284 PRETTY_DEBUG <<
"Rendered ipV4ThirdChunk item" << std::endl;
4285 win.value()->draw(*(ipV4ThirdDotItem.value()));
4286 PRETTY_DEBUG <<
"Rendered ipV4ThirdDot item" << std::endl;
4287 win.value()->draw(*(ipV4FourthChunkItem.value()));
4288 PRETTY_DEBUG <<
"Rendered ipV4FourthChunk item" << std::endl;
4289 win.value()->draw(*(portV4ColumnItem.value()));
4290 PRETTY_DEBUG <<
"Rendered portV4Column item" << std::endl;
4291 win.value()->draw(*(portV4ChunkItem.value()));
4292 PRETTY_DEBUG <<
"Rendered portV4Chunk item" << std::endl;
4293 win.value()->draw(*(ipChunkOneUpItem.value()));
4294 PRETTY_DEBUG <<
"Rendered ipChunkOneUp item" << std::endl;
4295 win.value()->draw(*(ipChunkOneDownItem.value()));
4296 PRETTY_DEBUG <<
"Rendered ipChunkOneDown item" << std::endl;
4297 win.value()->draw(*(ipChunkTwoUpItem.value()));
4298 PRETTY_DEBUG <<
"Rendered ipChunkTwoUp item" << std::endl;
4299 win.value()->draw(*(ipChunkTwoDownItem.value()));
4300 PRETTY_DEBUG <<
"Rendered ipChunkTwoDown item" << std::endl;
4301 win.value()->draw(*(ipChunkThreeUpItem.value()));
4302 PRETTY_DEBUG <<
"Rendered ipChunkThreeUp item" << std::endl;
4303 win.value()->draw(*(ipChunkThreeDownItem.value()));
4304 PRETTY_DEBUG <<
"Rendered ipChunkThreeDown item" << std::endl;
4305 win.value()->draw(*(ipChunkFourUpItem.value()));
4306 PRETTY_DEBUG <<
"Rendered ipChunkFourUp item" << std::endl;
4307 win.value()->draw(*(ipChunkFourDownItem.value()));
4308 PRETTY_DEBUG <<
"Rendered ipChunkFourDown item" << std::endl;
4309 win.value()->draw(*(portChunkUpItem.value()));
4310 PRETTY_DEBUG <<
"Rendered portChunkUp item" << std::endl;
4311 win.value()->draw(*(portChunkDownItem.value()));
4312 PRETTY_DEBUG <<
"Rendered portChunkDown item" << std::endl;
4317void Main::_lobbyList()
4320 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
4322 if (!win.has_value()) {
4328 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
4329 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
4331 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
4336void Main::_lobbyRoom()
4339 PRETTY_DEBUG <<
"Getting the window manager component" << std::endl;
4341 if (!win.has_value()) {
4347 std::shared_ptr<GUI::ECS::Systems::EventManager> events = _getEventManager();
4348 PRETTY_DEBUG <<
"Checking if the escape key was pressed" << std::endl;
4350 PRETTY_DEBUG <<
"Escape key pressed, returning to the home screen" << std::endl;
4377 PRETTY_WARNING <<
"Player name is empty, defaulting to 'Player'" << std::endl;
4380 if (player.length() > 9) {
4381 PRETTY_WARNING <<
"The player name is to long, defaulting to 'Player'" << std::endl;
4385 _networkManager->setPlayerName(_player);
4423void Main::_goSettings()
4433void Main::_goGameOver()
4443void Main::_goGameWon()
4453void Main::_goBossFight()
4463void Main::_goUnknown()
4473void Main::_goConnectionFailed()
4489void Main::_goConnect()
4493 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> chunkOne = _getTextComponent(_ipV4FirstChunkKey);
4494 if (!chunkOne.has_value()) {
4495 PRETTY_ERROR <<
"Could not find the text component for the first IP chunk." << std::endl;
4496 _goConnectionFailed();
4501 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> chunkTwo = _getTextComponent(_ipV4SecondChunkKey);
4502 if (!chunkTwo.has_value()) {
4503 PRETTY_ERROR <<
"Could not find the text component for the second IP chunk." << std::endl;
4504 _goConnectionFailed();
4509 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> chunkThree = _getTextComponent(_ipV4ThirdChunkKey);
4510 if (!chunkThree.has_value()) {
4511 PRETTY_ERROR <<
"Could not find the text component for the first IP chunk." << std::endl;
4512 _goConnectionFailed();
4517 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> chunkFour = _getTextComponent(_ipV4FourthChunkKey);
4518 if (!chunkFour.has_value()) {
4519 PRETTY_ERROR <<
"Could not find the text component for the first IP chunk." << std::endl;
4520 _goConnectionFailed();
4524 _ip = chunkOne.value()->getText() +
".";
4525 _ip += chunkTwo.value()->getText() +
".";
4526 _ip += chunkThree.value()->getText() +
".";
4527 _ip += chunkFour.value()->getText();
4529 const std::optional<std::shared_ptr<GUI::ECS::Components::TextComponent>> port = _getTextComponent(_portV4ChunkKey);
4530 if (!port.has_value()) {
4531 PRETTY_ERROR <<
"Could not find the text component for the port chunk." << std::endl;
4532 _goConnectionFailed();
4536 PRETTY_DEBUG <<
"The text port is: " << port.value()->getText() << std::endl;
4537 _port = std::stoi(port.value()->getText());
4540 catch (std::invalid_argument &e) {
4541 PRETTY_ERROR <<
"Could not convert the port to an integer." << std::endl;
4542 _goConnectionFailed();
4547 _initialiseConnection();
4548 _connectionInitialised = _networkManager->isConnected();
4549 PRETTY_DEBUG <<
"Checking if we are connected" << std::endl;
4550 if (_connectionInitialised) {
4555 _goConnectionFailed();
4564void Main::_goConnectionAddress()
4574void Main::_goLobbyList()
4584void Main::_goLobbyRoom()
4592void Main::_toggleMusic()
4594 PRETTY_DEBUG <<
"Getting the event manager component" << std::endl;
4596 if (!event_ptr.has_value()) {
4601 event_ptr.value()->flushEvents();
4607 _updateMusicStatus();
4610 _updateMusicStatus();
4617void Main::_toggleSound()
4619 PRETTY_DEBUG <<
"Getting the event manager component" << std::endl;
4621 if (!event_ptr.has_value()) {
4626 event_ptr.value()->flushEvents();
4630 PRETTY_DEBUG <<
"Getting the sound library if present" << std::endl;
4631 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4632 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4636 if (!soundLib.has_value()) {
4637 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
4640 PRETTY_DEBUG <<
"Fetched the sound library" << std::endl;
4643 if (soundLib.has_value() && soundLib.value()->isEnabled()) {
4644 soundLib.value()->setPlay(
false);
4647 if (soundLib.has_value()) {
4648 soundLib.value()->setPlay(
true);
4652void Main::_updateMusicStatus()
4655 PRETTY_WARNING <<
"No music is supposed to play, not playing any" << std::endl;
4656 _stopMainMenuMusic();
4657 _stopGameLoopMusic();
4658 _stopBossFightMusic();
4661 PRETTY_DEBUG <<
"Updating the current music that is supposed to play." << std::endl;
4663 PRETTY_DEBUG <<
"We're not in game nor in a boss fight, switching to menu music." << std::endl;
4664 _startMainMenuMusic();
4665 _stopGameLoopMusic();
4666 _stopBossFightMusic();
4668 PRETTY_DEBUG <<
"Were gaming, swithing to game music." << std::endl;
4669 _stopMainMenuMusic();
4670 _startGameLoopMusic();
4671 _stopBossFightMusic();
4673 PRETTY_DEBUG <<
"Boss fight!, switching to boss fight music." << std::endl;
4674 _stopMainMenuMusic();
4675 _stopGameLoopMusic();
4676 _startBossFightMusic();
4678 PRETTY_DEBUG <<
"Game won!, switching to game won music." << std::endl;
4679 _stopMainMenuMusic();
4680 _stopGameLoopMusic();
4681 _stopBossFightMusic();
4684 PRETTY_DEBUG <<
"Game won!, switching to game won music." << std::endl;
4685 _stopMainMenuMusic();
4686 _stopGameLoopMusic();
4687 _stopBossFightMusic();
4691 PRETTY_DEBUG <<
"Game won!, switching to game won music." << std::endl;
4692 _stopMainMenuMusic();
4693 _stopGameLoopMusic();
4694 _stopBossFightMusic();
4697 PRETTY_DEBUG <<
"No specific music rules, defaulting to no music" << std::endl;
4698 _stopMainMenuMusic();
4699 _stopGameLoopMusic();
4700 _stopBossFightMusic();
4702 PRETTY_DEBUG <<
"Updated the current music that is supposed to play." << std::endl;
4714void Main::_startMainMenuMusic()
4716 if (_mainMenuMusicStarted) {
4720 for (std::any music : musics) {
4722 if (!node.has_value()) {
4725 if (node.value()->getApplication() ==
"mainMenu" || node.value()->getMusicName() ==
"mainMenu") {
4726 node.value()->setLoopMusic(
true);
4727 node.value()->play();
4728 _mainMenuMusicStarted =
true;
4742void Main::_stopMainMenuMusic()
4744 if (!_mainMenuMusicStarted) {
4748 for (std::any music : musics) {
4750 if (!node.has_value()) {
4754 node.value()->getApplication() ==
"mainMenu" ||
4755 node.value()->getMusicName() ==
"mainMenu" ||
4756 node.value()->getApplication() ==
"Main Menu" ||
4757 node.value()->getMusicName() ==
"Main Menu"
4759 node.value()->stop();
4760 _mainMenuMusicStarted =
false;
4774void Main::_startGameLoopMusic()
4776 if (_gameMusicStarted) {
4780 for (std::any music : musics) {
4782 if (!node.has_value()) {
4786 node.value()->getApplication() ==
"gameLoop" ||
4787 node.value()->getMusicName() ==
"gameLoop" ||
4788 node.value()->getApplication() ==
"Game Loop" ||
4789 node.value()->getMusicName() ==
"Game Loop"
4791 node.value()->setLoopMusic(
true);
4792 node.value()->play();
4793 _gameMusicStarted =
true;
4808void Main::_stopGameLoopMusic()
4810 if (!_gameMusicStarted) {
4814 for (std::any music : musics) {
4816 if (!node.has_value()) {
4820 node.value()->getApplication() ==
"gameLoop" ||
4821 node.value()->getMusicName() ==
"gameLoop" ||
4822 node.value()->getApplication() ==
"Game Loop" ||
4823 node.value()->getMusicName() ==
"Game Loop"
4825 node.value()->stop();
4826 _gameMusicStarted =
false;
4840void Main::_startBossFightMusic()
4842 if (_bossFightMusicStarted) {
4846 for (std::any music : musics) {
4848 if (!node.has_value()) {
4852 node.value()->getApplication() ==
"bossFight" ||
4853 node.value()->getMusicName() ==
"bossFight" ||
4854 node.value()->getApplication() ==
"Boss Fight" ||
4855 node.value()->getMusicName() ==
"Boss Fight"
4857 node.value()->setLoopMusic(
true);
4858 node.value()->play();
4859 _bossFightMusicStarted =
true;
4873void Main::_stopBossFightMusic()
4875 if (!_bossFightMusicStarted) {
4879 for (std::any music : musics) {
4881 if (!node.has_value()) {
4885 node.value()->getApplication() ==
"bossFight" ||
4886 node.value()->getMusicName() ==
"bossFight" ||
4887 node.value()->getApplication() ==
"Boss Fight" ||
4888 node.value()->getMusicName() ==
"Boss Fight"
4890 node.value()->stop();
4891 _bossFightMusicStarted =
false;
4904void Main::_shootSound()
4906 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4907 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4911 if (!soundLib.has_value()) {
4912 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
4915 soundLib.value()->shootSound();
4926void Main::_damageSound()
4928 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4929 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4933 if (!soundLib.has_value()) {
4934 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
4937 soundLib.value()->damageSound();
4948void Main::_deadSound()
4950 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4951 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4955 if (!soundLib.has_value()) {
4956 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
4959 soundLib.value()->deadSound();
4970void Main::_buttonSound()
4972 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4973 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4977 if (!soundLib.has_value()) {
4978 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
4981 soundLib.value()->buttonSound();
4992void Main::_gameOverSound()
4994 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
4995 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
4999 if (!soundLib.has_value()) {
5000 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
5003 soundLib.value()->gameOverSound();
5014void Main::_winSound()
5016 if (_ecsEntities[
typeid(
SoundLib)].size() == 0) {
5017 PRETTY_WARNING <<
"Skipping audio playing because the sound library is missing" << std::endl;
5021 if (!soundLib.has_value()) {
5022 PRETTY_WARNING <<
"The library to find the found player is missing, skipping sound" << std::endl;
5025 soundLib.value()->winSound();
5032void Main::_testContent()
5036 for (
unsigned int index = 0; index < musics.size(); index++) {
5038 std::shared_ptr<GUI::ECS::Components::MusicComponent> music_ptr = std::any_cast<std::shared_ptr<GUI::ECS::Components::MusicComponent>>(musics[index]);
5039 PRETTY_INFO <<
"Playing " << music_ptr->getMusicName() <<
" audio." << std::endl;
5042 catch (std::bad_any_cast &e) {
5043 PRETTY_ERROR <<
"Error casting music component, system error: " + std::string(e.what()) << std::endl;
5055void Main::_mainLoop()
5058 std::int64_t elapsedTime = 0;
5059 std::shared_ptr<GUI::ECS::Systems::Clock> ECSClock = std::make_shared<GUI::ECS::Systems::Clock>(_baseId);
5066 if (!window_ptr.has_value()) {
5069 std::shared_ptr<GUI::ECS::Systems::Window> window = window_ptr.value();
5071 if (!event_ptr.has_value()) {
5074 std::shared_ptr<GUI::ECS::Systems::EventManager>
event = event_ptr.value();
5082 if (!font_title_ptr.has_value()) {
5085 if (!font_body_ptr.has_value()) {
5088 if (!font_default_ptr.has_value()) {
5091 if (!font_button_ptr.has_value()) {
5095 const std::shared_ptr<GUI::ECS::Systems::Font> font_title = font_title_ptr.value();
5096 const std::shared_ptr<GUI::ECS::Systems::Font> font_body = font_body_ptr.value();
5097 const std::shared_ptr<GUI::ECS::Systems::Font> font_default = font_default_ptr.value();
5098 const std::shared_ptr<GUI::ECS::Systems::Font> font_button = font_button_ptr.value();
5101 PRETTY_INFO <<
"Updating loading text to 'All the ressources have been loaded'." << std::endl;
5102 _updateLoadingText(
"All the ressources have been loaded.");
5103 PRETTY_INFO <<
"Updated loading text to 'All the ressources have been loaded'." << std::endl;
5115 PRETTY_DEBUG <<
"Going to start the mainloop." << std::endl;
5116 while (window->isOpen()) {
5117 PRETTY_DEBUG <<
"The active screen is: '" << _activeScreen <<
"'" << std::endl;
5118 elapsedTime = ECSClock->reset();
5119 PRETTY_DEBUG <<
"Since the last clock reset, the time that has elapsed is: '" << elapsedTime <<
"'" << std::endl;
5120 PRETTY_INFO <<
"Sending all the packets" << std::endl;
5122 PRETTY_INFO <<
"All the packets have been sent" << std::endl;
5123 PRETTY_INFO <<
"Processing incoming packets" << std::endl;
5124 _processIncommingPackets();
5127 PRETTY_SUCCESS <<
"Processed window events (user input basically)" << std::endl;
5128 _updateMouseForAllRendererables(event->getMouseInfo());
5129 PRETTY_SUCCESS <<
"Updated mouse position for all rendererables" << std::endl;
5131 PRETTY_INFO <<
"Caps lock is pressed, switching to debug mode" << std::endl;
5136 PRETTY_DEBUG <<
"Menu screen components are going to be set to be displayed" << std::endl;
5138 PRETTY_SUCCESS <<
"Menu screen components are set to be displayed" << std::endl;
5140 PRETTY_DEBUG <<
"Game screen components are going to be set to be displayed" << std::endl;
5142 PRETTY_SUCCESS <<
"Game screen components are set to be displayed" << std::endl;
5144 PRETTY_DEBUG <<
"Demo screen components are going to be set to be displayed" << std::endl;
5146 PRETTY_SUCCESS <<
"Demo screen components are set to be displayed" << std::endl;
5148 PRETTY_DEBUG <<
"Settings screen components are going to be set to be displayed" << std::endl;
5150 PRETTY_SUCCESS <<
"Settings screen components are set to be displayed" << std::endl;
5152 PRETTY_DEBUG <<
"Game Over screen components are going to be set to be displayed" << std::endl;
5154 PRETTY_SUCCESS <<
"Game Over screen components are set to be displayed" << std::endl;
5156 PRETTY_DEBUG <<
"Game Won screen components are going to be set to be displayed" << std::endl;
5158 PRETTY_SUCCESS <<
"Game Won screen components are set to be displayed" << std::endl;
5160 PRETTY_DEBUG <<
"Boss Fight screen components are going to be set to be displayed" << std::endl;
5162 PRETTY_SUCCESS <<
"Boss Fight screen components are set to be displayed" << std::endl;
5164 PRETTY_DEBUG <<
"Connection Failed screen components are going to be set to be displayed" << std::endl;
5165 _connectionFailedScreen();
5166 PRETTY_SUCCESS <<
"Connection Failed screen components are set to be displayed" << std::endl;
5168 PRETTY_DEBUG <<
"Connection Address screen components are going to be set to be displayed" << std::endl;
5169 _connectionAddressScreen();
5170 PRETTY_SUCCESS <<
"Connection Address screen components are set to be displayed" << std::endl;
5172 PRETTY_DEBUG <<
"Lobby list screen components are going to be set to be displayed" << std::endl;
5174 PRETTY_SUCCESS <<
"Lobby list screen components are set to be displayed" << std::endl;
5176 PRETTY_DEBUG <<
"Lobby room screen components are going to be set to be displayed" << std::endl;
5178 PRETTY_SUCCESS <<
"Lobby room screen components are set to be displayed" << std::endl;
5180 PRETTY_DEBUG <<
"Update loading text screen components are going to be set to be displayed" << std::endl;
5181 _updateLoadingText(
"Apparently we are loading something...");
5182 PRETTY_SUCCESS <<
"Update loading text screen components are set to be displayed" << std::endl;
5184 PRETTY_INFO <<
"Exit choice detected, stopping" << std::endl;
5187 _updateMusicStatus();
5188 PRETTY_INFO <<
"The window is set to close" << std::endl;
5191 PRETTY_DEBUG <<
"Unknown screen components are set to be displayed" << std::endl;
5193 PRETTY_ERROR <<
"Unknown active screen: " << _activeScreen << std::endl;
5207 _initialiseRessources();
5223 if (_isIpInRange(ip) ==
true) {
5225 _networkManager->setIp(ip);
5240 if (_isPortCorrect(port) ==
true) {
5242 _networkManager->setPort(_port);
5255 _windowWidth = width;
5265 _windowHeight = height;
5275 _windowCursor = cursorVisible;
5285 _windowFullscreen = fullscreen;
5295 _windowTitle = title;
5340 if (cursorImage ==
"" || cursorImage ==
"NULL") {
5341 _windowCursorIcon =
nullptr;
5342 }
else if (_isFilePresent(cursorImage) ==
true) {
5343 _windowCursorIcon = cursorImage;
5356 _imageIsSprite = imageIsSprite;
5367 _spriteWidth = spriteWidth;
5377 _spriteStartTop = spriteStartTop;
5387 _spriteStartLeft = spriteStartLeft;
5398 _spriteHeight = spriteHeight;
5409 _spriteWidth = width;
5410 _spriteHeight = height;
5420 if (_isFrameLimitCorrect(frameLimit) ==
false) {
5423 _windowFrameLimit = frameLimit;
5433 _configFilePath = configFile;
5468 PRETTY_DEBUG <<
"Getting the event manager component" << std::endl;
5470 if (!event_ptr.has_value()) {
5475 event_ptr.value()->flushEvents();
5479 _activeScreen = screen;
5481 _updateMusicStatus();
5511 return _windowWidth;
5521 return _windowHeight;
5532 return _windowCursor;
5543 return _windowFullscreen;
5553 return _windowTitle;
5565 return _windowCursorIcon;
5576 return _imageIsSprite;
5587 return _spriteStartTop;
5598 return _spriteStartLeft;
5608 return _spriteWidth;
5618 return _spriteHeight;
5651 return _windowFrameLimit;
5662 return _configFilePath;
5674 std::tuple<unsigned int, unsigned int> position;
5675 position = std::make_tuple(_windowX, _windowY);
5688 std::tuple<unsigned int, unsigned int> dimension;
5689 dimension = std::make_tuple(_windowWidth, _windowHeight);
5700 return _activeScreen;
5731void Main::_loadToml()
ActiveScreen
This is the enum class in charge of the window switcher code. This enum allows the mainloop of the pr...
#define PRETTY_ERROR
Error log with details and colour.
#define PRETTY_DEBUG
Debug log with details and colour.
#define PRETTY_INFO
Info log with details and colour.
#define PRETTY_CRITICAL
Critical log with details and colour.
#define PRETTY_WARNING
Warning log with details and colour.
#define PRETTY_SUCCESS
Success log with details and colour.
This is the file in charge of containing the main class and other ressources at the root of the progr...
This is the class in charge of informing the user that the provided file path could not be found.
This is the class in charge of informing the user that the background configuration they provided is ...
This is the class in charge of informing the user that the font configuration they provided is incorr...
This is the class in charge of informing the user that the window frame limit is invalid.
This is the class in charge of informing the user that the icon configuration they provided is incorr...
This is the class in charge of informing the user that the entered ip is incorrect.
This is the class in charge of informing the user that the music configuration they provided is incor...
This is the class in charge of informing the user that the port is incorrect.
This is the class in charge of informing the user that the sprite configuration they provided is inco...
This is the class in charge of informing the user that the type of the toml key is not the one that w...
This is the class in charge of informing the user that they tried to play music from a class that has...
This is the class in charge of informing the user that the program could not find the Background sect...
This is the class in charge of informing the user that there is no configuration for the font in char...
This is the class in charge of informing the user that there is no configuration for the font in char...
This is the class in charge of informing the user that they tried to access a non-existant Event Mana...
This is the class in charge of informing the user that they tried to access a non-existant font insta...
This is the class in charge of informing the user that they tried to access a non-existant Icon.
This is the class in charge of informing the user that they tried to access a non-existant toml key i...
This is the class in charge of informing the user that they tried to access a non-existant text insta...
This is the class in charge of informing the user that there is no configuration for the font in char...
This is the class in charge of informing the user that they tried to access a non-existant window.
Represents an image component in the GUI ECS system.
Manages music playback and properties for an entity in the ECS system.
Manages shapes and their associated properties in the ECS framework.
Represents a drawable and interactive sprite in the ECS system.
A class that represents a text component in the GUI system. It manages font, size,...
void render()
Renders the game entities to the window.
void tick()
Updates the game state for the current frame.
void stop()
Stops the game logic and resets the playing state.
const bool isGameOver() const
Checks if the game is over.
const bool isGameWon() const
Checks if the game has been won.
void start()
Starts the game logic and sets the game to a playing state.
void initialiseClass(std::unordered_map< std::type_index, std::vector< std::any > > &ecsEntities)
Initializes the ECS entities managed by the orchestrator.
void reset()
Resets the game state, clearing all entities and resetting conditions.
const bool isGameWon() const
Checks if the game has been won.
void tick(const std::vector< GUI::Network::MessageNode > &packets)
Updates the game state for the current frame.
void start()
Starts the game logic and sets the game to a playing state.
void reset()
Resets the game state, clearing all entities and resetting conditions.
const bool isGameOver() const
Checks if the game is over.
void render()
Renders the game entities to the window.
void stop()
Stops the game logic and resets the playing state.
void initialiseClass(std::unordered_map< std::type_index, std::vector< std::any > > &ecsEntities)
Initializes the ECS entities managed by the orchestrator.
void setNetworkClass(const std::shared_ptr< GUI::Network::ThreadCapsule > &network)
A class for managing time tracking within the ECS system.
A class for representing and manipulating colors using RGBA components. Inherits from EntityNode to a...
static const Colour MediumAquamarine
static const Colour Aquamarine
static const Colour CadetBlue
static const Colour Grey50
static const Colour YellowGreen
static const Colour Wheat
static const Colour Transparent
static const Colour Black
static const Colour White
static const Colour DeepSkyBlue
static const Colour Chartreuse
static const Colour Firebrick
static const Colour GreenYellow
static const Colour Coral4
static const Colour OrangeRed
static const Colour Chartreuse1
static const Colour BlueViolet
static const Colour Green
Manages input events such as mouse movements, key presses, and window interactions.
Manages font entities in the GUI ECS.
Manages an SFML-based graphical window and handles rendering of ECS components.
void setLogEnabled(bool enabled)
Enables or disables the logging.
static Log & getInstance(const bool debug=false)
Provides access to the singleton instance of the Debug class.
void setDebugEnabled(bool enabled)
Enables or disables the debug logging.
void run()
This is the function used to start the program's main section.
bool getWindowCursor()
Get the status of the window cursor.
const std::string getIp()
Get the value of the ip that was set.
const unsigned int getPort()
Get the value of the port.
std::tuple< unsigned int, unsigned int > getWindowPosition()
Get the window's position.
void setWindowFullscreen(bool fullscreen)
Start the window in full screen mode.
const ActiveScreen getActiveScreen() const
Function in charge of returning the screen that is currently active.
const std::string & getWindowCursorIcon()
Get the icon to display for the window's cursor.
void setWindowCursor(bool cursorVisible)
Set if the cursor is visible when in the window.
std::tuple< unsigned int, unsigned int > getWindowSize()
Get the windows dimensions.
void setDebug(const bool debug)
Toggle the debug mode for the program.
const std::string getActiveScreenAsString() const
Function in charge of returning the screen that is currently active but here, the type will be conver...
void setWindowCursorSprite(bool imageIsSprite)
Set if the image passed is of type sprite or not.
bool getWindowCursorSprite()
Get the status if the cursor is of type image or spritesheet.
~Main()
Destroy the Main:: Main object.
bool getWindowCursorSpriteReadFromLeft()
Get if the program is supposed to read from the left or the rigth.
unsigned int getWindowCursorSpriteWidth()
Get the width of the sprite texture.
void setWindowPositionX(unsigned int x)
Set the X position of the window.
void setWindowCursorSpriteReadFromTop(bool spriteStartTop)
Inform if the animation should start from the top.
void setFrameLimit(unsigned int frameLimit)
The function in charge of setting the frame Limit.
void setWindowCursorIcon(const std::string cursorImage)
Set the icon of the cursor (if the user wishes to change the default icon)
void setWindowCursorSpriteWidth(unsigned int spriteWidth)
Set the height for the sprite's overlay texture, which is used to draw the sprite's texture during an...
void setIp(const std::string &ip)
This is the function in charge of setting the ip on which the GUI is going to use to communicate abou...
std::string getConfigFile() const
Function in charge of returning the path to the config file.
unsigned int getWindowCursorSpriteHeight()
Get the height of the sprite texture.
void setWindowSize(unsigned int width, unsigned int height)
The window width and height that will be created.
bool getWindowFullscreen()
Get the status of the window (if it is in fullscreen)
const std::string getPlayer() const
Retrieves the player's name.
void setPlayer(const std::string &player)
Sets the player's name.
void setWindowPosition(unsigned int x, unsigned int y)
Set the position of the window.
unsigned int getWindowHeight()
Get the value of the window height.
unsigned int getFrameLimit() const
Function in charge of returning the current frame limit.
void setWindowHeight(unsigned int height)
Set the height of the window.
void setWindowCursorSpriteHeight(unsigned int spriteHeight)
Set the height for the sprite's overlay texture, which is used to draw the sprite's texture during an...
void setPort(const unsigned int port)
Set the port on which the GUI is going to connect to.
void setConfigFile(const std::string &configFile)
This is the function in charge of seting the config filepath.
void setWindowPositionY(unsigned int y)
Set the Y position of the window.
void setActiveScreen(const ActiveScreen screen)
Function in charge of updating the type of screen that is supposed to be displayed as well as change ...
void setLog(const bool debug)
Toggle the logging mode for the program.
bool getWindowCursorSpriteReadFromTop()
Get if the program is supposed to read from the top or not.
const std::string & getWindowTitle()
Get the title of the window.
const bool getLog() const
The function in charge of returning the status of the logging variable.
void setWindowWidth(unsigned int width)
Set the width of the window.
void setWindowTitle(const std::string &title)
Set the title of the window.
const bool getDebug() const
The function in charge of returning the status of the debug variable.
void setWindowCursorSpriteReadFromLeft(bool spriteStartLeft)
Inform if the animation should start from the left.
Main(const std::string &ip="127.0.0.1", unsigned int port=9000, unsigned int windowWidth=800, unsigned int windowHeight=600, bool windowCursor=true, bool windowFullscreen=false, const std::string &windowTitle="R-Type", unsigned int windowX=0, unsigned int windowY=0, const std::string &windowCursorIcon="NULL", bool imageIsSprite=false, bool spriteStartTop=false, bool spriteStartLeft=false, unsigned int spriteWidth=20, unsigned int spriteHeight=20, unsigned int frameLimit=60, const std::string &configFilePath="client_config.toml", const bool log=false, const bool debug=false, const std::string &player="Player")
Constructor for the Main class.
unsigned int getWindowWidth()
Get the value of the window width.
The SoundLib class manages sound effects and interactions with ECS entities.
A utility class for parsing, navigating, and managing TOML files and data.
const toml::node_type getValueType(const std::string &key) const
Retrieves the type of a value for a specific key as a TOML node type.
const std::string getTOMLPath() const
Retrieves the path of the loaded TOML file.
toml::table getTable(const std::string &key) const
Retrieves a TOML table for a specific key.
const bool hasKey(const std::string &key) const
Checks if a specific key exists in the TOML data.
void setTOMLPath(const std::string &tomlPath)
Sets the path of the TOML file to load.
void printTOML() const
Prints the TOML data to the debug stream.
std::vector< std::string > getKeys() const
Retrieves all keys from the TOML table.
const std::string getTypeAsString(const std::string &key) const
Retrieves the type of a value for a specific key as a string (alias).
T getValue(const std::string &key) const
Retrieves a value of type T from the TOML table.
const std::string myToString(const Rect< RectType > &rectangle)
Converts a Rect<T> object to its string representation.
std::optional< T > unCast(const std::any &classNode, const bool raiseOnError=true, const std::string customErrorMessage="")
Casts the content of a std::any back to its original type.