2012-06-13 4 views
5

Sto facendo un programma con l'SDK, dove quando gli utenti vengono rilevati, il programma disegna uno scheletro per loro da seguire. Recentemente ho visto un gioco pubblicizzato sul mio Xbox, Nike+ Kinect e ho visto come si visualizza una copia del personaggio fare qualcos'altro come:Point-Cloud of Body con Kinect SDK

http://www.swaggerseek.com/wp-content/uploads/2012/06/fcb69__xboxkinect1.jpg

O

http://www.swaggerseek.com/wp-content/uploads/2012/06/fcb69__xboxkinect.jpg

Posso creare un punto di -presente la rappresentazione della sola persona rilevata (non di uno sfondo)? Grazie in anticipo!


EDIT

Utilizzando this site, posso creare nuvole di punti, ma ancora non può ritagliare intorno al corpo della persona.

risposta

5

Non sembra che stiano visualizzando una nuvola di punti completa ma piuttosto una mappa di intensità ombreggiata in blu. Questo potrebbe essere fatto con l'immagine di profondità dal sdk di Kinect per Windows. Quello che stai cercando è l'indice del giocatore. Questo è un bit fornito in ciascun pixel dell'immagine di profondità. Per ottenere il bit di indice del giocatore devi abilitare anche il flusso scheletrico nel codice di inizializzazione.

Quindi questo è come lo farei. Sto modificando uno dei Kinect per Windows Quickstarts SDK trovato here carico su e apportare le seguenti modifiche:

//Change image type to BGRA32 
image1.Source = 
       BitmapSource.Create(depthFrame.Width, depthFrame.Height, 
       96, 96, PixelFormats.Bgra32, null, pixels, stride); 

     //hardcoded locations to Blue, Green, Red, Alpha (BGRA) index positions  
     const int BlueIndex = 0; 
     const int GreenIndex = 1; 
     const int RedIndex = 2; 
     const int AlphaIndex = 3; 

//get player and depth at pixel 
int player = rawDepthData[depthIndex] & DepthImageFrame.PlayerIndexBitmask; 
int depth = rawDepthData[depthIndex] >> DepthImageFrame.PlayerIndexBitmaskWidth; 

//check each pixel for player, if player is blue intensity. 

      if (player > 0) 
      { 
       pixels[colorIndex + BlueIndex] = 255; 
       pixels[colorIndex + GreenIndex] = intensity; 
       pixels[colorIndex + RedIndex] = intensity; 
       pixels[colorIndex + AlphaIndex] = 100; 

      } 
      else 
      { 
       //if not player make black and transparent 
       pixels[colorIndex + BlueIndex] = 000; 
       pixels[colorIndex + GreenIndex] = 000; 
       pixels[colorIndex + RedIndex] = 000; 
       pixels[colorIndex + AlphaIndex] = 0; 
      } 

Mi piace usare questo esempio per testare i colori in quanto ancora vi fornisce lo spettatore di profondità sulla destra lato.Ho allegato un'immagine di questo effetto che scorre sotto:

enter image description here

L'immagine a sinistra è la mappa intensità con dati leggermente colorate intensità livello di pixel.

Speranza che aiuta David Bates

+2

Dopo aver considerato l'effetto a livello di pixel. Per ogni altro pixel è possibile aumentare l'intensità in modo da ottenere l'effetto sparkle mostrato sull'immagine campione. Basta dire :) – davidbates

+0

Cool! Molte grazie! –

2

Questo non è possibile automaticamente con Kinect SDK ufficiale. Ma è implementato in SDK alternativo chiamato OpenNI, lì si può semplicemente ottenere l'insieme di punti in cui consiste l'utente. Se non vuoi usarlo, posso suggerire un metodo piuttosto semplice per separare l'utente dallo sfondo. Dato che conosci la posizione z dell'utente, puoi semplicemente prendere dei punti che z è da 0 a userZ + un valore che rappresenta lo spessore del corpo.

Un'altra idea è calpestare la nuvola di punti partendo da un giunto (o giunti) e prendendo punti solo se la distanza cambia senza intoppi, perché se si prende il punto di sfondo, il corpo del bordo e il prossimo punto del corpo la distanza sarà facilmente visibile. Il problema qui è che inizierai a contare il pavimento come parte del corpo, perché la transizione è liscia, quindi dovresti convalidarla usando l'articolazione più bassa (caviglia).

Oppure è possibile utilizzare la segmentazione in PCL (http://docs.pointclouds.org/trunk/group__segmentation.html) ma non so se il problema del piedino è risolto lì. Sembra che stiano bene con questo (http://pointclouds.org/documentation/tutorials/planar_segmentation.php).

+0

Sì dispiace controllare le modifiche, e posso avere un esempio? –

+0

@OutlawLemur per PCL c'è il collegamento al tutorial. Se decidi di implementarlo da solo, non può esserci un esempio, è un compito da risolvere. – Andrey

0

Kinect per Windows SDK v1.5 ha un esempio che potrebbe essere modificato per questo.

Nome di esempio: profondità-d3d o profondità con colore-d3d.

Entrambi fanno nuvole di punti.

+0

Non posso fare a meno di notare che sono entrambi esempi C++, sto usando C# –

+1

Sembra che questo pezzo non sia stato portato su SDK gestito – Andrey

6

Si può fare una semplice triangolazione dei punti. Controllare questo tutorial:

http://www.riemers.net/eng/Tutorials/XNA/Csharp/Series1/Terrain_basics.php

controllare il risultato:

enter image description here

+0

Molto bello. potresti pubblicare il progetto attuale o come stai mappando dalla profondità ai triangoli? Il tutorial crea una griglia statica ma non parla sulla mappatura. – davidbates

+0

È semplice. Ogni pixel nella profondità diventa un vertice, X e Y è la posizione dei pixel e Z è la profondità. Quindi usando il metodo su quel tutorial crei gli indici dei triangoli. – EdgarT

+0

Ecco la funzione per creare i triangoli. È un codice piuttosto sporco, je je. http://paste.ideaslabs.com/show/wUQpbnvU5T – EdgarT