[AS3] 표시 리스트를 사용하는 어프로치의 이점

Programming/ActionScript 3.0 2007. 6. 15. 15:52
렌더링의 효율화와 파일 사이즈의 경량화

ActionScript 1.0 및 2.0에서는 MovieClip 오브젝트에서만 셰이프를 표현할 수 있었다. 하지만 ActionScript 3.0 에서는 셰이프를 표현 할 수 있는 간단한 표시 오브젝트 클래스가 있다. ActionScript 3.0 표시 오브젝트 클래스에는 MovieClip 오브젝트에 포함되는 메소드와 프롭퍼티가 모두 포함되지 않기 때문에 기존의 ActionScript(2.0 이하)보다 메모리 및 프로세서 자원에의 부담이 경감되었다.
예를 들어, 각 MovieClip 오브젝트에는 무비 클립의 타임 라인의 프롭퍼티가 포함됩니다만 Shape 오브젝트에는 포함되지 않는다. 타임 라인을 제어하기 위한 프롭퍼티는 대량의 메모리 및 프로세서 자원을 사용하는 경우가 있지만 ActionScript 3.0의 Shape 오브젝트를 사용하면 퍼포먼스가 향상된다. Shape 오브젝트는 복잡한 MovieClip 오브젝트보다 오버헤드가 적기 때문이다. Flash Player가 Shape에서는 MovieClip 프롭퍼티를 관리할 필요는 없기 때문에 스피드가 향상과 함께 오브젝트가 사용하는 메모리 용량을 줄일 수 있어 전제적으로는 CPU의 낭비를 줄일 수 있는 이점이 생겼다.


심도 관리의 향상

ActionScript 1.0 및 2.0에서의 depths는 직선적인 심도 관리 및 getNextHighestDepth() 등의 메소드를 사용해 관리되고 있었다. ActionScript 3.0에서는 표시 오브젝트의 심도를 관리하기 위해서 편리한 메소드 및 프롭퍼티가 포함된다. DisplayObjectContainer 클래스가 바로 그것이다.

ActionScript 3.0는 표시 오브젝트를 DisplayObjectContainer 인스턴스의 아이 리스트 내의 새로운 위치로 이동하면 표시 오브젝트 컨테이너 내의 다른 아이는 자동적으로 위치가 변경되어 표시 오브젝트 컨테이너내의 적절한 아이 인덱스 위치를 할당할 수 있다.

ActionScript 3.0는 항상 표시 오브젝트 컨테이너의 아이 오브젝트를 모두 찾아낼 수 있다. 어느 DisplayObjectContainer 인스턴스에도 표시 오브젝트 컨테이너의 아이의 수를 일람표시 할 수 있는 numChildren 프롭퍼티를 제공하고 있다. 또 표시 오브젝트 컨테이너의 아이 리스트는 항상 인덱스 리스트이기 위해 리스트내의 인덱스 위치 0으로부터 마지막 인덱스 위치 (numChildren - 1) 까지의 모든 오브젝트를 조사할 수 있다. 이것은 ActionScript 1.0 및 2.0 의 MovieClip 오브젝트의 메소드와 프롭퍼티에서는 불가능했던 점이다.

ActionScript 3.0는 표시 리스트 내를 순서로 이동하는 것은 간단하다. 왜냐하면 표시 오브젝트 컨테이너의 아이 리스트의 인덱스 번호에 결핍 번호가 없기 때문이다. 표시 리스트 내의 이동과 오브젝트의 depths 관리는 ActionScript 1.0 및 2.0 보다 간단하게 되었다. ActionScript 1.0 및 2.0에서는 무비 클립의 심도순서에 불연속인 결핍이 있는 오브젝트가 포함되어 있었기 때문에 오브젝트의 리스트 내를 이동하는 것이 곤란했지만 ActionScript 3.0에서는 표시 오브젝트 컨테이너의 각각의 아이 리스트가 1 개의 배열로서 내부에 캐쉬되므로 인덱스에 의한 룩업이 매우 고속으로 실행된다. 또한 표시 오브젝트 컨테이너의 모든 아이를 매우 고속으로 루프 할 수도 있게 되었다.


