Executing order of Flex component life cycle functions

Flex Component life cycle  is pretty well known by every one who have knowledge of Flex . But  let me explain here if any one not aware of it .

Flex component Life cycle contains some event which is dispatched by flash player while creating component .These events are

1) FlexEvent.PREINITIALIZE
2) FlexEvent.INITIALIZE
3) FlexEvent.CREATION_COMPLETE
4) FlexEvent.UPDATE_COMPLETE

Flash player dispatches  above events while creating any component and with respect to these events some methods get called. These method are

1) constructor of component
2) createChildren()
3) commitProperties()
4) measure()
5) updateDisplayList()

Now there are two question .

1) what is the Executing order of  these methods ?
2) which method get execute after which event ?

To find out answer of these two questions I wrote one sample custom component , which I am going to post here .

This component extend  UIComponent class and override all required method . I put trace statement in every method so we can easily recognize order of method and event .
copy and paste this component in your project then add in main file and run in debug mode .
package
{
 import flash.events.Event;
 import mx.controls.Button;
 import mx.core.UIComponent;
 import mx.events.FlexEvent;

 public class CustomComp  extends UIComponent
 {
  public function CustomComp ()
  {
   trace("CustomComp  constructor called");
   this.addEventListener(FlexEvent.INITIALIZE , initializeEventHandler);
   this.addEventListener(FlexEvent.PREINITIALIZE , preInitializeEventHandler);
   this.addEventListener(FlexEvent.CREATION_COMPLETE,creationcompleteEventHandler);
   this.addEventListener(FlexEvent.UPDATE_COMPLETE , updateCompleteEventHandler);
   super();
  }

  private function initializeEventHandler(event:FlexEvent):void{
   trace("initializeEventHandler called");
  }

  private function preInitializeEventHandler(event:FlexEvent):void{
   trace("preInitializeEventHandler called");
  }

  private function creationcompleteEventHandler(event:FlexEvent):void{
   trace("creationcompleteEventHandler called");
  }

  private function updateCompleteEventHandler(event:FlexEvent):void{
   trace("updateCompleteEventHandler called");
  }
 
  override protected function createChildren():void{
   trace("createChildren called");
   super.createChildren();

     }

     override protected function commitProperties():void{
      trace("commitProperties called");
      super.commitProperties();
     }
   
     override protected function measure():void{
      trace("measure called");
      super.measure();
    
     }
     override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void{
      trace("updateDisplayList called");
      super.updateDisplayList(unscaledWidth ,unscaledHeight);
     }

 }
}
After running in debug mode you can see trace statement in following order .

CustomComp constructor called
preInitializeEventHandler called
createChildren called
initializeEventHandler called
commitProperties called
measure called
updateDisplayList called
creationcompleteEventHandler called
updateCompleteEventHandler called

Now you can easily find out answer of above questions.




Air Integration with SQLite



