동강의AS3.0 강좌2008.12.11 01:52

디자인을 하다가 Flash 를 시작하시는 분이나, 일반 프로그래밍을 하다가 시작하는 분이나, Actionscript 의 이벤트라는 개념은 생소하게 다가 옵니다. 그래서 시작하는 분들이 조금이라도 빨리 이해를 돕고자 Event... 에 대해 이야기를 해 보겠습니다.  

Actionscript 3.0 을 시작하고 적응하기 어려웠던 점은 2.0 과 다르게 브로드 케스팅으로 이벤트를 호출하고 호출 받는 다는 점이었습니다. 2.0 에서도 그러한 개념이 있긴 했지만, 3.0 에 와서는 완전 바뀌었습니다.  

가장 많이 사용하는 flash.events.Event  = Event
flash.events.MouseEvent = MouseEvent  

초기에 Event 는 ENTER_FRAME 을 돌리기 위한 이벤트로 많이 사용되고 MouseEvent 는 마우스의 각기 반응들에 이벤트를 걸어 주기 위해 사용 됩니다. 그렇다면 어떠한 원리로 이벤트가 걸리게 되는 걸까요? ( 개념을 정리 하기 위한 추상적인 클래스이니, 고칠 부분을 알려 주시기 바람니다. )  

우선 Mouse 라는 Class 가 존재 합니다.

Mouse 라는 클래스 안에는 마우스의 상태가 MOUSE_OVER ,MOUSE_OUT, CLICK 되었을때의 호출되는 함수(여기에서는 각각의 문을 함수라고 생각하시면 됩니다 ) 가 정의 되어 있습니다. 이 세개의 문들은 마우스 이벤트가 일어날때를 대비 해서 항상 기다리고 있지요. (addEventLister 로 이벤트가 걸렸을 경우에만 기다리고 있습니다. )

이 문이 열리는 것이 마우스 이벤트가 실행 되었다는 의미 입니다. Actionscript 에서는 이 문들을 대기 시키기 위해서  

addEventListener(MouseEvent...)
의 방법으로 이벤트를 대기 목록에 하나하나씩 추가 하게 됩니다. 이벤트를 대기 하는 메모리 공간에 자신이 추가 하고 싶은 이벤트 를 추가(add) 하는 것이지요. 반대로 이 이벤트 대기 목록에서 빼기 위한 방법으로  removeEventLister(MouseEvent...) 의 방법을 사용함니다. 더이상 이벤트가 발생하는걸 기다리지 않아도 된다는 의미 입니다.  

하지만 위의 Mouse class 에 있는 각각의 문들이 열렸다는 것은 어떻게 알수 있을까요? 내부적으로 마우스가 클릭되거나 Over 되거나 했을때 자동적으로 문이 열리기 되는 것일까요? 내부적으로 그렇게 구현되었을 수도 있겠지만, Actionscript 에서는 이벤트를 발생시키고 생성하는 매소드를 제공합니다.  이때 사용 하는 것이 dispatchEvent 입니다.  

 
dispatchEvent () 메서드  
public override function dispatchEvent(event:Event):Boolean

언어 버전 :  ActionScript 3.0
Player 버전 :  Flash Player 9

이벤트를 이벤트 흐름으로 전달합니다. 이벤트 대상은 dispatchEvent() 메서드가 호출된 EventDispatcher 객체입니다.

매개 변수

event:Event — 이벤트 흐름으로 전달된 Event 객체입니다. 이벤트를 다시 전달하는 경우, 해당 이벤트의 복제본이 자동으로 만들어집니다. 이벤트가 전달된 뒤에는 이벤트의 target 속성을 변경할 수 없으므로, 재전달에 성공하려면 이벤트의 복사본을 새로 만들어야 합니다.

반환값
Boolean — 이벤트가 성공적으로 전달된 경우 값은 true입니다. false 값은 실패를 나타내거나 해당 이벤트에서 preventDefault()가 호출되었음을 나타냅니다.

오류
SecurityError — Stage 객체의 dispatchEvent() 메서드를 호출하면 스테이지 소유자(기본 SWF 파일)와 다른 보안 샌드박스에 있는 호출자에 대해 예외가 발생합니다. 스테이지 소유자는 이와 같은 상황을 피하기 위해 Security.allowDomain() 메서드 또는 Security.allowInsecureDomain() 메서드를 호출하여 호출자 도메인에 권한을 부여할 수 있습니다. 자세한 내용은 ActionScript 3.0 프로그래밍의 "보안" 장을 참조하십시오.

 중요한건 알겠는데 어떻게 사용 되는 것인가? Actionscript 에서는 내부적으로 Mouse 가 CLICK 되었을때 발생하는 함수가 구현되어 있을것입니다. 만약 MouseCLICK 이 발생할때 실행 되는 함수가 Class Mouse 의 function CLICK ():void {} 이라면 dispatchEvent 를 사용해서 연결 시킬수 있습니다.

 

 flash.events.MouseEvent
 
  1. package flash.events{
  2.        
  3.         public class MouseEvent
  4.         {
  5.                 public static const MOUSE_OVER:String = "mouseover";
  6.                 public static const MOUSE_OUT:String = "mouseout";
  7.                 public static const CLICK:String = "click";
  8.                
  9.                 etc....
  10.                
  11.                 public function MouseEvent(type : String, bubbles : Boolean = false, cancelable : Boolean = false)
  12.                 {
  13.                         ........
  14.                        
  15.                 }
  16.                
  17.                
  18.         }
  19. }
  20.  

 

Mouse Class 안에 존재 하는 CLICK 매소드 , 이 매소드는 마우스가 클릭되면 호출된다. 하지만 이벤트를 발생 시키는

담당은 dispatchEvent 가 맡게 된다. 

 

public function CLICK():void
{

  ........................

  .......................... dispatchEvent 로 이벤트와 함수를 연결시켜주는 것 외에 다른것들도 구현되어 있을것 같습니다.
 dispatchEvent(new MouseEvent(MouseEvent.CLICK));

}

 

dispatchEvent 로 인해 CLICK 이라는 함수와 MouseEvent 의 CLICK 이라는 이벤트는 동기화가 되게 됩니다. CLICK 함수가 실행되면 '아 MouseEvent.CLICK 이벤트가 실행 되었구나 ' 하고 리스너들이 알게 되는 것입니다.

 Flash 에서의 이벤트 전달과 캐취는 이런식으로 발생하게 됩니다. 이러한 것들은 이미 Actionscript 에서 내부적으로 구현 되어 있는 것들이고, 이 원리를 이용하여 CustomEvent 를 만들수 있고, 이벤트를 좀더 유도리 있게 사용할수 있게 되는 것입니다.   

간단한 예로 마이크에서 나오는 소리를 1초 단위로 받기 위한 이벤트를 만들어 보겠습니다. 우선 SoundEvent 란 CustomEvent 를 생성하고, flash.events.Event 를 상속 받았습니다.

 

  1. package customEvent {
  2.  import flash.events.Event;
  3.  
  4.  /**
  5.   * @author dongkang
  6.  
  7.   */
  8.  public class SoundEvent extends Event {
  9.  
  10.   public static const CATCH:String = "catching";
  11.  
  12.   public function SoundEvent(type : String, bubbles : Boolean = false, cancelable : Boolean = false) {
  13.    super(type, bubbles, cancelable);
  14.   }
  15.  }
  16. }

 

