2015-10-21 3 views
0

В настоящее время я пытаюсь понять, как делать преобразования матриц при рисовании объектов в html5, но различные объяснения, обнаруженные в нескольких разных источниках информации, вызвали некоторую путаницу. Я нашел информацию о том, что для анимации рисованных объектов в html5, как видно, here, хотя я также видел, что преобразования могут быть применены к отдельным объектам на странице путем преобразования рисованной точки, но я не совсем уверен, как это работает.Функциональность преобразования матрицы html5

Я нашел образец кода, который реализует анимацию ног (две строки), но делает анимацию без применения преобразований к холсту, используя объект функции для матрицы преобразования, определенной в каком-либо другом файле. Код обеспечивает собственную реализацию moveTo() и lineTo() (которые обычно используются с объектом canvas), в которых он преобразует точку, переданную в нее, перенастраивает ее положение на основе окна просмотра, а затем вызывает версию перемещения холста к передаче в преобразованной точки.

Итак, здесь есть несколько путаниц: 1. Какова цель реализации новой функции преобразования объекта преобразования, когда setTransform() может использоваться только на холсте? 2. Способы, подобные rotate() и translate(), вызываются на объект-матрицу без передачи точки, так как применяются какие-либо из этих операций? 3. Когда преобразования должны применяться ко всему холсту (как это сделано в предоставленной ссылке), а не к конкретным объектам, нарисованным, как кажется, что оба могут работать?

Я вообще просто ищу общий обзор этого, поскольку я довольно смущен тем, как это работает. Код из примера ниже для справки:

<head> 
<script src=g.js></script> 
<script src=matrix4x4.js></script> 
</head> 
<body onload=g_start()> 
<canvas id=myCanvas1 width=480 height=480></canvas> 
<script> 
    var w, h, g; 

    function viewport(p) { 
     return [ w/2 * p[0] + w/2, h/2 - p[1] * w/2 ]; 
    } 

    function moveTo(p) { 
     var q = m.transform(p); // APPLY 3D MATRIX TRANFORMATION 
     var xy = viewport(q); // APPLY VIEWPORT TRANSFORM 
     g.moveTo(xy[0], xy[1]); 
    } 

    function lineTo(p) { 
     var q = m.transform(p); // APPLY 3D MATRIX TRANFORMATION 
     var xy = viewport(q); // APPLY VIEWPORT TRANSFORM 
     g.lineTo(xy[0], xy[1]); 
    } 

    myCanvas1.animate = function(_g) { 
     g = _g; 
     w = g.canvas.width; 
     h = g.canvas.height; 

     g.fillStyle = 'rgb(200,140,255)'; 
     g.beginPath(); 
     g.moveTo(0, 0); 
     g.lineTo(w, 0); 
     g.lineTo(w, h); 
     g.lineTo(0, h); 
     g.lineTo(0, 0); 
     g.stroke(); 

     g.fillStyle = 'rgb(128,0,0)'; 
     g.strokeStyle = 'rgb(0,0,0)'; 

     var legBend = .4; 

     var t = 3 * time; 

     for (var leg = 0 ; leg < 2 ; leg++) { 
    var angle = -Math.PI/2 * (1 + Math.sin(time)); 
    console.log(angle); 
     var sign = (leg == 0) == (angle < -Math.PI/2) ? -1 : 1; 

     m.identity(); 
     m.rotateY(-Math.PI/2 * (1 + Math.sin(time))); 

     g.beginPath(); 

     m.translate(0, .5, .1 * sign); 
     moveTo([0,0,0]);    // HIP 

     m.rotateZ(-.5 * legBend + sign * legBend * Math.cos(t)); 

     m.translate(0, -.5, 0); 

     lineTo([0,0,0]);    // HIP 

     m.rotateZ(2 * legBend + 2 * legBend * sign * Math.sin(t)); 
     m.translate(0, -.5, 0); 
     lineTo([0,0,0]);    // KNEE 

     m.translate(-.1, 0, 0); 
     lineTo([0,0,0]);    // KNEE 

     g.strokeStyle = 'rgb(0,0,0)'; 
     g.lineWidth = 30; 
     g.stroke(); 

     g.strokeStyle = 'rgb(255,0,0)'; 
     g.lineWidth = 20; 
     g.stroke(); 
     } 
    } 

