Archive

Archive for the ‘Flash development’ Category

The first 360|Flex

January 27th, 2010 3 comments

It was Ted Patrick‘s fault. He dared to come to Edmonton in January and I was so impressed with his presentation at EFUG that I registered for the first 360Flex conference which was being held at EBay HQ in SJ. Never been there before. Didn’t know anyone there. Friend and fellow Edmontonian Grant Skinner was going (and presenting) and that gave me confidence that at least I would know someone there (as it turned out, he was quite busy with the Adobe peeps and I didn’t see him much).

Leading up to the conference the buzz on the 360Flex website was to sign up on Twitter. I signed up under the name of “brando”. Remember, this is February 2007. NO ONE knew what Twitter was. Seemed like a useless service to me but it gave me a bunch of new Flex-knowing friends and maybe it would help me connect with some people when I got there. Through twitter I met PolyGeek and told him I was going to hunt him down and say hi.

On the flight to San Jose I met another Edmontonian who was going to the conference: Victor Rubba. Great guy. Now I have another friend to hang out with at the conference.

The morning of the first day I walked from my hotel to EBay and in the main entrance and I couldn’t believe my eyes. Thousands of miles from home, feeling like I was not in Kansas anymore, a guy was standing there with an Edmonton Oilers jersey on. (turns out he was from Calgary, which is ironic to the extreme). I met Tom and John for the first time and they offered me Chocolate cake that Tom’s wife made (nice!). They asked me what my Twitter sig was. They said in unison “Ah, Brando”. While waiting for the keynote I was chatting with some guy who looked really familiar to me. I asked him where he was from and he said San Diego. I shrugged and walked away. Sorry, Josh Tynjala, I was out of touch.

After the first session I was getting Danny Patterson to sign his book on Design Patterns for me when I looked up and saw two smiling faces in front of me. Zach Graves and Aaron King were developers on the Y! Maps team. Because RunningMap.com makes good use of Yahoo! Maps, I was pretty active in the maps online group. I had told them I was coming to the event. They found me first. Now I knew I had someone to hang with. GREAT GUYS. Aaron even gave me his staff issued Y! backpack (at Max 2008 Allen Rabinovich asked me where I got it because they are exclusive to Y! employees).

The food was amazing considering what I paid for the event ($150). I phoned my wife while sitting on the green grass by the ponds of coy and she was extremely jealous. Back home it was -15C˚ with snow up your waist. While chatting with Grant and some other guys I did a double take. “Phillip Kerman?” His was the first Actionscript book I have ever read. Chris Cantrell. Can’t miss Mike Chambers. Victor introduced me to Peter McKiernan who showed up on day two with the same shirt as me. LOL. I did in fact find Dan “PolyGeek” Florio and introduce myself. I didn’t chat with him long because I had to run and pee. Er. RunPee.com.

The presentations were amazing. Ely Greenfield’s was my favourite. Deepa Subramaniam. Mike Chambers. They were all great. I went to a presentation on ANT and the speaker, Joe Berkovitz, asked the audience if they were not using version control. I raised my hand then looked behind me. I was the only one with my hand up. Heh. Still don’t. Just kidding. Maybe not.

Ok, this post has gone on too long already and I think you got the point. Sign up for 360|Flex, San Jose, you will meet a ton of people and have your head filled up until it explodes. It’s the best Flex conference out there so sign up!

Categories: Flash development Tags:

This OSMF has RobotLegs

January 17th, 2010 9 comments

For ActionScript 3 development I have just begun exploring the Open Source Media Framework (OSMF) and the MVC based framework called RobotLegs. What better way than to use them together? The best way to learn this stuff is to dive in and apply it to real solutions. PLEASE leave a comment if I have gone astray.

You can download the source code here (based on OSMF sprint 8 and RobotLegs 1.0.2).

Here is the working proof of concept with video served by Castfire.com:

video swf did not load


Project goals:

  1. Build a production ready video player
  2. Learn OSMF
  3. AS3 only compiled with mxmlc
  4. Keep things organized

