Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Web программирование > Общие вопросы Web
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 07.07.2011, 15:35   #1
crazy horse
ios developer
Старожил
 
Аватар для crazy horse
 
Регистрация: 16.11.2007
Сообщений: 2,885
Лампочка ActionScript3: Кэширование анимации и ее проигрывание (blitting).

ActionScript3: Кэширование анимации и ее проигрывание (blitting).

Всем, кто имеет хоть какое– нибудь отношение к игроиндустрии или созданию спецэффектов, хорошо известно, насколько ресурсоемка такая вещь, как отображение векторной анимации и ее расчет в процессе рендеринга. Но к счастью, разработчики оставили нам путь к всеобщему процветанию и дали нам возможность использовать такую великолепную вещь, как вывод на экран предварительно откешированного в растр изображения. Помните, как устроен кинематограф, основанный на смене одной картинки на другую? Вот этим мы сейчас и займемся.
Для начала нам нужно получить кэш мувклипа. Код интуитивно понятен, очевидные вещи пока комментировать не буду:

Код:
package cache2bmp
{
import ru.dijump.wonf.cache2bmp.*;

import flash.display.BitmapData;
import flash.display.MovieClip;
import flash.geom.Matrix;
import flash.geom.Rectangle;

public class CacheAsBitmap
{
    private var _sourceMovieClip:MovieClip;

    public function CacheAsBitmap():void
    {
        this._sourceMovieClip = new MovieClip();
    }

    public function cache(source:MovieClip):Vector.<CachedFrameModel>
    {
//конечный материал будет состоять из массива простых объектов - кадров с необходимой
//информацией об выдираемом кадре
       //и его "оттиском" в виде BitmapData
        var clip:Vector.<CachedFrameModel> = new Vector.<CachedFrameModel>();
        this.sourceMovieClip = source;
        var totalFrames:int = sourceMovieClip.totalFrames;
        //перебираем все кадры и кэшим их в наш массив
        for (var i:int = 1; i <= totalFrames; i++)
        {
            sourceMovieClip.gotoAndStop(i);

            clip.push(cacheFrame(sourceMovieClip));
        }
        return clip;
    }

    private function cacheFrame(sourceMovieClip:MovieClip):CachedFrameModel
    {
        //сохраняем всю информацию о кадре
        var cachedFrame:CachedFrameModel = new CachedFrameModel();
        cachedFrame.width = sourceMovieClip.width;
        cachedFrame.height = sourceMovieClip.height;
        cachedFrame.x = sourceMovieClip.x;
        cachedFrame.y = sourceMovieClip.y;
        cachedFrame.numFrame = sourceMovieClip.currentFrame;
        //получаем прямоугольник, описанный вокруг изображения, с его размерами и координатами в координатном пространстве
        //нашего мувклипа:
        var bounds:Rectangle = sourceMovieClip.getBounds(sourceMovieClip);
        //матрица геометрических трансформаций - отдельная тема для разговора, о ней можно почитать в эдабовских справочниках.
        //в данном случае она нам нужна, чтобы переместить отпечаток изображения в систему координат с началом в верхнем левом углу полученного
        // прямоугольника:
        var matrix:Matrix = new Matrix();
            matrix.translate(-bounds.x, -bounds.y);
        //Оччень тонкий и мутный момент. Если мы хотим чтобы пустые пространства были прозрачными, заливка битмапдаты
        //  ДОЛЖНА быть черной. Простая установка свойства transparent=true без этого не сработает.
        var bitmapData:BitmapData = new BitmapData(bounds.width, bounds.height,true,0x000000);
        bitmapData.draw(sourceMovieClip, matrix);
        cachedFrame.bitmapData = bitmapData;
        return cachedFrame;
    }

    public function get sourceMovieClip():MovieClip
    {
        return _sourceMovieClip;
    }

    public function set sourceMovieClip(value:MovieClip):void
    {
        _sourceMovieClip = value;
    }
}
}
Делайте что хотите, но чтобы через полчаса в лесу было светло, сухо и медведь!
crazy horse вне форума Ответить с цитированием
Старый 07.07.2011, 15:36   #2
crazy horse
ios developer
Старожил
 
Аватар для crazy horse
 
Регистрация: 16.11.2007
Сообщений: 2,885
По умолчанию

продолжение:

Вот как выглядит объект кадра:

