как использовать кадр анимации запроса в коде, который следует следующему шаблону?

Я решал эту проблему уже несколько дней. Я впервые написал свой код в шаблоне конструктора. Я хочу увеличить высоту 10 строк Безье в переходе. в анимации). Поэтому я, наконец, прибегнул к requestAnimationFrame. Но из-за этого шаблона конструктора я полностью запутался, где его включить и какие изменения нужно внести.

Это то, что я сделал до сих пор --- JSFIDDLE

Таким образом, в основном я буду расширять свои endY и cpY1 и cpy2 в переходе. При наведении курсора мыши на холст высота всех линий Безье должна увеличиваться в переходе, придавая ощущение анимации.

ЯВАСКРИПТ:

//for entire code please have a look at the fiddle.this is just 10% of my code
//for simplification purpose,you can use 3 instances instead of 9!!!
    (function() {
        hair = function() {
            return this;
        };


    hair.prototype={

     draw_hair:function(a,b,c,d,e,f,g,h){

            var sx  =136+a;//start position of curve.used in moveTo(sx,sy)
            var sy  =235+b;
            var cp1x=136+c;//control point 1
            var cp1y=222+d;
            var cp2x=136+e;//control point 2
            var cp2y=222+f;
            var endx=136+g;//end points
            var endy=210+h;

         var canvas = document.getElementById('myCanvas');
         var context = canvas.getContext('2d');
         context.strokeStyle="grey";
         context.lineWidth="8";
         context.beginPath();
         context.moveTo(sx,sy);
         context.bezierCurveTo(cp1x,cp1y,cp2x,cp2y,endx,endy);
         context.lineCap = 'round';
         context.stroke();
    }
};
})();

person Community    schedule 14.06.2013    source источник
comment
Я взял ваш код и создал версию класса Hair с конструктором. Вы предоставляете этому классу необходимое количество волос, и он рисует/перерисовывает все волосы по мере необходимости как группу. Я сделал это для повышения производительности, потому что обработчик mousemove должен будет реагировать только на 1 группу вместо 9 отдельных объектов. Я также добавил в класс метод, который заставляет волосы расти. Как мы уже обсуждали, это делается путем повышения координаты Y контрольных точек и конечной точки. Удачи с вашим проектом. :)   -  person markE    schedule 15.06.2013
comment
@markE: в тот момент, когда я прохожусь по отросшим волосам, они снова становятся короткими, что нежелательно ... но это нормально ... я возьму отсюда, спасибо Марк !!! серьезно ... но небольшой вопрос, помимо кодирования ,Что тебя держит в 56 лет!!!#уважение   -  person    schedule 15.06.2013
comment
Я счастлив, когда узнаю что-то новое каждый день. До сих пор жизнь давала более чем достаточно интересных вещей для изучения!   -  person markE    schedule 15.06.2013


Ответы (1)


Вот ответ, который вы хотели о выращивании волос.

Здесь также есть информация, которую вы хотели, о том, как создать «объект» для волос.

Код и скрипка: http://jsfiddle.net/m1erickson/8K825/

<!doctype html>
<html>
<head>
<link rel="stylesheet" type="text/css" media="all" href="css/reset.css" /> <!-- reset css -->
<script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script>

<style>
    body{ background-color: ivory; }
    canvas{border:1px solid red;}
</style>