1. Build a video player

This is a longer term goal. The video player presented here is only a proof of concept. Video on the web continues to evolve and now seems like a good time to re-factor some key video player projects to bring them up to date and address new requirements.

2. Learn OSMF

Strobe Open Source Media Framework is an Adobe initiative to bring some standards to video player development. I have been itching to get my hands dirty with this new framework to decide for myself if it is worth buying into.

Some may think it is inevitable that OMSF will be over-architechted and therefore full of bloat. I can't really answer that yet. But I can say that I REALLY like the convenience methods that come with the MediaPlayer class. This build is 90k which includes RobotLegs ... acceptable.

Sure, you can build a video player that comes in at 15k. However, as soon as you start adding modern day requirements (CDN services, advert engines, analytics, chapters, xml lists etc) things quickly get complicated. The promise of OSMF is that all these things can be integrated into your video using a plug-in architecture which will greatly ease the burden of development.

3. ActionScript 3 only

Every video player I have worked on to date (other than a few Flex experiments) have been made with Flash Professional which means they need to be compiled from the Flash IDE. Using Flash Builder to compile the application de-couples the workflow from the Flash IDE which makes possible all sorts of interesting ideas.

This does not preclude the use of Flash Professional made libraries that can be used for things like the control bar. After all, the Flash IDE is still really good at some things.

4. Keep things organized

I have made probably a dozen or so custom video players to date. When building one from scratch it does not take tong before it gets complicated: video players are the mothers of all things asynchronous. I have my own particular way of using design patterns and structure but have never took the time to think through a solid framework and ultimately my projects get big enough that they no longer feel like they are on solid ground.

Someone else has thought it through and this is where RobotLegs comes in. I have had a pretty good experience with Cairngorm over the last couple years but it requires the Flex framework. Dependency Injection seems to be the hot topic recently and I have read some good things about RobotLegs so I thought I would give it a try. This video tutorial from John Lindquist helped me to put together this first implementation.

The thought here is that there are other views to manage than just the video player and control bar. RobotLegs will help make these views and OSMF plugins manageable and modular.

Some code

Here are a few classes to show how video player events flow through RobotLegs to the DetailsView so that bytes loaded and playback time can get updated. Download the source for the full meal deal.

