예제: 원근 투영

Flash Player 10 이상, Adobe AIR 1.5 이상

다음 예제에서는 원근 투영을 사용하여 3D 공간을 만드는 방법을 보여 줍니다. 또한 projectionCenter 속성을 통해 소실점을 수정하고 공간의 원근 투영을 변경하는 방법을 보여 줍니다. 이렇게 수정하면 focalLength fieldOfView 가 다시 계산되고 그에 따라 3D 공간이 왜곡됩니다.

이 예제에서 수행하는 작업은 다음과 같습니다.

  1. 십자형이 있는 원으로 center 라는 스프라이트를 만듭니다.

  2. 루트의 transform 속성의 perspectiveProjection 속성의 projectionCenter 속성에 center 스프라이트의 좌표를 할당합니다.

  3. 마우스 이벤트에 대해 center 객체의 위치를 따르도록 projectionCenter 를 수정하는 핸들러를 호출하는 이벤트 리스너를 추가합니다.

  4. 원근 공간의 벽을 형성하는 네 개의 아코디언 스타일 상자를 만듭니다.

이 ProjectionDragger.swf 예제를 테스트할 때는 다른 위치에 원을 그립니다. 소실점은 이 원을 따라가다가 사용자가 원을 놓는 위치에 고정됩니다. 투영 중심을 스테이지의 중심에서 멀리 이동할 때 상자 내부의 공간이 확장되면서 왜곡되는 것을 살펴보십시오.

이 샘플에 대한 응용 프로그램 파일을 가져오려면 www.adobe.com/go/learn_programmingAS3samples_flash_kr 을 참조하십시오. ProjectionDragger 응용 프로그램 파일은 Samples/ProjectionDragger 폴더에 있습니다.

package 
{ 
    import flash.display.Sprite; 
    import flash.display.Shape; 
    import flash.geom.Point; 
    import flash.events.*; 
    public class ProjectionDragger extends Sprite 
    { 
        private var center : Sprite; 
        private var boxPanel:Shape; 
        private var inDrag:Boolean = false; 
         
         public function ProjectionDragger():void 
        { 
            createBoxes(); 
            createCenter(); 
        }  
         public function createCenter():void 
         {   
              var  centerRadius:int = 20; 
     
              center = new Sprite(); 
     
              // circle 
              center.graphics.lineStyle(1, 0x000099); 
              center.graphics.beginFill(0xCCCCCC, 0.5); 
              center.graphics.drawCircle(0, 0, centerRadius); 
              center.graphics.endFill(); 
              // cross hairs 
              center.graphics.moveTo(0, centerRadius); 
              center.graphics.lineTo(0, -centerRadius); 
              center.graphics.moveTo(centerRadius, 0); 
              center.graphics.lineTo(-centerRadius, 0); 
              center.x = 175; 
              center.y = 175; 
              center.z = 0; 
              this.addChild(center); 
     
              center.addEventListener(MouseEvent.MOUSE_DOWN, startDragProjectionCenter); 
              center.addEventListener(MouseEvent.MOUSE_UP, stopDragProjectionCenter); 
              center.addEventListener( MouseEvent.MOUSE_MOVE, doDragProjectionCenter); 
              root.transform.perspectiveProjection.projectionCenter = new Point(center.x, center.y); 
        } 
        public function createBoxes():void 
        { 
            // createBoxPanel(); 
            var boxWidth:int = 50; 
            var boxHeight:int = 50; 
            var numLayers:int = 12; 
            var depthPerLayer:int = 50; 
             
            // var boxVec:Vector.<Shape> = new Vector.<Shape>(numLayers); 
            for (var i:int = 0; i < numLayers; i++) 
            { 
                this.addChild(createBox(150, 50, (numLayers - i) * depthPerLayer, boxWidth, boxHeight, 0xCCCCFF)); 
                this.addChild(createBox(50, 150, (numLayers - i) * depthPerLayer, boxWidth, boxHeight, 0xFFCCCC)); 
                this.addChild(createBox(250, 150, (numLayers - i) * depthPerLayer, boxWidth, boxHeight, 0xCCFFCC)); 
                this.addChild(createBox(150, 250, (numLayers - i) * depthPerLayer, boxWidth, boxHeight, 0xDDDDDD)); 
            } 
        } 
         
        public function createBox(xPos:int = 0, yPos:int = 0, zPos:int = 100, w:int = 50, h:int = 50, color:int = 0xDDDDDD):Shape 
        { 
            var box:Shape = new Shape(); 
            box.graphics.lineStyle(2, 0x666666); 
            box.graphics.beginFill(color, 1.0); 
            box.graphics.drawRect(0, 0, w, h); 
            box.graphics.endFill(); 
            box.x = xPos; 
            box.y = yPos; 
            box.z = zPos; 
            return box; 
        } 
        public function startDragProjectionCenter(e:Event)  
        {  
            center.startDrag(); 
            inDrag = true; 
        } 
         
        public function doDragProjectionCenter(e:Event)  
        {  
            if (inDrag) 
            { 
                root.transform.perspectiveProjection.projectionCenter = new Point(center.x, center.y); 
            } 
        } 
         
        public function stopDragProjectionCenter(e:Event) 
        { 
            center.stopDrag();  
            root.transform.perspectiveProjection.projectionCenter = new Point(center.x, center.y); 
            inDrag = false; 
        } 
    } 
}

보다 복잡한 원근 투영의 경우에는 Matrix3D 클래스를 사용합니다.