The Xna-Way: Tutorial 15: Utente collegato ed X-Box Live pt2 L'Avatar

Questa volta vi voglio parlare un poco degli Avatar degli utenti.
Come sapete è possibile creare e personalizzare il proprio Avatar, sia attraverso la console, sia attraverso il sito di X-Box live.
Voglio farvi vedere come si può, con poche righe di codice, renderizzare il proprio Avatar :)

NOTA: il codice per la gestione degli Avatar può essere fatto girare anche sotto Windows 7 (e mi pare che per i Phone, ma non avendo un tale dispositivo non ne sono sicuro), solo che in tal caso i valori ritornati dalle varie funzioni non saranno validi, e quindi non verrà renderizzato nulla.
In parole povere, GLI AVATAR SONO ESCULISA DELLA CONSOLE!

In parte riutilizzerò il codice scritto nel precedente articolo.
Nella classe del gioco aggiungiamo questi 3 campi:
   1:          AvatarDescription avatarDescription;
   2:          AvatarRenderer avatarRenderer;        
   3:          AvatarAnimation avatarAnimation;
   4:          AvatarRenderer avatarRenderer2;
   5:          AvatarDescription avatarDescription2;
che rappresentano la descrizione di come è fatto il nostro Avatar (in parole povere la descrizione fisica), l'oggetto che utilizzeremo per renderizzare il nostro Avatar, l'animazione corrente che stiamo riproducendo, ed infine l'enumeratore che indica quale delle animazioni preimpostate vogliamo usare.
Gli ultimi due oggetti, avatarRender2 ed avatarDescription2, serviranno per renderizzare e contenere un Avatar creato in modo random, in modo che alla fine del nostro esempio avremo a schermo il proprio Avatar ed un altro Avatar in più.
Avremo naturalmente bisogno di mantenere i dati del giocatore attualmente loggato (rivedere articolo precedente).

Nel LoadContent del game aggiungiamo questo:
   1:              avatarDescription2 = AvatarDescription.CreateRandom(AvatarBodyType.Female);
   2:              avatarRenderer2 = new AvatarRenderer(avatarDescription2);
   3:   
   4:              avatarAnimation = new AvatarAnimation(preset);
Le prime due righe creano un avatar casuale (femminile) ed un renderer basato sulla descrizione dell'Avatar appena creata.
La terza riga imposta l'animazione con il preset definito come campo della classe.

Ci servirà poi un metodo per il recupero in modo asincrono dei dati dell'Avatar, che può essere il seguente:
   1:          void LoadMyAvatar(IAsyncResult result)
   2:          {
   3:              avatarDescription = AvatarDescription.EndGetFromGamer(result);
   4:   
   5:              if (avatarDescription.IsValid)
   6:                  avatarRenderer = new AvatarRenderer(avatarDescription);
   7:          }
Questo perchè per caricare la descrizione dell'Avatar dobbiamo chiamare il metodo AvatarDescription.BeginGetFromGamer, il quale lavora in metodo asincrono (quindi la sua esecuzione non si blocca in attesa del suo completamento) e può richiedere diverso tempo per essere completato. Quando il metodo avrò completato la sua esecuzione chiamerà il metodo da noi definito per completare le operazioni.
Per mettere tutto assieme aggiungiamo alla fine del metoto LoadContent questo:
   1:              gamer = SignedInGamer.SignedInGamers[0];
   2:              if (gamer != null)
   3:                  AvatarDescription.BeginGetFromGamer(gamer, LoadMyAvatar, null);
che non fa altro che provare a recuperare i dati del giocatore loggato, ed avvia il recupero dei dati dell'Avatar.

Nel metodo update le uniche cose da mettere sono queste:

Ci manca solo il Draw:
GraphicsDevice.Clear(Color.CornflowerBlue);
 