I Could not find out a good sample project of AIR and SQLite  ,So here I am  posting Flex  source Code .
In this Sample Project I created Database in SQLite and populated data in DataGrid .  You can perform Insert and Delete Operation .
you just need to create one AIR Project using Flex Builder then copy and paste this source code .
AirSQLiteSample.MXML
  1:  <?xml version="1.0" encoding="utf-8"?>
  2:  <mx:WindowedApplication xmlns:mx="http://www.adobe.com/2006/mxml" layout="vertical"
  3:    horizontalAlign="center" verticalAlign="middle"
  4:   creationComplete="init();">
  5:   
  6:   <mx:Script>
  7:    <![CDATA[
  8:     import mx.events.DataGridEvent;
  9:     import mx.collections.ArrayCollection;
 10:     import mx.controls.Alert;
 11:     import mx.managers.CursorManager;
 12:     import flash.data.SQLResult;
 13:     import flash.filesystem.File;
 14:     import flash.data.SQLStatement;
 15:     import flash.data.SQLConnection;
 16:     import flash.events.SQLEvent;
 17:     import flash.events.SQLErrorEvent;
 18:     
 19:     
 20:     private var userDB:SQLConnection;
 21:     private var userDBFile:File;
 22:     private var dbStatement:SQLStatement;
 23:     
 24:     
 25:    // The birthdate parameter's name and value:
 26:     private static const PARAM_BIRTHDATE:String = ":birthdate";
 27:     private static const BIRTHDATE:Date = new Date(1983,3,15);
 28:     [Bindable]
 29:     private var userData:ArrayCollection = new ArrayCollection();
 30:     
 31:     private static const CREATE_USER_SQL:String = 
 32:     "CREATE TABLE user(" + "\n" + 
 33:     " user_id INTEGER PRIMARY KEY AUTOINCREMENT," + "\n" + 
 34:     " first_name TEXT NOT NULL," + "\n" + 
 35:     " last_name TEXT NOT NULL," + "\n" + 
 36:     " address TEXT," + "\n" + 
 37:     " birthday DATE," + "\n" + 
 38:     " notes TEXT" + "\n" + 
 39:     ")";
 40:    
 41:     private static const POPULATE_USER_SQL:String = 
 42:     "INSERT INTO user (first_name, last_name, address, birthday, notes)" + "\n" + 
 43:     "SELECT 'Neeraj', 'Kanthariya', 'Bangalore India', " + PARAM_BIRTHDATE + ", 'SoftWare Engineer'";
 44:     
 45:     private function init():void
 46:     {
 47:      userDBFile = File.applicationStorageDirectory.resolvePath("neeraj.db");
 48:         userDB = new SQLConnection();
 49:         CursorManager.setBusyCursor();
 50:      
 51:      if (!userDBFile.exists)
 52:      { 
 53:       userDB.addEventListener(SQLEvent.OPEN, onUserDBCreateOpend);
 54:          userDB.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
 55:          userDB.open(userDBFile);
 56:          CursorManager.removeBusyCursor();
 57:      }
 58:        else
 59:      {
 60:       userDB.addEventListener(SQLEvent.OPEN, selectAllFromUser);
 61:          userDB.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
 62:          userDB.openAsync(userDBFile,SQLMode.UPDATE);
 63:          CursorManager.removeBusyCursor();
 64:      }       
 65:     }
 66:     
 67:     //create user table 
 68:     private function onUserDBCreateOpend(event:SQLEvent):void
 69:     {
 70:      if (event.type == "open")
 71:         {
 72:          dbStatement = new SQLStatement();
 73:       dbStatement.sqlConnection = userDB;
 74:       dbStatement.text = CREATE_USER_SQL;
 75:       dbStatement.addEventListener(SQLEvent.RESULT, createTableResultHandler);
 76:       dbStatement.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
 77:       dbStatement.execute();
 78:     
 79:         }
 80:     }
 81:     // papulate static data in user table 
 82:     private function createTableResultHandler(event:SQLEvent=null):void{
 83:      if(event!= null){
 84:       var stmt:SQLStatement = event.target as SQLStatement;
 85:       if (stmt == null) { return; }
 86:      
 87:       stmt.removeEventListener(SQLEvent.RESULT, createTableResultHandler);
 88:       stmt.removeEventListener(SQLErrorEvent.ERROR, onUserDBError);
 89:      }
 90:      
 91:      dbStatement = new SQLStatement();
 92:      dbStatement.sqlConnection =userDB;
 93:      dbStatement.text = POPULATE_USER_SQL;
 94:      dbStatement.parameters[PARAM_BIRTHDATE] = BIRTHDATE;
 95:      dbStatement.addEventListener(SQLEvent.RESULT, populateTableHandler);
 96:      dbStatement.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
 97:      dbStatement.execute();
 98:     }
 99:     // call onUserDBUpdateOpened
100:     private function populateTableHandler(event:SQLEvent):void{
101:      var stmt:SQLStatement = event.target as SQLStatement;
102:      if (stmt == null) { return; }
103:      
104:      stmt.removeEventListener(SQLEvent.RESULT, populateTableHandler);
105:      stmt.removeEventListener(SQLErrorEvent.ERROR, onUserDBError);
106:      
107:      selectAllFromUser();
108:     }
109:     
110:     // retrive data from user table
111:     private function selectAllFromUser(event:SQLEvent=null):void{
112:      dbStatement = new SQLStatement();
113:      dbStatement.sqlConnection = userDB;
114:      dbStatement.text = "select * from user";
115:      dbStatement.addEventListener(SQLEvent.RESULT, resultHandler);
116:      dbStatement.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
117:      dbStatement.execute();
118:     }
119:     // insert data in dataprovider 
120:     private function resultHandler(event:SQLEvent):void
121:        {
122:      dbStatement.removeEventListener(SQLEvent.RESULT, resultHandler);
123:      dbStatement.removeEventListener(SQLErrorEvent.ERROR, onUserDBError);
124:      var result:SQLResult = dbStatement.getResult();
125:      userData.removeAll();
126:      for each (var row:Object in result.data)
127:      {
128:       userData.addItem(row);
129:      }
130:     }
131:     
132:     // insert data in user table
133:     private function insertUser():void{
134:      dbStatement = new SQLStatement();
135:      dbStatement.sqlConnection = userDB;
136:      dbStatement.text = "insert into user(first_name,last_name,address,birthday,notes)"+
137:             "values(:first_name,:last_name,:address,:birthday,:notes)";
138:      dbStatement.parameters[":first_name"] = firstNameTextInput.text;
139:      dbStatement.parameters[":last_name"] = lastNameTextInput.text;
140:      dbStatement.parameters[":address"] = addressTextInput.text;
141:      dbStatement.parameters[":birthday"] = birthday.selectedDate;
142:      dbStatement.parameters[":notes"] = note.text;
143:  
144:      dbStatement.addEventListener(SQLEvent.RESULT, insertUserHandler);
145:      dbStatement.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
146:      dbStatement.execute();
147:     }
148:     // call onUserDBUpdateOpened
149:     private function insertUserHandler(event:SQLEvent):void{
150:      dbStatement.removeEventListener(SQLEvent.RESULT, insertUserHandler);
151:      dbStatement.removeEventListener(SQLErrorEvent.ERROR, onUserDBError);
152:      selectAllFromUser();
153:     }
154:     // delete data from user table
155:     private function DeleteUser():void{
156:      dbStatement = new SQLStatement();
157:      dbStatement.sqlConnection = userDB;
158:      //dbStatement.text = "DROP TABLE user";
159:      dbStatement.text = "delete from user where user_id ="+usersDataGrid.selectedItem["user_id"];
160:      dbStatement.addEventListener(SQLEvent.RESULT, deleteUserHandler);
161:      dbStatement.addEventListener(SQLErrorEvent.ERROR, onUserDBError);
162:      dbStatement.execute();
163:  
164:     }
165:     // call onUserDBUpdateOpened
166:     private function deleteUserHandler(event:SQLEvent):void{
167:      dbStatement.removeEventListener(SQLEvent.RESULT, deleteUserHandler);
168:      dbStatement.removeEventListener(SQLErrorEvent.ERROR, onUserDBError);
169:      selectAllFromUser();
170:     }
171:     
172:     
173:     
174:     private function onUserDBError(event:SQLErrorEvent):void
175:     {
176:      Alert.show(event.toString());
177:     }
178:     
179:   ]]>
180:   </mx:Script>
181:  
182:    <mx:VBox horizontalScrollPolicy="off" verticalScrollPolicy="off">
183:     <!-- Form -->
184:     <mx:Form>
185:         <mx:FormHeading label="AIR SQLITE INSERT DELETE OPERATION SAMPLE"/>
186:      <mx:FormItem label="First Name:">
187:       <mx:TextInput id="firstNameTextInput"/>
188:      </mx:FormItem>
189:      <mx:FormItem label="Last Name:">
190:       <mx:TextInput id="lastNameTextInput"/>
191:      </mx:FormItem>
192:      <mx:FormItem label="Address">
193:       <mx:TextInput id="addressTextInput"/>
194:      </mx:FormItem>
195:      <mx:FormItem label="Birthday:">
196:       <mx:DateField id="birthday" editable="true" yearNavigationEnabled="true" width="120"/>
197:      </mx:FormItem>
198:      <mx:FormItem label="Notes">
199:       <mx:TextArea id="note"/>
200:      </mx:FormItem>
201:     </mx:Form>
202:     <mx:HBox>
203:       <mx:Button label="Insert User" click="insertUser()"/>
204:        <mx:Button label="Delete User" click="DeleteUser()"/>
205:        </mx:HBox>
206:    </mx:VBox>
207:  
208:    <!-- Results -->
209:    <mx:DataGrid  id="usersDataGrid" dataProvider="{userData}" width="100%">
210:     <mx:columns>
211:      <mx:DataGridColumn headerText="First Name" dataField="first_name"/>
212:      <mx:DataGridColumn headerText="Last Name" dataField="last_name"/>
213:      <mx:DataGridColumn headerText="Address" dataField="address"/>
214:      <mx:DataGridColumn headerText="BirthDay" dataField="birthday"/>
215:      <mx:DataGridColumn headerText="Notes" dataField="notes"/>
216:     </mx:columns>
217:    </mx:DataGrid>
218:  </mx:WindowedApplication>
219: 


