2014-07-13 83 views
2

我想繪製簡單的矩形圖像到畫布。我有一個四點像一個;用點畫圖像到畫布

  • (0)345223
  • (1)262191
  • (2)262107
  • (3)347,77

渲染矩形和圖象是波紋管;

render image

什麼是做到這一點的最佳做法?

回答

0

那真是有趣。 10多年來沒有做過軟件紋理映射。懷舊很棒,但openGL更好。 :D

基本上,這個想法是繪製圖像的垂直切片。 ctx只允許我們繪製垂直或水平拉伸的圖像或其中的一部分。因此,爲了解決這個問題,我們將圖像分成垂直切片,將其中的每一個拉伸以填充1像素寬的矩形,並從頂部邊緣到底部邊緣。

首先,我們計算頂部和底部邊緣的斜率。這對應於在+ X方向上行進的每個像素邊緣上升(或下降)的量。接下來,由於圖像可能大於或小於要繪製的圖像,因此我們必須計算出畫布中X方向1個像素對應的條帶寬度。

注意,它是不透視正確的。畫布右邊的每一步表示圖像上相同寬度切片的一個步驟 - 透視正確映射將跨越圖像寬度變化數量。隨着圖像距離我們越來越近,越來越少。

最後,應該指出的是,有一些關於輸入座標的假設。

  1. 的COORDS顯示爲對x和y的
  2. 的COORDS列表與左上角
  3. 的COORDS必須沿順時針方向
  4. 的左邊緣和右列出開始邊必須是垂直的。

在這些假設下堅持,我得到如下:

結果 enter image description here

代碼:

<!DOCTYPE html> 
<html> 
<head> 
<script> 
function byId(e){return document.getElementById(e);} 
function newEl(tag){return document.createElement(tag);} 

window.addEventListener('load', onDocLoaded, false); 

function onDocLoaded() 
{ 
    var mImg = newEl('img'); 
    mImg.onload = function() { stretchImage(this, quadPoints, byId('tgtCanvas')); } 
    mImg.src = imgSrc; 
} 

var quadPoints = [ [262,107], [347,77], [347,223], [262,191] ]; 
var imgSrc = "img/rss128.png"; 

function stretchImage(srcImgElem, points, canvasElem) 
{ 
    var ctx = canvasElem.getContext('2d'); 

    var yTopStart = points[0][1]; 
    var yTopEnd = points[1][1]; 
    var tgtWidth = points[1][0] - points[0][0]; 
    var dX = tgtWidth; 
    var topDy = (yTopEnd-yTopStart)/dX; 

    var yBotStart = points[3][1]; 
    var yBotEnd = points[2][1]; 
    tgtWidth = points[2][0] - points[3][0]; 
    dX = tgtWidth; 
    var botDy = (yBotEnd-yBotStart)/dX; 

    var imgW, imgH, imgDx; 
    imgW = srcImgElem.naturalWidth; 
    imgH = srcImgElem.naturalHeight; 
    imgDx = imgW/dX; 

    var curX, curYtop, curYbot, curImgX; 
    var i = 0; 
// ctx.beginPath(); 
    for (curX=points[0][0]; curX<points[1][0]; curX++) 
    { 
     curYtop = yTopStart + (i * topDy); 
     curYbot = yBotStart + (i * botDy); 

     curImgX = i * imgDx; 

//  ctx.moveTo(curX, curYtop); 
//  ctx.lineTo(curX, curYbot); 

     var sliceHeight = curYbot - curYtop; 
//  console.log(sliceHeight); 
     ctx.drawImage(srcImgElem, curImgX, 0, 1,imgH, curX, curYtop, imgDx, sliceHeight); 

     i++; 
    } 
// ctx.closePath(); 
// ctx.stroke(); 
} 

</script> 
<style> 
canvas 
{ 
    border: solid 1px black; 
} 
</style> 
</head> 
<body> 
    <canvas width=512 height=512 id='tgtCanvas'></canvas> 
</body> 
</html> 

Src的圖像: enter image description here

+0

其修正了該點。我怎麼能在其他矩形中做到這一點。請檢查以下鏈接以查看我的示例http://zor.lu/lab1/domino1/cube_2.html –

+0

呵呵。有趣的是,我認爲提及persepctive-correctness完全是相關的,但想確保。那麼,就你而言,你需要內插屏幕位置的Y和X座標,也就是紋理U,V座標(紋理的x和y)。您需要爲本質上不同的問題找到/移植不同的代碼。這兩個鏈接可能是有趣的:http://tulrich.com/geekstuff/canvas/perspective.html和http://learningwebgl.com/blog/?p=507 – enhzflep

+0

也可以查看http://stackoverflow.com/問題/ 4097688 /抽取失真,圖像上html5s畫布/ 30088700#30088700 –