2013-03-27 44 views
25

Tôi đang cố gắng ánh xạ hình ảnh tới lưới "3d" mô phỏng vải bằng strokeStyle và canvas, tôi có hình ảnh được bao gồm nhưng hiện đang hoạt động dưới dạng hình nền và không thực sự chảy với "vải" như gợn sóng, IE hình ảnh tĩnh như lưới chảy. đây là số jsfiddle tự giải thích (chỉ hoạt động trong Chrome). bất kỳ trợ giúp nào được đánh giá cao. đây là javascript mà ám ảnh vào nền, Làm thế nào để tôi ngăn chặn từ render làm hình nền và chỉ làm cho nó lấp đầy lưới ?:html5 canvas strokeStyle?

function update() { 

    var img = new Image(); 
    img.src = 'http://free-textures.got3d.com/architectural/free-stone-wall- textures/images/free-stone-wall-texture-002.jpg'; 
    img.onload = function() { 

     // create pattern 
     var ptrn = ctx.createPattern(img, 'repeat'); 

     ctx.clearRect(0, 0, canvas.width, canvas.height); 

     physics.update(); 

     ctx.strokeStyle = ptrn; 
     ctx.beginPath(); 
     var i = points.length; 
     while (i--) points[i].draw(); 
     ctx.stroke(); 

     requestAnimFrame(update); 
    } 
} 