Actionscript:
  1. /**
  2. * author: Randy Troppmann January 17, 2010
  3. * http://www.randytroppmann.com
  4. *
  5. * Permission is hereby granted, free of charge, to any person
  6. * obtaining a copy of this software (the "Software"),
  7. * to use the Software without restriction,
  8. * including without limitation the rights to use,
  9. * copy, modify, merge, publish, distribute, sublicense, and/or sell
  10. * copies of the Software, and to permit persons to whom the
  11. * Software is furnished to do so.
  12. *
  13. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  14. * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
  15. * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  16. * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  17. * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  18. * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  19. * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  20. * OTHER DEALINGS IN THE SOFTWARE.
  21. **/
  22.  
  23. package org.osmf.experiments.view{
  24.     import flash.display.Sprite;
  25.     import flash.events.Event;
  26.     import org.osmf.media.URLResource;
  27.     import org.osmf.net.NetLoader;
  28.     import org.osmf.utils.URL;
  29.     import org.osmf.video.VideoElement;
  30.     import org.osmf.display.MediaPlayerSprite;
  31.     import org.osmf.events.*;
  32.     import org.osmf.experiments.controller.MediaPlayerEvent;
  33.     import flash.text.TextField;
  34.     import flash.events.MouseEvent;
  35.    
  36.     public class MediaPlayerView extends Sprite{
  37.        
  38.         public static const TEST_PROGRESSIVE_URL:String = "http://serve.castfire.com/s:pre_post_M9Ow2/video/50082/50082_2009-01-14-235108.flv";
  39.         protected var media:MediaPlayerSprite;
  40.         protected var totalBytes:Number;
  41.         protected var duration:Number;
  42.         protected var currentTime:Number;
  43.         protected var playButton:PlayButton;
  44.         protected var isPlaying:Boolean = false;
  45.        
  46.         public function MediaPlayerView(){
  47.             media = new MediaPlayerSprite();
  48.             media.setAvailableSize(320, 240);
  49.             media.mediaPlayer.autoPlay = false;
  50.             media.mediaPlayer.addEventListener(LoadEvent.BYTES_LOADED_CHANGE, onBytesLoadedChange, false, 0, true);
  51.             media.mediaPlayer.addEventListener(LoadEvent.BYTES_TOTAL_CHANGE, onBytesTotalChange, false, 0, true);         
  52.             media.mediaPlayer.addEventListener( TimeEvent.DURATION_CHANGE, onDurationChange, false, 0, true );
  53.             media.mediaPlayer.addEventListener(TimeEvent.CURRENT_TIME_CHANGE, onPlayheadChange, false, 0, true);
  54.             addChild(media);
  55.             //// ADD PLAY BUTTON
  56.             playButton = new PlayButton();
  57.             addChild(playButton);
  58.             playButton.x = playButton.y = 5;
  59.            
  60.             playButton.addEventListener(MouseEvent.CLICK, handlePlayClick, false, 0, true);
  61.            
  62.         }
  63.        
  64.         public function testProgressive():void{
  65.             media.element = new VideoElement(new NetLoader(), new URLResource(new URL(TEST_PROGRESSIVE_URL)));
  66.         }
  67.        
  68.         protected function handlePlayClick(evt:MouseEvent):void{
  69.             isPlaying = !isPlaying;
  70.             if (isPlaying){
  71.                 media.mediaPlayer.play();
  72.                 playButton.label.text = "pause";
  73.             }
  74.             else{
  75.                 media.mediaPlayer.pause();
  76.                 playButton.label.text = "play";
  77.             }
  78.         }
  79.        
  80.         //// OSMF event methods
  81.         protected function onBytesLoadedChange(evt:LoadEvent):void{
  82.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.BYTES_LOADED_CHANGE);
  83.             mediaEvent.bytes = evt.bytes;
  84.             dispatchEvent(mediaEvent);   
  85.         }
  86.        
  87.         protected function onBytesTotalChange(evt:LoadEvent):void{
  88.             totalBytes = evt.bytes;
  89.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.PLAYER_SENDS_SIZE_CHANGE);
  90.             mediaEvent.bytes = evt.bytes;
  91.             dispatchEvent(mediaEvent);
  92.         }
  93.        
  94.         protected function onDurationChange(evt:TimeEvent):void{
  95.             duration = evt.time;
  96.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.PLAYER_SENDS_DURATION_CHANGE);
  97.             mediaEvent.time = evt.time;
  98.             dispatchEvent(mediaEvent);
  99.         }
  100.        
  101.         protected function onPlayheadChange(evt:TimeEvent):void{
  102.             currentTime = evt.time;
  103.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.PLAYER_SENDS_PLAYHEAD_TIME_CHANGE);
  104.             mediaEvent.time = evt.time;
  105.             dispatchEvent(mediaEvent);
  106.         }
  107.        
  108.     }
  109. }

The MediaPlayerViewMediator class captures the events from MediaPlayerView which sets a property in the model.

