Flex reference child element - actionscript-3

How can we reference to an element which is added dynamically on runtime?
Example code:
<?xml version="1.0" encoding="utf-8"?>
<s:WindowedApplication xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" applicationComplete="init(event)">
<fx:Script>
<![CDATA[
import mx.events.FlexEvent;
protected function init(event:FlexEvent):void
{
// TODO Auto-generated method stub
trace(button1.label);
var newbtn:Button = new Button();
newbtn.label = "New Button";
newbtn.id = "button3";
newbtn.name = "button3";
mygroup.addElement(newbtn);
trace(this["button3"].label);
}
]]>
</fx:Script>
<s:HGroup id="mygroup">
<s:Button id="button1" label="Button 1" />
<s:Button id="button2" label="Button 2" />
</s:HGroup>
</s:WindowedApplication>
When I try to run above code, it dispatch error
Error #1069: Property button3 not found on project1 and there is no default value.
So, how can I call to the newly added button?

Store your instance in a variable and reference it whenever you feel like it. Use an array for a list of variables.

you can try using
var obj = this.getChildByName("button3");
after that you can use obj to trace the label

Related

"null object reference" error in ActionScript 3

I used my app's resize handler to resize my component but it is throwing this error :
TypeError: Error #1009: Cannot access a property or method of a null object reference
Here is my code :
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600"
resize="application2_resizeHandler(event)" >
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
</fx:Declarations>
<fx:Script>
<![CDATA[
import mx.events.FlexEvent;
import mx.events.ResizeEvent;
private var employeeName:String = 'ravi';
protected function application2_resizeHandler(event:ResizeEvent):void
{
mainGroup.width = stage.width - 10;
mainGroup.x = 5;
}
]]>
</fx:Script>
<s:Group width="100%" height="100%">
<s:VGroup id="mainGroup" >
<s:Label id="employeeNameLabel" text="{employeeName}" />
<s:Label id="departmentLabel" />
</s:VGroup>
<s:Button id="getData" />
</s:Group>
</s:Application>
You got the #1009 error because your resize event is fired before the creation of your objects. So, you should wait for that and that your app is added to the stage to be able to use the stage object.
For that, I think that the best event is the applicationComplete event, then you can add a resize event to resize your component ...
So you can do like this for example :
<s:Application
xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600"
applicationComplete="application2_applicationCompleteHandler(event)" >
then
protected function application2_applicationCompleteHandler(event:FlexEvent):void
{
// if you want you can resize your component for the 1st time
// by calling the application2_resizeHandler() function
application2_resizeHandler(new ResizeEvent(ResizeEvent.RESIZE));
// add the resize event listener to your app
event.target.addEventListener(ResizeEvent.RESIZE, application2_resizeHandler);
}
Hope that can help.

how to set source parameter for bitmap image in mxml using action script

