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

Algorithmes et structures de données Discussion :

Mouvement d'un mobile : problème d'orientation


Sujet :

Algorithmes et structures de données

  1. #1
    mat.M
    Invité(e)
    Par défaut Mouvement d'un mobile : problème d'orientation
    Bonjour à tous , mon problème :
    je souhaite à représenter un véhicule en mouvement à l'écran , par exemple un voilier selon une vitesse en noeuds et un cap en degrés.

    J'arrive parfaitement à représenter le déplacement du voilier selon que l'on donne un ordre de cap de 0 à 360 .
    Si le voilier à un cap de 45 degrés , on donne un ordre de virer à 145 degrés et à toutes les secondes ( avec un timer ) le cap est incrémenté pour atteindre 145

    Petit problème idiot :
    le voilier a un cap de 20 degrés ; on donne l'ordre de virer à 350 degrés.

    Mais comment faire pour virer de 20 degrés à 350 degrés , c'est à dire du nord -est vers le nord-ouest au lieu de virer de 30 degrés puis 40 puis 50 puis 60 etc pour atteindre 350 degrés c.a.d dans l'autre sens .

    Je ne sais pas si c'est bien clair ?

    Merci pour les réponses.

  2. #2
    Inactif  
    Avatar de Mac LAK
    Profil pro
    Inscrit en
    Octobre 2004
    Messages
    3 893
    Détails du profil
    Informations personnelles :
    Âge : 49
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Octobre 2004
    Messages : 3 893
    Points : 4 846
    Points
    4 846
    Par défaut
    Heu.......... Pourquoi pas avec un "modulo 360", tout simplement ? ;-)
    Mac LAK.
    ___________________________________________________
    Ne prenez pas la vie trop au sérieux, de toutes façons, vous n'en sortirez pas vivant.

    Sources et composants Delphi sur mon site, L'antre du Lak.
    Pas de question technique par MP : posez-la dans un nouveau sujet, sur le forum adéquat.

    Rejoignez-nous sur : Serveur de fichiers [NAS] Le Tableau de bord projets Le groupe de travail ICMO

  3. #3
    Membre actif

    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    479
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 479
    Points : 267
    Points
    267
    Par défaut
    Tu construis un tableau contenant chaque valeur de 10° (par exemple).

    Tu localises le cap de départ sur le tableau. Si la différence entre les 2 caps est inférieure ou égale à 180 ° tu vas normalement du cap 1 au cap 2 par itération successive.

    ex 80 à 10 passe par 80, 70, 60 ...

    Sinon tu vas du cap1 au cap2 en passant par l'extrémité la plus proche du cap1. Par exemple 20 à 350 passe par 20 10 0 350. L'extrémité 0 du tableau est plus proche de 20 que l'extrémité 350.

    Ce qui revient à considérer le tableau de cap comme un anneau fermé et à déterminer le chemin le plus court avant de prendre la route.

  4. #4
    Membre éprouvé

    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    1 163
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 1 163
    Points : 1 148
    Points
    1 148
    Par défaut
    Oui c'est une bonne idée mais le tableau est d'après moi loin d'être indispensable.

    Un simple if qui si la différence entre les 2 caps est inférieure ou égal à 180° met +1 dans une variable sens et -1 sinon.

    Ensuite pour se déplacer de 10° chaque seconde suffit de faire dans le code executé par ton Timer :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    if ( nouveau_cap != cap )
    cap = cap + sens * 10;
    Neilos

  5. #5
    mat.M
    Invité(e)
    Par défaut
    Eh bien merci à tous en me rasant ce matin 'j'ai trouvé une solution similaire à celles que vous proposez
    Mac Lak je vais tenter avec modulo , Neilos je vais tenter d'appliquer la formule donnée et frantzgac c'est cette solution en quelque sorte que j'ai trouvée
    Comme vous le suggérez il suffit de faire 2 boucles une avec incrémentations et l'autre avec décrementations et de ne considérer que celle contenant le moins d'itérations ; en prenant garde par exemple du fait que si cap=-1 , cap=359

    Merci encore pour les réponses

  6. #6
    Membre expert
    Avatar de 2Eurocents
    Profil pro
    Inscrit en
    Septembre 2004
    Messages
    2 177
    Détails du profil
    Informations personnelles :
    Âge : 54
    Localisation : France

    Informations forums :
    Inscription : Septembre 2004
    Messages : 2 177
    Points : 3 166
    Points
    3 166
    Par défaut
    Le fait d'utiliser une variable indiquant le sens du virage est une bonne idée car on peut calculer ce sens automatiquement (pour faire le virage dont l'angle est le plus faible), mais aussi l'imposer.

    En effet, dans certains cas, il peut être nécessaire de faire exprès le virage dont la valeur d'angle est la plus importante (pour "enrouler" des bouées, par exemple, où en cas de risque de collision, de gestion de la priorité, etc.).
    La FAQ Perl est par ici
    : La fonction "Rechercher", on aurait dû la nommer "Retrouver" - essayez et vous verrez pourquoi !

  7. #7
    Inactif  
    Avatar de Mac LAK
    Profil pro
    Inscrit en
    Octobre 2004
    Messages
    3 893
    Détails du profil
    Informations personnelles :
    Âge : 49
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations forums :
    Inscription : Octobre 2004
    Messages : 3 893
    Points : 4 846
    Points
    4 846
    Par défaut
    Citation Envoyé par mat.M
    Mac Lak je vais tenter avec modulo
    Avec certains langages, la fonction modulo a des comportements bizarres avec les nombres négatifs.
    Je te conseille une formule de "correction positive" après chaque opération :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    cap = Nouveau_Cap() ;
    // Code de correction : on s'assure que "cap" est positif.
    while cap<0
      cap = cap + 360
    end while
    // Ensuite, on effectue le modulo.
    cap = cap modulo 360
    Pour trouver le plus court changement de cap entre "cap1" et "cap2" (bref, virer à tribord ou à babord), il te suffit de vérifier la différence (en valeur absolue) entre "cap1" et "cap2", tous deux étant garantis en modulo 360.
    Si cette différence est supérieure à 180 (= plus d'un demi-tour), il faut ajouter 360 au plus petit cap, recalculer la différence et inverser le sens du changement de cap.
    Mac LAK.
    ___________________________________________________
    Ne prenez pas la vie trop au sérieux, de toutes façons, vous n'en sortirez pas vivant.

    Sources et composants Delphi sur mon site, L'antre du Lak.
    Pas de question technique par MP : posez-la dans un nouveau sujet, sur le forum adéquat.

    Rejoignez-nous sur : Serveur de fichiers [NAS] Le Tableau de bord projets Le groupe de travail ICMO

  8. #8
    Membre actif

    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    479
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 479
    Points : 267
    Points
    267
    Par défaut didactique
    La solution du tableau est certes un peu lourde mais elle a l'avantage de permettre une représentation mentale du problème qui guide aisément vers les nombreuses solutions possibles.

  9. #9
    Membre éprouvé

    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    1 163
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 1 163
    Points : 1 148
    Points
    1 148
    Par défaut
    Mouais...pas besoin d'un tableau pour "aiguiser mon mental" et trouver une variable de sens et une seule boucle
    Neilos

  10. #10
    Membre actif

    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    479
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 479
    Points : 267
    Points
    267
    Par défaut cqfd
    c'est pour cela que ce n'est pas toi qui a posé la question

  11. #11
    mat.M
    Invité(e)
    Par défaut Re: cqfd
    Citation Envoyé par frantzgac
    c'est pour cela que ce n'est pas toi qui a posé la question
    Du calme du calme c'est bon j'ai trouvé et ça marche impec
    Effectivement pas besoin de tableau , voilà le code source ( en C++ sorry , pour MFC )

    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
    void CLeftDlg::OnButtonHeadCommand() 
    {
    char *stop;
    double 	nStartCourse;
    int nCount;
    int nCount1;
    int nCount2;
    CMySoftDoc *pDoc=(CAtcDoc *)GetDocument();
    CString strVal;
    CString strCommand;
    m_ebHeading.GetWindowText(strVal);
    pDoc->m_pCurrentBoat->m_nRequiredTrueCourse=strtod(strVal,&stop);
    nCount1=0;
    nCount2=0;
    	if(pDoc->m_pCurrentBoat->m_TrueCourse!=pDoc->m_pCurrentBoat->m_nRequiredTrueCourse )
     
    	{	
    		nStartCourse=pDoc->m_pCurrentBoat->m_TrueCourse;
    		while(pDoc->m_pCurrentBoat->m_nRequiredTrueCourse!=nStartCourse)
    		{
    			nStartCourse++;
    			if(nStartCourse==360)nStartCourse=0;
    			nCount1++;
     
    		}
    		nStartCourse=pDoc->m_pCurrentBoat->m_TrueCourse;
    		while(pDoc->m_pCurrentBoat->m_nRequiredTrueCourse!=nStartCourse)
    		{
    			nStartCourse--;
    			if(nStartCourse==-1)nStartCourse=359;
    			nCount2++;
     
    		}
     
    		nCount1 < nCount2 ? pDoc->m_pCurrentBoat->m_nLeftRight=2:pDoc->m_pCurrentBoat->m_nLeftRight=1;
    	}
     
    }
    Dans l'événement Timer:
    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
     
    if(m_TrueCourse!=m_nRequiredTrueCourse )
     
    	{	
     
    		if( m_nLeftRight ==1)
    		{
    				m_TrueCourse--;
    				if(m_TrueCourse==-1)m_TrueCourse=359;
     
    		}
    		else
    		{
     
    				m_TrueCourse++;
    				if(m_TrueCourse==360)m_TrueCourse=0;
     
    		}
     
    	}
    Quand j'aurais fini mon gratuiciel je le diffuserai sur des sites de gratuiciels

  12. #12
    Membre éprouvé

    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    1 163
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 1 163
    Points : 1 148
    Points
    1 148
    Par défaut Re: cqfd
    Ok mais ça fait toujours deux boucles
    Neilos

  13. #13
    mat.M
    Invité(e)
    Par défaut Re: cqfd
    Citation Envoyé par Neilos
    Ok mais ça fait toujours deux boucles
    Oui je sais c'est pas folichon , mais le temps tourne , Time is Money et si j'en ai j'optimiserai plus tard
    Je suis tout seul à mener des projets et ça consomme un temps gigantesque
    Tant que ça fonctionne


    Et encore merci pour les tuyaux à tous

  14. #14
    Membre éprouvé

    Profil pro
    Inscrit en
    Octobre 2003
    Messages
    1 163
    Détails du profil
    Informations personnelles :
    Âge : 39
    Localisation : France

    Informations forums :
    Inscription : Octobre 2003
    Messages : 1 163
    Points : 1 148
    Points
    1 148
    Par défaut Re: cqfd
    Citation Envoyé par mat.M
    Je suis tout seul à mener des projets et ça consomme un temps gigantesque
    Tant que ça fonctionne
    Tout à fait d'accord...travailler seul sur un projet prend beaucoup de temps !
    Neilos

Discussions similaires

  1. JavaFx Mobile : problème emulator
    Par CaptainChoc dans le forum JavaFX
    Réponses: 1
    Dernier message: 06/03/2009, 04h32
  2. Réponses: 3
    Dernier message: 30/12/2008, 10h31
  3. Problème d'orienté objet
    Par zenux dans le forum C++
    Réponses: 6
    Dernier message: 21/11/2007, 19h44
  4. [MFC]Problèmes pour orienter du texte
    Par Deedier dans le forum MFC
    Réponses: 1
    Dernier message: 25/03/2005, 16h15
  5. Problème d'orientation
    Par JMF dans le forum QuickReport
    Réponses: 2
    Dernier message: 13/05/2003, 10h09

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