2014-05-22 4 views
0

Je suis en train de développer un jeu HTML5 Canvas en utilisant EaselJS et j'ai trouvé un problème après avoir changé mon code. Les événements tactiles fonctionnaient avant ce changement, mais cela ne fonctionne plus et je ne me souviens pas de ce que j'ai changé, mais ce n'était pas lié aux événements stagemousedown/stagemouseup. J'ai testé le jeu sur iOS 7 uniquement.Les événements tactiles ne fonctionnent pas EaselJS

Quelqu'un peut-il m'aider?

Comme je l'ai dit, je ne sais pas où le problème est alors je vais mettre tout le code ici au lieu de la partie pertinente seulement (> 400 lignes). Je recommande fortement de voir le [violon] [1] à la place.

Voici mon code:

function init() { 

    var objectsCollideAt = { 
     it: [], // If it is collideable, it'll be in this array. 
     top: [], 
     left: [], 
     right: [], 
     bottom: [] 
    }, 
    key = { 
     up: false, // W, arrow up or spacebar 
     left: false, // A or arrow left 
     right: false, // D or arrow right 
     down: false, // S or arrow down 
     holdingUp: false 
    }, 
    mouse = { 
     x: 0, 
     y: 0 
    }, 
    touch = { 
     tollerance: 50 // Object "margins" when using touch or mouse 
    }, 
    collisionSystem = { 
     /* This variable is responsible for deactivating the 
     * edge-to-edge collision detection forEach when a 
     * side-to-side collision happened, to get better 
     * performance. Can cause extremely rare bugs. 
     */ 
     //sideCollided: false // Commented because it was causing a critical bug. 
    }; 

    var stage = new createjs.Stage("canvas"); 

    createjs.Touch.enable(stage); 

    var Graphic = function (src, blockWidth, blockHeight) { 
     src = src.split(","); 
     return { 
      createBlockAt: function (x, y, blockGroupWidth, blockGroupHeight, clsdir, alpha) { 
       for (var blockY = 0; blockY < blockGroupHeight/blockHeight; blockY++) { 
        for (var blockX = 0; blockX < blockGroupWidth/blockWidth; blockX++) { 

         var obj = new createjs.Bitmap(src[Math.floor(Math.random() * src.length)]); 

         obj.width = blockWidth; 
         obj.height = blockHeight; 
         if (typeof alpha !== 'undefined') { 
          obj.alpha = alpha; // While debugging this can be used to check if a block was made over another block. 
         } 

         obj.x = Math.round(x + (blockWidth * blockX)); 
         obj.y = Math.round(y + (blockHeight * blockY)); 

         if (clsdir != "none") { 
          objectsCollideAt.it.push(obj); 
         } 
         if (typeof clsdir !== "undefined") { 
          clsdir.split(" "); 
          if (clsdir.indexOf("top") >= 0 && blockY == 0) { 
           objectsCollideAt.top.push(obj); 
          } 
          if (clsdir.indexOf("left") >= 0 && blockX == 0) { 
           objectsCollideAt.left.push(obj); 
          } 
          if (clsdir.indexOf("right") >= 0 && blockX == (blockGroupWidth/blockWidth - 1)) { // blockGroupWidth/width results in the horizontal number of blocks 
           objectsCollideAt.right.push(obj); 
          } 
          if (clsdir.indexOf("bottom") >= 0 && blockY == (blockGroupHeight/blockHeight - 1)) { // blockGroupHeight/height results in the vertical number of blocks. 
           objectsCollideAt.bottom.push(obj); 
          } 
         } else { 
          if (blockY == 0) { 
           objectsCollideAt.top.push(obj); 
          } 
         } 

         obj2container.addChild(obj); 
        } 
       } 
      } 
     } 
    } 
    var dirt = Graphic("http://i.imgur.com/zF6Lhfl.png", 40, 40); 
    var rock = Graphic("http://i.imgur.com/QgxGfJs.png", 40, 40); 
    var grass = Graphic("http://i.imgur.com/5SkIyyM.png, http://i.imgur.com/CT6yf5q.png, http://i.imgur.com/gTwOePB.png", 40, 40); 
    var shadow = Graphic("http://i.imgur.com/50I5K1F.png", 40, 40); 
    var shadow2 = Graphic("http://i.imgur.com/dR9195w.png", 40, 40); 

    var obj2container = new createjs.Container(); 
    // Note that the hero will respawn in the middle of each object if he die. 
    // dirt.createBlockAt(X, Y, W, H); 
    dirt.createBlockAt(0, 40, 40 * 3, 40 * 9); 
    rock.createBlockAt(40 * 4, 40 * 3, 40 * 3, 40); 
    dirt.createBlockAt(40 * 3, 40 * 5, 40 * 4, 40 * 5); 
    rock.createBlockAt(40 * 12, 40 * 6, 40, 40); 
    shadow.createBlockAt(40 * 5 - 20, 40 * 8 - 2, 40, 40, "none", 0.5); 
    shadow.createBlockAt(40 * 4, 40 * 9 - 2, 40, 40, "none", 0.5); 
    rock.createBlockAt(40 * 5 - 20, 40 * 7, 40, 40); 
    rock.createBlockAt(40 * 4, 40 * 8, 40, 40); 
    shadow2.createBlockAt(0, 40 * 9, 40 * 7, 40, "none", 0.5); 
    dirt.createBlockAt(0, 40 * 10, 40 * 14, $(window).height() - (40 * 10)); // Use $(window).height() instead of stage.canvas.height here. stage.canvas.height wasn't set yet. // This will be unnecessary after implementing camera movement. 
    grass.createBlockAt(0, 40 * 1 - 20, 40 * 3, 20, "none"); 
    grass.createBlockAt(40 * 3, 40 * 5 - 20, 40 * 4, 20, "none"); 
    grass.createBlockAt(0, 40 * 10 - 20, 40 * 14, 20, "none"); 

    obj2container.cache(0, 0, $(window).width(), $(window).height()); 
    stage.addChild(obj2container); 

    var data = { 
     images: ["http://i.imgur.com/RjVQ6e1.png"], 
     frames: { 
      width: 30, 
      height: 40 
     }, 
     animations: { 
      stand: 0, 
      run: [1, 2, "runloop", 0.15], 
      runloop: [3, 7, true, 0.15], 
      jump: 11, 
      fall: 12, 
      stopfalling: [13, 15, "stand", 0.25] 
     } 
    }; 
    var spriteSheet = new createjs.SpriteSheet(data); 
    var hero = new createjs.Sprite(spriteSheet, "stand"); 
    hero.offset = 4 + 1; // "+1" is important, change the first number only. 
    hero.regX = hero.offset + 2; 
    hero.regY = hero.offset; 
    hero.width = 30 - (hero.offset * 2) - 10; 
    hero.height = 40 - (hero.offset * 2); 
    hero.xvel = hero.yvel = 0; // Number of pixels the hero will move/8. 

    if (localStorage.x && localStorage.y && localStorage.xpast && localStorage.ypast) { // Was localStorage declared? 
     hero.x = Number(localStorage.x); 
     hero.y = Number(localStorage.y); 
     hero.xpast = Number(localStorage.xpast); 
     hero.ypast = Number(localStorage.ypast); 
    } else { 
     hero.x = hero.xpast = 40; // Very first X. 
     hero.y = hero.ypast = 0; // Very first Y. 
    } 

    hero.jumping = true; 
    hero.airtime = 0; 
    hero.animation = "stand"; 
    stage.addChild(hero); 


    if (typeof Storage === undefined) { 
     alert("Your browser doesn't support saving the game. All changes will be discarted when you leave the page."); 
    } 

    document.addEventListener("keydown", function (evt) { 
     if (evt.keyCode == 87 || evt.keyCode == 38 || evt.keyCode == 32) { // up 
      if (!key.holdingUp && !hero.jumping) { // Check if hero isn't jumping and if user isn't holding the key. 
       key.up = true; 
      } 
     } 
     if (evt.keyCode == 65 || evt.keyCode == 37) { // left 
      key.left = true; 
     } 
     if (evt.keyCode == 68 || evt.keyCode == 39) { // right 
      key.right = true; 
     } 
     if (evt.keyCode == 83 || evt.keyCode == 40) { // down 
      key.down = true; 
     } 
    }); 

    document.addEventListener("keyup", function (evt) { 
     if (evt.keyCode == 87 || evt.keyCode == 38 || evt.keyCode == 32) { // up 
      key.up = false; 
      key.holdingUp = false; 
     } 
     if (evt.keyCode == 65 || evt.keyCode == 37) { // left 
      key.left = false; 
     } 
     if (evt.keyCode == 68 || evt.keyCode == 39) { // right 
      key.right = false; 
     } 
     if (evt.keyCode == 83 || evt.keyCode == 40) { // down 
      key.down = false; 
     } 
    }); 

    stage.on("stagemousedown", function (e) { 
     if (event.which === 1) { 
      mouse.x = e.stageX, 
      mouse.y = e.stageY; 

      if (mouse.x > hero.x + hero.width + touch.tollerance) { 
       key.right = true; 
      } 
      if (mouse.x < hero.x - touch.tollerance) { 
       key.left = true; 
      } 
      if (mouse.x > hero.x - touch.tollerance && mouse.x < hero.x + hero.width + touch.tollerance && mouse.y > hero.y - touch.tollerance && mouse.y < hero.y + hero.height + touch.tollerance) { 
       key.up = true; 
      } 
     } 
    }); 


    stage.on("stagemouseup", function() { 
     setTimeout(function() { 
      key.up = false; 
      key.right = false; 
      key.left = false; 
      key.holdingUp = false; 
     }, 1000/60); // Wait for one tick loop. 
    }); 

    // Collision handler: 

    function collisionHandler(obj1, obj2array) { // MASTERPIECE! 

     // Side-to-side collision handler: 
     objectsCollideAt.top.forEach(function (obj2) { 
      // Top side: 
      if (obj1.ypast + obj1.height < obj2.y && obj1.y + obj1.height >= obj2.y && 
      // Checks if past position X was correct: 
      obj1.xpast + obj1.width >= obj2.x && obj1.xpast <= obj2.x + obj2.width) { 
       hero.yvel = 0; 
       hero.jumping = false; 
       if (hero.airtime > 30) { 
        // hero.xpast and hero.ypast must be set to the same position so it will not cause a collision. 
        hero.x = hero.xpast = Number(localStorage.x); 
        hero.y = hero.ypast = Number(localStorage.y); 
       } else { 
        obj1.y = obj2.y - obj1.height - 1; 
        if (typeof Storage !== undefined && !hero.jumping && hero.y == hero.ypast) { // Checks for localStorage support. 
         localStorage.x = obj2.x + ((obj2.width/2) - (obj1.width/2)); 
         localStorage.y = hero.y; 
         localStorage.xpast = hero.xpast; 
         localStorage.ypast = hero.ypast; 
         //Debugging: 
         //console.log("Stored "+Number(hero.x)+" as "+Number(localStorage.x)+"."); 
        } 
       } 
       hero.airtime = 0; 
      } 
     }); 

     objectsCollideAt.left.forEach(function (obj2) { 
      // Left side: 
      if (obj1.xpast + obj1.width < obj2.x && obj1.x + obj1.width >= obj2.x && 
      // Checks if past position Y was correct: 
      obj1.ypast + obj1.height >= obj2.y && obj1.ypast <= obj2.y + obj2.height) { 
       hero.xvel = 0; 
       obj1.x = obj2.x - obj1.width - 1; 
      } 
     }); 

     objectsCollideAt.right.forEach(function (obj2) { 
      // Right side: 
      if (obj1.xpast > obj2.x + obj2.width && obj1.x <= obj2.x + obj2.width && 
      // Checks if past position Y was correct: 
      obj1.ypast + obj1.height >= obj2.y && obj1.ypast <= obj2.y + obj2.height) { 
       hero.xvel = 0; 
       obj1.x = obj2.x + obj2.width + 1; 
      } 
     }); 

     objectsCollideAt.bottom.forEach(function (obj2) { 
      // Bottom side: 
      if (obj1.ypast > obj2.y + obj2.height && obj1.y <= obj2.y + obj2.height && 
      // Checks if past position X was correct: 
      obj1.xpast + obj1.width >= obj2.x && obj1.xpast <= obj2.x + obj2.width) { 
       hero.yvel = 0; 
       obj1.y = obj2.y + obj2.height + 1; 
      } 
     }); 

     /* 
       Now that every side-to-side collision change was made, 
       the edge-to-edge collision handler will not detect 
       blocked collisions. 
       */ 
     // Edge-to-edge collision handler: 

     objectsCollideAt.left.forEach(function (obj2) { 
      // Top left edge: 
      if (obj1.ypast + obj1.height < obj2.y && obj1.xpast + obj1.width < obj2.x && obj1.y + obj1.height >= obj2.y && obj1.x + obj1.width >= obj2.x) { 
       hero.xvel = 0; 
       obj1.y = obj2.y - obj1.height - 1; 
       obj1.x = obj2.x - obj1.width - 1; 
      } 
      // Bottom left edge: 
      if (obj1.ypast > obj2.y + obj2.height && obj1.xpast + obj1.width < obj2.x && obj1.y <= obj2.y + obj2.height && obj1.x + obj1.width >= obj2.x) { 
       hero.yvel = hero.xvel = 0; 
       obj1.y = obj2.y + obj2.height + 1; 
       obj1.x = obj2.x - obj1.width - 1; 
      } 
     }); 

     objectsCollideAt.right.forEach(function (obj2) { 
      // Top right edge: 
      if (obj1.ypast + obj1.height < obj2.y && obj1.xpast > obj2.x + obj2.width && obj1.y + obj1.height >= obj2.y && obj1.x <= obj2.x + obj2.width) { 
       hero.xvel = 0; 
       obj1.y = obj2.y - obj1.height - 1; 
       obj1.x = obj2.x + obj2.width + 1; 
      } 

      // Bottom right edge: 
      if (obj1.ypast > obj2.y + obj2.height && obj1.xpast > obj2.x + obj2.width && obj1.y <= obj2.y + obj2.height && obj1.x <= obj2.x + obj2.width) { 
       hero.yvel = hero.xvel = 0; 
       obj1.y = obj2.y + obj2.height + 1; 
       obj1.x = obj2.x + obj2.width + 1; 
      } 
     }); 
    } 

    function changeAnimation(obj1, frameOrAnimation) { 
     if (obj1.animation != frameOrAnimation) { 
      obj1.animation = frameOrAnimation; 
      obj1.gotoAndPlay(frameOrAnimation); 
     } 
    } 

    // Tick: 

    createjs.Ticker.on("tick", tick); 
    createjs.Ticker.setFPS(60); 

    function tick(event) { 

     if (key.up && !hero.jumping && !key.holdingUp && Math.abs(hero.ypast - hero.y) < 6) { // Distance between last frame and actual frame y must be less than 6px. 

      // KNOWN BUG: SOMETIMES THE JUMP HEIGHT DOUBLE! [IMPORTANT] 
      // Diagnostic: None. 
      // Reproduction: This bug normally occur during lags and was amplified after implementing time-based logic. 
      // Solution: Unknown. 

      hero.yvel -= 145; // How much speed the jump will produce. Please avoid changing this number — Speeds over 200 can kill the hero. 
      hero.jumping = true; 
      key.holdingUp = true; // Prevent jumping multiple times while holding the key. 
     } else { 
      if (hero.yvel < 0) { 
       hero.yvel += 3; 
      } 
     } 
     if (key.left && !key.right) { 
      hero.xvel -= (!hero.jumping) ? 3 : 2; 
      hero.regX = hero.offset + 12; // Need review. 
      hero.scaleX = -1; 
     } 
     if (key.right && !key.left) { 
      hero.xvel += (!hero.jumping) ? 3 : 2; 
      hero.regX = hero.offset + 2; // "+2" is due to the head's opposite side. 
      hero.scaleX = 1; 
     } 
     if (key.down) { 
      //hero.yvel+=3; // Commented because there's no need for pushing the hero down. If uncommented: // Need review. 
     } 

     hero.xvel = (hero.xvel > 0) ? Math.min(hero.xvel, 50) : Math.max(hero.xvel, -50); 
     //hero.yvel = (hero.yvel > 0)?Math.min(hero.yvel, 125):Math.max(hero.yvel, -125); // No need for this, there's gravity already. 


     if (hero.jumping == true) { 
      if (hero.yvel < 50) { 
       changeAnimation(hero, "jump"); 
      } else { 
       changeAnimation(hero, "fall"); 
      } 
     } 

     if (hero.ypast != hero.y && hero.yvel > 0) { 
      hero.airtime++; 
      changeAnimation(hero, "fall"); 
     } 
     if (hero.airtime > 100) { 
      // hero.xpast and hero.ypast must be set to the same position so it will not cause a collision. 
      hero.x = hero.xpast = 0; 
      hero.y = hero.ypast = 0; 
     } 
     if (!key.left && !key.right) { 
      if (!hero.jumping) { 

       if (hero.animation == "fall" || hero.animation == "stopfalling") { 
        changeAnimation(hero, "stopfalling"); 
       } else { 
        changeAnimation(hero, "stand"); 
       } 

       if (hero.xvel != 0) { 
        hero.xvel += (hero.xvel < 0) ? 5 : -5; 
       } 
      } else { 
       if (hero.xvel != 0) { 
        hero.xvel += (hero.xvel < 0) ? 2 : -2; 
       } 
      } 
      if (Math.abs(hero.xvel) < 3) { 
       hero.xvel = 0; 
      } 
     } else { 
      if (!hero.jumping && hero.xvel != 0) { // Not jumping, pressing left or right 
       changeAnimation(hero, "run"); 
      } 
     } 

     setTimeout(function() { 
      hero.yvel += 7; 
     }, 250); 

     hero.xpast = hero.x; 
     hero.ypast = hero.y; 
     hero.x += Math.round(event.delta/1000 * (hero.xvel * 6)); 
     hero.y += Math.round(event.delta/1000 * (hero.yvel * 6)); 

     collisionHandler(hero, objectsCollideAt.it); 

     stage.update(); 
    } 

    // Canvas resizing: 
    var resizeCanvas = function() { 
     stage.canvas.width = window.innerWidth; 
     stage.canvas.height = window.innerHeight; 
    } 
    resizeCanvas(); 
    $(window).on('resize', resizeCanvas); 
} 

