eMusic Picks for November 07

October 31st, 2007

I haven’t been keeping up with this but I’ll try from now on!

Clorox Girls - Jaime Les Filles (thanks to Plan Nine Rock Show)
Beth Hirsch - Titles & Idols (thanks to Dave’s Lounge)
Beth Hirsch - Life Is Mine
Beth Hirsch - P-Town Rubies
Beirut - The Flying Club Cub (thanks to Criminal Records)
Of Montreal - Hissing Fauna, Are You The Destroyer?
Thom Yorke - The Eraser
The Octopus Project - Hello Avalanche
Shriekback - Care, Tench And Related Tracks
Lene Lovich - Shadows and Dust (First Four Tracks)

August 07 eMusic Picks

August 4th, 2007

Chromeo - Fancy Footwork Remixes
Josh Rouse - Country Mouse, City House
The Long Blondes - Somone To Drive You Home
Manchester Orchestra - You Brainstorm, I Brainstorm….
Rasputina - Oh Perilous World
Spoon - Ga Ga Ga Ga Ga
St. Vincent - Marry Me
Stars - In Our Bedroom After the War
Stars - Set Yourself On Fire

To the Mile High City!

May 30th, 2007

My goal of moving toward more app-centric development has come true! I’m moving to Denver for at least six months to take on a contract to hire opportunity. The adventure for me and new partner in crime Donnie begins tomorrow!

Things have been super stressful with me trying to get ready to move while working marathon hours but the time is here. I’m soooo ready to start this next step in my life! Thanks to all of my family and friends who have helped me out during the last few months of enormous change - you know who you are!

Shame on You, Atlanta Sports Media

April 15th, 2007

I’m watching the Sunday sports final show on WSB television and what do they start the show with? Early season Braves baseball. WTF!?! Moose had a career game on Saturday and well, this town’s media could care less. It’s a load of crap. Who made the playoffs this season? Not the Braves. The Thrashers. Thank God for the fans.

Stooges LIVE at SXSW on NPR, Friday at 2:00 PM!

March 15th, 2007

Heard a blurb this morning on Morning Edition about SXSW and thought I’d check out the NPR website. Well they have full coverage including full days of streaming audio. One to note: The Stooges will be playing Friday at 2:00 PM!

ActionScript Coder for Hire!

February 7th, 2007

As of February, I am on the market for work coding Flash. I am well versed in AS2 and currently working on picking up AS3. I am looking for full time work but I will be glad to take contract as well. I have worked on sites such as:

whiteboard.ups.com
www.vwfeatures.com (GTI Joyride)
www.gptimemachine.com
onehundred.genworth.com
www.freedomoftheseas.com

I currently live in the Atlanta area.

If you are interested, contact me: brentpub [at] darbymedia {dot} com.

IE, Local Playback, FLVs and Querystrings

January 29th, 2007

I had a problem today with a Flash site converted to playback on CD-ROM where it would work fine in Firefox but FLV content would not playback in IE.

It turns out that for the web version if bandwidth had not been detected and tracked that I was appending a ?nocache=[random number] to the filename in order to make sure that the file would load even if cached. On the CD-ROM (or running directly from the hard drive) this would cause a “stream not found” error. Disabling this so that a querystring was not used solved my problem.

Receiving Object Data With .NET/Fluorine/Flex

January 22nd, 2007

So I went through the very basics last time, and while I'm gonna keep it simple, I'm not gonna do a newbie style step-by-step like I did before. For this tutorial I'm going to create a little media library sample for you to work with to show how typed object data can be received via Fluorine.

To start out, download and install the latest version of the Fluorine Gateway. Zoli made some upates since my last posting that will allow your program to run on a shared hosting website. Worked for my last sample anyway. This also goes to show that the folks at The Silent Group are extremely helpful when issues arise with Fluorine. I don't think the guy sleeps.

Setting up the project folder structure
Start out by setting up a project folder structure by creating a master project folder with a Dot Net and a Flex folder in it. Mine is D:\Projects\Flex\Fluorine Flex 2.

Setting up the Visual Studio project
This time we'll use the new Fluorine ASP.NET Web Application template. Fire up Visual Studio and create a new web site project. Select the Fluorine template and set up a virtual web directory that points to the project folder's Dot Net folder. For me it's http://localhost/fluorineflex2/. If you tried the last tutorial, you'll quickly figure out that this template saves you a LOT of steps. Once you've created the project, you only have to do one thing to configure Fluorine.

