3

角丸四角形のグリッドを描画しましたが、それらを画像の背景で塗りつぶす必要があります。最終的には多くの画像の背景ができるようになりますが、今のところ、1 つの画像で動作するようにしようとしています。私は近くにいます、私の長方形は描画しますが、塗りつぶしは少し奇妙です. パスを「クリップ」しようとしましたが、1 つの四角形だけが塗りつぶされます。何が間違っているのかわかりません。キャンバスの専門家がそれを見つけてくれることを願っていますか?

/* build rounded rectangle */
var roundedRect=function(ctx,x,y,width,height,radius,fill,stroke) 
{ 

 ctx.save(); // save the context so we don't mess up others ctx.beginPath(); 

// draw top and top right corner ctx.moveTo(x+radius,y);
ctx.arcTo(x+width,y,x+width,y+radius,radius); 

// draw right side and bottom right corner 
ctx.arcTo(x+width,y+height,x+width-radius,y+height,radius); 

// draw bottom and bottom left corner 
ctx.arcTo(x,y+height,x,y+height-radius,radius); 

// draw left and top left corner 
ctx.arcTo(x,y,x+radius,y,radius); 
ctx.clip(); 

if(fill){ ctx.fill(); } 

if(stroke){ ctx.stroke(); } 

 ctx.restore(); // restore context to what it was on entry 
} 

/* onload, fill canvas with pattern of rounded rectangles separated by 2px */
window.onload = function() {
var canvas = document.getElementById("canvas");
/* rounded filled rectangle pattern */
var canvasWidth=530;
    var canvasHeight=530;
    var recWidth=42;
    var recHeight=42;
    var grout=2;
    var radius=2;
    var cols=canvasWidth/(recWidth+grout);
    var rows=canvasWidth/(recHeight+grout);


    /* loop through each row/column to build pattern */
    alert("rows" + rows + " & cols " + cols);
    for (i=1; i<rows; i++){
        for (j=1; j<cols; j++){
            var ctx = canvas.getContext("2d");
            /* fill pattern */
            var img=document.getElementById("poppy");
            var pat=ctx.createPattern(img,"repeat");
            ctx.fillStyle=pat;  
            roundedRect(ctx,(j*grout + (j-1)*recWidth),(i*grout + (i-1)*recHeight),recWidth,recHeight,radius,true,false);       

                }
             }
};
4

1 に答える 1

2

問題がこの JSFiddle: http://jsfiddle.net/hBEwr/で再現されると仮定しましょう。(そうでない場合、この回答の残りは ~bunk です。正確な問題に合わせて編集してください。)

  1. 式からパターンを完全に削除すると、直接の原因ではないことがわかります。
    http://jsfiddle.net/hBEwr/1/
    代わりに、丸みを帯びた四角形は、それらの間に必要なグラウトを残していません。

  2. すべてが重なり合っているため、塗りつぶしの色を不透明度の低い青に変更します。面白い!
    http://jsfiddle.net/hBEwr/2/
    多くのパスが何度も描画されていることがわかります。この洞察により、 の実装をroundedRect()より詳しく調べて、 を決して呼び出さないことに気付くようになりますbeginPath()。実際、上記の質問のコードでは、コメントに食い​​込まれたようです。この呼び出しがないと、 を呼び出すたびに、最初からやり直すのではなく、拡大し続けるパスに追加roundedRect()の四角形が追加されます。

  3. backへの呼び出しを追加すると、beginPath()成功への道を歩んでいることがわかります:
    http://jsfiddle.net/hBEwr/3/

  4. これで、パターンを追加して (若干の変更を加えて)、輝かしい勝利を収めることができます:
    http://jsfiddle.net/hBEwr/4/
    ポピー! ポピー! ポピー!

私が行った他の小さな調整に関するいくつかのメモ:

  • 常にvarローカル変数を確認してください:

    for (i=0; i<10; i++)     // Oops! i is a global variable
    for (var i=0; i<10; i++) // Much better
    
  • 、 、を再取得しctximgタイルごとにパターンを作成するのは効率的ではありません。上記の最終的なコードでは、単純さと速度のためにこれらをループの外に移動しました。

  • console.log多くの場合、デバッグの代わりに使用alertする方がはるかに簡単です。(開発者コンソールを開いて出力を確認します。)

  • グラウトの最後の外側の行/列を列の計算に追加して、それが含まれるスペースがあることを確認しました。使う・使わないはお好みで。

于 2012-07-13T03:27:58.400 に答える