I am very new to actionscript. I want to access already existing BitmapImage in mxml so as to change its source The Bitmap Image already exists im mxml with its id. I dont hav e to create it dynamically only its source is to be set.
I have seen some examples but they add image itself dynamically I dont want that.
Action Script3 is to be used.
here is the code:
Kindly suggest.
<fx:Script>
//code to set image source to url1(a string)
</fx:Script>
<s:Graphic>
<s:BitmapImage
id="ini_image"
source="#Embed('C:/horizontal_red.png')"
width="640"
height="480"
fillMode="scale"
includeIn="ready"
/>
</s:Graphic>
I tried it like this :
var ini_image:BitmapImage = new BitmapImage();
ini_image.source = url;
But it gives error in namespace might be because ii is creating a new object of same type with same name. Which is not allowed.
Please correctify me if I am wrong and suggest corrections.
I assume you have more than one state in your application, so you have to take care if the ready state was or not initialized before setting the BitmapImage source. Hope the following code example will solve your problem.
<?xml version="1.0"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
currentState="other">
<s:states>
<s:State name="ready"/>
<s:State name="other"/>
</s:states>
<fx:Script><![CDATA[
private function onButtonClick(event:MouseEvent):void {
currentState = 'ready';
ini_image.source = 'http://lorempixel.com/200/200';
}
]]></fx:Script>
<s:Graphic>
<s:BitmapImage
id="ini_image"
source="http://lorempixel.com/100/100"
width="640"
height="480"
fillMode="scale"
includeIn="ready"
/>
</s:Graphic>
<s:Button click="onButtonClick(event)"/>
</s:Application>
You can also include image in both states and use different image source.
<?xml version="1.0"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
currentState="other">
<s:states>
<s:State name="ready"/>
<s:State name="other"/>
</s:states>
<s:Graphic>
<s:BitmapImage
id="ini_image"
source.other="http://lorempixel.com/100/100"
source.ready="http://lorempixel.com/200/200"
width="640"
height="480"
fillMode="scale"/>
</s:Graphic>
<s:Button click="onToggleStates(event)"/>
<fx:Script><![CDATA[
private function onToggleStates(event:MouseEvent):void {
currentState = currentState == 'other' ? 'ready' : 'other';
}
]]></fx:Script>
</s:Application>

Binding is not happening on Object Property and text Input

I am trying bind an Object property value to a text field. (Well I have taken this as an example ... I have no.of form fields and to be bound by other values)
But when change its value on button click the text field is not getting updated?
Below is the example code,
<?xml version="1.0" encoding="utf-8"?>
<s:Application
minHeight="600"
minWidth="955"
xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx">
<fx:Declarations>
</fx:Declarations>
<fx:Script>
<![CDATA[
[Bindable]
var currentFormItem:Object = new Object();
public function changeName():void
{
currentFormItem.name = "hello";
}
]]>
</fx:Script>
<s:HGroup>
<s:TextInput id="test"
text="{currentFormItem.name}"/>
<s:Button click="changeName()"/>
</s:HGroup>
Thanks
I got the solution for this. I can just wrap this object in ObjectProxy.

arraycollection error in flex4.6

I'm having difficulty passing json to a datagrid.
I get the following error:
TypeError: Error #1034: Type Coercion failed: cannot convert mx.collections::ArrayCollection#bc292a9 to Array.
at Function/<anonymous>()[C:\Users\Birger\Dropbox\Rich Media Applications\P006_Project\src\FULLTEST.mxml:10]
at Function/http://adobe.com/AS3/2006/builtin::apply()
at mx.binding::Binding/wrapFunctionCall()[E:\dev\4.y\frameworks\projects\framework\src\mx\binding\Binding.as:395]
at mx.binding::Binding/innerExecute()[E:\dev\4.y\frameworks\projects\framework\src\mx\binding\Binding.as:469]
at Function/http://adobe.com/AS3/2006/builtin::apply()
at mx.binding::Binding/wrapFunctionCall()[E:\dev\4.y\frameworks\projects\framework\src\mx\binding\Binding.as:395]
at mx.binding::Binding/execute()[E:\dev\4.y\frameworks\projects\framework\src\mx\binding\Binding.as:333]
at mx.binding::BindingManager$/executeBindings()[E:\dev\4.y\frameworks\projects\framework\src\mx\binding\BindingManager.as:153]
at FULLTEST/_FULLTEST_ArrayCollection1_i()[C:\Users\Birger\Dropbox\Rich Media Applications\P006_Project\src\FULLTEST.mxml:4]
at FULLTEST()[C:\Users\Birger\Dropbox\Rich Media Applications\P006_Project\src\FULLTEST.mxml:4]
my code is:
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" minWidth="955" minHeight="600" xmlns:components="components.*" initialize="getData.send();">
<fx:Declarations>
<!-- Place non-visual elements (e.g., services, value objects) here -->
<mx:HTTPService id="getData" url="http://localhost/P006_Project/Query.php"
useProxy="false" method="POST" resultFormat="text" result="getPHPData(event)">
</mx:HTTPService>
<s:ArrayCollection id="acItems" source="{dataArray}" />
</fx:Declarations>
<fx:Script>
<![CDATA[
import mx.collections.ArrayCollection;
import mx.events.FlexEvent;
import mx.rpc.events.ResultEvent;
[Bindable]private var dataArray:ArrayCollection = new ArrayCollection();
private function initDataGrid():void
{
getData.send();
}
private function getPHPData(event:ResultEvent):void
{
var rawArray:Array;
var rawData:String = String(event.result);
rawArray = JSON.parse(rawData) as Array;
dataArray = new ArrayCollection(rawArray);
}
]]>
</fx:Script>
<mx:Accordion id="accItems" creationPolicy="auto">
<s:NavigatorContent label="Frisdranken">
<components:FULLTESTCOMP acItems="{acItems}" creationComplete="{initDataGrid()}"/>
</s:NavigatorContent>
</mx:Accordion>
</s:Application>
so I'm trying to fill my datagrid with content from my database by converting it into JSON. I'm using a custom component (just an ordinary datagrid in this one).
Here is the problem:
<s:ArrayCollection id="acItems" source="{dataArray}" />
source needs to be of type "Array" but you're assigning the source to an ArrayCollection object.
You should do:
<s:ArrayCollection id="acItems" source="{dataArray.source}" />
Hope this helps.

