Terve.
Päätin aloittaa tälle uuden aiheen, kun eivät liity keskenään toisiinsa.
Eli tarkoitus on siis tehdä hedelmäpeli (Tuommoinen kuin kaupoissa näkee).
Ihan ensimmäinen kysymys: Kun aloitan uuden projektin, niin mikä sen näistä pitää olla: Windows Application, Static Library, Tyhjä projekti vai DLL?
2. Miten voin lisätä peliin gif kuvia, jotka ovat tietenkin erillisenä tiedostossa? Kaipa sekin on mahdollista, ettei tarvitse "piirtää" koodaamalla.
Yst. terv.
MIB
Pari kysymystä alkuun. Riittäkö satunnainen kolmen kuvan arpominen, vai pitääkö olla yksi yhteen kaupan version kanssa? Eli siis yksi pitkä kuva, jota kierretään satunnainen määrä. Mikäli ensimmäinen vaihtoehto riittää, niin ratkaisu on helpompi, muttei silmälle ihan yhtä realistinen.
Ensimmäinen vaihtoehto riittää. Jos minulla on jokaisessa ruletissa 7 vaihtoehtoa (vai montakohan niitä on, en ole koskaan pelannut), ja on piirrettynä yhtä monta kuvaa (esim. sitruuna.gif, mandariini.gif...). Sitten muuttujaan ruletti1 lisättäisiin rand(1, max kierrosten määrä). Sitten käydään for silmukassa ruletti1 arvon verran läpi, ja tulostetaan joka kerralla kuva korvaten edellinen, jolloin nämä näyttävät vaihtuvan. Eikös tämä ole mahdollista?
Kun jokainen ruletti (olkoon nyt ruletti, en tiedä oikeaa nimitystä) on käyty läpi, niin asetetaan jokaisen kuvan nimi muuttujaan. Sitten verrataan:
if(ruletti1 == ruletti2) { kaksi oikein } if(ruletti2 == ruletti3) { kaksi oikein } if(ruletti1 == ruletti2 && ruletti2 == ruletti3) { kolme oikein }
Jos on kaksi oikein, kasvatetaan rahoja tietyllä määrällä. Jos kaikki ovat oikein, kasvatetaan myös.
Näin ajateltuna tämä on mielestäni helppo toteuttaa.
Pelin tulosten tallentaminen:
Jos tulokset tallentaa tavalliseen tekstitiedostoon selkokielisenä tekstinä, niin sehän on hyvin muuteltavissa, joten nämä täytyy cryptata ja luku vaiheessa suomentaa teksti.
PHP:n grafiikka -osion koodivinkeissä on "Päänvaivaa spämmiroboteille" (tms.) jossa on mielestäni hyvä idea jolla tämänkin voisi toteuttaa.
Eikö kukaan tiedä vastauksia? Luulisin, että kyllä kaikki osaavat ovat tehneet jotain vastaavaa.
MIB kirjoitti:
Eikö kukaan tiedä vastauksia? Luulisin, että kyllä kaikki osaavat ovat tehneet jotain vastaavaa.
Ei tuolla hirveän montaa sellaista kysymystä ole, johon pystyisi antamaan järkevän vastauksen. Mutta vastaan nyt kuitenkin kaikkiin kysymyksiisi:
MIB kirjoitti:
Ihan ensimmäinen kysymys: Kun aloitan uuden projektin, niin mikä sen näistä pitää olla: Windows Application, Static Library, Tyhjä projekti vai DLL?
Jos tarkoituksesi on tehdä windows-sovellus, niin "Windows Application".
MIB kirjoitti:
2. Miten voin lisätä peliin gif kuvia, jotka ovat tietenkin erillisenä tiedostossa? Kaipa sekin on mahdollista, ettei tarvitse "piirtää" koodaamalla.
On se mahdollista. Tapa miten se toteutetaan riippuu
a) Mitä ohjelmointikieltä käytät (C, C++, Delphi(object Pascal) vai Pascal) sekä
b) jos käytät grafiikkaan kehitysympäristöön sisältyviä kirjastoja siitä mitä kehitysympäristöä käytät tai
c) mitä ulkoisia kirjastoja käytät, jos käytät niitä grafiikkaan
MIB kirjoitti:
Eikös tämä ole mahdollista?
Kyllä on.
Vaikuttaa siltä, että olet hedelmäpelisi ja sen toteuttamiseen tarvittavien tekniikoiden opettelun kanssa vielä aika alkutekijöissä. Suosittelisin ottamaan ensimmäiseksi tavoitteeksi vaikkapa sen, että saat ylipäätänsä piirrettyä kuvan näytölle. Olettaen, että haluat koodata C:llä tai C++:lla, kannattanee lähteä liikkeelle SDL:n opettelusta. Kieliin liittyviä ongelmia voit sitten yrittää ratkaista vaikka näiden avulla:
https://www.ohjelmointiputka.net/oppaat/opas.
https://www.ohjelmointiputka.net/oppaat/opas.
http://www.cplusplus.com/reference/
Vinkkinä projektin mahdollisia myöhempiä vaiheita varten, että GIF on aika kinkkinen formaatti ja helpoimmalla pääset varmaankin tallentamalla kaikki animaatiosi kuvat erillisinä kuvatiedostoina. Myös tiedostojen kryptaamisia kannattaa miettiä myöhemmin. Lopputuloshan on joka tapauksessa vain hieman "päänvaivaa" jollekin, joka ne haluaisi murtaa - ei siis mikään todellinen este.
Grez kirjoitti:
MIB kirjoitti:
Ihan ensimmäinen kysymys: Kun aloitan uuden projektin, niin mikä sen näistä pitää olla: Windows Application, Static Library, Tyhjä projekti vai DLL?
Jos tarkoituksesi on tehdä windows-sovellus, niin "Windows Application".
Selvä, kiitos.
Kun loin uuden projektin, siellä oli valmiina tallentamaton main.cpp tiedosto jossa luki:
#include <windows.h> /* Declare Windows procedure */ LRESULT CALLBACK WindowProcedure (HWND, UINT, WPARAM, LPARAM); /* Make the class name into a global variable */ char szClassName[ ] = "WindowsApp"; int WINAPI WinMain (HINSTANCE hThisInstance, HINSTANCE hPrevInstance, LPSTR lpszArgument, int nFunsterStil) { HWND hwnd; /* This is the handle for our window */ MSG messages; /* Here messages to the application are saved */ WNDCLASSEX wincl; /* Data structure for the windowclass */ /* The Window structure */ wincl.hInstance = hThisInstance; wincl.lpszClassName = szClassName; wincl.lpfnWndProc = WindowProcedure; /* This function is called by windows */ wincl.style = CS_DBLCLKS; /* Catch double-clicks */ wincl.cbSize = sizeof (WNDCLASSEX); /* Use default icon and mouse-pointer */ wincl.hIcon = LoadIcon (NULL, IDI_APPLICATION); wincl.hIconSm = LoadIcon (NULL, IDI_APPLICATION); wincl.hCursor = LoadCursor (NULL, IDC_ARROW); wincl.lpszMenuName = NULL; /* No menu */ wincl.cbClsExtra = 0; /* No extra bytes after the window class */ wincl.cbWndExtra = 0; /* structure or the window instance */ /* Use Windows's default color as the background of the window */ wincl.hbrBackground = (HBRUSH) COLOR_BACKGROUND; /* Register the window class, and if it fails quit the program */ if (!RegisterClassEx (&wincl)) return 0; /* The class is registered, let's create the program*/ hwnd = CreateWindowEx ( 0, /* Extended possibilites for variation */ szClassName, /* Classname */ "Windows App", /* Title Text */ WS_OVERLAPPEDWINDOW, /* default window */ CW_USEDEFAULT, /* Windows decides the position */ CW_USEDEFAULT, /* where the window ends up on the screen */ 544, /* The programs width */ 375, /* and height in pixels */ HWND_DESKTOP, /* The window is a child-window to desktop */ NULL, /* No menu */ hThisInstance, /* Program Instance handler */ NULL /* No Window Creation data */ ); /* Make the window visible on the screen */ ShowWindow (hwnd, nFunsterStil); /* Run the message loop. It will run until GetMessage() returns 0 */ while (GetMessage (&messages, NULL, 0, 0)) { /* Translate virtual-key messages into character messages */ TranslateMessage(&messages); /* Send message to WindowProcedure */ DispatchMessage(&messages); } /* The program return-value is 0 - The value that PostQuitMessage() gave */ return messages.wParam; } /* This function is called by the Windows function DispatchMessage() */ LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { switch (message) /* handle the messages */ { case WM_DESTROY: PostQuitMessage (0); /* send a WM_QUIT to the message queue */ break; default: /* for messages that we don't deal with */ return DefWindowProc (hwnd, message, wParam, lParam); } return 0; }
Onko tällä jotain tekemistä sen kanssa, että toimiiko ohjelma vai ei? Voiko tämän poistaa, ja korvata omilla tiedostoilla?
Toimiihan Windows Applicationeissa samat komennot kuin komentorivi ohjelmissa?
Grez kirjoitti:
MIB kirjoitti:
2. Miten voin lisätä peliin gif kuvia, jotka ovat tietenkin erillisenä tiedostossa? Kaipa sekin on mahdollista, ettei tarvitse "piirtää" koodaamalla.
On se mahdollista. Tapa miten se toteutetaan riippuu
a) Mitä ohjelmointikieltä käytät (C, C++, Delphi(object Pascal) vai Pascal) sekä
b) jos käytät grafiikkaan kehitysympäristöön sisältyviä kirjastoja siitä mitä kehitysympäristöä käytät tai
c) mitä ulkoisia kirjastoja käytät, jos käytät niitä grafiikkaan
a) Käytän C++, enkö maininnut sitä vielä?
b & c) En käytä mitään noita, ainakaan vielä. Millaisella käskyllä saisin kuvia tiettyihin kohtiin?
*************************************************** * otsikko otsikko otsikko otsikko otsikko otsikko * *************************************************** * * * logo logo logo logo logo logo logo logo logo * * * *************************************************** * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * * itse peli itse peli itse peli itse peli itse... * ***************************************************
Pitäisi saada tohon logo kohtaan kuva. Miten?
Ehotan, että teet komentorivi-projektin ja käytät sdl kirjastoa apuna. Itse ainakin tykkään paljon enemmän häärätä sdl:n kanssa mitä winapin kanssa...
jos käytät putkan opasta https://www.ohjelmointiputka.net/oppaat/opas.
Ei ei! Tarkoitus olisi tehdä joka tapauksessa tuollainen Windows Application ohjelma. Kun on mahdollista piirtää kuva paintilla, ja liittää se ohjelmaan, niin miksi alkaa tekemään kaikkea kummallista koodaamalla?
_______________
Koitin miten arpoisin numeron väliltä 1 - 7. C++:ssa on tuo rand(), mutta jos laitan int muuttuja = rand() % 7, niin vastaus on aina 6. PHP:ssä on kätevä, kun laittaa rand(1, 7) niin toimii.
Edit.
#include <iostream> using namespace std; int main() { int ruletti1 = rand() % 7; int ruletti2 = rand() % 7; int ruletti3 = rand() % 7; cout << ruletti1 << "\n"; cout << ruletti2 << "\n"; cout << ruletti3 << "\n"; system("PAUSE > NUL"); }
Tulostaa
6
1
6 joka kerta. Miten siis saan sen arpomaan luvut kuin PHP:n rand?
__________________
Voisiko joku antaa C++:lle esimerkin, miten saan tehtyä Windows Applicationin jossa ikkunan otsikko on Hedelmäpeli ja siellä lukee jotain? En saa tuosta mitään selvää, mitä lukee Dev-C++:n esimerkissä... :/
Tolla pitäis tulla satunnaisesti...
#include <ctime> #include <iostream> int main() { srand(time(NULL)); short int ruletti = rand() % 7; std::cin.get(); return 0; }
Edit: Miten sää muka saat tolla winapilla helpommin kuvia ohjelmaa, kuin sdl?
sdl:
...koodia SDL_Surface* kuva = SDL_LoadBMP("kuva.bmp"); ...koodia
Tuo lataa siis bmp kuvan. Enemmän aiheesta oppaassa, jonka linkkasin aikaisemmin.
MIB kirjoitti:
Ei ei! Tarkoitus olisi tehdä joka tapauksessa tuollainen Windows Application ohjelma.
Miksi?
MIB kirjoitti:
Kun on mahdollista piirtää kuva paintilla, ja liittää se ohjelmaan, niin miksi alkaa tekemään kaikkea kummallista koodaamalla?
Mistä sait päähäsi, että kuvia on mahdollista vain jotenkin maagisesti "liittää" ohjelmaan ilman koodausta?
Kuten aiemmin sanoin, kannattaa käyttää SDL:llää. VS-projektin tyypiksi pitää tällöin valita "Console application", kuten vehkis91 sanoi.
MIB kirjoitti:
Tulostaa
6
1
6 joka kerta. Miten siis saan sen arpomaan luvut kuin PHP:n rand?
Yrititkö edes etsiä vastausta ennen kuin kysyit?
https://www.ohjelmointiputka.net/oppaat/opas.
http://www.cplusplus.com/reference/clibrary/
http://letmegooglethatforyou.com/?q=c rand same&l=1
MIB kirjoitti:
__________________
Voisiko joku antaa C++:lle esimerkin, miten saan tehtyä Windows Applicationin jossa ikkunan otsikko on Hedelmäpeli ja siellä lukee jotain? En saa tuosta mitään selvää, mitä lukee Dev-C++:n esimerkissä... :/
http://www.winprog.org/tutorial/
Sieltä vain opettelemaan... (kannattaa tosiaan mieluummin käyttää SDL:llää, tai jotakin muuta kirjastoa, kuten vaikka wxWidgets)
En tarkoittanut, että sen kuvan voi liittää maagisesti, vaan tarkoitin että en mielellään ala "piirtämään" kuvia koodilla kun voi koodilla liittää valmiin kuvan.
NO siis, annappa esimerkki siitä mitä oikein tarkoitat?
On kuva kuva.bmp, ja tiedosto main.cpp. Koodilla sisällytän sen kuvan ohjelmaan.
__________
Latasin SDL:n uusimman paketin täältä, mutta miten tuo asennetaan? :/
Yritäs nyt. Lue ensin ohje, kysy vasta sitten.
SDL:n käyttö vaatii jonkinasteista C-osaamista, joten kannattaa katsoa, että ainakin Ohjelmointiputkan C-oppaan asiat ovat suurin piirtein hallinnassa. C ja C++ eivät tosiaan ole mitään helpoimpia mahdollisia kielivalintoja yksinkertaiseen peliohjelmointiin.
Haluatko tehdä hedelmäpelin C++:lla vai hedelmäpelin Windowsille?
Jos haluat tehdä hedelmäpelin Windowsille, helpompi kieli olisi esim. VB.NET. Siinä kuvan arpomiseen ja näyttämiseen riittää muutaman rivin koodi.
Kumpaakin perjaatteessa. Pääasiassa Windowsilla sitä pelattaisiin, mutta kielenä toimii C++. En alkaisi millään opettelemaan toista kieltä, kun tämäkin on vielä kesken...
Edit. Tein nytten kokeilun vuoksi komentoriviohjelmana tämän:
#include <iostream> #include <ctime> using namespace std; int main() { //Alustetaan muuttujat int ruletti1; int ruletti2; int ruletti3; int rahat = 1000; int panos = 10; //Kysytään, että pelataanko cout << "Pelataanko hedelm\x84peli\x84? (k / e)\n"; char vastaus; cin >> vastaus; //Jos kyllä while(vastaus == 'k') { main: system("CLS"); cout << "Sinulla on " << rahat << " euroa, ja panos on " << panos << " euroa.\n\n"; arvo: srand(time(NULL)); ruletti1 = rand() % 7; ruletti2 = rand() % 7; ruletti3 = rand() % 7; cout << "Ruletti1: " << ruletti1 << "\n"; cout << "Ruletti2: " << ruletti2 << "\n"; cout << "Ruletti2: " << ruletti3 << "\n\n"; tarkista: rahat = rahat - panos; if(ruletti1 == ruletti2 && ruletti3 == ruletti2) { //Kolme oikein rahat = rahat + panos * 3; goto seuraava; } else if(ruletti1 == ruletti2) { //Kaiksi oikein rahat = rahat + panos * 2; goto seuraava; } else if(ruletti2 == ruletti3) { //Kaksi oikein rahat = rahat + panos * 2; goto seuraava; } else rahat = rahat; seuraava: if(ruletti1 == ruletti2 && ruletti3 == ruletti2) { cout << "Kolme oikein! Sait rahaa " << panos * 3 << " euroa! Sinulla on rahaa " << rahat << " euroa\n"; cout << "Pelaa uudestaan painamalla nappulaa"; system("PAUSE > NUL"); } else if(ruletti1 == ruletti2) { cout << "Kaksi oikein! Sait rahaa " << panos * 2 << " euroa! Sinulla on rahaa " << rahat << " euroa\n"; cout << "Pelaa uudestaan painamalla nappulaa"; system("PAUSE > NUL"); } else if(ruletti2 == ruletti3) { cout << "Kaksi oikein! Sait rahaa " << panos * 2 << " euroa! Sinulla on rahaa " << rahat << " euroa\n"; cout << "Pelaa uudestaan painamalla nappulaa"; system("PAUSE > NUL"); } else { cout << "Ei voittoa!\n"; system("PAUSE > NUL"); } cout << "\n\nNostetaanko panosta, vastaa p. Jatketaanko, vastaa v: "; char v; cin >> v; if(v == 'p') { system("CLS"); cout << "Kuinka paljon nostetaan panosta?\n"; int nosta; cin >> nosta; if(panos + nosta > rahat) goto error; panos = panos + nosta; goto main; system("PAUSE > NUL"); } else { goto main; } error: //Sammutetaan ohjelma return 0; if(rahat < panos) { system("CLS"); //Palautetaan takaisin oikeat arvot panos = 10; rahat = 1000; cout << "Rahasi loppuivat!\n\n"; cout << "Uudelleen? (k / e)\n"; char uudelleen; cin >> uudelleen; while(uudelleen == 'k') goto main; while(uudelleen != 'k') return 0; system("PAUSE > NUL"); } } if(vastaus != 'k') { return 0; } }
Ei millää pahalla, mutta hirveen näköistä koodia... ÄLÄ KÄYTÄ GOTOa!!!!!!!!!!!!!!
Voisitko kertoa, että mitä tuossa olisi muutettavaa - goton lisäksi?
Ei voi kuin nauraa kun lukee tätä keskustelua =) Ei millään pahalla, mutta lue nyt vain tuo ohjelmointiputkan C++ opas tai etsippä vaikka googlen avulla jokin hyvä python opas. Myös kirjastossa on monia hyviä ohjelmointikirjoja.
Asentelin tota SDL:ää, ja tuli Dev-C++ Package Manager (version 2.2.6) ohjelma. Siinä on lista joistain asioista, ovatko ne jo asennettu? En ole varma, kun jokaisessa paketissa lukee remove ja install... Tai, oikeastaan uskoisin olevan asennettu, kun install nappulaa painaa, niin pitäisi hakea tiedosto.
Eli, nyt kun käynnistän Dev-C++:n uudelleen, niin SDL:n pitäisi toimia?
MIB kirjoitti:
Eli, nyt kun käynnistän Dev-C++:n uudelleen, niin SDL:n pitäisi toimia?
Uutta projektia luodessa pitäisi löytyä jokin "SDL Multimedia Application" tms. Valitse se. (Jos ei löydy, asennus ei ole onnistunut.)
Nähtävästi ei onnistunut... :(
Mene exceliin ja paina alt + f11. Siitä aukeaa visual basic for applications IDE. VBA:lla on älyttömän helppo toteuttaa pikkuohjelmia :). (vaikka vihaan sen syntaksia).
Annatko esimerkin, että kuinka helppo sillä on toteuttaa ohjelma joka aukeaa erillisessä ikkunassa ja tulostaa tekstin "moi"? (Eli ei komentoriviohjelmaa)
Ohjelman voi luoda näin:
1. Valitse Insert->UserForm, joka luo ohjelman ikkunan.
2. Lisää ikkunaan kohta tekstille (Label).
3. Kirjoita äskeiseen kohtaan haluttu teksti.
4. Paina F5, jolloin ohjelma käynnistyy.
Käytännössä ohjelmointitila näyttää tältä:
Ei vaikuta vaikealta, mutta uuden kielen opettelu ei ole minusta hyvä asia kun tätäkään en osaa vielä kovin hyvin, eli pysyttelen tässä C++:ssa.
Mod. poisti koodin, joka on jo aiemmassa viestissä.
Miten saan tämän myös tulostamaan jotain? Jos lisään loppuun esim int main() { cout... } niin antaa errorin.
MIB kirjoitti:
Ei vaikuta vaikealta, mutta uuden kielen opettelu ei ole minusta hyvä asia kun tätäkään en osaa vielä kovin hyvin, eli pysyttelen tässä C++:ssa.
Päätös on tietysti sinun, mutta VB:llä koko hedelmäpelin koodi vie puolet vähemmän tilaa kuin tuo ikkunan näyttävä C++-ohjelma.
MIB kirjoitti:
Miten saan tämän myös tulostamaan jotain?
Laita lopussa olevan switch-rakenteen alkuun tämä:
case WM_PAINT: TextOut(GetDC(hwnd), 10, 10, "Moi!", 4); break;
Tässä 10, 10 tarkoittaa tulostuskohtaa ja 4 tarkoittaa tekstin pituutta.
WinAPI-ohjelmointi on aika mutkikasta, eikä sillä tehtyjä ohjelmia voi kääntää kuin Windowsille. En usko, että täällä moni jaksaa siinä auttaa, varsinkaan, kun oma kykysi opetella ja etsiä tietoja itse tuntuu olevan erittäin rajallinen ja tavoitteesi taas hyvin paljon sitä korkeammalla.
Poista Dev-C++ ja asenna Code::Blocks ja siihen SDL, niin pääset alkuun Ohjelmointiputkassa olevien SDL:ää käsittelevien oppaiden ja koodivinkkien avulla. Ilmeisesti haluat kuitenkin ohjelmoida pelejä, ja siihen SDL on huomattavasti yksinkertaisempi väline kuin WinAPI.
no niin vihdoin pääsin koneelle..
Jätä se winapi suosiolla pois, itsekkin sitä joskus kokeilin ja pelkkä viivan piirtäminen ikkunaan tuotti vaikeuksia.
Siinä vba:ssa koodi toimii aika samalla tavalla kuin c++:ssa mutta aaltosulkujen {} sijasta esim if lause toimii näin:
if ehto then
...
end if
ja vba:ssa saat ikkunan luotua ilman koodia painamalla insert->userform kuten ylempänä lukee. Muutenkin siinä säästyt paljolta vaivalta kun voit laittaa objekteja userformille graafisesti.
Luulisin, että nyt kun tiedän miten tulostetaan tekstiä, niin pääsen vähän eteenpäin. Muuten, miten saan tuon tekstin taustaväriä vaihdettua? Se on nyt valkoinen, ja pitäisi saada sopimaan se tuohon harmaaseen.
Miten muuten saan tulostettua muuttujan?
string muuttuja = "Joo jee"; TextOut(GetDC(hwnd), 10, 10, muuttuja, 4);
Tämä ei toimi, valittaa tuosta TextOut rivistä.
Luitko Antin viestiä, jossa 4 oli tekstin pituus? Tuossa sinun tekstisi pituus on selvästi yli 4 merkkiä eikös vaan?
Teuro kirjoitti:
Luitko Antin viestiä, jossa 4 oli tekstin pituus? Tuossa sinun tekstisi pituus on selvästi yli 4 merkkiä eikös vaan?
Ohhops, luin aivan päin puuta tuon mitä Antti kirjoitti. Katsoin, että "4 tarkoittaa tekstin paksuutta". Höh!
Edit. Se herjaa silti:
C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp In function `LRESULT WindowProcedure(HWND__*, UINT, WPARAM, LPARAM)': 85 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp cannot convert `std::string' to `const CHAR*' for argument `4' to `BOOL TextOutA(HDC__*, int, int, const CHAR*, int)' 87 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp jump to case label 84 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp crosses initialization of `std::string muuttuja' 87 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp [Warning] destructor needed for `muuttuja' 87 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp [Warning] where case label appears here 87 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp [Warning] (enclose actions of previous case statements requiring destructors in their own scope.) 90 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp [Warning] destructor needed for `muuttuja' 90 C:\Documents and Settings\xxxx\Työpöytä\hedelmäpeli projektitiedostot\main.cpp [Warning] where case label appears here
Yrität sijoittaa std::string muuttujaa const *char muuttujaan, jolloin kääntäjä huomauttaa asiasta. Voit siis muuttaa tuon (toki oikein tehdyn) muuttujan c tyyliseksi merkkitaulukoksi metodilla c_str(). Metodin käytön opettelun jätän sinulle. Korjaa tuo ensin katsotaan onko sen jälkeen virheitä jäljellä. Muuttujien nimeäminen nimellä muuttuja on yleensä huonoa idea.
Näin päästä heitettynä:
#include <string> //...koodia.... std::string muuttuja = "Joo jee"; TextOut(GetDC(hwnd), 10, 10, muuttuja.c_str(), muuttuja.length()); //...koodia...
Ei toimi yhtään sen paremmin, nyt se herjaa seuraavaa asiaa jo. Taidampas katsoa, että jos jatkaisin sillä Visual Basicillä, kun se näyttää olevan helpohko kieli tähän. Onko tässä kuitenkin vastaava syntaxi kuin C++:ssa vai onko tämä ihan eri kokonaan? C++ minun olisi helpompi oppia, kun PHP:ssä on suhtkoht samanlainen syntaxi. No, lataan täältä Visual Basic 2008 express editionin, niin sillä pystyn siis tekemään tuon minkä Antti mainitsi?
VB::ssä on ihan erinlainen syntaxi, mitä c++ tai php:ssä. Me ollaan jo sanottu, että älä käytä Winapia, mutta et näytä kuuntelevan!!! Lataa Code::blocks, joka on paljon parempi IDE, mitä DEV-cpp. Ja asenna siihen SDL.
Jos olet katsonut sdl-opasta, huomaat, että sdl on varmaan 100x helpompi, mitä winapi!
Ja kerro se seuraava virheilmoitus.
Mun mielestä vähän hassu ehdotus muutenkin tuo VB.Net kun kuitenkin myös C# ja managed C++ on tarjolla. Eli ne voisi olla varteenotettavia vaihtoehtoja, jos ei halua vaihtaa niin paljon syntaksia, mutta haluaisi silti käyttää .Net frameworkin tarjoamia mahdollisuuksia. Toki SDL on monessa mielessä parempikin vaihtoehto.
VB.netin ainoa etu C#:aan verrattuna on sen VB:hen tottuneelle tutumpi syntaksi, ja päinvastoin.
Voit kokeilla myös C#-kieltä. Se on muuten melkein kuin VB.Net ("VB2008"), mutta syntaksi muistuttaa C++:aa, PHP:tä ja Javaa. Siitäkin on saatavilla MS:n Express Edition.
Setting up Code::Blocks to work with SDL kirjoitti:
Now go to File>New>Project and select Console application (Don't worry, we are doing graphics, this is just a generic thing)
Call the project "New SDL Project" (you'll see why we give it such a generic name later on)
Miten kutsun tuota SDL Projektia?
Kutsu projektia nimellä "New SDL Project". Siis anna projektille tämä nimi.
Kiitos, yleensä kun puhutaan kutsumisesta (call), niin tarkoitetaan mielestäni vähän muuta: kutsu esimerkiksi funktiota die(). :D
Setting up Code::Blocks to work with SDL kirjoitti:
Now go to Project>Build Options and make sure that New SDL Project is selected in the tree menu on the left, this is so that it is set for both Debug and Release compile options.
Missä päin? Tuossa on vaan listaa erillaisista prosessoreista. :o
Jos nyt välttämättä haluaa käyttää Winapia, niin kyllä tuollaisen sillä tekee helpostikin. Muista ideistä en tiedä, mutta Visual C++ Express Editionilla onnistuu kun luot windows applikaation ja siihen formin. Formiin voit vain maagisesti liittää kolme kuvakenttää ja voila: sinulla on siellä hedelmäpelin kuvat ilman koodausta! Sitten lisäät tekstikentän, joka näyttää rahamäärää ja napin jolla pelataan. Kaikki on tähän mennessä vain drag n' drop.
Lopuksi ainoa koodiosuus. Eli teet actionin pelinapille. Actionissa vähenettään rahaa jos sitä on ja arvotaan kaikki kolme hedelmää. Arvonnan tuloksen perusteella valitaan kuvat, jotka sijoitetaan edellä piirrettyihin kuvakenttiin. Saman tuloksen perusteella katsotaan menetettiinkö vai tienattiinko rahaa ja päivitetään rahakenttä sen mukaan. Jos rahat meni, niin game over (esim kolme pääkalloa hedelmiksi ;)).
Tässä siis ei ole mitään lukitsemisia tai muutakaan hienouksia ja koodaamisen määrä on minimaalista. Kun pääset tähän vaiheeseen, niin voit kokeilla lisätä esim. lukitsemisnapit hedelmien alle ja suorittaa arvonnan vaikka siten että kuvia pyöritetään samassa järjestyksessä koko ajan, jolloin ne vaihtuvat ruudulla jatkuvasti ja arpakone päättää milloin kukin rulla pysähtyy.
On niin monta tapaa tässä esitelty, että menee pää pyörälle. Osa sanoo, että Winapin tekeminen on vaikeaa, ja jotkut sanoo että helppoa.
Käsitin tässä selityksenne väärin kun lueskelin. Ymmärsin aluksi, että Winapi olisi ainoa ( :( ) tapa toteuttaa erillinen ikkuna Windowsilla ja SDL:llä tehtäisiin vain hienoudet kuten kuvat ja äänet. Nyt kuitenkin tajusin, että SDL:llä pystyy piirtämään sen ikkunan, ja siihen tekstin.
vehkis91 kirjoitti:
Jos olet katsonut sdl-opasta, huomaat, että sdl on varmaan 100x helpompi, mitä winapi!
Jos näin on, niin näytätkö miten helppoa on tulostaa se perinteinen "Moi!" teksti näytölle, niin voisin verrata kuinka paljon on 100x helpompi toteutus.
Torgo: WinAPI-ohjelmointi tarkoittaa minusta, että komponentteja nimenomaan ei tehdä millään graafisella työkalulla vaan tuohon tapaan, kuin MIBin lähettämässä projektipohjassa on tehty. Mutta kuvaamasi tapa kyllä taitaisi olla tälle herralle paremmin soveltuva menetelmä. Itse suosittelisin siinä tapauksessa ennemmin C#-kieltä.
Helppous on suhteellista, eikä kaikki ole helppoa samalla välineellä. Esimerkiksi tekstin piirto SDL:ssä täytyy tehdä enemmän tai vähemmän kuvien kautta, joten Moi-tekstin näyttäminen vaatii suunnilleen yhtä paljon työtä kuin hedelmäpelin rullan pyörittäminen.
Metabolix kirjoitti:
Helppous on suhteellista, eikä kaikki ole helppoa samalla välineellä. Esimerkiksi tekstin piirto SDL:ssä täytyy tehdä enemmän tai vähemmän kuvien kautta, joten Moi-tekstin näyttäminen vaatii suunnilleen yhtä paljon työtä kuin hedelmäpelin rullan pyörittäminen.
No, mutta voihan SDL:ää ja "normaalia" C++ "sekoittaa", että
#include <iostream> using namespace std; int main() { //sdlää //sdlää cout << "Moi!"; //sdlää... }
Vai voiko?
Jos haluaa päästä helpommin eteenpäin voisi suositella vaikkapa allegroa, jolla onnistuu kohtuullisen helposti tuokin peli. Tekstin ja kuvien piirto on melko suoraviivaista koodausta.
#include <allegro.h> int main(){ /* Tähän allegon alustukset */ allegro_init(); /* näytölle, fontilla, itse teksti, x, y, väri, taustaväri */ textout_ex(screen, font, "Moi!", 10, 10, 3, -1); /* Tähän allegron lopetus */ alegro_exit(); } END_OF_MAIN();
Voi, mutta tuo tulostaa tekstin edelleenkin siihen mustaan konsoliin, ei suinkaan SDL:n ikkunaan. Yritä ymmärtää, että konsolissa oleva teksti on vain kirjaimia, ja riippuu käyttöjärjestelmästä, miltä ne näyttävät, kun taas ikkunaan piirretty teksti on tietyllä fontilla piirrettyjä tietyn kokoisia kirjaimia, siis ihan oikeaa grafiikkaa.
Kieltämättä Teuron ehdottama Allegro on myös hyvä vaihtoehto – joissain suhteissa parempi kuin SDL, joissain huonompi. Siitä ei valitettavasti ole opasta Ohjelmointiputkassa.
SDL:llä esimerkiksi ikkunan ja kuvan saa näin helposti:
#include <SDL.h> int main(int argc, char **argv) { // Alustus SDL_Init(SDL_INIT_VIDEO); // Luodaan ikkuna, 640x480 pikseliä, 32-bittiset värit, kaksoispuskurointi. SDL_Surface *ruutu = SDL_SetVideoMode(640, 480, 32, SDL_DOUBLEBUF); // Ladataan kuva. SDL_Surface *kuva = SDL_LoadBMP("kuva.bmp"); // Kuvan piirtokohta on tietueessa (C++-opas: osa 4, tietueet). SDL_Rect kohta = {100, 30}; // Piirretään kuva (muistissa; ei näy vielä ruudulla). SDL_BlitSurface(kuva, 0, ruutu, &kohta); // Vapautetaan kuva; se on jo piirretty eikä sitä tarvita. SDL_FreeSurface(kuva); // Laitetaan piirretyt asiat ruudulle ("käännetään paperi"). SDL_Flip(ruutu); // "Ikuinen" silmukka, loppuu breakiin. while (1) { // Käsketään SDL:n tarkistaa viestit (näppäinten painallukset yms.). SDL_PumpEvents(); // Haetaan näppäimet (C++-opas: osa 4, taulukot, ja osa 7, osoittimet). const Uint8 * const napit = SDL_GetKeyState(0); // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) break; // Nukutaan 10 millisekuntia eli yksi sadasosa ennen uutta Esc-tarkistusta. SDL_Delay(10); } // Ohjelman lopussa suljetaan SDL-ikkuna. SDL_Quit(); }
Ohjelma sulkeutuu Esc-näppäimellä.
Aika helpon oloinen systeemi.
Metabolix kirjoitti:
SDL_Delay(10);
Eikö tälleinen rasita, kun kokoajan käydään sitä läpi? :o
Setting Up Code::Blocks To Work With SDL kirjoitti:
Now go to Project>Build Options and make sure that New SDL Project is selected in the tree menu on the left, this is so that it is set for both Debug and Release compile options.
Täh? Tarkoitetaanko nyt tätä konsoliprojektia? En ole löytänyt mistään... :S
Metabolix kirjoitti:
WinAPI-ohjelmointi tarkoittaa minusta, että komponentteja nimenomaan ei tehdä millään graafisella työkalulla vaan tuohon tapaan, kuin MIBin lähettämässä projektipohjassa on tehty.
No joo, niinhän se tietysti on. Toisaalta tuo Visual C++:n graafinen työkalu tuottaa winapia käyttävää koodia, joten siinä mielessä sen voisi mieltää samaan kategoriaankin.
MIB kirjoitti:
näytätkö miten helppoa on tulostaa se perinteinen "Moi!" teksti näytölle, niin voisin verrata kuinka paljon on 100x helpompi toteutus.
Käytännössä tapoja taitaa olla kolme. Vaikein tapa on toteuttaa omat kirjoitusrutiinit. Nopeiten pääset tavoitteeseesi tekemällä "Moi!" -kuvan ja lataamalla sen näytölle. Järkevin tapa mielestäni on ladata jokin valmis fonttikirjasto. Niitä löytyy sdl:n sivuilta ja sen käyttötapa on kirjastoriippuvainen. Yleensä kuitenkin niinkin helppoa kuin: alusta_fontti(fontti); kirjoita_teksti(x, y, "Moi!");
MIB kirjoitti:
No, mutta voihan SDL:ää ja "normaalia" C++ "sekoittaa"
Juu voi, mutta cout tulostaa standardivirtaan. Oletusarvoisesti se tulostaa konsoliin. Jotta saisit sen tulostumaan SDL:n pinnalle, olisi sinulla oltava kirjoitusrutiinit SDL:lle, sekä jotenkin saatava ohjattua standardivirta kyseisille rutiineille.
MIB kirjoitti:
Eikö tälleinen rasita, kun kokoajan käydään sitä läpi? :o
Nimenomaan siksi nukutaan, ettei tarvitsisi käydä läpi jatkuvasti vaan vain sata kertaa sekunnissa. Saa sen laittaa nukkumaan pidempäänkin.
Metabolix kirjoitti:
ettei tarvitsisi käydä läpi jatkuvasti vaan vain sata kertaa sekunnissa.
Heh :D Vain sata kertaa sekunnissa on minusta aika suuri käsite, mutta se on kyllä aika pakollinen tarkistaa tässä tilanteessa.
MIB kirjoitti:
Setting Up Code::Blocks To Work With SDL kirjoitti:
Now go to Project>Build Options and make sure that New SDL Project is selected in the tree menu on the left, this is so that it is set for both Debug and Release compile options.
Täh? Tarkoitetaanko nyt tätä konsoliprojektia? En ole löytänyt mistään... :S
MIB kirjoitti:
Setting Up Code::Blocks To Work With SDL kirjoitti:
Now go to Project>Build Options and make sure that New SDL Project is selected in the tree menu on the left, this is so that it is set for both Debug and Release compile options.
Täh? Tarkoitetaanko nyt tätä konsoliprojektia? En ole löytänyt mistään... :S
Siis ruudun vasemmassa reunassa pitäisi olla puurakenne, josta pitäisi valita se "New SDL Project" (kai nimesit sen niin?) eikä mitään niistä alemmista oksista.
Aaa, ymmärsin. Sain nyt sen SDL:n toimimaan, mutta sinun koodisi herjaa ja reilusti:
||=== New SDL Project, Debug ===| \New SDL Project\main.cpp|1|SDL.h: No such file or directory| \New SDL Project\main.cpp||In function `int main(int, char**)':| \New SDL Project\main.cpp|5|error: `SDL_INIT_VIDEO' was not declared in this scope| \New SDL Project\main.cpp|5|error: `SDL_Init' was not declared in this scope| \New SDL Project\main.cpp|8|error: `SDL_Surface' was not declared in this scope| \New SDL Project\main.cpp|8|error: `ruutu' was not declared in this scope| \New SDL Project\main.cpp|8|error: `SDL_DOUBLEBUF' was not declared in this scope| \New SDL Project\main.cpp|8|error: `SDL_SetVideoMode' was not declared in this scope| \New SDL Project\main.cpp|11|error: `kuva' was not declared in this scope| \New SDL Project\main.cpp|11|error: `SDL_LoadBMP' was not declared in this scope| \New SDL Project\main.cpp|14|error: `SDL_Rect' was not declared in this scope| \New SDL Project\main.cpp|14|error: expected `;' before "kohta"| \New SDL Project\main.cpp|17|error: `kohta' was not declared in this scope| \New SDL Project\main.cpp|17|error: `SDL_BlitSurface' was not declared in this scope| \New SDL Project\main.cpp|20|error: `SDL_FreeSurface' was not declared in this scope| \New SDL Project\main.cpp|23|error: `SDL_Flip' was not declared in this scope| \New SDL Project\main.cpp|28|error: `SDL_PumpEvents' was not declared in this scope| \New SDL Project\main.cpp|31|error: expected initializer before '*' token| \New SDL Project\main.cpp|34|error: `napit' was not declared in this scope| \New SDL Project\main.cpp|34|error: `SDLK_ESCAPE' was not declared in this scope| \New SDL Project\main.cpp|34|warning: unused variable 'napit'| \New SDL Project\main.cpp|34|warning: unused variable 'SDLK_ESCAPE'| \New SDL Project\main.cpp|37|error: `SDL_Delay' was not declared in this scope| \New SDL Project\main.cpp|28|warning: unused variable 'SDL_PumpEvents'| \New SDL Project\main.cpp|37|warning: unused variable 'SDL_Delay'| \New SDL Project\main.cpp|41|error: `SDL_Quit' was not declared in this scope| \New SDL Project\main.cpp|5|warning: unused variable 'SDL_INIT_VIDEO'| \New SDL Project\main.cpp|5|warning: unused variable 'SDL_Init'| \New SDL Project\main.cpp|8|warning: unused variable 'SDL_DOUBLEBUF'| \New SDL Project\main.cpp|8|warning: unused variable 'SDL_SetVideoMode'| \New SDL Project\main.cpp|11|warning: unused variable 'SDL_LoadBMP'| \New SDL Project\main.cpp|14|warning: unused variable 'SDL_Rect'| \New SDL Project\main.cpp|17|warning: unused variable 'kohta'| \New SDL Project\main.cpp|17|warning: unused variable 'SDL_BlitSurface'| \New SDL Project\main.cpp|20|warning: unused variable 'SDL_FreeSurface'| \New SDL Project\main.cpp|23|warning: unused variable 'SDL_Flip'| \New SDL Project\main.cpp|41|warning: unused variable 'SDL_Quit'| ||=== Build finished: 21 errors, 15 warnings ===|
Koitin tätä:
#include <SDL/SDL.h> const int SCREEN_WIDTH = 640; const int SCREEN_HEIGHT = 480; const int SCREEN_DEPTH = 32; int main(int argc, char *argv[]) { SDL_Surface *screen; Uint8 *p; int x = 10; //x coordinate of our pixel int y = 20; //y coordinate of our pixel /* Initialize SDL */ SDL_Init(SDL_INIT_VIDEO); /* Initialize the screen / window */ screen = SDL_SetVideoMode(SCREEN_WIDTH, SCREEN_HEIGHT, SCREEN_DEPTH, SDL_SWSURFACE); /* Make p point to the place we want to draw the pixel */ p = (Uint8 *)screen->pixels + y * screen->pitch + x * screen->format->BytesPerPixel; /* Draw the pixel! */ *p=0xff; /* update the screen (aka double buffering) */ SDL_Flip(screen); while(true); }
Ja toimii hienosti ;)
Sinulta puuttuu siis projektin asetuksista SDL:n include-polku. En jaksa neuvoa, miten se lisätään, joten pidä vain mielessä, että sinun pitää muuttaa kaikissa koodeissa <SDL.h>:n paikalle <SDL/SDL.h> eli lisätä alkuun SDL/. (Sama pätee muihinkin otsikoihin, mm. <SDL_opengl.h> => <SDL/SDL_opengl.h>.)
MIB kirjoitti:
Aaa, ymmärsin. Sain nyt sen SDL:n toimimaan, mutta sinun koodisi herjaa ja reilusti:
Johtuu tuosta ensimmäisestä virherivistä: SDL.h: No such file or directory. Muuta include-rivin osoitteeksi SDL/SDL.h.
Jeps, kiitos! Tuonhan pitäisi tulostaa se kuva? Ei näytä toimivan... :o
Onko sinulla sellainen kuva (kuva.bmp-niminen BMP-tiedosto) oikeassa paikassa, siis samassa hakemistossa kuin koodit? (Tiedän: ei ole.)
Metabolix kirjoitti:
Onko sinulla sellainen kuva (kuva.bmp-niminen BMP-tiedosto) oikeassa paikassa, siis samassa hakemistossa kuin koodit? (Tiedän: ei ole.)
Anteeksi, oli mennyt kansiot sekaisin :(
Edit. Nyt alan sitten lukemaan sitä SDL opasta :) Totta, tämä Code::Blocks on monta kertaa parempi ohjelma, kuin Dev-C++ =)
Edit. Jos luon uutta projektia, niin siinä ei ole suoraan SDL projektia, eli pitää tehdä "komentoriviohjelma" joka käynnistää sen SDL ikkunan, kuten tuossa aikaisemminkin.
Luitko ohjeet loppuun?
Ohjesivu kirjoitti:
OK, now that we know it works, go to File>Save project as user-template and choose a descriptive name for it. (This is why we called the project "New SDL Project")
Now, if you go to File>New>From user template you should see your project template. Select it, and you should have a duplicate of the project that we just created. From now on, you can select this whenever you want to create an SDL application! Nifty, huh? BUT: Don't forget to copy SDL.dll to your new project!
Käsittääkseni voisit myös lisätä SDL.dll:n tuohon malliprojektiin niin, että se tulisi uusiinkin projekteihin automaattisesti. Helpompaa on kuitenkin kopioida SDL.dll esimerkiksi hakemistoon C:\windows\system32, jolloin kaikki ohjelmat löytävät sen sieltä.
Joo, mun virhe. Katsoin tosta Projects kohdasta, kun siellä oli User templates myös, josta se oma löytyi.
:)
Äh! Nyt olisi muuten hyvä, mutta tuo komentorivi tulee kokoajan näkyviin. Miten saan pelkästään tuon SDL ikkunan käynnistymään?
Komentorivi tulee kehitysvaiheessa, ja sen kanssa ei kannata tapella: on aika kätevää tulostaa coutilla debug-viestejä ohjelmasta. Jos etsit ohjelman tiedostoselaimella ja käynnistät sieltä, komentorivi ei kai aukea? (Muista silloin laittaa kuvat ja ohjelma samaan hakemistoon; kehitysvaiheessa tiedostojen sijainnit menevät hieman eri tavalla kuin lopullisessa, levitettävässä versiossa.)
MIB kirjoitti:
Edit. Nyt alan sitten lukemaan sitä SDL opasta :) Totta, tämä Code::Blocks on monta kertaa parempi ohjelma, kuin Dev-C++ =)
Ohjelmointityökalujen valinta on aika pitkälti makuasia. Omat C-ohjelmointityökalu suosikkini Windows-alustalle:
Pelles C : http://www.christian-heffner.de/index.php?page=overview&lang=en
Ohjeet SDL:n käyttöön ylläolevalle: http://www.friedspace.com/cprogramming/sdlsetup.
OpenWatcom : http://www.openwatcom.org/index.php/Main_Page
jalski kirjoitti:
Omat C-ohjelmointityökalu suosikkini...
Harmi vain, että tässä onkin kyse C++:sta eikä C:stä. Pikaisen vilkaisun perusteella näyttäisi, että tuo Pelles C on vain C-ympäristö eikä siis juuri liity aiheeseen.
\C++\SDL\main.cpp||In function `int SDL_main(int, char**)':| \C++\SDL\main.cpp|14|error: cannot convert `const std::string' to `int' in initialization| \C++\SDL\main.cpp|23|error: invalid conversion from `int' to `const char*'| \C++\SDL\main.cpp|23|error: initializing argument 1 of `SDL_RWops* SDL_RWFromFile(const char*, const char*)'| ||=== Build finished: 3 errors, 0 warnings ===|
Tälläinen virheen antaa. Tältä näyttää rivit, joilla virhe tulee:
#include <SDL/SDL.h> #include <string> #include <ctime> #include <iostream> using namespace std; const string hedelmat[7] = {"sitruuna.gif", "omena.jpg", "mandariini.jpg", "kirsikka.jpg", "kiivi.jpg", "banaani.jpg", "appelsiini.jpg"}; int main(int argc, char **argv) { srand(time(NULL)); int i = rand() % 7; int ruletti1 = hedelmat[i]; // Alustus SDL_Init(SDL_INIT_VIDEO); // Luodaan ikkuna, 640x480 pikseliä, 32-bittiset värit, kaksoispuskurointi. SDL_Surface *ruutu = SDL_SetVideoMode(640, 480, 32, SDL_DOUBLEBUF); // Ladataan kuva. SDL_Surface *kuva = SDL_LoadBMP(ruletti1);
Toivon, ettei tuo ollut koko ajamasi koodi.
cannot convert `const std::string' to `int' in initialization
Yrität määrätä int-merkkisen ruletti1-muuttujan arvoksi string-merkkistä muuttujaa. Mikä tässä voisi olla vikana?
Myöhemmin annat SDL_LoadBMP-funktiolle int-muuttujan, vaikka se haluaa merkkijonon.
On mukavaa, että Ohjelmointiputka tarjoaa avuksesi läjän osaavia ja avuliaita ihmisiä, joilla on aikaa, mutta on hyvä oppia ajattelemaan myös itse. Kokeile ratkaista (vaikka sanakirja apunasi) kääntäjän suoltamia virheilmoituksia ensin itse ja sitten pähkäiltyäsi kirjoita viesti tänne.
No voi nyt... Jeps, anteeksi taas. Toi oli kyllä huolimattomuusvirhe ;(
Edit.
\C++\SDL\main.cpp|22|error: cannot convert `const std::string' to `const char*' for argument `1' to `SDL_RWops* SDL_RWFromFile(const char*, const char*)'|
SDL_Surface *kuva = SDL_LoadBMP(hedelmat[i]);
Onko tälle jotain järkevää selitystä?
Sen ruletti1:n pitää olla string, koska sijoitat siihen stringin. (Parempi olisi poistaa koko ruletti1 ja käyttää vain hedelmat[i]:tä.) Ja stringistä saa const char*:n metodilla teksti.c_str()
. (Kirjoita Googleen C++ string c_str, jos et parin minuutin kokeilemisella saa tuota kohdalleen.) Luokasta string ja C:n merkkijonoista eli char-taulukoista on kyllä kerrottu C++-oppaassa, joten takaisin sinne vain.
Et nähtävästi ehtinyt huomata, että tein juuri tuon muunnoksen.
Kyllä tuo ohjeeni silti pätee aivan kokonaan. OP:n haullakin löytyy (ihan äskettäin käydystä keskustelusta) rivi SDL_LoadBMP(filename.c_str());
sanoilla SDL_LoadBMP string. Kannattaa ihan oikeasti opetella keksimään tuollaisia aivan yksinkertaisia hakusanoja.
Kiitos kaikille avusta tähän mennessä. Nyt on vielä yksi kysymys, mihin en millään löytänyt vastausta: Miten saan ikkunan taustaväriä muutettua? Siitä pitäisi saada valkoinen.
no teet sen taustan kokoisen kuvan, joka on valkoinen ja piirrät sen kohtaan 0,0. :D Itse käytän tuollaista, mutt onnistuu kait SDL_FillRect() funktiolla http://sdl.beuc.net/sdl.wiki/SDL_FillRect
Ookkei. =) Vielä yksi kysymys (:s):
for(int a = 0; a < 3; a++) { int x = 0; int y = 0; if(a != 0) x += 40; srand(time(NULL)); int i = rand() % 7; string ruletti1 = hedelmat[i]; // Alustus SDL_Init(SDL_INIT_VIDEO); // Luodaan ikkuna, 640x480 pikseliä, 32-bittiset värit, kaksoispuskurointi. SDL_Surface *ruutu = SDL_SetVideoMode(640, 480, 32, SDL_DOUBLEBUF); // Ladataan kuva. SDL_Surface *kuva = SDL_LoadBMP(ruletti1.c_str()); // Kuvan piirtokohta on tietueessa (C++-opas: osa 4, tietueet). SDL_Rect kohta = {x, 0}; // Piirretään kuva (muistissa; ei näy vielä ruudulla). SDL_BlitSurface(kuva, 0, ruutu, &kohta); // Vapautetaan kuva; se on jo piirretty eikä sitä tarvita. SDL_FreeSurface(kuva); // Laitetaan piirretyt asiat ruudulle ("käännetään paperi"). SDL_Flip(ruutu); }
Tämä tulostaa vain yhden kuvan, joka on tuon 40 pikseliä reunasta. Pitäisi olla 3 kuvaa vierekkäin yläreunassa.
Nyt pliis opettele lukemaan koodiasi, koska tuossa ei ole kertakaikkiaan mitään järkeä. Nopeasti sanottuna alustat satunnaislukugeneraattorin turhaan monta kertaa. Et piirrä taustapuskuriin mitään yhtenäisesti. Teet turhia alustuksia jokaisella kierroksella. Muuttujan x arvo on jokaisella kierroksella 40 jne jne...
if(a != 0) x += 40;
Aika erikoinen ratkaisu! Mutta huomaathan, että nollaat x:n joka kerta, kun silmukka alkaa. Tee nollaus silmukan ulkopuolella niin saatat päätyä haluttuun tulokseen.
Luepa sitä SDL-opasta. Suunnilleen kaikki SDL:ää koskevat asiat ovat nimittäin nyt väärässä paikassa. Alustukset ja kuvien lataukset pitäisi tehdä kerran (ohjelman alussa) ja sulkemiset kerran (ohjelman lopussa) ja SDL_Flip aina siinä vaiheessa, kun kaikki ruudulle haluttava on piirretty. Tarkemmin kerrotaan vielä SDL-oppaassa, joten en ala tässä opettaa samoja asioita toistamiseen. Lisäksi tgunner osoitti koodistasi aivan ilmiselvän logiikkavirheen.
Vertaa koodiasi alla olevaan pätkään. Eli siis koodisi piirtää kyllä kohtaan 0, 0 kuvan, mutta seuraavalla kierroksella piirrät kohtaan 40, 0 uuden kuvan, mutta edellinen kuvahan ei ole enää tallella. Viimeinen kuva jää näkyvile, joten sinulle jäänee mielikuva, että koodisi ei piirrä kuin yhden kuvan
#include <iostream> int main(){ for(int a = 0; a < 3; a++){ int x = 0; int y = 0; if(a != 0) x += 40; std::cout << "a:n arvolla " << a << " on x:n arvo " << x << std::endl; } return EXIT_SUCCESS; }
Teuron ehdotus on loistava! Jatketaanpa siitä vielä hieman. Kommentoi kaikki rivit, kuten minun antamani rivit on kommentoitu, ja tulosta kaikki kommentit:
// Alustus std::cout << "Alustus" << std::endl; SDL_Init(SDL_INIT_VIDEO);
Näin voit helposti tarkkailla, mitä ohjelmassa tapahtuu. Näet toivottavasti heti, että tapahtuu aika paljon vääriä asioita. (Varsinaista kommenttia ei välttämättä enää tarvita, kun sen näkee tulostusriviltäkin.)
Kiitos hyvistä neuvoista! Nyt sain sen sitten tulostamaan kaikki kuvat.
Edit. Niin ja miten se siihen sdl ikkunaan tulostaminen onnistuikaan?
Ei ei ei! Et ilmeisesti vieläkään sisäistänyt noita mun ja metabolixin neuvoja? Teet edelleen samoja mokia, jotka on erittäin helppo korjata. Siis alusta satunnaislukugeneraattori silmukan ulkopuolella. Piirrä taustaan kaikki tarpeellinen kerralla, jonka jälkeen tulee vasta flip().
Toisaalta silmukkaa ei kannata käyttää, koska piirrät staattisesti kolme kuvaa, etkä käytä edes silmukkaa hyväksesi. Katsopa tätä versiota.
Tehty korjaus tohon koodiin siirretty kuvan vapautus silmukan ulkopuolelle, sekä korjattu kuvan piirtokoordinaatit.
#include <SDL/SDL.h> #include <string> #include <ctime> const string hedelmat[] = {"0.bmp", "1.bmp", "2.bmp", "3.bmp", "4.bmp", "5.bmp", "6.bmp", "7.bmp"}; int main(int argc, char **argv) { // Alustus SDL_Init(SDL_INIT_VIDEO); // Luodaan ikkuna, 640x480 pikseliä, 32-bittiset värit, kaksoispuskurointi. SDL_Surface *ruutu = SDL_SetVideoMode(640, 480, 32, SDL_DOUBLEBUF); /* Muuttujat luodaan kerran */ SDL_Surface *kuva; std::string rulla; srand(time(NULL)); int i = 0; int x = 0; int y = 0; for(int a = 0; a < 3; a++){ /* arvotaan uusi numero */ i = rand() % 7; /* sijoitetaan rullaan uusi kuva */ rulla = hedelmat[i]; // Ladataan kuva. kuva = SDL_LoadBMP(rulla.c_str()); // Kuvan piirtokohta on tietueessa (C++-opas: osa 4, tietueet). SDL_Rect kohta = {x, 0}; // Piirretään kuva (muistissa; ei näy vielä ruudulla). SDL_BlitSurface(kuva, 0, ruutu, &kohta); x += 40; } // Vapautetaan kuva; se on jo piirretty eikä sitä tarvita. SDL_FreeSurface(kuva); // Laitetaan piirretyt asiat ruudulle ("käännetään paperi"). SDL_Flip(ruutu); // "Ikuinen" silmukka, loppuu breakiin. while (1) { // Käsketään SDL:n tarkistaa viestit (näppäinten painallukset yms.). SDL_PumpEvents(); // Haetaan näppäimet (C++-opas: osa 4, taulukot, ja osa 7, osoittimet). const Uint8 * const napit = SDL_GetKeyState(0); // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) break; // Nukutaan 10 millisekuntia eli yksi sadasosa ennen uutta Esc-tarkistusta. SDL_Delay(10); } // Ohjelman lopussa suljetaan SDL-ikkuna. SDL_Quit(); }
Jeps, poistin koodin ennen kuin lisäsit tuon. Huomasin näes itsekkin sen virheen, ja korjasin. Samalla putkahti uusi kysymys sinne.
Latasin koneelleni SDL_tff-2.0.9 fontin, minkä Metabolix mainitsi jossain vanhassa aiheessa. Luen parhaillaan ohjeita sen käyttöön.
Edit. Onko tämä todellakin "helppo" tapa saada tulostettua tekstiä?
Mitä "vaikeaa" tuossa tekstin tulostamisessa sinusta sitten on? Lataat haluamasi fontin ja kirjoitat haluamasi tekstin haluamaasi kohtaan. Tarkkaan ottaen osaisit tehdä tuon ihan itsekin, koska tuo on kuvien piirtämistä. Tästä metabolix taisi mainitakin jokunen viesti sitten.
Ei tarvita oikeastaan kuin kuvatiedosto, josta jokainen kirjain voidaan lukea. Sitten vain luodaan kuvapinta, jolle nuo kirjaimet piirretään. Toki työ on iso, mutta idea on aika simppeli. Tähän voinee toteuttaa itse vaikkapa viivaa seuraavan tekstin tai jotain muuta hauskaa.
Okei, kiitos vastauksesta.
Koitin laittaa ikkunaan otsikon, ja sainkin sen: SDL_WM_SetCaption("Hedelm\x84peli", "Hedelm\x84peli");
Tuo ä vaan ei toimi siinä. SDL:n sivuilla sanotaan, että otsikko on UTF8 koodattu.
No niin oletko luonut char *Testi nimisen muuttujan, kuten ohjeessa sanotaan? Vastauksen toki tiedämme et ole. Sitten kokeilit laittaa tekstin lainausmerkkeihin, joka olikim ihan oikea liike. Mutta mitä sitten tapahtui? Ei sinne mitään kuvapolkua anneta, vaan teksti joka tulee alapalkkiin ikkunan ollessa minimoitu. Turhat muuttujat (y ja teksti) voi poistaa, kuten herja kertookin.
MIB kirjoitti:
Tuo ä vaan ei toimi siinä. SDL:n sivuilla sanotaan, että otsikko on UTF8 koodattu.
Pitäisikö se tekstikin olla sitten UTF-8?
Joo, kiitos tuosta vielä. :)
Nyt sain pelille "ulkoasun" eli kuvat liitettyä. Nyt tämä arpoo numerot kun painaa välilyöntiä. Ongelma on se, että taustakuva ja logo vilkahtavat aina, kun ne ladatataan uudelleen. Tiedän, ettette tykkää jostain syystä siitä gotosta, mutta nyt tässä koodissa on se. Koitan keksiä vielä jonkin järkevämmän tavan, jos se on huono.
Esimerkkinä, tämä osaa tulostaa joka kerralla kuvat, mutta se vilkahtaa ärsyttävästi:
#include <SDL/SDL.h> int main() { alku: //ladataan kuvat ja tulostetaan for(i = 0; i < 3; i++) { //arvotaan numerot ja tulostetaan } while(1) { //tarkistetaan, että mitä näppäintä on painettu //Jos se on esc, poistutaan //Jos se on space, goto alku (Aijai, nyt vilkahtaa) } }
Entä jos tekisi tuosta kuvien arpomisesta funktion? Sitten kuvien pirrosta funktion, jonka jälkeen liittäisi ne tuohon ikuiseen while silmukkaan sopivaan kohtaan. Säästyisit goton käytöstä ja koodista tulisi ehkä hiukka helpommin ylläpidettävää.
int arvo_numero(int ala, int yla){ srand(time(NULL)); return (ala + rand() % (ala + yla)); } void piirra_kuva(int x, int y){ /* arvotaan numero */ int kuva_id = arvo_numero(0, 7); /* sijoitetaan rullaan uusi kuva */ rulla = hedelmat[kuva_id]; /* Ladataan kuva. */ kuva = SDL_LoadBMP(rulla.c_str()); /* Kuvan piirtokohta on tietueessa (C++-opas: osa 4, tietueet). */ SDL_Rect kohta = {x, y}; /* Piirretään kuva (muistissa; ei näy vielä ruudulla). */ SDL_BlitSurface(kuva, 0, ruutu, &kohta); }
Lähinnä tarkoitin, että taustakuva ja logo välähtää. Nuo numerot pysyvät oikein eivätkä välähdä. Eli, ohjelman alussa pitäisi ladata kuvat siihen ohjelmaan, mutta jos jotain muuta kohtaa suoritetaan uudelleen, niin kuvat joko välähtävät (suoritus alkaa alusta) tai niitä ei tule (ei suoriteta kohtaa).
En oikein ymmärtänyt, että mitä koitit tarkoittaa noilla funktioilla.
Tarkoitus olisi, että kuvat laitetaan siis ruudulle, ja ne pysyvät siinä koko ohjelman suorittamisen ajan, eli niitä ei ladata joka välilyönnin painalluksella uudelleen.
Joo nyt tajuan mikä on ongelmasi. Voit siis käyttää goto jos haluat, mutta laita tuo alku nimiö noiden kuvien piirron jälkeen, jolloin niitä ei suoriteta uudelleen.
Teuro kirjoitti:
Voit siis käyttää goto jos haluat, mutta liat tuo alku nimiö noiden kuvien piirron jälkeen, jolloin niitä ei suoriteta uudelleen.
Anteeksi mitä? En ihan ymmärtänyt. Jos koodi näyttäisi tältä:
int main() { //Tulostetaan taustakuva ja logo //Tämä pitäisi suorittaa vain kerran arvo: //Tämä suoritetaan aina kun painetaan spacea for(i = 0; i < 3; i++) { //Arvotaan numerot, eli ne ruletit } while(1) { //Jos painettiin esciä, poistutaan //Jos painettiin spacea, goto arvo } }
Tämä tulostaa kerran nuo kuvat, mutta ei muista niitä kun painetaan välilyöntiä.
Laita alku nimiö tuon for silmukan jälkeen ihan niin kuin edellisessä viestissä sanoin.
int main() { //Tulostetaan kuvat for(i = 0; i < 3; i++) { //Arvotaan kuvat } arvo: while(1) { //Jos painettiin esciä, poistutaan //Jos painettiin spacea, goto arvo } }
Aa, kiitos :) Nyt sain toimimaan.
Tämä toimii nyt niinkuin se olisi hyvä, mutta tämä sotkee kyllä pelin voittojen ja tappioiden kannalta.
#include <SDL/SDL.h> #include <string> #include <ctime> #include <iostream> using namespace std; const string hedelmat[8] = {"0.bmp", "1.bmp", "2.bmp", "3.bmp", "4.bmp", "5.bmp", "6.bmp", "7.bmp"}; int main(int argc, char **argv) { //Otetaan siemenluku ajasta, ettei arvota samoja kuvia joka kerta srand(time(NULL)); //Tässä kohtaa tulostetaan tausta ja logo alku: for(int a = 0; a < 3; a++) { int x = 0; //180 pikseliä paddingia koska logo tulee siihen yläreunaan int y = 180; //Tähän tulee vielä korjaus. if(a == 0) x = 0; if(a == 1) x = 40; if(a == 2) x = 80; int i = rand() % 7; string ruletti1 = hedelmat[i]; // Ladataan kuva. SDL_Surface *kuva = SDL_LoadBMP(ruletti1.c_str()); // Kuvan piirtokohta on tietueessa (C++-opas: osa 4, tietueet). SDL_Rect kohta = {x, y}; // Piirretään kuva (muistissa; ei näy vielä ruudulla). SDL_BlitSurface(kuva, 0, ruutu, &kohta); // Vapautetaan kuva; se on jo piirretty eikä sitä tarvita. SDL_FreeSurface(kuva); // Laitetaan piirretyt asiat ruudulle ("käännetään paperi"). SDL_Flip(ruutu); } // "Ikuinen" silmukka, loppuu breakiin. while (1) { // Käsketään SDL:n tarkistaa viestit (näppäinten painallukset yms.). SDL_PumpEvents(); // Haetaan näppäimet (C++-opas: osa 4, taulukot, ja osa 7, osoittimet). const Uint8 * const napit = SDL_GetKeyState(0); // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) break; //Jos painettiin välilyöntiä, niin arvotaan numerot uudelleen else if(napit[SDLK_SPACE]) goto alku; // Nukutaan 10 millisekuntia eli yksi sadasosa ennen uutta Esc-tarkistusta. SDL_Delay(10); } // Ohjelman lopussa suljetaan SDL-ikkuna. SDL_Quit(); }
Nyt tuo toimii kuin oikea hedelmäpeli (noin silmällä katsottuna), mutta voitot ja tappiot menevät sekaisin. Koitappas itse, jos et tajunnut mitä tarkoitin. Tuo pyörittää niitä kuvia (for silmukassa) niin kauan, kuin space on pohjassa kun pitäisi arpoa kuvat kerran kun paina spacea.
Edit. Jos tälläisen pelin laittaa nettiin (käännettynä kuvat mukana), niin tämän pelin kuviahan voi muokata helpolla kun avaa ne vain paintilla. Pystynkö jotenkin estämään näiden muokkaamisen? Voiko niistä ottaa jotain oikeuksia pois (kuten Linuxilla on nuo CHMODit) tai voiko ne cräkätä niin, että vain ohjelma voisi lukea niitä?
Ei se pyöritä kuvia for silmukassa, kuin ainoastaan 3 kertaa / kierros. Opettele viimeinkin lukemaan sitä koodiasi, koska tuosta selviät niinkin helposti, kuin lisäämällä SDL_Delay funktion nukkumisaikaa vaikkapa 200 - 250 ms, jolloin kerkiät ottamaan napin pois pohjasta.
Mutta ei sitten kelvannut nuo muutama viesti sitten ehdottamani muutokset muuttujien luomisesta silmukassa. Samoin tein korjauksen sulle tohon x:n arvon laskemiseen, mutta käytät edelleen tuota purkkaratkaisua. Sinällään ihan sama, mutta tulee vain sellainen olo, että luetko sä näitä vinkkejä ollenkaan?
Älä käytä gotoa, ennen kuin olet viisastunut niin paljon, että ymmärrät, milloin se kannattaa. Kaiken voi tehdä ilmankin, useimmat asiat vielä paljon paremmin.
Jos lukisit mm. sitä SDL-opasta, oppisit toisen tavan näppäinten käsittelyyn, jolloin ei tuotakaan ongelmaa tulisi. Jos lukisit koodiasi tarkemmin ja jos tulostaisit kaikki kommentit, kuten kehotettiin, ymmärtäisit, että SDL_Delay-riville ei koskaan päästä, jos välilyönti on pohjassa.
Muilta osin en jaksa edes lukea viestejäsi. Luultavasti oppisit ohjelmoimaan paremmin, jos lukisit ajatuksella niitä oppaita ja miettisit jokaista ongelmaa ainakin 3–4 päivää ihan itse, ennen kuin täytät foorumit yksinkertaisilla kysymyksilläsi. Yksi hyvä vaihtoehto on, että tallennat oppaat koneellesi ja otat nettipiuhan kuukaudeksi irti. Järki ei parane, jos sitä ei käytä.
Voisit opetella käyttämään niitä funktioita!! Toi koodi on meinaa hirveen näköistä. Jos vaikka lukisit c++ oppaan, voisit osata korjata virheesi. -.-
Teuro kirjoitti:
Ei se pyöritä kuvia for silmukassa, kuin ainoastaan 3 kertaa / kierros. Opettele viimeinkin lukemaan sitä koodiasi, koska tuosta selviät niinkin helposti, kuin lisäämällä SDL_Delay funktion nukkumisaikaa vaikkapa 200 - 250 ms, jolloin kerkiät ottamaan napin pois pohjasta.
No, selviää siitä, mutta sitten pitää myös aina painaa sitä välilyöntiä tms. aina sillä tietyllä hetkellä kun se tarkistaa.
Teuro kirjoitti:
Mutta ei sitten kelvannut nuo muutama viesti sitten ehdottamani muutokset muuttujien luomisesta silmukassa. Samoin tein korjauksen sulle tohon x:n arvon laskemiseen, mutta käytät edelleen tuota purkkaratkaisua. Sinällään ihan sama, mutta tulee vain sellainen olo, että luetko sä näitä vinkkejä ollenkaan?
int main() { //Tulostetaan kuvat for(i = 0; i < 3; i++) { //Arvotaan kuvat } arvo: while(1) { //Jos painettiin esciä, poistutaan //Jos painettiin spacea, goto arvo } }
En ymmärrä mitä järkeä tuossa sitten on. Mihin se 'alku' pitäisi sitten laittaa? Tuonne while silmukan alle? Mitä se sitten sielä tekee?
Tuossa kun painaisi sitä spacea, niin hypätään uudelleen taas tuohon while silmukkaan.
Kun kuvat ladattiin joka kerta uudelleen, niin se esti sen, ettei voinut kuin kerran painaa sitä spacea. Nyt se pitäisi korjata, että kun spacea painaa (vaikka pitäisi pohjassa), niin se suorittaa arvonnan vain kerran.
En ymmärrä, että miten voin korjata "virheen" oppaan perusteella, missä ei kerrota asiasta?
Olet oikeassa: oppaassa ei kerrota, "tee näin, jos ohjelma jatkuu välilyöntiä painettaessa monta kierrosta eikä vain yhtä". Oppaassa sen sijaan kerrotaan, miten C++:n erilaiset rakenteet toimivat, ja sen perusteella voit todeta, kuten edellisessä viestissäni sanoinkin, että kun välilyönti on pohjassa, SDL_Delay-riviä ei suoriteta ja päädytään aina vain uudestaan alkuun. Ohjelma toistaa siis tuota pätkää mahdollisimman nopeasti, kunnes otat napin pois pohjasta. (Kuvien lataaminen "auttoi", koska se hidasti ohjelmaa.)
Jos yhtään ymmärrät ohjelmoinnista, osaat C++-oppaan, SDL-oppaan tai äskeisen selostuksen perusteella korjata asian (siis kolme vaihtoehtoa). Jos et ymmärrä, ole hyvä ja mieti asiaa ihan itseksesi pari päivää; tähän mennessä et ole koodannut itse juuri mitään, vaan ohjelmasi on liimailtu muiden antamista pätkistä muiden antamilla ohjeilla.
Kerrataan vielä. Yhden ratkaisun ongelmaasi voit päätellä viestini alusta. Toisen jo mainitsin aiemmin: käsittele viestit SDL-oppaassa neuvotulla toisella tavalla. Tässä on vielä kolmas: käytä muuttujaa, josta tarkistat, onko välilyönti otettu pois pohjasta edellisen arvonnan jälkeen. Ole hyvä ja mieti edes pari päivää itse näitä vaihtoehtoja, ennen kuin tulet taas pyytämään, että joku tekisi ne puolestasi. Yritä toteuttaa kaikki kolme eri ratkaisuvaihtoehtoa, niin opit enemmän.
Turhaan yrität graafista peliä tehdä, jos et osaa tehdä vastaavaa tekstipohjaisena. Teepä siis ensin tekstihedelmäpeli:
Tämä on hedelmäpeli! Tervetuloa! -------------------------- Rahat Voitot Panos 0.00 0.00 0.20 1. Syötä rahaa. 2. Nosta panosta. 3. Laske panosta. Valinta: 1 Summa: 2.00 -------------------------- Rahat Voitot Panos 2.00 0.00 0.20 1. Syötä rahaa. 2. Nosta panosta. 3. Laske panosta. 4. Pelaa. Valinta: 4 -------------------------- Rahat Voitot Panos 1.80 0.00 0.20 Omena Banaani Kirsikka Ei voittoa. 1. Syötä rahaa. 2. Nosta panosta. 3. Laske panosta. 4. Pelaa. Valinta: 2 -------------------------- Rahat Voitot Panos 1.80 0.00 0.40 Omena Banaani Kirsikka Ei voittoa. 1. Syötä rahaa. 2. Nosta panosta. 3. Laske panosta. 4. Pelaa. Valinta:
Jne.
Tein jo, tosin tuo on vähän vajaa versio.
Metabolix kirjoitti:
(Kuvien lataaminen "auttoi", koska se hidasti ohjelmaa.)
Kyllä, siksi juuri. Nyt kuitenkin haluaisin saada ongelman pois tästä, tappelematta teidän kanssanne asiasta.
MIB kirjoitti:
Tein jo, tosin tuo on vähän vajaa versio.
Ei tuollainen sotku kelpaa. Tee se selkeästi, siististi ja niin, että se toimii täysin loogisesti ja on tyylikäs. Et tarvitse yhtäkään gotoa tai system-funktiota. (CLS:n saat laittaa, jos se niin tärkeältä tuntuu.) Koodin pitää olla sellaista, että täysin ulkopuolinen lukija pystyy helposti seuraamaan sen logiikkaa.
Siististi tehdyn pelin main-funktio voisi näyttää vaikka tältä:
int main() { aloitus(); while (1) switch (valikko()) { case NOSTA_PANOSTA: nosta_panosta(); break; case LASKE_PANOSTA: laske_panosta(); break; case PELAA: pelaa(); break; case TUPLAA: tuplaa(); break; case LATAA_RAHAA: lataa_rahaa(); break; case LOPETA: lopetus(); return 0; } }
Jaa-a. Siitä muuttujien tulostuksesta... Sanoit, että niitä muuttujia voi tulostaa sillä coutilla sinne komentoriville, kun säätää siinä sdl ikkunassa, mutta ei sinne mitään tulostunut millään.
Ehkä SDL-versiosi on ehkä ohjannut tulostuksen tiedostoon stdout.txt. Jostain syystä Windowsissa on toisinaan ollut sellainen tapa.
No sielläpä se oli. Voiko sitä jotenkin muuttaa?
Laita linkkerin optioksi seuraava rimpsu:
-lmingw32 -lSDL -lSDL_ttf -DNO_STDIO_REDIRECT -Dmain=SDL_main
Game Dev kavereiden mielestä pitäisi toimia.
Tyhmä kysymys, mutta minkä linkkerin?
Kokeile korvata lib-hakemistossa oleva tiedosto libSDLmain.a tällä. (Ota vanha talteen varmuuden vuoksi.)
Eipä toiminut :( Ihan samalla lailla tekee. (Kyllä, käynnistin ohjelman uudelleen)
Pitää myös kääntää ohjelma uudelleen. Tee koodiin jokin muutos (lisää vaikka kommentti) ja kokeile uudestaan.
Nyt se ei suostu enään kääntymään:
||=== Hedelmäpeli, Debug ===| \C++\SDL\main.cpp||In function `int SDL_main(int, char**)':| \C++\SDL\main.cpp|135|warning: control reaches end of non-void function| C:\Program Files\CodeBlocks\MinGW\lib\libSDLmain.a(SDL_win32_main.o)||In function `fprintf':| \usr\lib\gcc\i486-mingw32\4.4.0\..\..\..\..\ i486-mingw32\include\stdio.h|246|undefined reference to `___mingw_vfprintf'| ||=== Build finished: 1 errors, 1 warnings ===|
No testaa vielä tällä. Jos ei auta, siirry näihin ohjeisiin. Aika typerää, ettei tuota tulostusta voi muuttaa järkevästi oman ohjelman puolelta tai ohjelmaa käynnistäessä.
Kiitos, toi toimii :)
Edit. Kysyn vielä sitä, minkä mainitsinkin jo: Eli, lähdekoodiahan ei pysty muokkaamaan käännetystä ohjelmasta, tai ei ainakaan helpolla. Peliin kun liittyy kuvia, niin niitä pystyy muokkaamaan, kun avaa ne vaikka Paintilla. Ei ole kiva, jos näitä kuvia mennään muokkaamaan, ja väitetään ohjelmaa omatekemäksi.
Onko siis mahdollista cryptata/kräkätä/tms. ne kuvat niin, että niitä ei voi muokata?
Tekijän nimen saisi siihen kaikista varmemmin siihen niin, että se pysyy kun kirjoittaisi sen siihen ohjelmaan. Mikä fonttikirjasto SDL:n kaveriksi olisi helppo asentaa?
Ei ole, ei varsinkaan sinun taidoillasi. Tekijän nimi muuttuu ohjelmasta heksaeditorilla hyvin helposti, ja kuvienkaan muuntelu ei ole suinkaan mahdoton tehtävä.
Voit miettiä noita suojausasioita sitten muutaman vuoden kuluttua, kun ensin opit tekemään jotain niin hienoa, että joku muukin kuin tyhmimmät koulukaverisi kehtaisi väittää sitä omakseen.
Paras ratkaisu on hankkia projektille tarpeeksi mainetta, että jutussa on aivan selvää, kuka sen on alunperin tehnyt. (Hyvä projekti saa mainetta ihan itsestään, eli ei tarvitse mainostaa.) Tekijänoikeuslaki on puolellasi, joten voit sitten haastaa oikeuteen laittomasta kopioinnista ja muuntelusta.
MIB kirjoitti:
Edit. Kysyn vielä sitä, minkä mainitsinkin jo: Eli, lähdekoodiahan ei pysty muokkaamaan käännetystä ohjelmasta, tai ei ainakaan helpolla. Peliin kun liittyy kuvia, niin niitä pystyy muokkaamaan, kun avaa ne vaikka Paintilla. Ei ole kiva, jos näitä kuvia mennään muokkaamaan, ja väitetään ohjelmaa omatekemäksi.
No tämä nyt tuskin on huolistasi suurin ;D
Sinuna keskittyisin enemmän perus-ohjelmointiin ja vähemmän tuollaiseen turhaan säätöön...
MIB kirjoitti:
Tekijän nimen saisi siihen kaikista varmemmin siihen niin, että se pysyy kun kirjoittaisi sen siihen ohjelmaan. Mikä fonttikirjasto SDL:n kaveriksi olisi helppo asentaa?
... ja sitten kun avaa ohjelman heksaeditoriin ja sieltä etsii tekstin "Tämän tosi hienon pelin on tehnyt MIB!" tms. ja muuttaa sen haluamakseen niin kas vain, teksti muuttuu. Tosin en tiedä kuka moiseen vaivautuisi, kun oman (paremman) hedelmäpelin kirjoittaa käden käänteessä. :P
En tarkoittanut sitä, että pelistä tulisi niin hyvä että kukaan haluaisi sen omiin nimiinsä, vaan ihan toiselta laidalta ajattelin asiaa. Muuallakin olisi käyttöä, ettei kuvia kopioitaisi.
Niin, mikä olisi hyvä fonttikirjasto?
Se jo mainittu SDL_ttf.
Eikö SDL_TTF kelvannutkaan? Voisit pienen harjoittelun jälkeen yrittää toteuttaa kirjoitusfunktiot ihan itse.
Latasin Windows32 binaryt sieltä. Siellä oli 3 dll tiedostoa. Kopioinko ne sinne Code::Blocksin include/lib kansioon, tai laitanko projektikansioon missä niitä tarvitaan?
Koitin tehdä tämän mukaan tuota tekstin tulostusta. Exe toimii hyvin, mutta kun avaan sen cpp tiedoston ja koitan kääntää, niin tulee errorit:
\ATest\test.cpp|2|SDL_image.h: No such file or directory| \ATest\test.cpp|3|SDL_ttf.h: No such file or directory| \ATest\test.cpp||In function `SDL_Surface* ImgLoader(char*, bool, int, int, int, int)':| \ATest\test.cpp|28|error: `IMG_Load' was not declared in this scope| \ATest\test.cpp|30|error: `IMG_GetError' was not declared in this scope| \ATest\test.cpp||In function `int SDL_main(int, char**)':| \ATest\test.cpp|50|error: `TTF_Font' was not declared in this scope| \ATest\test.cpp|50|error: `font' was not declared in this scope| \ATest\test.cpp|51|error: `TTF_Init' was not declared in this scope| \ATest\test.cpp|52|error: `TTF_OpenFont' was not declared in this scope| \ATest\test.cpp|60|error: `TTF_RenderText_Solid' was not declared in this scope| ||=== Build finished: 9 errors, 0 warnings ===|
Ei vaan lataat ton kehitys-zipin (devel) ja sen sitten purat kansioon, missä muutkin otsikkotiedostot ja kirjastot on (varmaan sama kansio mihin kääntäjä on asennettu, siellä lib/ ja include/). Ne DLL:t jotka latasit voit laittaa samaan kansioon ohjelmasi kanssa tai sitten kopioit nuo DLL:t, jotka on tuolla devel-zipissä lib-kansiossa ja siirrät ne ohjelmasi kansioon.
Samaa mieltä muiden kanssa ettei sinun kannata päätä noilla kopiosuojauksilla vaivata.
Jos kuitenkin haluat, niin kyllä sen kuvatiedoston voi salata salauksella, jonka vain oma ohjelmasi tai osaava krakkeri saa auki.
Tekijänoikeuksien suojelemiseksi on kehitetty myös digitaalinen vesileimaus, jonka avulla tieto alkuperäisestä tekijästä välittyy kuvan mukana.
http://en.wikipedia.org/wiki/
Jotta edellä mainituista tekniikoista olisi suurempaa iloa, niin sinun täytyisi pystyä estämään kuvaruutukaappaukset. Siihen ainoa varma tapa on, että et näytä sitä kuvaa ollenkaan. ;)
Jos asensit Code::Blocksin mukana DevPak-tuen, voit asentaa SDL_ttf:n helposti DevPakista. Kannattaa asentaa myös SDL_image, ja tuolta löytyy valmiiksi paketoituna monta muutakin kirjastoa.
Joo, asennuksessa valitsin että kaikki laitetaan, niin kaipa se sitten on. Miten sieltä pystyn asentamaan sen?
Löytyisikö ehkä Plugins-valikosta apua?
Jep, mutta siellä listassa ei ole sitä sdl_ttf juttua, enkä tiedä mitä sillä DevPackille kuuluisi tehdä.
Mietiskelin tässä, että kun siihen SDL ikkunaan jossain vaiheessa opin tulostamaan, että miten saan vanhat viestit aina häviämään kun uusi tulee tilalle (toisin sanoen pelataan uusi kierros). Ajattelin, että teen yhden muuttujan, vaikka viesti. Joka kierros laitan siihen yhteen muuttujaan sen kierroksen tiedot (Tässä tapauksessa vain jos voitettiin tai hävittiin) ja tulostan ne silmukan jälkeen.
Mietin tässä myös, että kun niiden kuvien lataaminen hidasti suoritusta niin, että välilyöntiin reagoitiin vain kerra, niin koitan selvittää miten saan vain kerran suoritettua silmukan, vaikka space olisi pohjassa. En kuitenkaan keksinyt mitään järkevää vastausta selaillessa Putkan SDL ja C++ opasta.
Miten kannattaisi tehdä?
MIB kirjoitti:
Mietin tässä myös, että kun niiden kuvien lataaminen hidasti suoritusta niin, että välilyöntiin reagoitiin vain kerra, niin koitan selvittää miten saan vain kerran suoritettua silmukan, vaikka space olisi pohjassa. En kuitenkaan keksinyt mitään järkevää vastausta selaillessa Putkan SDL ja C++ opasta.
Miten kannattaisi tehdä?
No tämä(kin) pitäisi itse tajuta, mutta...
Teet nousevan reunan:
bool pohjassa = false; while (pelataan) { // koodia // ... if (napit[SDLK_SPACE] && !pohjassa) { // tee sitä ja tätä // ... pohjassa = true; } else if (!napit[SDLK_SPACE]) { pohjassa = false; } }
Lisäystä:
MIB kirjoitti:
Mietiskelin tässä, että kun siihen SDL ikkunaan jossain vaiheessa opin tulostamaan, että miten saan vanhat viestit aina häviämään kun uusi tulee tilalle (toisin sanoen pelataan uusi kierros). Ajattelin, että teen yhden muuttujan, vaikka viesti. Joka kierros laitan siihen yhteen muuttujaan sen kierroksen tiedot (Tässä tapauksessa vain jos voitettiin tai hävittiin) ja tulostan ne silmukan jälkeen.
Ei se SDL(_ttf) mitenkään puskuroi noita tekstejä ja sitten siirrä aina fontin korkeuden verran ylöspäin. Teksti piirretään, ei tulosteta kuten konsoli-ikkunaan. Eli homma toimii niin, että "tyhjennät" vanhan kuvan (piirtämällä taustakuvan tai taustavärin) aina ennen uuden piirron alkamista, jolloin taustalle ei jää mitään roskaa (vanhaa tekstiä alle), kun teksti vaihtuu.
Laitoin:
#include <SDL/SDL.h> #include <iostream> using namespace std; int main(int argc, char **argv) { // Luodaan ikkuna, 300 x 300 pikseliä, 32-bittiset värit, kaksoispuskurointi. SDL_Surface *ruutu = SDL_SetVideoMode(500, 350, 32, SDL_DOUBLEBUF); // Alustus SDL_Init(SDL_INIT_VIDEO); bool pohjassa = false; // "Ikuinen" silmukka, loppuu breakiin. while (1) { // Käsketään SDL:n tarkistaa viestit (näppäinten painallukset yms.). SDL_PumpEvents(); // Haetaan näppäimet const Uint8 * const napit = SDL_GetKeyState(0); // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) return 0; else if (napit[SDLK_SPACE] && !pohjassa) { cout << "Nappia on painettu ja se ei ole pohjassa!\n\n"; pohjassa = true; } else if (!napit[SDLK_SPACE]) { pohjassa = false; } // Nukutaan 10 millisekuntia eli yksi sadasosa ennen uutta Esc-tarkistusta. SDL_Delay(10); } // Ohjelman lopussa suljetaan SDL-ikkuna. SDL_Quit(); }
Ja tästä tulee:
C:\Program Files\CodeBlocks\MinGW\lib\libSDLmain.a(SDL_win32_main.o)||In function `console_main':| \tmp\sdl-tmp\SDL-1.2.13\.\src\main\win32\SDL_win32_main.c|181|undefined reference to `_SDL_strlcpy'| \tmp\sdl-tmp\SDL-1.2.13\.\src\main\win32\SDL_win32_main.c|186|undefined reference to `_SDL_GetError'| \tmp\sdl-tmp\SDL-1.2.13\.\src\main\win32\SDL_win32_main.c|196|undefined reference to `_SDL_SetModuleHandle'| C:\Program Files\CodeBlocks\MinGW\lib\libSDLmain.a(SDL_win32_main.o)||In function `WinMain@16':| \tmp\sdl-tmp\SDL-1.2.13\.\src\main\win32\SDL_win32_main.c|256|undefined reference to `_SDL_strlcpy'| C:\Program Files\CodeBlocks\MinGW\lib\libSDLmain.a(SDL_win32_main.o)||In function `cleanup':| \tmp\sdl-tmp\SDL-1.2.13\.\src\main\win32\SDL_win32_main.c|148|undefined reference to `_SDL_Quit'| ||=== Build finished: 5 errors, 0 warnings ===|
MIB kirjoitti:
Linkitys virheitä...
Onhan linkkerille kerrottu, että SDL pitää linkata mukaan? (se -lSDL valitsin)
Ei, koska muut SDL ohjelmani toimivat.
Mitä siis muutit, että ohjelma lakkasi toimimasta?
Otin kuvien tulostukset pois, ja pari if lausetta. Toimimaton koodi on yllä.
No projektin asetukset on kuitenkin pielessä. Onko tuo nyt joku uusi projekti? Mikäli on, kokeile copy-pastetta toi sama koodi vanhan projektin päälle mikä on toiminut.
Yksi logiikkavirhehuomautus:
int main() { // ... while (1) { // ... // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) return 0; } // Ohjelman lopussa suljetaan SDL-ikkuna. (Ai suljetaan vai?) SDL_Quit(); }
Tuo return sulkee ohjelman "suoraan" eli nyt tuo SDL_Quit() jää kutsumatta. Tuollainen ikuinen looppi, mistä sitten breakilla poistutaan ei ole se paras vaihtoehto muutenkaan, vaan kannattanee tehdä näin:
int main() { // ... bool pelataan = true; while (pelataan) { // ... // Jos painetaan Esc-näppäintä, lopetetaan silmukka. if (napit[SDLK_ESCAPE]) { pelataan = false; } } // Ohjelman lopussa suljetaan SDL-ikkuna. (ja esim. vapautetaan kuvat) SDL_Quit(); return 0; }
Toinen logiikkavirhehuomautus: alustat tuossa SDL:n vasta ikkunan luomisen jälkeen, eli yritäpä nyt muistella ihan SDL:n perusasioita.
No, saimpas toimimaan. Olin vahingossa luonut "Emty File"n, enkä sitä projektia.
Edit. Saimpas korjattua!
Kysyn vielä siitä DevPackista, että miten se asennetaan tuolla Code::blocksilla?
Koitin etsiä oppaita netistä, että miten se sdl_ttf saadaan toimimaan ja miten sillä tulostetaan. En vain ole saanut edes "asennettua" sitä. Eli, apua kaipaisin.
a) Latasin sen kehityspaketin koneelleni. Kansiossa on kaksi alihakemistoa; include ja lib. Kopioinko include kansion sisällön include kansioon Code::Blocksin hakemistossa, ja libin lib kansioon siellä?
b) Miten tekstiä nyt sitten tulostetaan "yksinkertaisimmin"? Onko järkevää luoda joku funktio, kuten tulosta(teksti, marginaali y, marginaali x) vai miten? Ymmärsin, että tulostaminen ei onnistu yhdellä rivillä, vaan pitää olla monen rivin pituinen sotku aina tulostamaan yksi teksti.
Jos a kohta osui oikeaan ja b kohdassa on järkevintä tehdä funktio tuolla tavoin, niin voisiko joku näyttää, miten tällä kuuluisi tulostaa tekstiä? Netissä on kyllä paljon oppaita löytynyt, mutta niissä tehdään niin paljon kaikkea muutakin, että en saa koodista selvää.
Laita lib-asiat lib-hakemistoon ja include-asiat include/SDL-hakemistoon, ja käytä includessa polkua SDL/SDL_ttf.h. Jos (kun) mukana on jokin dll-tiedosto, se pitää sijoittaa samaan paikkaan kuin SDL.dll (ja lähettää kavereillekin ohjelman mukana).
Jos teet tekstin tulostamiseen muutaman rivin funktion (joka ei ole sotku!), voit käyttää aina sitä samaa funktiota, jolloin muualla koodissa tulostaminen vie tasan sen yhden rivin. Fontti pitää ladata tiedostosta, tästä tulee muutama rivi lisää.
Jos opettelisit ensin C++:aa kunnolla, osaisit tehdä nämä asiat itsekin, joten annan yhä saman neuvon: mene pois foorumilta ja opettele ja kokeile ihan kaikessa rauhassa omilla aivoillasi. Kärsimättömyytesi on sinulle suureksi vahingoksi, tuolla menolla et opi ikinä mitään.
Ei ole vaikeuksia tehdä funktiota, mutta siinä on vaikeuksia, että mitä sinne kirjoitetaan sisään että saadaan tekstiä tulostettua. Kuten mainitsinkin:
MIB kirjoitti:
Netissä on kyllä paljon oppaita löytynyt, mutta niissä tehdään niin paljon kaikkea muutakin, että en saa koodista selvää.
MIB kirjoitti:
Ei ole vaikeuksia tehdä funktiota, mutta siinä on vaikeuksia, että mitä sinne kirjoitetaan sisään että saadaan tekstiä tulostettua.
Sitä se funktion teko juuri tarkoittaa. Ja kyllä siitä koodista pitää oppia saamaan selvää, et voi koko elämääsi saada kaikkia ohjelman palasia valmiiksi kirjoitettuna eteesi. (Ja sitten vielä kehtaat väittää niitä ohjelmia omiksesi!) Ymmärtämisessä auttaa, kun opettelet kärsivällisesti ohjelmoimaan kunnolla ihan tavallista C++:aa etkä jatkuvasti kurkottele liian ylös. Onko uusi, parempi ja siistimpi komentorivihedelmäpeli jo valmis?
Metabolixilta ihan hyvä ehdotus tehdä ensin komentoriviohjelma ja saada logiikka kohdalleen.
Voit aloittaa yksinkertaisesti ja hedelmien kuvien sijasta voit vaikka käyttää numeroita: Esim. laita taulukkoon numerot nollasta kahdeksaan, mistä randomilla haet numeron. Eli käytännössä ruudulla on kolme numerokenttää, joihin voit sijoittaa ensimmäisen kierroksen alkuarvoiksi vaikka nollat. Näppäintä painettaessa haet edellä kertomallani tavalla uuden numeron kaikkiin kolmeen tekstikenttään. Saat toteutettua yksinkertaisen animaation arpomalla useamman kerran ennen lopullista tulosta ja laittamalla viiveen arpomiskertojen väliin. Jos mietit, miksi käskin laittaa arvontanumerot taulukkoon: voit myöhemmin toteuttaessasi graafista käyttöliittymää korvata taulukon numerot esim. bittikarttojen nimillä.
Muuten, jos kiinnostaa miten noissa oikeissa hedelmäpeleissä ne kuviot niissä kiekoissa menee, niin tuolta löytyy Tähden lisäksi muidenkin RAYn vehkeiden kuvioinnit.
Jos ottaisin tuolta tommoisen kelan, ja lättäisin koodiin, niin miten saisin sen pyörimään? Jos vaikka pyöräytyksin määrä olisi vaikka rand() % 10?
Edit, jaa, empäs sittenkään taida ottaa suoraan.
Ray kirjoitti:
Hedelmäkuvat Copyright © RAY
Copyright © Rahapeliopas, ellei toisin mainittu
Lähinnä laitoin tuon sen vuoksi, että tuosta näkee havainnollisesti miten noi painotukset toimii, eli kun on 24 kuvion kiekko ja eri kuvioita on vain 9 ja tietyillä kuvioilla on isompi painoarvo kuin toisilla.
Toisaalta jos teet pelkästään omaan käyttöön harjoittelumielessä tuollaista peliä, niin ihan hyvin voit käyttää esimerkiksi noita kuvia. Kunhan et levitä sitä eteenpäin, niin se on yksityistä käyttöä. Ja jos sitten joskus haluat pistää sen levitykseen, niin voit siinä vaiheessa vaihtaa omat tilalle.
MIB kirjoitti:
Jos ottaisin tuolta tommoisen kelan, ja lättäisin koodiin, niin miten saisin sen pyörimään?
Kaikista helpoin tapa ja miten sinun kannattaa lähteä alussa liikkeelle, on että lasket montako kuvaa kelassa on. Sen jälkeen arvot kuvaindeksin lasketun lukumäärän perusteella. Kuvaindeksin perusteella voit piirtää vain halutun osan kelasta. Olen niin vähän sdl:n kanssa pelannut, etten muista miten ne rutiinit siinä menevät, mutta periaatetasolla piirrät kelasta kohdan (0, indeksi*kuvakoko_y) - (kuvakoko_x, indeksi*kuvakoko_y + kuvakoko_y).
Se ei vielä ole oikeaa pyörimistä, mutta askeleen lähempänä jo.
Grez kirjoitti:
Toisaalta jos teet pelkästään omaan käyttöön harjoittelumielessä tuollaista peliä, niin ihan hyvin voit käyttää esimerkiksi noita kuvia. Kunhan et levitä sitä eteenpäin, niin se on yksityistä käyttöä. Ja jos sitten joskus haluat pistää sen levitykseen, niin voit siinä vaiheessa vaihtaa omat tilalle.
Tietenkin se aluksi on vain omassa käytössä, mutta tarkoitus olisi antaa se parille kaverille jotka sitä pyysivät. En vain arvannut, että pitäisi aloittaa opettelemaan SDL:ää, niin tuli tälläinen jännä keskustelu.
Edit. Koska pitäisi saada jpg kuvia peliin, niin laitoin SDL_LoadBMP() -> IMG_Load(). Tämä nähtävästi vaatii sdl_image lisäkirjaston. Latasin sen SDL:n sivuilta ja laitoin includet Code::Blocksin include kansioon ja lib tiedostot kopioin projektikansioon että toimivat muillakin. Ei kuitenkaan lähetenyt toimimaan.
peli\main.cpp|2|SDL/SDL_image.h: No such file or directory| peli\main.cpp||In function `int SDL_main(int, char**)':| peli\main.cpp|136|error: `IMG_load' was not declared in this scope| peli\main.cpp|136|warning: unused variable 'IMG_load'| ||=== Build finished: 2 errors, 1 warnings ===|
No kun ne includet pitää laittaa include/SDL-hakemistoon. Näethän tuosta virheestäkin: "SDL/SDL_image.h: No such file or directory".
Menepä nyt sanomaan suosiolla niille kavereillesi, ettet osaa vielä ja että palataan asiaan vuoden kuluttua. Tästä jää väkisinkin sellainen kuva, ettet edes halua oppia ohjelmoimaan, haluat vain saada tekeleesi valmiiksi.
Jos C++ ohjelmoinnin aloitus tuntuu alkuun vaikealta, niin voisit harkita muita vaihtoehtoja.
Omat lempityökaluni Windows-ohjelmointin:
- XBLite : http://www.xblite.com/
- XHarbour : http://www.xharbour.org/
Alla esimerkkinä XHarbourin visuaalisella työkalulla tehty toteutus:
GLOBAL AppCaption GLOBAL Roll #include "vxh.ch" #include "MyForm.xfm" #translate xCRLF => CHR(13) + CHR(10) //---------------------------------------- End of system code ----------------------------------------// METHOD ButtonSpin_OnClick( Sender ) CLASS MyForm Roll := .T. ::MyTimer:Start() ::Mytimer2:Start() RETURN Self METHOD MyTimer_OnTimeOut( Sender ) CLASS MyForm LOCAL nNumbers := "01234" ::LabelSlot1:Caption := nNumbers[HB_RANDOM(1, LEN(nNumbers))] ::LabelSlot2:Caption := nNumbers[HB_RANDOM(1, LEN(nNumbers))] ::LabelSlot3:Caption := nNumbers[HB_RANDOM(1, LEN(nNumbers))] IF Roll == .F. ::MyTimer:Stop() ::MyTimer2:Stop() IF ::LabelSlot1:Caption == ::LabelSlot2:Caption .AND. ::LabelSlot1:Caption == ::LabelSlot3:Caption IF ::MessageBox( "Onnittelut!" + xCRLF + xCRLF + "Haluatko pelata uudelleen?", AppCaption, MB_YESNO + MB_ICONQUESTION) == 6 Roll := .T. ::MyTimer:Start() ::MyTimer2:Start() END ELSEIF ::LabelSlot1:Caption == ::LabelSlot2:Caption .OR. ::LabelSlot1:Caption == ::LabelSlot3:Caption .OR. ::LabelSlot2:Caption == ::LabelSlot3:Caption IF ::MessageBox( "Melkein!" + xCRLF + xCRLF + "Haluatko pelata uudelleen?", AppCaption, MB_YESNO + MB_ICONQUESTION) == 6 Roll := .T. ::MyTimer:Start() ::MyTimer2:Start() END ELSE IF ::MessageBox( "Harmi!" + xCRLF + xCRLF + "Haluatko pelata uudelleen?", AppCaption, MB_YESNO + MB_ICONQUESTION) == 6 Roll := .T. ::MyTimer:Start() ::MyTimer2:Start() END END END RETURN Self METHOD MyTimer2_OnTimeOut( Sender ) CLASS MyForm Roll := .F. RETURN Self //-- INITIALISE SAMPLE -------------------------------------------------------------------------------// METHOD MyForm_OnLoad( Sender ) CLASS MyForm // SAMPLE DETAILS AppCaption := "Testi" ::Caption := AppCaption RETURN Self
Metabolix kirjoitti:
Tästä jää väkisinkin sellainen kuva, ettet edes halua oppia ohjelmoimaan, haluat vain saada tekeleesi valmiiksi.
Haluan oppia! Tosin, nyt äsken minulle ehdotettiin (taas) uutta kieltä tämän toteuttamiseen. Minulla ei ole koskaan ollut näin suuri halu oppia ohjelmointikieltä nettisivupuolen kielten lisäksi (olisihan se silti mukava saada peli valmiiksi).
Ei auta, että luen C++-oppaan monta kertaa läpi, kun osaan nämä asiat jo mitä siellä opetetaan. Hedelmäpelin tekemisessä käytetään vähän "laajempaa" C++.
MIB kirjoitti:
Ei auta, että luen C++-oppaan monta kertaa läpi, kun osaan nämä asiat jo mitä siellä opetetaan. Hedelmäpelin tekemisessä käytetään vähän "laajempaa" C++.
Ei siinä ole mitään sen "laajempaa". Ainoastaan se on erona että et voi suoraan kopioida oppaiden esimerkkejä, vaan joudut soveltamaan niistä opittuja taitoja. Osaaminen ei ole sitä että osaat tehdä täsmälleen samanlaisia ohjelmia kuin oppaiden esimerkeissä, vaan sitä että ymmärrät ne ja osaat soveltaa omissa projekteissasi.
MIB kirjoitti:
Koska pitäisi saada jpg kuvia peliin, niin laitoin SDL_LoadBMP() -> IMG_Load(). Tämä nähtävästi vaatii sdl_image lisäkirjaston. Latasin sen SDL:n sivuilta ja laitoin includet Code::Blocksin include kansioon ja lib tiedostot kopioin projektikansioon että toimivat muillakin. Ei kuitenkaan lähetenyt toimimaan.
Virheilmoituksesta päätellen laitoit polut väärin. Ilmeisesti laitoit includeihin sdl_imagen polun ja nyt yrität etsiä sitä sen polun takaa SDL-hakemistosta mitä siellä ei ole. Tarkistapa vielä ne polut. Libit ei tarvitse olla projektikansiossa, kunhan linkkerille on kerrottu mistä kansiosta niitä haetaan.
Opettele lukemaan niitä kääntäjän ja linkkerin virheilmoituksia. Iden helpistä ja googlesta löytyy virheilmoituksista tajuntaa laajentavaa tietoa. Olet nyt jo moneen kertaan kysynyt apua täsmälleen samalle virheilmoitukselle, joka kerta kun sellainen esiintyy.
MIB kirjoitti:
Ei auta, että luen C++-oppaan monta kertaa läpi, kun osaan nämä asiat jo mitä siellä opetetaan. Hedelmäpelin tekemisessä käytetään vähän "laajempaa" C++.
Teuro vastasi yllä aivan oikein: osaaminen ja ymmärtäminen on aivan eri asia kuin se, että vain muistat ulkoa nuo rakenteet. Tämänkin ketjun kysymyksistä päätellen et osaa juuri mitään; miksi esimerkiksi sen space-ongelman korjaaminen oli niin vaikeaa?
Vilkaisepa tätä matopeliä. Koodista ei kannata ottaa mallia: pääasia oli tuolloin saada nopeasti aikaan toimiva versio, jonka voi sitten heittää roskiin. (Enpä sitten heittänytkään, kun tuli niin hauska.) Peli on tehty C++-oppaan tiedoilla yhtä kohtaa lukuun ottamatta, ja senkin voisi korvata tavallisella funktiolla (edit: ja nyt on korvattu). Lisäksi on tietysti käytetty SDL:ää ja matematiikkafunktioita, joista ei kerrota oppaassa, mutta ne toimivat aivan kuten muutkin funktiot, joten niitä ei tarvitse erikseen opetella, vaan ne voi etsiä jostakin funktiolistasta.
Joten lakkaahan valittamasta laajemmista tiedoista ja ryhdy järjestelmällisesti opettelemaan asioiden soveltamista omiin tarkoituksiisi. Aloita vaikka siitä tekstipohjaisesta hedelmäpelistä.
Ei myöskään ole olennaisesti eroa sillä, osaatko ohjelmoida C++:lla vai PHP:llä; jos osaat yhdellä hyvin, osaat kyllä toisellakin edes kohtalaisesti. Niinpä suosittelen, että rupeat ahkerasti tekemään PHP-haasteen tehtäviä PHP:llä, ja lisäksi voisit harjoituksen vuoksi tehdä samantapaisia asioita myös C++:lla. Voit vaikka tehdä ohjelmat niin, että kirjoitat alkuarvot valmiiksi koodiin:
#include <iostream> int main() { const int taulukko[] = {2, 6, 7, 3}; const int maara = 4; // Tehtävä: laske ja tulosta lukujen summa. }
Valitse tähän tarkoitukseen PHP-haasteesta joitakin tehtäviä, ratkaise ne ensin PHP:llä, tee sitten tähän tapaan C++-ohjelma ja tarkista muutamalla syötteellä, että se toimii samoin kuin PHP-versio.
Menee nyt tästä hedelmäpeliaiheesta ohi, mutta...
legu@turbokone:~/Koodaus/metabolixin_matopeli$ g++ matopeli.cpp -o matopeli `sdl-config --cflags --libs` -lSDL_gfx matopeli.cpp: In function ‘int main(int, char**)’: matopeli.cpp:542: error: ‘time’ was not declared in this scope
Matopelistä on jäänyt näköjään ctime:n sisällyttäminen pois, eikä GCC sitä ainakaan suostunut pyöräyttämään binääriä ilman sitä. Ihan siltä varalta ilmoitin, että mikäli vaikkapa MIB haluaa sen kääntää ja törmää tuohon virheeseen, niin siitä ei enää erikseen tarvitse kysymystä lähettää.
Legu kirjoitti:
Matopelistä on jäänyt näköjään ctime:n sisällyttäminen pois...
Aikoinaan Ubuntussa toimi ilmankin. Korjasin tämän, ja lisäksi muutin koodista ne harvat kohdat, joissa käytettiin ominaisuuksia, joita C++-oppaassa ei ole vielä käsitelty. Nyt siis koko koodin voi ymmärtää C++-oppaan nykyisten osien perusteella. (Lisäksi pitää ymmärtää käytetyt SDL:n funktiot ja parissa maagisessa kohdassa hieman SDL:n sielunelämää ja pikselinviilauksen saloja.)
Opetuksen vuoksi voin listata tähän koodin huonoja puolia:
Kaksi ensimmäistä kohtaa selittyvät osittain sillä, että tein peliä ensin C:llä johonkin asti, ja lisäksi poistin äsken viimeisetkin rippeet siitä hienommasta koodista, jotta näkyisi, ettei sitä tarvita. Loput taas johtuvat siitä, että koodia ei ole tarkoitettukaan hienoksi ja kehittyväksi vaan pikaiseksi kokeiluksi.
Matopelistä sen verran, että sivuiltasi lataamani SDL.dll on jotenkin hassu. Käynnistäessäni pelin Windows lennättää ruudulle virheen: Proseduurin aloituskohtaa SDL_strlcat ei löydy dynaamisesti linkitettävästä kirjastosta SDL.dll. Virhe korjaantuu lataamalla SDL:n sivuilta SDL.dll Windowsille suunnatusta runtime-pakkauksesta.
Toimiva dll-tiedosto on n. 100 kilotavua Metabolixin jakamaa suurempi, mikä kaiketi heijastaa ongelmaa.
tgunner kirjoitti:
Matopelistä sen verran, että sivuiltasi lataamani SDL.dll on jotenkin hassu. ... Toimiva dll-tiedosto on n. 100 kilotavua Metabolixin jakamaa suurempi, mikä kaiketi heijastaa ongelmaa.
O_o Myönnän, etten ole testannut asiaa kolmeen vuoteen, mutta kyllä se ainakin silloin vielä toimi. Täytynee päivittää toimiva SDL.dll tuon tilalle, miten lie hajonnut... (Nyt pitäisi olla kunnossa.)
Aihe on jo aika vanha, joten et voi enää vastata siihen.