//creo la matrix per la view
Matrix view = Matrix.CreateLookAt(new Vector3(0, 0.3f, -3), new Vector3(0, 0, 0), new Vector3(0, 1, 0));
//creo la matrix per la projection
Matrix projection = Matrix.CreatePerspectiveFieldOfView(MathHelper.PiOver4, GraphicsDevice.Viewport.AspectRatio, .01f, 40.0f);
 
if (avatarRenderer != null && gamer != null)
{
avatarRenderer.View = view;
avatarRenderer.Projection = projection;
avatarRenderer.World = Matrix.CreateTranslation(-1, -1, 0);
avatarRenderer.Draw(avatarAnimation.BoneTransforms, avatarAnimation.Expression);
}
 
if (avatarRenderer2 != null && avatarDescription2.IsValid)
{
avatarRenderer2.View = view;
avatarRenderer2.Projection = projection;
avatarRenderer2.World = Matrix.CreateTranslation(1, -1, 0);
avatarRenderer2.Draw(avatarAnimation.BoneTransforms, avatarAnimation.Expression);
}
 
spriteBatch.Begin(SpriteSortMode.Immediate, BlendState.AlphaBlend);
if (gamer != null)
{
spriteBatch.DrawString(myFont, gamer.Gamertag, Vector2.Zero, Color.Black);
spriteBatch.Draw(image, new Vector2(0, 30), Color.White);
spriteBatch.DrawString(myFont, String.Format("Current Animation: {0}", preset.ToString()), new Vector2(0, 100),
Color.Black);
}
spriteBatch.End();
Prima creiamo la view e la projection per il render, controlliamo che il giocatore loggato, il renderer e l'animazione siano validi, e poi renderiziamo il tutto.
Poi ripetiamo anche per l'Avatar random.
Alla fine, come nel precedente articolo, si visualizza il nome della nostra gamer tag, la nostra immagine e poi si stampa il nome dell'animazione che stiamo riproducendo.

Ecco il codice completo sorgente del Game in questione:

Show∇


Sinceramente pensavo che sarebbe stato molto più difficile fare una cosa del genere, invece ho trovato tutto molto ben strutturato e semplificato.
Certo non ho ancora provato ad utilizzare le animazioni personalizzate per gli Avatart, o a fare il blend tra due animazioni... Ma quelle le vedrò in futuro!

Intanto ecco a voi uno screen di quello che vedo utilizzando il mio profilo: l'Avatar sulla destra è il mio, quello sulla sinistra è quello generato casualmente!



Alla prossima :)
Continua a leggere!

The Xna-Way: Tutorial 14: Utente collegato ed X-Box Live pt1 Dati di base

Oggi voglio condividere alcune cose che ho provato riguardo alla gestione degli utenti XBox Live, come riconoscere se un utente ha fatto login, se ha fatto logout, chi è attualmente loggato, e le sue informazioni.

Questa sarà la prima parte di considerazioni, dovuto al fatto che alcune funzionalità sono esclusive per X-Box 360, come al gestione degli Avatar.
Riporto quindi qua solo quanto provato sotto piattaforma Windows.

Il metodo più semplice per recuperare le informazioni sull'untente attualmente collegato è tramite il seguente codice:

   1:  SignedInGamer gamer1 = Gamer.SignedInGamers[PlayerIndex.One];
Scrivendo questo, chiediamo di recuperare l'oggetto SignedInGamer relativo al giocatore che sta utilizzando il gamepad numero 1 (cosa simile si può fare con gli altri gamepad, fino all'indice 4).
Questa classe ci fornisce tutti metodi necessari per recuperare le informazioni del nostro giocatore.
Il problema però sorge quando non c'è nessuno giocatore che ha fatto log-in. In questo caso il codice precedente ci fornirà un null.
Sulla console questo si verifica quando lanciamo un gioco in modalità "anonima" possiamo dire, senza aver selezionato cioè il profilo che vogliamo usare.

