2012-04-06 23 views
1

私はHTML5(およびOO Javascript)を学習中です。単純なゲームエンジンを作成しようとしていますが、キャンバスへのレンダリングは非常に奇妙な条件下で動作します。 Hereは、ページへのリンクであり、ここで私のindex.htmlです:最初にロードされると

HTML5 Canvas rendering odd odd

<html> 
<head> 
    <script type="text/javascript"> 
     function load() 
     { 
      var game = new Game(); 
      game.start(); 
     } 
    </script> 
    <title>Game</title> 
    <style> 
     canvas 
     { 
      outline:0; 
      border:1px solid #000; 
      margin-left: auto; 
      margin-right: auto; 
     } 
    </style> 
</head> 
<body onload="load()"> 
    <canvas id='c'></canvas> 

    <script src="classes/Tuple.js"></script> 
    <script src="classes/Rect.js"></script> 
    <script src="classes/Sprite.js"></script> 
    <script src="classes/Game.js"></script> 
</body> 
</html> 



が、それは、Firefox 11.0でNS_ERROR_DOM_TYPE_MISMATCH_ERR例外とTypeError例外を与える Chrome 18.0の例外それを動作させるには:

Firefoxの11.0

  • は、アドレスバーにURLを選択して、手動で入力するか、または
  • リフレッシュボタンや
  • F5キーを押しをクリックしますヒット。

クローム18.0

  • は、アドレスバーにURLを選択して、手動で入力するか、または
  • リフレッシュボタンや
  • [F5]キーを押しOR
  • Shiftキーを押しながら/ Ctrlキー+ F5をクリックしてくださいヒット。
  • 私は疑う何

- ただ、推測ではなくの.jsファイルのいずれかが、それが最初のページのロード時に呼び出された時点でレディ/利用できないように思えます。 Firebugで数回ステップを踏んで、スプライトイメージが最初のページリクエストにロードされることはないようです。

Game()のインスタンス化が行われ、キャッシュされ、2ページ目のロードだけが利用可能なため、一部の.jsファイルがまだダウンロードされていますか?

アイデア?私はあなたのそれに感謝します、ありがとう!

+0

私はGame.jsを4つのインクルードの最初のものにしましたが、私は同じ動作をしているようです(私はリフレッシュされたので、キャッシュされたコピーから外れません) –

答えて

3

ファイルをローカルにコピーしてテストしました。それはあなたのスプライトが利用できないJavaScriptファイルではないように私に見えます。

Game.startに電話するまで、PNGは読み込まれません。次の場合:

roadSpritesheetImage.src = "assets/sprites/player/playerSpriteSheet.png"; 

これで、画像の非同期ダウンロードが開始されます。残りのコードはイメージが完全にロードされる前に実行されるため、イメージをスライスするときにsrc属性がnullの場合と同じようにスライスします。

これは、リフレッシュすることができ、すべてが正常に動作する理由です。イメージがキャッシュされています。

あなたは一種のちょうどキャンバスの前にイメージタグを追加することで、スプライトのロードを先取りすることができます体のloadイベントが(画像を含む)内容までは解雇されていないため、

<img src="assets/sprites/player/playerSpriteSheet.png" style="display:none;" /> 

はこれが働くだろうさ(私はこれを見なければならないと信じています)。次に、このイメージをimg.srcに割り当てると、キャッシュされたイメージが参照されます。

また、残りのゲーム機能をimg.onloadにバインドすることもできます。例:

self.loadSprites = function() 
{ 
    var roadSpritesheetImage = new Image();  
    roadSpritesheetImage.onload = function() { 
     self.entities.push(new Sprite("testTile", 
      roadSpritesheetImage, 
      new Tuple(16, 16), 
      new Rect(0, 0, 32, 16))); 
     self.run(); 
    }; 

    roadSpritesheetImage.src = "assets/sprites/player/playerSpriteSheet.png"; 
}; 

self.run = function() { 
    var drawSuccessful = false; 
    drawSuccessful = self.entities[0].draw(self.context); 
    self.entities[0].nextFrame(); 

    //if we managed to draw the Sprite successfully without any raised exceptions 
    if(drawSuccessful) { 
     setTimeout(self.run, 300); 
    } else { alert("stopping execution of the game."); } 
}; 

self.start = function() 
{ 
    self.loadSprites(); 
}; 

これは少しクリーナーであり、リソースとの競合状態を保証しません。

ソース画像からN-puzzleを作成するために作成したjQueryプラグインで同様の問題が発生しました。 this MDN documentationは非常に便利でしたが、キャンバスの代わりにスライスされたdivを使用しました。

+0

ありがとうございました! Chromeタイムライン機能の読み込みプロセスを見て、私は同じことを疑うようになりました。 しかし、私は、新しいImage()オブジェクトを宣言すると、処理が始まるまで画像がロードされるまで待つと仮定しました。私は今、それがそうでないことを見る。 これは新しいアカウントですので、私はあなたの投稿をupvoteするのに十分な評判はありませんが、私はそうするでしょう。もう一度ありがとう、あなたは私に数時間の混乱を救った! –

+1

@AlexAlksne、答えとしてマークすることができます。今度は、2つ以上のスプライトをロードするときに考慮する必要があります。 'self.run()'はすべてがロードされるまで呼び出されません。 – Alexander

+0

@AlexAlksne問題ありません。このような場合、ローディング時間を捕まえるのが難しいかもしれません...特にスプライトがわずか4Kである場合。 –