Please let me know If I am unclear .


Neeraj

JavaServer Faces with Flex Component

 

JavaServer Faces Flex goal is to provide users capability in creating standard Flex components, part of flexSDK which is open sourced through MPL license, as normal JSF components [note that other dynamic components such as chart are not part of flexSDK]. So users would create the components as normal JSF components and the project will create the necessary SWC, SWF, and etcetera and link the values of the components back to the managed beans using JSON+JavaScript and ActionScript. This article, which is mainly targeted for JSF developers, will provide an overview of creating a simple multilingual JSF page consisting of JSF Flex tags.

for More Detail  …..    JSF Flex  By ji Hoon kim

Flex 3 Component Life Cycle

presented by Brad Umbaugh and RJ Owen at 360 | Flex, San Jose.

Memory Leak in AdvancedDataGrid HeaderRenderer

 

There is huge memory leak  while Extending AdvancedDataGridHeaderRenderer to create custom headerRenderer  for AdvancedDataGrid

If  you Refresh your AdvancedDataGrid  by  reassign DataProvider then instance of   itemRenderer  become Double every time .

Here i am giving sample code .

Create new project and copy and past code . Run from flex 3 profile .

if you click on ResetDataProvider Button  and instance  of EXRDeviceListLabel from profile .

instance of ExrDeviceListLabel  increased  on every click of ResetDataProvider .

 

 