Actionscript:
  1. package org.osmf.experiments.view{
  2.     import org.robotlegs.mvcs.Mediator;
  3.     import org.osmf.experiments.model.PlayerModel;
  4.     import org.osmf.events.TimeEvent;
  5.     import org.osmf.experiments.controller.MediaPlayerEvent;
  6.    
  7.     public class MediaPlayerViewMediator extends Mediator{
  8.         [Inject]
  9.         public var mediaPlayerView:MediaPlayerView;
  10.         [Inject]
  11.         public var model:PlayerModel;
  12.        
  13.         override public function onRegister():void{
  14.             mediaPlayerView.addEventListener(MediaPlayerEvent.PLAYER_SENDS_DURATION_CHANGE, handleDurationChange);     
  15.             mediaPlayerView.addEventListener(MediaPlayerEvent.PLAYER_SENDS_PLAYHEAD_TIME_CHANGE, handlePlayheadTimeChange);   
  16.             mediaPlayerView.addEventListener(MediaPlayerEvent.PLAYER_SENDS_SIZE_CHANGE, handleTotalBytesChange);           
  17.             mediaPlayerView.addEventListener(MediaPlayerEvent.BYTES_LOADED_CHANGE, handleBytesLoaded);     
  18.         }
  19.        
  20.         protected function handleDurationChange(p_evt:MediaPlayerEvent):void{
  21.             model.duration = p_evt.time;
  22.         }      
  23.        
  24.         protected function handlePlayheadTimeChange(p_evt:MediaPlayerEvent):void{
  25.             model.currentTime = p_evt.time;
  26.         }
  27.        
  28.         protected function handleTotalBytesChange(p_evt:MediaPlayerEvent):void{
  29.             model.totalBytes = p_evt.bytes;
  30.         }
  31.        
  32.         protected function handleBytesLoaded(p_evt:MediaPlayerEvent):void{
  33.             model.bytesLoaded = p_evt.bytes;
  34.         }
  35.     }
  36. }

The model extends the RobotLegs Actor class can use the RobotLegs dispatch() method so that the event can be listened for from anywhere within the RobotLegs ecosystem.

Actionscript:
  1. package org.osmf.experiments.model{
  2.     import org.robotlegs.mvcs.Actor;
  3.     import org.osmf.experiments.controller.MediaPlayerEvent;
  4.    
  5.     public class PlayerModel extends Actor{
  6.        
  7.         public var _totalBytes:Number;
  8.         public var _bytesLoaded:Number;
  9.         public var _duration:Number;
  10.         public var _currentTime:Number;
  11.        
  12.         public function PlayerModel(){
  13.         }
  14.        
  15.         public function get duration():Number{
  16.             return _duration;
  17.         }
  18.  
  19.         public function set duration(value:Number):void{
  20.             _duration = value;
  21.             var durationEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.DURATION_CHANGE);
  22.             durationEvent.time = duration;
  23.             dispatch(durationEvent);
  24.         }      
  25.  
  26.         public function get currentTime():Number{
  27.             return _currentTime;
  28.         }
  29.  
  30.         public function set currentTime(value:Number):void{
  31.             _currentTime = value;         
  32.             var timeEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.PLAYHEAD_TIME_CHANGE);
  33.             timeEvent.time = value;
  34.             dispatch(timeEvent);
  35.         }
  36.  
  37.         public function get totalBytes():Number{
  38.             return _totalBytes;
  39.         }
  40.  
  41.         public function set totalBytes(value:Number):void{
  42.             _totalBytes = value;       
  43.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.SIZE_CHANGE);
  44.             mediaEvent.bytes = value;
  45.             dispatch(mediaEvent);
  46.         }
  47.  
  48.         public function get bytesLoaded():Number{
  49.             return _bytesLoaded;
  50.         }
  51.  
  52.         public function set bytesLoaded(value:Number):void{
  53.             _bytesLoaded = value;      
  54.             var mediaEvent:MediaPlayerEvent = new MediaPlayerEvent(MediaPlayerEvent.BYTES_LOADED_CHANGE);
  55.             mediaEvent.bytes = value;
  56.             dispatch(mediaEvent);
  57.         }
  58.     }
  59. }

In this experiment, DetailsViewMonitor listens for the events from the model. Since it is injected with the DetailsView instance, it can hit its property setters with new data.