</script> 
</body> 
+2

Это физически больно, чтобы не видеть цитаты вокруг 'src = g.js'. –

ответ

1

Важные понятия трансформации html5 холст:

  • Все способы трансформации холст (а также .transform) работают относительно текущего холста происхождения и этому происхождению задана координата [0,0]. Исходное начало находится в верхнем левом углу холста. .setTransform оба сбросят текущее начало холста, а затем сделают преобразования относительно этого источника возврата.

  • Трансформации не влияют на существующие чертежи. Поэтому fillRect (0,0), за которым следует перевод (5,0), не будет перемещать уже вытянутый прямоугольник. Существующий прямоугольник по-прежнему будет отображаться в верхнем левом углу холста.

  • Трансформации действительно влияют на новые рисунки.

  • Метод translate будет перемещать начало координат на указанные расстояния x, y. Таким образом, перевод (5,0) приведет к тому, что начало рисования холста [0,0] будет 5 пикселей с левой стороны холста. Поэтому translate (5,0), за которым следует fillRect (0,0), заставит новый прямоугольник отображать 5 пикселей с левой стороны холста.

  • Преобразования на самом деле переводят (перемещают), поворачивают, масштабируют всю поверхность рисования холста. Поэтому новые чертежи не перемещаются индивидуально, не поворачиваются и не масштабируются. Новый рисунок выглядит перемещенным, повернутым или масштабированным, потому что вся поверхность рисования холста была перемещена, повернута или масштабирована.

  • Преобразование является совокупным.Поэтому, если вы переводите (5,0), а затем переводите (0,50), начало холста [0,0] будет в 5 пикселей слева и 50 пикселей сверху. Так fillRect (0,0) будет нарисовано 5 пикселей слева и 50 пикселей сверху.

Таким образом, чтобы ответить на ваши вопросы:

  1. Последовательные преобразования являются полезными, поскольку преобразования являются накопительными. Поэтому, чтобы заставить изображение человека «двигаться», вы можете использовать кумулятивные эффекты преобразований, не задумываясь о своей последней позиции или не вычисляя свою новую позицию.

    // the person image will move across the canvas in 5px increments over time 
    // No need to remember its last location 
    // No need to calculate its new position 
    // That's because the canvas internally remembers & calculates its own origin. 
    for(var i=0;i<20;i++){ 
        context.clearRect(0,0,canvas.width,canvas.height); 
        context.translate(5,0); 
        context.drawImage(person,0,0); 
        // wait 1 second 
    } 
    
  2. Поскольку все преобразования относительно текущего холста происхождения координат, вам не нужно повторно указать, что координаты для любого способа трансформации - холст «помнит» свое нынешнее происхождение для вас.

  3. Индивидуальные рисунки на холсте не подвержены изменениям. Трансформации перемещают весь холст, а новые рисунки просто «идут на прогулку». Любые чертежи, которые существовали до преобразований, не были затронуты этими последующими преобразованиями - ранее существовавшие чертежи остаются точно там, где они были сначала нарисованы.

+0

Спасибо за ответ! Итак, вы говорите, что всякий раз, когда вы делаете преобразования в html5, вы можете применять преобразования только ко всему холсту, а не к конкретным объектам (т. Е. Без использования '' 'setTransform()' '')? Мне просто показалось, что в этом примере функция '' 'transform()' '' может применять свой собственный вид преобразования, который не использует '' 'setTransform()' '', потому что эта функция работает только с 2D линии, когда эта программа работает с 3d. – loremIpsum1771

+0

Также, если использование '' 'setTransform()' '' является единственным способом реализации метода '' 'Transform()' '', как вы можете использовать его с 3d-фигурами, b/c, я в настоящее время использую jquery чтобы получить контекст с '' 'canvas.getContext (" 2d ")' '', но я не знаю, есть ли способ сделать это в 3d. – loremIpsum1771

Смежные вопросы