표시 리스트내의 자유로운 이동


ActionScript 1.0 및 2.0 에서는 벡터 셰이프나 Flash authoring tool로 묘화 된 오브젝트에는 액세스 할 수 없다. ActionScript 3.0에서는 그러한 표시 리스트상의 모든 오브젝트, 즉 ActionScript를 사용해 작성된 오브젝트 및 Flash authoring tool로 작성된 모든 표시 오브젝트에 액세스 할 수 있게 되었다.


    

설정

트랙백

댓글

[AS3] 정적 프롭퍼티와 스코프 체인

Programming/ActionScript 3.0 2007. 6. 15. 14:00
정적 프롭퍼티는 계승되지 않지만 그 프롭퍼티가 정의된 클래스 및 그 클래스의 서브 클래스에서는 스코프 체인내에 있다. 즉, 정적 프롭퍼티가 정의된 클래스 및 그 서브 클래스의 스코프 내로부터 직접 정적 프롭퍼티에 액세스 할 수가 있다.













package {
import flash.display.MovieClip;
public class StaticExample extends MovieClip {
public function StaticExample() {
var myExt:Extender = new Extender();
}
}
}

class Base {
public static var test:String = "static";
}

class Extender extends Base {
public function Extender () {
trace(test); //
}
}

출력 : static


인스턴스 프롭퍼티가 같은 클래스 또는 슈퍼 클래스내에서 정적 프롭퍼티와 같은 이름을 사용하고 있는 경우 인스턴스 프롭퍼티는 스코프 체인내에서 우선 순위가 높아진다. 이는 정적 프롭퍼티의 값이 아니라 인스턴스 프롭퍼티의 값이 사용되는 것을 의미한다.

package {
import flash.display.MovieClip;
public class StaticExample extends MovieClip {
public function StaticExample() {
var myExt:Extender = new Extender();
}
}
}

class Base {
public static var test:String = "static";
}

class Extender extends Base {
public var test:String = "instance";
public function Extender () {
trace(test); //
}
}

출력 : instance
다른 예로 parent_mc라는 무비클립에 포함된 child_mc라는 무비클립이 있을 때 두개의 무비클립에 CLICK 이벤트 적용하게 되면 결과는 아래와 같이 나오게 된다.

parent_mc.child_mc.addEventListener(MouseEvent.CLICK, childClickHandler);
parent_mc.addEventListener(MouseEvent.CLICK, parentClickHandler);

function childClickHandler(evt:Event):void{
trace(evt.target.name +" is a child");
}
function parentClickHandler(evt:Event):void{
trace(evt.target.name +" is a parent");
}
출력 :
child_mc is a child
child_mc is a parent
parentClickHandler에서 해당 이벤트가 적용된 무비클립에 접근하기 위해서는 아래와 같은 형태로 접근을 시도해야 한다.

trace(evt.target.parent.name +" is a parent");

    

설정

트랙백

댓글

[AS3] Bound methods

Programming/ActionScript 3.0 2007. 6. 15. 11:38
ActionScript 3.0는 오브젝트 인스턴스를 자동적으로 기억하는 Bound methods를 제공한다. 이 기능은 이벤트 처리에 도움을 줄 수 있는데 기존의 ActionScript 2.0에서는 Bound methods에 추출원의 오브젝트 인스턴스가 기억되지 않아서 Bound methods가 불려 갔을 때에 예기치 않은 동작이 발생했다. 이를 해결하기 위해서 mx.utils.Delegate 클래스를 사용하는 것이 일반적인 방법이었지만, ActionScript 3.0부터는 불필요한 과정이 되었다.









class ThisTest {
private var num:Number = 3;
function foo () { // 정의된 Bound methods
trace ("foo's this: " + this);
trace ("num: " + num);
}
function bar () {
return foo; // 돌려주는 Bound methods
}
}