Actionscript:
  1. package org.osmf.experiments.view{
  2.     import org.robotlegs.mvcs.Mediator;
  3.     import org.osmf.experiments.controller.MediaPlayerEvent;
  4.    
  5.     public class DetailsViewMediator extends Mediator   {
  6.        
  7.         [Inject]
  8.         public var detailsView:DetailsView;
  9.        
  10.         override public function onRegister():void{
  11.             eventMap.mapListener(eventDispatcher, MediaPlayerEvent.DURATION_CHANGE, onDurationChange);
  12.             eventMap.mapListener(eventDispatcher, MediaPlayerEvent.PLAYHEAD_TIME_CHANGE, onPlayheadTimeChange);
  13.             eventMap.mapListener(eventDispatcher, MediaPlayerEvent.SIZE_CHANGE, onTotalBytesChange);
  14.             eventMap.mapListener(eventDispatcher, MediaPlayerEvent.BYTES_LOADED_CHANGE, onBytesLoadedChange);
  15.         }
  16.        
  17.         //// EVENT handlers
  18.         protected function onDurationChange(evt:MediaPlayerEvent):void{
  19.             detailsView.duration = evt.time;
  20.         }   
  21.        
  22.         protected function onPlayheadTimeChange(evt:MediaPlayerEvent):void{
  23.             detailsView.currentTime = evt.time;
  24.         }
  25.        
  26.         protected function onTotalBytesChange(evt:MediaPlayerEvent):void{
  27.             detailsView.size = evt.bytes;
  28.         }
  29.        
  30.         protected function onBytesLoadedChange(evt:MediaPlayerEvent):void{
  31.             detailsView.bytesLoaded = evt.bytes;
  32.         }
  33.     }
  34. }

Conclusion

Reading framework documentation makes my eyes bleed. The only way I can really intrinsically understand how they fit into how I build applications is to use them. RobotLegs is a winner. I have not worked with OSMF enough to have an opinion one way or the other ... it has not reached a dot oh release yet.

Categories: Flash development Tags:

Apple Magic Mouse

December 4th, 2009 No comments

I use a MacBook Pro as my main machine. When I am in my office it is plugged into an external monitor and sits on a stand. I use a wired Apple keyboard and an inexpensive wired Logitech mouse. I have tried many different combinations of wired and 'less keyboards and mice and I much prefer wired devices. Batteries problems, connection problems, tracking problems. It would take more than a mighty effort to change my mind.

Then came the bluetooth wireless "Mighty Mouse". Unlike other third party bluetooth mice, it connects quickly and tracks well. I like the little scroll ball (although when it gets dirty it does not work so well). I really don't like the side buttons. There is one fatal flaw with this mouse: the whole body of the mouse is the click mechanism. If you need to lift the mouse because you run out of space, the mouse unclicks. Big problem. That being said, it has worked really well for me as a mouse I keep in my backpack when I am using the MBP away from the office. But, it didn't change my mind.

I am happy to report that Apple's brand spanking new "Magic Mouse" has solved this problem. You hold the mouse by the bottom half of the mouse. This is the single biggest reason I decided to write this blog post. No one is talking about what I think is a great fix to a gargantuan design mistake! Like the Mighty Mouse, the whole mouse is one big button which is a "left click" if your finger is pressing on the left side or "right click" if on the right. Leo Laporte complained on TWIT that this means you have to lift one finger and click with the other. That is the height of lazy! It's a non issue to me.

The design is stunning: it's like they put the Mighty Mouse on a diet. It is thin, sleek, shiny and light. I like the way it fits in my hand because I tend to hold a mouse and move it with my fingers. A mouse that is designed to fit my whole hand "erognomically" forces me to use more of my wrist and arm when mousing, which leads to shoulder pain. The sharp edges of the top take getting used to.

Now the killer feature: 2/3 of the top surface of the mouse is a trackpad. Gone is the scroll ball. With the lightest of touches of a single finger you can scroll a web page up, down left or right. Flick your finger and the window scrolls with momentum that stops immediately when you touch the top of the mouse again. Works brilliantly well. The only multi-finger use is side to side navigation using two fingers. I can see lots of possibilities. For example, click and drag is an ergonomic problem to me. Imagine clicking, release and move your finger to select text. I am sure there are more multitouch features to be added in the future.

