Instanz einer Klasse an Funktion anderer Klasse übergeben



  • Hallo zusammen,

    ich versuche mich gerade an einem kleinen Spiel mit der SDL und C++.
    Ist das 1., das ich schreibe und benutzte das ganze damit auch zum Lernen...

    Hab jetzt aber eine Frage und zwar:

    Ich habe bisher 2 Klassen geschrieben, 1 für die Grafik und 1 namens "Spieler", in der bisher die Koordinaten des Spielers stehen.
    Im Hauptcode erstelle ich nun eine Instanz von beidem und möchte nun eine Funktion der Grafikklasse aufrufen und dieser als Parameter den "Spieler1" geben (die Instanz der Spielerklasse).
    Dafür hab' ich einen Pointer vom Typ "Spieler", der auf die Instanz "Spieler1" zeigt.
    Den übergeb' ich. Jetzt wollte ich in der Grafikklasse diesen Pointer deklarieren/anmelden, bekomm' da aber immer eine Fehlermeldung "ISO C++ forbids declaration of "Spieler" with no type.
    Was ist da wohl das Problem?

    Ich habe die "spieler.hpp" der Spielerklasse nur in der main-Datei inkludiert, wenn ich die auch noch in der Grafikklasse in den Header stecke, bekomme ich den Fehler, dass die Klasse 2x definiert wird 😕

    Weiß jemand weiter?

    Hier bisschen Code:

    main:

    #include <iostream>
    #include "SDL/SDL.h"
    #include "grafik.hpp"
    #include "spieler.hpp"
    
    //zum Code testen: www.codepad.org
    
    using namespace std;
    
    //The attributes of the screen
    const int SCREEN_WIDTH = 1200;  // Hier wird die Größe des Ausgabebildschirms festgelegt....
    const int SCREEN_HEIGHT = 800;
    const int SCREEN_BPP = 32;  //SCREEN_BPP is the bits per-pixel. In all of the tutorials, 32-bit color will be used.
    
    float time1, time2, time_gesamt;
    int test;
    int contador1=0;
    bool game=true;
    
    SDL_Surface *screen, *osito_vorne = NULL; // Pointer auf Null setzen
    SDL_Rect dest2;
    SDL_Event event;
    Uint8 *keys;
    Spieler *p_Spieler1 = NULL;
    
     int main( int argc, char* args[] ) // SDL brauch diese Parameter
    {
        cout << "hallo" << endl; // Wie schreib ich in die Konsole? -> SDL leitet das ganze in eine Textdatei um, die sich im bin-Ordner befindet
    
        // INITIALISIERUNG VON SDL
        if (SDL_Init ( SDL_INIT_EVERYTHING ) == -1)
            cout << "Fehler in der SDL-Initialisierung" << endl;
    
        screen = SDL_SetVideoMode( SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_BPP, SDL_SWSURFACE ); // Zeiger wird initialisiert
        SDL_WM_SetCaption( "Artes marciales", NULL );
    
        time1 = SDL_GetTicks(); // speichert die Zeit in Milisekunden
        cout << time1 << endl;
    
    Grafik Zeichnung; // Instanz der Klasse Grafik  , am besten hier schon den screen übergeben und für alle Memberfunktionen zugänglich machen
    Spieler Spieler1; // Instanz für den Spieler1
    p_Spieler1 = &Spieler1;
    
        while (game==true)
        {
            while (SDL_PollEvent(&event))
            {
            cout << "Zähler1:" << contador1 << endl;
    
            //Zeichnung.update(screen); // 1x pro Schleifendurchlauf wird gezeichnet! screen-Zeiger muss übergeben werden...
            SDL_Flip(screen);
    
            // consultamos el estado del teclado
            keys=SDL_GetKeyState(NULL);
            //if (keys[SDLK_UP]) {dest1.x +=20;}
            if (keys[SDLK_DOWN]) {game=false;}
            if (keys[SDLK_RIGHT]) {Zeichnung.update(screen,osito_vorne,p_Spieler1); Spieler1.laufen_rechts();} // Zeiger wird übergeben
            cout << "Schleife" <<endl;
    

    grafik.hpp:

    #include <iostream>
    #include "SDL/SDL.h"
    //#include "spieler.hpp"
    
    using namespace std;
    
    class Grafik
    {
      private:
      // Membervariablen
      int x_koordinate_spieler1, y_koordinate_spieler1; // sollte ich mir aus der Klasse Spieler holen!
      int x_koordinate_gegner, y_koordinate_gegner;
      SDL_Rect dest3;
      SDL_Rect hintergrund_werte;
      SDL_Rect osito_werte, osito_werte_overwrite;
    
      public:
    
      SDL_Surface *screen, *osito_vorne, *hintergrund;
      Spieler *p_Spieler1;
    
     /* SDL_Surface *osito_vorne = NULL;
      osito_vorne = SDL_LoadBMP("osito_vorne.bmp");
      SDL_Rect dest1, dest1_overwrite;
      dest1_overwrite=dest1;  // löscht die vorherige Position der Animation
      SDL_SetColorKey(osito_vorne, SDL_SRCCOLORKEY|SDL_RLEACCEL, SDL_MapRGB(osito_vorne->format,255,0,255));
        //              für welches Bild,                                      Format für das Bild, R,G,B der transparenten Farbe
    
      // Definimos donde dibujaremos el gráfico
            // y lo copiamos a la pantalla.
            dest1.x = 100;
            dest1.y = 100;
            dest1.w = osito_vorne->w;
            dest1.h = osito_vorne->h;
    */
      //Memberfunktionen
      void update(SDL_Surface *screen, SDL_Surface *osito_vorne, Spieler *p_Spieler1);
      void draw_hintergrund (SDL_Surface *screen, SDL_Surface *osito_vorne);
      void draw_spieler1 (SDL_Surface *screen, SDL_Surface *osito_vorne, Spieler *p_Spieler1);
      //void draw_gegner ();
    
    };
    

    spieler.hpp:

    #include <iostream>
    
    using namespace std;
    
    class Spieler
    {
    
      private:
      //Membervariablen
      int x_koordinate_spieler1; // können hier nicht initalisiert werden?
      int y_koordinate_spieler1;
    
      public:
      //Memberfunktionen
           Spieler(); //Konstruktor, initialisiert die Werte... Achtung!: Muss genau wie die Klasse heißen und ohne void!
      void laufen_rechts();
    
    };
    

    Danke für alle Tipps! 🙂



  • Du musst deine Header mit Includeguards versehen, dann vermeidest du das Problem mit den doppelten Definitionen.
    Desweiteren kannst du immer eine forward declaration machen, also schon mal mit class Spieler; anmelden, dass es die Klasse überhaupt gibt. Dann ist der Compiler auch zufrieden.



  • Nanyuki schrieb:

    Du musst deine Header mit Includeguards versehen, dann vermeidest du das Problem mit den doppelten Definitionen.
    Desweiteren kannst du immer eine forward declaration machen, also schon mal mit class Spieler; anmelden, dass es die Klasse überhaupt gibt. Dann ist der Compiler auch zufrieden.

    Danke! Der Includeguard war die Lösung 😉 Kannte ich bisher noch nicht...



  • Und bitte kein "using namespace std;" in Header-Dateien!


Anmelden zum Antworten