var myTest:ThisTest = new ThisTest();
var myFunc:Function = myTest.bar();
trace(this);
myFunc();
출력 :
[object global]
foo's this:[object ThisTest]
num: 3

Bound methods foo() 의 this 참조가 그 직전의 행의 this 참조가 글로벌 오브젝트를 가리키고 있지만 여전히 ThisTest 클래스의 인스턴스를 가리키는 것을 나타내고 있다. 게다가 myFunc 변수에 속하고 있는 Bound methods는 계속 ThisTest 클래스의 멤버 변수에 액세스 할 수 있다. 이 같은 코드를 ActionScript 2.0에서 실행하면 this 참조가 일치하기 때문에 num 변수는 undefined 가 된다.

    

설정

트랙백

댓글

[AS3] 파일 내에 복수 클래스

Programming/ActionScript 3.0 2007. 6. 15. 04:11
ActionScript 2.0에서는 클래스 파일을 작성하는 경우 클래스와 같은 이름의 파일을 만들게 된다.  예를 들어 Rec이라는 클래스가 있을 때 클래스의 원시 코드는 "Rec.as" 와 같은 파일명으로 저장이 되어야 한다. "Rec.as" 파일에 존재할 수 있는 클래스는 Rec클래스만 가능한 일이었다.

하지만 ActionScript 3.0 에서는 1개의 파일 내에 복수의 클래스를 저장할 수 있도록 설계되었다. Flash 9 alpha 버전에서는 package{} 내에서도 internal class로 여러 개의 클래스가 package내에서 사용가능하도록 하였으나 CS3로 만들면서 이러한 기능은 제외되었다. 하지만 package 외에는 여러개의 클래스를 정의할 수가 있도록 되어 있다. 1 개의 원시 소스 파일에 복수의 클래스를 보존하는 것이 편리할 수도 있지만 남용하면 OOP형태의 언어에서 바람직하지 않은 문제를 양산할 우려가 있다. 문제는 다음과 같은 경우이다.

1.    복수의 클래스가 1 개의 소스파일에 보존되고 있는 경우, 각각의 클래스를 재이용하는 것이 곤란하게 된다.

2.    파일명과 클래스명이 대응하고 있지 않는 경우, 특정의 클래스의 원시 소스코드를 찾아내는 것이 곤란하다.

이러한 문제점으로 인하여 Adobe에서는 각각 하나의 클래스는 하나의 원시소스파일로 저장하는 것을 권장하고 있다. Alpha 버전에서 package 내에서 복수 클래스를 정의할 수 있었던 것을 제외시킨 이유 또한 이러한 문제점 때문일 것이라는 생각이다.

다시 생각해보면 기존 ActionScript 2.0에서 디렉토리 형태로만 패키지 영역을 정의했던 것을 벗어나 package에서 명시적으로 패키지 영역을 정의하고 그 영역 안에서 복수의 클래스를 정의할 수 있도록 하는 방향으로 검토하였으나 위와 같은 두가지 문제로 인하여 언어적 비판을 벗어나기 위해 CS3 제품에서 package 내 복수 클래스 정의 부분을 제외한 것이 아닌가 생각된다. 개념적 접근에서 실의[實義]를 추구했다고 보여진다.

    

설정

트랙백

댓글

[AS3] for each..in 문법

Programming/ActionScript 3.0 2007. 6. 15. 04:04
var myObj:Object = {x:20, y:30};
for each (var num in myObj) {
    trace (num);
}
//
출력 :
// 20
// 30


XML 또는 XMLList 오브젝트의 반복 처리를 실행.
var myXML:XML = <users>
                   <fname>Jane</fname>
                   <fname>Susan</fname>
                   <fname>John</fname>
                </users>;

for each (var item in myXML.fname) {
    trace(item);
}
/*
출력
Jane
Susan
John
*/


배열의 엘리먼트의 반복 처리를 실행할 수도 있음.
var myArray:Array = ["one", "two", "three"];
for each (var item in myArray) {
    trace (item);
}
//
출력 :
// one
// two
// three

    

설정

트랙백

댓글