The official Fatica Labs Blog! RSS 2.0
# Thursday, July 29, 2010

La cosa bella di saper programmare è che la vastità di cose che si possono fare non ha praticamente limiti. Uno dei task più divertenti è sicuramente la scrittura di un videogioco: si spazia dalla conoscenza pura di un linguaggio, alla matematica 3d, all’arte e, ovviamente l’idea. La parte matematica, per chi si interessa dell’argomento, è ben definita, basta leggere uno o più classici, tra i quali segnalerei, per averne usato ed abusato OpenGL SuperBible, Mathematics for 3D Game Programming & Computer Graphics, ed altri che per legami con qualche particolare framework sono oggi anacronistici. Dal punto di vista artistico, un gioco ha texture, modelli suoni, musiche… tutte risorse facilmente reperibili, anche in Open Source, anche gratuitamente – se non si vuole fare un gioco da vendere – in rete. Il problema di quasi tutti i framework era che nessuno forniva metodi per caricare diversi tipi di “asset”. Fortunatamente questo gap è stato colmato da XNA Game Studio. Basato su DirectX – Direct3d è facile ed intuitivo da usare per chiunque abbia visto un po’ di grafica 3d, ma offre veramente dei grandi vantaggi in termini di import di risorse  (texture, suoni, modelli 3d in svariati formati, etc ). In pratica basta “compilare” l’asset e poi chiamare Load<tipodellasset>(“Nome”) ed il gioco è fatto.

Ciò detto, per fare un gioco ( che per il programmatore è più divertente che giocarlo ), serve un idea: o si fa il solito clone, o si trae ispirazione da qualcosa… nel mio caso, negli uffici di una delle ditte in cui ho lavorato, c’erano delle putrelle a vista: a qualcuno venne l’idea di lanciare una pallina da tennis e di bloccarla con bello stile nello spazio che la putrella crea con la sua doppia “T”. Al dil à dell’idiozia della cosa, e di quanto ancor più idiota sia pensare di creare un videogame con quell’argomento, ecco nascere “Putrella ! ( The Game)”. La stanza è un po’ claustrofobica, il monitor è anch’esso allietato dallo stesso videogame, quasi a citare una più famosa scena che compariva su un disco del 1969… 

Difficile da spiegare… ma vediamo qualche screenshot:

s1

Un bel freccione verde fosforescente per scegliere dove tirare la pallina. Per inciso la pallina è una mesh sferica disegnata con Milkshape, e la texture invece è gentilmente offerta da google maps. La strana scriita in greco sulla pallina invece…

Ovviamente si può modificare la posizione di lancio e anche lo “Ziembolo” che è un piemontesismo per dire “Spin”

 

 

 

 

s2

Beh, con lo spazio si decide la forza, e in altro a destra compare un decanewtonmetro un po’ old fashion: si tratta in realtà di una immagine di un milliamperometro corretta, la lancetta invece è una texture di una linea che viene fatta ruotare per simulare uno strumento analogico. Con due stupidaggini l’effetto è alquanto realistico.

 

 

 

 

s2a

Non sempre si fa putrella, anzi per la verità non lo si fa quasi mai: di solito la pallina cade, fa qualche rimbalzo e la storia finisce li… Già, ma come rimbalza una pallina ? Per questo ci viene in aiuto quello che si chiama engine fisico, ovvero uno strumento software che ci permette di simulare un mondo di corpi rigidi, data una descrizione del suo stato iniziale e delle forze applicate ai vari elementi. Io ho scelto OOPS. In realtà è ancora un progetto giovane, ha qualche problemino, ma è fully managed, facilissimo da usare, e per quello che dovevo fare bastava. Come è modellato il mondo ? Niente di speciale, la pallina è, nella “lingua” di OOPS una CollisionSphere, I muri sono dei CollisionPlane, e tutto il resto, putrella compresa, delle CollisionMesh. Ah, dimenticavo, la putrella l’ho disegnata con MilkShape, mentre le altre paccottiglie ( sedia, scrivania, computer ) sono modelli free presi in rete.

 

