• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Jak ulepszyć kod gry RPG?

0 głosów
477 wizyt
pytanie zadane 19 maja w C i C++ przez lorenz Początkujący (470 p.)

Cześć jak można ulepszyć kod tej tekstowej gry rpg w stylu Diablo, Path of Exile.

Enemy.cpp

#include "Enemy.h"

void Enemy::createEnemy(int type)
{
    if (type == 0) {
        name = "Zombie";
        maxHealth = 50;
        damage = 5;
    } else if (type == 1) {
        name = "Szkieletor";
        maxHealth = 35;
        damage = 8;
    } else if (type == 2) {
        name = "Goblinek";
        maxHealth = 30;
        damage = 10;
    } else {
        name = "Zombiak";
        maxHealth = 50;
        damage = 5;
    }
    currentHealth = maxHealth;
}

void Enemy::SetLevel(int enemyLevel)
{
    level = enemyLevel;
    maxHealth += (level - 1) * 10;
    damage += (level - 1) * 2;
    currentHealth = maxHealth;
}

Enemy.h

#pragma once
#include <string>

class Enemy {
public:
    std::string name { }; // nowa składnia C++23
    int maxHealth { 0 };
    int currentHealth { 0 };
    int level { 1 };
    int damage { 0 };

    void createEnemy(int type);
    void SetLevel(int enemyLevel);
};

main.cpp

#include "Enemy.h"
#include "Player.h"
#include "Print.h"
#include <cstdlib>
#include <ctime>
#include <iostream>
#include <vector>

// Stany gry
enum class GameState { MainMenu,
    CharacterSelect,
    Playing,
    Exit };

// Funkcje losujące przeciwników
int GetEnemyCount()
{
    int roll = rand() % 100;
    if (roll < 50)
        return 1;
    if (roll < 75)
        return 2;
    if (roll < 90)
        return 3;
    return 4;
}

int GetEnemyType() { return rand() % 3; } // 0-Zombie,1-Szkieletor,2-Goblin
int GetEnemyLevel() { return 1 + rand() % 3; }

// Funkcja losująca obrażenia z możliwością krytyka
int DealDamage(int baseDamage)
{
    int roll = rand() % 100;
    if (roll < 10)
        return baseDamage * 2; // 10% krytyk
    return baseDamage;
}

int main()
{
    srand(time(0));

    Player player;
    bool running = true;
    GameState state = GameState::MainMenu;

    while (running) {
        if (state == GameState::MainMenu) {
            Print::WriteColor("====UpiornePotyczki====\n\n", Color::Red);
            Print::Write("1. Nowa Gra\n");
            Print::Write("2. Wyjście\n");
            Print::WriteColor("\nWybierz opcję: ", Color::Yellow);
            int choice;
            std::cin >> choice;

            if (choice == 1)
                state = GameState::CharacterSelect;
            else if (choice == 2)
                state = GameState::Exit;
            Print::Clear();
        }

        else if (state == GameState::CharacterSelect) {
            Print::WriteColor("Wybierz klasę postaci:\n\n", Color::Yellow);
            Print::Write("1. Wojownik\n");
            Print::Write("2. Łotrzyk\n");
            Print::Write("3. Mag\n");
            Print::WriteColor("\nOpcja: ", Color::Yellow);

            int choice;
            std::cin >> choice;
            player.SetClass(choice);
            player.DisplayPickedCharacter();

            int continueChoice;
            std::cin >> continueChoice;
            Print::Clear();
            state = GameState::Playing;
        }

        else if (state == GameState::Playing) {
            std::vector<Enemy> enemies;
            int enemyCount = GetEnemyCount();

            for (int i = 0; i < enemyCount; i++) {
                Enemy enemy;
                enemy.createEnemy(GetEnemyType());
                enemy.SetLevel(GetEnemyLevel());
                enemies.push_back(enemy);
            }

            bool inCombat = true;
            while (inCombat) {
                Print::Clear();
                Print::WriteColor("Pojawiają się przeciwnicy!\n\n", Color::Red);

                Print::Write("Twoje zdrowie:\n");
                Print::DrawHPBar(player.currentHealth, player.maxHealth, 20, Color::Green);

                for (size_t i = 0; i < enemies.size(); i++) {
                    Print::Write(enemies[i].name + " (Poziom " + std::to_string(enemies[i].level) + "):\n");
                    Color hpColor = enemies[i].currentHealth > 0 ? Color::Yellow : Color::Red;
                    Print::DrawHPBar(enemies[i].currentHealth, enemies[i].maxHealth, 20, hpColor);
                }

                Print::Write("\n1. Atak\n2. Ucieczka\n");
                Print::WriteColor("Opcja: ", Color::Yellow);
                int choice;
                std::cin >> choice;

                if (choice == 1) {
                    Print::WriteColor("\nWybierz przeciwnika do ataku: ", Color::Yellow);
                    int targetChoice;
                    std::cin >> targetChoice;
                    size_t targetIndex = targetChoice - 1;

                    if (targetIndex < enemies.size()) {
                        int dmg = DealDamage(player.damage);
                        enemies[targetIndex].currentHealth -= dmg;

                        Print::Write("\nUderzasz ");
                        Print::WriteColor(enemies[targetIndex].name, Color::Yellow);
                        if (dmg > player.damage)
                            Print::WriteColor(" krytycznie! ", Color::Red);
                        Print::Write(" za " + std::to_string(dmg) + " obrażeń!\n");

                        if (enemies[targetIndex].currentHealth <= 0) {
                            enemies[targetIndex].currentHealth = 0;
                            Print::WriteColor("\n" + enemies[targetIndex].name + " został pokonany!\n", Color::Green);
                            enemies.erase(enemies.begin() + targetIndex);
                        }

                        if (enemies.empty()) {
                            Print::WriteColor("\nWygrałeś walkę!\n", Color::Green);
                            inCombat = false;
                        } else {
                            Print::Write("\nPrzeciwnicy atakują!\n");
                            for (size_t i = 0; i < enemies.size(); i++) {
                                int enemyDmg = DealDamage(enemies[i].damage);
                                player.currentHealth -= enemyDmg;
                                if (player.currentHealth < 0)
                                    player.currentHealth = 0;

                                Print::WriteColor(enemies[i].name, Color::Red);
                                Print::Write(" uderza cię za " + std::to_string(enemyDmg) + " obrażeń!\n");

                                if (player.currentHealth <= 0) {
                                    Print::WriteColor("\nZostałeś pokonany..\n", Color::Red);
                                    inCombat = false;
                                    state = GameState::Exit;
                                    break;
                                }
                            }
                        }
                    } else {
                        Print::Write("\nNieprawidłowy cel!\n");
                    }
                } else if (choice == 2) {
                    Print::WriteColor("\nUciekasz jak tchórz!\n", Color::Yellow);
                    inCombat = false;
                } else {
                    Print::Write("\nNieprawidłowy wybór!\n");
                }

                Print::WriteColor("\nNaciśnij Enter, aby kontynuować...", Color::Cyan);
                std::cin.ignore();
                std::cin.get();
            }

            state = GameState::Exit;
        }

        else if (state == GameState::Exit) {
            running = false;
        }
    }

    Print::WriteColor("\n************************************\n", Color::Magenta);
    Print::WriteColor("* Dzięki za grę w UpiornePotyczki! *\n", Color::Magenta);
    Print::WriteColor("************************************\n", Color::Magenta);

    return 0;
}

