15/12: Executar un quadre de diàleg en Win32 i c++
Una de les coses a les que ens malacostuma l'assistent de programes Win32 de Visual Studio és a fer les coses més simples molt més complexes del que han de ser... Per això moltes vegades per no complicar-me la vida quan havia de fer un programa que només contingués un quadre de diàleg.
Una opció seria crear els controls en temps d'execució en la finestra principal, però sovint és massa feina per fer un programa simple.
El procediment que feia servir inicialment era fer servir l'assistent del Visual Studio per crear un projecte bàsic i en el WndProc() capturava el missatge WM_CREATE (que es rep abans de mostrar la finestra) i allà executava el quadre de diàleg i després matava el programa.
...
switch (message)
{
case WM_CREATE:
DialogBox(hInst, (LPCTSTR)IDD_DIALEG, hWnd, (DLGPROC)Dialeg);
PostQuitMessage(0);
break;
...
Això feia que es veiés només el quadre de diàleg i que el programa es morís abans de mostrar la finestra principal (recordo que en el moment en que es rep el WM_CREATE encara no tenim la finestra visible)
Però està clar que hi ha formes millors de fer-ho. Perquè crear una finestra principal si no ens fa falta?
Categoria: Programació | Fet per: Xavier | | Afegir comentari
15/12: Programació fent servir l'API Win32

- La biblioteca MFC (Microsoft Foundation Class) encapsula gran part de la API de Win32, encara que no tota i genera una jerarquia de classes en forma orientada a objectes. MFC ofereix classes que representen objectes fonamentals de Windows, com finestres, quadres de diàleg, pinzells, etc.. . Les funcions membre d'aquestes classes es fan servir per obtenir les funcions més importants de la API associades a l'objecte principal.
La biblioteca MFC tradicionalment es considera bastant lenta. - La biblioteca ATL (Active Template Library) és un subconjunt de classes de C++ basades en plantilles que faciliten la creació d'objectes petits i ràpids del model COM. ATL encapsula les API de Win32 i de la biblioteca de temps d'execució de C, però no tant com MFC. Es va crear perquè MFC feia massa grans els executables i això era un problema per Internet.
- La biblioteca WTL (Windows Template Library) és una llibreria que s'assembla a MFC però està basada en plantilles i és menys extensa (no té classes per a sockets o base de dades) . Afegeix la possibilitat de treballar amb finestres a ATL. Està alliberada sota llicència GPL per Microsoft
Però no sé perquè sento una mena de passió per programar amb C++ i cridant l'API de Windows directament. Segurament deu ser una reminiscència de quan vaig començar a programar per Windows. Quan jo vaig començar ho vaig fer, com molta gent, fent servir Visual Basic. D'aquella època el que en recordo més era el seu funcionament lent, i que això em desesperava tant que fins i tot hi havia vegades que redissenyava varies vegades els mateixos trossos de programa per intentar trobar formes de fer-los més ràpids.
En el moment en que em van encarregar un programa que havia de fer una petita animació per pantalla em va obligar a aprendre a fer els programes amb C. I el mateix programa fet amb C++ i MFC anava visiblement molt més de pressa que amb Visual Basic! Un cop entregat em vaig obligar a fer-lo fent servir C++ a pèl i només fer servir les crides a l'API... La velocitat era estratosfèrica...
Per això i perquè he vist que és difícil trobar-ne informació (Microsoft s'ha volcat completament en el .NET framework), si tinc temps, aniré posant uns quants articles basats en el que Microsoft anomena C++ non managed.
Per fer els exemples faré servir Visual Studio però no hi hauria d'haver cap problema per fer servir cap altre compilador que pugui compilar programes en Windows.
Categoria: Programació | Fet per: Xavier | | Afegir comentari
10/11: QtCreator a Ubuntu Intrepid Ibex
D'entre les llibreries per realitzar programes n'hi ha una que m'agrada especialment, Qt. Des de que la versió de Windows és lliure, fer programes amb les llibreries Qt ens permet desenvolupar programes amb un entorn gràfic multiplataforma de forma realment senzilla.Fins ara he estat fent servir KDevelop per fer els programes però la versió estable actual de KDevelop no és gaire amigable per desenvolupar programes fent servir Qt 4 (la propera versió de KDevelop 4 si que ho serà però pel meu gust està en un estat molt primerenc)

La instal·lació és realment senzilla. Es baixa el paquet autoinstal·lable de la seva web i simplement s'executa i es va responent a quin lloc el volem instal·lar. Una instal·lació més semblant a les de Windows que a les de Linux. Al acabar et deixa una icona a l'escriptori per poder-lo iniciar ràpidament

Al arrancar-lo es pot veure clarament que Nokia va comprar aquestes llibreries :-)

M'agrada de l'entorn la solució dels botons de debug i d'execució amb l'estat del projecte a sota a l'esquerra.
Categoria: Programació | Fet per: Xavier | | Afegir comentari
08/06: Fitxers de dades en KDevelop
Però amb el sistema de compilació/instal·lació de codi font més popular actualment, amb automake i autoconf, els usuaris estan acostumats a poder canviar el directori en el que s'instal·laran els fitxers (per exemple perquè no tenen permisos de root), això implica que definir el camí en un #define dins del nostre programa no és gaire bona idea.
Un usuari amb el configure pot definir en quin lloc s'instal·laran les dades en comptes de deixar el camí per defecte:
./configure --prefix=/home/federicu
Si fa això, el nostre executable ha de buscar les dades en el directori especificat en comptes de al directori per defecte!
Especificar el camí a les dades al compilar
Una forma interessant de solucionar això que permet Gnu C és la de definir constants en temps de compilació. D'aquesta forma si al compilar li passem el camí, l'executable no tindrà cap problema per trobar les dades independentment d'on s'hagin instal·lat.
Això es pot fer passant-li el valor al compilador amb el paràmetre -D. Vegem un exemple ràpid del que estic explicant:
Editem un fitxer prova.cpp amb el següent contingut:
#include
int main(int argc, char *argv[])
{
printf("%s\n",DIRECTORI);
return 0;
}
Com podeu veure, DIRECTORI no està definida en el codi font, per tant si compilem normalment ens dirà que no està definit. Però ara el compilem de la següent forma:
$ g++ -DDIRECTORI=\"/home/federicu/\" -o prova prova.cpp
Com podeu observar ara compila correctament i la execució d'aquest programa ens mostra el que hem especificat ("/home/federicu")
$ ./prova
/home/federicu/
$
Categoria: Programació | Fet per: Xavier | |
07/06: Empaquetat de codi font amb KDevelop

El programa que hem fet funciona molt bé des de dins del KDevelop (compila sense problemes) i fa l'empaquetat sense donar cap error, però quan intentem compilar el paquet generat falla estrepitosament en el make perquè per algun motiu no té en compte les llibreries que hem afegit nosaltres en les propietats del projecte.

És un problema amb el que ja m'hi havia trobat (i que encara em passa a la versió 3.4.1) però jo ja no hi faig gaire cas perquè ho soluciono mecànicament, però està clar que és un apartat que encara no està gaire ben solucionat i que als usuaris novells pot fer-los perdre els nervis.
La veritat és que es pot solucionar fàcilment.
1. Afegir la comprovació de les llibreries per l'autoconf
La idea general és que s'ha de donar la informació necessària a l'autoconf perquè sàpiga quines llibreries ens faran falta a l'hora de generar el make. (en concret li hem de dir quines llibreries hem de posar al enllaçar)
Per mi el més senzill és obrir el fitxer configure.in amb un editor de text i afegir-hi els paràmetres que fan referència a les llibreries. Això es pot fer amb qualsevol editor de texts normal, kate, gedit, ... però jo ho faig amb el millor editor del món, el joe (sempre havia volgut posar això a Internet :-))
$ cd projecte
$ joe configure.in
Per dir-li al autoconf que comprovi si una llibreria de desenvolupament està instal·lada en el sistema ho podem fer a través de la macro AC_CHECK_LIB. Aquesta macro ens permet fer dues coses: comprovar si l'usuari té instal·lades les llibreries necessàries o no ( i si posteriorment ens hi fixem al fer el "configure", veurem entre el piló de línies també hi surt la nostra) i afegir els paràmetres a la compilació.
El prototipus és el següent:
AC_CHECK_LIB(Llibreria,
funcio,
LIBS="$LIBS -lllibreria",
AC_MSG_ERROR([*** Missatge d'error!])
)
Posaré un exemple real per fer-ho menys pesat. Per exemple si volem que el configure comprovi si l'usuari té instal·lada la llibreria SDL_image i en el cas de que la tingui, afegeixi el paràmetre necessari per enllaçar el projecte, escriurem el següent:
AC_CHECK_LIB(SDL_image,
IMG_Load,
LIBS="$LIBS -lSDL_image",
AC_MSG_ERROR([*** SDL_image no trobada!])
)
En l'exemple IMG_Load és una funció de la llibreria SDL_image i pot ser canviada per qualsevol de les funcions que hi ha dins d'aquesta llibreria. A la variable LIB és allà on hem d'especificar el paràmetre d'enllaçat que necessita la llibreria i l'AC_MSG_ERROR és el missatge d'error que donarà el configure si falla perquè la llibreria no està instal·lada o la versió que té no té la funció que hem posat (jo poso els missatges d'error en català perquè sóc més xulo que ningú, però tothom els posa en anglès...)
Això ho hem de fer per totes les llibreries que el nostre projecte necessiti. O sigui una directiva AC_CHECK_LIB per cada llibreria que s'hagi d'incloure al compilar.
Només hem de vigilar una cosa: que afegim les línies abans de la línia AC_OUTPUT. Si afegim coses després d'aquesta no les farà perquè ja haurà generat el 'Makefile' abans de processar-les.

Categoria: Programació | Fet per: Xavier | |
28/05: Cenbubble en SDL
Es tracta d'una pràctica que he posat als alumnes i com que veia que no acabaven mai em vaig decidir a provar si realment era una cosa tan complicada. No hi he estat gaire, o sigui que ...Es un clon del joc Frozzen Bubble fet amb SDL però com podeu veure no he dedicat gaire estona als gràfics :-)
El deixo sota llicència GPL v2.
No he usat gaire les característiques dels objectes perquè els alumnes encara n'estan aprenent i l'objectiu era que entenguessin el codi.
També he sacrificat la optimització per facilitar la lectura o sigui que podeu millorar-lo fàcilment.

Per ara només té una sola pantalla que està en el fitxer pantalla0.txt i té la forma:
coordenadax coordenaday color
coordenadax coordenaday color
O sigui que és senzill fer-ne més...
Les llibreries de les que depèn el programa són SDL, SDL_image i SDL_gfx o sigui que per poder compilar-lo s'han d'instal·lar. Per exemple en Ubuntu he hagut de fer:
$ sudo apt-get install libsdl1.2-dev
$ sudo apt-get install libsdl-image1.2-dev
$ sudo apt-get install libsdl-gfx1.2-dev
Després per compilar el codi només cal fer el mateix de sempre:
$ tar xvfz cenbubble-0.1.tar.gz
$ cd cenbubble
$ ./configure
$ make
$ sudo make install
Com ja sabeu amb el configure es pot instal·lar el programa en qualsevol directori simplement especificant-lo com a prefix:
$ configure --prefix=/home/pepet
$ make
$ make install
Això farà que instal·li el binari a /home/pepet/bin i les dades a /home/pepet/cenbubble
No m'he entretingut a posar-lo en els menús de KDE o Google, o sigui que el podeu executar des de la consola amb:
$ cenbubble
Es pot desinstal·lar simplement des del mateix directori en que s'ha compilat el programa executant:
$ sudo make uninstall
Encara que jo només l'he fet en Linux s'hauria de poder compilar sense problemes amb la majoria dels compiladors de C++ en Windows amb les llibreries SDL especificades abans (SDL, SDL_Image i SDL_gfx).
* Crec que només s'hauria de definir el paràmetre que passo al compilador, per definir en quin directori són els gràfics i el fitxer de dades, que anomeno DATA_PREFIX (la millor forma normalment serà un #define DATA_PREFIX "C:\CamiALesDades").
Per descarregar-lo:
Categoria: Programació | Fet per: Xavier | | Afegir comentari