s4

 

E’ difficile fare putrella, un po’ più facile è fare il cesto ( bin ). Anche questo è fatto con MilkShape. Visto che Milkshape non supporta la CSG ( Constructive Solid Geometry, ammazza che parolone ) bisogna ingegnarsi , facciamo due tronchi di cono, li infiliamo uno dentro l’altro, e a quello + interno cambiamo l’ordine dei vertici, semplice e banale, nonchè funzionante.

 

 

 

s3

Ancorchè difficile, prima o poi ci si riesce. Ma chi cambia l’inquadratura ? Molto semplicemente, quando la pallina rallenta, la Camera ( anche qui un concetto 3D, la camera è l’unione della ViewMatrix e della ProjectionMatrix ) da fissa si trasforma in una chasing camera. Per evitare movimenti troppo bruschi, I vettori sono interpolati in modo da avere una prospettiva che gradualmente si avvicina alla palla.

 

 

 

 

Bene in pratica cosa ho dovuto scrivere per fare questo gioco ? Molto, molto poco. Sempre di più nella programmazione bisogna saper scegliere e fare leva sulle cose buone già costruite, ed aggiungere un piccolo contributo di qualità, che altri possano usare. In questo caso la cosa che ho aggiunto penso possa essere questa.

Thursday, July 29, 2010 10:24:17 PM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
Games | XNA
# Monday, July 26, 2010

José F. Romaniello started an addin project to allow HQL editing with intellisense and sintax Highligting from inside Visual Studio 2010. I’m very interested in it, expecially to see how he solve ( or he will solve ) the problem of providing code completion facilities.

Monday, July 26, 2010 11:16:03 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback

# Tuesday, July 20, 2010

After a bug report, I solved an issue on db2hbm in command line parsing. The binary with the fixed issue are  located here.

no-bugs

here is the thread about the bug report.

Tuesday, July 20, 2010 9:14:37 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback

# Wednesday, July 14, 2010

Apprendo da questo post di Fabio Maulo una interessante feature di NHibernate 3 implementata nel nuovo subset di API: QueryOver. Il post di Fabio approfondisce il pattern Query Object, e quello che salta all’occhio è la pulizia con cui si riesca finalmemte a farte un paging “ad arte”. Per fare l’accesso paginato in generale occorre avere il count delle righe che il sistema vorrebbe tornarci, e questo constringeva in passato a fare delle implementazioni un po’ sporche in cui si era costretti a specificare la query di selezione e quella di count. QueryOver propone la funzione query.ToRowCountQuery(); – dove query è appunto una query di QueryOver, e la funzione ci restituisce la query di conteggio in modo pulito e trasparente. Assolutamente molto utile. Io non sono uno da trunk, ma una funzione del genere mi fa venire voglia di passare subito a NH3, ancor prima che venga rilasciata la GA.

Wednesday, July 14, 2010 8:50:20 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
NHibernate
# Monday, July 05, 2010

A volte si vuole ottenere l amedesima configurazione di logging per log con diverso nome, accomunati da una radice: xEs se usiamo NHibernate avremo NHibernate.Cfg.XmlHbmBinding,NHibernate.Cfg.Configuration, NHibernate.Cfg.SettingsFactory, NHibernate.Dialect.Dialect … e via discorrendo. E’ bello sapere che log4net supporta una gerarchia tra logger, e che questa è implicata dal nome: se voglio, per esempio, per tutti i logger di NH loggare solo i messaggi di fatal error posso scrivere:

<logger name="NHibernate" >
    <level value="FATAL" />
  </logger>

 

Ed tutti i logger NHibernate.* cadranno in questo caso. Ovviamente lo stesso lo posso fare con una sotto gerarchia, per esempio con name=”NHibernate.Cfg” riferirò tutti i log di configurazione.

Buono a sapersi, anche per quando si decidono i nomi dei logger nelle proprie applicazioni.