Hers là bản gốc codepen Tôi đang làm việc từ. `cập nhật fiddle với hình ảnh bên ngoài cập nhật chức năng(): Nó hiện tại dường như thực sự điền vào các tế bào cũng như áp dụng nó như là một hình nền. là có cách nào để ngăn chặn nó trở thành một hình ảnh nền và chỉ áp dụng nó để điền vào lưới điện? Tôi đã thử điều này:
ctx.fillStyle = ptrn; và xóa dòng 260:
ctx.strokeStyle = ptrn; nhưng có vẻ như xóa hình nền chỉ hiển thị hình ảnh dưới dạng lưới đen ... cảm ơn bạn một lần nữa vì sự kiên nhẫn

+0

không, tôi không mong đợi bất kỳ ai sửa mã tường của câu hỏi chính xác của tôi là: Làm cách nào để ánh xạ hình ảnh vào lưới, cập nhật hàm() { var img = new Image(); img.src = 'file: /// C: /Users/CL%20Ceintuurbaan/Desktop/texture_2.jpg'; img.onload = function() { // tạo mẫu var ptrn = ctx.createPattern (img, 'lặp lại'); \t ctx.clearRect (0, 0, canvas.width, canvas.height); \t physics.update(); \t ctx.strokeStyle = ptrn; \t ctx.beginPath(); \t var i = points.length; \t trong khi (i--) điểm [i] .draw(); \t ctx.stroke(); \t requestAnimFrame (cập nhật); } } Chức năng có xử lý hiển thị hình ảnh không. – vimes1984

+0

hãy để tôi chỉnh sửa câu hỏi xin lỗi vì sự bất tiện này. – vimes1984

+0

OK, tôi hiểu rồi. Nhưng tôi e rằng bạn sẽ phải tạo một 'drawImage' trên mỗi ô của bức tường. –

Trả lời

33

Oh my! Câu hỏi tuyệt vời!

Vì vậy, hãy xem những gì chúng tôi có. Một hệ thống có một loạt các "ràng buộc", là các bộ gồm 2 điểm. Contraints tự đi theo cặp, và họ thực hiện hai dòng, tạo thành một hình dạng (phía dưới bên phải của một hộp).

Nếu chúng ta để vẽ mỗi dòng hạn chế cá nhân chúng tôi muốn thấy điều này:

boxes!

Đó là tất cả các dòng màu đỏ ngang và đường màu xanh dọc. Vẽ một hình duy nhất chúng ta sẽ thấy rằng hình dạng , và mỗi đường màu đỏ dài thực sự là hàng trăm dòng nhỏ, đáy của mỗi hình dạng , kết thúc để kết thúc. Có hàng trăm s ở đây, và cùng nhau chúng làm cho nó trông giống như một lưới kết dính. Thực tế là mỗi người đã là cá nhân làm cho điều này dễ dàng cho chúng tôi.

Hình dạng đó là tất cả những gì chúng tôi cần để xác định một hộp giới hạn sắp xếp. Và có vẻ như mỗi Point trong một Constraint có các giá trị ban đầu, vì vậy, chúng tôi sẽ lưu các giá trị đó dưới dạng sxsy.

Nếu chúng ta biết giới hạn của các hộp tại vị trí mới của chúng, và chúng ta biết các giới hạn ban đầu, chúng tôi đã lưu tất cả các giá trị của điểm cho các Contraints, sau đó chúng ta nên vàng.

Một khi chúng ta có hộp bounding ban đầu của một Hạn chế và khung giới hạn hiện tại của nó, tại sao, tất cả chúng ta phải làm là gọi drawImage với cả hai ô: ctx.drawImage(img, sx, sy, sw, sh, dx, dy, dw, dh);

Tôi đã viết một Constraint.prototype.draw thói quen mới, Nó trông giống như thế này :

yeah!

more yeah!

Và vân vân.

Có một vài cách bạn có thể "vá" các lỗ, và nó thực sự tùy thuộc vào bạn, nếu không bạn sẽ phải kết thúc với các phép biến đổi.

Hãy xem mã. Tôi không thay đổi nhiều. Tìm kiếm !!! trong mã (các chỉnh sửa của tôi) và DEBUG: trong mã (mã gỡ lỗi trong trường hợp hình ảnh không tải hoặc bạn muốn xem các wireframes).

http://jsfiddle.net/simonsarris/Kuw6P/

Mã này là dài vì vậy tôi không muốn dán nó tất cả ở đây, nhưng đây là một bản sao lưu trong trường hợp jsfiddle đi xuống: https://gist.github.com/simonsarris/5405304

Và đây là phần phù hợp nhất:

// !!! new super awesome draw routine! So cool we skipped naming it draw2! 
Constraint.prototype.draw3 = function(otherP2) { 

    // NOW dear friends consider what we have. Each box is made out of two lines, 
    // the bottom and rightmost ones. 
    // From these lines we can deduce the topleft and bottom-right points 
    // From these points we can deduce rectangles 
    // From the skewed rectangle vs the original rectangle we can "stretch" 
    // an image, using drawImage's overloaded goodness. 

    // AND WE'RE OFF: 

    // destination rect has 2 points: 
    //top left: Math.min(this.p2.x, otherP2.x), Math.min(this.p2.y, otherP2.y) 
    //bottom right: (this.p1.x, this.p1.y) 

    // image destination rectangle, a rect made from the two points 
    var dx = Math.min(this.p1.x, Math.min(this.p2.x, otherP2.x)); 
    var dy = Math.min(this.p1.y, Math.min(this.p2.y, otherP2.y)); 
    var dw = Math.abs(this.p1.x - Math.min(this.p2.x, otherP2.x)); 
    var dh = Math.abs(this.p1.y - Math.min(this.p2.y, otherP2.y)); 
    // DEBUG: IF THERE IS NO IMAGE TURN THIS ON: 
    //ctx.strokeStyle = 'lime'; 
    //ctx.strokeRect(dx, dy, dw, dh); 

    // source rect 2 points: 
    //top left: Math.min(this.p2.sx, otherP2.sx), Math.min(this.p2.sy, otherP2.sy) 
    //bottom right: (this.p1.sx, this.p1.sy) 

    // these do NOT need to be caluclated every time, 
    // they never change for a given constraint 
    // calculate them the first time only. I could do this earlier but I'm lazy 
    // and its past midnight. See also: http://www.youtube.com/watch?v=FwaQxDkpcHY#t=64s 
    if (this.sx === undefined) { 
    this.sx = Math.min(this.p1.sx, Math.min(this.p2.sx, otherP2.sx)); 
    this.sy = Math.min(this.p1.sy, Math.min(this.p2.sy, otherP2.sy)); 
    this.sw = Math.abs(this.p1.sx - Math.min(this.p2.sx, otherP2.sx)); 
    this.sh = Math.abs(this.p1.sy - Math.min(this.p2.sy, otherP2.sy)); 
    } 
    var sx = this.sx; 
    var sy = this.sy; 
    var sw = this.sw; 
    var sh = this.sh; 
    // DEBUG: IF THERE IS NO IMAGE TURN THIS ON: 
    //ctx.strokeStyle = 'red'; 
    //ctx.strokeRect(sx, sy, sw, sh); 


    // IF we have a source and destination rectangle, then we can map an image 
    // piece using drawImage(img, sx, sy, sw, sh, dx, dy, dw, dh) 
    // Only problem, we're not exactly dealing with rectangles.... 
    // But we'll deal. Transformations have kooties anyways. 
    ctx.drawImage(img, sx, sy, sw, sh, dx, dy, dw, dh); 
};