Ma come possiamo fare, su pc, ad poter fare una cosa simile?
NOTA: per poter far funzionare correttamente il codice che segue, il LiveID che utilizzerete per fare log-in deve avere a disposizione un account Studente o superiore su App Hub, altrimenti andrete contro a delle spiacevoli eccezioni.

La prima cosa da fare è di aggiungere un GamerServicesComponent al nostro gioco. Possiamo farlo all'interno del costruttore del nostro Game:

   1:  Components.Add(new GamerServicesComponent(this));

Il primo passo è fatto. Ora dobbiamo far si che quando si effettua il login di un account si deve recuperare i dati, tra cui per ora ci occuperemo del nome della GamerTag e dell'immagine associata.
Aggiungiamo i seguenti campi alla nostra classe:

   1:  SignedInGamer gamer;
   2:  Texture2D image;
così facendo abbiamo definito dove andremo a memorizzare i dati recuperati.

Abbiamo bisogno di registrare un EventHandler per recuperare i dati del profilo quando viene completata la fase di login. Ecco un esempio di come può essere fatto:

   1:          void LoadGamer(object sender, SignedInEventArgs e)
   2:          {
   3:              gamer = e.Gamer;
   4:              //recupero lo stream per l'immagine
   5:              System.IO.Stream imgIO = gamer.GetProfile().GetGamerPicture();
   6:              //creo la texture2D a partire dallo stream
   7:              image = Texture2D.FromStream(GraphicsDevice, imgIO);
   8:          }
mentre nel costruttore, dopo la creazione del GamerServicesComponent, andiamo a registrare il nostro handler come segue:
   1:  SignedInGamer.SignedIn += new EventHandler<SignedInEventArgs>(LoadGamer); 

Il nostro metodo Draw sarà semplicissimo!
   1:          protected override void Draw(GameTime gameTime)
   2:          {
   3:              GraphicsDevice.Clear(Color.CornflowerBlue);
   4:   
   5:              spriteBatch.Begin(SpriteSortMode.Immediate, BlendState.AlphaBlend);
   6:              if (gamer != null)
   7:              {
   8:                  spriteBatch.DrawString(myFont, gamer.Gamertag, Vector2.Zero, Color.Black);
   9:                  spriteBatch.Draw(image, new Vector2(0,30), Color.White);
  10:              }
  11:              spriteBatch.End();
  12:   
  13:              base.Draw(gameTime);
  14:          }

Ok vediamo di riassumere: creiamo il nostro EventHandler, il quale serve a recuperare i dati del Gamer che fa login (quindi la GamerTag, la sua immagine, i suoi Ack, la lista dei suoi amici, etc). Questo Handler viene chiamato quando il login viene completato con successo. E dopo di questo verrano visualizzate dal metodo Draw il nome della GamerTag e la sua immagine.

Ecco ora a voi alcuni screenshot! (sono relativi alla versione che ho fatto girare sotto Windows 7, quindi sulla console potrebbero essere "leggermente" differenti)
Una volta fatto partire il gioco premete il tastone centrale del vostro pad (o il tasto Home sulla tastiera). E quello che vedrete sarà più o meno questo:
Dopo che avrete accettato le condizioni d'uso, andate su "Accedi", dove avrete una schermata come la seguente:
Inserite i dati del vostro LiveID (che vi ricordo deve disporre di un account Studente o superiore su Abb Hup per essere provato con successo da chi scrive il codice), e avrete che inizierà la procedura di login (io ho anche spuntato l'opzione per fare in modo che ogni volta effettui l'accesso in automatico).
Quando il login sarà completo vi verrà notificato con un messaggio!
Se fate come me, e avete messo il login automatico dell'account (in modo da non dover rifare la procedura a mano ogni volta), se riavviate l'applicazione ed aspettate qualche secondo, ecco cosa vedrete (salvo GamerTag diversa XD):

Ora le basi ci sono! Potete sbizzarrirvi!

Spero di esservi stato utile!
A presto :)
Continua a leggere!

Donazioni

My Menu'