Forums Développement Multimédia

Aller au contenu

tuiles perdues dans le code de scrolling

CODE

2 réponses à ce sujet

#1 darkrat

    Ceinture Verte

  • Members
  • PipPipPipPip
  • 61 messages

Posté 25 July 2012 - 20:23 PM

Bonjour ou bonsoir à vous,

j'ai un problème avec un procédé qui ne posait aucun problème en procédural lorsque j'essaye de l'appliquer en poo.

Il s'agit d'une base pour un moteur de map de tuiles. Le problème est le suivant : lorsque j'effectue scrollings horinzontaux et verticaux l'un après l'autre sur quelques coups certaines cases semblent ne pas se réaligner en début ou en fin de carte comme le script le voudrait (la dernière ligne revient devant la première ou vice versa) et semblent rester sur leur position courante alors que si j'effectue un scrolling vertical ou horizontal en continu il n'y aura aucun problème.

Pour le fonctionnement, je crée donc une map de tuiles à partir de plusieurs instance d'un même movieclip qui ont chacune leur propre frame suivant la position sur la carte. Lorsque j'effectue un scrolling, j'envoie en même temps la ligne ou colonne qui est la suivante dans la direction ou se déplace le héro pour pouvoir rafraichir si néscéssaire.


voici la partie de ma classe map qui gère les scrolling :
public function scrollingHorizontal(mouvement:Number,rangeeSuivante:Array=null){
            var i:Number;
            var j:Number;
            if(mouvement>0){
                if(this.x-mouvement<=-longueurCase){
                    i=0;
                    //mettre la premiere colonne en derniere
                    while(i<largeurMap){
                        if(rangeeSuivante!=null){
                            MovieClip(getChildByName("case_"+premiereC+"_"+i)).setFrame(rangeeSuivante[i]);
                        }
                        getChildByName("case_"+premiereC+"_"+i).x=longueurMap*longueurCase;
                        i++;
                    }
                   
                    //reajuster les cases sur la carte
                    i=j=0;
                    while(j<largeurMap){
                        getChildByName("case_"+i+"_"+j).x-=longueurCase;
                        if(i==longueurMap-1){
                            i=0;
                            j++;
                        }else{
                            i++;
                        }
                    }
                   
                    //reajuster carte
                    this.x+=longueurCase-mouvement;
                   
                    //mise à jour de la premiere et derniere colonne
                   
                    if(premiereC==longueurMap-1){
                        premiereC=0;
                        derniereC=longueurMap-1;
                    }else{
                        premiereC++;
                        if(derniereC==longueurMap-1){
                            derniereC=0;
                        }else{
                            derniereC++;
                        }
                    }
                   
                    return true;
                }else{
                    this.x-=mouvement;
                    return false;
                }
            }else{
                //trace("xCarte("+this.x+")-mouvement("+mouvement+")>0.    premiere colonne="+premiereC+"    derniere colonne="+derniereC);
                if(this.x-mouvement>0){
                   
                    i=0;
                   
                   
                    //mettre la derniere colonne en premiere
                    while(i<largeurMap){
                        if(rangeeSuivante!=null){
                            MovieClip(getChildByName("case_"+derniereC+"_"+i)).setFrame(rangeeSuivante[i]);
                        }
                        getChildByName("case_"+derniereC+"_"+i).x=-longueurCase;
                       
                        i++;
                    }
                   
                    //reajuster les cases sur la carte
                    i=j=0;
                    while(j<largeurMap){
                        getChildByName("case_"+i+"_"+j).x+=longueurCase;
                        if(i==longueurMap-1){
                            i=0;
                            j++;
                        }else{
                            i++;
                        }
                    }
                   
                    //reajuster carte
                    this.x-=longueurCase+mouvement;
                    //mise à jour de la premiere et derniere colonne
                   
                    if(derniereC==0){
                        derniereC=longueurMap-1;
                        premiereC=0;
                    }else{
                        derniereC--;
                        if(premiereC==0){
                            premiereC=longueurMap-1;
                        }else{
                            premiereC--;
                        }
                    }
                    return true;
                }else{
                    this.x-=mouvement;
                    return false;
                }    
            }
        }
       
        public function scrollingVertical(mouvement:Number, rangeeSuivante:Array=null){
            var i:Number;
            var j:Number;
           
            if(mouvement>0){
                if(this.y-mouvement<=-longueurCase){
                   
                    i=0;
                    //mettre la premiere colonne en derniere
                    trace(longueurMap);
                    while(i<longueurMap){
                        if(rangeeSuivante!=null){
                            MovieClip(getChildByName("case_"+i+"_"+premiereL)).setFrame(rangeeSuivante[i]);
                        }
                        getChildByName("case_"+i+"_"+premiereL).y=largeurMap*longueurCase;
                        i++;
                    }
                   
                    //reajuster les cases sur la carte
                    i=j=0;
                    while(j<longueurMap){
                        getChildByName("case_"+i+"_"+j).y-=longueurCase;
                        if(i==longueurMap-1){
                            i=0;
                            j++;
                        }else{
                            i++;
                        }
                    }
                   
                    //reajuster carte
                    this.y+=longueurCase-mouvement;
                   
                    //mise à jour de la premiere et derniere colonne
                   
                    if(premiereL==largeurMap-1){
                        premiereL=0;
                        derniereL=largeurMap-1;
                    }else{
                        premiereL++;
                        if(derniereL==largeurMap-1){
                            derniereL=0;
                        }else{
                            derniereL++;
                        }
                    }
                    return true;
                }else{
                    this.y-=mouvement;
                    return false;
                }
            }else{
                if(this.y-mouvement>0){
                    trace(longueurMap);
                    i=0;
                   
                   
                    //mettre la derniere colonne en premiere
                    while(i<longueurMap){
                        if(rangeeSuivante!=null){
                            MovieClip(getChildByName("case_"+i+"_"+derniereL)).setFrame(rangeeSuivante[i]);
                        }
                        getChildByName("case_"+i+"_"+derniereL).y=-longueurCase;
                        i++;
                    }
                   
                    //reajuster les cases sur la carte
                    i=j=0;
                    while(j<longueurMap){
                        getChildByName("case_"+i+"_"+j).y+=longueurCase;
                        if(i==longueurMap-1){
                            i=0;
                            j++;
                        }else{
                            i++;
                        }
                    }
                   
                    //reajuster carte
                    this.y-=longueurCase+mouvement;
                    //mise à jour de la premiere et derniere colonne
                   
                    if(derniereL==0){
                        derniereL=largeurMap-1;
                        premiereL=0;
                    }else{
                        derniereL--;
                        if(premiereL==0){
                            premiereL=largeurMap-1;
                        }else{
                            premiereL--;
                        }
                    }
                    return true;
                }else{
                    this.y-=mouvement;
                    return false;
                }
            }
        }


