2010/03/03 | 转-FLASH as3 多点触摸 手机 杂
类别(flash As) | 评论(0) | 阅读(1754) | 发表于 15:57

http://hi.baidu.com/dabstudio

 

http://www.mt2a.com

 

http://www.mt2a.com/tag.php?name=flash

 

一些经验,写给多点触摸开发刚入门的同志

 

本帖最后由 NICK_LEE 于 2009-6-11 16:05 编辑 

大家好,很高兴看到有这样一个多点触摸论坛的存在

我大概07年开始接触到多点触摸的概念,当然也是通过Jeff Han那段神奇的视频认识到的(什么?你还没看过?赶紧补课吧~)

 

Jeff Han在TED大会上的视频地址:

 

http://www.ted.com/talks/jeff_ha ... gh_touchscreen.html

 

一直到现在,也做了很多多点触摸方面的应用,看到论坛中还是很多新加入的伙伴,不知道怎样开始,我觉得作为一个老鸟(呵呵,总算也混了段时间了),有必要写一篇入门级的文章,让大家尽快可以加入多点触摸的开发行列。

当然以下我主要从软件的角度去谈多点触摸的开发,至于硬件上的DIY,这篇文章暂不涉及,大家上网找找吧,有很多的教程的~

 

第一,touchlib

 

首先,我们先从总体结构上谈谈多点触摸软件。

现在我们自己DIY的触摸屏都是属于OpticalMultitouch,说白了就是用红外灯把你手指照亮,然后用摄像头去捕捉你的手指的位置来实现多点触摸。所以,在最低层要有一个摄像头的检测软件,用于捕捉跟踪你的手指位置,这个属于计算机视觉领域的活,别怕,现在开源世界里面已经有了好几个用于多点触摸捕捉的软件了,其中比较早也比较经典的一个就是touchlib。这个软件我没记错的话

 

大概07年中间的时候发布,后来又修改了好久,现在版本已经基本稳定在ver.401。很久没有变化了。

touchlib是用C++编写,最终是以dll(动态链接库)的形式发布,随着touchlib项目一起的(具体参见touchlib源码)还有几个用C++编的例子,比如smoke,mousedrive,osc等。有的看官读到这里也许会问了,那我要开发多点触摸程序,就必须用C++了?非也。

如果您是位C++程序员,并且也只准备用C++来开发多点触摸的程序,那么您就别往下看了,去好好看看touchlib里面带的例子吧,看会了就可以开发了。如果您想用其他开发语言(如as3),那就请继续往下看。

 

第二,OSC

 

在上面提到的几个例子中,有一个程序要特别注意的就是osc。要理解这个程序,你就不得不了解两个协议:osc和tuio。osc,全名(opensound control),是一个通信协议,定义了一些传输时用的格式,为了方便数据传输用的,比较底层,了解就可以了。

tuio,全名(A Protocol for Table Based Tangible User Interfaces),如果要理解osc.exe机制的话,这个协议可不能放过,它定义了如何在程序中表示触摸界面上出现的实体,如手指。这是touchlib和as3通信的格式。

看到这里有的看官是不是已经开始犯晕了,没事,不想看这些协议也没问题,我画张图您就全明白了~

 

摄像机--〉touchlib --〉osc --〉flosc --〉as3

又有人问了,这个flosc是个什么东西啊?这是个用java写的类似于桥一样的东西,将osc的消息(tuio格式)经过flosc传给as3。

好了消息传过来了,现在就让我们开始解析以下as3的结构(想用as3开发的同志,下面注意看吧)

 

第三,AS3 

 

