views:

487

answers:

2

Hi,

I'm hacking my way through learning Flex and have found some strange behaviour. When I try to compile my code, I'm thrown this error - Error: Call to a possibly undefined method updateStory. I've used method calls in this way before, and can't spot what's going wrong in this case. Here's the code for the component:

<?xml version="1.0" encoding="utf-8"?>
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"&gt;

  <mx:Script>
 <![CDATA[

 import mx.collections.ArrayCollection;

 [Bindable]
 public var storyCards:ArrayCollection;

 private function updateStory():void
 {
    trace("success");
 } 

 ]]>
  </mx:Script>

  <mx:TileList dataProvider="{storyCards}" >

 <mx:itemRenderer>

   <mx:Component>

 <mx:HBox>
   <mx:Label />
   <mx:TextInput keyUp="updateStory()" />
   <mx:TextArea text="{data.notes}" />
 </mx:HBox>

   </mx:Component>

 </mx:itemRenderer>

  </mx:TileList>
</mx:Canvas>

Can anyone point me in the right direction?

+6  A: 

the problem is with the mx:Component parent tag.

from the docs:

The <mx:Component> tag defines a new scope within an MXML file, where the local scope of the item renderer or item editor is defined by the MXML code block delimited by the <mx:Component> and </mx:Component> tags. To access elements outside of the local scope of the item renderer or item editor, you prefix the element name with the outerDocument keyword.

So you need to make 'updateStory' public and add the outerdocument keyword, like so:

<?xml version="1.0" encoding="utf-8"?>
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"&gt;
<mx:Script>
    <![CDATA[

    import mx.collections.ArrayCollection;

    [Bindable]
    public var storyCards:ArrayCollection;

    public function updateStory():void
    {
       trace("success");
    }       
    ]]>
</mx:Script>
<mx:TileList dataProvider="{storyCards}" >
       <mx:itemRenderer>
            <mx:Component>
                <mx:HBox>
                 <mx:Label />
                 <mx:TextInput keyUp="outerDocument.updateStory()" />
                 <mx:TextArea text="{data.notes}" />
                </mx:HBox>
            </mx:Component>
        </mx:itemRenderer>
    </mx:TileList>
</mx:Canvas>
JStriedl
To add a bit more detail... mx:Component really just creates a new class that gets instantiated once for every visible item in a List-based control. outerDocument is a reference in that class to the object which created the class.
James Ward
+1  A: 

You could also dispatch an Event from the ItemRenderer Component, and add a Listener in the main document. This is useful should you want to port the ItemRenderer Component to a separate MXML Component file.

Here it is with your code:

<?xml version="1.0" encoding="utf-8"?>
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"&gt;
  <mx:Script>
        <![CDATA[

        import mx.collections.ArrayCollection;

        [Bindable]
        public var storyCards:ArrayCollection;

        private function updateStory():void
        {
           trace("success");
        }       

        ]]>
  </mx:Script>

  <mx:TileList dataProvider="{storyCards}" myEvent="updateStory();">

        <mx:itemRenderer>

          <mx:Component>
            <mx:Metadata>
                [Event(name="myEvent", type="flash.events.Event")]
            </mx:Metadata>

        <mx:HBox>
          <mx:Label />
          <mx:TextInput keyUp="dispatchEvent(new Event('myEvent', true))" />
          <mx:TextArea text="{data.notes}" />
        </mx:HBox>

          </mx:Component>

        </mx:itemRenderer>

  </mx:TileList>
</mx:Canvas>

Here's how you would use it in a separate MXML Component:

<?xml version="1.0" encoding="utf-8"?>
<mx:Canvas xmlns:mx="http://www.adobe.com/2006/mxml"&gt;
  <mx:Script>
        <![CDATA[

        import mx.collections.ArrayCollection;

        [Bindable]
        public var storyCards:ArrayCollection;

        private function updateStory():void
        {
           trace("success");
        }       

        ]]>
  </mx:Script>

  <mx:TileList dataProvider="{storyCards}" myEvent="updateStory();" itemRenderer="StoryEditor" />
</mx:Canvas>

StoryEditor.mxml:

<mx:HBox xmlns:mx="http://www.adobe.com/2006/mxml"&gt;
    <mx:Metadata>
        [Event(name="myEvent", type="flash.events.Event")]
    </mx:Metadata>

    <mx:Label />

    <mx:TextInput keyUp="dispatchEvent(new Event('myEvent', true));" />

    <mx:TextArea text="{data.notes}" />
</mx:HBox>
Eric Belair