// Image preloading (Primitive!): 

function loadImgs(src, callback) { 
    var sprite = new Image(); 
    sprite.onload = callback; 
    sprite.src = src; 
} 
loadImgs("http://i.imgur.com/RjVQ6e1.png", function() { // Hero Sprite 
    loadImgs("http://i.imgur.com/zF6Lhfl.png", function() { // Dirt 
     loadImgs("http://i.imgur.com/gTwOePB.png", function() { // Grass 3 
      loadImgs("http://i.imgur.com/CT6yf5q.png", function() { // Grass 2 
       loadImgs("http://i.imgur.com/5SkIyyM.png", function() { // Grass 
        loadImgs("http://i.imgur.com/QgxGfJs.png", function() { // Rock 
         loadImgs("http://i.imgur.com/50I5K1F.png", function() { // Shadow 
          loadImgs("http://i.imgur.com/dR9195w.png", function() { // Shadow2 
           init(); 
          }); 
         }); 
        }); 
       }); 
      }); 
     }); 
    }); 
}); 

JSFiddle

Répondre

0

que j'ai trouvé le problème dans mon code. Cela ne fonctionnait pas en raison de la condition event.which == 1 dans le gestionnaire d'événements "stagemousedown". Cela se produit car, au moins sur iOS, le event.which est égal à 0.

Voici mon dernier gestionnaire d'événements stagemousedown:

stage.on("stagemousedown", function (e) { 
    if (event.which < 2) { 
     mouse.x = e.stageX, 
     mouse.y = e.stageY; 

     if (mouse.x > hero.x + hero.width + touch.tollerance) { 
      key.right = true; 
     } 
     if (mouse.x < hero.x - touch.tollerance) { 
      key.left = true; 
     } 
     if (mouse.x > hero.x - touch.tollerance && mouse.x < hero.x + hero.width + touch.tollerance && mouse.y > hero.y - touch.tollerance && mouse.y < hero.y + hero.height + touch.tollerance) { 
      key.up = true; 
     } 
    } 
}); 

JSFiddle

Questions connexes