1 ///////////////////////////////////////////////////////////////////////////////
\r
2 // RSS Reader example widget that demonstrates use of the WRTKit UI toolkit
\r
3 // in a real-world widget.
\r
5 // Feed update frequency.
\r
6 var updateFrequencyOptions = [
\r
7 { value: -1, text: "never" },
\r
8 { value: (1000 * 60 * 5), text: "every 5 min" },
\r
9 { value: (1000 * 60 * 15), text: "every 15 min" },
\r
10 { value: (1000 * 60 * 60), text: "every 60 min" },
\r
13 // Feed update broker.
\r
14 var feedUpdateBroker = null;
\r
16 // Reference to current feed items controls.
\r
17 var feedItemControls = [];
\r
19 // Feed item control pool.
\r
20 var feedItemControlPool = [];
\r
22 // Time when the feed was last modified.
\r
23 var feedLastModified = null;
\r
25 // Flag that tracks if a feed update is commanded or automatic.
\r
26 var feedUpdateCommanded = false;
\r
28 // Reference to the WRTKit user interface manager and views.
\r
33 // Reference to settings controls.
\r
37 var feedUpdateFrequencySelection;
\r
38 var settingsSaveButton;
\r
39 var settingsCancelButton;
\r
41 // Constants for menu item identifiers.
\r
42 var MENU_ITEM_SETTINGS = 0;
\r
43 var MENU_ITEM_REFRESH = 1;
\r
44 var MENU_ITEM_ABOUT = 2;
\r
46 // Feed update timer identifier.
\r
47 var updateTimerId = null;
\r
52 // Feed name, URL and update frequency (in milliseconds; -1 if no auto update).
\r
53 var feedName = "CNN Top Stories";
\r
54 var feedURL = "http://rss.cnn.com/rss/cnn_topstories.rss";
\r
55 //var feedURL = "feed.xml";
\r
56 var feedUpdateFrequency = -1;
\r
58 // Next scheduled update time; -1 if never.
\r
59 var feedUpdateTime = -1;
\r
61 // Called from the onload event handler to initialize the widget.
\r
63 if (window.widget) {
\r
64 // set tab-navigation mode and show softkeys
\r
65 widget.setNavigationEnabled(false);
\r
66 window.menu.showSoftkeys();
\r
69 var settingsMenuItem = new MenuItem("Settings", MENU_ITEM_SETTINGS);
\r
70 settingsMenuItem.onSelect = menuItemSelected;
\r
71 menu.append(settingsMenuItem);
\r
72 var refreshMenuItem = new MenuItem("Refresh", MENU_ITEM_REFRESH);
\r
73 refreshMenuItem.onSelect = menuItemSelected;
\r
74 menu.append(refreshMenuItem);
\r
75 var aboutMenuItem = new MenuItem("About", MENU_ITEM_ABOUT);
\r
76 aboutMenuItem.onSelect = menuItemSelected;
\r
77 menu.append(aboutMenuItem);
\r
83 // create UI manager
\r
84 uiManager = new UIManager();
\r
87 mainView = new ListView();
\r
89 // create settings view
\r
90 settingsView = new ListView(null, "Settings");
\r
93 aboutView = new ListView(null, "RSS Reader");
\r
95 // feed name control
\r
96 feedNameText = new TextField('feedNameText', "Feed name", feedName);
\r
97 settingsView.addControl(feedNameText);
\r
100 feedUrlText = new TextField('feedUrlText', "Feed URL", feedURL);
\r
101 settingsView.addControl(feedUrlText);
\r
103 // About lable control
\r
104 aboutLabel = new Label();
\r
105 aboutView.addControl(aboutLabel);
\r
107 // feed update frequency selection control
\r
108 feedUpdateFrequencySelection = new SelectionList(null, "Check for updates", updateFrequencyOptions);
\r
109 settingsView.addControl(feedUpdateFrequencySelection);
\r
111 // save settings button
\r
112 settingsSaveButton = new FormButton(null, "Save");
\r
113 settingsSaveButton.addEventListener("ActionPerformed", saveSettingsClicked);
\r
114 settingsView.addControl(settingsSaveButton);
\r
116 // cancel settings button
\r
117 settingsCancelButton = new FormButton(null, "Cancel");
\r
118 settingsCancelButton.addEventListener("ActionPerformed", showMainView);
\r
119 settingsView.addControl(settingsCancelButton);
\r
121 // display the main view if a feed has been configured
\r
122 // otherwise show the settings view
\r
123 if (feedURL != null) {
\r
129 // start feed update timer (called once every second)
\r
130 updateTimerId = setInterval(updateFeedTimerFunc, 1000);
\r
133 // Callback for when menu items are selected.
\r
134 function menuItemSelected(id) {
\r
136 case MENU_ITEM_SETTINGS:
\r
139 case MENU_ITEM_REFRESH:
\r
142 case MENU_ITEM_ABOUT:
\r
148 // Loads widget preferences.
\r
149 function loadPreferences() {
\r
150 if (window.widget) {
\r
151 // read feed URL, name and update frequency from the widget settings
\r
153 if (typeof widget.preferenceForKey("FeedURL") != 'undefined' && typeof widget.preferenceForKey("FeedName") != 'undefined') {
\r
154 feedURL = widget.preferenceForKey("FeedURL");
\r
155 feedName = widget.preferenceForKey("FeedName");
\r
156 var feedUpdateFrequencyStr = widget.preferenceForKey("FeedUpdateFrequency");
\r
157 feedUpdateFrequency = (feedUpdateFrequencyStr == null) ? -1 : parseInt(feedUpdateFrequencyStr);
\r
162 // Loads widget preferences.
\r
163 function savePreferences() {
\r
164 if (window.widget) {
\r
165 // save settings in widget preferences store
\r
166 widget.setPreferenceForKey(feedURL, "FeedURL");
\r
167 widget.setPreferenceForKey(feedName, "FeedName");
\r
168 widget.setPreferenceForKey(feedUpdateFrequency.toString(), "FeedUpdateFrequency");
\r
172 // Callback for settings view save button.
\r
173 function saveSettingsClicked() {
\r
174 // remember old URL
\r
175 var oldURL = feedURL;
\r
177 // update feed name and URL
\r
178 var selectedFeed = feedUrlText.getText();
\r
180 if (selectedFeed != null) {
\r
181 feedURL = selectedFeed;
\r
182 feedName = feedNameText.getText();
\r
188 // update frequency
\r
189 var selectedFrequency = feedUpdateFrequencySelection.getSelected();
\r
190 feedUpdateFrequency = (selectedFrequency != null) ? selectedFrequency.value : -1;
\r
192 // save preferences
\r
195 // return to main view
\r
198 // update the feed if the feed URL has changed
\r
199 if (feedURL != oldURL) {
\r
200 feedLastModified = null;
\r
207 function showMainView() {
\r
208 // set main view caption from feed name
\r
209 var mainViewCaption = (feedName == null) ? null : feedName;
\r
210 mainView.setCaption(mainViewCaption);
\r
212 // set right softkey to "exit"
\r
213 if (window.widget) {
\r
214 menu.setRightSoftkeyLabel("", null);
\r
217 // show the main view
\r
218 uiManager.setView(mainView);
\r
221 // Show settings view.
\r
222 function showSettings() {
\r
224 feedNameText.setText(feedName);
\r
227 feedUrlText.setText(feedURL);
\r
230 var feedUpdateFrequencyOption = feedUpdateFrequencySelection.getOptionForValue(feedUpdateFrequency);
\r
231 feedUpdateFrequencySelection.setSelected(feedUpdateFrequencyOption);
\r
233 if (feedURL == null) {
\r
234 // no valid configuration
\r
235 // disable cancel button - set right softkey to "exit"
\r
236 settingsCancelButton.setEnabled(false);
\r
237 if (window.widget) {
\r
238 menu.setRightSoftkeyLabel("", null);
\r
241 // we have a valid configuration
\r
242 // enable cancel button - set right softkey to "cancel"
\r
243 settingsCancelButton.setEnabled(true);
\r
244 if (window.widget) {
\r
245 menu.setRightSoftkeyLabel("Cancel", showMainView);
\r
249 // show the settings view
\r
250 uiManager.setView(settingsView);
\r
253 //Displays the About view
\r
254 function showAboutView(){
\r
255 aboutLabel.setText("This Widget includes software licensed from Nokia © 2008");
\r
257 setAboutViewSoftkeys();
\r
258 uiManager.setView(aboutView);
\r
261 // Sets the softkeys for about view.
\r
262 function setAboutViewSoftkeys() {
\r
263 if (window.widget) {
\r
264 // set right softkey to "Ok" (returns to main view)
\r
265 menu.setRightSoftkeyLabel("Ok", showMainView);
\r
269 // Schedules an immediate feed update.
\r
270 function updateFeed() {
\r
271 feedUpdateTime = 0;
\r
272 feedUpdateCommanded = true;
\r
276 // Timer function for feed updates - called once every second.
\r
277 function updateFeedTimerFunc() {
\r
278 var now = new Date().getTime();
\r
280 // check if a feed update has been scheduled, if it's time to update now,
\r
281 // and if there's no update currently in progress and if we're in the main view
\r
282 if ((feedURL != null) &&
\r
283 (feedUpdateTime != -1) &&
\r
284 (now > feedUpdateTime) &&
\r
285 (feedUpdateBroker == null) &&
\r
286 (uiManager.getView() == mainView)) {
\r
287 // show progress dialog if this is a commanded feed update
\r
288 if (feedUpdateCommanded) {
\r
289 // no auto hiding, wait-type notification, unknown progress
\r
290 uiManager.showNotification(-1, "wait", "Loading feed...", -1);
\r
293 // fetch the feed from the specified URL
\r
294 feedUpdateBroker = new FeedUpdateBroker();
\r
295 feedUpdateBroker.fetchFeed(feedURL, feedUpdateCompleted);
\r
297 if (feedUpdateFrequency != -1) {
\r
298 // schedule next update
\r
299 feedUpdateTime = now + feedUpdateFrequency;
\r
301 // feed update frequency is "never"
\r
302 feedUpdateTime = -1;
\r
307 // Callback function that gets called when a feed update has completed.
\r
308 function feedUpdateCompleted(event) {
\r
309 if (event.status == "ok") {
\r
310 // if there aren't any feed items yet, we'll hide the progress dialog
\r
311 if (feedUpdateCommanded) {
\r
312 uiManager.hideNotification();
\r
315 // check if the feed has updated
\r
316 if (event.lastModified != feedLastModified) {
\r
317 // remember the last modified timestamp
\r
318 feedLastModified = event.lastModified;
\r
320 // feed fetched and parsed successfully
\r
321 setFeedItems(event.items);
\r
323 // focus the first feed item control
\r
324 // (but only if we are in the main view)
\r
325 if (uiManager.getView() == mainView) {
\r
326 feedItemControls[0].setFocused(true);
\r
330 // show error message
\r
331 uiManager.showNotification(3000, "warning", "Error while updating feed!<br/>(check network settings)");
\r
334 // null the broker reference to indicate that there's no current
\r
335 // update in progress
\r
336 feedUpdateBroker = null;
\r
338 // reset commanded feed update flag
\r
339 feedUpdateCommanded = false;
\r
342 // Removes feed items.
\r
343 function removeFeedItems() {
\r
344 // remove all current feed items from the main view
\r
345 for (var i = 0; i < feedItemControls.length; i++) {
\r
346 mainView.removeControl(feedItemControls[i]);
\r
349 // reset feed item control array
\r
350 feedItemControls = [];
\r
353 // Sets feed items.
\r
354 function setFeedItems(items) {
\r
355 // start by removing all current feed items
\r
358 // create new feed items and add them to the main view
\r
359 // use feed item pool to recycle controls
\r
360 for (var i = 0; i < items.length; i++) {
\r
361 // get a feed item control from the pool or create one and
\r
362 // place it in the pool if there aren't enough feed item controls
\r
363 var feedItemControl;
\r
364 if (i == feedItemControlPool.length) {
\r
365 feedItemControl = new ContentPanel(null, null, null, true);
\r
366 feedItemControlPool.push(feedItemControl);
\r
368 feedItemControl = feedItemControlPool[i];
\r
371 // initialize feed item control
\r
372 var item = items[i];
\r
373 feedItemControl.setCaption(item.title);
\r
374 feedItemControl.setContent(getContentHTMLForFeedItem(item));
\r
375 feedItemControl.setExpanded(false);
\r
377 // add the feed item control to the main view
\r
378 feedItemControls.push(feedItemControl);
\r
379 mainView.addControl(feedItemControl);
\r
383 // Returns the content HTML for a feed item.
\r
384 function getContentHTMLForFeedItem(item) {
\r
388 if (item.date != null) {
\r
389 buf += "<div class=\"FeedItemDate\">" + item.date + "</div>";
\r
392 // item description
\r
393 if (item.description != null) {
\r
394 buf += "<div class=\"FeedItemDescription\">" + item.description + "</div>";
\r
398 if (item.url != null) {
\r
399 buf += "<div class=\"FeedItemLink\">";
\r
400 buf += "<a href=\"JavaScript:void(0)\" onclick=\"openURL('" + item.url + "'); return false;\">";
\r
401 buf += "Read more...";
\r
410 function openURL(url) {
\r
411 if (window.widget) {
\r
413 widget.openURL(url);
\r
416 window.open(url, "NewWindow");
\r