pass data from popup to parent

I have a parent w/ a popup child. When parent loads, I have to call a function within the popup without showing the popup (thus, I load "pupLove" but don't include it in layout)....I then pass this data to the parent. When the user manually clicks another button to open the popup, the same function is called & data passed to the parent. However, I am not able to pass dg.length to the parent. I believe the root problem is that I am loading "pupLove" & thus the parents are getting confused.....I'm guessing if I get rid of "pupLove" I can pass the data correctly but will need to call the child's function at creationComplete of the parent....how do I do that?
Here's my parent:
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
backgroundColor="green" width="50%" height="100%"
xmlns:local="*"
>
<fx:Script>
<![CDATA[
import pup;
import mx.managers.PopUpManager;
public function showPup(evt:MouseEvent):void {
var ttlWndw:pup = PopUpManager.createPopUp(this, pup, true) as pup;
PopUpManager.centerPopUp(ttlWndw);
}
]]>
</fx:Script>
<mx:VBox>
<local:pup id="pupLove" visible="false" includeInLayout="false" />
<s:Button click="showPup(event);" label="launch Pup" />
<mx:Text id="Ptest" color="black" text="from Parent:{pupLove.dg.length}" />
</mx:VBox>
</s:Application>
And a popup child called 'pup.mxml':
<?xml version="1.0" encoding="utf-8"?>
<s:Group xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx" width="400" height="300">
<fx:Script>
<![CDATA[
public function init():void{
// send php call
}
import mx.events.CloseEvent;
import mx.managers.PopUpManager;
private function removePup(evt:Event):void {
PopUpManager.removePopUp(this);
}
]]>
</fx:Script>
<fx:Declarations>
<s:ArrayCollection id="dg">
</s:ArrayCollection>
</fx:Declarations>
<s:TitleWindow width="100%" height="100%" close="removePup(event)">
<mx:VBox>
<mx:Text id="test" color="red" text="from Child:{dg.length}" />
<s:Button label="add Items" click="dg.addItem({id:'cat'})" />
</mx:VBox>
</s:TitleWindow>
</s:Group>
UPDATE: I guess my question can be more easily stated as: "is there a way to call a child's function from the parent without actually loading the child?"
Well, if in your child's function, you don't need to access any of its UI component, then you could instanciate the child in the parent view and call the method.
When you need to display the popup afterwhile, use the PopupManager addPopup method with this existing instance instead of using createPopup