Nice design. Tracks well. Connects quickly. Added rechargeable batteries. Magically changed my mind FTW.

UPDATE (25-03-2010): Hold yer horses. My home machine is a unibody MacBook Pro connected to a 23" Cinema display, and the mouse works really well. I made my employer pony up for one to go with my dual quad core Mac Pro and the mouse is terrible! Nothing I did made it any better. It was mousing through molasses particularly when clicking and dragging up at an angle. Shrug. I gave up on it and am looking for another wireless mouse.

Apple Magic Mouse

Apple Magic Mouse

Categories: Flash development Tags:

Displaying elevation with Axiis – example

October 29th, 2009 No comments

Axiis is the open source data visualization framework Tom Gonzalez talked about at Adobe Max earlier this month. Watch his presentation here. At this session Tom announced the release of Beta 1.0 of the library which is built upon Flex 3.

I recently finished and deployed a complete rewrite of the map mashup RunningMap.com which uses Axiis to display elevation data in a line graph. After seeing his presentation 360|Flex last May I decided to give the (then alpha) Axiis framework a try. Upgrading to the Beta 1.0 release was painless and immediately I noticed the drawing performance of the graph went from slow(ish) (which actually was not a bad effect) to instantaneous.

Connecting my data source to the graph was a challenge and I had to use the debugger to get the data wrapped "just right". I put together an example that illustrates:

  • use of Axiis LineSeriesGroup
  • wrapping an array collection "just right" so it can be bound as a data source
  • overlaying the graph on a map
  • setting the data tip using a function

The live example is here which is source view enabled.

Axiis line graph example

Categories: Flash development, Flex development Tags:

Happy inter-national Comic Sans day!

October 1st, 2009 No comments

Comic Sans gets a rough ride. Let's face it. I am joining the chorus of John Wilker's post to say yes! I agree! I think though that this makes it now an international day since my blog comes out of Canada.

Categories: Flash development Tags:

FITC Edmonton discount code

September 13th, 2009 No comments

FITC Edmonton is rolling into town on October 17-18, 2009. If you live anywhere near Edmonton you would be crazy not to attend. The presenter list is stellar: Grant Skinner, Mike Chambers, Erik Natzke, Charles "Chuck" Freeman, Lee Brimelow, Mario Klingermann just to name a few.

Chuck Freeman (Director of Developer Platform at Ribbit) was the lead developer for Maps at Yahoo! back in 2005 and I am hugely in his debt since Runningmap.com uses this API to this day. Mike "Mesh" Chambers. In the Flash world it doesn't get any bigger than that (I am positive that his Halo toon bleeds movieclips when he is shot). I will be seeing if Stacey Mulcahy deserves her self-assigned moniker "bitchwhocodes". Mario and I will discuss the difficulties we suffer in life over having two n's at the end of our last name.

I am a speaker too. Because of that and since you have gotten this far in the post, I can offer you a discount code. Use the code randy20 and you will get 20% off! See you there!!

Categories: Flash development Tags:

AS3 casting String to Number?

July 6th, 2009 1 comment

Converting FlashVars parameters to properties is an example where you are forced to deal with strings and sometimes these values need to be numbers. I have been annoyed with with my own inconsistencies with how I test to see if the FlashVar casts correctly or should be rejected (because it had a character other than a number in the string). I was discovering that some techniques were giving false negatives. So I spent some time of trying to establish a best practice.

I considered these four techniques for casting a string to a Number:

  1. parseInt("1234");
  2. new Number("1234");
  3. "1234" as Number;
  4. Number("1234");

Below is the AS3 code and the trace results which I used to base my conclusions here.

Results:
Using "as Number" to cast a string to a Number looks like bad news to me. All other techniques preformed as expected. Casting a string such as "foo" using "as Number" to cast is to a strongly typed variable results with a false value when isNaN() is applied to it. This is the false negative I mentioned before. Even casting the string "1337" using "as Number" results in the value 0 which not only fails the falsies ternary test but is wrong.