la gestion du déplacement du personnage:

function deplacer(evt:Event){
    var changement:Boolean=false;
    if(toucheGauche==true){
        if(hero.currentFrame<=24 || hero.currentFrame>=44){
            hero.gotoAndPlay(24);
        }
       
        changement=map1.scrollingHorizontal(-3,obtentionColonne(carte,positionX-1));
        map2.scrollingHorizontal(-3,obtentionColonne(carte2,positionX-1));
        map3.scrollingHorizontal(-3,obtentionColonne(carte3,positionX-1));
        if(changement==true){
            positionX--;
        }
    }else{
        if(toucheDroite==true){
            if(hero.currentFrame<=46 || hero.currentFrame>=66){
                hero.gotoAndPlay(46);
            }
           
            changement=map1.scrollingHorizontal(3,obtentionColonne(carte,positionX+TAILLE_CARTE));
            map2.scrollingHorizontal(3,obtentionColonne(carte2,positionX+TAILLE_CARTE));
            map3.scrollingHorizontal(3,obtentionColonne(carte3,positionX+TAILLE_CARTE));
            if(changement==true){
                positionX++;
            }
        }else{
            if(toucheHaut==true){
                if(hero.currentFrame<=68 || hero.currentFrame>=88){
                    hero.gotoAndPlay(68);
                }
                if(positionY>0){
                   
                    changement=map1.scrollingVertical(-3,carte[positionY-1].slice(positionX,positionX+TAILLE_CARTE));
                    map2.scrollingVertical(-3,carte2[positionY-1].slice(positionX,positionX+TAILLE_CARTE));
                    map3.scrollingVertical(-3,carte3[positionY-1].slice(positionX,positionX+TAILLE_CARTE));
                }else{
                    changement=map1.scrollingVertical(-3,carte[15].slice(15,30));
                    map2.scrollingVertical(-3,carte2[0]);
                    map3.scrollingVertical(-3,carte3[0]);
                }
                if(changement==true){
                    positionY--;
                }
            }
       
        }
       
       
    }
}
function obtentionColonne(carte:Array,colonne:int){
    var ligne:Array=new Array;
    var i:Number=positionY;
    while(i<positionY+TAILLE_CARTE){
        ligne.push(carte[i][colonne]);
        i++;
    }
   
    return ligne;
}

 