先从AS3这个文件夹上看(什么?AS3文件夹在哪里?请上http://code.google.com/p/touchlib/自己下载先),里面一共有三个文件夹ext,int,src。其中ext是外部一些as3库,像pv3d之类的,就甭管它了。src文件夹中是各个flash例子的fla文件也暂时不管了。

 

最重要的就是int这个文件夹中的东西。

int文件夹中又有三个文件夹(靠,耍我们啊~),其中com_old就别去管它了,过时了(人家标明了old嘛)。app文件夹咱们一会儿再去看它。现在先来看flash这个文件夹中的东西。flash文件夹里面只有一个event文件夹,再下去就是五个文件了,这五个就是AS3中实现多点触摸功能最核心的五个类了,咱们一个个看下来:

 

TUIO

.as -- 这个是最主要的类,有两个功能,1.与osc(不会已经忘了它是干什么的吧?看看上面那张图)进行通信,接收osc传来的tuio格式的消息。2.将tuio格式的消息转化为TUIOObject,并且dispatch多点触摸事件。重点去看processMessage这个函数,基本功能都在里面了。

 

TUIOObject.as -- 这个是类说的白话一点就表示了触摸屏上的触摸点。

 

TouchEvent.as -- AS3多点触摸事件的定义都在里面了。因为现在AS3 api没有文档,所以要好好看这里面定义的事件类型。

 

TUIOCursor.as -- 不是很重要的一个类,只是用于调试用的光标。

 

TUIOSimulator.as -- 看名字就知道了,一个模拟器。其实现在好得模拟器很多,也用不到这个功能了。

 

好了,最重要的五个文件已经解析完了,当然如果你要理解其中机制的话,还是要你自己去阅读源码,毕竟我不能替代你去读。

下面回到app文件夹,里面又有两个文件夹core和demo。demo从名字上就知道了,是flash实例的源文件,这个先放放。先来看core文件夹,哎哟,这个里面的东西太多了,还是先挑重要的看吧,action文件夹是最重要的一个,因为所有多点的动作(如,放大,缩小,旋转)都是这个里面的类实现的。说句老实话,因为这个里面的类不是一个人写的,所以比较混乱,一共有两个分支:

 

RotatableScalable.as,这个是最早的一个现实旋转和缩放的类,用起来也比较简单,但代码有点混乱。另一个分支是

 

Multitouchable.as,其他开发者觉得老的类结构不好,想写个更清楚的,就出现了这个类,由这个类又衍生了好多其他的类。

 

所以,该文件夹下面的类都是继承或者是由这两个类改编而来的。具体的大家就自己看吧。好了,解析的部分先写那么多吧(好累啊~)。以上的部分是给想要研究多点触摸机制的同志看的,如果您觉得我不想知道这些,我就想立刻开始开发多点触摸程序,该从哪里开始呢?

我的建议是,看src文件夹底下的例子吧,这是最快的方法。再下载一个TUIO模拟器和flosc网桥就可以了立刻进行开发了!

 

模拟器的下载地址:

 

http://nuigroup.com/forums/viewthread/1495/

 

这个帖子中的附件都有了。好了,各位看官努力吧

也欢迎到我的博客看看(虽然更新不够快~):

 

http://hi.baidu.com/summer150

 

 

 

创建你的第一个Flash多点触摸程序(图文详尽教程)

 

多点触摸, Flash

本帖最后由 Thons 于 2009-8-7 23:06 编辑 

 

//-------------------------------------------------------------------

 

 

//原文地址:

 

http://wiki.nuigroup.com/Building_Your_First_Application

//Translator:Thons

 

 

//感谢panther的投递

 

 

//-------------------------------------------------------------------

 

//首先,必须使用SVN文件,否则可能无法正常工作  

 

如何使用SVN?

 

1.创建一个新的

 

Flash

文件(ActionScript 3);

 

=============================================================================

 

2.点击一下画布(舞台),这个时候文件属性面板就应该被激活了;

 

=============================================================================

 

3.点击“尺寸”按钮;

 

4.改变尺寸至1024*768,帧率大于30FPS;

 

=============================================================================

 

5.点击“设置”按钮(在“尺寸”按钮下面);

 

6.在“ActionScript 版本”一栏中,选择“ActionScript 3”,并点击右面的“设置”按钮;

 

=============================================================================

 

7.在下面的“类路径(classpath)”一栏中,点击 + 按钮并输入

 

 

        1.../ext

 

 

        2.以此类推

 

 

        3.../int

 

=============================================================================

 

8.保存这个Flash文件到

 

touchlib

文件夹中的AS3/src文件夹下,并起一个名字,比如touch.fla ;

 

=============================================================================

 

9.在AS3/int/app/demo文件夹下,创建一个新的文件夹,命名为MyTouchApp(这个可以不同,但是考虑到类路径和package。这个名字必须准确);

 

=============================================================================

 

10.创建一个新的ActionScript文件;

 

=============================================================================

 

11.保存为MyTouchApp.as,在AS3/int/app/demo/MyTouchApp文件夹里;

 

=============================================================================

 

12.返回至Flash文件里,也就是上面说的touch.fla ;

 

=============================================================================

 

13.在文档类(Document Class)里填入app.demo.MyTouchApp.MyTouchApp ;

 

=============================================================================

 

14.选择“矩形”按钮,在画布(舞台)上画一个矩形,要求尺寸漫过并大于整个舞台;

 

=============================================================================

 

15.右击刚刚画的矩形,选择“转换为元件”;

 

=============================================================================

 

16.确保矩形为MovieClip,然后点击确定

 

=============================================================================

 

17.保存文件。返回至MyTouchApp.as中;

 

=============================================================================

 

18.从例子中拷贝并粘贴代码(确保在此之前,代码区域里没有任何字符);

 

=============================================================================

 

19.保存文件,返回至touch.fla文件中;

 

=============================================================================

 

20.发布文件,现在应该可以工作了。

 

*****************************************************

 

代码示例

 

//这段代码用来显示每个触点下面的小红圈

=============================================================================

 

package app.demo.MyTouchApp{ //adds a circle where you touch (no resize)

 

    import flash.display.*;        

    import flash.events.*;

    import flash.net.*;

    import flash.geom.*;        

 

    public class MyTouchApp extends Sprite {

 

        public function MyTouchApp() {

 

            //--------connect to TUIO-----------------

            TUIO.init(this,'localhost',3000,'',true);

            trace("MyTouchApp Initialized");

            //----------------------------------------        

 

            addEventListener(TouchEvent.MOUSE_DOWN, touchDown); //run touchdown, when touched

        }

 

        public function touchDown(e:TouchEvent):void{        

 

            var curPt:Point = parent.globalToLocal(new Point(e.stageX, e.stageY)); //convert touch points to x,y               

 

            var circle:Sprite = new Sprite(); //create a new sprite

 

            circle.graphics.lineStyle(10, 0xff0000); //set line width to 10px and red

            circle.graphics.drawCircle(0,0,40); // draw a 40px circle

            circle.x = curPt.x; //put it where touch is (x cord)

            circle.y = curPt.y; //put it where touch is (y cord)

 

            addChild(circle); //add the circle where touch happened

 

        }

    }

}

 

=============================================================================

 

 

//这段代码允许你缩放舞台以及让触点下面出现小红圈

//下面的代码只是继承自RotatableScalable类。里面的内容只针对上述讲的东西,因为每个App构造函数不同。

 

 

=============================================================================

 

package app.demo.MyTouchApp{

 

        import flash.display.*;

        import flash.events.*;

        import flash.net.*;

        import flash.geom.*;

        import app.core.action.RotatableScalable;

 

        public class MyTouchApp extends RotatableScalable {//allows it to be scaled around

                public function MyTouchApp() {

 

                        //--------connect to TUIO-----------------

                        TUIO.init(this,'localhost',3000,'',true);

                        trace("MyTouchApp Initialized");

                        //----------------------------------------        

                        addEventListener(TouchEvent.MOUSE_DOWN, touchDown);//run touchdown, when touched

                }

 

                public function touchDown(e:TouchEvent):void {

 

                        var curPt:Point=parent.globalToLocal(new Point(e.stageX,e.stageY));//convert touch points to x,y               

                        var circle:Sprite = new Sprite();//create a new sprite

 

                        circle.graphics.lineStyle(10, 0xff0000);//set line width to 10px and red

                        circle.graphics.drawCircle(0,0,40);// draw a 40px circle

                        circle.x=curPt.x;//put it where touch is (x cord)

                        circle.y=curPt.y;//put it where touch is (y cord)

                        addChild(circle);//add the circle where touch happened

 

                }

        }

}

 

=============================================================================

 

//这段代码的作用是使你在触摸的时候,手指下面出现红色的涟漪(不支持选择和缩放的时候出现这个效果)

 

=============================================================================

 

package app.demo.MyTouchApp{

 

        import flash.events.TUIO; // allows to connect to touchlib/tbeta

        import flash.display.*;

        import flash.events.*;

        import flash.geom.*; // needed for curPt;

 

        public class MyTouchApp extends Sprite {

 

                var ripple:Ring; //ring class at end of code

                var ripples:Array = new Array(); // holds the list of rings to be animated

 

                var color:uint = 0xff0000;

                var radius:Number = 10;

                var thickness:Number = 5;

 

                public function MyTouchApp() {

 

                        //--------connect to TUIO-----------------

                        TUIO.init(this,'localhost',3000,'',true);

                        trace("MyTouchApp Initialized");

                        //----------------------------------------

 

                        stage.addEventListener(TouchEvent.MOUSE_DOWN, onTouchDown);

                        addEventListener(Event.ENTER_FRAME, rippler);

 

                }

 

                private function onTouchDown(e:TouchEvent):void { // makes a ripple, puts it in the array and starts the rippler

 

                        var curPt:Point=parent.globalToLocal(new Point(e.stageX,e.stageY));

 

                        ripple = new Ring(thickness, radius, color); // all defined above

                        ripple.x=curPt.x; // x pos of touch

                        ripple.y=curPt.y; // y pos of touch

                        addChild(ripple); // adds the ripple to the stange

                        ripples.push(ripple); // adds it to the ripples array so it can be animated

                }

 

                private function rippler(e:Event):void {

 

                        for (var i:uint = 0; i < ripples.length; i++) { // cycle through the ripples on stage and animate them

                                ripples.width *= 1.15;

                                ripples.height *= 1.15;

                                ripples.alpha -= .05;

 

                                if (ripples.alpha < .01) { // when the ripple's alpha is below 1% remove it from the stage, and the array

                                        removeChild(ripples);

                                        ripples.splice(i, 1);

                                }

                        }

                }

        }

}

 

import flash.display.Sprite; // ring class

 

class Ring extends Sprite {

 

        public function Ring(thickness:Number = 10, radius:Number = 40, color:uint = 0xff0000) {

                graphics.lineStyle(thickness, color);

                graphics.drawCircle(0,0,radius);

                graphics.endFill();

        }

}

 

=============================================================================

 

//这段代码联合了触摸和鼠标操作。

//当你用鼠标点击的时候,会出现一个小红圈,同时也允许用鼠标来模拟手指进行选择和缩放。

 

=============================================================================

 

package app.demo.MyTouchApp{

 

    import flash.display.*;

    import flash.events.*;

    import app.core.action.RotatableScalable;

 

    public class MyTouchApp extends RotatableScalable {

 

        public function MyTouchApp() {

 

            //--------connect to TUIO-----------------

            TUIO.init(this,'localhost',3000,'',true);

            trace("MyTouchApp Initialized");

            //----------------------------------------        

 

            addEventListener(MouseEvent.MOUSE_DOWN, onMouseDown); // adds an event listener looking for a mouse click - runs "onMouseDown"

        }

 

 

        private function onMouseDown(event:MouseEvent):void { //creats a circle when the mouse is clicked

 

            var circle:Sprite = new Sprite();

 

            circle.graphics.lineStyle(10, 0xff0000); //set line width to 10px and red

            circle.graphics.drawCircle(0,0,40); // draw a 40px circle

            circle.x = mouseX; //put it where the mouse clicked

            circle.y = mouseY;

 

            addChild(circle); //add the circle to the plane

        }

    }

}

 

=============================================================================

 

//这个小程序在舞台上以x轴的随机值分布一些圆环。每个圆环都可以移动和缩放。这个效果可以通过对RotatableScalable类的继承很简单的实现

 

=============================================================================

 

package app.demo.MyTouchApp{

 

    import flash.events.TUIO;// allows to connect to touchlib/tbeta

    import flash.display.Sprite;

 

    public class MyTouchApp extends Sprite {

 

 

        private var num:Number=5; // number of rings to put

        var ring:Ring; //ring class (at bottom)

 

        public function MyTouchApp():void {

 

            //--------connect to TUIO-----------------

            TUIO.init(this,'localhost',3000,'',true);

            trace("MyTouchApp Initialized");

            //----------------------------------------

 

 

            // put "num" rings randomly on the stage

            for (var i:int = 0; i < num; i++) {

                ring = new Ring();

                ring.x = Math.random() * stage.stageWidth;

                ring.y = Math.random() * stage.stageHeight;

                addChild(ring);

            }

        }

 

    }

}

 

import flash.display.Sprite; // ring class

import app.core.action.RotatableScalable;

 

class Ring extends RotatableScalable {

 

    public function Ring(thickness:Number = 10, radius:Number = 40, color:uint = 0xff0000) {

 

        //---RotatableScalable options------------

            //noScale = true;

            noRotate = true;   

            //noMove = true;

        //----------------------------------------

 

        graphics.lineStyle(thickness, color);

        graphics.drawCircle(0,0,radius);

 

        graphics.beginFill(0xffffff);

        graphics.drawCircle(0,0,radius);

        graphics.endFill();

    }

}

 

=============================================================================

 

//现在我们稍微整合一下代码,做一个简单的画图程序

 

=============================================================================

 

package app.demo.MyTouchApp{

 

    import flash.events.TUIO; // allows to connect to touchlib/tbeta

 

    import flash.display.*;

    import flash.events.*;

    import flash.geom.*; // needed for curPt;

 

    public class MyTouchApp extends Sprite {

 

        private var color:uint = 0xff0000; // color of lines

        private var thickness:Number = 30; // thickness of lines

 

        private var blobs:Array = new Array(); // blobs we are currently interacting with

        private var lines:Array = new Array(); // array to hold the lines

 

        public function MyTouchApp():void {

 

            //--------connect to TUIO-----------------

            TUIO.init(this,'localhost',3000,'',true);

            trace("MyTouchApp Initialized");

            //----------------------------------------

 

            addEventListener(TouchEvent.MOUSE_DOWN, downEvent, false, 0, true); // run when finger down

            addEventListener(TouchEvent.MOUSE_UP, upEvent, false, 0, true); // run when finger up

            addEventListener(Event.ENTER_FRAME, updater, false, 0, true); // keep running

        }

 

        // updates/draws the drawn lines by:

        // cycling through all existing blobs

        // getting the id of each blob

        // use that id to get the line, as the lines are named after their blobs (eg line1280 )

        // tuioobj is the blob - see how it is called by request using the blob id?

        // if it is not there remove it from the blobs array.

        // draw the next segment of the line using lineTo and current loc (tuioobj.x, tuioobj.y)

        function updater(e:Event):void {

            for (var i:int = 0; i < blobs.length; i++) {

                var tuioobj:TUIOObject=TUIO.getObjectById(blobs.id);

 

                // if not found, then it must have died..

                if (! tuioobj) {

                    removeBlob(blobs.id);

                } else if (parent != null) {

 

                    lines["line"+blobs.id].graphics.lineTo(tuioobj.x, tuioobj.y);

                }

            }

        }

 

        // when touched, this calls addblob with the blob ID and the X/Y of where it started

        public function downEvent(e:TouchEvent):void {

            var curPt:Point=parent.globalToLocal(new Point(e.stageX,e.stageY));

            addBlob(e.ID, curPt.x, curPt.y);

            e.stopPropagation();

        }

 

        // When a finger stops touching, call removeBlob

        public function upEvent(e:TouchEvent):void {

            removeBlob(e.ID);

            e.stopPropagation();

        }

 

        // This takes the sent ID, x,y and puts it all in the blobs array

        // It then creats a new sprite, and sets the starting loc of the line

        // The line is put in an array called lines, so it can be called over and over by name

        // if the lines did not have unique names you could only draw one line at a time

        // so each line is named in the array after the id of the blob (EG line1280)

        function addBlob(id:Number, origX:Number, origY:Number):void {

            blobs.push( {id: id, origX: origX, origY: origY, myOrigX: x, myOrigY:y} );

 

            var line:Sprite = new Sprite();

            lines["line"+id] = line;

            lines["line"+id].graphics.lineStyle(thickness, color); //<-- config above

            lines["line"+id].graphics.moveTo(origX, origY); //starting point of line to be drawn

            addChild(lines["line"+id]); // add line to stage

        }

 

        // when called, this function removes the blobs from the array

        // cycles through the blobs array until the blob is found by its ID, then it is removed.

        function removeBlob(id:Number):void {

            for (var i=0; i < blobs.length; i++) {

                if (blobs.id==id) {

                    blobs.splice(i, 1);

                    return;

                }

            }

        }

 

    }

}

 

=============================================================================

 

 

 

 

 

 

[教程]图片的缩放和旋转,初学者进

 

multi-touch, actionscript, 多点触摸, flash

最近MTer初学者问我图片缩放怎么写,就写了个简单例子,高手就不要看了,哈。

先说说思想,就是建立一个支持缩放和旋转的容器,然后,把图片装进这个容器,那么图片也就支持缩放和旋转了。

 

1,建立一个MTimage.fla文件,存储在..\touchlib\AS3\int文件夹下。

2,建立一个MTimage.as文件,存储在..\touchlib\AS3\int文件夹下。

3,输入代码:

 

package

{

        import flash.events.TUIO;

        import flash.events.TouchEvent;

        import flash.net.URLRequest;

        import flash.display.Sprite;

        import app.core.action.*;

        import flash.display.Loader;

        public class MTimage extends Sprite

        {

                private var imageContainer:RotatableScalable=new RotatableScalable();//建一个支持缩放和旋转的容器

                private var imageLoaderoader=new Loader();

                public function MTimage()

                {

                        TUIO.init(this,'localhost',3000,'',true);//和mt服务器建立连接

                        

                        init();

                }

                private function init()

                {

                        addChild(imageContainer);

                        imageLoader.load(new URLRequest("image.jpg"));//加载图片

                        imageContainer.addChild(imageLoader);//把图片装进支持缩放和旋转的容器

                }

        }

        

}

4,在.fla文件的文档类输入:MTimage。

5,运行。

0

评论Comments

日志分类
首页[193]
flash As[107]
有的没的[59]
数码照片[4]
自由世界[19]
blender[4]