Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

Paulm

Frischling

  • »Paulm« ist der Autor dieses Themas

Beiträge: 69

Wohnort: Baden-Württemberg

Beruf: Schüler

  • Private Nachricht senden

1

07.02.2015, 11:32

C++ | SDL | Eigene Initialisierungsfunktion in Include-Datei liefert Fehler

Hallo,

Ich habe nach längerer Zeit wieder angefangen mit c++ und sdl zu programmieren und so passieren mir so manche einfache Fehler.
Ich habe mein Projekt mit VS 2013 Community aufgesetzt und solange ich meine SDL in der main.cpp Initialisiere funktioniert alles einwandfrei, sobald ich jedoch die Initialisierung in eine Funktion packe und diese in eine andere .cpp auslagere bekomme ich folgende Fehlermeldung beim Kompilieren: error LNK2005: "bool __cdecl init(struct SDL_Window *,struct SDL_Surface *)" (?init@@YA_NPAUSDL_Window@@PAUSDL_Surface@@@Z) already defined in Init.obj
Ich bin mir generell unsicher inwiefern ich SDL-Funktionen außerhalb der cpp-Datei verwenden kann in der die SDL initialisiert wurde. Damit meine ich ob es möglich ist die SDL in einer Funktion in einer Init.cpp zu initialisieren und diese Funktion in der main.cpp aufzurufen um dort ganz normal weitere SDL-Funktionen zu verwenden?

Hier mein Quellcode:

Main.cpp

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
#include "Init.cpp"

int main(int argc, char *argv[])
{
    SDL_Window *gWindow = NULL;
    SDL_Surface *gSurface = NULL;

    if (!init(gWindow, gSurface))
    {
        printf("Failed to initialize!\n");
    }
    else
    {
        //Update the surface
        SDL_UpdateWindowSurface(gWindow);

        //Wait two seconds
        SDL_Delay(2000);
    }

    SDL_DestroyWindow(gWindow);
    SDL_FreeSurface(gSurface);

    return 0;
}


Init.cpp

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
#include <SDL.h>
#include <stdio.h>

bool init(SDL_Window* gWindow, SDL_Surface* gScreenSurface)
{
    //Initialization flag
    bool success = true;

    //Initialize SDL
    if (SDL_Init(SDL_INIT_VIDEO) < 0)
    {
        printf("SDL could not initialize! SDL_Error: %s\n", SDL_GetError());
        success = false;
    }
    else
    {
        //Create window
        gWindow = SDL_CreateWindow("SDL Tutorial", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, 1280, 720, SDL_WINDOW_SHOWN);
        if (gWindow == NULL)
        {
            printf("Window could not be created! SDL_Error: %s\n", SDL_GetError());
            success = false;
        }
        else
        {
            //Get window surface
            gScreenSurface = SDL_GetWindowSurface(gWindow);
        }
    }

    return success;
}


Vielen Dank im voraus für Eure/Ihre Antworten und allen ein schönes Wochenende!
Paul

BlueCobold

Community-Fossil

Beiträge: 10 738

Beruf: Teamleiter Mobile Applikationen & Senior Software Engineer

  • Private Nachricht senden

2

07.02.2015, 12:05

Jede *.cpp Datei wird in eine *.obj Datei übersetzt. Alle *.obj Dateien werden dann zu einer *.exe gelinkt. Kommen jetzt dieselben Funktionen in mehreren *.obj vor, bekommst Du diesen Fehler. Da aber Init.cpp zu Init.obj wird und *alle* Inhalte von Init.cpp per Include auch in Main.cpp definiert sind und somit in Main.obj vorkommen, hast Du ein Problem. Schau Dir an wie man Header verwendet.
Teamleiter von Rickety Racquet (ehemals das "Foren-Projekt") und von Marble Theory

Willkommen auf SPPRO, auch dir wird man zu Unity oder zur Unreal-Engine raten, ganz bestimmt.[/Sarkasmus]

Architekt

Community-Fossil

Beiträge: 2 481

Wohnort: Hamburg

Beruf: Student

  • Private Nachricht senden

3

07.02.2015, 12:06

Leg eine Init.hpp an mit folgenden Inhalt:

C-/C++-Quelltext

1
2
3
4
struct SDL_Window;
struct SDL_Surface;

bool init(SDL_Window*, SDL_Surface*);


Und include die .hpp anstelle deiner .cpp in der main. Dafür sind solche Header Dateien da. Achte darauf, dass du natürlich trotzdem die Init.cpp mit kompilierst.
Der einfachste Weg eine Kopie zu entfernen ist sie zu löschen.
- Stephan Schmidt -