le swf de test (le déplacement bas n'est pas activé mais c'est le même problème):

http://www.swfcabin....open/1343238638

voila, je peux vous passer d'autres parties ou vous expliquer si vous ne comprenez pas tout

merci à vous d'avance :)

#2 Monsieur Spi

  • Community Manager
  • PipPipPipPipPipPipPipPip
  • 7017 messages

Posté 26 July 2012 - 16:49 PM

Salut,

Je déplace ton sujet dans la salle réservée au développement de jeux vidéos ;-)

Sinon, pfffffffffff quelle tartine de code...... ne pourrais tu pas simplifier et limiter le tout pour ne nous montrer qu'une forme simple qui reprend le bug ?

Je vais jeter un oeil mais il y a tellement de code que ça donne pas super envie ;-)


EDIT : bon j'ai jeté un oeil au code, beaucoup de petites erreurs risquent de te compliquer sérieusement la vie.
Tel que tu nous le présente il va être difficile de t'aider car ton code utilise des choses que nous ne connaissons pas, comme par exemple map1, map2, map3, etc.... il n'y a aucun commentaires et a moins de le réécrire ligne par ligne ca va nous être difficile de trouver le bug. Peux-tu en faire une version épurée ? Vire tout ce qui n'est pas propre à ton problème, sauve ton projet sous un autre nom, et supprime tout ce qui n'est pas directement lié à ton problème, le but est que tu te retrouve avec juste une map de tuiles et un clip (le héro) qui nous permet de nous déplacer, tout ce qui est animations du héro, contenu des tuiles etc.... on s'en fou, ce n'est pas ça qui plante le programme ;-)

Sinon, je te recommande d'éviter d'utiliser les getChildByName pour faire du scrolling, c'est lent, ça surcharge le code et devient inutile si tu utilise des tableaux.

Un petit tuto à lire au cas ou tu aurais besoin de revoir certaines choses à propos du scrolling : http://forums.mediab...-base/scrolling
La méthode qui y est expliquée est la même que celle que tu utlise, c'est à dire les "rondins", on déplace des rangées de conteneurs. Saches que ce n'est pas la meilleure méthode, surtout à cause de l'utilisation de clips, l'idéal serait de redessinner directement ta map dans un sprite unique avec du copypixel par exemple, c'est bien plus optimisé.

Bref, pour en revenir à ton code, j'ai déjà été confronté à ce problème, dans mon cas c'était une erreur de calcul, mais il va falloir se plonger plus avant dans ton code pour en être sur.... peux-tu donc tenter une simplification à l'extrème de manière à ce que le problème soit complétement isolé ?

#3 darkrat

    Ceinture Verte

  • Members
  • PipPipPipPip
  • 61 messages

Posté 29 July 2012 - 16:10 PM

salut et tout dabord merci pour ta réponse.

J'avais déjà vu qu'il existait d'autres méthodes que celle des "rondins" mais comme je n'ai vu que celle la, je l'utilise par défaut. Vu que je cherche à faire une classe que je pourrai réexploiter il vaudrait mieux que je parte sur cette piste alors? Le problème c'est que je n'ai jamais vraiment trouvé de tuto qui traitait du copyPixels et du scrolling (il y a bien le raycasting ici mais j'ai du mal avec le concept de base). Saurais tu m'expliquer brièvement comment exploiter cette méthode dans le cas d'un scrolling ou me rediriger vers un tuto?

D'après ce que je vois, cette méthode peut copier une zone de pixel pour la mettre dans un autre conteneur (ou dans le même j'espère) donc il suffirait à ce moment, dans le cas d'un scrolling vers la gauche, de copier toute la partie qui se trouve à x pixels (x étant la vitesse de déplacement) du bord gauche, de le coller à gauche du conteneur et de combler les colonnes restantes avec une copie du début des images suivantes. C'est bien cela? Il faut garder les images en mémoire ou charger/décharger à chaque scrolling?

Peut être qu'en tentant cette méthode, je n'aurai plus de bug, par la même occasion^^

Encore faut il que je sache la maitriser

merci encore à toi en tous cas



1 utilisateur(s) li(sen)t ce sujet

0 membre(s), 1 invité(s), 0 utilisateur(s) anonyme(s)