Player.cpp

#include "Player.h"
#include "Print.h"

void Player::SetClass(int choice)
{
    name = "Bohater";
    if (choice == 1) {
        playerClass = "Wojownik";
        strength = 10;
        intelligence = 2;
        vitality = 8;
    } else if (choice == 2) {
        playerClass = "Łotrzyk";
        strength = 6;
        intelligence = 5;
        vitality = 6;
    } else if (choice == 3) {
        playerClass = "Mag";
        strength = 2;
        intelligence = 10;
        vitality = 5;
    }
    CalculateStats();
}

void Player::CalculateStats()
{
    maxHealth = 50 + vitality * 10;
    currentHealth = maxHealth;
    maxMana = 30 + intelligence * 10;
    currentMana = maxMana;

    if (playerClass == "Wojownik")
        damage = strength * 2;
    else if (playerClass == "Łotrzyk")
        damage = strength * 2 + 2;
    else if (playerClass == "Mag")
        damage = intelligence * 2;
    else
        damage = 5;
}

void Player::DisplayPickedCharacter()
{
    Print::Clear();
    Print::Write("Wybrałeś ");
    Print::WriteColor(playerClass, Color::Cyan);
    Print::Write("!\n\n");
    Print::Write("Siła: " + std::to_string(strength) + "\n");
    Print::Write("Inteligencja: " + std::to_string(intelligence) + "\n");
    Print::Write("Witalność: " + std::to_string(vitality) + "\n");
    Print::Write("Zdrowie: ");
    Print::WriteColor(std::to_string(currentHealth), Color::Green);
    Print::Write("\nMana: ");
    Print::WriteColor(std::to_string(currentMana), Color::Cyan);
    Print::Write("\n\nNaciśnij 1, aby kontynuować: ");
}

Player.h

#pragma once
#include <string>

class Player {
public:
    std::string name { }; // nowa składnia C++23
    std::string playerClass { };

    int strength { 0 };
    int intelligence { 0 };
    int vitality { 0 };

    int maxHealth { 0 };
    int currentHealth { 0 };

    int maxMana { 0 };
    int currentMana { 0 };

    int damage { 0 };

    void SetClass(int choice);
    void CalculateStats();
    void DisplayPickedCharacter();
};

Print.cpp

#include "Print.h"
#include <cstdlib>

void Print::Write(const std::string& text) { std::print("{}", text); }

void Print::SetColor(Color color)
{
    switch (color) {
    case Color::Red:
        std::print("\033[31m");
        break;
    case Color::Green:
        std::print("\033[32m");
        break;
    case Color::Yellow:
        std::print("\033[33m");
        break;
    case Color::Cyan:
        std::print("\033[36m");
        break;
    case Color::Blue:
        std::print("\033[34m");
        break;
    case Color::Magenta:
        std::print("\033[35m");
        break;
    case Color::White:
        std::print("\033[37m");
        break;
    case Color::Black:
        std::print("\033[30m");
        break;
    default:
        std::print("\033[0m");
        break;
    }
}

void Print::WriteColor(const std::string& text, Color color)
{
    SetColor(color);
    std::print("{}", text);
    SetColor(Color::Default);
}

void Print::Clear() { system("clear"); }

void Print::DrawHPBar(int current, int max, int width, Color color)
{
    int filled = (current * width) / max;
    SetColor(color);
    std::print("[");
    for (int i = 0; i < filled; i++)
        std::print("█");
    for (int i = filled; i < width; i++)
        std::print(" ");
    std::print("] {}/{}\n", current, max);
    SetColor(Color::Default);
}

Print.h

#pragma once
#include <print>

enum class Color { Default,
    Red,
    Green,
    Yellow,
    Cyan,
    Blue,
    Magenta,
    White,
    Black };

class Print {
public:
    static void Write(const std::string& text);
    static void SetColor(Color color);
    static void WriteColor(const std::string& text, Color color);
    static void Clear();
    static void DrawHPBar(int current, int max, int width, Color color);
};

Makefile

# Kompilator i flagi
CXX = clang++
CXXFLAGS = -std=c++23 -Wall -Wextra -I./src

# Katalogi
SRC_DIR = src
BIN_DIR = bin

# Pliki źródłowe
SRCS = $(SRC_DIR)/main.cpp \
       $(SRC_DIR)/Player.cpp \
       $(SRC_DIR)/Enemy.cpp \
       $(SRC_DIR)/Print.cpp

# Plik wynikowy
TARGET = $(BIN_DIR)/UpiornePotyczki

# Domyślna akcja
all: $(TARGET)

# Kompilacja plików źródłowych i linkowanie
$(TARGET): $(SRCS)
	@mkdir -p $(BIN_DIR)
	$(CXX) $(CXXFLAGS) $^ -o $@