Conclusions

  • don't use "as Number" to cast a string to a Number.
  • Using a "falsies ternary test" is not a great approach for string to number validation since "0" is a valid number and will correctly fail this test. Maybe that works well for your logic anyhow.

Discussion
Casting is perhaps the wrong term since I am converting a primitive to an object which isn't true polymorphism, but perhaps string is being treated as an object.

I talked to Ryan Frishberg at the recent 360|Flex in Indianapolis about this. Ryan works on the Flex SDK team at Adobe. He said that "new Number('foo')" make use of conversion methods that are not available to the technique "'foo' as Number" which will evaluate to null since this casting is not possible. String can't be a Number. Ok, that is the d'oh moment for me. Should know better.

It's problematic though, because it fails to report a run-time or compile-time error.

Actionscript:
  1. var n1a:Number = parseInt("foo");
  2. var n2a:Number = new Number("foo");
  3. var n3a:Number = "foo" as Number;
  4. var n4a:Number = Number("foo");
  5.  
  6. var n1b = parseInt("foo");
  7. var n2b = new Number("foo");
  8. var n3b = "foo" as Number;
  9. var n4b = Number("foo");
  10.  
  11. var n1c:Number = parseInt("1337");
  12. var n2c:Number = new Number("1337");
  13. var n3c:Number = "1337" as Number;
  14. var n4c:Number = Number("1337");
  15.  
  16. trace (".............. strong typed 'foo'");
  17. trace ("n1a: " + n1a);
  18. trace ("n2a: " + n2a);
  19. trace ("n3a: " + n3a);
  20. trace ("n4a: " + n4a);
  21. trace (".............. not strong typed 'foo'");
  22. trace ("n1b: " + n1b);
  23. trace ("n2b: " + n2b);
  24. trace ("n3b: " + n3b);
  25. trace ("n4b: " + n4b);
  26. trace (".............. Strong typed '1337'");
  27. trace ("n1c: " + n1c);
  28. trace ("n2c: " + n2c);
  29. trace ("n3c: " + n3c);
  30. trace ("n4c: " + n4c);
  31. trace (".............. isNaN n1");
  32. trace ("n1a: " + isNaN(n1a));
  33. trace ("n1b: " + isNaN(n1b));
  34. trace ("n1c: " + isNaN(n1c));
  35.  
  36. trace (".............. isNaN n2");
  37. trace ("n2a: " + isNaN(n2a));
  38. trace ("n2b: " + isNaN(n2b));
  39. trace ("n2c: " + isNaN(n2c));
  40.  
  41. trace (".............. isNaN n3");
  42. trace ("n3a: " + isNaN(n3a));
  43. trace ("n3b: " + isNaN(n3b));
  44. trace ("n3c: " + isNaN(n3c));
  45.  
  46. trace (".............. isNaN n4");
  47. trace ("n4a: " + isNaN(n4a));
  48. trace ("n4b: " + isNaN(n4b));
  49. trace ("n4c: " + isNaN(n4c));
  50.  
  51. trace (".............. falsies ternary test");
  52. (n1a)?trace("n1a: true"):trace("n1a: false");
  53. (n2a)?trace("n2a: true"):trace("n2a: false");
  54. (n3a)?trace("n3a: true"):trace("n3a: false");
  55. (n4a)?trace("n4a: true"):trace("n4a: false");
  56.  
  57. (n1b)?trace("n1b: true"):trace("n1b: false");
  58. (n2b)?trace("n2b: true"):trace("n2b: false");
  59. (n3b)?trace("n3b: true"):trace("n3b: false");
  60. (n4b)?trace("n4b: true"):trace("n4b: false");
  61.  
  62. (n1c)?trace("n1c: true"):trace("n1c: false");
  63. (n2c)?trace("n2c: true"):trace("n2c: false");
  64. (n3c)?trace("n3c: true"):trace("n3c: false");
  65. (n4c)?trace("n4c: true"):trace("n4c: false");