Код:
package cache2bmp
{
import flash.display.BitmapData;

public class CachedFrameModel
{
    private var _bitmapData:BitmapData;
    private var _x:int;
    private var _y:int;
    private var _width:int;
    private var _height:int;
    private var _numFrame:int;
    private var _action:Function;
    private var _layer:String;
…
Гэттеры и сеттеры описывать не буду, ленивым можно сделать свойства публичными

Далее на очереди эмулятор мувклипа – проигрыватель нашей скэшированной анимации. Сами эдабовцы уверяют, что наибыстрейший способ вывода на экран – это свойство copyPixels() битмапдаты, и у нас нет оснований им не верить Вот что у нас должно получится (класс реализует необходимые для клипа органы управления, присущие MovieClip, которые я комментировать не буду – они элементарны.
Код:
package cache2bmp
{
import ru.dijump.wonf.cache2bmp.*;

import flash.display.Bitmap;
import flash.display.BitmapData;
import flash.events.Event;
import flash.geom.Point;
import flash.geom.Rectangle;

public class CachedMovieClip extends Bitmap
{
    private var _clip:Vector.<CachedFrameModel>;
    private var _currentFrame:int;
    private var _totalFrame:int;
    private var _destinationPoint:Point;
    private var _areaRectangle:Rectangle;
    private var _clearRectangle:Rectangle;

    public function CachedMovieClip(width:int = 150, height:int = 150)
    {
        bitmapData = new BitmapData(width, height, true,0x000000);
        this.width = width;
        this.height = height;
        this._clip = new Vector.<CachedFrameModel>();
        this._destinationPoint = new Point();
        this._areaRectangle = new Rectangle();
        this._clearRectangle = new Rectangle(0, 0, width, height);
        this.currentFrame=1;
    }

    public function gotoAndStop(frame:int = 1):void
    {
        if (frame < 1)
        {
            frame = 1;
        }
        if (frame > totalFrame)
        {
            frame = totalFrame;
        }
        render(frame);
        this.currentFrame = frame;
        this.removeEventListener(Event.ENTER_FRAME, playEnterFrameHandler);
    }

    private function render(frame:int):void
    {
        // считываем данные с нашего объекта-снимка
        destinationPoint.x = clip[frame - 1].x;
        destinationPoint.y = clip[frame - 1].y;
        areaRectangle.width = clip[frame - 1].width;
        areaRectangle.height = clip[frame - 1].height;
        //Очень тонкий момент! Чтобы плеер не рендерил лишнюю муть, навроде очистки битмапдаты, лочим ее:
        bitmapData.lock();
        //Очищаем битмапдату от предыдущего изображения черной заливкой (это единственно верный путь):
        this.bitmapData.fillRect(_clearRectangle,0x000000);
        //рисуем новую картинку
        this.bitmapData.copyPixels(clip[frame - 1].bitmapData, areaRectangle, destinationPoint);
        //и позволяем вывести теперь ее на экран
        bitmapData.unlock();
    }

    public function gotoAndPlay(frame:int = 1):void
    {
        if (frame < 1)
        {
            frame = 1;
        }
        if (frame > totalFrame)
        {
            frame = totalFrame;
        }
        render(frame);
        this.currentFrame = frame;
        this.addEventListener(Event.ENTER_FRAME, playEnterFrameHandler);
    }

    public function play():void
    {
        this.addEventListener(Event.ENTER_FRAME, playEnterFrameHandler);
    }

    public function stop():void
    {
        this.removeEventListener(Event.ENTER_FRAME, playEnterFrameHandler);
    }


    public function get clip():Vector.<CachedFrameModel>
    {
        return _clip;
    }

    public function set clip(value:Vector.<CachedFrameModel>):void
    {
        _clip = value;
        this.totalFrame = value.length;
        this.currentFrame = 1;
        gotoAndStop(1);
    }

    public function get currentFrame():int
    {
        return _currentFrame;
    }

    public function set currentFrame(value:int):void
    {
        _currentFrame = value;
    }

    public function get totalFrame():int
    {
        return _totalFrame;
    }

    public function set totalFrame(value:int):void
    {
        _totalFrame = value;
    }

    public function get destinationPoint():Point
    {
        return _destinationPoint;
    }

    public function set destinationPoint(value:Point):void
    {
        _destinationPoint = value;
    }

    public function get areaRectangle():Rectangle
    {
        return _areaRectangle;
    }

    public function set areaRectangle(value:Rectangle):void
    {
        _areaRectangle = value;
    }

    private function playEnterFrameHandler(event:Event):void
    {
        if (currentFrame != totalFrame)
        {
            render(currentFrame);
            currentFrame++;
        }
        else
        {
            render(1);
            currentFrame = 1;
        }
    }
}
}
Вот, собственно, и все!
Делайте что хотите, но чтобы через полчаса в лесу было светло, сухо и медведь!
crazy horse вне форума Ответить с цитированием
Старый 07.07.2011, 19:25   #3
Alar
Александр
Администратор
 
Аватар для Alar
 
Регистрация: 28.10.2006
Сообщений: 17,758
По умолчанию

а почему свободное общение? так и уговорите новый раздел создать. как называть?
Alar вне форума Ответить с цитированием
Старый 07.07.2011, 19:49   #4
crazy horse
ios developer
Старожил
 
Аватар для crazy horse
 
Регистрация: 16.11.2007
Сообщений: 2,885
По умолчанию

Ну, вероятно - ActionScript/flash/flex?
Делайте что хотите, но чтобы через полчаса в лесу было светло, сухо и медведь!
crazy horse вне форума Ответить с цитированием
Старый 07.07.2011, 21:04   #5
Bustle
Interdicted
Участник клуба
 
Аватар для Bustle
 
Регистрация: 25.11.2010
Сообщений: 1,194
По умолчанию

Я еще раз
Предложу несколько идей :
Добавить к разделу: Операционные системы
Подразделы:
-Linux/Unix
-MS Windows

Добавить в категорию технологии разделы:
-Алгоритмы

Добавить в категорию Низкоуровневое программирование раздел:
-Микроконтроллеры, микропроцессоры

Добавить в категорию Web программирование разделы:
-Администрирование Web серверов
-Хостинг и доменные имена
Love writing code and I am really passionate about it
Bustle вне форума Ответить с цитированием
Старый 07.07.2011, 21:07   #6
Alar
Александр
Администратор
 
Аватар для Alar
 
Регистрация: 28.10.2006
Сообщений: 17,758
По умолчанию

против разделения операционных систем большинство модераторов. Хотя логически разделить надо бы.
Alar вне форума Ответить с цитированием
Старый 07.07.2011, 21:16   #7
Bustle
Interdicted
Участник клуба
 
Аватар для Bustle
 
Регистрация: 25.11.2010
Сообщений: 1,194
По умолчанию

Модераторы ну, что же Вы?
Одного я знаю, что не против.
Цитата:
ActionScript/flash/flex
Этот раздел, то будет?
Но наверное так круче:
Категория:
flash
Разделы:
FAQ
ActionScript 1.0/2.0
ActionScript 3
flex
Love writing code and I am really passionate about it

Последний раз редактировалось Bustle; 07.07.2011 в 21:23.
Bustle вне форума Ответить с цитированием
Старый 07.07.2011, 21:53   #8
crazy horse
ios developer
Старожил
 
Аватар для crazy horse
 
Регистрация: 16.11.2007
Сообщений: 2,885
По умолчанию

As 1-2 фтопку, они давно подохли, и пепел их развеян по ветру.
Каким образом флэкс стал подразделом флэша - тоже мало понятно. Да и делить ничего смысла никакого нет, лучше один хоть как-то заполненный раздел чем пять пустых. Опять же, если есть в таком разделе смысл. Раньше я громче всех вопил, что он нужен, но теперь не очень уверен.
Делайте что хотите, но чтобы через полчаса в лесу было светло, сухо и медведь!
crazy horse вне форума Ответить с цитированием
Старый 07.07.2011, 22:01   #9
Alar
Александр
Администратор
 
Аватар для Alar
 
Регистрация: 28.10.2006
Сообщений: 17,758
По умолчанию

Цитата:
Сообщение от crazy horse Посмотреть сообщение
Раньше я громче всех вопил, что он нужен, но теперь не очень уверен.
Теперь - это после каких событий?
Alar вне форума Ответить с цитированием
Старый 07.07.2011, 22:07   #10
crazy horse
ios developer
Старожил
 
Аватар для crazy horse
 
Регистрация: 16.11.2007
Сообщений: 2,885
По умолчанию

Ну, меня долго убеждали в этом всем форумом и в результате я осел на забугорных форумах Хотя русскоязычного ресурса, конечно, не хватает. Flasher.ru напоменает какую-то свалку, где, тем не менее, иногда можно найти что-то нужное.
Делайте что хотите, но чтобы через полчаса в лесу было светло, сухо и медведь!
crazy horse вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Поочередное проигрывание анимации текста в Power Point 2007 nigretos Свободное общение 4 14.06.2011 13:46
Кэширование файлов romanzi Общие вопросы Delphi 1 21.05.2011 18:51
Как запретить кэширование страниц? sunplant HTML и CSS 1 26.09.2010 20:15
Какими способами можно реализовать кэширование для прокси - сервера? Slavka8800 Работа с сетью в Delphi 0 02.06.2009 22:08
КАК отключить кэширование на proxy-сервере? aviv Свободное общение 2 20.02.2009 13:45