IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Développement 2D, 3D et Jeux Discussion :

Générer un point dans un cône


Sujet :

Développement 2D, 3D et Jeux

  1. #1
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2015
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2015
    Messages : 41
    Points : 14
    Points
    14
    Par défaut Générer un point dans un cône
    Bonjour,

    Je souhaite générer dans un point dans un cône. Je dispose de l'angle et de la direction ainsi que le rayon. Je travaille avec des vector 2D donc seulement des positions x et y.

    J'ai trouvé ce thread : http://gamedev.stackexchange.com/que...-within-a-cone

    Vous allez sûrement trouver ça bête (car cela a l'air facile, je le reconnais) mais je n'arrive pas à générer de bonnes valeurs.

    Merci de votre aide

  2. #2
    Membre éclairé
    Avatar de N_I_C_S
    Profil pro
    Inscrit en
    Septembre 2006
    Messages
    450
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2006
    Messages : 450
    Points : 681
    Points
    681
    Par défaut
    Allez une réponse à chaud (y a peut-être plus rapide) :

    - Conidérer un cône "vers le haut" : base(0, 0) , bord1( cos(angle/2)*rayon, rayon ) , bord2( -cos(angle/2)*rayon, rayon )
    - choisir x = aleatoire entre bord1.x et bord2.x
    - choisir y aleatoire entre 0 et rayon et faire : x = x * ( y / rayon )
    - faire (x, y) = (x, y) * (longueur(x, y) / rayon)
    - retouver l'angle a de rotation du cône depuis (0, 1) avec la direction (normalisée) et quelques arcsin/arccos
    - multiplier (x, y) par la matrice :
    cos(a) -sin(a)
    sin(a) cos(a)

    ou sinon choisir un vecteur aleatoirement dans le champs du rayon en boucle et vérifier qu'il est dans le cône,
    si ça se trouve c'est plus rapide en moyenne au delà d'un petit angle .

  3. #3
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2015
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2015
    Messages : 41
    Points : 14
    Points
    14
    Par défaut
    Super merci !

    Je teste cela et je te reviens !

  4. #4
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2015
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2015
    Messages : 41
    Points : 14
    Points
    14
    Par défaut
    Salut,

    [EDIT] NE FAIS PAS ATTENTION AU MESSAGE, J'AI TROUVE L'ERREUR JE TE DIS SI CELA FONCTIONNE

    Voici mon code.

    J'obtiens des valeurs complétements fausses.

    Le calcul avec les cosinus et sinus fonctionne car j'utilise exactement le même pour pivoter des points issus d'une autre génération dans une autre fonction:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
     
    void computeBoundsCone(const glm::fvec2& start, const glm::fvec2& end, const glm::fvec2& direction, float& x, float& y)
    {
            const float angleRotation = computeAngle(glm::fvec2(0.f, 1.f), glm::normalize(direction));
     
            // On se met dans une repère à l'origine
    	glm::fvec2 vecteur(end.x - start.x, end.y - start.y);
     
    	static const float angleCone = 20.f;
     
    	glm::fvec2 v1(glm::cos(angleCone / 2) * vecteur.y, vecteur.y);
    	glm::fvec2 v2(-glm::cos(angleCone / 2) * vecteur.y, vecteur.y);
     
    	std::random_device rdx;
    	std::mt19937 genX(rdx());
    	std::uniform_real<> disX(v2.x, v1.x);
    	x = disX(genX);
     
    	std::random_device rdy;
    	std::mt19937 genY(rdy());
    	std::uniform_real<> disY(0.f, vecteur.y);
    	y = disY(genY);
     
    	x = x * (y / vecteur.y);
     
    	glm::fvec2 xy(x, y);
     
    	xy *= (glm::length2(xy) / vecteur.y);
     
    	if (angleRotation != 0)
    	{
    		float radians = glm::radians(angleRotation);
     
    		float cosinus = glm::cos(radians);
    		float sinus = glm::sin(radians);
     
    		// rotation around 0,0
    		float xnew = cosinus * x + sinus * y;
    		float ynew = sinus * -x + cosinus * y;
     
    		// translation
    		x = xnew + start.x;
    		y = ynew + start.y;
    	}
    	else
    	{
    		x += start.x;
    		y += start.y;
    	}	
     
    	x = xy.x;
    	y = xy.y;
    }

  5. #5
    Membre éclairé
    Avatar de N_I_C_S
    Profil pro
    Inscrit en
    Septembre 2006
    Messages
    450
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Septembre 2006
    Messages : 450
    Points : 681
    Points
    681
    Par défaut
    Ok.
    Tiens en me relisant j'ai vu qu'il y avait des étapes complètement inutiles : tu peux laisser tomber les arcsin/arccos/calculs d'angle gourmands, la direction normalisée donne déjà les valeurs nécessaires à la matrice .
    du coup pour la rotation tu peux multiplier directement le point random initial par :
    dir.y dir.x
    -dir.x dir.y
    (il me semble, de tête)

  6. #6
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2015
    Messages
    41
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2015
    Messages : 41
    Points : 14
    Points
    14
    Par défaut
    Salut,

    J'ai repris ce projet il y a quelques jours voilà pourquoi ma réponse est si tardive.

    Ce que j'obtiens ce sont deux cônes qui forment un V à eux deux.

    Le fait de générer le point entre "-glm::cos(angleCone / 2)" et le rayon tu es sûr que c'est bon ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
     
    void computeBoundsCone(glm::fvec2 a, glm::fvec2 b, const glm::fvec2& direction, float& x, float& y)
    {
    	const float angleRotation = computeAngle(glm::fvec2(0.f, 1.f), glm::normalize(direction));
     
    	glm::fvec2 vecteur(b.x - a.x, b.y - a.y);
     
    	const float angleCone = 20.f;
     
    	glm::fvec2 v1(glm::cos(angleCone / 2) * vecteur.y, vecteur.y);
    	glm::fvec2 v2(-glm::cos(angleCone / 2) * vecteur.y, vecteur.y);
     
    	std::random_device rdx;
    	std::mt19937 genX(rdx());
    	std::uniform_real<> disX(v2.x, v1.x);
    	x = disX(genX);
     
    	std::random_device rdy;
    	std::mt19937 genY(rdy());
    	std::uniform_real<> disY(0.f, vecteur.y);
    	y = disY(genY);
     
    	x *= (y / vecteur.y);
     
    	glm::fvec2 xy(x, y);
     
    	xy *= (glm::length2(xy) / vecteur.y);
     
    	if (angleRotation != 0)
    	{
    		float radians = glm::radians(angleRotation);
     
    		float cosinus = glm::cos(radians);
    		float sinus = glm::sin(radians);
     
    		// rotation around 0,0
    		float xnew = cosinus * xy.x + sinus * xy.y;
    		float ynew = sinus * -xy.x + cosinus * xy.y;
     
    		// translation
    		xy.x = xnew + a.x;
    		xy.y = ynew + a.y;
    	}
    	else
    	{
    		xy.x += a.x;
    		xy.y += a.y;
    	}	
     
    	x = xy.x;
    	y = xy.y;
    }

Discussions similaires

  1. Réponses: 6
    Dernier message: 01/05/2012, 17h56
  2. générer des points appartenant à l'intersection d'une sphère et d'un cône
    Par christophe_halgand dans le forum Mathématiques
    Réponses: 3
    Dernier message: 25/06/2009, 18h07
  3. emission particules dans un cône
    Par Mat 74 dans le forum Algorithmes et structures de données
    Réponses: 4
    Dernier message: 08/08/2005, 13h05
  4. Générer un model dans Eclipse 3
    Par ArchFolken dans le forum Eclipse Java
    Réponses: 1
    Dernier message: 29/09/2004, 15h29
  5. Réponses: 4
    Dernier message: 11/06/2004, 10h21

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo