[MY - AL] Subdivision de mesh en zones
Règles du forum
Merci de respecter la NOMENCLATURE suivante pour vos TITRES de messages :
Commencez par le niveau de vos scripts
DB = Débutant
MY = Moyen
CF = Confirmé
Puis le domaine d'application
-RS = Réseau
-AL = Algorithmie
Exemple :
[DB-RS] Mouvement perso multijoueur
Merci de respecter la NOMENCLATURE suivante pour vos TITRES de messages :
Commencez par le niveau de vos scripts
DB = Débutant
MY = Moyen
CF = Confirmé
Puis le domaine d'application
-RS = Réseau
-AL = Algorithmie
Exemple :
[DB-RS] Mouvement perso multijoueur
Re: [MY - AL] Subdivision de mesh en zones
Vraiment content que ça fonctionne sur ton projet.
C'est vrai que je n'avais pas trop optimisé mais plutôt écris à la vas vite.^^
Pour optimiser tu peux déjà commencer par baisser le nombre d'itération de recherche de centerZone. j'avais mis une grande valeur ne connaissant pas les données de ton mesh. tu peux réduire par palier de 100 et tester à chaque fois. dès que tu remarque des zones trop grandes par rapport à d'autre, remonte de 100 pour être garder une marge.
Pour la void FindCenter, tu peux gagner aussi un peu.la distance d'un centre a l'autre est calculée avec un Vector3.magnitude, pour que ta distance minimal soit une valeur en unité réel ( 1 c'est un mètre). Cependant pour juste de la comparaison de distance, il est plus rapide d'utiliser un Vector3.sqrtMagnitude qui est plus rapide. Mais dans ce cas bien penser a mettre au carré ta distance minimal. Par exemple pour des zones de 1.5, il faudra comparer les sqrtMagnitude avec 2.25. FindCenter(1.5f) => FindCenter(2.25f);
Ensuite en travaillant avec les mesh, il est préférable de stocker les donnée une fois plutot que d’accéder au mesh a chaque fois. Ici tu stock juste le _nbVertex, et pour chaque vertex que tu test par rapport aux centre, utilise _planeteMesh.vertices(i) qui est une opération lente. Regarde mon code, je n’accède au mesh juste pour en sortir les vertex, que je met dans un array. et ensuite je n'utilise plus que cet array au lieu d’accéder au mesh pour chaque calcul.
Une autre optimisation, c'est du coté de foreach qui sont si ma mémoire est bonne , plus couteux en ressource et certainement en temps par rapport à mon script qui utilisait les for(int i ... etc ), c'est certes un peu plus long a écrire, mais plus performant.
C'est vrai que je n'avais pas trop optimisé mais plutôt écris à la vas vite.^^
Pour optimiser tu peux déjà commencer par baisser le nombre d'itération de recherche de centerZone. j'avais mis une grande valeur ne connaissant pas les données de ton mesh. tu peux réduire par palier de 100 et tester à chaque fois. dès que tu remarque des zones trop grandes par rapport à d'autre, remonte de 100 pour être garder une marge.
Pour la void FindCenter, tu peux gagner aussi un peu.la distance d'un centre a l'autre est calculée avec un Vector3.magnitude, pour que ta distance minimal soit une valeur en unité réel ( 1 c'est un mètre). Cependant pour juste de la comparaison de distance, il est plus rapide d'utiliser un Vector3.sqrtMagnitude qui est plus rapide. Mais dans ce cas bien penser a mettre au carré ta distance minimal. Par exemple pour des zones de 1.5, il faudra comparer les sqrtMagnitude avec 2.25. FindCenter(1.5f) => FindCenter(2.25f);
Ensuite en travaillant avec les mesh, il est préférable de stocker les donnée une fois plutot que d’accéder au mesh a chaque fois. Ici tu stock juste le _nbVertex, et pour chaque vertex que tu test par rapport aux centre, utilise _planeteMesh.vertices(i) qui est une opération lente. Regarde mon code, je n’accède au mesh juste pour en sortir les vertex, que je met dans un array. et ensuite je n'utilise plus que cet array au lieu d’accéder au mesh pour chaque calcul.
Une autre optimisation, c'est du coté de foreach qui sont si ma mémoire est bonne , plus couteux en ressource et certainement en temps par rapport à mon script qui utilisait les for(int i ... etc ), c'est certes un peu plus long a écrire, mais plus performant.
______________________________________________________________
\_______________________ Impossible is nothing _______________________/
Re: [MY - AL] Subdivision de mesh en zones
Vu que tu avais bien remarqué que le GPU est beaucoup plus rapide pour le calcul, et que dans ton WIP je t'ai suggéré les ComputeShader, j'ai profiter de ton cas pour me faire la main sur ces ComputeShader.
Configuration des données:
- Sphère de 25'159 vertices;
- MinDist à 0.05f soit environ 1'550 zones.
- recherche de la zone de chaque vertex (25'159 x 1550 = 3.8*10^7 calculs = 38 millions environ).
Pour les résultats bluffants :
- version pure CPU : 2.436s en moyenne
- version mixte CPU GPU : 0.01s en moyenne
==> soit 240 fois plus rapide dans ce cas.
j'ai fait un petit UnityPackage à importer si tu veux tester sur ton ordi.
Ouvre la scène CPUvsGPU, Juste à mettre Play pour chacune et tu verra dans la console le temps mis pour le calcul ( print)
______________________________________________________________
\_______________________ Impossible is nothing _______________________/
Re: [MY - AL] Subdivision de mesh en zones
Hello Djulio !
Cool ! Le seul hic c'est que ton lien me renvoie un code error 2...
J'ai continué dans ma lancé et à partir des vertex sélectionnés j'ai généré des mesh en procédural :
Les MeshColliders générés à partir des vertices :
Puis j'ai créé des mesh à partir de ces mêmes vertices... le soucis c'est que les vertex étaient pas triés selon leur position dans l'espace Et donc ça m'a donné des mesh bien dégueux avec des triangles dans tous les sens ^^
Du coup j'ai récupéré un code de "convexification" qui me donne une belle zone bien lisse
La méthode : MIConvexHull
Mes zolies zones :
Cool ! Le seul hic c'est que ton lien me renvoie un code error 2...
J'ai continué dans ma lancé et à partir des vertex sélectionnés j'ai généré des mesh en procédural :
Les MeshColliders générés à partir des vertices :
Puis j'ai créé des mesh à partir de ces mêmes vertices... le soucis c'est que les vertex étaient pas triés selon leur position dans l'espace Et donc ça m'a donné des mesh bien dégueux avec des triangles dans tous les sens ^^
Du coup j'ai récupéré un code de "convexification" qui me donne une belle zone bien lisse
La méthode : MIConvexHull
Mes zolies zones :
Re: [MY - AL] Subdivision de mesh en zones
bah c'est étonnant ça, je viens juste de re-tester sans être identifier sous mon compte oneDrive, et le lien marche très bien pour moi. ou alors une erreur sous unity?
En effet plutôt sympa, dommage tu n'ai pas essayer d'analyser la chose pour gérer toi même les mesh, te faire ton propre script quoi. Il doit y avoir que moi d'assez taré pour ça
Mais du coup, concrettement, ça va te servir a quoi ces meshCollider. Si tu les utilise en trigger, fais gaffe on dirait qu'ils s'entrecroisent , ça pourrait donner des surprise à la détection..
______________________________________________________________
\_______________________ Impossible is nothing _______________________/
Re: [MY - AL] Subdivision de mesh en zones
Essayé d'analyser, je t'assure que je l'ai fais, et pas qu'un peu ^^ J'ai bien dû passer 2 jours à trouver une bonne solution, j'avais des résultats mais pas très convaincants... Je suis plutôt du genre à essayer au maximum de faire par moi-même, mais là le script est d'un tout autre niveau Bref, j'ai trouvé une source en ligne qui avait l'air assez connue/sérieuse/exploitée, que j'ai quand même dû adapter à mon besoin (donc y a quand même toute une partie que j'ai dû coder à la main), mais là j'aurais été incapable de pondre ça moi-mêmeEn effet plutôt sympa, dommage tu n'ai pas essayer d'analyser la chose pour gérer toi même les mesh, te faire ton propre script quoi. Il doit y avoir que moi d'assez taré pour ça
Effectivement ça sera pour du trigger, et ils s'entrecroisent en effet parce que je leur ai appliqué un scale De base ils ne se touchent pasMais du coup, concrettement, ça va te servir a quoi ces meshCollider. Si tu les utilise en trigger, fais gaffe on dirait qu'ils s'entrecroisent , ça pourrait donner des surprise à la détection..
Re: [MY - AL] Subdivision de mesh en zones
Ma remarque n’était pas péjorative hein
Un truc tout simple, ou plutôt relativement on va dire. vu que tu arrivait a faire un mesh a partir de tes points, même si ce mesh est affreux niveau topologie ( aucun ordre des vertex mais tous présents), ça aurait été de l'assigner en tant que meshCollider à ta zone, avec l'option "Convex" et unity aurait fait tout le travail de convertir ton mesh en un convex, englobant tout tes points/triangles, ajustant par la même le nombre de vertex/tri.
En tout cas bien joué, allez hop la suite! ^^
Un truc tout simple, ou plutôt relativement on va dire. vu que tu arrivait a faire un mesh a partir de tes points, même si ce mesh est affreux niveau topologie ( aucun ordre des vertex mais tous présents), ça aurait été de l'assigner en tant que meshCollider à ta zone, avec l'option "Convex" et unity aurait fait tout le travail de convertir ton mesh en un convex, englobant tout tes points/triangles, ajustant par la même le nombre de vertex/tri.
En tout cas bien joué, allez hop la suite! ^^
______________________________________________________________
\_______________________ Impossible is nothing _______________________/
Re: [MY - AL] Subdivision de mesh en zones
Je l'ai pas mal pris, t'inquiète pasMa remarque n’était pas péjorative hein
Eh bien figure-toi que c'est ce que j'avais fais avant d'opter pour l'autre solution ^^ Mais unity râlait quand je passais le mesh collider en convex et le rendu était pas joli du toutUn truc tout simple, ou plutôt relativement on va dire. vu que tu arrivait a faire un mesh a partir de tes points, même si ce mesh est affreux niveau topologie ( aucun ordre des vertex mais tous présents), ça aurait été de l'assigner en tant que meshCollider à ta zone, avec l'option "Convex" et unity aurait fait tout le travail de convertir ton mesh en un convex, englobant tout tes points/triangles, ajustant par la même le nombre de vertex/tri.
Bon, petit update du jour, j'ai extrudé mes zones (assez facile vu que j'ai ma liste de vertex, juste à les dupliquer en les additionnant au Vector3.normalized de la différence entre le centre du mesh et le centre de la planète )
Maintenant je me penche sur un moyen de "connecter" les zones entre elles, donc indiquer que les vertices des bords sont partagés avec les mesh voisins. Une idée ? Je fais signe si je trouve une solution ^^
Re: [MY - AL] Subdivision de mesh en zones
@Djulio : ça y est j'ai réussi à récupérer ton unitypackage
ça marche bien chez toi ? Moi j'ai une sphère qui reste blanche et j'ai un message d'erreur :
ça marche bien chez toi ? Moi j'ai une sphère qui reste blanche et j'ai un message d'erreur :
Mais très sympa l'idée de comparer les deux sinonArgumentException: ComputeBuffer.SetData() : C# Data stride (28 bytes) is not integer multiple of Compute Buffer stride (32 bytes)
Re: [MY - AL] Subdivision de mesh en zones
C'est etonnant ça, ça marche tres bien chez moi. quelle version d'unity as tu?Sebela a écrit : ↑30 Nov 2018 12:44@Djulio : ça y est j'ai réussi à récupérer ton unitypackage
ça marche bien chez toi ? Moi j'ai une sphère qui reste blanche et j'ai un message d'erreur :Mais très sympa l'idée de comparer les deux sinonArgumentException: ComputeBuffer.SetData() : C# Data stride (28 bytes) is not integer multiple of Compute Buffer stride (32 bytes)
sinon regarde dans le script GPU_Colorized. Dans la void UseShader
tu as deux lignes
Code : Tout sélectionner
VertexBuffer = new ComputeBuffer(vertex.Length,32);
CenterBuffer = new ComputeBuffer(centerZone.Count,32);
______________________________________________________________
\_______________________ Impossible is nothing _______________________/