<script>
$(function(){

    window.requestAnimationFrame = (function(callback) {
      return window.requestAnimationFrame || window.webkitRequestAnimationFrame || window.mozRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame ||
      function(callback) {
        window.setTimeout(callback, 1000 / 60);
      };
    })();

    var canvas=document.getElementById("canvas");
    var ctx=canvas.getContext("2d");

    var canvasOffset=$("#canvas").offset();
    var offsetX=canvasOffset.left;
    var offsetY=canvasOffset.top;

    // the Hair "object"
    // Hair is a containing object that hosts a user-specified # of hairs
    var Hair = (function () {

        // constructor
        function Hair(x,y,width,height,haircount) {

            this.x=x;
            this.y=y;
            this.width=width;
            this.height=height;
            this.right=this.x+this.width;
            this.bottom=this.y+this.height;
            this.hairCount=haircount;
            this.startX=x+20;
            this.startY=y+height-3;  //235;
            this.hairHeight=25;
            this.hairGrowth=0;
            this.lastEndX=[];

            for(var i=0;i<haircount;i++){
                this.lastEndX[i]= x+20+(i*15);
            }

        }
        // grows the hair
        // works by changing the Y value of the end & control points
        Hair.prototype.grow = function(increment){
            this.hairGrowth+=increment;
            return(this.hairGrowth);
        }
        // draw all the hairs
        Hair.prototype.draw = function(mouseX){

            // clear this object's space on the canvas
            // and set its styles
            ctx.clearRect(this.x,this.y,this.width,this.height);
            ctx.beginPath();
            ctx.strokeStyle="grey";
            ctx.lineWidth=7;
            ctx.lineCap = 'round';
            ctx.beginPath();

            for(var i=0;i<this.hairCount;i++){

                // straight hair 
                var sx=cp1x=cp2x= this.startX+(i*15);
                var sy= this.startY;
                var cp1y = cp2y = (this.startY-(this.hairHeight+this.hairGrowth)/2);
                var endy = this.startY-this.hairHeight-this.hairGrowth;
                var endx = this.lastEndX[i];

                // create bend, if any
                if(Math.abs(mouseX-sx)<=10){ 
                    endx = sx+(mouseX-sx)*1.1;
                    this.lastEndX[i]=endx;
                };

                // draw this curve
                ctx.moveTo(sx,sy);
                ctx.bezierCurveTo(cp1x,cp1y,cp2x,cp2y,endx,endy);

            }
            // stroke
            ctx.stroke();
            // temp outline
            ctx.lineWidth=1;
            ctx.beginPath();
            ctx.rect(this.x,this.y,this.width,this.height);
            ctx.stroke();
        }
        //
        return Hair;
    })();


    var direction=1;
    var fps = 3;
    function animate() {
        setTimeout(function() {

            // change hair length
            var hairLength=hair.grow(direction);
            if(hairLength<1 || hairLength>10){ direction=(-direction); }

            // draw
            hair.draw();

            // request next frame
            requestAnimationFrame(animate);

        }, 1000 / fps);
    }


    function handleMouseMove(e){
      mouseX=parseInt(e.clientX-offsetX);
      mouseY=parseInt(e.clientY-offsetY);
      $("#movelog").html("Move: "+ mouseX + " / " + mouseY);

      // Put your mousemove stuff here
      if(mouseX>=hair.x && mouseX<=hair.right && mouseY>=hair.y && mouseY<=hair.bottom){
          hair.draw(mouseX);
      }
    }

    $("#canvas").mousemove(function(e){handleMouseMove(e);});

    $("#grow").click(function(e){ animate(); });

    // create a new patch of hair 
    var hair=new Hair(25,50,150,50,8);
    hair.draw(225);


}); // end $(function(){});
</script>

</head>

<body>
    <p id="movelog">Move</p>
    <canvas id="canvas" width=300 height=200></canvas><br>
    <button id="grow">Grow Hair</button>
</body>
</html>

[Добавлено: объяснение «Класса» и создания экземпляра объекта из класса]

var Hair=(function(){ …; return Hair; })() создает «класс» Hair.

var hair = new Hair(…) создает настоящий, пригодный для использования «объект» Hair.

Думайте о классе Hair как о шаблоне (или чертеже, или шаблоне). Весь код внутри класса Hair определяет только свойства и методы класса. На самом деле вы не вызываете какой-либо код в классе Hair. Вы просто используете его как шаблон для создания реальных объектов волос.

Вы можете использовать класс Hair для создания любого количества реальных объектов волос — его можно использовать повторно. Акт создания объекта волос известен как «создание экземпляра класса Hair».

Кстати, в javascript на самом деле нет классов, так что это просто псевдокласс. Но это совсем другое объяснение!

Вы спросите: какая польза от direction=0,25?

Переменная направления используется для постепенного увеличения высоты волос, когда волосы «растут» во время анимации. .25 сообщает контрольным/конечным точкам волос подняться на 0,25 пикселя за кадр анимации.

Вы спросите: какое значение имеет функция обратного вызова и этот settimeout?

setTimeout оборачивает requestAnimationFrame, так что анимация происходит с фиксированной частотой кадров в секунду.

RequestAnimationFrame (RAF) отлично справляется с оптимизацией производительности, но вы не можете контролировать количество кадров в секунду только с помощью RAF. Если вы оберните RAF внутри setTimeout, вы сможете контролировать количество кадров в секунду. Например, setTimeout(anyFunction,1000/fps) будет запускать anyFunction примерно 3 раза в секунду, когда fps==3. См. эту замечательную статью о RAF+setTimeout: http://creativejs.com/resources/requestanimationframe/

Как вы обнаружили, RAF без setTimeout все равно будет работать, но RAF будет стараться отрастить ваши волосы как можно быстрее, а не с интервалом fps.