Configuring the Fluorine Gateway in Visual Studio
Open the WEB-INF/flex/services-config.xml file and modify the endpoint node to point to the virtual web directory location of Gateway.aspx. In my case it was http://localhost/fluorineflex2/Gateway.aspx. You should be able to copy and paste this url into a browser and a blank page should load without any error messages.

UPDATE
I was not aware of this, but I recieved an email from Zoli at The Silent Group and he notified me that the uri attribute does not have to change as long as the context root remains the same on the server you are deploying to. In this case if I'm developing on http://localhost/fluorineflex2/Gateway.aspx, and deploying to http://www.darbymedia.com/fluorineflex2/Gateway.aspx, then I can leave the uri attribute as it's default: http://{server.name}:{server.port}/{context.root}/Gateway.aspx. You should still however be able to copy and past the actual URL of the Gateway.aspx file and the blank page should load without any errors. It's a quick way to check for issues if you are not getting the results you want.

Setting up the Flex project
Start Flex Builder 2 and create a new Flash Data Service Project with the Root folder pointing to the Dot Net folder of your project directory (D:\Projects\Flex\Fluorine Flex 2\Dot Net) and the Root URL pointing to the virtual web directory for the Visual Studio project (http://localhost/fluorineflex2/). The Context root should be the final bit of the virtual web path (/fluorineflex2). Enter the project name (fluorineflex2) and use the Flex directory of your project folder as the location of your Flex project files (D:\Projects\Flex\Fluorine Flex 2).

If you need help with any of the stuff above please check out the previous tutorial.

Creating a C# compact disc value object class
To start out we'll need a value object on the server side to pass back to Flex when requested. Let's create a class called CompactDiscVO that has the properties, artist, title, and year.

C#:
  1. using System;
  2.  
  3. namespace com.darbymedia.medialibrary.vo
  4. {
  5.     public class CompactDiscVO
  6.     {
  7.         public string artist;
  8.         public string title;
  9.         public string year;
  10.  
  11.         public CompactDiscVO(){}
  12.     }
  13. }

Creating a Fluorine Gateway service class
To start out, create a basic service that you can point to with your Flex RemoteObject. We'll also include a method called getCDVO that will instantiate and return a CompactDiscVO object.

C#:
  1. using System;
  2. using System.Web;
  3. using com.darbymedia.medialibrary.vo;
  4.  
  5. namespace com.darbymedia.medialibrary.service
  6. {
  7.     public class MediaLibraryService
  8.     {
  9.         public MediaLibraryService() { }
  10.  
  11.         public CompactDiscVO getCDVO()
  12.         {
  13.             CompactDiscVO cd = new CompactDiscVO();
  14.  
  15.             cd.artist = "Redd Kross";
  16.             cd.title = "Third Eye";
  17.             cd.year = "1990";
  18.  
  19.             return cd;
  20.         }
  21.     }
  22. }

Now we can move on to Flex Builder.

Creating a corresponding Actionscript compact disc value object
In Flex Builder 2 create a CompactDiscVO class. I've added a toString() method for demonstration purposes (good for debugging too!). Note that the namespace/package path and class name are the same. This is not absolutely necessary but makes sense here.

ACTIONSCRIPT:
  1. package com.darbymedia.medialibrary.vo
  2. {   
  3.     public class CompactDiscVO extends Object
  4.     {   
  5.         public var artist:String;
  6.         public var title:String;
  7.         public var year:String;
  8.        
  9.         public function CompactDiscVO(){}
  10.        
  11.         public function toString():String
  12.         {
  13.             var s:String = "[CompactDiscVO]"
  14.            
  15.             s += "\nArtist: " + artist;
  16.             s += "\nTitle: " + title;
  17.             s += "\nYear: " + year;
  18.            
  19.             return s;
  20.         }
  21.     }
  22. }

Building the main MXML application file
This time I've decided to use Actionscript only for my RemoteObject file. This way you can compare with the previous tutorial which used an MXML RemoteObject if you want. On creationComplete, the initApp() method instantiates the remote object with the destination, which is the destination name used in the services-config.xml file, the source, which is the namespace and class path of the C# service class we created, and listeners for result and fault events. Here is the MXML:

XML:
  1. <?xml version="1.0" encoding="utf-8"?>
  2. <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="initApp()">
  3.     <mx:Script>
  4.         <![CDATA[
  5.             import com.darbymedia.medialibrary.vo.CompactDiscVO;
  6.             import mx.rpc.events.FaultEvent;
  7.             import mx.rpc.events.ResultEvent;
  8.             import mx.rpc.remoting.RemoteObject;
  9.            
  10.             private var ro:RemoteObject;
  11.            
  12.             private function initApp():void
  13.             {
  14.                 ro = new RemoteObject();
  15.                 ro.destination = "fluorine";
  16.                 ro.source = "com.darbymedia.medialibrary.service.MediaLibraryService";
  17.                 ro.addEventListener(ResultEvent.RESULT, roResult);
  18.                 ro.addEventListener(FaultEvent.FAULT, roFault); 
  19.                 ro.getCDVO();
  20.             }
  21.            
  22.             private function roResult(event:ResultEvent):void
  23.             {
  24.                 trace(event.result);
  25.                 trace(event.result.artist);
  26.                 var cd:CompactDiscVO = event.result as CompactDiscVO;
  27.                 trace(cd);
  28.             }
  29.            
  30.             private function roFault(event:FaultEvent):void
  31.             {
  32.                 trace("roFault(event)");
  33.                 trace(event.fault.faultCode);
  34.                 trace(event.fault.faultString);
  35.                 trace(event.fault.faultDetail);
  36.             }
  37.         ]]>
  38.     </mx:Script>
  39. </mx:Application>

At this point we're calling the getCDVO method on the service immediately. roResult will trace out information to the console when run in debug mode. Go ahead and do that and you'll get the following:

[SWF] /fluorineflex2/fluorineflex2/FluorineFlex2-debug.swf - 628,788 bytes after decompression
[object Object]
Redd Kross
null

Interesting. In roResult, our first trace of event.result gives us [object Object] so obviously we're getting an Object type, but our CompactDiscVO.toString() method is not kicking in. Our second trace of the event.result.artist property, Redd Kross, shows that our data came through but when we try to put it into a typed variable as CompactDiscVO for our third trace we get null. So we are getting data back but it's not typed correctly. It's just a generic Object with properties.

To force the correct mapping you have use the flash.net.registerClassAlias() method. You pass it the full namespace and class name of the server side class as a string and the Actionscript class you want it to map to, like so:

flash.net.registerClassAlias("com.darbymedia.medialibrary.vo.CompactDiscVO", CompactDiscVO);

I put this in the initApp() method.

Now our MXML looks like this:

XML:
  1. <?xml version="1.0" encoding="utf-8"?>
  2. <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="initApp()">
  3.     <mx:Script>
  4.         <![CDATA[
  5.             import com.darbymedia.medialibrary.vo.CompactDiscVO;
  6.             import mx.rpc.events.FaultEvent;
  7.             import mx.rpc.events.ResultEvent;
  8.             import mx.rpc.remoting.RemoteObject;
  9.             import flash.net.registerClassAlias;
  10.            
  11.             private var ro:RemoteObject;
  12.            
  13.             private function initApp():void
  14.             {
  15.                 flash.net.registerClassAlias("com.darbymedia.medialibrary.vo.CompactDiscVO", CompactDiscVO);
  16.                
  17.                 ro = new RemoteObject();
  18.                 ro.destination = "fluorine";
  19.                 ro.source = "com.darbymedia.medialibrary.service.MediaLibraryService";
  20.                 ro.addEventListener(ResultEvent.RESULT, roResult);
  21.                 ro.addEventListener(FaultEvent.FAULT, roFault); 
  22.                 ro.getCDVO();
  23.             }
  24.            
  25.             private function roResult(event:ResultEvent):void
  26.             {
  27.                 trace(event.result);
  28.                 trace(event.result.artist);
  29.                 var cd:CompactDiscVO = event.result as CompactDiscVO;
  30.                 trace(cd);
  31.             }
  32.            
  33.             private function roFault(event:FaultEvent):void
  34.             {
  35.                 trace("roFault(event)");
  36.                 trace(event.fault.faultCode);
  37.                 trace(event.fault.faultString);
  38.                 trace(event.fault.faultDetail);
  39.             }
  40.         ]]>
  41.     </mx:Script>
  42. </mx:Application>

Run this in debug mode and you can see that our first trace of event.result gives us the toString() output of the CompactDiscVO class, our second trace of event.result.artist gives us Redd Kross, and our third trace of the typed variable, cd, prints out not null, but the toString() output as well! Pretty cool!

Doing something with the content
Now let's put this data into display items. I've added some labels and input fields to hold the data, a button to trigger the return, and an alert for any faults. I've put the call to the remote object's getCDVO in the button's click handler this time. Check it out:

XML:
  1. <?xml version="1.0" encoding="utf-8"?>
  2. <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="initApp()">
  3.     <mx:Script>
  4.         <![CDATA[
  5.             import mx.controls.Alert;
  6.             import flash.net.registerClassAlias;
  7.             import com.darbymedia.medialibrary.vo.CompactDiscVO;
  8.             import mx.rpc.events.FaultEvent;
  9.             import mx.rpc.events.ResultEvent;
  10.             import mx.rpc.remoting.RemoteObject;
  11.            
  12.             private var ro:RemoteObject;
  13.            
  14.             private function initApp():void
  15.             {
  16.                 flash.net.registerClassAlias("com.darbymedia.medialibrary.vo.CompactDiscVO", CompactDiscVO);
  17.            
  18.                 ro = new RemoteObject();
  19.                 ro.destination = "fluorine";
  20.                 ro.source = "com.darbymedia.medialibrary.service.MediaLibraryService";
  21.                 ro.addEventListener(ResultEvent.RESULT, roResult);
  22.                 ro.addEventListener(FaultEvent.FAULT, roFault); 
  23.             }
  24.            
  25.             private function btnGet_Click(event:Event):void
  26.             {
  27.                 ro.getCDVO();
  28.             }
  29.            
  30.            
  31.             private function roResult(event:ResultEvent):void
  32.             {
  33.                 var cd:CompactDiscVO = event.result as CompactDiscVO;
  34.                 txtArtist.text = cd.artist;
  35.                 txtTitle.text = cd.title;
  36.                 txtYear.text = cd.year;
  37.             }
  38.            
  39.             private function roFault(event:FaultEvent):void
  40.             {
  41.                 trace("roFault(event)");
  42.                 trace(event.fault.faultCode);
  43.                 trace(event.fault.faultString);
  44.                 trace(event.fault.faultDetail);
  45.                
  46.                 Alert.show(event.fault.faultDetail,"Fault Event");
  47.             }
  48.            
  49.         ]]>
  50.     </mx:Script>
  51.    
  52.     <mx:Label text="Compact Disc" x="10" y="10"/>
  53.     <mx:Label text="Artist:" x="10" y="35"/>
  54.     <mx:TextInput x="56" y="35" id="txtArtist"/>
  55.     <mx:Label text="Title:" x="10" y="70"/>
  56.     <mx:TextInput x="56" y="70" id="txtTitle"/>
  57.     <mx:Label x="10" y="105" text="Year:"/>
  58.     <mx:TextInput x="56" y="105" id="txtYear"/>
  59.     <mx:Button x="140" y="135" label="Get Data" id="btnGet" click="btnGet_Click(event)"/>
  60. </mx:Application>

Check it out here. Sending is easy...next time we'll do that.

How to Set Up .NET Remoting with Flex 2 and Fluorine

January 20th, 2007
    I've finally gotten the bug to get this Flex thing going and my only stumbling block for really useful applications was that for server-side stuff I'm way more adept with Visual Studio .NET and C# than I am with PHP. I had been looking for a solution and found WebOrb, which requires a server install and isn't free for AMF3. Since I use shared hosting this is really not an option. Then I found Fluorine created by Zoltan Csibi at The Silent Group which is open source after a bit of teeth gnashing easy to set up. After finding Sam Shrefler's excellent examples I decided to put something together something that was a bit more basic than his Cairngorm examples (Not that those weren't basic and very helpful!).

    I'm going to start out with something extremely simple just to demonstrate the setup. The service will basically echo back any string you send to it. I saw this morning as I got the latest update that it installs a Visual Studio project template that is probably the best way to go when setting things up, but I've decided to go ahead and go through the steps of setting things up manually so that hopefully the purpose of the elements is more clear.

    Download and Install the Fluorine Gateway
    Go to the Fluorine download page and download and install the Fluorine Windows Installer.

    Setting Up Project Folders

    • Create a project folder. I called mine Fluorine Flex.
    • Inside this folder create a folder called Dot Net for the .NET code and a folder called Flex for the Flex code

    Creating the Project in Visual Studio .NET

    • Start Visual Studio. I'm using Visual Studio 2005 Standard Edition
    • Select File -> New -> Web Site
    • In the dialog box, select Empty Website
    • In the language dropdown select C#
    • In the location dropdown section select http
    • On the right select Browse
    • In the new dialog on the left select Local IIS
    • On the top right select Create new virtual directory
    • Enter an alias name. I entered fluorineflex.
    • Browse and select the Dot Net folder in your project folder and select OK
    • Now select the virtual directory you just created and select OK

    Configuring the Project in Visual Studio .NET
    I gleaned this mostly from Setting up a Flash Remoting-enabled ASP.NET application at the Fluorine site.

    • In the Solution Explorer, right-click the project icon and select Add Reference
    • Under the .NET tab locate and select Fluorine and select OK
    • Right-click the project icon and select Add New Item
    • Select Web Configuration File. Leave the name as is and select Add
    • In the system.web node of the new Web.config file add the following:
      XML:
      1. <httpModules>
      2.       <add name="FluorineGateway" type="com.TheSilentGroup.Fluorine.FluorineGateway,com.TheSilentGroup.Fluorine" />
      3.  </httpModules>

      and save.

    • Right-click the project icon and select Add Item
    • Select Web Form and name the file Gateway.aspx

    The next part is from the Flex2 basic setup section within Using Flex2 and AMF3 on the Fluorine site.

    • Right-click the project icon and select New Folder. Name it WEB-INF.
    • Right-click the new WEB-INF folder and select New Folder. Name it flex.
    • Right-click the new flex folder and select Add New Item.
    • Select XML File and name it services-config.xml.
    • Open the new services-config.xml and paste the following content below the initial xml tag:
      XML:
      1. <services-config>
      2.     <services>
      3.         <service id="remoting-service"
      4.                  class="flex.messaging.services.RemotingService"
      5.                  messageTypes="flex.messaging.messages.RemotingMessage">
      6.             <destination id="fluorine">
      7.                 <channels>
      8.                     <channel ref="my-amf"/>
      9.                 </channels>
      10.                 <properties>
      11.                     <source> *</source>
      12.                 </properties>
      13.             </destination>
      14.         </service>
      15.     </services>
      16.  
      17.     <channels>
      18.         <channel-definition id="my-amf" class="mx.messaging.channels.AMFChannel">
      19.             <endpoint uri="http://{server.name}:{server.port}/{context.root}/Gateway.aspx" class="flex.messaging.endpoints.AMFEndpoint"/>
      20.         </channel-definition>
      21.     </channels>
      22. </services-config>

    • In the endpoint node change the uri property to point to Gateway.aspx in the virtual directory that you created. In my case it's uri="http://localhost/fluorineflex/Gateway.aspx".

    UPDATE
    I was not aware of this, but I recieved an email from Zoli at The Silent Group and he notified me that the uri attribute does not have to change as long as the context root remains the same on the server you are deploying to. In this case if I'm developing on http://localhost/fluorineflex/Gateway.aspx, and deploying to http://www.darbymedia.com/fluorineflex/Gateway.aspx, then I can leave the uri attribute as it's default: http://{server.name}:{server.port}/{context.root}/Gateway.aspx.

    Configuring the Flex Project

    • Download and install Flex Data Services 2 Express from the Flex download page. No serial number is neccessary for development work. (Not necessary - Thanks Richard!)
    • Start Flex Builder 2.
    • Select File -> New -> Flex Project.
    • Select Flex Data Services.
    • Select Compile application locally in Flex Builder.
    • Select Next.
    • Uncheck Use default local Flex Data Services Location.
    • In Root folder select Browse and select the Dot Net folder in your project folder. For me it was D:\Projects\Flex\Fluorine Flex\Dot Net.
    • In Root URL enter the path to the virtual directory created earlier. In my case it was http://localhost/fluorineflex/.
    • As far as I can tell Context root should be the last folder name of your virtual web directory. Mine was /fluorineflex.
    • Select Next
    • Uncheck the Use default location box and select the Flex folder in you project folder. In my case it's D:\Projects\Flex\Fluorine Flex\Flex.
    • Select Finish

    Now we're ready to ROCK!

    Creating a Fluorine Service in .NET

    • In Visual Studio, right-click the project icon and select Add New Item.
    • Select Class and name it FlexService.cs. (You can name the class anything you want at this point. I'll use FlexService.)
    • When prompted to put the file in an App_Code folder, click Yes.
    • At this point you'll only need to "use" System and System.Web, but it won't hurt to leave the other classes.
    • I've cleaned up mine and given it a fancy namespace (com.darbymedia.com.flex) to look like this:
      C#:
      1. using System;
      2. using System.Web;
      3.  
      4. namespace com.darbymedia.flex
      5. {
      6.     public class FlexService
      7.     {
      8.         public FlexService() { }
      9.     }
      10. }

    • Add a function called echo and have it return a message that is sent and our class looks like this:
      C#:
      1. using System;
      2. using System.Web;
      3.  
      4. namespace com.darbymedia.flex
      5. {
      6.     public class FlexService
      7.     {
      8.         public FlexService() { }
      9.  
      10.         public string echo(string msg)
      11.         {
      12.             return "echo(msg) msg: " + msg;
      13.         }
      14.     }
      15. }

    Accessing the Service via Flourine in Flex

    • Return to Flex Builder 2
    • Create a RemoteObject with the following properties:
      • destination: fluorine. This is the destination set up in the services-config.xml file.
      • source: com.darbymedia.flex.FlexService. This is the namespace and class name for our service.
      • result: roResult. This is method to receive the return value. We'll do this in a minute.
      • fault: roFault. This is the method to receive any errors. We'll make this in sec too.

      Adding an input field, submit button, output text area and a bad call button your mxml will look like this:

      XML:
      1. <mx:RemoteObject
      2.     id="roFlexService"
      3.     destination="fluorine"
      4.     source="com.darbymedia.flex.FlexService"
      5.     showBusyCursor="true"
      6.     result="roResult(event)"
      7.     fault="roFault(event)"
      8.     />
      9.        
      10. <mx:TextArea id="taMessage" width="250" height="150"  x="50" y="40"/>
      11. <mx:TextInput x="50" y="10" id="txtInput" width="185"/>
      12. <mx:Button x="243" y="10" label="Echo!" id="btnSend" click="submitText()"/>
      13. <mx:Button x="50" y="198" label="Submit Bad Call" id="btnBad" click="badCall()"/>

    • Now to create the roResult and roFault methods as well as button handlers. They look like this:
      XML:
      1. <mx:Script>
      2.     <![CDATA[
      3.         import mx.rpc.events.FaultEvent;
      4.         import mx.rpc.events.ResultEvent;
      5.        
      6.         public function submitText():void
      7.         {
      8.              roFlexService.echo(txtInput.text);
      9.         }
      10.            
      11.         public function badCall():void
      12.         {
      13.             //this won't work because there is no method called badCall()
      14.             roFlexService.badCall(txtInput.text);
      15.         }
      16.            
      17.         public function roResult(e:ResultEvent):void
      18.         {
      19.             taMessage.text = "roResult(e)";
      20.             taMessage.text += "\n" + e.result;
      21.         }
      22.            
      23.         public function roFault(e:FaultEvent):void
      24.         {
      25.             taMessage.text = "roFault(e)";
      26.             taMessage.text += "\n" + e.fault.faultCode;
      27.             taMessage.text += "\n" + e.fault.faultString;
      28.             taMessage.text += "\n" + e.fault.faultDetail;
      29.         }
      30.     ]]>
      31. </mx:Script>

    • Now that we have our RemoteObject set up we can call any method within our service class directly.

    Now the entire mxml file looks like this:

    XML:
    1. <?xml version="1.0" encoding="utf-8"?>
    2. <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute">
    3.  
    4.     <mx:Script>
    5.         <![CDATA[
    6.             import mx.rpc.events.FaultEvent;
    7.             import mx.rpc.events.ResultEvent;
    8.            
    9.             public function submitText():void
    10.             {
    11.                 roFlexService.echo(txtInput.text);
    12.             }