이렇게 하는 것 만으로도 자신만의 커스텀 이벤트가 생성됩니다. FDT 나 Flex Builder 를 사용하시는 분들은 Event 를 상속 받는 클래스를 생성했을때 자동으로 인자값이 들어 가는것을 확인할수 있을 것입니다. 그리고 SoundEvent 의 속성으로 사용될 public static const CATCH:String = "catching"; 를 생성하였습니다. CATCH 는 SoundEvent.CATCH 와 같이 사용될 수 있는 것이고 catching 은 addEventListener("catching',함수); 와 같이 사용할수 있게 합니다. 하지만 위의 SoundEvent Class 만으로는 동작이 불가능합니다. 어떠한 일을 하는지도 모를 뿐더러 SoundEvent 라는 이름만 정의 되어 있는 Class 이기 때문입니다. 그렇다면 어떻게 ? 이 클래스에 생명을 불어 넣을수 있을까요?   

dispatchEvent 를 사용 하면 됩니다.  

  1. /* dongkang . 2008-02-23
  2. SoundGauge Class  : checking sound 0 ~ 100 */
  3.  
  4. package interactive.sound{
  5.  
  6.  import flash.events.ActivityEvent;
  7.  import flash.events.StatusEvent;
  8.  import flash.events.Event;
  9.  import flash.events.TimerEvent;
  10.  
  11.  import flash.media.Microphone;
  12.  
  13.  import flash.display.Sprite;
  14.  import flash.display.MovieClip;
  15.  
  16.  import flash.utils.Timer;
  17.  
  18.  import customEvent.SoundEvent;
  19.  
  20.  public class SoundGauge extends Sprite {
  21.   private var device_arr:Array;
  22.   public var mic:Microphone;
  23.   private var gauge:MovieClip;
  24.   private var soundtimer:Timer;
  25.  
  26.   public function SoundGauge(_gauge:MovieClip):void {
  27.    gauge = _gauge;
  28.    device_arr = Microphone.names;
  29.    mic = Microphone.getMicrophone();
  30.    mic.gain = 40;
  31.    mic.rate = 11;
  32.    mic.setUseEchoSuppression(true);
  33.    mic.setLoopBack(true);
  34.    mic.setSilenceLevel(0,10);
  35.  
  36.  
  37.    for (var i:int =0; i < device_arr.length; i++) {
  38.     trace("   " + device_arr[i]);
  39.    }
  40.    
  41.    soundtimer = new Timer(1000);
  42.    soundtimer.start();
  43.    soundtimer.addEventListener("timer",onSoundhandler);
  44.   }
  45.  
  46.   private function onSoundhandler(e:TimerEvent) : void {
  47.    dispatchEvent(new SoundEvent(SoundEvent.CATCH));
  48.   }

 

 위의 클래스는 마이크에서 받은 소리를 1초 단위로 확인하기 위한 클래스 입니다. soundtimer 는 1초 단위로 onSoundhandler를 실행 시킬 것이고, 이 함수안에는 dispatchEvent 가 있어 SoundEvent.CATCH 가 호출되었다는 사실을 1초 단위로 계속 알려주게 됩니다. 그런데 누구 한테 알려 주는 걸까요? dispatchEvent 란 의미는 자기 자신이 해당되는 Class 에 SoundEvent.CATCH 를 걸어 주겠다는 의미 입니다. 다시 말해서 SoundGauge 에 SoundEvent.CATCH 이벤트가 걸리게 됩니다. 우리는 이 이벤트를 받아 오기 위해 SoundGauge 를 생성한 함수 내부에서 받아 올수 있습니다.  

 

var sg:SoundGauge = new SoundGauge();

sg.addEventListener(SoundEvent.CATCH, onCatch);

 

function onCatch(e:SoundEvent):void

{

 이함수는 어떻게 호출 되는 걸까요?

           SoundGauge 가 생성되자 마자 내부에 있는 soundtimer가 시작되기 때문에

         이 함수 또한 1초 마다 실행 되게 됩니다.

}

 

 

이처럼 dispatchEvent 는 정말 다양하게 중요하게 사용되는 메서드 입니다.
"이벤트를 이벤트 흐름으로 전달하고, 이벤트 대상은 dispatchEvent() 매서드가 호출된 EventDispatcher 객체 입니다. 쉬운 개념이 아닌 만큼 알게 되면 그동안 힘들게 했던 이벤트 전달을 손쉽게 적용할수 있으니, 그야 말로 최강 무기 라고 할수 있습니다. Actionscript 는 이벤트가 전부다 라고 말해도 될 만큼 이벤트중심으로 코드가 짜여 있습니다. 특히 이벤트를 전달하는 개념인 dispatchEvent 를 모르고 넘어 가신다면, 좋은 아이템을 버리고 싸우러 가는 것을 의미 할 정도로 중요합니다. 

 저도 알아 가고 있는 상태라 설명이 제대로 된지 모르겠습니다. 역시 잘못된 부분은 거침없이 태클 달아 주시고요, 잘 이해 안가는 부분은 알려 주시면 더 보충하도록 하겠습니다. 금요일 입니다. 주말 잘 보내시고 곧 있을 컨퍼런스가 기대가 되네요. 



Posted by Flash 동강
동강의AS3.0 강좌2008.12.11 01:43

지난 번 강좌에 이어서 해 보겠습니다. 다들 iMac navigation 이라면 아시지요? 맥을 쓰는 사람들은 항상 모니터 아랫쪽에 위치 시켜 두고 쓰는 편리 한(?) 네비게이션 입니다. 이미 많은 분들이 구현을 해 놓으셨고 윤용호 님이 쓰신 플래시 네비게이션 패턴 18 에서도 다루고 있습니다.  

1단계에서 만들 네비게이션은 아래와 같습니다.


stage 에 자신의 icon 을 디자인 하고, 그 icon 을 무비 클립으로 등록합니다.


저는 5개의 icon 을 만들었고, icon0 ~ icon4 로 이름을 붙였습니다. 이 5개의 무비 클립을 배열에 저장하고 그 배열의 순서로 icon 들을 조정할 것 입니다.  Document class 를 만들고 위의 icon 들을 저장할 배열을 만듭니다.   

 
  1. public function Main() {
  2.                        
  3.                         bit_arr = new Array();
  4.                         bit_arr = [icon0,icon1,icon2,icon3,icon4];
  5.                         
  6.                                
  7.                         for (var i:int=0; i< bit_arr.length; i++) {
  8.                                
  9.                                
  10.                                 bit_arr[i].trgScale = 1.0;
  11.                                 bit_arr[i].num = i;
  12.                                 bit_arr[i].addEventListener(MouseEvent.MOUSE_OVER, iconOverhandler);
  13.                                 bit_arr[i].addEventListener(MouseEvent.MOUSE_OUT, iconOuthandler);
  14.                                
  15.                                
  16.                                
  17.  
  18.                                 addChild(bit_arr[i]);
  19.                                
  20.                                
  21.                         }
  22.                        
  23.                         this.addEventListener(Event.ENTER_FRAME, onEnterframehandler);         
  24.                         mid =  Math.floor(bit_arr.length/2);
  25.                         overIcon = mid;
  26.                         overbool = false;
  27.                         center = bit_arr[mid].x;
  28.                 }

  for 문을 돌려서 만들었던 icon 들의 위치를 정해 주고, addEventListener 를 해 줍니다. 여기에서 각 icon 들 마다 num 과 trgScale 을 지정하였는데, num 은 icon 이 몇번째에 위치해 있나를 알려 주는 변수 이고, trgScale 은 icon 들의 크기를 조정할때 원래 크기로 돌아 가기 위한 기준을 저장하는 변수 입니다. enterframe 으로 돌리기 위한 이벤트로 등록을 하고, icon 들 사이에서 가운데에 존재 하는 icon 을 알기 위한 overIcon 을 지정해 줍니다. 그리고 그 x 위치를 저장해 줍니다. 위의 결과물에서도 알수 있듯이, icon 의 크기와 위치가 변하고, icon 에서 RollOut 되면 다시 원래의 자리로 돌아와야 합니다.  mid 값과 overIcon, center 값을 몰랐을 경우, 신경쓰지 않았을 경우에는 다음과 같은 일이 발생합니다. 무비 클립은 dynamic class 이기 때문에 직접적인 변수 생성이 가능합니다.
참고 : http://cafe.naver.com/flashactionscript/11367


마우스 롤 오버 & 아웃

 
  1. private function iconOverhandler(event : MouseEvent) : void {
  2.                         overbool = true;
  3.                         overIcon = event.target.num;
  4.                        
  5.  }

 

 

  1. private function iconOuthandler(event : MouseEvent) : void {
  2.                        
  3.                         iconReset();
  4.                                
  5.                         overbool = false;
  6.                        
  7. }

 마우스를 icon 에 오버 하면 enterframe 에서 if 문 처리를 판단하는 overbool 변수를 true 로 해 줍니다. 초기값은 false 로 되어있었지요. 그리고 어떤 icon이 오버 되었다는것을 알려 주는 overIcon 에 event.target.num 으로 숫자를 전달해 줍니다.  

지금 부터 산수 입니다;;;;;;;

 
  1. private function onEnterframehandler(event : Event) : void {
  2.                        
  3.                                        
  4.                         for (i=overIcon+1; i < bit_arr.length; i++) {
  5.                                 bit_arr[i].x = bit_arr[i-1].x + bit_arr[i-1].width/2 + bit_arr[i].width/2;
  6.                         }
  7.                         for (i=overIcon-1; i > -1; i--) {
  8.                                                                
  9.                                 bit_arr[i].x = bit_arr[i+1].x - bit_arr[i+1].width/2 - bit_arr[i].width/2;
  10.                         }
  11.                 }   

 

 

 

위에서

  1.   overbool = true;
  2.   overIcon = event.target.num;

한 이유가 여기서 나오게 됩니다. RollOver 하는 icon 이 바뀔때 마다 계속 Enterframe 을 돌려 주고 계속 위치를 변경해 줍니다.

 
  1. private function onEnterframehandler(event : Event) : void {
  2.                        
  3.                         for (var i:int=0; i<bit_arr.length; i++) {
  4.                                
  5.                                 if (overbool)
  6.                                 {
  7.                                         var distance:int = Math.abs(bit_arr[i].x- mouseX)/2;
  8.                                         bit_arr[i].trgScale = (200-distance)/100;
  9.                                         if (bit_arr[i].trgScale < 1.0)
  10.                                         {
  11.                                                 bit_arr[i].trgScale = 1.0;
  12.                                         }
  13.                                 }
  14.                                
  15.                                 bit_arr[i].scaleX = bit_arr[i].scaleY += (bit_arr[i].trgScale-bit_arr[i].scaleX)*0.4;                          
  16.                         }                              
  17.                         for (i=overIcon+1; i < bit_arr.length; i++) {
  18.                                 bit_arr[i].x = bit_arr[i-1].x + bit_arr[i-1].width/2 + bit_arr[i].width/2;
  19.                         }
  20.                         for (i=overIcon-1; i > -1; i--) {
  21.                                                                
  22.                                 bit_arr[i].x = bit_arr[i+1].x - bit_arr[i+1].width/2 - bit_arr[i].width/2;
  23.                         }
  24.                 }       
  25.  

 

마우스의 X 위치 값과 icon 의 x 위치 값을 이용하여 distance 를 구합니다. 마우스가 멀리 있을 수록 distance 는 커지게 되고 icon 에 영향을 주게 되는 trgScale 값이 작아 지게 됩니다.  

  1. if (bit_arr[i].trgScale < 1.0)
  2. {
  3.        bit_arr[i].trgScale = 1.0;
  • }

    if 문을 이용해서 trgScale 이 원래의 scale 크기인 1.0 보다 작아 지는것을 막아 줍니다. if 문을 빼고 돌려 보세요.

    bit_arr[i].scaleX = bit_arr[i].scaleY += (bit_arr[i].trgScale-bit_arr[i].scaleX)*0.4;   

    그런후 가속도 공식을 이용하여, 크기를 변화 시켜 줍니다.
    가속도 공식 :   

    변화시키고 싶은 속성 += (원래 속성값 - 변화후 속성값)*변위(?)( 갑자기 단어가 생각이 안남 )
    ex ) this.x += ( this.x - targetX ) *0.1;   x 의 위치를 targetX 까지 변화 시킴  

    여기까지 오버 하였을때 icon 들을 변화 시켜 보았습니다. 그럼 롤 아웃 하면 ? 위에서 나왔던 iconReset() 함수를 구현해 보면

     
    1. private function iconReset():void
    2.                 {
    3.                         for (var i:int=0; i<bit_arr.length; i++) {      -------------- 1)
    4.                                 bit_arr[i].trgScale = 1.0;
    5.                         }
    6.                         overIcon = mid;                                     -------------- 2)
    7.                        
    8.                        
    9.                         bit_arr[mid].addEventListener(Event.ENTER_FRAME,mcEnterframe);            -------- 3)
    10.                 }
    11.                
    12.                 private function mcEnterframe(event : Event) : void { ----------------- 4)
    13.                         var speed:int = (center-event.target.x)*0.1;
    14.                         event.target.x += speed;
    15.                         if (Math.abs(speed)<0.01) {
    16.                                 bit_arr[mid].removeEventListener(Event.ENTER_FRAME,mcEnterframe);
    17.                         }
    18.                 }

     

    1) 모든 icon 의 scale 을 1.0 로 조절함니다. ( onEnterframe 에서 계속 돌아 가고 있기 때문에 trgScale 만 바꿔주면 됩니다 )

    2) 다시 mid 값을 가운데 위치한 icon 으로 초기화 합니다.

    3) 원래 위치로 돌아 가기 위한 mcEnterframe 를 등록합니다.  

    4) 롤 아웃이 되면 전에 있었던 center 로 가운데 있던 icon 이 이동합니다. 이 icon 만 이동 시켜도 되는 이유는 onEnterframe 에서 계속 아래 for 문이 돌아 가고 있기 때문입니다. 그리고 어느 정도 오차가 생기겠지만 speed 값이 0.01 보다 작아 지면 removeEventListener 를 해 줍니다. ( enterframe 을 계속 돌리는 것은 낭비 0.01 정도 되면 거의 변화가 느껴지지 않습니다 )

    1. private function onEnterframehandler(event : Event) : void {
    2.                        
    3.                                        
    4.                         for (i=overIcon+1; i < bit_arr.length; i++) {
    5.                                 bit_arr[i].x = bit_arr[i-1].x + bit_arr[i-1].width/2 + bit_arr[i].width/2;
    6.                         }
    7.                         for (i=overIcon-1; i > -1; i--) {
    8.                                                                
    9.                                 bit_arr[i].x = bit_arr[i+1].x - bit_arr[i+1].width/2 - bit_arr[i].width/2;
    10.                         }
    11.                 }   

    사용된 전체 코드.

     
    1. package {
    2.         import flash.display.MovieClip;
    3.         import flash.events.Event;
    4.         import flash.events.MouseEvent;
    5.         import flash.utils.Timer;
    6.         import com.pixelfumes.reflect.*;
    7.        
    8.         import icon.Cicon;     
    9.  
    10.         /**
    11.          * @author navi main
    12.          */
    13.         public class Main extends MovieClip {
    14.                
    15.                 private var overbool:Boolean;
    16.                 private var overIcon:int;
    17.                 
    18.                 private var center:int;
    19.                 private var mid:int;
    20.                 private var frametime:Timer;
    21.                 private var bit_arr:Array;
    22.                        
    23.                 public function Main() {
    24.                        
    25.                         bit_arr = new Array();
    26.                         bit_arr = [icon0,icon1,icon2,icon3,icon4];
    27.                       
    28.                                
    29.                         for (var i:int=0; i< bit_arr.length; i++) {
    30.                                
    31.                                
    32.                                 bit_arr[i].trgScale = 1.0;
    33.                                 bit_arr[i].num = i;
    34.                                 bit_arr[i].addEventListener(MouseEvent.MOUSE_OVER, iconOverhandler);
    35.                                 bit_arr[i].addEventListener(MouseEvent.MOUSE_OUT, iconOuthandler);
    36.                                
    37.                                
    38.                                 addChild(bit_arr[i]);
    39.                                
    40.                                
    41.                         }
    42.                        
    43.                         this.addEventListener(Event.ENTER_FRAME, onEnterframehandler);         
    44.                         mid =  Math.floor(bit_arr.length/2);
    45.                         overIcon = mid;
    46.                         overbool = false;
    47.                         center = bit_arr[mid].x;
    48.                 }
    49.        
    50.  
    51.                 private function iconReset():void
    52.                 {
    53.                         for (var i:int=0; i<bit_arr.length; i++) {
    54.                                 bit_arr[i].trgScale = 1.0;
    55.                         }
    56.                         overIcon = mid;
    57.                        
    58.                        
    59.                         bit_arr[mid].addEventListener(Event.ENTER_FRAME,mcEnterframe);
    60.                 }
    61.                
    62.                 private function mcEnterframe(event : Event) : void {
    63.                         var speed:int = (center-event.target.x)*0.1;
    64.                         event.target.x += speed;
    65.                         if (Math.abs(speed)<0.01) {
    66.                                 bit_arr[mid].removeEventListener(Event.ENTER_FRAME,mcEnterframe);
    67.                         }
    68.                 }
    69.  
    70.                 private function iconOuthandler(event : MouseEvent) : void {
    71.                        
    72.                         iconReset();
    73.                                
    74.                         overbool = false;
    75.                        
    76.                 }
    77.  
    78.                 private function iconOverhandler(event : MouseEvent) : void {
    79.                         overbool = true;
    80.                         overIcon = event.target.num;
    81.                        
    82.                 }
    83.                        
    84.                
    85.                 private function onEnterframehandler(event : Event) : void {
    86.                        
    87.                         for (var i:int=0; i<bit_arr.length; i++) {
    88.                                
    89.                                 if (overbool)
    90.                                 {
    91.                                         var distance:int = Math.abs(bit_arr[i].x- mouseX)/2;
    92.                                         bit_arr[i].trgScale = (200-distance)/100;
    93.                                         if (bit_arr[i].trgScale < 1.0)
    94.                                         {
    95.                                                 bit_arr[i].trgScale = 1.0;
    96.                                         }
    97.                                 }
    98.                                
    99.                                 bit_arr[i].scaleX = bit_arr[i].scaleY += (bit_arr[i].trgScale-bit_arr[i].scaleX)*0.4;                          
    100.                         }                              
    101.                         for (i=overIcon+1; i < bit_arr.length; i++) {
    102.                                 bit_arr[i].x = bit_arr[i-1].x + bit_arr[i-1].width/2 + bit_arr[i].width/2;
    103.                         }
    104.                         for (i=overIcon-1; i > -1; i--) {
    105.                                                                
    106.                                 bit_arr[i].x = bit_arr[i+1].x - bit_arr[i+1].width/2 - bit_arr[i].width/2;
    107.                         }
    108.                 }       
    109.         }
    110. }

     

    네비게이션의 경우에는 수학적인 이해가 들어 가는 부분이 많은것 같습니다. 하지만 공식처럼 쓸줄만 알면 되니깐 걱정 하진 마세요. 이번에는 한 Document class 에 다 때려 박았는데, 다음 강 부터 네비게이션을 보완하면서 2단계로 만들어 보겠습니다. 그러기 위해서는 이 하나의 클래스를 잘 이해 하고 계시는게, 2단계를 나가는데 지장이 없을꺼라 생각 됩니다.  

    다음 강에서는 클래스를 분리 하고, 좀더 이것 저것 붙여 보겠습니다. 휙휙 지나간 면이 없지 않아 있네요;; ㅋ 잘못된 점이나, 질문이 있으시면 거침 없는 댓글이나, 답글 부탁 드립니다. !! 수고하셨습니다.

     - 완료 파일 다운 받기-



  • Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 01:41

    10강을 시작으로 다룰 내용은 Flash Navigation 입니다. 플래시 메뉴라고 하면 되겠네요. 아주 간단한 메뉴에서 시작해서 xml 을 이용한 메뉴 구성 까지 계획을 하고 있습니다. 우선 적으로 알아야 할것이 Array Class 와  caurina Tweener 의 사용법을 알아야 합니다.  

     

      Array 

      Package    :loadClassListFrame('class-list.html')" href="file:///C:/Documents%20and%20Settings/All%20Users/Application%20Data/Adobe/Flash%20CS3/en/Configuration/HelpPanel/Help/ActionScriptLangRefV3/package-detail.html">Top Level
      Class            public dynamic class Array
      Inheritance  : Array -> Object

     Array 는 배열 입니다. ( 기본 속성은 레퍼런스를 참조하세요 )

     
    1. var twoArray:Array = ["z"]; 
    2.  twoArray[0] = "z";            
    3.  trace(oneArray);              
    4.  

     여기서 알고 넘어 갈 부분은 push, pop , Array 속성의 함수 입니다. push 는 배열에 넣어 주는 역할 pop 은 배열의 가장 끝에 있는 객체를 반환에 주는 함수 입니다.

      

      push 예제  a,b,c String 을 letters 에 넣어 주고 toString 으로 확인해 봅니다.

    1. var letters:Array = new Array();
    2.  
    3. letters.push("a");
    4. letters.push("b");
    5. letters.push("c");
    6.  
    7. trace(letters.toString()); // a,b,c

     

     

     pop 예제  // 자료구조에서 pop 과 의미가 같다. 배열의 가장 뒤에 있는 객체를 반환한다. (반환된 객체를 받지 않으면

     소멸 된다 )

    1. var letters:Array = new Array("a", "b", "c");
    2. trace(letters); // a,b,c
    3. var letter:String = letters.pop();
    4. trace(letters); // a,b
    5. trace(letter);     // c

     

     
    1. var mc:MovieClip = new MovieClip();
    2. var a_arr:Array = new Array();
    3. var b_arr:Array = new Array();
    4.  
    5. a_arr[0] = mc;
    6. b_arr[0] = mc;
    7.  
    8. trace("a_arr[0] : "+a_arr[0].name);
    9. trace("b_arr[0] : "+b_arr[0].name);
    10.  

    1. a_arr[0] = mc;
    2. b_arr[0] = mc;

    이 부분을 a_arr.push(mc);  b_arr.push(mc) 로 해도 같은 결과가 출력됩니다. 요지는, Array 의 사용에 있어서 push 와 pop 을 잘 활용 해야 된다는 점 입니다. push 와 [0] = mc 로 인해 배열에 저장되는 값은 실체 그 객체가 아니라, 그 객체가 저장되어 있는 주소 값이 라고 생각하시면 될것 같습니다. 지금까지는 언급하지 않았지만 , 배열을 사용할때 Actionscript 에서의 메모리 문제를 잘 이해 하시고 사용하셔야 됩니다. 우선 Actionscript 에서의 메모리 참조 해제 방식은 Flash Player 에 있는 가비지 콜렉션  이 관장을 하고 있습니다. 가비지 콜렉션이란, 뜻 그대로 쓰레기 값들을 모아 준다는 말입니다. 일반적으로 Java 에서는 객체 = null 하면 메모리가 바로 해제 되는 경우였지만 플레시 에서는 조금 다름이다. 예제를 보면

     
    1. var mc:MovieClip = new MovieClip();
    2. mc = null;
    3.  

     mc 라는 무비 클립의 메모리가 바로 해제 되는 것이 아니라, 가비지 콜렉션의 수집 대상이 되는 것입니다. ( 수집이 완료된 후에 메모리 해제가 일어 나는 것이지요 ) 이 경우는 addEventListener 의 경우에서도 똑같이 적용 됩니다.   

    addEventListener () 메서드  

    public override function addEventListener(type:String, listener:Function, useCapture:Boolean = false, priority:int = 0, useWeakReference:Boolean = false):void
     
    마지막 파라미터 값인 useWeakReference 로 인해  리스너에 대한 참조가 강한지 아니면 약한지를 결정합니다. 강한 참조(기본값)는 해당 리스너의 가비지 수집을 막습니다. 약한 참조는 이를 막지 못합니다.
     
    addEventListener 을 하고 removeEventListener 를 해 줬다고 해서 메모리가 바로 해제 되는 것은 아니라는 점입니다. 일반 적으로 addEventListener 를 사용할때 두 가지 파라 미터만 쓰는 경우가 많은데 이 경우도 알아 놓으시기 바람니다.
     
    한가지의 예제를 더 보면
     
    1. var mc:MovieClip = new MovieClip();
    2. addChild(mc);
    3. var a_arr:Array = new Array();
    4. var b_arr:Array = new Array();
    5.  
    6. a_arr[0] = mc;
    7. b_arr[0] = mc;
    8.  
    9. mc = null;
    10.  
    11. trace("a_arr[0] : "+a_arr[0].name);
    12. trace("b_arr[0] : "+b_arr[0].name);
    13.  
    14. output
    15. a_arr[0] : instance1
      b_arr[0] : instance1
    16.  
     
    1. var mc:MovieClip = new MovieClip();
    2. addChild(mc);
    3. var a_arr:Array = new Array();
    4. var b_arr:Array = new Array();
    5.  
    6. a_arr[0] = mc;
    7. b_arr[0] = mc;
    8.  
    9. mc = null;
    10. a_arr[0] = null;
    11. b_arr[0] = null;
    12. trace("a_arr[0] : "+a_arr[0].name);
    13. trace("b_arr[0] : "+b_arr[0].name);
    14.  
    15. output
    16. TypeError: Error #1009: null 객체 참조의 속성이나 메서드에 액세스할 수 없습니다.
       at Untitled_fla::MainTimeline/frame1()

     mc = null 로 객체의 주소 값에 대한 참조를 삭제 하긴 했지만

    1. a_arr[0] = mc;
    2. b_arr[0] = mc;

    여기에서 새로운 참조가 생겨 가비지 콜렉션의 수집을 막게 됩니다. 수집대상으로 만들기 위해서는 모든 연결을 없애 주어야 겠지요?

    요지는 쓸대 없는 객체의  = null 을 생활화 하자 입니다. 어려운 내용이니 계속 반복해서 보세요.  

    가비지 콜렉션의 자세한 내용은 : http://memolog.blog.naver.com/dongkang0626/38
     
    Caurina Tweener
    caurina 트위너는 Google code 에 업댓 되고 있는 AS2.0, AS3.0 트윈 클래스 입니다.    

    클래스원본위치

    http://code.google.com/p/tweener/  

    사용을 위해서는 우선 caurina 패치지를 다운 받으시고, (첨부 파일) fla 나 as 파일이 있는 곳에 압축을 풀어 놓으심니다. 그후

    import caurina.transitions.Tweener;               // 클래스를 사용하기 위한 import

    여기에서 import 를 잘못해서 헤매시는 분이 있는데, fla 이 만들어져 있는 폴더에 caurina 폴더가 함께 있으면 됩니다.  

     

    아주 간단한 사용법

    Tweener.addTween(myMovieClip, {속성이 들어감});

    myMovieClip 은 무비 클립 이름입니다 (지금까지 무비 클립의 이름을 지정해서 사용했던 방법으로 입력하면 됨)

    그리고 트위너 자체에서 제공 하고 있는 엄청난 종류의 속성들

    x , y , width ,height , scaleX, scaleY , alpha , _bezier:[],time, onComplete:,onCompleteParams:[],onStart:,onUpdate, rotation,delay, 등등.

     

    onStart : tween 시작 핸들러 등록
    onComplete : tween 큰 핸들러 등록
    onUpdate : tween 진행중 핸들러 등록

    onCompleteParams:[], onComplete 함수 지정시 넘길 파라미터를 지정해 준다.(onStart 와 onUpdate로 똑같이적용)

     

    _bezier: [] 이동할때 베지어 곡선을 만들기 위한 점을 지정해 준다.

    time : 변화가 진행되는 시간을 정해준다.

    delay : 명령문이 실행되고, delay: 몇초 가 흐른 뒤에 해당 명령문을 실행 시켜 준다.

     

    transition:"" 변화 진행되는 그래프를 지정해 준다.

     

     
     그럼 사용해 보겠습니다. circle_mc 무비 클립을 만들고,

     
    1. import caurina.transitions.Tweener;
    2.  
    3. Tweener.addTween(circle_mc,{x:300,y:300,time:2.0,transition:"easeoutinelastic"});

     Flash 자체의 Tween 과 다르게 한번에 여러 속성을 변경 시킬수 있습니다. 해당 속성에 들어 가는 값은 목표치 즉, 변경 하고자 하는 결과 위치를 나타 냄니다. 괴물투수 형님이 쓰신 팁을 인용하면

     

     

    간단히 사용해보기

    <A>

    Tweener.addTween(myObject , {x:20, time:1, transition:"easeOut"});

     

    <B>

    Tweener.addTween(myObject , {_frame:20, time:1, transition:"easeOut"});

     

    간단한 설명

    이것은 기본적으로 1. 바꾸고 싶은 것과 바꾸고 싶은것의 2. 목표치를 적어넣음으로써 작동합니다.

     

    위의 <A>에서 바꾸고 싶은건 x 좌표이고 목표치는 20이 되겠고

    <B>에서는 바꾸고 싶은건 프레임이고 가고 싶은 프레임은 20프레임이 되겠네요

     

    그리고 뒤의 time은 이동하는 시간이고 뒤의 transitions는 운동의 느낌을 나타냅니다.

     

    <A>

    x는 myObject 이놈이 원래 가지고 있는 속성입니다.

    myObject가 무비클립이라면 x , y , alpha , width , height 등등이 되겠죠?

     

    <B>

    여기서 _frame은 myObject란 놈이 원래 가지고 있는 속성이 아닙니다

    이것은 google tweener에서 스페셜하게도 제공하는 스페셜한 special properties인 것입니다

    frame , color , sound 등등이 있고 사용은 동일하게 하되 ,

    속성명 앞에 _(언더바)가 붙는 특징이 있습니다.

     

     

     
    1. import caurina.transitions.Tweener;
    2.  
    3. startfunc(circle_mc);
    4.  
    5. function startfunc(_mc:MovieClip):void
    6. {
    7.         Tweener.addTween(_mc,{onComplete:completefunc,onCompleteParams:[_mc],scaleX:5.0,scaleY:5.0,time:2.0,transition:"easeoutinelastic"});
    8. }
    9. function completefunc(_mc:MovieClip):void
    10. {
    11.         trace("트윈종료 : "+_mc);
    12. }

     

    참 쉽지요? ;;; 

    저는 Tween 보다 caurina 를 자주 사용 한담니다. 그 만큼 편하고, 속도도 나름(?) 괜찬게 나오는 좋은 녀석입니다. 지금까지 네비게이션을 만들기 위한 기초 부분에 대해 써 보았습니다. 다음에는 iMac navigation 디자인 및, 구현 방법, 프로토 타입을 만들어 보도록 하겠습니다.   

    이제 3월 18일이면 AIR 가 우리나라에서도 정식으로 나오게 되고, Flex 3 도 런칭이 되게 됩니다. 이 말은 Actionscript 3.0 이 더이상 Flash Flex 만을 위한 조금한 일부분을 벗어나 RIA 의 선두 주자로의 도약을 시작할것이라 생각됩니다. 많은 분들이 Actionscript 3.0 은 선택이 아니라, 필수라는 말을 하심니다. 이제 그 말이 현실이 되어 나타 나고 있습니다. 곧 Adobe 에서 디자이너와 개발자의 협업을 위한

    "Thermo"(http://labs.adobe.com/wiki/index.php/Thermo) 가 출시 될 것이고, Actionscript3.0 의 중요성은 더욱 강조될 것입니다.  

    Adobe 에서 이렇게 발빠르게 움직이고 있는데, 쓰는 사람이 가만히 있을수는 없겠지요??

    "자 공부 합시다. 그리고 삽질 합시다."

    역시나 잘못된 부분이나, 질문 사항 거침 없이 댓글 부탁드립니다. 



    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 01:37

    스터디에서 같이 해보게 될 이미지 슬라이드  소스 파일 입니다.
    3가지 클래스를 메인으로 사용하고 있습니다.    

    1. Tween
    2. Loader
    3. Timer 

    지금까지의 강좌에서 계속 사용해 왔고, 언급했으므로 소스를 파악하시기엔 무리가 없을듯 합니다.
    중점적으로 볼 부분에는 강조를 해 놓았으니 그 부분에 대해 어떤 구조로 이미지가 돌아가고 있구나 정도 파악하시고 참여 하시면 됩니다. 소스를 미리 올리는 이유는 로직적으로 이해하기 어려운 부분이 포함되어 있기 때문에  미리 올리는 것이니 꼭 꼭 실행 시켜 보세요.   

     CustomMain.as ( Document class)

     
    1. package {
    2.        
    3.         import flash.display.MovieClip;
    4.         import flash.utils.Timer;
    5.         import fl.transitions.Tween;
    6.         import fl.transitions.easing.*;
    7.         import Circle;
    8.                
    9.         import flash.events.TimerEvent;
    10.  
    11.                
    12.         public class CustomMain extends MovieClip
    13.         {
    14.                 private var frame_arr:Array;
    15.                 private var frame_time:Timer;
    16.                 private var frame_num:int;
    17.                
    18.                 private var position_arr:Array;
    19.                
    20.                 public function CustomMain():void
    21.                 {
    22.                          frame_num = -1;
    23.                          frame_arr = new Array();
    24.                          position_arr = [-500,0,500];
    25.                          frame_arr[0] = new Circle(-500,0);
    26.                          frame_arr[1] = new Circle(-500,0);
    27.                          frame_arr[2] = new Circle(-500,0);
    28.                                                  
    29.                                                  
    30.                                                  frame_arr[0].loadimage("http://dongkang.ivyro.net/data/image.jpg");
    31.                                                  frame_arr[1].loadimage("http://dongkang.ivyro.net/data/image2.jpg");
    32.                                                  frame_arr[2].loadimage("http://dongkang.ivyro.net/data/image3.jpg");
    33.                                                  
    34.                          addChild(frame_arr[0]);
    35.                          addChild(frame_arr[1]);
    36.                          addChild(frame_arr[2]);
    37.                          
    38.                          frame_time = new Timer(3000);
    39.                          frame_time.start();
    40.                          frame_time.addEventListener("timer",frametimehandler);
    41.              
    42.                 }
    43.                 private function frametimehandler(e:TimerEvent):void
    44.                 {              
    45.                                
    46.                                                
    47.                         if(frame_num == -1)
    48.                         {
    49.                             new Tween(frame_arr[0],"x",Strong.easeInOut,frame_arr[0].x,position_arr[1],20,false);  
    50.                                                        
    51.                         }
    52.                         else
    53.                         {       
    54.                                                        
    55.                                                         var targetF:int = frame_num%3;
    56.                                                         var targetB:int = (frame_num+1)%3;
    57.                                                         trace(targetB);
    58.                                                        
    59.                       new Tween(frame_arr[targetF],"x",Strong.easeInOut,position_arr[1],position_arr[2],20,false);      
    60.                       new Tween(frame_arr[targetB],"x",Strong.easeInOut,position_arr[0],position_arr[1],20,false);
    61.                                                        
    62.                            
    63.                                
    64.                         }
    65.                                                 frame_num++;
    66.                                                
    67.                        
    68.                        
    69.                 }              
    70.                
    71.         }
    72.        
    73.        
    74. }

     

     Circle.as
     
    1. package {
    2.         import flash.display.DisplayObject;
    3.         import flash.display.Loader;
    4.         import flash.display.MovieClip;
    5.         import flash.events.Event;
    6.         import flash.net.URLRequest;   
    7.  
    8.         public class Circle extends MovieClip {
    9.  
    10.                 public function Circle(xn:int,yn:int):void {
    11.                         this.x = xn;
    12.                         this.y = yn;
    13.  
    14.  
    15.                 }
    16.                 public function loadimage(url:String):void {
    17.  
    18.                         var ld:Loader = new Loader();
    19.                         ld.load(new URLRequest(url));
    20.                         ld.contentLoaderInfo.addEventListener(Event.COMPLETE, onldComplete);
    21.                         addChild(ld);
    22.  
    23.                 }
    24.                 public function onldComplete(e:Event):void
    25.                 {
    26.                          var mObject:DisplayObject = e.target.content;
    27.              mObject.width=500;
    28.              mObject.height=450;               
    29.                 }
    30.                
    31.         }
    32. }

     

    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 01:36

    요즘엔 구글링을 하면서, 이 사이트 저 사이트 많이 돌아 다니고 있는데, 정말 세상을 넓고, 대단한 사람들은 많다 라고 세삼 느껴지네요.  

    월요일 입니다. 다들 피곤하시져?? 주말에도 일하신 분들도 있으실테고, 주말 동안 푹 쉬신 분들도 있을 겁니다.  월요일이고, 새롭게 시작하는 느낌으로 일주일을 시작하는것도 좋을듯 싶습니다.  

    이번에 볼 내용은 Timer class 와 Loader class 입니다. 두 클래스 모두 강력한 기능으로 작업의 능률을 높여 주는 그런 클래스들 입니다. 우선 Timer class 부터 레퍼런스를 살펴 봅시다.  

     Timer 

    클래스  public class Timer
    상속 Timer  EventDispatcher  Object

    언어 버전 :  ActionScript 3.0
    Player 버전 :  Flash Player 9

     

     
      Timer(delay:Number, repeatCount:int = 0)
      지정된 지연 및 반복 횟수 상태를 사용하여 새 Timer 객체를 만듭니다.  
     
    1. var time:Timer = new Timer(1000,5);
    2. time.start();

      delay 시간은 ms 단위로 합니다. 1000 = 1초가 되는 거지요. repeatCount 는 이 timer을 몇번 반복해서 실행 시키겠는가?

      위에서는 5번 실행 시키고 실행을 중단하게 됩니다.

     꼭 start() 를 해줘야 시작이 되고, 멈추는건 stop(); 으로 멈출수 있습니다. 그러면 저거 두개만 으로 어떻게 Timer 를 활용하는가? 보통 TimerEvent 라는 Timer 가 가지고 있는 기본 이벤트와 함께 사용됩니다.

     

     
    1. package{
    2.        
    3.         import flash.display.Sprite;                  
    4.         import flash.events.TimerEvent;                // 기본 import
    5.         import flash.utils.Timer;
    6.        
    7.         public class TimerExample extends Sprite
    8.         {
    9.                 private var time:Timer;                   // 객체 정의
    10.                
    11.                 public function TimerExample():void
    12.                 {
    13.                         time = new Timer(1000,5);
    14.                         time.start();
    15.                         time.addEventListener(TimerEvent.TIMER,ontimerhandler);
    16.                         time.addEventListener(TimerEvent.TIMER_COMPLETE,onCompletehandler);
    17.                
    18.                 }
    19.                 private function ontimerhandler(event:TimerEvent):void
    20.                 {
    21.                         trace("1초");
    22.                        
    23.                 }
    24.                 private function onCompletehandler(event:TimerEvent):void
    25.                 {
    26.                         trace("타임 끝");
    27.                 }
    28.                
    29.         }
    30. }

     

    time.addEventListener(TimerEvent.TIMER,ontimerhandler);
    1초 마다 실행되는 함수를 정의합니다. 지정한 시간에 호출되는 함수를 정의(이벤트를 생성시켜줌)

    time.addEventListener(TimerEvent.TIMER_COMPLETE,onCompletehandler);
    time 이 모두 실행 된 후에 실행되는 함수를 지정 (이벤트를 생성시켜줌)

    //output

    1초
    1초
    1초
    1초
    1초
    타임 끝

    우리가 쓰고 있는 enterframe 이 fps 단위로 실행되는 반면, Timer 는 초 단위로 실행 됩니다. Timer 가 enterframe 에 비해서 정확할수 있다고 말하는것도 여기에 있는듯 합니다. 다른 속성도 있으나 잘 쓰이지 않으므로 레퍼런스를 한번 보시는것도 좋을듯  싶습니다.

     

     Loader

     

     
      클래스 public class Loader
      상속 Loader  DisplayObjectContainer InteractiveObject  DisplayObject  EventDispatcher  Object

     

     
     Loader()
     SWF, JPEG, GIF 또는 PNG 파일 등을 로드하는 데 사용할 수 있는 Loader 객체를 만듭니다.
     
     
    1. var ld:Loader = new Loader();
    2. ld.load(new URLRequest("image.jpg"));

     ld 라는 로더를 만들어서 URLRequest 로 정의된 주소값의 jpg나 gif png swf 파일을 로드 합니다.

     

    참고 ) URLRequest

    URLRequest 클래스는 하나의 HTTP 요청에 포함된 모든 정보를 캡처합니다.

    말이 어려워지므로, 걍 주소를 정의하기 위해서는 URLRequest 타입으로 해야 된다는것만 알아 주세요

    (2.0 과의 차이점입니다. )

     

     

     
    1. package{
    2.        
    3.         import flash.display.Sprite;
    4.         import flash.display.Loader;
    5.         import flash.events.*;
    6.         import flash.net.URLRequest;
    7.         import flash.display.DisplayObject;
    8.  
    9.         public class LoaderExample extends Sprite{
    10.                
    11.                 private var ld:Loader;
    12.                
    13.                 public function LoaderExample():void
    14.                 {
    15.                         ld = new Loader();
    16.                         var url:URLRequest = new URLRequest("image.jpg");
    17.                         ld.load(url);
    18.                         ld.contentLoaderInfo.addEventListener(Event.COMPLETE, completehandler);
    19.                         ld.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS, progresshandler);
    20.                        
    21.                         addChild(ld);                  
    22.                 }
    23.                 private function completehandler(event:Event):void
    24.                 {
    25.                          var mObject:DisplayObject = event.target.content;
    26.                          mObject.width=100;
    27.                          mObject.height=100;
    28.                        
    29.                 }
    30.                 private function progresshandler(event:ProgressEvent):void
    31.                 {
    32.                         var mPercent:Number =int( event.bytesLoaded/event.bytesTotal*100.0);
    33.  
    34.                         trace(mPercent);
    35.                 }
    36.                
    37.         }
    38.        
    39. }

     

    같은 폴더에 image.jpg 라는 파일이 있어야 로드가 됩니다. 없으면 URL 에러를 일으킴니다.

     

    //output

    로드중
    로드중
    로드중
    로드중
    로드끝

     

    여기서 contentLoaderInfo 는 뭔가?

      contentLoaderInfo : LoaderInfo
    [read-only] 로드 중인 객체에 해당하는 LoaderInfo 객체를 반환합니다.
     

    LoaderInfo 란 Loader 에 의해 불러와지는 데이터의 정보 입니다. 예를 들면 jpg 이미지라면 크기 (width, height 가 있겠지요?)

    Loader 는 이러한 LoaderInfo 를 참조하여 그 값들을 변경할수 있습니다. 어쩌피 이미지가 swf 파일이 로드 되는 것도 bitmapdata 를 거쳐서 들어 오는것이기 때문에 변환이 가능합니다. ( 하지만 크로스 브라우징 문제가 발생할수도 있습니다 )

     

    1.  
    2. package{
    3.        
    4.         import flash.display.Sprite;
    5.         import flash.display.Loader;
    6.           import flash.display.DisplayObject;
    7.         import flash.events.*;
    8.     import flash.net.URLRequest;
    9.  
    10.         public class LoaderExample extends Sprite{
    11.                
    12.                 private var ld:Loader;
    13.                
    14.                 public function LoaderExample():void
    15.                 {
    16.                         ld = new Loader();
    17.                         var url:URLRequest = new URLRequest("image.jpg");
    18.                         ld.load(url);
    19.                         ld.contentLoaderInfo.addEventListener(Event.COMPLETE, completehandler);
    20.                         ld.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS, progresshandler);
    21.                        
    22.                         addChild(ld);                  
    23.                 }
    24.                 private function completehandler(event:Event):void
    25.                 {
    26.                          var mObject:DisplayObject = event.target.content;
    27.                          mObject.width=100;
    28.                          mObject.height=100;              // 로드된 이미지는 100 / 100 으로 사이즈 변경
    29.                        
    30.  
    31.                 }
    32.                 private function progresshandler(event:ProgressEvent):void
    33.                 {
    34.                         var mPercent:Number =int( event.bytesLoaded/event.bytesTotal*100.0);
    35.  
    36.                         trace(mPercent);                // 로드 되는 과정을 알수 있다.
    37.                 }
    38.  
    39.                
    40.         }
    41.        
    42. }

     

    위의 completehandler 함수에서는 event.target.content 로 정보를 받은 뒤 변경을 해 주게 되고 progresshandler 에서는 byteLoaded 를 이용해서 실시간 로드된 값을 알수 있습니다. 이것을 이용해서 로딩 바를 만들수 있습니다.  앞으로 만들어 볼것의 기본이 되는 두 클래스를 설명해 보았습니다. 잘 이해 안되는 부분은 질문 날려 주시고요 . 잘못된 부분이나 추가 내용은 댓글이나 답글 달아 주세요. 이 공간의 저 만의 강좌 공간이 아니라, 강좌라는 주제에 대해 토의하는 공간입니다. 쑥스러워 하지 마시고, 참여 부탁드립니다. 그럼 두 클래스를 이용한 간단한 해보기 입니다.  

    1. 5장의 이미지를 준비

    2. 배열에 5장의 이미지를 저장

    3. Timer class 를 이용해 2초에 한번씩 로드 되는 겔러리를 만든다.   

    겔러리를 만들면서 Ctrl + Alt + del 을 눌러 메모리가 늘어 나는 상황을 관찰해 봅시다! 기초 스터디 팀에게는 미리 낸 해보기라, 미리 올라온 소스를 참고해 보시는것도 좋을듯 합니다. 다하신 분들은 꼭 메모리가 늘어 나는 상황을 관찰해 보시기 바람니다.   

    수고 하셨습니다. 기분좋은 한주 시작 하세요!

     

    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 01:32

    자주 올린다고 했는데, 속도가 더디네요.ㅋㅋ 졸업 시즌이다 보니 친구들 졸업식에 갔다 오게 되고, 오늘은 친형 졸업식에 갔다 왔담니다;; 크헐...... 날씨도 많이 풀리고, 학기가 시작한다고 생각하니;; 머리에 쥐가 날꺼 같은;; 으악!!!!!  

    오늘은 기초스터디를 하고 있는 것과 이어서 " 사용자 정의 클래스 " 에 대해 간단히 하는 방법을 알아 보고

    "내가 만든 클래스를 사용한다" 라는 주제로 시작해 보겠습니다.   

    우선 5강 동적 생성 부분에서 Linkage 로 객체를 정의 해서 Linkage Properties 창에서  Class 에 이름을 입력을 하는것으로 내가 스테이지에 그린 객체가 클래스로 정의 된다는 것을 알았습니다 

    (잘 기억 안나시면 http://cafe.naver.com/flashactionscript/12025 되돌아 가보시는것도 좋습니다 )  

    그럼 내가 클래스를 만들었는데, 그 클래스의 속성을 지정할수 없는가? 이 객체에 속성을 추가해 보고 싶다. 어떻게 해야 될까요?

    단순 Frame 액션에서는 어떻게 하는지 감이 오셨을 것입니다. 제가 말하고 있는 건 Linkage 로 Circle 이라는 클래스를 만들었을때, 이 객체를 어떻게 사용하는지는 알겠는데, 속성을 어떻게 추가 할것인가 하는 것입니다.

    어떻게 하시겠어요? Frame 액션에서는 이렇게 해 왔습니다.

     

     // circle frame 액션으로 적용
    1. var cir:Circle = new Circle();
    2. cir.x = 100;
    3. cir.y = 100;
    4. cir.alpha = 0.8;
    5. cir.width = 200;
    6. cir.height = 100;
    7. addChild(cir);
    8.  
    9. // 마우스 이벤트를 추가 하려면
    10. cir.addEventListener(MouseEvent.CLICK, fcirdownhandler);
    11.  
    12. function fcirdownhandler(event:MouseEvent):void
    13. {
    14.         trace("마우스 다운이랑께");
    15.        
    16.        
    17. }

     

    지금부터 사용하고자 하는 사용자 정의 클래스는 위의 액션과 똑같은 작용을 합니다. 그런데 구지 클래스로 만들어서 사용하려고 하는가? 우선은 습관이라고 말해 드리고 싶습니다. 단순 100줄도 안되는 액션 코드에서는 자신이 알아 볼수 있다면 frame 액션에 때려 박고, 사용하셔도 상관없습니다. 하지만 코드가 500~ 1000줄 10000줄까지 가면 어떻게 하시겠어요? Ctrl + F 조낸 눌러 가면서 일일이 변수명 확인해서 사용하는게 좋을까요 ? 아님 클래스를 따로 만들어서 관리 하시는게  좋으시겠어요? 선택은 자유지만, 전 필수라고 생각이 됩니다. 그 밖에도 무궁 무진한 장점들이 있으니 절 믿고 따라와 보세욜.

    이제 클래스 파일을 만들어 보겠습니다.

    메뉴의 File - New - Actionscript File 을 클릭 하세요.

    우선은 클래스를 만들기 위한 기본 구조 부터 익히겠습니다.

     
    1. package {
    2.        
    3.         import flash.display.MovieClip;
    4.         /* import 를 정의하는 부분 입니다.
    5.         import 란 이 package 안에서 사용되어질 다른 클래스들을 불러 오기 위한 부분입니다
    6.         C 에서는 include 라고 생각하시면 되겠고 자바랑은 똑같습니다.
    7.         보통 Flash fla 파일에서는 무비 클립과 같은 클래스들은 import 를 하지 않아도 사용이 가능하지만
    8.         여기에서는 import 를 해야 사용이 가능합니다. 아무 것도 없는 상태에서 하나하나 불러서 써야
    9.         사용할수 있는 것입니다
    10.         */
    11.        
    12.         public class Circle extends MovieClip{
    13. extends MovieClip 을 왜 해주는가? 구지 MovieClip 으로 안하고 Sprite로
    14. 하는 방법도 있지만 우선은 우리가 정의한 것이 MovieClip 이니 MovieClip
    15. 을 상속받아야 정의가 가능합니다.
    16.        
    17.                 // 클래스의 메인이 되는 부분 전역 변수를 여기에 선언합니다.
    18.                 public function Circle():void
    19.                 {
    20.                         /*
    21.                         클래스의 생성자 라는 부분입니다. 함수이름은 클래스 이름과 동일하게 작성해야
    22.                         이 해당 클래스의 생성자로 적용이 되게됩니다. 생성자란 무엇인가?
    23.                         사용자가 Circle 이라는 클래스를 만들었을때 바로 호출되는 부분입니다. 이 생성자에서
    24.                         이 클래스의 속성을 지정할수 있고, 처음으로 해야 되는 부분을 모두 여기에서
    25.                         정의하고 사용하게 됩니다
    26.                         */
    27.                          
    28.                         trace("생성");
    29.                        
    30.                 }
    31.                
    32.                
    33.         }
    34.        
    35.        
    36. }

     

    그리고 클래스 파일명은 Document 파일및 fla파일을 저장한 같은 폴더 안에 클래스 이름과 같은 이름으로 저장합니다

    (여기 에서는 Circle.as 입니다) 

    그리고 전 시간에 만들어보았던 Document 클래스를 fla 파일에 연결 시켜 봅시다.

     
    1. package {
    2.        
    3.         import flash.display.MovieClip;
    4.                
    5.         public class CustomMain extends MovieClip
    6.         {
    7.        
    8.                 public function CustomMain():void
    9.                 {
    10.                         var cir:Circle = new Circle();
    11.                         addChild(cir);
    12.                        
    13.                 }
    14.                
    15.                
    16.         }
    17.        
    18.        
    19. }

     

    // output

    생성  

    그동안 Document 클래스 사용법은 숙지 하셨지요? 기억 안나시면 6강으로...................
    그럼 위의 frame 액션으로 추가 시켜 줬던 Circle 에 대한 속성은 어떻게 정의해 줄까요?? 아주 간단합니다.

     
    1. package {
    2.  
    3.         import flash.display.MovieClip;
    4.         import flash.events.MouseEvent;
    5.         public class Circle extends MovieClip {
    6.  
    7.                 public function Circle():void {
    8.                         trace("생성");
    9.                         this.x = 100;
    10.                         this.y = 100;
    11.                         this.alpha = 0.8;
    12.                         this.width = 200;
    13.                         this.height = 100;
    14.  
    15.                         this.addEventListener(MouseEvent.CLICK, fcirdownhandler);
    16.  
    17.  
    18.                 }
    19.                 public function fcirdownhandler(event:MouseEvent):void {
    20.                         trace("마우스 다운이랑께");
    21.  
    22.                 }
    23.         }
    24. }

     

    여기서 this 란 Circle 이란 클래스 자기 자신의 의미 합니다. 그러니 자기 자신에게 속성을 추가해 주는것이지요. 정말 간단하죠? 지금까지 as 파일 2 개 fla 파일 1개가 생성되었습니다.  function 앞에 public 이나 private 로 정의를 하고 있는데, 우선은 모두 public 으로 해도 무방합니다. 클래스의 개념을 좀더 추가해 주면서 설명하도록 하겠습니다.   

    어찌 파일이 좀 깔끔해 졌다 라는 것을 느끼고 계신가요??  이것으로 [Base 강좌] 에서 이론에 대한 부분중 큰 가닥은 잡은것 같습니다.  늘 하는 얘기지만 어렵다고 생각하시는 분들이 많으실꺼라 봄니다. 하지만 이게 3.0 의 아주아주아주 기초중에 기초 라는 점을 알아 두셨으면 좋겠습니다. 앞으로 엄청난 기능을 자랑하는 내장 클래스들과, 우수한 개발자들이 만들어 놓은 클래스를 활용할 수 있게 되기 위해서는 아직 갈길이 많이 남아 있습니다. 기초 부터 탄탄히 라고, 하나하나 스텝을 밟아 가시기 바람니다.   

    앞으로는 실습을 중심으로 이론을 추가해 나아가면서 Base에 살을 붙여 나가도록 하겠습니다. 수고 하셨습니다.

    다음 강에 뵙겠습니다. 안뇽~ 

     

    역시 틀린 부분이나 질문 거침없는 답글 댓글 부탁드립니다. (해보기는 없습니다;;;;;  아싸! ) 



    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 01:30

    안녕하세요 "동강" 입니다. 저번 시간에 이어서 Class 의 대한 이야기를 계속 해나갈까 합니다. 앞으로의 강좌에서는 frame 액션의 사용을 최대한 버리고, 오직 Class 상에서의 액션으로 진행하겠습니다. 우선 Class 에 대해 다시 한번 알아 보도록 합니다. 클래스를 알기 위해서는 우선 객체 지향 프로그래밍 부터 알아야 합니다.  

    0. Class 와 객체 지향 프로그래밍  

    그럼 객체 지향 프로그래밍은 무엇일까요? 흔히 OOP 라고 알고 있는 객체 지향 프로 그래밍은 말 그대로 객체 하나하나를 존중해서 프로그래밍 한다는 의미 입니다.  

    예) 자전거를 예로 들면, 움직이는 자전거를 프로그래밍 한다고 생각해 봅시다. 우선 자전거를 기능 별로 나눠 보면 앞바퀴 부분, 뒷바퀴 부분, 페달 부분, 그리고 몸체 부분으로 나눌수 있습니다. 이것들 하나하나가 다 클래스가 되는 것이지요. 각각의 클래스들의 서로의 연관 관계는 나중에 생각하기로 하고, 앞바퀴 클래스의 안을 들여다 보면 그 안에는 기어가 있고, 바퀴 타이어가 있고, 바람 넣는 구멍도 있고, 여러 가지 클래스 안의 구성물들이 존재 합니다. 이 구성물들은 자신의 부모 클래스의 지시에 따라 움직이게 됩니다. 

    이때, 페달을 밟고 있는 사용자는 바퀴의 기어 부분에서 무슨일이 일어 나고 있다는것을 모두 신경쓰고 있어야 될까요??    아님니다. 사용자는 오직 페달 부분에만 신경 쓸뿐 바퀴가 돌아 가는건 신경을 쓰지 않아도 됩니다. 바퀴는 페달이 관장을 하겠지요. 객체 지향이 뭔지 감이 좀 오시나요? 이 객체 지향 프로그래밍 방법론(OOP)으로 구성되어 있는것이 Actionscript 자체 입니다.

    ( "대충 설명 하고서 먼 감이 오냐" 라는 분들을 위해 자료를 첨부하겠습니다 ;;; )

    여기에서 우리가 곡 알고 넘어가야 할 부분은  객체지향 프로그래밍( 앞으로는 OOP 라 하겠습니다 )의 특징중 상속이란 개념입니다. 상속은 무엇일까요? 앞에 강에서 언급했던 것이 이어서 말하겠습니다 ( 2~4강을 참고 하세요 ) Actionscript는 객체 지향 자체의 언어 입니다. 우리가 지금 까지 썼던 MovieClip 도 Flash 안에서 정의 되어 있는 내장 클래스 입니다   

    MovieClip 

    MovieClip  Sprite  DisplayObjectContainer  InteractiveObject  DisplayObject  EventDispatcher  Object 

    Object 에서 시작하여 살을 붙이고 붙여 MovieClip 이 탄생하게 되는 것이지요. 그럼 Object 는 뭐냐? Object 는 아무 것도 없는 하나의 공간 입니다. 여기에는 무엇이든 넣을수 있고, 어떤 한 물건을 넣어서 한종류의 어느 무엇으로도 사용될수 있습니다. (배열같이 사용될수도 있고, 그냥 무비 클립으로도 사용될수도 있다는 뜻입니다) 대략 적으로 위의 상속 구조를 언급한다면, Object 의 빈 공간에서 시작하여

    1. EventDispatcher 에서 Event 를 가질수 있는 구조를 상속 받는다.
    ( MovieClip 의 addEventListener 는 괜히 가지고 있는게 아니겠지요? 여기에서 상속 받은 것입니다.)
    2. DisplayObject 에서 화면에 보일수 있는 객체로 정의 되어 진다.
    3. InteractionObject 에서 마우스와 키보드와 상호 작용할수 있는 속성을 상속 받는다.
    4. DisplayObjectContainer 에서 무엇인가 담을수 있는 그릇으로 진화 한다.
    5. 기본 표시 목록을 구성하는 단위로 그패릭을 표시할수 있고, 자식도 포함할수 있는 Sprite 가 만들어 지게 된다.
    6. 타임라인이 추가 되어 MovieClip 이 완성 된다.  

    Object 는 무한한 공간이지만 속성이 없습니다.
    MovieClip 은 무한한 공간은 아니지만 속성이 많습니다. ( 상속을 통한 속성 추가 )
    이제 이러한 것들이 어떻게 사용되는 가를 보겠습니다.  

    - Document Class 로의 진화 

    CS 3 들어 와서 가장 큰 변화의 하나는 Document Class 로 정의 되는 fla 파일의 main 클래스 부분 입니다. Document class 는 그 자체로 fla 의 타임라인이라고 생각하시면 됩니다. fla 파일의 라이브러리 및 stage 에 있는 모든 객체들의 접근이 가능하고, 타임라인에서 조정했던것과 마찬가지로 객체들을 바로 바로 움직일수 있습니다.  


    main 이라 써 있는 저 부분에 지정을 하여 사용합니다. (위의 M 자를 m 으로 바꾸세요;; ) 그리고 stage 위에 무비 클립을 만들고 이름을 지정해 보세요. 여기서는 circle_mc 로 하겠습니다. 이제 main class 파일을 만듬니다. File - > New -> ActionScript File  기본 문법이기 따라서 타이핑 하세요. 

    // main.as

     
    1. package {
    2.        
    3.         import flash.display.MovieClip;
    4.        
    5.         public class main extends MovieClip
    6.         {
    7.  
    8.                 private var text:Number;
    9.              
    10.                 public function main():void
    11.                 {
    12.                         trace(circle_mc);
    13.                        
    14.                 }
    15.                
    16.         }
    17.        
    18. }
    19.  

     그리고 main.as 와 fla 파일을 같은 폴더에 저장합니다. 실행해 보세요.
    // output
    [object MovieClip]  

    접근이 되나요?
    main.as 에 대해 설명 하면 class 는 생성자와 class 인스턴스 그리고 인스턴스 함수로 이루어 짐니다.

    위에서

    1.   public function main():void
    2.                 {
    3.                         trace(circle_mc);
    4.                        
    5.                 }

    이 부분이 생성자 Class 가 생성되어 질때 실행 되는 부분입니다. 여기에서는 fla 파일이 실행 되자 바자 이 함수가 호출되어 실행 되어 집니다.  

     private var text:Number;  

    이 부분이 Class 인스턴스를 선언하는 부분입니다. 걍 쓰일 변수를 여기에 선언한다고 생각하면 됩니다. 이제 circle_mc 에 간단한 마우스 이벤트를 추가해 보겠습니다. 

     
    1. package {
    2.        
    3.         import flash.display.MovieClip;
    4.         import flash.events.MouseEvent;
    5.        
    6.         public class main extends MovieClip
    7.         {
    8.                
    9.                 public function main():void
    10.                 {
    11.                         trace(circle_mc);
    12.                        
    13.                         circle_mc.addEventListener(MouseEvent.MOUSE_OVER, fcircleOver);
    14.                        
    15.                 }
    16.                 private function fcircleOver(e:MouseEvent):void
    17.                 {
    18.                         trace("마우스 오버");
    19.                        
    20.                 }
    21.                
    22.         }
    23.        
    24. }
    25.  

    바뀐점은 import flash.events.MouseEvent; 입니다. fla 와 다르게 class 파일에서는 내장함수를 직접 불러 올수 없습니다 .( 참고로 fla 에서도 자주 쓰는 class 만 fla 파일 만들때 불러와 지는 것으로 보입니다 ) 그래서 import 문으로 그 class 를 불러 오는 것이지요. 멀 불러 오는지 어떻게 아느냐? 저 같은 경우는 F1 의 예제를 참고해서 import 합니다. 

    잘 되나요??  

    구지 어려운 개념인 Document class 로 작업을 하자고 한건, frame 액션으로 막코딩을 하다 보면 잘못된 습관이 들수도 있다는 생각이 들어서 입니다. 저도 frame 액션으로 시작해서 막코딩에서 Document 로 넘어 올때 편한 frame 액션만 찾다 보니 점점 코드가 엉망이 되더군요. 위에 있는 기본 뼈대만 잘 알아 놓으신다면 frame 액션 보다 휠씬더 효율 적이라는 것을 금방 느끼실수 있을것 입니다. frame 액션보다 class 액션이 좋은 몇가지만 말씀 드리자면, 

    1. 유지 보수가 쉽다.

    2. 코드가 알아 보기 쉽다.

    3. 객체 지향 프로그래밍으로 발전 하기 위해서는 꼭 필요한 요소 이다.  

    입니다. 갑자기 어려워 져서 당황하는 분들이 많이 있으실것 같습니다. 어렵다고 포기 하지 마시고, 천천히 따라해 보세요. 잘 안되는 부분은 바로 질문 올려 주시고요.
    그럼 4강에서 했던 예제 파일을 Document class 형식으로 바꿔보는 것으로 이번 강을 마치겠습니다.

     

     
    1. package {
    2.  
    3.         import flash.display.MovieClip;
    4.         import flash.events.MouseEvent;
    5.         import fl.transitions.easing.*;
    6.         import fl.transitions.Tween;
    7.  
    8.  
    9.         public class main extends MovieClip {
    10.  
    11.                 public function main():void {
    12.  
    13.                         for (var i:int = 0; i < 50; i++) {
    14.                                 var cir:Circle = new Circle();
    15.                                 cir.x = Math.random() * 550;
    16.                                 cir.y = Math.random() * 400;
    17.                                 addChild(cir);
    18.                         }
    19.                         addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler);
    20.  
    21.  
    22.                 }
    23.                 function mouseOverhandler(event:MouseEvent):void {
    24.                         var targetX = Math.random() * 550;
    25.                         var targetY = Math.random() * 400;
    26.                         new Tween(event.target,"x",Strong.easeOut,event.target.x,targetX, 30,false);
    27.                         new Tween(event.target,"y",Strong.easeOut,event.target.y,targetY, 30,false);
    28.  
    29.  
    30.                 }
    31.         }
    32. }

     한번 해 읽어 보기 : 객체 지향 프로그래밍 , 상속 개념
    과제는 자신이 지금까지 frame 액션으로 작성하시던 예제 하나를 Document class 형식으로 바꿔서 제출 하셨으면 합니다.   

    수고 하셨습니다. 다음강에는 개념보다는 실습으로 이뤄지도록 하겠습니다. ( 개념이 어렵네요;;; )



    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 00:53

    지난 강에서 DisplayObject 의 개념에 대해 잠깐 언급하였습니다. 그때 클래스 다이어 그램은 기억이 나시는지요? ( 4강참고) 그 다이어 그램과 같이 Flash 에 존재 하는 모든 객체속성( class ) 들은 상속에 상속을 거쳐서 자신의 속성을 만들게 됩니다.  

    예를 들어 F1 을 눌러 봅시다.

     

     

    MovieClip

    패         키지 :loadClassListFrame('class-list.html')" href="file:///C:/Documents%20and%20Settings/All%20Users/Application%20Data/Adobe/Flash%20CS3/en/Configuration/HelpPanel/Help/ActionScriptLangRefV3/flash/display/package-detail.html">flash.display
    클래스 public dynamic class MovieClip
    상속 MovieClip  Sprite  DisplayObjectContainer  InteractiveObject  DisplayObject  EventDispatcher  Object

    모든 클래스의 최상위인 Object 에서 DisplayObject Sprite 를 거쳐서 MovieClip 이 만들어 짐니다. 이게 바로 상속관계지요

    그러면 1) 상속되면 머가 좋은거냐??  2) 왜 상속 되는 거냐??  

    1) 상속되면 하위 클래스에서 상위 클래스의 속성을 그대로 가져다 쓸수 있기 때문에 속성을 재 정의할 필요가 없습니다.

    단적인 예를들면 MovieClip 은 Sprite 를 상속 받는데 이 Sprite 속성은 F1 을 보시면 알겠지만 MovieClip 에서 타임라인이 없는 Class 라고 보시면 됩니다. 따라서 MovieClip 에서 사용가능한 gotoAndPlay, gotoAndStop 속성을 사용할수가 없습니다.  

    2) 왜 상속되는거냐? class 에 대해 확실하게 이해 하고 있지는 않지만, 제 의견은 이렇습니다. 있던 속성을 갔다 쓰면 되지 또 만들 필요가 있는가? 라는 생각입니다. 자세한건 객체 지향 프로그램 관련 서적을 참고 하세요.  

    위와 같이 우리가 가장 많이 쓰고 있는 MovieClip 은 이렇게 만들어 지는 것입니다. 상속에 개념은 여기 까지 하고 이제 DisplayObject 와 DisplayObejectContainer 개념을 적용해 보겠습니다.

    우선 fla action 창에
    trace(root, stage); 
    를 찍어 봅시다.
    // output
    [object MainTimeline] [object Stage]

    그리고
    var mc:MovieClip = new MovieClip();
    trace(mc); 
    // output
    [object MovieClip] 

    여기서 말하는 stage 는 위에서 output 으로 나온것과 같이 object Stage 타입의 하나의 객체 입니다.
    보이는 화면이라고 해서 객체가 아닌것이 아니라 그 화면 자체도 객체인 것입니다.
    단적인 예를 들어 지구 = stage , 사람 = MovieClip 이라 볼수 있습니다.


    위와 같은 계층도로 되어 있습니다. 복잡하니깐 여기에선 Stage 와 Main 부분만 보도록 하겠습니다. 

    trace(stage.root);
    trace(this.parent);
    trace(stage.getChildAt(0));

    trace(stage.getChildAt(0).root);
    trace(stage.getChildAt(0).parent);

    (getChildAt 은 (안) 안에 있는 숫자의 뎁스로 접근하여 그 뎁스에 있는 객체를 반환 합니다. 

    // output

    [object Stage]
    [object Stage]
    [object MainTimeline]
    [object MainTimeline]
    [object Stage] 

    parent 는 객체.parent  ==> 객체의 부모에 접근한다는 말 입니다. 여기서 유심이 볼 부분은 빨간색 입니다. stage 에 0 뎁스에 있는 것은 MainTimeline 이다. stage 가 시작 부터 가지고 있는 객체 이지요 ( 그냥 첫 화면에서 보는 타임 라인 이라고 생각하시면 됩니다 ) 이렇게 stage 는 담을 공간을 마련해 주고, 우리는 그 위에 무비클립을 생성하여 사용하는 것이지요. 어려운 개념이니 어렵다고 대충 넘어 가지 마시고 찬찬히 trace 찍어 보시기 바람니다.

     

    자 이제 stage 에 마우스 클릭으로 무비 클립을 만들어 circle_mc 를 만들어 봅시다.
    action 창에는 ( 앞으로 action 이라고만 쓰겠습니다 )  

    removeChild(circle_mc);
    trace(circle_mc); 

    짠! 어디로 갔을까요??  화면에서는 사라졌지만 아직도 trace 문에서는 찍히고 있는 것을 알수 있습니다. 이 말은 뭘 의미하는 것일까요?

    화면에서 사라졌다고 해서 메모리에서도 지워진 건 아님니다.
    장난 하냐 ? 그럼 어떻게 지워야 다 지워지는 거냐?   

    removeChild(circle_mc);
    trace(circle_mc);
    circle_mc = null;
    trace(circle_mc);  

    // output
    [object MovieClip]
    null  

    null 값을 넣어 줘야 지워 지게 됩니다. ( 어렵게 말하면 플레시에는 가비지 콜렉션이라는 쓰레기 값들을 ( 메모리에서 필요하지 않은 부분 ) 을 수집하는 장치가 있습니다. 그 수집 장치의 수집되는 후보가 되는 것이지요 ) 이 개념은 단순 코딩할때는 그냥 지나치는 부분 이지만 Loader class 나 URLLoader

    로 파일을 불러 들일 때는 광장히 중요하게 작용하는 부분입니다. 예를 들어 Loader 로 이미지를 주기적으로 10개씩 로드 한다고 생각하면 removeChild 와 null 값으로 이미 지나간 이미지를 지워주지 않는다면 메모리는 점점 쌓이게 되어 컴퓨터 다운!!! 의 결과를 볼수 있으실 것입니다.  

    지워주는건 이제 어떻게 하는지 알았고, 같은 무비 클립을 어떻게 동적으로 생성 할거냐? 가 문제 인데 2.0 에서는 duplicateMovieClip 나 attachMovie 을 사용하였지만, 3.0 으로 오면서 모두 사라졌습니다. 대신에 좀더 강력한 세부적으로 작용하는 addChild 나왔습니다.
    우선 아까 소스에서

    removeChild(circle_mc);
    trace(circle_mc);
    addChild(circle_mc); 

    다시 원이 나타남니다. 그럼  


    removeChild(circle_mc);
    trace(circle_mc);
    circle_mc = null;
    addChild(circle_mc);
    // output
    [object MovieClip]
    TypeError: Error #2007: 매개 변수 child은(는) null이 아니어야 합니다.
     at flash.display::DisplayObjectContainer/addChild()
     at Untitled_fla::MainTimeline/frame1()

    이미 참조 할수 없게 되어 버렸다는 에러가 나오네요.


    addChild removeChild 를 알았다고 해서 동적 생성을 할수 있는건 아님니다. 이제 부터 중요한 라이브러리에 있는 무비클립을 Linkage 하는 절차에 대해 알아 보겠습니다. 우선 아까 것에 이어서 circle_mc 를 stage 에서 지워 버림니다. 그리고 라이브러리에 등록되어 있는 무비클립 위에서 마우스 우클릭을 합니다.

    Linkage 에 Export for Actionscript 를 클릭하면 아래와 같이 바뀌게 됩니다. Class 명에는 자신이 지정하고 싶은 이름을 쓰면 됨니다 여기서는 Circle 로 하겠습니다.



    이제 준비가 끝났습니다. 이제 addChild 해 볼까요?

    var cir:Circle = new Circle();       // 방금전 Circle 이라는 Class 를 생성하였습니다. 이제 그

    addChild(cir);                                 클래스를 이용하는 것이지요.  

    짠! 붙었습니다. 부모인 stage 에 자식인 cir 을 addChild 했습니다. stage.addChild(cir); 도 같은
    의미 입니다. (stage 상에서만 )

    변수를 생성하는 방법은

    var 이름:클래스명 = new 클래스명();  

    본래 검은색으로 써있는 클래스명은 인터페이스 명이라고 해야 되는게 맞지만 그냥 넘어 가겠습니다.( 인터 페이스는 아주 나중에...)  

    이제 이걸 이용하여 좀더 재미난걸 만들어 보겠습니다.   

     
    1. import fl.transitions.easing.*;
    2. import fl.transitions.Tween;
    3.  
    4. for(var i:int = 0; i < 50; i++)
    5. {
    6.         var cir:Circle = new Circle();
    7.         cir.x = Math.random() * 550;
    8.         cir.y = Math.random() * 400;
    9.         addChild(cir);
    10. }
    11.  
    12. addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler);
    13.  
    14. function mouseOverhandler(event:MouseEvent):void
    15. {
    16.         var targetX = Math.random() * 550;
    17.         var targetY = Math.random() * 400;
    18.         new Tween(event.target,"x",Strong.easeOut,event.target.x,targetX, 30,false);
    19.         new Tween(event.target,"y",Strong.easeOut,event.target.y,targetY, 30,false);
    20.        
    21.        
    22. }

    만들어 보시면 알겠지만 여기서 Tween 클래스의 치명적인 버그가 존재(?) 한다는 걸 알수 있습니다.
    움직이다 멈춰 버리지요..ㅋㅋㅋ 그래서 ENTER_FRAME 을 돌리던가 google Tweener 를 쓰곤 한담니다. 한번 영역 밖으로 나가지 않게 소스를 수정해 보세요.
    Math.random() 함수는 뒤에 오는 인자 값으로 랜덤한 값을 반환해 줍니다.
    예)
    Math.random() * 10; 
    0~ 10 까지 숫자중 하나는 반환해 줌.  

    이제 클래스 개념이 본격적으로 시작 되었슴니다. 다음 강 부터는 Frame 액션에서 벗어나 class 액션으로의 업그래이드를 해 보겠습니다.  

    역시나 잘못된 점이나 질문들을 거침없는 댓글 부탁드리고요.



    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 00:45

    자 오랜만에 공부를 시작하겠습니다. 이것 저것 참고하면서 쓰니 덩달아 잘 이해가 안되었던 부분까지 이해가 되니 기분이 좋습니다. ㅎㅎ 정작 보는 사람은 이해 못하고 있는데 나만이해 되는건 아닌지;;;; ;후덜덜 지난 시간에 ENTER_FRAME 을 이용해서 노가다로 객체의 크기를 변화 시켜 보았는데 먼저 그 코드의 길이를 줄이겠습니다.  

    Tween 
    패키지 fl.transitions
    클래스 public class Tween
    상속 Tween  EventDispatcher  Object  
    Tween 클래스는 Flash 에서 객체의 움직임을 조절할수 있도록 정의해놓은 내장 class 입니다.
    사용방법은 아래와 같습니다.  

    import fl.transitions.Tween;
    import fl.transitions.easing.*;
    var myTween:Tween = new Tween(myObject, "x", Elastic.easeOut, 0, 300, 3, true);

    import 는 사용자 정의 class 나 flash 에서 사용되는 내장 class 를 불러올때 쓰입니다.
    1)  import 패키지이름.클래스이름;
    2_  import 패키지이름.*; 

    * 는 패키지 안에 있는 모든 class 를 불러 올때 쓰입니다.  

    Tween(obj:Object, prop:String, func:Function, begin:Number, finish:Number, duration:Number, useSeconds:Boolean = false)
    Tween(객체:Object, 변화시킬속성:String, 변화스타일:Function, 시작위치:Number, 끝위치:Number, 변화시간:Number, useSeconds:Boolean = false)
    우선 stage 에 import 를 시킨뒤 my_mc 라는 무비클립을 만드세요 여기서는 Tween 이름을 myTween으로 하겠습니다.   

     
    1. import fl.transitions.Tween;
    2. import fl.transitions.easing.*;
    3.  
    4. var myTween:Tween = new Tween(my_mc, "x", Elastic.easeOut, 100, 300, 1, true);
    5.  

     어떻게 되나요? 움직임을 자세히 보기 위해 마우스 이벤트를 넣어 보겠습니다

     
    1. import fl.transitions.Tween;
    2. import fl.transitions.easing.*;
    3.  
    4. my_mc.addEventListener(MouseEvent.MOUSE_OVER, myOverhandler);
    5. function myOverhandler(event:MouseEvent):void
    6. {
    7.         var myTween:Tween = new Tween(my_mc, "x", Elastic.easeOut, 100, 300, 1, true);
    8.        
    9. }
    10.  
    11. my_mc.addEventListener(MouseEvent.MOUSE_OUT, myOuthandler);
    12. function myOuthandler(event:MouseEvent):void
    13. {
    14.        
    15.         var myTween:Tween = new Tween(my_mc, "x", Elastic.easeOut, 300, 100, 1, true);
    16.  
    17.  
    18. }

     여기서는 "x" 속성을 바뀌었지만 여기에 들어 갈수 있는 속성은 MovieClip 이나 Sprite 등 이 가지고 있는 모든(?) 속성이 들어 갈수 있습니다. 그럼 크기를 바꾸려면 어떻게 해야 될까요? "scaleX" 와 "scaleY" 를 동시에 바꿔주어야 합니다. Elastic.easeOut 이라는 변화 속성을 넣어 줬는데, 이것 외에도 여러가지가 있습니다

    Elastic.easeOut, easeIn, easeInOut
    Bounce.easeOut, easeIn, easeInOut
    None.easeOut, easeIn, easeInOut
    Strong.easeOut, easeIn, easeInOut

    등등 한번식 사용해 보세요. 은근 Tween 클래스를 가지고 노는건 재미 있답니다.  

    그럼 저번시간에 했던 것을 바꿔보겠습니다.

     
    1. import fl.transitions.Tween;
    2. import fl.transitions.easing.*;
    3.  
    4. var ori_W = my_mc.width
    5. var ori_H = my_mc.height            // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 my_mc 의 값을 저장
    6. var targetW = 120;
    7. var targetH = 120;
    8. //var bo:Boolean = false;
    9. addEventListener(MouseEvent.MOUSE_OVER, Overhandler);  
    10. addEventListener(MouseEvent.MOUSE_OUT, Outhandler);    
    11. var myTween:Tween;
    12. function Overhandler(event:MouseEvent):void
    13. {
    14.         myTween = new Tween(my_mc, "width", Elastic.easeOut, ori_W, targetW, 1, true);
    15.         myTween = new Tween(my_mc, "height", Elastic.easeOut, ori_H, targetW, 1, true);
    16.    
    17. }
    18. function Outhandler(event:MouseEvent):void
    19. {
    20.         myTween = new Tween(my_mc, "width", Elastic.easeOut,targetW ,ori_W,1, true);
    21.         myTween = new Tween(my_mc, "height", Elastic.easeOut,targetW, ori_H,1, true);
    22.  
    23. }

     어떤가요? 저는 Tween 을 알게 되었을때 ENTER_FRAME 으로 왜 노가다를 했을까 하고 한탄을 했었는데, 이 Tween 클래스 는 잘만 사용하면 정말 편리하고 강력하게 사용됩니다. 그밖에 가지고 있는 속성들은 후에 다루도록 하겠습니다.  

    DisplayObject
    DisplayObjectContainer

    도대체 이놈들은 뭐냐?  

    나열되는객체
    나열되는 객체 그릇 

    한글로 써진 그대로 입니다. stage 에 올려진 것들은 모두 DisplayObject 이고 그 중에서는 DisplayObjectContainer 기능을 하는것도 있습니다. 쉽게 말하면(?) , 바구니는 그 자체로 하나의 객체가 될수 있지만 그안에 다른 물체들을 담을수도 있지요. 이 바구니가 DisplayObjectContainer 입니다. 이게 왜 중요한가?  

    DisplayObject

    패키지              :loadClassListFrame('class-list.html')" href="http://livedocs.adobe.com/flash/9.0_kr/ActionScriptLangRefV3/flash/display/package-detail.html">flash.display
    클래스 public class DisplayObject
    상속 DisplayObject EventDispatcher Object
    구현 IBitmapDrawable
    하위 클래스 AVM1Movie, Bitmap, InteractiveObject, MorphShape, Shape, StaticText, Video

     

    DisplayObjectContainer

    패키지            :loadClassListFrame('class-list.html')" href="http://livedocs.adobe.com/flash/9.0_kr/ActionScriptLangRefV3/flash/display/package-detail.html">flash.display
    클래스 public class DisplayObjectContainer
    상속 DisplayObjectContainer InteractiveObject DisplayObject EventDispatcher Object
    하위 클래스 Loader, Sprite, Stage

    위와 같이 DisplayObject 에서 시작하여 stage위에서 구현되는 객체들이 정의되게 됩니다. (상속관계를 잘 보세요) 그럼 상속은 뭔가? 신상품과 구상품의 예를 들어 보겠습니다. 구상품이 상위 클래스 이고, 신상품이 하위 클래스 입니다.  

    구상품이 출시되고 신상품이 출시 될때 신상품이 가지고 있는 기능은 무엇일까요? 구상품이 가지고 있는 기능들은 모두 가지고 있고 그 기능을 변화 시키던가, 새로운 기능을 추가 해 주어서 신상품이 만들어 지는 것입니다. 따라서 신상품은 구상품보다 덩치(가지고 있는 기능들) 가 더 커지게 되는 것이지요.

     이 관계는 우리가 지금까지 써 보았던 MovieClip 과 DisplayObject 와 의 관계라고 할수 있습니다. MovieClip 이 신상품이고 DisplayObject 가 구상품이지요. 

    상속관계를 더 살펴 보면 모든 클래스의 최상위 클래스인 Object 는 모든것을 쓸수 있는 전자 제품을 예로 들면 아무것도 추가 시키지 않은 기판이라 할수 있습니다. ( 여기서, 공대생 특징이 나오는군요;; )

    다현아빠 님의 글을 인용해 보겠습니다

     

    red : 추상화 클래스(3.0에서는 추상화 클래스가 없지만 추상화 계념의 기반클래스이다.

    물론 추상화이니 당연히 인스턴스도 생성을 해서는 안된다.)

    yellow : 생성제한(MorphShape/StaticText는 플래시 오서링툴로만 생성가능.

    AVM1Movie는 2.0이하 기반에서 제작한 swf 또는 심볼 객체이다.) 

    green : 동적으로 인스턴스 생성이 가능한 클래스 

    purple : 마커 인터페이스(마커 인터페이스에 대한 포스팅글 참조.)

    뭐야 왜이렇게 갑자기 어려워 진거냐, 이거 기초 강좌 아니었냐  

    어려워도 이것만은 꼭 알아 두고 넘어가야할 부분입니다. DisplayObject 야 말로 flash 의 핵심이고 flash 그 자체라고 해도 과언이 아닐 정도로 중요한 class 입니다. (위의 그림과 연관하여 ) http://livedocs.adobe.com/flash/9.0_kr/ActionScriptLangRefV3/flash/display/DisplayObject.html

     정독하면서 읽어 보세요. 무슨말인지 모르겠다고 해도, 다음 강에서는 예를 들어 이해 시켜 드리기 위해 노력하겠습니다. flash 에 이런 class 들이 있구나 참고 하시고 공부하시는것도 좋을것 같습니다.

     

    역시나 잘못된 부분이나 질문은 거침없이 댓글 날려 주세요.

     

    http://dongkang.ivyro.net/zbxe/?module=file&act=procFileDownload&file_srl=3846&sid=493dd3dea32e8baf0c73221c13a66134

    클래스 다이어그램 링크 입니다. 


    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 00:37

    1, 2 강에서 Event 중 마우스 이벤트와 ENTERFRAME 이벤트에 대해 잠깐 훑어 보았습니다. 이 두가지 이벤트는 Flash 에서 가장 많이 쓰이는 이벤트에 불과 하고요( 하지만 굉장히 중요한 이벤트들 입니다 ) 상상하지 못할 별에 별 신기한 이벤트 들이 Actionscript 3.0 에 존재 하고 있고, 사용자는 단지 이벤트의 전달 구조만 이해 한다면 손 쉽게 사용할수 있습니다.  

    시작에 앞서 사람들이 말하는 "F1 형님" 에 대해 알아 보겠습니다. F1 형님이란, Flash 에서 제공하는 도움말입니다. Actionscript 에서 제공하는 거의 모든 클래스를 포함하고 설명하고 예제로 사용법을 알려 주는 아주 편안한 도구 입니다.  

    사용법은 그냥 F1 키를 누르면 도움말 기본이 뜨고 위에 있는 검색 창에 모르는 클래스나 함수를 써주게 되면 도움말에 들어 있는 파일중에서 그 단어가 포함된 링크들을 찾아 줍니다. ( 실제로 이 도움말은 html 파일로 되어 있습니다 )  



    이건 단순한 사용법이고 좀더 효율적으로 해당 클래스를 찾으려면 아래 그림과 같이 문자열을 마우스로 드레그 하고 F1 을 누르면 해당 클래스나 메소드로 바로 이동하게 됩니다. ( 아래 그림에서는 MouseEvent ) 처음 시작할때 부터 F1 습관을 들여 놓는 것이, 실력이 쭉쭉쭉 향상 되는 지름길 입니다. 영어가 부담스러우신 분들은 CS3 한글판을 설치 하시던가,

      http://cafe.naver.com/flashactionscript/9310 

    이글을 참고 하세요.

    1. Event 이용하기

    지금까지 배웠던 3 가지 이벤트로 간단한 크기 변환 버튼을 만들어 보겠습니다. 우선 Stage 에 자신이 원하는 버튼의 모양을 3개를 만들어 주세요. ( 이름을 : bu_mc1, bu_mc2, bu_mc3 이라 하겠습니다.


    이름을 입력 하고 레이어를 추가한 후에 action 을 추가 하겠습니다. 

    1. bu_mc1.addEventListener(MouseEvent.MOUSE_OVER, Overhandler);
    2. bu_mc2.addEventListener(MouseEvent.MOUSE_OVER, Overhandler);
    3. bu_mc3.addEventListener(MouseEvent.MOUSE_OVER, Overhandler);
    4. bu_mc1.addEventListener(MouseEvent.MOUSE_OUT, Outhandler);
    5. bu_mc2.addEventListener(MouseEvent.MOUSE_OUT, Outhandler);
    6. bu_mc3.addEventListener(MouseEvent.MOUSE_OUT, Outhandler);
    7.  
    8. function Overhandler(event:MouseEvent):void
    9. {
    10.         trace("오버");
    11.  
    12. }
    13. function Outhandler(event:MouseEvent):void
    14. {
    15.         trace("아웃");
    16.  
    17. }

    다 타이핑 하기 지겨우시지요? for문을 이용해서 간략화 하겠습니다.

    1. for(var i:int= 1; i < 4; i++)
    2. {
    3.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OVER, Overhandler);        
      // bu_mc1 를 [] 를 통해 표현하는방법
    4.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OUT, Outhandler);      
      // addEventListener 사이에 .() 이없다는것 주의
    5.  
    6.                                                                                                                    
    7. }
    8.  
    9. function Overhandler(event:MouseEvent):void
    10. {
    11.  
    12.  trace("오버");
    13. }
    14. function Outhandler(event:MouseEvent):void
    15. {
    16.  trace("아웃");
    17.  
    18. }

    같은 기능을 수행 하지만 보기에 더 깔끔합니다. 그런데 6개의 Event 에 대해 작용하는 함수를 왜 두개 밖에 않만들었을까요? Actionscript 의 EventListener 는 함수를 이어 주는 역할만 하는게 아니라 이벤트가 발생한 객체와 이벤트를 전달할 객체 그리고 이벤트 자체에서 포함하고 있는 정보 들도 전달해 주는 기능을 합니다.

    1. event.target
    2.  
    3. function Overhandler(event:MouseEvent):void
    4. {
    5.    trace(event.target.name);
    6. }
    7. function Outhandler(event:MouseEvent):void
    8. {
    9.    traceevent.target.name);
    10.  
    11. }

    어떤 결과가 나올까요???? 직접 해 보시기 바랍니다. 위와 같이 event 는 정보 덩어리 입니다. ( 위에서는 무비 클립의 name 속성을 이용했습니다 ) name 속성 뿐만 아니라 event.target.x , event.target.width, event.target.alpha 등등.. 전달되는 객체가 가지고 있는 ( 여기서 전달 되는 객체는 bu_mc 들이고, bu_mc 들은 MovieClip 으로 정의 했다는 거 기억 하시지요? ) 속성들을 알아 볼수 있습니다. ( 엄격하게 따지면 달라지는 경우도 있지만 여기에서는 그냥 넘어 가겠습니다.) 소스를 보다 보면 event.target 이 아니라 event.currentTarget 으로 전달 받는 경우가 있는데, 잠깐 언급하고 지나가겠습니다.

    2. event.target , event.currentTarget 

     target <- 이벤트를 쏜놈 입니다. 보통은 EventDispatcher 이며 EventDispatcher를 상속받은 클래스. IEventDispatcher를 구현한 클래스만이 event.target 이 될 수 있습니다. currentTarget 은 보통은 화면에 출력되는 객체 입니다. DO와 DOC는 트리구조이죠. 간다한 예를 들어... 나무가 있습니다. 나무의 뿌리(target) 부분에 링겔(이벤트리스너)을 꼽습니다. 최초 뿌리 부분에서의 약물이 잎사귀 까지 가는 단계를 캡쳐 단계라 합니다. 약물이 잎사귀(타겟)에 도달한 후 다시 (약물을 전달한)수액은 뿌리로 돌아갑니다. 이것은 버블링 단계라 합니다. currentTarget 은 현재 (약물을 전달하는)수액이 어느지점에 있는가를 나타냅니다. - 퍼옴 

    한마디로 target 은 이벤트를 발생 시킨 객체고 currentTarget 은 이벤트가 발생하는 객체 입니다. 따라서 target 과 currentTarget 이 같은 경우도 있고 달라지는 경우도 있습니다. 두가지를 잘 구분해서 써야 원하는 코딩이 이루어 질수 있습니다. ( 저도 확실하게 이해 하고 있지 않은 부분이라 더 깊게 들어 가는건 조금 공부를 더 한후에 하겠습니다.. ㅜㅡ;; 곧 수정하겠습니다. (2008-12-11)  

    또 지겨운 이론을 이렇게 줄줄줄 늘어 놓았네요... 다시 돌아 와서 ..위와 같은 원리로 함수는 두개만 있어도 상관이 없다는 말을 하고 싶었습니다..   

    변수를 추가 해서 제일 상단에 처음 width 값과 height 값을 저장합니다.
    var ori_W = bu_mc1.width
    var ori_H = bu_mc1.height           
    // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 bu_mc1 의 값을 저장 
     

    그리고 변화 시키고 싶은 target 값을 지정하겠습니다.
    var targetX = 120;
    var targetY = 120; 
    1. var ori_W = bu_mc1.width
    2.  
    3. var ori_H = bu_mc1.height            // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 bu_mc1 의 값을 저장
    4.  
    5.  
    6.  
    7. var targetW = 120;
    8.  
    9. var targetH = 120;
    10.  
    11.  
    12.  
    13. for(var i:int= 1; i < 4; i++)
    14. {
    15.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OVER, Overhandler);         // bu_mc1 를 [] 를 통해 표현하는방법
    16.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OUT, Outhandler);       // addEventListener 사이에
    17.  
    18.                                                                                                                     .() 이없다는것 주의
    19. }
    20.  
    21. function Overhandler(event:MouseEvent):void
    22. {
    23.  
    24.      event.target.width = targetW;
    25.      event.target.height = targetH;
    26.  }
    27. function Outhandler(event:MouseEvent):void
    28. {
    29.    event.target.width = ori_W;
    30.      event.target.height = ori_H;
    31.  
    32.  
    33. }
      실행! 생각한 대로의 결과 인가요?
    1. 그럼 여기에 부드러운 크기 변화를 위한 ENTER_FRAME 이벤트를 적용해 보겠습니다. fpt 는 36으로 조절
      var ori_W = bu_mc1.width
    2. var ori_H = bu_mc1.height            // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 bu_mc1 의 값을 저장
    3. var targetW = 120;
    4. var targetH = 120;
    5. for(var i:int= 1; i < 4; i++)
    6. {
    7.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OVER, Overhandler);  
    8.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OUT, Outhandler);    
    9.                                                                                                      
    10. }
    11.  
    12. function Overhandler(event:MouseEvent):void
    13. {
    14.  
    15.    event.target.addEventListener(Event.ENTER_FRAME, enterframehandler);    
    16.    
    17. }
    18. function Outhandler(event:MouseEvent):void
    19. {
    20.    event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);    
    21.    
    22. }
    23. function enterframehandler(event:Event):void
    24. {
    25.  if(targetW > event.target.width){        // targetW 에서 정한 크기보다 작을때 까지 +3 씩 해 준다.
    26.   event.target.width += 3;                    
    27.   event.target.height += 3;
    28.  }
    29.  else                                              // 그 크기가 되면 이벤트 삭제
    30.   event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);
    31.  
    32.  
    33. }

    아놔...  왜 크게만 되고 작게는 안되요?


    1. var ori_W = bu_mc1.width
    2. var ori_H = bu_mc1.height            // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 bu_mc1 의 값을 저장
    3. var targetW = 120;
    4. var targetH = 120;
    5. for(var i:int= 1; i < 4; i++)
    6. {
    7.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OVER, Overhandler);  
    8.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OUT, Outhandler);    
    9.                                                                                                      
    10. }
    11.  
    12. function Overhandler(event:MouseEvent):void
    13. {
    14.  
    15.  event.target.addEventListener(Event.ENTER_FRAME, enterframehandler);    
    16.    
    17. }
    18. function Outhandler(event:MouseEvent):void
    19. {
    20.    event.target.addEventListener(Event.ENTER_FRAME, enterframehandler2);    
    21.    event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);    
    22.  
    23.    
    24. }
    25. function enterframehandler(event:Event):void
    26. {
    27.  if(targetW > event.target.width){
    28.   event.target.width += 3;
    29.   event.target.height += 3;
    30.  }
    31.  else
    32.   event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);
    33.  
    34.  
    35. }
    36. function enterframehandler2(event:Event):void
    37. {
    38.  if(ori_W < event.target.width){
    39.   event.target.width -= 3;
    40.   event.target.height -= 3;
    41.  }
    42.  else
    43.   event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler2);
    44.  
    45.  
    46. }


    코드가 점점 길어 짐니다.. 으악!!! 어떻게 코드를 줄일수 있을까요? if 문을 사용해 봅시다.

    1. var ori_W = bu_mc1.width
    2. var ori_H = bu_mc1.height            // bu_mc 들은 모두 같은 크기 이기 때문에 임의로 bu_mc1 의 값을 저장
    3. var targetW = 120;
    4. var targetH = 120;
    5. var bo:Boolean = false;
    6. for(var i:int= 1; i < 4; i++)
    7. {
    8.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OVER, Overhandler);  
    9.  this["bu_mc"+i].addEventListener(MouseEvent.MOUSE_OUT, Outhandler);    
    10.                                                                                                      
    11. }
    12.  
    13. function Overhandler(event:MouseEvent):void
    14. {
    15.  bo = true;
    16.  event.target.addEventListener(Event.ENTER_FRAME, enterframehandler);    
    17.    
    18. }
    19. function Outhandler(event:MouseEvent):void
    20. {
    21.   bo = false;
    22.  event.target.addEventListener(Event.ENTER_FRAME, enterframehandler);    
    23.  
    24. }
    25. function enterframehandler(event:Event):void
    26. {
    27.  if(bo){
    28.   if(targetW > event.target.width){
    29.    event.target.width += 3;
    30.    event.target.height += 3;
    31.   }
    32.   else
    33.   {
    34.    event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);
    35.    bo = false;
    36.   }
    37.  }
    38.  else
    39.  {
    40.   if(ori_W < event.target.width){
    41.    event.target.width -= 3;
    42.    event.target.height -= 3;
    43.   }
    44.   else{
    45.    event.target.removeEventListener(Event.ENTER_FRAME, enterframehandler);
    46.    bo = true;
    47.   }
    48.  }
    49.  
    50. }


    bo 값을 이용해 ture, false 를 조절해서 enterframehandler 를 하나로 줄였습니다. 어렵다고요?
    제가 봐도 어렵습니다. 최종 코드를 하나하나 타이핑 해 보시고, 이 ENTERFRAME 과 MouseEvent 와의 이벤트 전달 관계를 잘 이해해야 뒤에 나오는 더 어려운 이벤트들의 관계를 이해 할수 있을꺼라 생각이 됩니다. 우리의 생각을 컴퓨에서 전달하기 위해서는 한글을 이해를 못하는 멍청한 컴퓨터를 배려 해서 10101111111001 로 전달해 줘야 되는데 그 10101111101의 중심에는 if 문이 있습니다. 잘 활용하면 명검이 될수도 있고 잘 활용못한다면 무수히 많은 에러로 인해 프로그램을 망가뜨릴수 있으니 잘 이해 하고 넘어 가세요. 

    버튼 크기 바꾸는데 왜이리 복잡하냐!!!!!!!!! 라고 말하시는 분들을 위해

     위의 방법을 쓴 것은 ENTERFRAME 의 이해를 위해서 사용한 것이고, actionscript 에는 알아서 계산해 주는 Tween 이라는 클래스가 있습니다. 위의 방법은 강력한 Tween 클래스를 사용하기 전의 연습단계이고,, Tween클래스는 좀 후에 다루겠습니다. 궁금하신 분들은 Tween 클래스를 F1 에서 찾아 보는것도 좋을것 같습니다.  

    ps : 위와 같이 enterframe 을 하나로 사용하면 문제가 발생합니다. 왜 발생하는 것일까요?  
           생각해 봅시다.

     

     문제 수정전 swf 파일
     

     

    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.11 00:11


    1강에서 3.0 의 대략 적인 소개와 다시 읽어 보니깐 대충 넘어 간 부분 들이 있어서 정리해 보았습니다.

    0. 연산자 

    연산자 라고 하면 + , - , / , * , == , => , != , += , -= , &&, || 등등 여러가지가 사용 되고 있습니다. + 는 

    var num = 200+ 100;
    var num = num + 100;   ===> num += 100; 과 같은 의미로 쓰임니다.

    그러면 i += 1; 은 i = i + 1 이겠지요? 또 다르게 표현하면 i++, ++i 로 표현 가능합니다 i++,++i 차이는
    전위 연산자와 후위 연산자라고, i 가 단독으로 쓰이면 차이가 없이 쓰임니다. 저런게 있다는것만 알아 두시면 될것 같아요. - 도 +와 똑같은 형식으로 쓰입니다. 프로그래밍을 처음 하실때 헛갈린 부분이 '=' 와 '==' 차이 입니다. 종종 질문에 if문 안에 = 를 쓰시고 if 문이 생각대로 안돌아 간다고 하시는 분들이 많은데 A 와 B 가 있을때,

    A = 10; B = 34;
    A = B
    trace(A); 
    // output
    34 

    이런 식으로 오른쪽 변수를 왼쪽 변수에 할당 한다는 의미로 쓰입니다. 그러니깐 아무리 if 문에서 = 를 써봤자 원하는 연산과정이 수행이 안되는 것입니다. if ( 조건 ) if 문은 안에 들어 있는 조건이 0 이 아니면 무조건 (1 이상이면) true 라고 인식을 합니다. 컴퓨터 프로그램에서 0 은 false 를 1 은 true 를  의미 합니다. 그럼 00000000000000000 은? 0 입니다 false 

    0.0 and 와 or 연산자 (&& , || , | , & )


    && 는 and 연산 즉 둘다 성립해야 true 를 반납하는 and 연산자 입니다. 예를 들어

    var A = 10
    var B = 5
    var C = 14
    if( A > B && C > A) = > true 
    if( A > B && C < A) = > false
    if( A < B && C < A) = > false

    || 는 or 연산 즉 둘중 하나만 성립해도 true 를 반납합니다.

    if( A > B || C > A) = > true 
    if( A > B || C < A) = > true
    if( A < B || C < A) = > false

    && 와 & 의 의미상의 차이점은 없지만, 컴퓨터 연산에서 || 의 경우 || 로 이어진 if(W||E) 조건이 있을때 W 가 true일 경우 뒤에 조건은 무시하고 바로 true 를 리턴하여 연산 속도를 향상시켜 줍니다. 보통은 &&, || 를 많이 사용합니다.

    1 . 조건문

    if 문의 경우 if - else 문과 그냥 순수히 if 문으로 나열된 경우 두가지를 생각할수 있는데,
    if - else 문은
    if(A){}
    else{}
    A 조건이 아니면 else 문을 실행한다.

    if(A){}
    else if(B){}
    else{}
    A조건이 아니면 B 문 B조건이 아니면 else 를 실행 합니다.
    그냥 if 문으로만 연결된 경우에는
    if(A){}
    if(B){}
    if(C){}
    if(D){}
    일일이 4가지 경우를 모두 확인하게 됩니다. 오해의 소지가 있을 만한 부분을 써 보았습니다. 

     

    2. Timeline

    위와 같이 레이어에 액션이 써 있을 경우 실행 되는 순서는 어떻게 될까요?
    4번 부터 실행 됩니다. 예를 들어 1 번 레이어에 var a = 10; 라고 써놓고 2번 레이어에서 trace(a); 를 실행 시켜 봅시다. undefined 가 출력됩니다. 같은 프레임에 있어도 엄연하게 실행 순서가 존재 합니다. 위에서 아래로  기억해 두세요.

    3. 전역변수와 지역 변수

    var a = 0; 
    function varible():void
    {
           var b = 10;
    }
    trace(a);
    trace(b);
    // 어떤 결과가 나올까요?

    1120: Access of undefined property b. b 를 접근 할수 없다네요.

     

    // 왜 위에서는 undefined 라고 알려 줬는데 여기서는 접근 할수 없다고 하는거냐!! 위의 질문은 다음으로 미루고, (조금 생각해 보세요 ) 위에서 정의한 것과 같이 a 는 전역 변수이고 b 는 지역 변수 입니다.

    전역변수 : 어느곳에서나 쓰일수 있다. fla 파일 스크립트 작성시 위에서 언급했던 코드 작성의 전후 관계만 맞춰 사용한다면 어느 곳에서나 접근이 가능한 변수를 말합니다.
    지역변수 : b 는 왜 접근할수 없을까요? 간략히 말하면 b 는 varible 함수에서만 존재하는 값 입니다. varible 함수가 실행됨과 동시에 생성되고 varible 함수가 종료하게 되면 소멸하게 되지요.

    개념은 함수 사용에도 동일하게 적용이 됩니다.

    var a = 10;
    ba();
    function ba():void{
       var k = 20;
       trace(k);
       function ab():void
        {
               trace(a);
               trace(k);
         }

    }

    // 20
    var a = 10;
    ab();
    function ba():void{
       var k = 20;
       trace(k);
       function ab():void
       {           
             trace(a);
             trace(k);
       }

    }

    // 1180: Call to a possibly undefined method ab.

    ba 안에 있는 ab 함수 역시 ba 안에서만 존재하는 함수로 치부가 됩니다. 전역변수와 지역변수의 개념은 엄청나게 중요한 개념이니 잘 잡고, 넘어 가시는게 좋습니다.

    4. Function

    함수는 코드의 재 사용성을 위한 보따리 입니다. 자주 사용될 코드를 함수로 만들어 놓으므로서
    코드를 심플하게 만들며, 상황에 따라 코드를 적용할수 있게 해주는 편리한 도구 입니다.
    as 에서 쓰이는 방식은 아래와 같으며 
    function 함수명(넘겨줄변수명:타입, 넘겨줄변수명:타입 ......):리턴타입 예를 들어 보겠습니다


    var num1 = 20;
    var num2 = 34;
    var sum = test(num1,num2);
    trace(sum);
    function test(a:int, b:int):int
    {

       var c = 0;
       c = a + b;
       return c;

    }
    // 54    return 해 주는 c 를 sum 을 이용해서 받습니다. 
     

    var num1 = 20;
    var num2 = 34;
    var sum = 0;
    test(num1,num2);
    function test(a:int, b:int):void
    {
       
    sum = a + b;
    }
    trace(sum);
    // 54  전역변수인 sum 에 바로 대입합니다.

    여기서 void 는 이 함수는 return 을 시키지 않겠다는 뜻 입니다. 이 함수 개념이 더욱더 확장된게
    Class 입니다. class 는 천천히 다루도록 하겠습니다.
    아 잠깐만 다루려고 했던 개념들이 쓰다 보니깐 왕창 길어 졌네요;; Event 하려고 했는데;;

    5. Event - Enterframe ( 왕중요 )
    지금까지의 지루했던 플밍 개념들은 접어 두시고 , 재미 있는(?) 플래시의 세계로 돌아왔습니다. 지난 강에서는 MouseEvent 에서 Over 와 Out 을 써 보았는데요. 이번 강에서는 enterframe 을 잠깐 소개 하고 다음 강에서는 먼가를 만들어 보도록 하겠습니다. 플래시 창의 하단 Properties 창을 보면

    Frame rate XX fps 가 있습니다. fps 뭘까요? frame per second  프레임 기반인 flash 툴에서 1초당 몇 프레임을 이용시킬 것이냐(몇 프레임을 랜더링 할 것이냐) 하는 말입니다. 영화 TV 도 이 프레임 개념으로 우리 들의 눈속임을 하고 있는 것이지요 ( 잔상효과 ? ) 12 fps 란 말은 초당 12 frame 을 이동(보여 줄것이다) 시킬 것이다를 의미 합니다. 따라서 fps 를 높일 수록 움직임이 자연스러워지겠지요? ENTER_FRAME 은 이 fps 에 기본을 두고 있습니다. 사용법은 다음과 같습니다. 
    스테이지에 
    원을 그리고 F8 을 눌러 무비 클립으로 만든후 원 이름을 circle_mc 라 합니다.( 1강 참고 )
    그리고 fps 를 36 으로 조절 합니다.


    1. //code
    2.  
    3. circle_mc.addEventListener(Event.ENTER_FRAME, framehandler);
    4.  
    5. function framehandler(event:Event):void
    6. {
    7.  
    8.       if(circle_mc.x < 550)            
      // 배경 width 이 550 이므로 x 값이 550 을 넘어 가면 0 으로 옮겨 준다.
    9.              circle_mc.x += 3;
    10.  
    11.       else
    12.  
    13.              circle_mc.x = 0;
    14. }

    실행!!  fps 를 바꿔가면서 실행해 보세요. 아래 화면은 63 fps 로 처리한 것입니다. 이처럼 ENTER_FRAME 이벤트는 fps 에 종속되어 fps 속도 의 빠르기로 ENTER_FRAME 과 연결된 함수인 framehandler (함수 이름은 다르게 써도 무방합니다 ) 를 계속 해서 실행 시켜 줍니다. 이벤트를 지워주기 까지는... 
    이제 버튼을 추가 해서 이벤트를 제어해 보겠습니다. 원과 같은 방식으로 무비 클립을 두개 생성합니다.
    start_mc  ,stop_mc

     
    1. //code
    2. start_mc.buttonMode = true;                  // 마우스를 오버 했을때 손가락이 나타나게 한다.
    3. stop_mc.buttonMode =true;
    4. circle_mc.addEventListener(Event.ENTER_FRAME, framehandler);
    5.  
    6. function framehandler(event:Event):void
    7. {
    8.  
    9.       if(circle_mc.x < 550){             // 배경 width 이 550 이므로 x 값이 550 을 넘어 가면 0 으로 옮겨 준다.
    10.              circle_mc.x += 3;
    11.    }
    12.       else{
    13.              circle_mc.x = 0;
    14.    }
    15. }
    16.  
    17. start_mc.addEventListener(MouseEvent.CLICK, startClickhandler);       // 시작 버튼
    18. function startClickhandler(event:MouseEvent):void
    19. {
    20.  
    21.  circle_mc.addEventListener(Event.ENTER_FRAME, framehandler);
    22.  
    23. }
    24.  
    25. stop_mc.addEventListener(MouseEvent.CLICK, stopClickhandler);      // 정지 버튼
    26. function stopClickhandler(event:MouseEvent):void
    27. {
    28.  
    29.  circle_mc.removeEventListener(Event.ENTER_FRAME, framehandler);
    30. }

    위의 코드와 같이 생성된 이벤트를 제거 해 주는데는 removeEventLister 가 쓰이게 됩니다. addEventListener 로 한 객체에 EventListener를 add(더해) 줬으니 remove 해 주겠다는 뜻이지요.
    사용법은 addEventListener 로 등록했을때 의 똑같은 형식으로 add 를 remove 만 바꿔주면 됩니다. 

    ENTER_FRAME 이벤트의 기본적인 동작에 대해 알아 보았습니다. 다음 강에서는 ENTER_FRAME 이벤트를 이용하여 작업 하는 것들에 대해 더 알아 보겠습니다. 


     

    .

    Posted by Flash 동강
    동강의AS3.0 강좌2008.12.10 23:49

     안녕하세요. Actionscript3.0 기초강좌를 하게된 '동강'입니다. 짧은 Actionscript 의 이해를 가지고 있지만, Flash 를 처음 시작하는 분들이나 as2.0 을 쓰다가 새롭게 3.0 을 배우는 분들에게 좀더 빨리 AS3.0 에 적응을 돕고자 기초 강좌를 하게 되었습니다.  

     우선 기초강좌의 내용은 프로그래밍에 기본이되는 문법들 예를 들어 if 문 사용 방법이라든지, function 사용법은 다 안다는 가정하에 진행하겠습니다. ( 다른 C 나 Java 와 확연하게 구분되는 부분만 설명 ) 

     자 이제 부터 시작하겠습니다. 3.0 정복을 향하여~ 우왕 

     자주 쓰이게 되는 trace(); 함수는 C 에서는 printf , Java 에서는 System.out.println, C++ 에서는 cout 이라고 생각하시면 됩니다. trace(이름); 이름에 대한 내용을 output 창에 출력해 주는 역할을 합니다.


    0. Actionscript 3.0 
    Flash 는 객체 지향을 기반으로 하고 있는 타임라인 프로그램 입니다. Flash 에서 그려지고, 정의 되어 지는 모든 것들은 타임라인 위에 정의가 되고(그려진다) 타입 라인 위에서 조작이 되게 됩니다. 타임라인 프로그램이란 말은 예를 들면 Layer 1 위 1 frame 에 객체를 생성하게 되면 action 레이어 에서 해당 객체를 접근할수 있습니다. 하지만 아래의 경우 "Layer 1" 1frame 에 rect 라는 무비 클립을 정의해 놓고  "action" 레이어의 2frame 에 trace(rect); 를 출력해 보면 접근 할수가 없다고 error 가 발생합니다.


    타임라인 프로그램이라는 말이 무슨 뜻인지 아셨는지요? 레이어에 actionscript 를 작성하여 객체를 접근할때는 레이어에 입력되어 있는 actionscript 의 발생 순서를 잘 이해하고 있어야 합니다. 한번 프레임에 Actionscript 를 정의를 하게 되면 그 정의는 frame 이 바뀌어도 계속 유지 되게 됩니다. 예를 들어 위의 Action Layer 에 var num:int = 0;  이라 정의를 하게 되면 프레임이 이동 되어도 그 정의는 유효 하게 됩니다.

    객체의 경우에도 마찬가지로 적용되는데, Actionscript 를 적용할때는 항상 action 이 들어 가 있는 같은 frame 에 actionscript 를 이용해서 조작할 해당 객체가 존재 해야 됩니다.

    1. Actionscript3.0 의 시작
    Actionscript(이하 as 라 하겠습니다) 는 다른 웹 언어와 마찬가지로 ECMAScript 규정을 따르고 있습니다. 이 말은 다른 프로그래밍과 문법이 비슷하다는 말입니다. Java 를 사용해보신 분들은 거의 같다고
    생각하시면 될것 같습니다.

    자주 쓰는 변수의 선언 형태는 Number , int, MovieClip, TextField, Array 등등 이 있고 선언 형태는
    var num:Number = new Number();
    var mc:MovieClip = new MovieClip();

     + - * / 연산자도 같은 형식으로 쓰입니다.


    2. Event

    이론 적인것은 여기 까지 하고 ( 한것도 없지만 ) 이제 실제로 해 보겠습니다. Flash 에서 정의 되는 객체 들은 Event 를 가지고 있고, 그 해당 객체 들과 EventListener 로 연결이 되어 있습니다. 객체를 사람이라고 하면 EventListener 는 그사람의 귀 입니다. 귀를 통해서 무엇을 하라는 것을 듣고 사람은 행동하게(이벤트를 발생) 되는 것입니다.( 자신이 행동할수도 있고, 다른사람을 시킬수도있습니다) 우선 Stage(메인 창) 에 원을 그리고 F8 을 눌러 MovieClip 으로 지정합니다. 그리고 그 이름은 circle_mc 라고 하겠습니다.


    Name 을 circle_mc 라고 지정하였는데 Name 을 circle_mc 라고 했다고 해서 circle_mc 로 접근할수 있는 것은 아님니다. 단순히 객체들의 저장공간인 Library 에서 사용자가 알아 보기 쉽게 하기 위한 이름일 뿐 그 이상이 아님이다. 실제로 as 를 이용하여 접근하기 위해서는 무비클립을 클릭한후 아래 나오는 Properties 창에 circle_mc 라고 입력해 줍니다. 이제 action Layer 를 클릭하고  F9 눌러 as 를 입력합니다.

     

    trace(circle_mc);

    //output

    [object MovieClip]

    위에서 정의된 객체를 MovieClip 이라 합니다. 벡터 기반의 편리한 속성을 가지고 있는 이미지 객체라고 생각하면 되겠네요 MovieClip 의 속성은 아주 많지만 우선 기본적으로 를 가지고 있고, 더 자세한건 F1 을 눌러서 참고 하세요.

    circle_mc.x             // 객체의 x 좌표 위치
    circle_mc.y            // 객체의 y 좌표 위치
    circle_mc.width       // 너비
    circle_mc.height      // 높이
    circle_mc.alpha       // 투명도

    이 해당 객체에 Event를 걸어 줄수 있는데 이벤트를 거는 문법은 다음과 같습니다.

    circle_mc.addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler);       
    // 해당 객체에 마우스 오버
    circle_mc.addEventListener(MouseEvent.MOUSE_OUT,mouseOuthandler); 
    //  해당 객체에 마우스 오버
    circle_mc.addEventListener(MouseEvent.CLICK, mouseClickhandler); 
    //  해당 객체에 마우스 클릭
    circle_mc.addEventListener(Event.ENTER_FRAME, enterframehandler);   



    등등 의 이벤트를 생성해 줄수 있으며, 그 해당 이벤트에 대한 함수를 호출 하는 방식으로 동작을 수행하게 됩니다. 예를 들어 ex) ->
    circle_mc.addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler); 
    마우스 오버 에 대한 이벤트를 정의하고

    function mouseOverhandler(event:MouseEvent):void{
            // 동작 수행을 위한 코드

    마우스가 해당 객체에 오버 되면 mouseOverhandler 함수가 실행 되게 됩니다. 파라미터로 넘어 가는 (event:MouseEvent) 에는 MouseEvent 와 이벤트가 발생하는 해당 객체에 대한 정보를 가지고 있으며event.target , event.currentTarget 등의 형태로 이용되게 됩니다. ( 자세한 구분은 추후에 하도록 하겠습니다 )


    1. circle_mc.addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler);
      // 마우스 오버 에 대한 이벤트를 정의하고
    2.  
    3. function mouseOverhandler(event:MouseEvent):void 
    4. { 
    5.       event.target.x += 10
    6. } 
    7. // circle_mc 에 마우스를 오버 하면 x 위치를 10씩 증가 시키겠다.
    8.  
    9. Out 이벤트와 같이 써보면 
    10. circle_mc.addEventListener(MouseEvent.MOUSE_OVER, mouseOverhandler);
      // 마우스 오버 에 대한 이벤트를 정의하고 
    11. circle_mc.addEventListener(MouseEvent.MOUSE_OUT,mouseOuthandler);          
        // 아웃 이벤트 정의
    12.  
    13. function mouseOverhandler(event:MouseEvent):void{ 
    14.       event.target.x += 10;                            
      // event 에는 정보가 들어 있습니다. event를 줄여서 e 나 ev 로 쓰기도 합니다.
    15.  
    16. }                                                              
      // 함수 안에서 사용되는 이름만 같게 해주면 상관 없습니다. 
    17. function mouseOuthandler(event:MouseEvent):void 
    18. { 
    19.       event.target.x -= 10
    20. }

    이런식으로도 쓰일수 있겠네요, 위와 같이 Flash 에서 정의 되어지는 객체 들은 다양한 Event 를 가질수 있습니다. 위에서 예를 든것은 무비 클립의 한 단면이고요. 약간만 응용하면 버튼을 만들고 버튼 클릭시 움직이는 원을 만들수 있습니다. 

    그렇다면 버튼을 생성해야 되겠지요? 버튼 생성후 (cl_btn)


    1. cl_btn.addEventListener(MouseEvent.CLICK, clhandler);
    2.  
    3. function clhandler(event:MouseEvent):void
    4. {
    5.  if(circle_mc.x < 550)                // x 값이 Stage 보다 커지면  -5 위치로 옮긴다.
    6.   circle_mc.x += 10;
    7.  
    8.  else
    9.   circle_mc.x = -5;
    10.  
    11. }

    무비 클립에 간단한 마우스 이벤트를 적용해 보았습니다. 이제 슬슬 이벤트가 어떤식으로 왔다 갔다 하는지 감이 오시는지요? 간단한 이벤트 들이지만 제일 많이 쓰이게 되는 두 이벤트입니다. 앞으로 MovieClip 을 계속 해서 사용하게 될텐데요. MovieClip 에 대해 F1 을 참고해 보시는 것도 좋을듯 싶습니다.
    (F1 는 Flash 프로그램 안에서 제공되는 도움말 입니다. )
    한글 도움말 주소는 : http://livedocs.adobe.com/flash/9.0_kr/ActionScriptLangRefV3/index.html 

    다음 강에서는 Flash의 핵심이라 할수도(?) 있는 이벤트 ENTER_FRAME 에 대해 알아 보겠습니다. 화려한 모션을 하게 해주는 원동력이라고 할수 있습니다.



    Posted by Flash 동강