person markE    schedule 14.06.2013
comment
var hair=new Hair(25,50,150,50,8); теперь я думаю, что это экземпляр, который вы создали. но я смущен тем, что ссылается на то, что, т.е. волосы, является внешним объектом, а также именем функции, и для чего используется направление = 0,25? - person ; 16.06.2013
comment
и каково значение функции обратного вызова и этого settimeout? Я прокомментировал код и выполнил его, но в моем браузере Chrome он работал нормально. - person ; 16.06.2013
comment
Смотрите мой приложенный ответ на ваши вопросы. :) - person markE; 16.06.2013
comment
new Hair(25,50,150,50,8) ----- что такое волосы в этой... функции или классе??? ------- причина, по которой я спрашиваю, заключается в том, что вы передаете параметры волосам .Если вы видите мой предыдущий пример, вы заметите следующее: ------- var hair(aka object)=new Hair(aka class); hair.draw_hair(пара1,параграф2) - person ; 17.06.2013
comment
Столица H Hair == класс (шаблон). h волосы в нижнем регистре == объект (полезные волосы). - person markE; 17.06.2013
comment
но и класс, и волосы - это Hair в коде. Итак, функция Hair - это метод? И это нормально, если имя класса и имя метода совпадают??? - person ; 17.06.2013
comment
Да, совершенно нормально. Класс [ var Hair=function() ] содержит метод-конструктор [function Hair]. В языках, поддерживающих настоящие классы, часто конструктор имеет то же имя, что и класс. Это работает в javascript, потому что функции могут содержать функции. В этом случае класс Hair содержит конструктор Hair. - person markE; 17.06.2013
comment
:плохой день в офисе.Они полностью отвергли то, что я им показал.Они находят это жестким и ожидают некоторой плавности!!! И сформулировал некоторые новые идеи. Например, волосы должны вести себя более естественно, самая близкая аналогия, которую я могу вам дать, это то, что они хотят волнистости, как поток. То, как течет трава. Я пытался дать некоторую задержку, но это бесполезно дергаться!! полностью облажался человек cssdeck.com/labs/4ksohwya Эта ссылка может помочь (должен сказать, что это сложный код!!!) Можно ли создать ощущение волнистости при движении мыши? - person ; 17.06.2013
comment
: любые идеи относительно этого или любой ссылки, которая содержит важную информацию, касающуюся моего проекта? - person ; 17.06.2013
comment
Ваши текущие волосы представляют собой простую дугу (кривая с односторонним движением). Чтобы быть волнистым, вам нужна двойная кривая Безье. Для этого вам просто нужно переместить контрольные точки от оси X. Я предлагаю вам построить экспериментальный холст всего с 1 кубической кривой Безье и поиграть с этой кривой, пока вы не поймете, как контрольные + конечные точки влияют на кривую. Таким образом, вы можете настроить контрольные + конечные точки для создания волнистых волос. Дергание почти исчезнет после того, как вы поймете контрольные точки, потому что вы будете гораздо лучше контролировать движение волос. Эксперимент+Понимание=Успех!! - person markE; 17.06.2013
comment
: Я делал это в прошлом и понимаю природу кривой Безье. Но когда дело доходит до анимации, такой как cssdeck.com/labs/4ksohwya, я скорее не уверен, что делать? осторожно, а с mousemove еще сложнее.. - person ; 17.06.2013
comment
Нет... Не сложно - когда правильно понимаешь, это легко! Эксперимент+Понимание == Успех. Возьмите их код и разбейте его всего на 1 траву. Играть в! Постройте игровую площадку 1 Hair на холсте. Играть в! Когда вы по-настоящему понимаете природу кубической кривой Безье и ее контрольные и конечные точки, ваша задача становится легкой. Действительно! ;) Но, не понимая криво, вы метаете дротики в темной комнате. При правильном понимании согнуть кривую, основанную на движении мыши, так же просто, как пошевелить собственными волосами рукой). Так что... не копируйте cssdeck.com (это хороший код). Вместо этого поэкспериментируйте с ним + поймите !! - person markE; 17.06.2013
comment
: параметр времени трудно понять. И на основе этого параметра они использовали sin и cos, которые определяют движения? Можете ли вы помочь мне с этим?? И что именно делает эта функция lerp?? - person ; 18.06.2013
comment
Их временная переменная — это буквально часы (таймер). Их sin/cos используются для того, чтобы верхняя конечная точка их кривой двигалась по дуге, а не по горизонтальной линии (более естественно: поскольку объекты с фиксированным основанием качаются, они становятся выше, когда они наиболее вертикальны, и немного короче, когда они наклоняются влево). /Правильно). Lerp — это сокращение от linear-interpolation, что означает отслеживание точки при ее линейном перемещении. Их лерп используется для изменения цвета во времени (не имеет отношения к их травяному кодексу). - person markE; 18.06.2013
comment
: Я просмотрел несколько веб-сайтов для отслеживания природы синуса и cos, но сделать это так, как они это сделали, довольно сложно !!! Я буквально играл довольно много времени. используется и что вызывает плавное движение. Можешь подарить небольшой модуль на простые прямые волосы?? - person ; 18.06.2013
comment
:: Помогите мне с этим, в последний раз. Анимация, похожая на траву, даже на одном волоске подойдет. PLz, только один раз. stackoverflow.com/questions/17171010/ - person ; 23.06.2013