MemoryLeak.mxml

  1: <?xml version="1.0" encoding="utf-8"?>
  2: <mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute" creationComplete="init();">
  3: <mx:Script source="memoryLeak.as"/>
  4: <mx:VBox width="100%" height="100%">
  5: <mx:AdvancedDataGrid  id="deviceListDG" width="100%" height="50%"/>
  6: <mx:Button id="resetDataGrid" click="resetDataProvider();" label="ResetDataProvider"/>  
  7: </mx:VBox>
  8: </mx:Application>


memoryLeak.as



 



  1: // ActionScript file
  2: import mx.collections.ArrayCollection;
  3: import mx.controls.AdvancedDataGrid;
  4: import mx.controls.advancedDataGridClasses.AdvancedDataGridColumn;
  5: import mx.core.ClassFactory;
  6: import mx.core.IFactory;
  7: import mx.core.mx_internal;
  8: import mx.utils.ObjectProxy;
  9: use namespace mx_internal;
 10: 
 11: private static var headerR:IFactory = new ClassFactory(ExrHeaderRenderer);
 12: 
 13: 
 14: private var _columnsCollection:ArrayCollection = new ArrayCollection([
 15:     {columnWidth :"40"  , dataField : "serialIndex"  , visible : "true", headerText:"SerialIndex"},
 16:     {columnWidth : "80"  , dataField : "deviceType", visible : "true", headerText:"DeviceType"},
 17:     {columnWidth : "100" ,dataField : "powerStatus", visible : "true", headerText :"PowerStatus"},
 18:     {columnWidth : "120" ,dataField : "networkStatus", visible : "true", headerText:"NetworkStatus"},
 19:     {columnWidth : "150" ,dataField : "oS", visible : "true", headerText:"OS"},
 20:     {columnWidth : "200" ,dataField : "department", visible : "true", headerText:"Department"}
 21:     ])
 22: 
 23: private var _dgDataProvider:ArrayCollection = new ArrayCollection();
 24: private function init():void{
 25:   createDataGridColumns();
 26:   deviceListDG.validateDisplayList();
 27:   deviceListDG.validateProperties();
 28:   createdataProvider();
 29:   deviceListDG.dataProvider = _dgDataProvider;
 30: }
 31: 
 32: private function createdataProvider():void{
 33:   _dgDataProvider.removeAll();
 34:   var obj:ObjectProxy;
 35:   for(var i:int; i<100 ;i++){
 36:     obj = new ObjectProxy();
 37:     obj.serialIndex = i;
 38:     obj.deviceType = "Computer"+i;
 39:     obj.powerStatus = "ON"+i;
 40:     obj.networkStatus = "OFF";
 41:     obj.oS ="Window";
 42:     obj.department = "Symphony";
 43:     _dgDataProvider.addItem(obj);
 44:   }
 45:   
 46:   
 47: }
 48: private function createDataGridColumns():void{
 49:   var adgColumns:Array = deviceListDG.columns;
 50:   var adgColumn:AdvancedDataGridColumn;
 51:   var dataFieldName:String;
 52:   
 53:   for(var j:int=0; j<_columnsCollection.length; j++){
 54:       adgColumn = new AdvancedDataGridColumn();
 55:     adgColumn = setColumnProperties(adgColumn, _columnsCollection[j]);
 56:       adgColumns.push(adgColumn); 
 57:   }        
 58:   deviceListDG.columns = adgColumns
 59: }
 60: 
 61: private function setColumnProperties(adgColumn:AdvancedDataGridColumn, values:Object):
 62:    AdvancedDataGridColumn{
 63:   var dataFieldName:String;
 64:   dataFieldName = values.dataField;
 65:   adgColumn.dataField = dataFieldName;  
 66:   adgColumn.headerText = values.headerText;  
 67:   adgColumn.visible = (values.visible=="true");  
 68:         adgColumn.headerRenderer = headerR;
 69:   adgColumn.itemRenderer = new ClassFactory(EXRDeviceListLabel);
 70:   return adgColumn;
 71: }
 72: 
 73: private function resetDataProvider():void{
 74:   deviceListDG.dataProvider = [];
 75:   createdataProvider();
 76:   deviceListDG.dataProvider = _dgDataProvider;
 77:   deviceListDG.headerItems = null;
 78:   deviceListDG.headerRenderer = headerR;
 79: }
 80: 


 