Paulm

Frischling

  • »Paulm« ist der Autor dieses Themas

Beiträge: 69

Wohnort: Baden-Württemberg

Beruf: Schüler

  • Private Nachricht senden

4

07.02.2015, 12:39

Leg eine Init.hpp an mit folgenden Inhalt:

C-/C++-Quelltext

1
2
3
4
struct SDL_Window;
struct SDL_Surface;

bool init(SDL_Window*, SDL_Surface*);


Und include die .hpp anstelle deiner .cpp in der main. Dafür sind solche Header Dateien da. Achte darauf, dass du natürlich trotzdem die Init.cpp mit kompilierst.


Danke für die Antworten :)
Ich habe es genau so versucht wie du es mir geraten hast (Ich habe auch vorher schon ein header file verwendet) aber es tritt die selbe Fehlermeldung auf:
Main.obj : error LNK2005: "bool __cdecl init(struct SDL_Window *,struct SDL_Surface *)" (?init@@YA_NPAUSDL_Window@@PAUSDL_Surface@@@Z) already defined in Init.obj
1>MSVCRTD.lib(cinitexe.obj) : warning LNK4098: defaultlib 'msvcrt.lib' conflicts with use of other libs; use /NODEFAULTLIB:library
1>C:\_Projects\V C++\SDL_Test\Debug\SDL_Test.exe : fatal error LNK1169: one or more multiply defined symbols found

Ich verstehe außerdem nicht wieso du die beiden structs deklarierst wenn ich SDL.h in der cpp-datei includet habe und diese in die .h include...

Architekt

Community-Fossil

Beiträge: 2 481

Wohnort: Hamburg

Beruf: Student

  • Private Nachricht senden

5

07.02.2015, 12:42

Das nennt sich forward declarations. Und ja, ich habe dir keine ganze Lösung gegeben, du hast immer noch ein Problem. Blue hat recht, beschäftige dich noch einmal etwas genauer mit Header Files, dann wird es dir sicherlich klar. ;) Ansonsten noch einmal fragen.
Der einfachste Weg eine Kopie zu entfernen ist sie zu löschen.
- Stephan Schmidt -

Paulm

Frischling

  • »Paulm« ist der Autor dieses Themas

Beiträge: 69

Wohnort: Baden-Württemberg

Beruf: Schüler

  • Private Nachricht senden

6

07.02.2015, 13:06

Das nennt sich forward declarations. Und ja, ich habe dir keine ganze Lösung gegeben, du hast immer noch ein Problem. Blue hat recht, beschäftige dich noch einmal etwas genauer mit Header Files, dann wird es dir sicherlich klar. ;) Ansonsten noch einmal fragen.

Danke es läuft jetzt
Es lag wohl ein Denkfehler meinerseits vor :D
Und jetzt bin ich erst richtig verwirrt, woher weis der compiler dass Init.h und Init.cpp zusammengehören? Also woher weis Init.h dass der eigentliche code von bool init() in Init.cpp steht?

BlueCobold

Community-Fossil

Beiträge: 10 738

Beruf: Teamleiter Mobile Applikationen & Senior Software Engineer

  • Private Nachricht senden

7

07.02.2015, 13:12

Das weiß er nicht. Wenn der Compiler die Main.cpp kompiliert und eine Funktion benutzt wird, die in einer anderen *.h (das sollte übrigens *.hpp heißen) deklariert ist, geht er davon aus, dass alles OK ist, denn ihn interessiert es nur, ob etwas deklariert wurde und nicht, ob es auch definiert wurde. Danach kompiliert er die Init.cpp. Der Linker fügt dann am Ende alles zusammen und findet in Main.obj die Verwendung einer Funktion, die er nicht in Main.obj finden kann. Aber er findet sie in Init.obj und geht daher davon aus, dass das wohl die richtige sein muss. Findet er in Init.obj keine oder er findet sie sowohl in Main.obj als auch in Init.obj, gibt's einen Fehler.
Teamleiter von Rickety Racquet (ehemals das "Foren-Projekt") und von Marble Theory

Willkommen auf SPPRO, auch dir wird man zu Unity oder zur Unreal-Engine raten, ganz bestimmt.[/Sarkasmus]

Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von »BlueCobold« (07.02.2015, 13:17)


Paulm

Frischling

  • »Paulm« ist der Autor dieses Themas

Beiträge: 69

Wohnort: Baden-Württemberg

Beruf: Schüler

  • Private Nachricht senden

8

07.02.2015, 13:20

Ok vielen Dank für die Hilfe :)

Werbeanzeige