# Czyszczenie plików obiektowych i binarnych
clean:
	rm -rf $(BIN_DIR)/*.o $(TARGET)

CMakeLists.txt

cmake_minimum_required(VERSION 4.3.1)
project(UpiornePotyczki)

set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED True)

# Dodajemy wszystkie pliki źródłowe
file(GLOB SOURCES "src/*.cpp")

add_executable(UpiornePotyczki ${SOURCES})

README.md

# UpiornePotyczki

Konsolowa gra RPG w C++.

## Funkcje
- Wybór klasy: Wojownik, Łotrzyk, Mag
- Walki z losowymi przeciwnikami (Zombie, Szkieletor, Goblin)
- Paski HP w konsoli, kolory i komunikaty o krytykach
- System poziomów przeciwników i skalowanie obrażeń

## Kompilacja i uruchamianie

### Wymagania
- Kompilator C++23 (np. `clang++` lub `g++` obsługujący C++23)
- Użyłem Clang 22.1.5
- System Linux lub Mac (komenda `system("clear")` używana do czyszczenia konsoli)

### Kompilacja za pomocą Makefile

1. Przejdź do katalogu projektu:
   ```bash
   cd /ścieżka/do/project

## Kompilacja
```bash
mkdir build
cd build
cmake ..
make
./bin/UpiornePotyczki

Możesz też na szybko skompilować za pomocą polecenia w rozszerzeniu VSCode o nazwie Code Runner.

"code-runner.executorMap": {
  "cpp": "clear && cd $dir && mkdir -p bin && cd bin && clang++ -std=c++23 ../Player.cpp ../Enemy.cpp ../Print.cpp ../$fileName -o $fileNameWithoutExt && ./$fileNameWithoutExt",
}

5 odpowiedzi

0 głosów
odpowiedź 19 maja przez WojAbuk Gaduła (3,500 p.)

Jak już używasz C++23, to użyj modułów, a nie jakiegoś dziwactwa w postaci #pragma once, a jak zależy ci na kompatybilność, to używaj starych dobrych strażników, czyli include guard, bo #pragma once nie jest żadnym sensownym rozwiązaniem. Pliki nagłówkowe C++ nazywaj raczej .hpp, a nie .h. Kod lepiej udostępnić przez repozytorium na github niż wklejając wszystko w treść na forum szczególnie przy podziale na pliki. Widzę, że w Enemy.cpp używasz konstrukcji else if przy klasycznym przypadku użycia switch case i type powiano być raczej typu Enum Classes, a nie typu int. Nie rozumiem dlaczego używasz jednocześnie Makefile i CMake, bo Makefile powinno być generowane przez CMake. To są rzeczy jakie widzę na pierwszy rzut oka, ale ja jestem programistą C, a nie C++. 

1
komentarz 19 maja przez adrian17 Mentor (355,160 p.)

Jak już używasz C++23, to użyj modułów

Wciąż są niestabilne, bez dobrego toolingu i AFAIK ludzie wciąż je unikają; to jeden z rzadkich przypadków gdzie wciąż regularnie zdarzają się crashe kompilatorów.

a nie jakiegoś dziwactwa w postaci #pragma once

Dla odróżnienia, #pragma once działa uniwersalnie i stabilnie od -nastu lat i jest bez problemu używany w dużych projektach.

Pliki nagłówkowe C++ nazywaj raczej .hpp, a nie .h.

Kwestia gustu; osobiście częściej widuję .h, nawet nie jestem pewny czy w nowych projektach nie ma ich więcej niż w starszych.

Nie rozumiem dlaczego używasz jednocześnie Makefile i CMake, bo Makefile powinno być generowane przez CMake.

A z tym się zgadzam, też nie rozumiem.

komentarz 20 maja przez lorenz Początkujący (470 p.)
Użyłem Makefile ponieważ lepiej się nadaje do małych programów. Natomiast CMake trzeba osobno zainstalować i pobiera około 16MB danych, może nie każdy go mieć zainstalowany.

To jest druga opcja dla ludzi co korzystają z CMake gdyż jest bardziej uniwersalny pod inne systemy.

Widziałem więcej plików nagłówkowych z .h
komentarz 27 maja przez WojAbuk Gaduła (3,500 p.)

@adrian17, #pragma once nie działa uniwersalnie. Nawet nie ma go w standardzie, owszem jest często obsługiwane, ale nie jest zgodne z standardem. Równie dobrze możesz użyć #import, co akurat jest implementowane w C++ przez lenistwo programistów, bo jest w specyfikacji Objective-C, a #pragma once, to tylko nie oficjalne rozszerzenie. Uniwersalnym i stabilnym rozwiązaniem jest include guard, którego używanie ja osobiście preferuję, ale ja mam do ich obsługi napisany cały program w Lua do zarządzania nimi i nie wyobrażam sobie ręcznego zarządzania include guard. Nie wiem jak działają na chwilę obecną moduły w C++, ale po sześciu latach od wprowadzeniu ich obsługi spodziewałem się, że już są w miarę stabilne. 

0 głosów
odpowiedź 15 czerwca przez lorenz Początkujący (470 p.)

Skoro #pragma once jest stare to chcę przepisać tę grę na moduły ze standardu c++20.

Mam taki prosty program z modułami i on działa.

main.cpp

import std;
import Burrito;

int main()
{
    Burrito bo;
}

Burrito.cpp

module Burrito;
import std;

Burrito::Burrito()
{
    std::println("i am a burrito");
}

Burrito.ixx

export module Burrito;
import std;

// eksportujemy klasę do świata zewnętrznego
export class Burrito {
public:
    Burrito();
};
komentarz 18 czerwca przez adrian17 Mentor (355,160 p.)

Skoro #pragma once jest stare

Nie jest stare, tylko absolutnie normalnie działają na każdym współczesnym toolchainie, czego nie można powiedzieć o modułach. WojAbuk chwali jakie są dobre, a sam przyznaje że nie wie jak teraz działają.

CMakeLists.txt dla GCC 16

CMakeLists.txt dla Clang 22.1.7

Dokładnie po to jest cmake, żeby nie trzeba było mieć osobnych plików configów dla różnych toolchainów.

0 głosów
odpowiedź 15 czerwca przez lorenz Początkujący (470 p.)

Jednak z większą ilością modułów nie chcę działać.

Game.cpp

module Game;

import std;
import Enemy;
import Player;
import Print;

enum class GameState {
    MainMenu,
    CharacterSelect,
    Playing,
    Exit
};

static int GetEnemyCount()
{
    int roll = std::rand() % 100;
    if (roll < 50) return 1;
    else if (roll < 75) return 2;
    else if (roll < 90) return 3;
    else return 4;
}

static int GetEnemyType() { return std::rand() % 4; }
static int GetEnemyLevel() { return 1 + std::rand() % 3; }

void RunGame()
{
    Player player;

    std::srand(std::time(0));

    bool running = true;
    GameState state = GameState::MainMenu;

    while (running)
    {
        if (state == GameState::MainMenu)
        {
            Print::WriteColor("====UpiornePotyczki====\n\n", Color::Red);
            Print::Write("1. Nowa Gra\n");
            Print::Write("2. Wyjście\n");

            int choice;
            std::cin >> choice;

            state = (choice == 1) ? GameState::CharacterSelect : GameState::Exit;
            Print::Clear();
        }

        else if (state == GameState::CharacterSelect)
        {
            Print::WriteColor("Wybierz klasę:\n\n", Color::Yellow);
            Print::Write("1. Wojownik\n2. Łotrzyk\n3. Mag\n");

            int choice;
            std::cin >> choice;

            player.SetClass(choice);
            player.DisplayPickedCharacter();

            int tmp;
            std::cin >> tmp;

            Print::Clear();
            state = GameState::Playing;
        }

        else if (state == GameState::Playing)
        {
            std::vector<Enemy> enemies;

            int enemyCount = GetEnemyCount();

            for (int i = 0; i < enemyCount; i++)
            {
                Enemy e;
                e.createEnemy(GetEnemyType());
                e.SetLevel(GetEnemyLevel());
                enemies.push_back(e);
            }

            bool inCombat = true;

            while (inCombat)
            {
                Print::Clear();
                Print::WriteColor("Pojawiają się przeciwnicy!\n\n", Color::Red);

                for (int i = 0; i < enemies.size(); i++)
                {
                    Print::Write("Przeciwnik " + std::to_string(i + 1) + ": ");
                    Print::WriteColor(enemies[i].name, Color::Yellow);
                    Print::Write("\n");
                }

                int choice;
                std::cin >> choice;

                if (choice == 2)
                    inCombat = false;
            }

            state = GameState::Exit;
        }
        else
        {
            running = false;
        }
    }

    Print::WriteColor("\nKoniec gry\n", Color::Magenta);
}

Game.ixx

export module Game;

import std;
import Enemy;
import Player;
import Print;

export void RunGame();

Enemy.cpp

module Enemy;

import std;

void Enemy::createEnemy(int type)
{
    if (type == 0) {
        name = "Zombie";
        maxHealth = 50;
        damage = 5;
    }
    else if (type == 1) {
        name = "Szkieletor";
        maxHealth = 35;
        damage = 8;
    }
    else if (type == 2) {
        name = "Goblinek";
        maxHealth = 30;
        damage = 10;
    }
    else {
        name = "Zombiak";
        maxHealth = 50;
        damage = 5;
    }

    currentHealth = maxHealth;
}

void Enemy::SetLevel(int enemyLevel)
{
    level = enemyLevel;

    maxHealth += (level - 1) * 10;
    damage += (level - 1) * 2;

    currentHealth = maxHealth;
}

Enemy.ixx

export module Enemy;

import std;

export class Enemy {
public:
    std::string name;
    int maxHealth = 0;
    int currentHealth = 0;
    int level = 1;
    int damage = 0;

    void createEnemy(int type);
    void SetLevel(int enemyLevel);
};

Player.ixx

export module Player;

import std;
import Print;

export class Player {
public:
    std::string name;
    std::string playerClass;

    int strength = 0;
    int intelligence = 0;
    int vitality = 0;

    int maxHealth = 0;
    int currentHealth = 0;

    int maxMana = 0;
    int currentMana = 0;

    int damage = 0;

    void SetClass(int choice);
    void CalculateStats();
    void DisplayPickedCharacter();
};

Print.cpp

module Print;

import std;

void Print::Write(const std::string& text)
{
    std::print("{}", text);
}

void Print::SetColor(Color color)
{
    switch (color) {
    case Color::Red: std::print("\033[31m"); break;
    case Color::Green: std::print("\033[32m"); break;
    case Color::Yellow: std::print("\033[33m"); break;
    case Color::Cyan: std::print("\033[36m"); break;
    case Color::Blue: std::print("\033[34m"); break;
    case Color::Magenta: std::print("\033[35m"); break;
    case Color::White: std::print("\033[37m"); break;
    case Color::Black: std::print("\033[30m"); break;
    default: std::print("\033[0m"); break;
    }
}

void Print::WriteColor(const std::string& text, Color color)
{
    SetColor(color);
    std::print("{}", text);
    SetColor(Color::Default);
}

void Print::Clear()
{
    std::system("clear");
}

Print.ixx

export module Print;

import std;

export enum class Color {
    Default, Red, Green, Yellow, Cyan, Blue, Magenta, White, Black
};

export class Print {
public:
    static void Write(const std::string& text);
    static void SetColor(Color color);
    static void WriteColor(const std::string& text, Color color);
    static void Clear();
};

Makefile

CXX = g++-16
CXXFLAGS = -std=c++26 -fmodules -O2 -Wall

TARGET = game

# moduły
MODS = Print.ixx Enemy.ixx Player.ixx Game.ixx
MOD_OBJS = Print.o Enemy.o Player.o Game.o

# main
MAIN = main.o

all: $(TARGET)

# --- moduły ---
Print.o: Print.ixx
	$(CXX) $(CXXFLAGS) -c Print.ixx -o Print.o

Enemy.o: Enemy.ixx
	$(CXX) $(CXXFLAGS) -c Enemy.ixx -o Enemy.o

Player.o: Player.ixx
	$(CXX) $(CXXFLAGS) -c Player.ixx -o Player.o

Game.o: Game.ixx
	$(CXX) $(CXXFLAGS) -c Game.ixx -o Game.o

# --- main ---
main.o: main.cpp
	$(CXX) $(CXXFLAGS) -c main.cpp -o main.o

# --- linkowanie ---
$(TARGET): $(MOD_OBJS) $(MAIN)
	$(CXX) $(CXXFLAGS) $^ -o $(TARGET)

run: $(TARGET)
	./$(TARGET)

clean:
	rm -f *.o $(TARGET)

CMakeLists.txt dla GCC 16

cmake_minimum_required(VERSION 3.28)
project(UpiornePotyczki LANGUAGES CXX)

set(CMAKE_CXX_STANDARD 26)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
add_compile_options(-fmodules)
set(CMAKE_CXX_SCAN_FOR_MODULES OFF)

add_executable(game
    main.cpp
)

target_sources(game PRIVATE
    Game.ixx
    Player.ixx
    Enemy.ixx
    Print.ixx
)

CMakeLists.txt dla Clang 22.1.7

cmake_minimum_required(VERSION 3.28)
project(UpiornePotyczki LANGUAGES CXX)

set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_COMPILER clang++)

add_executable(game
    main.cpp
)

target_sources(game PRIVATE
    Game.ixx
    Player.ixx
    Enemy.ixx
    Print.ixx
)
komentarz 15 czerwca przez lorenz Początkujący (470 p.)

Mam błąd przy poleceniu make 


rm -rf build
mkdir build
cd build
cmake -DCMAKE_CXX_COMPILER=g++-16 -DCMAKE_CXX_STANDARD=26 ..
make
make
[ 16%] Building CXX object CMakeFiles/game.dir/main.cpp.o
In module imported at /home/user/UpiornePotyczki/main.cpp:1:1:
Game: error: failed to read compiled module: Nie ma takiego pliku ani katalogu
Game: note: compiled module file is ‘gcm.cache/Game.gcm’
Game: note: imports must be built before being imported
Game: fatal error: returning to the gate for a mechanical issue
compilation terminated.
make[2]: *** [CMakeFiles/game.dir/build.make:79: CMakeFiles/game.dir/main.cpp.o] Błąd 1
make[1]: *** [CMakeFiles/Makefile2:87: CMakeFiles/game.dir/all] Błąd 2
make: *** [Makefile:91: all] Błąd 2

GCC musi wygenerować .gcm zanim skompiluje main.cpp ale Game.ixx NIE został jeszcze zbudowany jako .gcm

komentarz 15 czerwca przez lorenz Początkujący (470 p.)

Tak też powinno działać w CodeRunner.

"cpp": "clear && cd $dir && mkdir -p bin && cd bin && g++-16 -std=c++26 -fmodules --compile-std-module ../Print.ixx ../Enemy.ixx ../Player.ixx ../Game.ixx ../Print.cpp ../Enemy.cpp ../Game.cpp ../main.cpp -o game && ./game"

"cpp": "clear && cd $dir && mkdir -p bin && cd bin && clang++ -std=c++26 -fmodules --compile-std-module ../Print.ixx ../Enemy.ixx ../Player.ixx ../Game.ixx ../Print.cpp ../Enemy.cpp ../Game.cpp ../main.cpp -o game && ./game"
0 głosów
odpowiedź 9 lipca przez lorenz Początkujący (470 p.)
edycja 9 lipca przez lorenz

Przepisałem grę do Rust i Zig. Jest trochę mniej kodu.

main.rs

mod enemy;
mod player;
mod print;

use crate::enemy::Enemy;
use crate::player::Player;
use crate::print::{Color, Print};
use rand::Rng;
use std::io;

fn get_enemy_count() -> usize {
    let mut rng = rand::rng();
    let roll = rng.random_range(0..100);
    
    match roll {
        0..=49 => 1,
        50..=74 => 2,
        75..=89 => 3,
        _ => 4,
    }
}

fn get_enemy_type() -> u8 {
    let mut rng = rand::rng();
    rng.random_range(0..3)
}

fn get_enemy_level() -> u8 {
    let mut rng = rand::rng();
    rng.random_range(1..=3)
}

fn main() {
    let mut player = Player::new();

    loop {
        Print::clear();
        Print::write_color("==== UpiornePotyczki ====\n\n", Color::Red);
        Print::write("1. Nowa Gra\n");
        Print::write("2. Wyjście\n");
        Print::write_color("\nWybierz opcję: ", Color::Yellow);

        let mut input = String::new();
        io::stdin().read_line(&mut input).unwrap();
        let choice = input.trim().parse::<u8>().unwrap_or(0);

        if choice == 2 {
            break;
        } else if choice == 1 {
            // wybór klasy
            Print::clear();
            Print::write_color("Wybierz klasę:\n\n", Color::Yellow);
            Print::write("1. Wojownik\n2. Łotrzyk\n3. Mag\n");
            Print::write_color("\nWybierz opcję: ", Color::Yellow);

            input.clear();
            io::stdin().read_line(&mut input).unwrap();
            let class_choice = input.trim().parse::<u8>().unwrap_or(1);
            player.set_class(class_choice);
            player.display();

            // rozpoczęcie walki
            let enemy_count = get_enemy_count();
            let mut enemies: Vec<Enemy> = Vec::new();
            for _ in 0..enemy_count {
                let mut e = Enemy::new();
                e.create_enemy(get_enemy_type());
                e.set_level(get_enemy_level());
                enemies.push(e);
            }

            let mut in_combat = true;
            while in_combat {
                Print::clear();
                Print::write_color("Przeciwnicy:\n", Color::Red);
                for (i, e) in enemies.iter().enumerate() {
                    Print::write(&format!("{}: {} lvl {} ", i + 1, e.name, e.level));
                    Print::draw_hp_bar(e.current_health, e.max_health, 20, Color::Green);
                }
                Print::write("\nTwoje HP: ");
                Print::draw_hp_bar(player.current_health, player.max_health, 20, Color::Cyan);

                Print::write("\n1. Atak\n2. Ucieczka\nWybierz: ");
                input.clear();
                io::stdin().read_line(&mut input).unwrap();
                let combat_choice = input.trim().parse::<u8>().unwrap_or(1);

                if combat_choice == 2 {
                    Print::write_color("\nUciekasz!\n", Color::Yellow);

                    Print::write("\nNaciśnij ENTER, aby kontynuować...");
                    let mut pause = String::new();
                    io::stdin().read_line(&mut pause).unwrap();

                    break;
                } else if combat_choice == 1 {
                    Print::write_color("\nWybierz przeciwnika: ", Color::Yellow);
                    input.clear();
                    io::stdin().read_line(&mut input).unwrap();
                    let target_idx = input.trim().parse::<usize>().unwrap_or(1) - 1;

                    if target_idx < enemies.len() {
                        let dmg = player.damage;
                        let e = &mut enemies[target_idx];
                        e.current_health = e.current_health.saturating_sub(dmg);
                        Print::write(&format!("\nZadajesz {} obrażeń {}!\n", dmg, e.name));

                        if e.current_health == 0 {
                            Print::write_color(&format!("{} pokonany!\n", e.name), Color::Green);
                            enemies.remove(target_idx);
                        }

                        if enemies.is_empty() {
                            Print::write_color("\nWygrałeś walkę!\n", Color::Green);

                            Print::write("\nNaciśnij ENTER, aby kontynuować...");
                            let mut pause = String::new();
                            io::stdin().read_line(&mut pause).unwrap();

                            in_combat = false;
                        } else {
                            // atak przeciwników
                            for e in enemies.iter() {
                                player.current_health =
                                    player.current_health.saturating_sub(e.damage);
                                Print::write_color(
                                    &format!("{} zadaje {} obrażeń!\n", e.name, e.damage),
                                    Color::Red,
                                );
                                if player.current_health == 0 {
                                    Print::write_color("\nZostałeś pokonany!\n", Color::Red);
                                    in_combat = false;
                                    break;
                                }
                            }
                        }
                    }
                }
            }
        }
    }

    Print::write_color("\nDzięki za grę!\n", Color::Magenta);
}

player.rs

use crate::print::{Color, Print};

pub struct Player {
    pub name: String,
    pub player_class: String,
    pub strength: u32,
    pub intelligence: u32,
    pub vitality: u32,
    pub max_health: u32,
    pub current_health: u32,
    pub damage: u32,
}

impl Player {
    pub fn new() -> Self {
        Self {
            name: String::new(),
            player_class: String::new(),
            strength: 0,
            intelligence: 0,
            vitality: 0,
            max_health: 0,
            current_health: 0,
            damage: 0,
        }
    }

    pub fn set_class(&mut self, choice: u8) {
        self.name = "Bohater".to_string();
        match choice {
            1 => {
                self.player_class = "Wojownik".to_string();
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            }
            2 => {
                self.player_class = "Łotrzyk".to_string();
                self.strength = 6;
                self.intelligence = 5;
                self.vitality = 6;
            }
            3 => {
                self.player_class = "Mag".to_string();
                self.strength = 2;
                self.intelligence = 10;
                self.vitality = 5;
            }
            _ => {
                self.player_class = "Wojownik".to_string();
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            }
        }
        self.calculate_stats();
    }

    fn calculate_stats(&mut self) {
        self.max_health = 50 + self.vitality * 10;
        self.current_health = self.max_health;
        self.damage = match self.player_class.as_str() {
            "Wojownik" => self.strength * 2,
            "Łotrzyk" => self.strength * 2 + 2,
            "Mag" => self.intelligence * 2,
            _ => 5,
        };
    }

    pub fn display(&self) {
        Print::clear();
        Print::write("Wybrałeś ");
        Print::write_color(&self.player_class, Color::Cyan);
        Print::write("!\n\n");

        Print::write(&format!("Siła: {}\n", self.strength));
        Print::write(&format!("Inteligencja: {}\n", self.intelligence));
        Print::write(&format!("Witalność: {}\n", self.vitality));

        Print::write("Zdrowie: ");
        Print::draw_hp_bar(self.current_health, self.max_health, 20, Color::Green);
    }
}use crate::print::{Color, Print};

pub struct Player {
    pub name: String,
    pub player_class: String,
    pub strength: u32,
    pub intelligence: u32,
    pub vitality: u32,
    pub max_health: u32,
    pub current_health: u32,
    pub damage: u32,
}

impl Player {
    pub fn new() -> Self {
        Self {
            name: String::new(),
            player_class: String::new(),
            strength: 0,
            intelligence: 0,
            vitality: 0,
            max_health: 0,
            current_health: 0,
            damage: 0,
        }
    }

    pub fn set_class(&mut self, choice: u8) {
        self.name = "Bohater".to_string();
        match choice {
            1 => {
                self.player_class = "Wojownik".to_string();
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            }
            2 => {
                self.player_class = "Łotrzyk".to_string();
                self.strength = 6;
                self.intelligence = 5;
                self.vitality = 6;
            }
            3 => {
                self.player_class = "Mag".to_string();
                self.strength = 2;
                self.intelligence = 10;
                self.vitality = 5;
            }
            _ => {
                self.player_class = "Wojownik".to_string();
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            }
        }
        self.calculate_stats();
    }

    fn calculate_stats(&mut self) {
        self.max_health = 50 + self.vitality * 10;
        self.current_health = self.max_health;
        self.damage = match self.player_class.as_str() {
            "Wojownik" => self.strength * 2,
            "Łotrzyk" => self.strength * 2 + 2,
            "Mag" => self.intelligence * 2,
            _ => 5,
        };
    }

    pub fn display(&self) {
        Print::clear();
        Print::write("Wybrałeś ");
        Print::write_color(&self.player_class, Color::Cyan);
        Print::write("!\n\n");

        Print::write(&format!("Siła: {}\n", self.strength));
        Print::write(&format!("Inteligencja: {}\n", self.intelligence));
        Print::write(&format!("Witalność: {}\n", self.vitality));

        Print::write("Zdrowie: ");
        Print::draw_hp_bar(self.current_health, self.max_health, 20, Color::Green);
    }
}

print.rs

use crossterm::{
    ExecutableCommand,
    cursor::MoveTo,
    style::Color as CtColor,
    style::Stylize,
    terminal::{Clear, ClearType},
};
use std::io::{Write, stdout};

#[derive(Clone, Copy)]
pub enum Color {
    //Default,
    Red,
    Green,
    Yellow,
    Cyan,
    //Blue,
    Magenta,
    //White,
    //Black,
}

pub struct Print;

impl Print {
    pub fn write(text: &str) {
        print!("{}", text);
        stdout().flush().unwrap();
    }

    pub fn write_color(text: &str, color: Color) {
        let ct_color = match color {
            Color::Red => CtColor::Red,
            Color::Green => CtColor::Green,
            Color::Yellow => CtColor::Yellow,
            Color::Cyan => CtColor::Cyan,
            //Color::Blue => CtColor::Blue,
            Color::Magenta => CtColor::Magenta,
            //Color::White => CtColor::White,
            //Color::Black => CtColor::Black,
            //Color::Default => CtColor::Reset,
        };
        print!("{}", text.with(ct_color));
        stdout().flush().unwrap();
    }

    pub fn clear() {       
        let mut stdout = stdout();

        stdout.execute(Clear(ClearType::All)).unwrap();
        stdout.execute(MoveTo(0, 0)).unwrap();

        stdout.flush().unwrap();
    }

    pub fn draw_hp_bar(current: u32, max: u32, width: usize, color: Color) {
        let filled = (current * width as u32) / max;
        let empty = width as u32 - filled;
        let bar = format!(
            "[{}{}] {}/{}",
            "█".repeat(filled as usize),
            " ".repeat(empty as usize),
            current,
            max
        );
        Print::write_color(&bar, color);
        Print::write("\n");
    }
}

enemy.rs

pub struct Enemy {
    pub name: String,
    pub max_health: u32,
    pub current_health: u32,
    pub level: u8,
    pub damage: u32,
}

impl Enemy {
    pub fn new() -> Self {
        Self {
            name: String::new(),
            max_health: 0,
            current_health: 0,
            level: 1,
            damage: 0,
        }
    }

    pub fn create_enemy(&mut self, enemy_type: u8) {
        match enemy_type {
            0 => { self.name = "Zombie".to_string(); self.max_health = 30; self.damage = 5; },
            1 => { self.name = "Szkieletor".to_string(); self.max_health = 25; self.damage = 6; },
            2 => { self.name = "Goblin".to_string(); self.max_health = 20; self.damage = 4; },
            _ => { self.name = "Zombie".to_string(); self.max_health = 30; self.damage = 5; },
        }
        self.current_health = self.max_health;
    }

    pub fn set_level(&mut self, level: u8) {
        self.level = level;
        self.max_health += (level as u32 - 1) * 10;
        self.current_health = self.max_health;
        self.damage += (level as u32 - 1) * 2;
    }
}

Cargo.toml

[package]
name = "upiorne_potyczki"
version = "0.1.0"
edition = "2024"

[dependencies]
crossterm = "0.26"
rand = "0.9"
0 głosów
odpowiedź 9 lipca przez lorenz Początkujący (470 p.)

Wersja Zig

enemy.zig

const std = @import("std");

pub const Enemy = struct {
    name: []const u8,
    max_health: u32,
    current_health: u32,
    level: u8,
    damage: u32,

    pub fn init() Enemy {
        return Enemy{
            .name = "",
            .max_health = 0,
            .current_health = 0,
            .level = 1,
            .damage = 0,
        };
    }

    pub fn createEnemy(self: *Enemy, enemy_type: u8) void {
        switch (enemy_type) {
            0 => {
                self.name = "Zombie";
                self.max_health = 30;
                self.damage = 5;
            },

            1 => {
                self.name = "Szkieletor";
                self.max_health = 25;
                self.damage = 6;
            },

            2 => {
                self.name = "Goblin";
                self.max_health = 20;
                self.damage = 4;
            },

            else => {
                self.name = "Zombie";
                self.max_health = 30;
                self.damage = 5;
            },
        }

        self.current_health = self.max_health;
    }

    pub fn setLevel(self: *Enemy, level: u8) void {
        self.level = level;

        self.max_health += (@as(u32, level) - 1) * 10;
        self.current_health = self.max_health;

        self.damage += (@as(u32, level) - 1) * 2;
    }
};

player.zig

const std = @import("std");
const Print = @import("print.zig").Print;
const Color = @import("print.zig").Color;

pub const PlayerClass = enum {
    Warrior,
    Rogue,
    Mage,
};

pub const Player = struct {
    name: []const u8,
    class: PlayerClass,

    strength: u32,
    intelligence: u32,
    vitality: u32,

    max_health: u32,
    current_health: u32,

    damage: u32,

    pub fn init() Player {
        return Player{
            .name = "",
            .class = .Warrior,

            .strength = 0,
            .intelligence = 0,
            .vitality = 0,

            .max_health = 0,
            .current_health = 0,

            .damage = 0,
        };
    }

    pub fn setClass(
        self: *Player,
        choice: u8,
    ) void {
        self.name = "Bohater";

        switch (choice) {
            1 => {
                self.class = .Warrior;
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            },

            2 => {
                self.class = .Rogue;
                self.strength = 6;
                self.intelligence = 5;
                self.vitality = 6;
            },

            3 => {
                self.class = .Mage;
                self.strength = 2;
                self.intelligence = 10;
                self.vitality = 5;
            },

            else => {
                self.class = .Warrior;
                self.strength = 10;
                self.intelligence = 2;
                self.vitality = 8;
            },
        }

        self.calculateStats();
    }

    fn calculateStats(
        self: *Player,
    ) void {
        self.max_health =
            50 + self.vitality * 10;

        self.current_health =
            self.max_health;

        self.damage = switch (self.class) {
            .Warrior => self.strength * 2,

            .Rogue => self.strength * 2 + 2,

            .Mage => self.intelligence * 2,
        };
    }

    pub fn display(
        self: Player,
    ) void {
        Print.clear();

        Print.write("Wybrałeś ");

        const class_name = switch (self.class) {
            .Warrior => "Wojownik",
            .Rogue => "Łotrzyk",
            .Mage => "Mag",
        };

        Print.writeColor(
            class_name,
            Color.Cyan,
        );

        Print.write("\n\n");

        std.debug.print(
            "Siła: {}\n",
            .{self.strength},
        );

        std.debug.print(
            "Inteligencja: {}\n",
            .{self.intelligence},
        );

        std.debug.print(
            "Witalność: {}\n",
            .{self.vitality},
        );

        Print.write("Zdrowie: ");

        Print.drawHpBar(
            self.current_health,
            self.max_health,
            20,
            Color.Green,
        );
    }
};

print.zig

const std = @import("std");

pub const Color = enum {
    Default,
    Red,
    Green,
    Yellow,
    Cyan,
    Blue,
    Magenta,
    White,
    Black,
};

pub const Print = struct {
    pub fn write(text: []const u8) void {
        std.debug.print("{s}", .{text});
    }

    pub fn writeColor(text: []const u8, color: Color) void {
        const code = switch (color) {
            .Red => "\x1b[31m",
            .Green => "\x1b[32m",
            .Yellow => "\x1b[33m",
            .Cyan => "\x1b[36m",
            .Blue => "\x1b[34m",
            .Magenta => "\x1b[35m",
            .White => "\x1b[37m",
            .Black => "\x1b[30m",
            .Default => "\x1b[0m",
        };

        std.debug.print("{s}{s}\x1b[0m", .{
            code,
            text,
        });
    }

    pub fn clear() void {
        std.debug.print("\x1b[2J\x1b[H", .{});
    }

    pub fn drawHpBar(
        current: u32,
        max: u32,
        width: usize,
        color: Color,
    ) void {
        const filled = (current * width) / max;
        const empty = width - filled;

        Print.writeColor(
            "[",
            color,
        );

        for (0..filled) |_| {
            Print.write("█");
        }

        for (0..empty) |_| {
            Print.write(" ");
        }

        std.debug.print("] {}/{}\n", .{
            current,
            max,
        });
    }
};

main.zig

const std = @import("std");

const Player = @import("player.zig").Player;
const Enemy = @import("enemy.zig").Enemy;
const Print = @import("print.zig").Print;
const Color = @import("print.zig").Color;

var random_counter: u32 = 0;

fn readNumber() u8 {
    var buffer: [32]u8 = undefined;

    const size = std.posix.read(
        0,
        &buffer,
    ) catch return 0;

    var end: usize = 0;

    while (end < size and buffer[end] != '\n') {
        end += 1;
    }

    return std.fmt.parseInt(
        u8,
        buffer[0..end],
        10,
    ) catch 0;
}

fn waitEnter() void {
    var buffer: [8]u8 = undefined;

    _ = std.posix.read(
        0,
        &buffer,
    ) catch {};
}

fn getEnemyType() u8 {
    random_counter += 1;

    return @intCast(
        random_counter % 3,
    );
}

fn getEnemyCount() usize {
    random_counter += 1;

    return switch (random_counter % 4) {
        0 => 1,
        1 => 2,
        2 => 3,
        else => 4,
    };
}

fn getEnemyLevel() u8 {
    random_counter += 1;

    return @intCast(
        (random_counter % 3) + 1,
    );
}

pub fn main() !void {
    var player = Player.init();

    while (true) {
        Print.clear();

        Print.writeColor(
            "==== UpiornePotyczki Zig ====\n\n",
            Color.Red,
        );

        Print.write(
            "1. Nowa Gra\n",
        );

        Print.write(
            "2. Wyjście\n\n",
        );

        Print.writeColor(
            "Wybierz: ",
            Color.Yellow,
        );

        const menu = readNumber();

        if (menu == 2) {
            break;
        }

        if (menu != 1) {
            continue;
        }

        Print.clear();

        Print.writeColor(
            "Wybierz klasę:\n\n",
            Color.Yellow,
        );

        Print.write(
            "1. Wojownik\n",
        );

        Print.write(
            "2. Łotrzyk\n",
        );

        Print.write(
            "3. Mag\n\n",
        );

        Print.writeColor(
            "Wybierz: ",
            Color.Yellow,
        );

        player.setClass(
            readNumber(),
        );

        player.display();

        waitEnter();

        var enemies: [4]Enemy = undefined;

        var enemy_count =
            getEnemyCount();

        var i: usize = 0;

        while (i < enemy_count) {
            enemies[i] =
                Enemy.init();

            enemies[i].createEnemy(
                getEnemyType(),
            );

            enemies[i].setLevel(
                getEnemyLevel(),
            );

            i += 1;
        }

        var fighting = true;

        while (fighting) {
            Print.clear();

            Print.writeColor(
                "=== WALKA ===\n\n",
                Color.Red,
            );

            i = 0;

            while (i < enemy_count) {
                std.debug.print(
                    "{}. {s} lvl {}\n",
                    .{
                        i + 1,
                        enemies[i].name,
                        enemies[i].level,
                    },
                );

                Print.drawHpBar(
                    enemies[i].current_health,
                    enemies[i].max_health,
                    20,
                    Color.Green,
                );

                i += 1;
            }

            Print.write(
                "\nTwoje HP:\n",
            );

            Print.drawHpBar(
                player.current_health,
                player.max_health,
                20,
                Color.Green,
            );

            Print.write(
                "\n1. Atak\n",
            );

            Print.write(
                "2. Ucieczka\n\n",
            );

            Print.writeColor(
                "Wybierz: ",
                Color.Yellow,
            );

            const action =
                readNumber();

            if (action == 2) {
                Print.writeColor(
                    "\nUciekasz!\n",
                    Color.Yellow,
                );

                fighting = false;

                continue;
            }

            if (action == 1) {
                Print.write(
                    "\nWybierz przeciwnika: ",
                );

                const target =
                    readNumber();

                if (target == 0 or target > enemy_count) {
                    continue;
                }

                const index =
                    target - 1;

                enemies[index].current_health =
                    if (enemies[index].current_health > player.damage)
                        enemies[index].current_health - player.damage
                    else
                        0;

                std.debug.print(
                    "\nZadajesz {} obrażeń {s}\n",
                    .{
                        player.damage,
                        enemies[index].name,
                    },
                );

                if (enemies[index].current_health == 0) {
                    Print.writeColor(
                        "Pokonany!\n",
                        Color.Green,
                    );

                    enemies[index] =
                        enemies[enemy_count - 1];

                    enemy_count -= 1;
                }

                if (enemy_count == 0) {
                    Print.writeColor(
                        "\nWygrałeś walkę!\n",
                        Color.Green,
                    );

                    fighting = false;

                    continue;
                }

                i = 0;

                while (i < enemy_count) {
                    player.current_health =
                        if (player.current_health > enemies[i].damage)
                            player.current_health - enemies[i].damage
                        else
                            0;

                    std.debug.print(
                        "{s} zadaje {} obrażeń!\n",
                        .{
                            enemies[i].name,
                            enemies[i].damage,
                        },
                    );

                    if (player.current_health == 0) {
                        Print.writeColor(
                            "\nZostałeś pokonany!\n",
                            Color.Red,
                        );

                        fighting = false;

                        break;
                    }

                    i += 1;
                }

                waitEnter();
            }
        }

        Print.write(
            "\nENTER aby wrócić do menu...\n",
        );

        waitEnter();
    }

    Print.writeColor(
        "\nDzięki za grę!\n",
        Color.Magenta,
    );
}

Kompilujemy za pomocą zig run.

Podobne pytania

0 głosów
2 odpowiedzi 1,033 wizyt
pytanie zadane 14 września 2018 w Systemy operacyjne, programy przez comoto45 Nowicjusz (160 p.)
+2 głosów
2 odpowiedzi 1,119 wizyt
pytanie zadane 3 listopada 2017 w Nasze projekty przez Insygnia Nowicjusz (150 p.)
–1 głos
0 odpowiedzi 1,244 wizyt
pytanie zadane 26 marca 2017 w C i C++ przez WireNess Stary wyjadacz (11,250 p.)

93,762 zapytań

142,717 odpowiedzi

323,368 komentarzy

63,359 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj

Twierdza Linux. Bezpieczeństwo dla dociekliwych

Aby uzyskać rabat -10%, użyjcie kodu pasja-linux, wpisując go w specjalne pole w koszyku.

...