ExrHeaderRenderer.as



  1: package
  2: {
  3:   import mx.controls.Label;
  4:   public class EXRDeviceListLabel extends Label
  5:   {
  6:     public function EXRDeviceListLabel()
  7:             {
  8:                   super();
  9:                   this.truncateToFit=true;
 10:             }
 11:             public function set label(value:String):void {
 12:               if(value == "" || value == "undefined" || value == null){ 
 13:           this.text = "";
 14:         }else{
 15:           this.text = value;
 16:                     this.setStyle("paddingLeft",5);
 17:                     this.setStyle("paddingRight",5);
 18:         }                 
 19:             }
 20:   }
 21: }




EXRDeviceListLabel.as





  1: package
  2: {
  3:   import mx.controls.Label;
  4:   public class EXRDeviceListLabel extends Label
  5:   {
  6:     public function EXRDeviceListLabel()
  7:             {
  8:                   super();
  9:                   this.truncateToFit=true;
 10:             }
 11:             public function set label(value:String):void {
 12:               if(value == "" || value == "undefined" || value == null){ 
 13:           this.text = "";
 14:         }else{
 15:           this.text = value;
 16:                     this.setStyle("paddingLeft",5);
 17:                     this.setStyle("paddingRight",5);
 18:         }                 
 19:             }
 20:   }
 21: }




please let me know if I am unclear .



Neeraj