Cover Flow Effect supported by Keyboard in Flex

music-family-win If you like Apple/iPod, I think you will like the iTunes styled "cover flow".We can do it in Flex/Flash by the Flex CoverFlow component(http://dougmccune.com/blog/2007/11/19/flex-coverflow-performance-improvement-flex-carousel-component-and-vertical-coverflow/) or isplayShelf Component (http://www.quietlyscheming.com/blog/components/tutorial-displayshelf-component/) or Flash iTunes Cover Flow (http://www.weberdesignlabs.com/blog/?p=10) etc. Following is another to do the same, keyboard support.

Search-256x256 Demo | DownloadDownload Full Project


Following is mxml source code:

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="init()" creationCompleteEffect="fadeOut" viewSourceURL="srcview/index.html">
  3.     <mx:Script>
  4.         <![CDATA[
  5.             import mx.states.AddChild;
  6.             import mx.controls.Image;
  7.             import mx.controls.Alert;
  8.             import mx.events.*;
  9.             import keymet.effect.SleekMove;
  10.             import mx.effects.easing.*;
  11.            
  12.             public var img:Array;
  13.             public var sm:SleekMove;
  14.             function init():void
  15.             {
  16.                 var i:int;
  17.                 var tmp:Image;
  18.                 img = new Array();
  19.                 foc.setFocus();
  20.                 for (i= 0; i<= 9 ;i++)
  21.                 {
  22.                     tmp = new Image();
  23.                     tmp.source= "pic/p"+(i+1).toString()+".jpg";
  24.                     img[i] = tmp;
  25.                     addChild(img[i]);
  26.                 }
  27.                 addEventListener(KeyboardEvent.KEY_UP,keyup);
  28.                 /* create cover flow effect object */
  29.                 sm = new SleekMove();
  30.                 /* init object:
  31.                 function init(img:Array,imgW:int,imgH:int,imgSpace:int=50,offsetX:int=0,offsetY:int=0,zoomInPer:Number=.6):void
  32.                 img Image object array
  33.                 imgH image's height
  34.                 imgW image's width
  35.                 imgSpace
  36.                 offsetX
  37.                 offsetY
  38.                 zoomInPer
  39.                 */
  40.                 sm.init(img,160,200,30,100,200,0.7);                               
  41.             }
  42.             function keyup(event:KeyboardEvent):void{
  43.                 if (event.keyCode == 37)
  44.                     sm.pressLeft();
  45.                 if (event.keyCode == 39)
  46.                     sm.pressRight();
  47.             }
  48.            
  49.             function keysel():void
  50.             {
  51.                 Alert.show(sm.getSelected().toString());
  52.             }
  53.         ]]>
  54.     </mx:Script>
  55.     <mx:Fade id="fadeOut" duration="1000" alphaFrom="0" alphaTo="1"/>
  56.    
  57.     <mx:Button id="foc" x="232" y="495" label="GetSelected" click="keysel()"/>
  58.    
  59. </mx:Application>

Following is as source code:

  1. package keymet.effect
  2. {
  3.     import mx.controls.Image;
  4.     import mx.events.EffectEvent;
  5.     import mx.effects.easing.*;
  6.    
  7.     public class SleekMove
  8.     {
  9.         import mx.controls.Alert;
  10.         import mx.effects.*;
  11.        
  12.         private var imgW:int;
  13.         private var imgH:int;
  14.         private var imgSpace:int;
  15.         private var offsetX:int;
  16.         private var offsetY:int;
  17.         private var zoomInPer:Number;
  18.         private var img:Array;
  19.         private var total:int;
  20.         private var cur5:Array;
  21.         private var x5:Array;
  22.         private var y5:Array;
  23.         private var yOffsetDiv:int;
  24.         private var curIndex:int = 0;
  25.         public function SleekMove()
  26.         {
  27.            
  28.         }
  29.        
  30.         public function init(img:Array,imgW:int,imgH:int,imgSpace:int=50,offsetX:int=0,offsetY:int=0,zoomInPer:Number=.6):void
  31.         {
  32.             this.img = img;
  33.             this.imgW = imgW;
  34.             this.imgH = imgH;
  35.             this.imgSpace = imgSpace;
  36.             this.offsetX = offsetX;
  37.             this.offsetY = offsetY;
  38.             this.zoomInPer = zoomInPer;
  39.             total = img.length;
  40.             cur5 = new Array(5);
  41.             //Alert.show(img.length.toString());
  42.             caleXY();
  43.             putImgArray();
  44.             createEffect();
  45.         }
  46.         private function caleXY():void
  47.         {
  48.             yOffsetDiv = int((imgH - int(imgH*zoomInPer))/2);
  49.  
  50.             x5 = new Array(5);
  51.             y5 = new Array(5);
  52.             x5[0] = offsetX;
  53.             x5[1] = x5[0] + int(imgW*zoomInPer) + imgSpace;
  54.             x5[2] = x5[1] + int(imgW*zoomInPer) + imgSpace;
  55.             x5[3] = x5[2] + imgW + imgSpace;
  56.             x5[4] = x5[3] + int(imgW*zoomInPer) + imgSpace;
  57.            
  58.             y5[0] = offsetY;
  59.             y5[1] = offsetY;
  60.             y5[2] = offsetY - yOffsetDiv;
  61.             y5[3] = offsetY;
  62.             y5[4] = offsetY;
  63.         }
  64.        
  65.         private function putImgArray():void
  66.         {
  67.             var i:int;
  68.             var tmp:Image;
  69.             for (i =0 ;i < total;i++)
  70.             {
  71.                 tmp = img[i] as Image;
  72.                 tmp.width = imgW;
  73.                 tmp.height = imgH;
  74.                 tmp.scaleX = zoomInPer;
  75.                 tmp.scaleY = zoomInPer;
  76.                 tmp.visible = false;
  77.             }
  78.            
  79.             for (i =0 ;i < 5;i++)
  80.             {
  81.                 cur5[i] = img[i];
  82.                 tmp = cur5[i] as Image;
  83.                 tmp.x = x5[i];
  84.                 tmp.y = y5[i];
  85.                 if (i == 2)
  86.                 {
  87.                     tmp.scaleX = 1;
  88.                     tmp.scaleY = 1;
  89.                 }
  90.                 tmp.visible = true;
  91.             }
  92.            
  93.         }
  94.         private var duration:int = 1000;
  95.         private var par_left:Parallel;
  96.         private var move_left1:Move;
  97.         private var move_left2:Move;
  98.         private var move_left3:Move;
  99.         private var par_right:Parallel;
  100.         private var move_right1:Move;
  101.         private var move_right2:Move;
  102.         private var move_right3:Move;
  103.         private var fadein:Fade;
  104.         private var fadeout:Fade;
  105.         private var apinX:AnimateProperty;
  106.         private var apinY:AnimateProperty;
  107.         private var apoutX:AnimateProperty;
  108.         private var apoutY:AnimateProperty;
  109.         private var stateInEffect:Boolean = false;
  110.         public function createEffect():void
  111.         {
  112.             move_left1 = new Move();
  113.             move_left1.xBy = -1 * (imgSpace + imgW * zoomInPer);
  114.             move_left1.duration = duration;
  115.             move_left2 = new Move();
  116.             move_left2.xBy = -1 * (imgSpace + imgW * zoomInPer);
  117.             move_left2.yBy = yOffsetDiv;
  118.             move_left2.duration = duration;
  119.             move_left3 = new Move();
  120.             move_left3.xBy = -1 * (imgSpace + imgW);
  121.             move_left3.yBy = -1 * yOffsetDiv;
  122.             move_left3.duration = duration;
  123.            
  124.             fadein = new Fade();
  125.             fadein.alphaFrom = 0.0;
  126.             fadein.alphaTo = 1.0;
  127.             fadein.duration = duration;
  128.            
  129.             fadeout = new Fade();
  130.             fadeout.alphaFrom = 1.0;
  131.             fadeout.alphaTo = 0.0;
  132.             fadeout.duration = duration;
  133.            
  134.             apinX = new AnimateProperty();
  135.             apinX.property = "scaleX";
  136.             apinX.fromValue = 1.0;
  137.             apinX.toValue = zoomInPer;
  138.            
  139.             apinY = new AnimateProperty();
  140.             apinY.property = "scaleY";
  141.             apinY.fromValue = 1.0;
  142.             apinY.toValue = zoomInPer;
  143.            
  144.             apoutX = new AnimateProperty();
  145.             apoutX.property = "scaleX";
  146.             apoutX.fromValue = zoomInPer;
  147.             apoutX.toValue = 1.0;
  148.            
  149.             apoutY = new AnimateProperty();
  150.             apoutY.property = "scaleY";
  151.             apoutY.fromValue = zoomInPer;
  152.             apoutY.toValue = 1.0;
  153.            
  154.             par_left = new Parallel();
  155.             par_left.addChild(move_left1);
  156.             par_left.addChild(move_left2);
  157.             par_left.addChild(move_left3);
  158.             par_left.addChild(fadeout);
  159.             par_left.addChild(fadein);
  160.             par_left.addChild(apinX);
  161.             par_left.addChild(apinY);
  162.             par_left.addChild(apoutX);
  163.             par_left.addChild(apoutY);
  164.            
  165.             move_right1 = new Move();
  166.             move_right1.xBy = imgSpace + imgW * zoomInPer;
  167.             move_right1.duration = duration;
  168.             move_right2 = new Move();
  169.             move_right2.xBy = imgSpace + imgW;
  170.             move_right2.yBy = yOffsetDiv;
  171.             move_right2.duration = duration;
  172.             move_right3 = new Move();
  173.             move_right3.xBy = imgSpace + imgW * zoomInPer;
  174.             move_right3.yBy = -1 * yOffsetDiv;
  175.             move_right3.duration = duration;
  176.            
  177.             par_right = new Parallel();
  178.             par_right.addChild(move_right1);
  179.             par_right.addChild(move_right2);
  180.             par_right.addChild(move_right3);
  181.             par_right.addChild(fadeout);
  182.             par_right.addChild(fadein);
  183.             par_right.addChild(apinX);
  184.             par_right.addChild(apinY);
  185.             par_right.addChild(apoutX);
  186.             par_right.addChild(apoutY);
  187.            
  188.             par_left.addEventListener(EffectEvent.EFFECT_START,effect_start);
  189.             par_left.addEventListener(EffectEvent.EFFECT_END,effect_end);
  190.             par_right.addEventListener(EffectEvent.EFFECT_START,effect_start);
  191.             par_right.addEventListener(EffectEvent.EFFECT_END,effect_end);
  192.         }
  193.        
  194.         private function effect_start(event:EffectEvent):void
  195.         {
  196.             stateInEffect = true;
  197.         }
  198.         private function effect_end(event:EffectEvent):void
  199.         {
  200.             stateInEffect = false;
  201.         }
  202.        
  203.         private function getCycIndex(indexadd:int):int
  204.         {
  205.             var tmp:int;
  206.             if (indexadd >= total)
  207.                 return indexadd%total;
  208.             tmp = indexadd;
  209.             while(tmp < 0)
  210.                 tmp += total;
  211.             return tmp;
  212.         }
  213.        
  214.         private function updateCur5():void
  215.         {
  216.             var i:int;
  217.             for (i = 0; i < 5; i++)
  218.             {
  219.                 cur5[i] = img[getCycIndex(curIndex + i)];
  220.             }
  221.         }
  222.         private function putLeftEffectBeforeAction():void
  223.         {
  224.             var newimg:Image = img[getCycIndex(curIndex + 5)];
  225.             newimg.visible = true;
  226.             //Alert.show(getCycIndex(curIndex + 5).toString());
  227.             fadeout.target = cur5[0];
  228.             move_left1.targets = new Array(cur5[1],cur5[4]);
  229.             move_left2.target = cur5[2];
  230.             move_left3.target = cur5[3];
  231.             fadein.target = newimg;
  232.             newimg.x = x5[4];
  233.             newimg.y = y5[4];
  234.             apinX.target = cur5[2];
  235.             apinY.target = cur5[2];
  236.             apoutX.target = cur5[3];
  237.             apoutY.target = cur5[3];
  238.         }
  239.        
  240.         private function putRightEffectBeforeAction():void
  241.         {
  242.             var newimg:Image = img[getCycIndex(curIndex - 1)];
  243.             newimg.visible = true;
  244.             fadeout.target = cur5[4];
  245.             move_right1.targets = new Array(cur5[0],cur5[3]);
  246.             move_right2.target = cur5[2];
  247.             move_right3.target = cur5[1];
  248.             fadein.target = newimg;
  249.             newimg.x = x5[0];
  250.             newimg.y = y5[0];
  251.             apinX.target = cur5[2];
  252.             apinY.target = cur5[2];
  253.             apoutX.target = cur5[1];
  254.             apoutY.target = cur5[1];
  255.         }
  256.        
  257.         public function pressLeft():void
  258.         {
  259.             if (stateInEffect)
  260.                 return;
  261.             putLeftEffectBeforeAction();
  262.             curIndex = getCycIndex(curIndex + 1);
  263.             par_left.play();           
  264.             updateCur5();
  265.         }
  266.         public function pressRight():void
  267.         {
  268.             if (stateInEffect)
  269.                 return;
  270.             putRightEffectBeforeAction();
  271.             curIndex = getCycIndex(curIndex - 1);
  272.             par_right.play();           
  273.             updateCur5();
  274.         }
  275.        
  276.         public function getSelected():int
  277.         {
  278.             return getCycIndex(curIndex + 2);
  279.         }
  280.        
  281.         public function setEasingFun(val:Function):void
  282.         {
  283.             move_left1.easingFunction = val;
  284.             move_left2.easingFunction = val;
  285.             move_left3.easingFunction = val;
  286.             move_right1.easingFunction = val;
  287.             move_right2.easingFunction = val;
  288.             move_right3.easingFunction = val;
  289.         }
  290.     }
  291. }
Share and Enjoy:
  • Digg
  • del.icio.us
  • Facebook
  • Google Bookmarks
  • DZone
  • Reddit
  • Technorati
  • StumbleUpon
  • Twitter
RSS Enjoy this Post? Subscribe to Ntt.cc

RSS Feed   RSS Feed     Email Feed  Email Feed
You can leave a response, or trackback from your own site.

9 Responses to “Cover Flow Effect supported by Keyboard in Flex”

  1. hi… you have dead links on Demo and Download Project..

    just to inform! :)

    Congrats to the blog, it’s my mandatory stop on ria’s subject !

  2. Ntt.cc says:

    Thanks, Mário Santos
    It seems some data were lost when Godaddy update my hosting account.
    I will fixed it later.
    Thanks again, Mário Santos. :)

  3. [...] 在Cover Flow Effect supported by Keyboard in Flex中介绍过翻转效果的实现,lemlinh.com发布了一款更加Cool的Flash模板,非常实用。有兴趣地可以看看。 [...]

  4. [...] “FishEye”和“cover flow”貌似会搅和在一起,让人头晕。。。当然,还有时候我们称之为“Dock Menu”……反正不管怎么称呼,就是这么一种效果。在Cover Flow Effect supported by Keyboard in Flex中我们可以看到如何用键盘来实现这种移动的效果。而在利用ComponentOne组件快速实现鱼眼菜单(Dock Menu)中,我们也可以看到利用ComponentOne来实现。下面是另外一款类似的组件,不同的是它还可以实现1D,2D的效果。让人感觉有立体感。 [...]

  5. [...] Flow” or “Dock Menu”. Ok, no matter what you call it, it is just a effect. In Cover Flow Effect supported by Keyboard in Flex we knew how to realize the move effect by keyboard. In Create Fish Eye Menu Fastly by ComponentOne [...]

  6. [...] 所谓的Crousel效果,其实就是控制图片在图片集中旋转。和我们前面介绍的Cover Flow Effect supported by Keyboard in Flex,一款很Cool的Fisheye组件以及利用ComponentOne组件快速实现鱼眼菜单(Dock Menu)都比较类似。不过下面的代码,不仅可以横向转动,还可以是竖直方向的。下面是Demo和代码: [...]

  7. [...] This function maybe is similar with these which have been introduced in following articles  Cover Flow Effect supported by Keyboard in Flex, A So Cool Fisheye Component,Create Fish Eye Menu Fastly by ComponentOne. But it could rotate not [...]

  8. runbao says:

    This is good!
    Thanks to share!

  9. amosta says:

    Hi, very nice effect – and unobtrusive – and I recommend a photoeffect application with cool features.

Leave a Reply