PDA

View Full Version : Stuck in Event Handling in Nested Repeaters!


shubs6
12-18-2007, 11:27 AM
Aim of this application is to display RSS feed from a link in the LinkButtons inside a Panel which is created for each RSS feed link at runtime.

There are 3 files an RSSReader.mxml, Main.as, Configuration.xml.

Program Flow is like this -

1. Parent Panel (title="Sample Application") is created and on its preinitialize event loadConfig() is called. loadConfig() will load the Configuration.xml and fill in the XMLListCollection urlList with its childnodes (<url address="http://www.ndtv.com/convergence/ndtv/rssnat.asp" title="NDTV India news"/> etc..).
2. 1st Repeater (id="newsPanel") takes urlList as dataProvider and will loop as many times as we have urls in Configuration.xml (In our case we have 2 urls there.)
3. A VDividedBox and Panel pair are created inside this repeater and on the preinitialize event of the VDividedBox loadXML(String) is called. This function will fetch the RSSFeed of the link that we pass as the String parameter inside it. The RSS data that is fetched is stored as an XMLListCollection in externalXML.
4. externalXML acts as a dataProvider for the second Repeater (id="newsItems") and creates as many LinkButtons in the Panel as there are <title> tags in externalXML. The label on these linkButtons will display RSS feed to the end user.

Expected Results:
In the two pairs of VDividedBox-Panel, RSS feed from two different urls provided in Configuration.xml should be displayed.

Actual Results:
Run the project and you'll see that in BOTH pairs of VDividedBox-Panel, RSS feed from the first link is being displayed at runtime. And after a fraction of a second the RSS feed in both the Panels will get overwritten by RSS feed from the second link.

I guess the problem is that the event handling gets somewhat delayed so the dataProvider of internal Repeater is null and the internal Repeater executes after the external repeater is through with all its iterations.

Please see the code below. How do i handle this issue?
RSS_Reader.mxml

<?xml version="1.0" encoding="utf-8"?>
<mx:WindowedApplication xmlns:mx="http://www.adobe.com/2006/mxml" layout="vertical"
width="100%" height="100%" paddingLeft="5" paddingRight="5" paddingBottom="5"
paddingTop="5" horizontalAlign="left" >

<mx:Script source="Main.as"/>

<mx:Panel title="Sample Application" width="439" height="437"
paddingLeft="5" paddingRight="5" paddingBottom="5" paddingTop="5" borderColor="#AC41A8" color="#C7ECF1"
preinitialize="loadConfig()">

<!--Pending : Validate that only as many Divboxes are created as there are valid
urls in urlList-->
<mx:Repeater id="newsPanel" dataProvider="{urlList}" >

<mx:VDividedBox width="285" horizontalAlign="left" autoLayout="true" height="179"
preinitialize="loadXML(newsPanel.currentItem.@address)">

<mx:Panel title="{newsPanel.currentItem.@title}" layout="vertical" width="282"
paddingLeft="5" paddingRight="5" paddingBottom="5" paddingTop="5" horizontalAlign="left" >

<mx:Repeater width="100%" id="newsItems" dataProvider="{externalXML}" >

<mx:LinkButton id="lbtn" textAlign="center" alpha="0.5"
label="{getField(XML( newsItems[newsPanel.currentIndex].currentItem),qnTitle)}" />

</mx:Repeater>
</mx:Panel>
</mx:VDividedBox>
</mx:Repeater>
</mx:Panel>

</mx:WindowedApplication>

Main.as
// ActionScript file
import flash.events.Event;
import flash.net.navigateToURL;

import mx.collections.XMLListCollection;
import mx.controls.Alert;
import mx.formatters.DateFormatter;

public var error:Error
private var mxna:Namespace = new Namespace("http://purl.org/rss/1.0/");
private var dc:Namespace = new Namespace("http://purl.org/dc/elements/1.1/");

[Bindable]
private var externalXML:XMLListCollection;
[Bindable]
private var urlList:XMLListCollection;
[Bindable]
private var qnTitle:QName = new QName(mxna, "title");

private function loadXML(rssFeedURL : String):void
{
var loader:URLLoader = new URLLoader();
var request:URLRequest = new URLRequest(rssFeedURL);
loader.load(request);
loader.addEventListener(IOErrorEvent.IO_ERROR, catchIOError);
loader.addEventListener(Event.COMPLETE, onComplete);
}

private function onComplete(event:Event):void
{
var loader:URLLoader = URLLoader(event.target);
var dataXML:XML = XML(loader.data);

if (dataXML.length()== 0) return
else
{
var qnItems:QName = new QName(mxna, "item");
dataXML.addNamespace(mxna);
var base:XMLList = dataXML.descendants(qnItems);
externalXML = new XMLListCollection(base);
}
}

private function loadConfig():void
{
var loader:URLLoader = new URLLoader();
var request:URLRequest = new URLRequest("Configuration.xml");
loader.load(request);
loader.addEventListener(IOErrorEvent.IO_ERROR, catchIOError);
loader.addEventListener(Event.COMPLETE, onConfigComplete);
}

private function onConfigComplete(event:Event):void
{
var loader:URLLoader = URLLoader(event.target);
var dataXML:XML = new XML(loader.data);
var childNodes:XMLList = dataXML.urlconf.url;
urlList = new XMLListCollection(childNodes);
}

private function getField( itemXML:XML, field:QName ):String
{
return itemXML.descendants( field ).toString();
}

private function catchIOError(event:IOErrorEvent) : void
{
Alert.show("IOError caught - Plz put a valid string in Text input");
trace("Error caught: "+event.type);
}

Configuration.xml
<urlconf>
<url address="http://www.ndtv.com/convergence/ndtv/rssnat.asp" title="NDTV India news"/>
<url address="http://rss.news.yahoo.com/rss/topstories" title="Yahoo Top Stories"/>
</urlconf>