Monday, July 05, 2010 10:56:00 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
log4net
# Thursday, June 24, 2010

L’accesso in scrittura ad un dictionary non è thread safe. In generale, se si utilizza un Dictionary<TKey,TValue> in .NET bisognerebbe loccare le operazioni di scrittura, e quelle di lettura se si suppone ci possano essere delle scritture/cancellazioni concomitanti. Tuttavia, utilizzare in modo “cieco” il lock, sia per le scritture che per le letture può avere dei decrementi di velocità. Ho trovato un’ottima e riconosciuta implementazione di un dictionary thread safe a questo indirizzo.

Thursday, June 24, 2010 8:28:17 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback

# Wednesday, June 23, 2010

Bene, skill richiesti per fare l’architetto in una nota società di consulenza ( non diciamo quale, che tanto si indovina ) eccoli qui:

image

Vediamoli un po’:

Deep experience with PowerPoint: e certo, se devo fare un’architettura, il tool primario che uso è proprio power point.

Deep experience with MS Excel modeling: ma santa polenta: Excel è un foglio di calcolo, cosa cavolo ci modello con excel ? Excel serve a fare i conti, anche se il 100% dei manager lo usa perchè ha delle caselle.

Le altre lasciamo perdere, ci stanno: quindi per essere un architetto in sta famosa ditta di consuleza devo conoscere PowerPoint ( Che sfida !!! ), e saper usare in modo improprio Excel. Che vergogna.

Wednesday, June 23, 2010 2:36:09 PM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback

# Monday, June 21, 2010

Well, since no feedback from the users, I decided to abandon the project NHModeller. It was an attempt to create a commercial tool for NH, without any interesting returns. If someone is interested to have the source and continue the project please contact me. The project is now replaced by the new NHibernate Workbench, that is open source.

Monday, June 21, 2010 8:03:01 AM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
Code GEneration | NHModeller
# Wednesday, June 16, 2010

Probabilmente vi sarà capitato di dovere eseguire qualche azione all’interno del vostro software dipendentemente da trigger innescati da data e/o ora. Per esempio un certo processo non si scatena del week-end, oppure un altro processo deve partire solo a mezzanotte etc etc. Quando queste cose non siano attuabili esternamente con il task scheduler di sistema, sarebbe bello poter avere una libreria pronto uso in .NET. Ebbene questa libreria c’è, ed è il parser di espressioni Cron che trovate qui. Lungi dall’essere un concetto moderno, si tratta di un modo di esprimere range temporali tramite una stringa che arriva da Unix. Oggi chiamiamo una cosa simile “Domain Specific Language”, ma tant’è il concetto è il medesimo. Lungi anche dall’ essere originale il concetto in .NET, la libreria che propongo è una estrapolazione di codice dalla più completa e complessa libreria Quartz.NET, a sua volta un porting della libreria Java Quartz. Se non volete introdurre troppa complessità al vostro deploy aggiungendo una nuova libreria, potete “grabbare” le classi dalla dll di Cron.NET ( sono tre file… ) e compilarli con il vostro progetto, ed avrete a disposizione tutta la potenza delle espressioni Cron ;).

Già, ma come funzionano le espressioni Cron ? Facciamo un paio di esempi:

"* * 10-11 L * ?" = questo trigger è valido l’ultimo del mese dalle 10-11

"* * * ? * MON-FRI" = questo trigger è valido tutti i giorni, a tutte le ore, eccetto il week end.

Ok, questo da l’idea delle potezialità della cosa, ma ovviamente serivirebbe una più estesa…

Documentazione

Una espressione Cron è composta da 6 campi obbligatori, più uno opzionale. Il significato dei campi è schematizzato nella tabella qui sotto:

Campo   Valori permessi   Caratteri speciali ammessi
Secondi   0-59   , - /
Minuti   0-59   , - /
Ore   0-23   , - /
Giorno del mese   1-31   , - ? / L W C
Mese   1-12 or JAN-DEC   , - /
Giorno della settimana   1-7 or SUN-SAT   , - ? / L #
Anno ( Opzionale )   vuoto, 1970-2099   , - /

 

Il carattere jolly ‘*’ può sempre essere usato con il significato di “tutti i valori”, per esempio se metto ‘*’ nel campo minuti significa tutti i minuti.

Il carattere ‘?’ può essere usato solo come Giorno del mese o giorno della settimana. Significa “nessun valore in particolare” e serve quando devo fissare l’altro. Se per esempio fisso il giorno della settimana metterò ‘?’ nel giorno del mese, e viceversa.

Il carattere ‘-‘ lo utilizzo quando voglio specificare un range: per esempio 10-12 nel campo ora significa dalle 10 a tutte le 12.

Uso invece la ‘,’ quando voglio specificare singolarmente più valori possibili: JAN,MAR significa il mese di Gennaio e di Marzo, ma non Febbraio ( e, ovviamente, non tutti gli altri ).

Per specificare dei periodi utilizzo ‘/’: per esempio se metto 0/15 nel campo secondi, significa “ogni 15 secondi”: sarà attivo il trigger quindi ai secondi 15,30,45 etc etc.

Il carattere speciale ‘L’ significa ultimo. Nel campo mese significa semplicemente l’ultimo giorno del mese (30/31/28 o 29 ) in modo concorde con il mese / anno bisestile. Nel campo settimana significa semplicemente 7 ( cioè Sabato ), ma se preceduto da un numero significa “l’ultimo xxxx del mese”. Per esempio se scrivo 6L significa l’ultimo Venerdì del mese.

Il carettere ‘W’ può essere specificato solo nel campo giorno del mese, preceduto da un solo carattere, e significa “il giorno lavorativo più vicino a”. Per esempio se scrivo 1W significa il giorno lavorativo più vicino al primo del mese. Se scrivo LW significa l’ultimo giorno lavorativo del mese.

Per ultimo il carattere ‘#’, utilizzabile solo nel giorno della settimana, indica l’ennesimo xxxx del mese. Per esempio, se mi interessa il terzo venerdì del mese, scriverò 6#3.

Per utilizzare una cron expression basta creare un istanza dell’ogegtto CronExpression, passando la stringa sul costruttore. Ecco un esempio:

   1:          [Test]
   2:          public void LastOfTheMonth()
   3:          {
   4:              var exp = new CronExpression("* * * L * ?");
   5:              Assert.IsTrue(exp.IsSatisfiedBy(new DateTime(2000, 1, 31)));
   6:              Assert.IsTrue(exp.IsSatisfiedBy(new DateTime(2000, 2, 29)));
   7:              Assert.IsFalse(exp.IsSatisfiedBy(new DateTime(2000, 2, 28)));
   8:          }
Wednesday, June 16, 2010 4:52:39 PM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
Cron | Programmin | Recipes
# Monday, June 14, 2010

bug The right place for bug reporting or requiring additional features is

here

Since the project is new, it is normal to have something to fix. The problem is that my testing would just be not sufficient, so your help will really be appreciated. Thanks!

Monday, June 14, 2010 4:31:59 PM (GMT Daylight Time, UTC+01:00)  #    Comments [0] - Trackback
Code GEneration | NHibernate | NHWorkBench
Archive
<July 2010>
SunMonTueWedThuFriSat
27282930123
45678910
11121314151617
18192021222324
25262728293031
1234567
About the author/Disclaimer

Disclaimer
The opinions expressed herein are my own personal opinions and do not represent my employer's view in any way.

© Copyright 2010
Felice Pollano
Sign In
Statistics
Total Posts: 67
This Year: 41
This Month: 2
This Week: 0
Comments: 36
This blog visits
Locations of visitors to this page
All Content © 2010, Felice Pollano
DasBlog theme 'Business' created by Christoph De Baene (delarou) and modified by Felice Pollano