Данный способ подходит не только для вращения объекта вокруг центра, но также и для вращения объекта вокруг любой точки, находящейся внутри него.
За поворот MovieClip’а отвечает свойство _rotation,
которому необходимо передать угол поворота объекта в градусах. Все бы ничего, но поворачивается объект вокруг собственной точки регистрации:
[Youtube] [Скачать SWF] [Смотреть SWF]
Код первого кадра:
onEnterFrame=function()
{
imvVert._rotation++;
}
Точка регистрации на сцене и в библиотеке (выделена красной рамкой)
И если для созданных в редакторе MovieClip’ов не это составляет особых проблем, т.к. изображение внутри клипа можно передвинуть вручную, относительно точки регистрации или задать точку регистрации при создании клипа:
[Youtube] [Скачать SWF] [Смотреть SWF]
то для клипов, создаваемых программно, например загруженных из внешнего источника картинок придется приложить немного усилий, т.к. точка регистрации по умолчанию находится в верхнем левом углу объекта:
Точка регистрации и центр
А вращать объект, например, надо вокруг его центра.
1. В данном примере будет использоваться изображение, загруженное в заранее созданный пустой MovieСlip из внешнего источника. Поэтому, вначале создается собственно сам пустой MovieClip в библиотеке, (названный в примере
mvVictim
), он помещается на сцену и его экземпляру (Instance) присваивается имя. В данном примере – imvVictim
Далее, в первый кадр добавляется следующий код:
stop(); //останавливаем воспроизведение
var MovieName="123.png"; //имя загружаемой картинки (должна лежать в том же каталоге, что и flash ролик)
var LoadComplete=false; //флаг-индикатор, показывает загрузилось изображение или нет
var lisVictim:Object = new Object();//создали слушатель для клипа
//обработчик слушателя*****************************
lisVictim.onLoadInit = function(mc:MovieClip)
{
//устанавливаем начальное состояние клипа, ставим его по центру:
imvVictim._x=(Stage.width-imvVictim._width)/2;
imvVictim._y=(Stage.height-imvVictim._height)/2;
LoadComplete=true;
}
//конец обработчика*********************************
//создаем объект-загрузчик
var imageLoader:MovieClipLoader = new MovieClipLoader();
imageLoader.addListener(lisVictim); //подключаем слушатель
imageLoader.loadClip(MovieName, imvVictim); //загружаем клип
//*************************************************************
Если запустить ролик на выполнение сейчас, то будет отображено статичное изображение из файла 123.png, находящееся в центре сцены
2. Для работы с углами во время расчетов и отрисовки вращения будет необходимо преобразовывать градусы в радианы, т.к. математические функции такие как Math.sin, Math.cos
требуют величин в радианах, а свойству _rotation
, объекта MovieClip необходимо присваивать значение угла в градусах.
Преобразование градусов в радианы производится по следующим формулам:
Где Ag – значение угла в градусах, Aк – в радианах
В виде программного кода функции преобразования выглядят так:
//преобразования градусов в радианы и обратно
function gradToRad(grad:Number):Number
{
rad=grad*Math.PI/180;
return rad;
}
function radToGrad(rad:Number):Number
{
grad=rad*180/Math.PI;
return grad;
}
Для того, чтобы объект вращался вокруг нужной точки необходимо скорректировать его положение на плоскости – т.е. координаты и внести поправку угла поворота. Для нагладности приведена следующая схема:
Нам известны координаты объекта Xо и Yо, они же координаты точки регистрации, а также координаты точки, вокруг которой объект должен вращаться Хт;Yт, а также угол Aо на который необходимо повернуть объект относительно точки, вокруг которой он будет вращаться
Сначала найдем отрезок a:
Далее найдем угол
Эти величины останутся неизменными при условии, если линейные размеры фигуры не будут меняться.
При повороте необходимо будет вычислить угол, на который объект должен повернуться относительно точки регистрации
И новые координаты объекта с учетом этого угла:
Под координатами имеются ввиду координаты относительно ролика, а не внутренней системы координат MovieClip'а
1. Определим необходимые переменные и инициализируем их нулевыми значениями до произведения всех действий. Сразу скажу, их может быть и нужно меньше, чем в примере, но так код более читабелен и понятен.
Необходимо добавить этот код перед
onLoadInit
var x_obj=0; //Координаты объекта
var y_obj=0;
var x_t=0; //Координаты точки, вокруг которой будем вращать
var y_t=0;
var alph=0; //угол Alpha - см картинку
var a_vect=0; //отрезок a - см картинку
var ugol=0; //угол на который надо поворачивать фигуру
var ugol_tp=0; //Угол используемый для вычисления поправки координат (A')
2. В обработчик
onLoadInit
перед установкой флага завершения загрузки добавляется следующий код:
x_obj=imvVictim._x; //запоминаем координаты объекта
y_obj=imvVictim._y;
x_t=x_obj+imvVictim._width/2; //... и координаты точки, вокруг которой будем вращать,
y_t=y_obj+imvVictim._height/2; // в данном случае - центра объекта
a_vect=Math.sqrt(Math.pow(x_t-x_obj,2)+Math.pow((y_t-y_obj),2)); //вычисляем длину отрезка a
alph=Math.asin((y_t-y_obj)/a_vect) //угол alpha в радианах
Функция
Math.sqrt (n)
возвращает значение квадратного корня числа n, а функция pow (n,m)
– значение числа n в степени m.3. Создаем функцию
vrach ()
которая будет выполнять действия по непосредственному повороту объекта
function vrash()
{
ugol+=1; //значение угла будет увеличиваться при каждом вызове функции vrash()
ugol_tp=180+radToGrad(alph)+ugol; //вычисляем угол поправки A'
x_obj=a_vect*Math.cos(gradToRad(ugol_tp))+x_t; //... новые координаты объекта
y_obj=a_vect*Math.sin(gradToRad(ugol_tp))+y_t;
//передаем объекту новые параметры
imvVictim._x=x_obj;
imvVictim._y=y_obj;
imvVictim._rotation=ugol;
}
В обработчике
onEnterFrame
, вызываемом с частотой смены кадров необходимо проверить, завершены ли процедура загрузки изображения и установки его начальных параметров, после чего вызвать функцию vrach()
onEnterFrame=function()
{
if (LoadComplete) //проверка, произведена ли загрузка изображения и установка начальных параметров
{
vrash();
}
}
1. Изменение направления вращения (по/против часовой стрелки)
Для изменения направления вращения достаточно изменить знак у числа, прибавляемого к переменной
ugol
в функции vrash()
Для того, чтобы вращающийся объект двигался, например, по оси X, достаточно ввести одну переменную там же где и предыдущие
var mtn=0;
и немного модифицировать код функции
vrach()
...
mtn++;
imvVictim._x=x_fig+mtn;
...
Исходник:
stop(); //останавливаем воспроизведение
var MovieName="123.png"; //имя загружаемой картинки (должна лежать в том же каталоге, что и flash ролик)
var LoadComplete=false; //флаг-индикатор показывает загрузилось или нет
var lisVictim:Object = new Object();//создали слушатель для клипа
var x_obj=0; //Координаты объекта
var y_obj=0;
var x_t=0; //Координаты точки, вокруг которой будем вращать
var y_t=0;
var alph=0; //угол Alpha - см картинку
var a_vect=0; //отрезок a - см картинку
var ugol=0; //угол на который надо поворачивать фигуру
var ugol_tp=0; //Угол используемый для вычисления поправки координат (A')
//преобразования градусов в радианы и обратно
function gradToRad(grad:Number):Number
{
rad=grad*Math.PI/180;
return rad;
}
function radToGrad(rad:Number):Number
{
grad=rad*180/Math.PI;
return grad;
}
//обработчик слушателя*****************************
lisVictim.onLoadInit = function(mc:MovieClip)
{
//устанавливаем начальное состояние клипа:
imvVictim._x=(Stage.width-imvVictim._width)/2; //по центру
imvVictim._y=(Stage.height-imvVictim._height)/2;
//устанавливаем начальные значения переменных, используемых для вращения
x_obj=imvVictim._x; //запоминаем координаты объекта
y_obj=imvVictim._y;
x_t=x_obj+imvVictim._width/2; //... и координаты точки, вокруг которой будем вращать,
y_t=y_obj+imvVictim._height/2; // в данном случае - центра объекта
a_vect=Math.sqrt(Math.pow(x_t-x_obj,2)+Math.pow((y_t-y_obj),2)); //вычисляем длину отрезка a
alph=Math.asin((y_t-y_obj)/a_vect) //угол alpha в радианах
LoadComplete=true; //устанавливаем флаг завершения загрузки изображения
}
//конец обработчика*********************************
//создаем объект-загрузчик
var imageLoader:MovieClipLoader = new MovieClipLoader();
imageLoader.addListener(lisVictim); //подключаем слушатель
imageLoader.loadClip(MovieName, imvVictim); //загружаем клип
//*************************************************************
//*************************************************************trace
function vrash()
{
ugol+=1; //значение угла будет увеличиваться при каждом вызове функции vrash()
ugol_tp=180+radToGrad(alph)+ugol; //вычисляем угол поправки A'
x_obj=a_vect*Math.cos(gradToRad(ugol_tp))+x_t; //... новые координаты объекта
y_obj=a_vect*Math.sin(gradToRad(ugol_tp))+y_t;
//передаем объекту новые параметры
imvVictim._x=x_obj;
imvVictim._y=y_obj;
imvVictim._rotation=ugol;
}
onEnterFrame=function()
{
if (LoadComplete) //проверка, произведена ли загрузка изображения и установка начальных параметров
{
vrash();
}
}
[Youtube] [Скачать SWF] [Смотреть SWF]
Ролик 2
[Youtube] [Скачать SWF] [Смотреть SWF]
Скачать исходники (Adobe Flash CS 6) [Yandex.Disk]
Скачать исходники (Adobe Flash CS 6) [Mega.nz]
Исходник 1 ролика на PasteBin Исходник 2 ролика на PasteBin
(L) Kevin Kurt, Hex_Laden
Это перепост заметки из моего блога на LJ.ROSSIA.ORG
Оригинал находится здесь: http://lj.rossia.org/users/hex_laden/103589.html
Прокомментировать заметку можно по ссылке выше.