CODE:
  1. .............. strong typed 'foo'
  2. n1a: NaN
  3. n2a: NaN
  4. n3a: 0         //unexpected
  5. n4a: NaN
  6. .............. not strong typed 'foo'
  7. n1b: NaN
  8. n2b: NaN
  9. n3b: null    //unexpected
  10. n4b: NaN
  11. .............. Strong typed '1337'
  12. n1c: 1337
  13. n2c: 1337
  14. n3c: 0        //unexpected
  15. n4c: 1337
  16. .............. isNaN test
  17. n1a: true
  18. n2a: true
  19. n3a: false    //unexpected
  20. n4a: true
  21. n1b: true
  22. n2b: true
  23. n3b: false    //unexpected
  24. n4b: true
  25. n1c: false
  26. n2c: false
  27. n3c: false
  28. n4c: false
  29. .............. falsies ternary test
  30. n1a: false
  31. n2a: false
  32. n3a: false
  33. n4a: false
  34. n1b: false
  35. n2b: false
  36. n3b: false
  37. n4b: false
  38. n1c: true
  39. n2c: true
  40. n3c: false    //unexpected
  41. n4c: true

Categories: Flash development, Flex development Tags:

YouTube as HTML5. The end of Flash dominance of video?

May 28th, 2009 5 comments

Google has posted a proof of concept showing YouTube using HTML 5.

http://www.youtube.com/html5

I was able to view this with Safari. You will note that there is no Flash on this page. Apparently the video tag uses system video resources so if you previously installed a h.264 codec, it should just work. The controls are all HTML. Does this mean the end to dominance of Flash delivered video on the web?

Categories: Flash development Tags:

Encryption and licensing with Nitro-LM

May 27th, 2009 2 comments

I recently attended a 3-day "entrepreneur bootcamp" where angel investors taught how to pitch an idea to angel investors for investment capital. One of the first things they will want to know is how you protect your intellectual property. In the case of software, protection of algorithms is key and in the case of Flex your software secrets are protected from a right click "view source" since the application is contained within a compiled swf. Tools are available, however, that allow you to easily decompile the swf and look at the goodies inside.

Simplified Logic Inc has a product that uses a private key encryption method that stops decompilation of the swf. They also have developed a backend system that can manage licenses to your application. I have been developing a Flex application for use in teaching anatomy to students at the technical institute I work at. It has proven to be a powerful tool and there is opportunity to license this application to other institutions, but there is no infrastructure to do this. I have built a proof of concept using Nitro-LM to show that we can deploy this application on the web using a Software as a Service model without creating much of a deployment infrastructure on our end beyond what we already have in place.

The NitroAdmin AIR app is used to set up and manage the encryption and licenses. Videos and examples show how to integrate the system into your Flex app but I think they need to do a bit more work around this ... perhaps a "wizard" or video that shows from start to finish the basic setup. It still took a bit of handholding to get me up and running (thanks Andrew). The proof of concept is doing its job of proving this works in a way that is unobtrusive to users. Now all that is left is the easy part: to build a business model around my application and then go out and sell it. That is someone else's job.

Simplified Logic was a major sponsor of the recent 360 Flex conference in Indianapolis. I want to say thanks to them for supporting this event. It was a good one and I enjoyed the environs.

Categories: Flash development, Flex development Tags:

FITC Edmonton 2009

May 8th, 2009 No comments

That's right. FITC has announced that they are bringing their conference to Edmonton, Alberta, Canada on October 17-18, 2009. This is the city where Grant Skinner and Co. hail from and Grant has pulled in a lot of favours to get some GREAT speakers to come in for the event. It is also the city that I live in, and Grant has asked me to do a presentation as well. Edmonton has a very active Flash user base which is supported by Michael Graves' great work with EFUG.I have it marked on my calendar already ... it's going to be a good one. I think he is going to bill this as one big mofo of an EFUG meeting.

Categories: Flash development Tags: