You are viewing a plain text version of this content. The canonical link for it is here.
Posted to cvs@cocoon.apache.org by je...@apache.org on 2005/10/02 14:41:24 UTC

svn commit: r293104 - in /cocoon/blocks: ajax/trunk/java/org/apache/cocoon/ajax/resources/js/ ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/ ajax/trunk/samples/ ajax/trunk/samples/i18n/ forms/trunk/java/org/apache/cocoon/forms/resources/ form...

Author: jeremy
Date: Sun Oct  2 05:41:05 2005
New Revision: 293104

URL: http://svn.apache.org/viewcvs?rev=293104&view=rev
Log:
Updating CForms to use the prototype.js lib for all AJAX work.
Adding TimedBrowserUpdater and sample to the Ajax Block

Added:
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/browserupdater.js
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/domutils.js
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/timedbrowserupdater.js
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml
    cocoon/blocks/ajax/trunk/samples/i18n/
    cocoon/blocks/ajax/trunk/samples/i18n/timedbrowserupdater.xml
    cocoon/blocks/ajax/trunk/samples/timed-updater.xml
Modified:
    cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/cocoon-ajax.js
    cocoon/blocks/ajax/trunk/samples/flow.js
    cocoon/blocks/ajax/trunk/samples/sitemap.xmap
    cocoon/blocks/ajax/trunk/samples/welcome.xml
    cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/forms-field-styling.xsl
    cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/js/cforms.js
    cocoon/blocks/forms/trunk/samples/sitemap.xmap

Added: cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/browserupdater.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/browserupdater.js?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/browserupdater.js (added)
+++ cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/browserupdater.js Sun Oct  2 05:41:05 2005
@@ -0,0 +1,275 @@
+/*
+ * Copyright 1999-2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* @version $Id$ */
+
+
+BrowserUpdater = Class.create();
+Object.extend(Object.extend(BrowserUpdater.prototype, Ajax.Request.prototype), {
+  initialize: function(url, options) {
+    this.transport = Ajax.getTransport();
+    this.setOptions(options);
+
+    var onComplete = this.options.onComplete || Prototype.emptyFunction;
+    this.options.onComplete = (function() {
+    	if (this.checkContinue(this.options.form)) {
+				this.updateContent();
+				onComplete(this.transport);
+      }
+    }).bind(this);
+
+    this.request(url);
+  },
+
+  updateContent: function() {
+		var doc = this.transport.responseXML;
+    if (doc) {
+				var nodes = doc.documentElement.childNodes;
+				for (var i = 0; i < nodes.length; i++) {
+						var node = nodes[i];
+						if (node.nodeType == DOMUtils.ELEMENT_NODE) {
+								var handler;
+								if (node.localName) {
+										handler = node.localName;
+								} else {
+										// No DOM2 support (IE6)
+										handler = node.nodeName.replace(/.*:/, "");
+								}
+								var handlerFunc = BrowserUpdater.handlers[handler];
+								if (handlerFunc) {
+										handlerFunc(node);
+								} else {
+										this.handleError("No handler found for element " + handler, this.transport);
+										return;
+								}
+						}
+				}
+    } else {
+    	this.handleError("No xml answer", this.transport);
+      return;
+    }
+
+    if (this.responseIsSuccess()) {
+      if (this.onComplete) {
+        setTimeout((function() {this.onComplete(this.transport)}).bind(this), 10);
+      }
+			document.body.style.cursor = "auto";
+			self.status = "Update Complete";
+    }
+  },
+  
+  checkContinue: function(form) {
+  	if (!form) return true;
+		var xca;
+		try { // An exception is thrown if header doesn't exist (at least in Moz)
+				xca = this.transport.getResponseHeader("X-Cocoon-Ajax");
+		} catch (e) {
+				// header doesn't exist
+		}
+		if (xca == "continue") {
+			// Interaction with this page is finished: redirect the browser to the form's action URL
+			// Get the continuation-id, if any.
+			var contParam = '?cocoon-ajax-continue=true';
+			if (form.elements && form.elements["continuation-id"]) {
+					contParam += "&continuation-id=" + form.elements["continuation-id"].value;
+			}
+			window.location.href = form.action + contParam;
+			return false;
+    } else {
+			return true;
+		}
+  },
+
+	handleError: function(message, request) {
+    if (confirm(message + "\nShow server response?")) {
+        var w = window.open(undefined, "Cocoon Error", "location=no");
+        if (w == undefined) {
+            alert("You must allow popups from this server to display the response.");
+        } else {
+	        var doc = w.document;
+	        doc.open();
+	        doc.write(request.responseText);
+	        doc.close();
+	    }
+    }
+	}
+	
+});
+
+BrowserUpdater.handlers = {
+    replace :  function(element) {
+        var id = element.getAttribute("id");
+        if (!id) {
+           alert("no id found on update element");
+           return;
+        }    
+        // Get the first child element (the first child may be some text!)
+        var firstChild = DOMUtils.firstChildElement(element);
+    
+        var oldElement = document.getElementById(id);
+        
+        if (!oldElement) {
+            alert("no element '" + id + "' in source document");
+            return;
+        }
+    
+        var newElement = DOMUtils.importNode(firstChild, document);
+        
+        // Warn: it's replace(new, old)!!
+        oldElement.parentNode.replaceChild(newElement, oldElement);
+        // Ensure the new node has the correct id
+        newElement.setAttribute("id", id);
+        
+        if (BrowserUpdater.highlight) {
+           BrowserUpdater.highlight(newElement);
+        }
+    }
+
+}
+
+// NB. This will probably be replaced with scriptaculous Effects
+
+
+
+//-------------------------------------------------------------------------------------------------
+// Fader used to highlight page areas that have been updated
+//-------------------------------------------------------------------------------------------------
+
+/**
+ * Create a fader that will progressively change an element's background color from
+ * a given color back to its original color.
+ *
+ * @param elt the element to fade
+ * @param color the starting color (default yellow)
+ * @param duration the fade duration in msecs (default 1000)
+ * @param fps the animation frames per seconds (default 25)
+ */
+function Fader(elt, color, duration, fps) {
+   // Set default values
+   if (!color) color = "#FFFF80"; // yellow
+   if (!duration) duration = 1000; // 1 sec
+   if (!fps) fps = 25; // 25 frames/sec
+   
+   this.element = elt;
+   this.fromColor = Fader.colorToRgb(color);
+   this.toColor = Fader.colorToRgb(Fader.getBgColor(this.element));
+   
+   this.maxFrames = Math.round(fps * duration / 1000.0);
+   this.delay = duration / this.maxFrames;
+}
+
+/**
+ * Creates a default fader for a given element. This function can be used to set BrowserUpdate.highlight
+ */
+Fader.fade = function(elt) {
+   new Fader(elt).start();
+}
+
+Fader.prototype.start = function() {
+   this.frame = 0;
+   this._changeColor();
+}
+
+Fader.prototype._changeColor = function() {
+    if (this.frame < this.maxFrames) {
+        // Schedule the next iteration right now to keep a more accurate timing
+        var fader = this;
+        setTimeout(function() {fader._changeColor();}, this.delay);
+    }
+    var newColor = new Array(3);
+    for (var channel = 0; channel < 3; channel++) {
+        newColor[channel] = Math.floor(
+            this.fromColor[channel] * ((this.maxFrames - this.frame) / this.maxFrames) +
+            this.toColor[channel] * (this.frame/this.maxFrames)
+        );
+    }
+
+    this.frame++;
+    var color = Fader.rgbToColor(newColor[0], newColor[1], newColor[2]);
+    this.element.style.backgroundColor = color;
+}
+
+/** Converts a "#RRGGBB" color as an array of 3 ints */
+Fader.colorToRgb = function(hex) {
+    return [
+        parseInt(hex.substr(1,2),16),
+        parseInt(hex.substr(3,2),16),
+        parseInt(hex.substr(5,2),16) ];
+}
+
+/** Converts rgb values to a "#RRGGBB" color */
+Fader.rgbToColor = function(r, g, b) {
+    r = r.toString(16); if (r.length == 1) r = '0' + r;
+    g = g.toString(16); if (g.length == 1) g = '0' + g;
+    b = b.toString(16); if (b.length == 1) b = '0' + b;
+    return "#" + r + g + b;
+}
+
+/** Get the background color of an element */
+Fader.getBgColor = function(elt) {
+    while(elt) {
+        var c;
+        if (window.getComputedStyle) c = window.getComputedStyle(elt,null).getPropertyValue("background-color");
+        if (elt.currentStyle) c = elt.currentStyle.backgroundColor;
+        if ((c != "" && c != "transparent") || elt.tagName == "BODY") { break; }
+        elt = elt.parentNode;
+    }
+    if (c == undefined || c == "" || c == "transparent" || c == "white") c = "#FFFFFF";
+
+    var rgb = c.match(/rgb\s*\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*\)/);
+    if (rgb) return this.rgbToColor(parseInt(rgb[1]),parseInt(rgb[2]),parseInt(rgb[3]));
+    return c;
+}
+
+BrowserUpdater.highlight = Fader.fade;
+
+//-------------------------------------------------------------------------------------------------
+// Blinker used to highlight page areas that have been updated
+//-------------------------------------------------------------------------------------------------
+
+function Blinker(elt, color, hltDelay, normalDelay, blinks) {
+    this.element = elt;
+    if (!color) color = "#FFFF80"; // yellow
+    if (!hltDelay) hltDelay = 100;
+    if (!normalDelay) normalDelay = 100;
+    if (!blinks) blinks = 2;
+    
+    this.hltColor = color;
+    this.hltDelay = hltDelay;
+    this.normalDelay = normalDelay;
+    this.normalColor = Fader.getBgColor(elt);
+    this.maxBlinks = blinks * 2;
+    this.blink = 0;
+}
+
+Blinker.prototype.start = function() {
+   this.blink = 0;
+   this._doBlink();
+}
+
+Blinker.blink = function(elt) {
+   new Blinker(elt).start();
+}
+
+Blinker.prototype._doBlink = function() {
+   var hlt = (this.blink % 2 == 0);
+   this.element.style.backgroundColor = hlt ? this.hltColor : this.normalColor;;
+   if (this.blink <= this.maxBlinks) {
+      var blinker = this;
+      setTimeout(function() {blinker._doBlink();}, hlt ? this.hltDelay : this.normalDelay);
+   }
+   this.blink++;
+}

Modified: cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/cocoon-ajax.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/cocoon-ajax.js?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/cocoon-ajax.js (original)
+++ cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/cocoon-ajax.js Sun Oct  2 05:41:05 2005
@@ -31,6 +31,8 @@
         this.require(path + 'dragdrop.js');
         this.require(path + 'controls.js');
         this.require(path + 'slider.js');
+        this.require(path + 'browserupdater.js');
+        this.require(path + 'domutils.js');
         return;
       }
     }

Added: cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/domutils.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/domutils.js?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/domutils.js (added)
+++ cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/domutils.js Sun Oct  2 05:41:05 2005
@@ -0,0 +1,91 @@
+/*
+ * Copyright 1999-2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+DOMUtils = {
+    // Stupid IE doesn't have these constants
+    ELEMENT_NODE : 1,
+    ATTRIBUTE_NODE : 2,
+    TEXT_NODE : 3,
+    CDATA_SECTION_NODE : 4,
+    ENTITY_REFERENCE_NODE : 5,
+    ENTITY_NODE : 6,
+    PROCESSING_INSTRUCTION_NODE : 7,
+    COMMENT_NODE : 8,
+    DOCUMENT_NODE : 9,
+    DOCUMENT_TYPE_NODE : 10,
+    DOCUMENT_FRAGMENT_NODE : 11
+}
+
+/**
+ * Get the first child element of an element, ignoring text nodes
+ */
+DOMUtils.firstChildElement = function(element) {
+    var nodes = element.childNodes;
+    for (var i = 0; i < nodes.length; i++) {
+        var node = nodes[i];
+        if (node.nodeType == this.ELEMENT_NODE) {
+            return node;
+        }
+    }
+}
+
+/**
+ * Imports an element into a document, taking care of using the correct implementation
+ * so that the browser interprets it as displayable XML
+ */
+DOMUtils.importNode = function(node, targetDoc) {
+    if(node.xml) {
+        // IE
+        var div = targetDoc.createElement("DIV");
+        div.innerHTML = node.xml;
+        return this.firstChildElement(div);
+    } else {
+        return DOMUtils._importNode(node, targetDoc);
+    }
+}
+
+/**
+ * DOM implementation of importNode, recursively creating nodes
+ */
+DOMUtils._importNode = function(node, targetDoc) {
+    switch(node.nodeType) {
+        case this.ELEMENT_NODE:
+            var element = targetDoc.createElement(node.nodeName);
+            //var element = targetDoc.createElementNS(node.namespaceURI, node.nodeName);
+            var attrs = node.attributes;
+            for (var i = 0; i < attrs.length; i++) {
+                attr = attrs[i];
+                element.setAttribute(attr.nodeName, attr.nodeValue);
+                //element.setAttributeNS(attr.namespaceURI, attr.nodeName, attr.nodeValue);
+            }
+            var children = node.childNodes;
+            for (var j = 0; j < children.length; j++) {
+                var imported = this.importNode(children[j], targetDoc);
+                if (imported) element.appendChild(imported);
+            }
+            return element;
+        break;
+        
+        case this.TEXT_NODE:
+            return targetDoc.createTextNode(node.nodeValue);
+        break;
+        
+        case this.CDATA_SECTION_NODE:
+            return targetDoc.createTextNode(node.nodeValue);
+        break;
+    }
+}
+

Added: cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/timedbrowserupdater.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/timedbrowserupdater.js?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/timedbrowserupdater.js (added)
+++ cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/js/timedbrowserupdater.js Sun Oct  2 05:41:05 2005
@@ -0,0 +1,218 @@
+/*
+ * Copyright 1999-2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/* @version $Id$ */
+
+
+TimedBrowserUpdater = Class.create();
+TimedBrowserUpdater.prototype = Object.extend(new Ajax.Base(), {
+  initialize: function(url, options) {
+    this.setOptions(options);
+    this.onComplete = this.options.onComplete;
+		this.autostart = (this.options.autostart || true); // default autostart: true
+    this.frequency = (this.options.frequency || 30);  // default frequency: 5 minutes
+    this.decay = 1;																		 // default decay: none
+		this.populated = false;
+    this.updater = {};
+    this.widgets = {};
+    this.url = url;
+		this.timerIsRunning = false;
+    this.start();
+  },
+
+  start: function() {
+    this.options.onComplete = this.updateComplete.bind(this);
+    this.onTimerEvent();
+    this.timerIsRunning = true;
+    self.status = "Timer Starting";
+  },
+
+  stop: function() {
+    this.updater.onComplete = undefined;
+    clearTimeout(this.timer);
+    this.timerIsRunning = false;
+    //(this.onComplete || Ajax.emptyFunction).apply(this, arguments);
+    self.status = "Timer Stoping";
+  },
+
+  updateComplete: function(request) {
+    if (this.options.decay) {
+      this.decay = (request.responseText == this.lastText ? 
+        this.decay * this.options.decay : 1);
+
+      this.lastText = request.responseText;
+    }
+    this.updateWidgets(request.responseXML);
+    this.timer = setTimeout(this.onTimerEvent.bind(this), this.decay * this.frequency * 1000);
+  },
+
+  onTimerEvent: function() {
+    if (this.populated) {
+    	this.options.postBody = this.buildQueryString();
+    	this.updater = new BrowserUpdater(this.url, this.options);
+    	    self.status = "Timer fired event";
+    } else {
+    	this.timer = setTimeout(this.onTimerEvent.bind(this), this.decay * this.frequency * 1000);
+    }
+  },
+  
+  updateWidgets: function(doc) {
+		var nodes = doc.documentElement.childNodes;
+		for (var i = 0; i < nodes.length; i++) {
+			var node = nodes[i];
+			if (node.nodeType == DOMUtils.ELEMENT_NODE) {
+				this.widgets[node.getAttribute("id")] = node.getAttribute("state");
+			}
+		}
+	},
+
+	registerWidget: function(id, state) {
+		this.widgets[id] = state;
+		this.populated = true;
+	},
+	
+	buildQueryString: function () {
+		var result = "cocoon-ajax=true";
+		for (var key in this.widgets) {
+			result += "&" + encodeURIComponent(key) + "=" + encodeURIComponent(this.widgets[key]);
+		}
+		// see if there is a form with a continuation parameter
+		for (var form in document.forms) {
+			if (form != null && form.elements != null && form.elements["continuation-id"] != null) {
+				result += "&continuation-id=" + form.elements["continuation-id"].value;
+				break;
+			}
+		}
+		self.status = result;
+		return result;
+	}
+	
+});
+
+TimedBrowserUpdater.Console = Class.create();
+TimedBrowserUpdater.Console.prototype = Object.extend(new Ajax.Base(), {
+	initialize: function(client, options) {
+		this.expires = 604800000; // cookie expiry, 1 week
+		this.client = client;
+		this.setOptions(options);
+		this.console = this.options.console;
+		this.message("Initialise");
+    this.isRunningTitle = ( this.options.isRunningTitle || "ON" );
+		this.notRunningTitle = ( this.options.notRunningTitle || "OFF" );
+		this.isRunningHint = ( this.options.isRunningHint || "Click to Stop" );
+		this.notRunningHint = ( this.options.notRunningHint || "Click to Start" );
+		this.frequencyControl = this.options.frequencyControl;
+		this.toggleControl = this.options.toggleControl;
+		
+		var autorun = this.getPreference( "TimedBrowserUpdater.autorun" );
+		if ( autorun == undefined ) {
+			this.message("Autorun undefined");
+			this.startTimer(  );
+		} else if ( autorun == "true" ) {
+			this.message("Autorun true");
+			this.startTimer(  );
+		} else {
+			this.message("Autorun false");
+			this.stopTimer(  );
+		}
+		
+		var frequency =  this.getPreference( "TimedBrowserUpdater.frequency" );
+		if ( frequency == undefined ) frequency = 300;
+		this.setFrequency(frequency);
+	},
+	
+	message: function(message) {
+		if (this.console != undefined) {
+			this.console.value = this.console.value + "\n" + message;
+		} else {
+			self.status = message;
+		}
+	},
+	
+	toggleTimer: function() {
+		if (this.client.timerIsRunning) {
+			this.stopTimer();
+		} else {
+			this.startTimer();
+		}
+	},
+	
+	startTimer: function() {
+			if (!this.client.timerIsRunning) {
+				this.client.start(  );
+				this.message("Client Started");
+			}
+			this.setPreference( "TimedBrowserUpdater.autorun", "true" );
+			this.toggleControl.value = this.isRunningTitle;
+			this.toggleControl.title =  this.isRunningHint;
+	},
+
+	stopTimer: function() {
+			if (this.client.timerIsRunning) {
+				this.client.stop(  );
+				this.message("Client Stopped");
+			}
+			this.setPreference( "TimedBrowserUpdater.autorun", "false" );
+			this.toggleControl.value = this.notRunningTitle;
+			this.toggleControl.title =  this.notRunningHint;
+	},	
+	
+	setFrequency: function() {
+		var frequency = this.frequencyControl.value;
+		this.client.frequency = frequency;
+		this.setPreference( "TimedBrowserUpdater.frequency", frequency );
+		for ( var i=0;i < this.frequencyControl.options.length;i++ ) {
+			if ( frequency == this.frequencyControl.options[i].value ) {
+				this.frequencyControl.selectedIndex = i;
+				break;
+			}
+		}
+	},
+	
+	setPreference: function(name, value) {
+		var expiredate = new Date();
+		expiredate.setTime(expiredate.getTime() + this.expires);
+		document.cookie = name + "=" + value + "; expires=" + expiredate.toGMTString() + "; path=/";
+		this.message("Set Preference: " + name + ": " + value);
+	},
+
+	getPreference: function(name){
+		var neq = name + "=";
+		var k = document.cookie.split(';');
+		for (var i=0; i < k.length; i++) {
+			var c = k[i];
+			while (c.charAt(0)==' ') c = c.substring(1,c.length);
+			if (c.indexOf(neq) == 0) {
+				var result = c.substring(neq.length,c.length);
+				this.message( "Read Preference: " + name + ": " + result);
+				return result;
+			}
+		}
+		this.message( "Read Preference: " + name + ": undefined");
+		return undefined;
+	}
+
+
+
+});
+
+TimedBrowserUpdaterInstance = new TimedBrowserUpdater(
+	document.location, 
+	{
+		method: 'post', 
+		onFailure: BrowserUpdater.handleError
+	}
+);

Added: cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml (added)
+++ cocoon/blocks/ajax/trunk/java/org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml Sun Oct  2 05:41:05 2005
@@ -0,0 +1,188 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  Copyright 1999-2005 The Apache Software Foundation
+
+  Licensed under the Apache License, Version 2.0 (the "License");
+  you may not use this file except in compliance with the License.
+  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+-->
+<!--
+  @version $Id$
+-->
+
+<!-- An implementation of the TimedBrowserUpdate template engine as a JXTemplate tag library -->
+    
+    <!--+	Usage Instructions
+    		+
+    		+		The purpose of this Macro is to make regions in a webpage 
+    		+		that update themselves periodically without user interaction.
+    		+		This is implemented using AJAX techniques taken from CForms.
+    		+
+    		+		1. Import this macro into your JXTemplate :
+    		+
+    		+			<jx:import uri="resource://org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml"/>
+    		+
+    		+		2. Use the tags in your page where you want auto-updating to occur :
+    		+
+    		+			<tbu:replace id="element.id" state="${change.value}">
+    		+				<td id="element.id">
+    		+					Your value is: <b>${change.value}</b>
+    		+				</td>
+				+			</tbu:replace>
+				+
+				+			Where:
+				+				"element.id" is an id that is unique to your page
+				+				"change.value" is the value that you are primarilily interested in tracking
+				+				i.e. the update is only made if this value changes.
+				+
+				+			Note: The id attribute of both the <tbu:replace> and the child of <tbu:replace> 
+				+			would normally be the same as this indicates that this is the element being replaced.
+				+			Only the first child of <tbu:replace> is used.
+    		+
+    		+		3. Add the BrowserUpdateTransformer to your pipeline, after the JXTGenerator.
+    		+
+    		+			<map:transform type="browser-update"/>
+    		+
+    		+		4. Have your page load the JavaScript.
+    		+
+				+			<script type="text/javascript" src="resources/ajax/js/cocoon-ajax.js"/>
+				+			<script type="text/javascript" src="resources/ajax/js/timedbrowserupdater.js"/>
+    		+
+    		+		5. Effect
+    		+
+    		+			When the page is first loaded, it will display all of it's content normally, 
+    		+			including the content of the <tbu:replace> tags.
+    		+			Thereafter, every 5 minutes, the regions inside <tbu:replace> tags will 
+    		+			automatically update, having retrieved any changed values via an XMLHTTPRequest
+    		+			in the background, to the same URI as the page.
+    		+
+    		+		6. Console
+    		+
+    		+		There is an optional sample console to control TimedBrowserUpdate.
+    		+
+    		+			<tbu:console i18nCatalogue="catalogue.name"/>
+    		+
+    		+		This outputs a simple form to control the Updater.
+    		+		It is not designed to be placed on the page more than once.
+    		+
+    		+		You need to supply the name of an i18n Catalogue that contain terms used by the console
+    		+		and you need to ensure that the I18nTransformer is in your pipeline.
+    		+
+    		+		The Console used these i18n keys :
+    		+
+    		+			tbu.name.title						the label in the console
+    		+			tbu.name.hint							the hint of the console
+    		+			tbu.delay.title						the label of the delay control
+    		+			tbu.delay.hint            the hint of the delay control
+    		+			tbu.delay.30  						delay for 300 secs
+    		+			tbu.delay.60  						delay for 60 secs
+    		+			tbu.delay.120  	  				delay for 120 secs
+    		+			tbu.delay.300   					delay for 300 secs
+    		+			tbu.delay.600   					delay for 600 secs
+    		+			tbu.isrunning.title				button text for running state
+    		+			tbu.isrunning.hint				button hint for running state
+    		+			tbu.notrunning.title			button text for not running state
+    		+			tbu.notrunning.hint				button hint for not running state
+    		+			
+    		+-->
+    
+    
+    
+<jx:template 	xmlns:jx="http://apache.org/cocoon/templates/jx/1.0"
+							xmlns:bu="http://apache.org/cocoon/browser-update/1.0"
+							xmlns:tbu="http://apache.org/cocoon/timed-browser-update/1.0"
+							xmlns:i18n="http://apache.org/cocoon/i18n/2.1">
+
+    <jx:macro name="replace" targetNamespace="http://apache.org/cocoon/timed-browser-update/1.0">
+      <jx:parameter name="id"/>
+      <jx:parameter name="state"/>
+			<jx:choose>
+				<jx:when test="${cocoon.request.getParameter('cocoon-ajax') == 'true' &amp;&amp; cocoon.request.getParameter(id) != state}">
+					<bu:replace id="${id}" state="${state}">
+						<jx:evalBody/>
+					</bu:replace>
+				</jx:when>
+				<jx:otherwise>
+					<script language="Javascript">
+						TimedBrowserUpdaterInstance.registerWidget("${id}","${state}");
+					</script>
+					<jx:evalBody/>
+				</jx:otherwise>
+			</jx:choose>
+    </jx:macro>
+
+
+    <jx:macro name="console" targetNamespace="http://apache.org/cocoon/timed-browser-update/1.0">
+			<jx:parameter name="i18nCatalogue"/>
+			
+			<form id="tbuconsole" name="tbuconsole">
+				<table class="tbuConsole" title="${i18nCatalogue}:tbu.name.hint" i18n:attr="title">
+					<tr>
+						<th class="tbuName">
+							<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.name.title</i18n:text>
+						</th>
+						<td class="tbuRunning">
+							<input id="tbuToggleRunButton" 
+								type="button" 
+								title="" 
+								value="" 
+								onClick="TimedBrowserConsole.toggleTimer();"  
+								tabindex="32000"
+							/>
+						</td>
+					</tr>
+					<tr>
+						<th class="tbuFrequencyTitle">
+							<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.title</i18n:text>
+						</th>
+						<td class="tbuFrequency">
+							<select id="tbuFrequencySelector" 
+								size="1" 
+								onchange="TimedBrowserConsole.setFrequency();" 
+								title="${i18nCatalogue}:tbu.frequency.hint"
+								i18n:attr="title"
+								tabindex="32001"
+							>
+								<option value="30"><i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.30</i18n:text></option>
+								<option value="60"><i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.60</i18n:text></option>
+								<option value="120"><i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.120</i18n:text></option>
+								<option value="300"><i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.300</i18n:text></option>
+								<option value="600"><i18n:text i18n:catalogue="${i18nCatalogue}">tbu.frequency.600</i18n:text></option>
+							</select>
+						</td>
+					</tr>
+					<!-- uncomment this row to see the debug console -->
+					<!--<tr>
+						<th align="top">console</th>
+						<td class="tbuDebugConsole">
+							<textarea id="tbuConsole" rows="10" cols="40"></textarea>
+						</td>
+					</tr>-->
+				</table>
+			</form>
+			<script language="Javascript">
+				TimedBrowserConsole = new TimedBrowserUpdater.Console (
+					TimedBrowserUpdaterInstance,
+					{
+						frequencyControl: $("tbuFrequencySelector"),
+						toggleControl: $("tbuToggleRunButton"),
+						console: $("tbuDebugConsole"),
+						isRunningTitle: "<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.isrunning.title</i18n:text>",
+						notRunningTitle: "<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.notrunning.title</i18n:text>",
+						isRunningHint: "<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.isrunning.hint</i18n:text>",
+						notRunningHint: "<i18n:text i18n:catalogue="${i18nCatalogue}">tbu.notrunning.hint</i18n:text>"
+					}
+				)
+			</script>
+		</jx:macro>
+
+
+</jx:template>

Modified: cocoon/blocks/ajax/trunk/samples/flow.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/samples/flow.js?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/ajax/trunk/samples/flow.js (original)
+++ cocoon/blocks/ajax/trunk/samples/flow.js Sun Oct  2 05:41:05 2005
@@ -17,6 +17,10 @@
 /**
  * @version $Id$
  */
+
+importClass(Packages.java.util.Calendar);
+
+
 var resolver = cocoon.getComponent(org.apache.excalibur.source.SourceResolver.ROLE);
 
 function fileBrowserSuggest() {
@@ -49,4 +53,15 @@
     
     cocoon.sendPage("display-suggestions", { suggestions: suggestions, selection: cocoon.request.getParameter("filename")});
     
+}
+
+function timedUpdateDemo() {
+	var calendar = Calendar.getInstance();
+	var data = {
+		time: calendar.getTime(),
+		hour: calendar.get(Calendar.HOUR_OF_DAY),
+		 min: calendar.get(Calendar.MINUTE),
+		rand: Math.random()
+	};
+	cocoon.sendPage("timed-updater-screen", {data: data});
 }

Added: cocoon/blocks/ajax/trunk/samples/i18n/timedbrowserupdater.xml
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/samples/i18n/timedbrowserupdater.xml?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/samples/i18n/timedbrowserupdater.xml (added)
+++ cocoon/blocks/ajax/trunk/samples/i18n/timedbrowserupdater.xml Sun Oct  2 05:41:05 2005
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+  Copyright 1999-2005 The Apache Software Foundation
+
+  Licensed under the Apache License, Version 2.0 (the "License");
+  you may not use this file except in compliance with the License.
+  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+-->
+<!--
+  @version $Id$
+-->
+<catalogue>
+	<message key="tbu.name.hint">Console for controlling the Timed Browser Updater</message>
+	<message key="tbu.name.title">Update</message>
+	<message key="tbu.frequency.hint">how often the updater will run</message>
+	<message key="tbu.frequency.title">Frequency</message>
+	<message key="tbu.frequency.30">30 secs</message>
+	<message key="tbu.frequency.60">1 minute</message>
+	<message key="tbu.frequency.120">2 minutes</message>
+	<message key="tbu.frequency.300">5 minutes</message>
+	<message key="tbu.frequency.600">10 minutes</message>
+	<message key="tbu.isrunning.title">ON</message>
+	<message key="tbu.notrunning.title">OFF</message>
+	<message key="tbu.isrunning.hint">click to stop the updater</message>
+	<message key="tbu.notrunning.hint">click to start the updater</message>
+</catalogue>
\ No newline at end of file

Modified: cocoon/blocks/ajax/trunk/samples/sitemap.xmap
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/samples/sitemap.xmap?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/ajax/trunk/samples/sitemap.xmap (original)
+++ cocoon/blocks/ajax/trunk/samples/sitemap.xmap Sun Oct  2 05:41:05 2005
@@ -20,6 +20,18 @@
   -->
 <map:sitemap xmlns:map="http://apache.org/cocoon/sitemap/1.0">
 
+ <map:components>
+  <map:transformers default="xslt">    
+    <map:transformer name="browser-update" src="org.apache.cocoon.ajax.BrowserUpdateTransformer"/>
+    <map:transformer name="i18n" src="org.apache.cocoon.transformation.I18nTransformer">
+      <catalogues default="tbu">
+        <catalogue id="tbu" name="timedbrowserupdater" location="i18n"/>
+      </catalogues>
+      <cache-at-startup>true</cache-at-startup>
+    </map:transformer>
+  </map:transformers>
+ </map:components>
+
  <map:resources>
    <!-- this will later become a virtual transformer -->
    <map:resource name="simple-page2html">
@@ -66,7 +78,28 @@
        <map:generate type="jx" src="display-suggestions.xml"/>
        <map:serialize type="xml"/>
      </map:match>
+
      
+     <!-- display the timed updater screen -->
+     <map:match pattern="timed-updater-screen">
+       <map:generate type="jx" src="timed-updater.xml"/>
+       <map:transform type="browser-update"/>
+       <map:transform type="i18n"/>
+       <map:call resource="simple-page2html">
+         <map:param name="file" value="timed-updater.xml"/>
+       </map:call>
+				<map:select type="request-parameter">
+					<map:parameter name="parameter-name" value="cocoon-ajax"/>
+					<map:when test="true"><map:serialize type="xml"/></map:when>
+					<map:otherwise><map:serialize type="html"/></map:otherwise>
+				</map:select>
+     </map:match>
+
+     <!--  Ajax Timed Browser Updater -->
+     <map:match pattern="timed-updater">
+       <map:call function="timedUpdateDemo"/>
+     </map:match>
+
      <map:match pattern="display-freememory">
        <map:generate type="jx" src="display-freememory.xml"/>
        <map:serialize type="xml"/>

Added: cocoon/blocks/ajax/trunk/samples/timed-updater.xml
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/samples/timed-updater.xml?rev=293104&view=auto
==============================================================================
--- cocoon/blocks/ajax/trunk/samples/timed-updater.xml (added)
+++ cocoon/blocks/ajax/trunk/samples/timed-updater.xml Sun Oct  2 05:41:05 2005
@@ -0,0 +1,62 @@
+<!--
+  Copyright 1999-2005 The Apache Software Foundation
+
+  Licensed under the Apache License, Version 2.0 (the "License");
+  you may not use this file except in compliance with the License.
+  You may obtain a copy of the License at
+
+      http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+-->
+<!--
+  @version $Id$
+-->
+<page
+	xmlns:jx="http://apache.org/cocoon/templates/jx/1.0"
+  xmlns:tbu="http://apache.org/cocoon/timed-browser-update/1.0">
+
+  <!-- Import the macros that define TBU template elements -->
+  <jx:import uri="resource://org/apache/cocoon/ajax/resources/macros/timedbrowserupdater.xml"/>
+  
+  <title>Timed Browser Updater Demo</title>
+  <!-- include ajax scripts -->
+  <script type="text/javascript" src="resources/ajax/js/cocoon-ajax.js"/>
+  <script type="text/javascript" src="resources/ajax/js/timedbrowserupdater.js"/>
+	
+	<style>
+		.tbuConsole {			
+				border-color: #09F;
+				border-width: 1px;
+				border-style: solid;
+				padding: 4px;
+		}
+		.tbuConsole th {
+			text-align: right;
+		}
+	</style>
+	
+	<content>
+		<p>This sample simulates specific data changes on the backend, being picked up automatically by the Browser.</p>
+		
+		<p>Be <em>patient</em>, the default update frequency is a mere <strong>30 secs</strong>.</p>
+		<blockquote>
+			<tbu:replace id="demo.hour" state="${data.hour}">
+				<p id="demo.hour" title="this piece of data changes every hour">Hour: ${data.hour} (last change: ${data.time})</p>
+			</tbu:replace>
+		
+			<tbu:replace id="demo.min" state="${data.min}">
+				<p id="demo.min" title="this piece of data changes every minute">Minute: ${data.min} (last change: ${data.time})</p>
+			</tbu:replace>
+		
+			<tbu:replace id="demo.rand" state="${data.rand}">
+				<p id="demo.rand" title="this piece of data changes randomly">Random: ${data.rand} (last change: ${data.time})</p>
+			</tbu:replace>
+		</blockquote>
+		<p><tbu:console i18nCatalogue="tbu"/></p><!---->
+	</content>
+</page>
\ No newline at end of file

Modified: cocoon/blocks/ajax/trunk/samples/welcome.xml
URL: http://svn.apache.org/viewcvs/cocoon/blocks/ajax/trunk/samples/welcome.xml?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/ajax/trunk/samples/welcome.xml (original)
+++ cocoon/blocks/ajax/trunk/samples/welcome.xml Sun Oct  2 05:41:05 2005
@@ -24,6 +24,7 @@
  </group>
 
  <group name="Basic Samples">
-  <sample name="File explorer" href="file-browser">Browse through the files in Cocoon's sample directory with Ajax autocompletion.</sample>
+  <sample name="File explorer" href="file-browser">Browse through the files in Cocoon's sample directory with Ajax auto-completion.</sample>
+  <sample name="Timed Browser Updater" href="timed-updater">Update regions of the screen with live information, asynchronously.</sample>
  </group>
 </samples>

Modified: cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/forms-field-styling.xsl
URL: http://svn.apache.org/viewcvs/cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/forms-field-styling.xsl?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/forms-field-styling.xsl (original)
+++ cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/forms-field-styling.xsl Sun Oct  2 05:41:05 2005
@@ -28,6 +28,7 @@
 
   <xsl:template match="head" mode="forms-field">
     <script src="{$resources-uri}/js/forms-lib.js" type="text/javascript"/>
+    <script src="{$resources-uri}/ajax/js/cocoon-ajax.js" type="text/javascript"/>
     <script src="{$resources-uri}/js/cforms.js" type="text/javascript"/>
     <link rel="stylesheet" type="text/css" href="{$resources-uri}/css/forms.css"/>
   </xsl:template>

Modified: cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/js/cforms.js
URL: http://svn.apache.org/viewcvs/cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/js/cforms.js?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/js/cforms.js (original)
+++ cocoon/blocks/forms/trunk/java/org/apache/cocoon/forms/resources/js/cforms.js Sun Oct  2 05:41:05 2005
@@ -1,23 +1,17 @@
 /*
-* Copyright 1999-2005 The Apache Software Foundation
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-*     http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-
-/**
- * Runtime JavaScript library for Cocoon forms.
+ * Copyright 1999-2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
  *
- * @version $Id$
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
  */
 
 //-------------------------------------------------------------------------------------------------
@@ -33,6 +27,7 @@
  * Submits a form. If ajax mode is on and the browser is ajax-aware, the page isn't reloaded
  */
 CForms.submitForm = function(element, name) {
+
     if (name == undefined) {
         name = element.name;
     }
@@ -45,56 +40,48 @@
         // FIXME: programmatically submitting the form doesn't trigger onsubmit ? (both in IE and Moz)
         forms_onsubmit();
         
-        // Provide feedback that something is happening.
-        document.body.style.cursor = "wait";
+        if (CForms.ajax && BrowserUpdater != null) {
         
-        var req = CForms.newXMLHttpRequest();
-        if (req) {
-	    // The "ajax-action" attribute specifies an alternate submit location used in Ajax mode.
-	    // This allows to use Ajax in the portal where forms are normally posted to the portal URL.
-	    var uri = form.getAttribute("ajax-action");
-	    if (! uri)
-	        uri = form.action;
-            if ( uri == "" )
-                uri = document.location;
-                
-            req.open("POST", uri, true);
-            req.setRequestHeader("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8");
-            // onreadystatechange must be all lower case (?)
-            req.onreadystatechange = function() {
-                if (req.readyState == 4) {
-                    CForms._handleBrowserUpdate(form, req);
-                }
-            }
-            req.send(CForms._buildQueryString(form, name));
-            // Reset submit-id
-            form["forms_submit_id"].value = '';
-            forms_onsubmitHandlers = new Array();
-            
+        	// Provide feedback that something is happening.
+        	document.body.style.cursor = "wait";
+
+					var uri = form.getAttribute("ajax-action");
+					if (! uri) uri = form.action;
+					if ( uri == "" ) uri = document.location;
+        
+        	var req = new BrowserUpdater(
+        		uri, 
+						{
+							method: 'post', 
+							postBody: CForms._buildQueryString(form, name), 
+							onFailure: BrowserUpdater.handleError,
+							form: form
+						}
+					);
+        
+					// Reset submit-id
+					form["forms_submit_id"].value = '';
+					forms_onsubmitHandlers = new Array();
         } else {
             // Non ajax-aware browser : regular submit
             form.submit();
         }
     }
+
 }
 
 // Override the default forms_submitForm
 forms_submitForm = CForms.submitForm;
 
 /**
- * Create an XHR if the browser supports it.
- */
-CForms.newXMLHttpRequest = function () {
-    if (this.ajax) {
-        if (window.XMLHttpRequest)
-            return new XMLHttpRequest;
-        else if (window.ActiveXObject)
-            return new ActiveXObject("Microsoft.XMLHTTP");
-    }
-}
-
-/**
  * Build a query string with all form inputs
+ *
+ * NB. It is possible that this could be replaced by the use of Form.serialize in prototype.js
+ * but that Objec t also sends Submit buttons, which it is possible CForms does not want
+ *
+ * Another possiblity is that we could overcome that horror in HTML whereby 
+ * unchecked checkboxes are not normally submitted :-)
+ *
  */
 CForms._buildQueryString = function(form, submitId) {
     // Indicate to the server that we're in ajax mode
@@ -114,323 +101,3 @@
     }
     return result;
 }
-
-/**
- * Handle the server response
- */
-CForms._handleBrowserUpdate = function(form, request) {
-    // Restore normal cursor
-    document.body.style.cursor = "auto";
-    if (request.status == 200) {
-        var xca;
-        try { // An exception is thrown if header doesn't exist (at least in Moz)
-            xca = request.getResponseHeader("X-Cocoon-Ajax");
-        } catch (e) {
-            // header doesn't exist
-        }
-        if (xca == "continue") {
-            // Interaction with this page is finished: redirect the browser to the form's action URL
-            // Get the continuation-id, if any.
-            var contParam = '?cocoon-ajax-continue=true';
-            if (form.elements["continuation-id"]) {
-                contParam += "&continuation-id=" + form.elements["continuation-id"].value;
-            }
-            window.location.href = form.action + contParam;
-        } else {
-            // Handle browser update directives
-            var doc = request.responseXML;
-            if (!doc) {
-                BrowserUpdate.handleError("No xml answer", request);
-                return;
-            }
-        
-           BrowserUpdate.processResponse(doc, request);
-       }
-    } else {
-        BrowserUpdate.handleError("Request failed - status=" + request.status, request);
-    }
-}
-
-//-------------------------------------------------------------------------------------------------
-
-DOMUtils = {
-    // Stupid IE doesn't have these constants
-    ELEMENT_NODE : 1,
-    ATTRIBUTE_NODE : 2,
-    TEXT_NODE : 3,
-    CDATA_SECTION_NODE : 4,
-    ENTITY_REFERENCE_NODE : 5,
-    ENTITY_NODE : 6,
-    PROCESSING_INSTRUCTION_NODE : 7,
-    COMMENT_NODE : 8,
-    DOCUMENT_NODE : 9,
-    DOCUMENT_TYPE_NODE : 10,
-    DOCUMENT_FRAGMENT_NODE : 11
-}
-
-/**
- * Get the first child element of an element, ignoring text nodes
- */
-DOMUtils.firstChildElement = function(element) {
-    var nodes = element.childNodes;
-    for (var i = 0; i < nodes.length; i++) {
-        var node = nodes[i];
-        if (node.nodeType == this.ELEMENT_NODE) {
-            return node;
-        }
-    }
-}
-
-/**
- * Imports an element into a document, taking care of using the correct implementation
- * so that the browser interprets it as displayable XML
- */
-DOMUtils.importNode = function(node, targetDoc) {
-    if(node.xml) {
-        // IE
-        var div = targetDoc.createElement("DIV");
-        div.innerHTML = node.xml;
-        return this.firstChildElement(div);
-    } else {
-        return DOMUtils._importNode(node, targetDoc);
-    }
-}
-
-/**
- * DOM implementation of importNode, recursively creating nodes
- */
-DOMUtils._importNode = function(node, targetDoc) {
-    switch(node.nodeType) {
-        case this.ELEMENT_NODE:
-            var element = targetDoc.createElement(node.nodeName);
-            //var element = targetDoc.createElementNS(node.namespaceURI, node.nodeName);
-            var attrs = node.attributes;
-            for (var i = 0; i < attrs.length; i++) {
-                attr = attrs[i];
-                element.setAttribute(attr.nodeName, attr.nodeValue);
-                //element.setAttributeNS(attr.namespaceURI, attr.nodeName, attr.nodeValue);
-            }
-            var children = node.childNodes;
-            for (var j = 0; j < children.length; j++) {
-                var imported = this.importNode(children[j], targetDoc);
-                if (imported) element.appendChild(imported);
-            }
-            return element;
-        break;
-        
-        case this.TEXT_NODE:
-            return targetDoc.createTextNode(node.nodeValue);
-        break;
-        
-        case this.CDATA_SECTION_NODE:
-            return targetDoc.createTextNode(node.nodeValue);
-        break;
-    }
-}
-
-
-//-------------------------------------------------------------------------------------------------
-// General purpose AJAX infrastructure to handle a BU ("browser update") response
-//
-// To implement a new instruction, add the corresponding function as a property of
-// BrowserUpdate.handlers.
-//-------------------------------------------------------------------------------------------------
-
-BrowserUpdate = {};
-
-BrowserUpdate.processResponse = function(doc, request) {
-    var nodes = doc.documentElement.childNodes;
-    for (var i = 0; i < nodes.length; i++) {
-        var node = nodes[i];
-        if (node.nodeType == DOMUtils.ELEMENT_NODE) {
-            var handler;
-            if (node.localName) {
-                handler = node.localName;
-            } else {
-                // No DOM2 support (IE6)
-                handler = node.nodeName.replace(/.*:/, "");
-            }
-            var handlerFunc = BrowserUpdate.handlers[handler];
-            if (handlerFunc) {
-                handlerFunc(node);
-            } else {
-                BrowserUpdate.handleError("No handler found for element " + handler, request);
-            }
-        }
-    }
-}
-BrowserUpdate.handlers = {
-    replace :  function(element) {
-        var id = element.getAttribute("id");
-        if (!id) {
-           alert("no id found on update element");
-           return;
-        }    
-        // Get the first child element (the first child may be some text!)
-        var firstChild = DOMUtils.firstChildElement(element);
-    
-        var oldElement = document.getElementById(id);
-        
-        if (!oldElement) {
-            alert("no element '" + id + "' in source document");
-            return;
-        }
-    
-        var newElement = DOMUtils.importNode(firstChild, document);
-        
-        // Warn: it's replace(new, old)!!
-        oldElement.parentNode.replaceChild(newElement, oldElement);
-        // Ensure the new node has the correct id
-        newElement.setAttribute("id", id);
-        
-        if (BrowserUpdate.highlight) {
-           BrowserUpdate.highlight(newElement);
-        }
-    }
-}
-
-BrowserUpdate.handleError = function(message, request) {
-    if (confirm(message + "\nShow server response?")) {
-        var w = window.open(undefined, "Cocoon Error", "location=no");
-        if (w == undefined) {
-            alert("You must allow popups from this server to display the response.");
-        } else {
-	        var doc = w.document;
-	        doc.open();
-	        doc.write(request.responseText);
-	        doc.close();
-	    }
-    }
-}
-
-
-//-------------------------------------------------------------------------------------------------
-// Fader used to highlight page areas that have been updated
-//-------------------------------------------------------------------------------------------------
-
-/**
- * Create a fader that will progressively change an element's background color from
- * a given color back to its original color.
- *
- * @param elt the element to fade
- * @param color the starting color (default yellow)
- * @param duration the fade duration in msecs (default 1000)
- * @param fps the animation frames per seconds (default 25)
- */
-function Fader(elt, color, duration, fps) {
-   // Set default values
-   if (!color) color = "#FFFF80"; // yellow
-   if (!duration) duration = 1000; // 1 sec
-   if (!fps) fps = 25; // 25 frames/sec
-   
-   this.element = elt;
-   this.fromColor = Fader.colorToRgb(color);
-   this.toColor = Fader.colorToRgb(Fader.getBgColor(this.element));
-   
-   this.maxFrames = Math.round(fps * duration / 1000.0);
-   this.delay = duration / this.maxFrames;
-}
-
-/**
- * Creates a default fader for a given element. This function can be used to set BrowserUpdate.highlight
- */
-Fader.fade = function(elt) {
-   new Fader(elt).start();
-}
-
-Fader.prototype.start = function() {
-   this.frame = 0;
-   this._changeColor();
-}
-
-Fader.prototype._changeColor = function() {
-    if (this.frame < this.maxFrames) {
-        // Schedule the next iteration right now to keep a more accurate timing
-        var fader = this;
-        setTimeout(function() {fader._changeColor();}, this.delay);
-    }
-    var newColor = new Array(3);
-    for (var channel = 0; channel < 3; channel++) {
-        newColor[channel] = Math.floor(
-            this.fromColor[channel] * ((this.maxFrames - this.frame) / this.maxFrames) +
-            this.toColor[channel] * (this.frame/this.maxFrames)
-        );
-    }
-
-    this.frame++;
-    var color = Fader.rgbToColor(newColor[0], newColor[1], newColor[2]);
-    this.element.style.backgroundColor = color;
-}
-
-/** Converts a "#RRGGBB" color as an array of 3 ints */
-Fader.colorToRgb = function(hex) {
-    return [
-        parseInt(hex.substr(1,2),16),
-        parseInt(hex.substr(3,2),16),
-        parseInt(hex.substr(5,2),16) ];
-}
-
-/** Converts rgb values to a "#RRGGBB" color */
-Fader.rgbToColor = function(r, g, b) {
-    r = r.toString(16); if (r.length == 1) r = '0' + r;
-    g = g.toString(16); if (g.length == 1) g = '0' + g;
-    b = b.toString(16); if (b.length == 1) b = '0' + b;
-    return "#" + r + g + b;
-}
-
-/** Get the background color of an element */
-Fader.getBgColor = function(elt) {
-    while(elt) {
-        var c;
-        if (window.getComputedStyle) c = window.getComputedStyle(elt,null).getPropertyValue("background-color");
-        if (elt.currentStyle) c = elt.currentStyle.backgroundColor;
-        if ((c != "" && c != "transparent") || elt.tagName == "BODY") { break; }
-        elt = elt.parentNode;
-    }
-    if (c == undefined || c == "" || c == "transparent" || c == "white") c = "#FFFFFF";
-
-    var rgb = c.match(/rgb\s*\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*\)/);
-    if (rgb) return this.rgbToColor(parseInt(rgb[1]),parseInt(rgb[2]),parseInt(rgb[3]));
-    return c;
-}
-
-BrowserUpdate.highlight = Fader.fade;
-
-//-------------------------------------------------------------------------------------------------
-// Blinker used to highlight page areas that have been updated
-//-------------------------------------------------------------------------------------------------
-
-function Blinker(elt, color, hltDelay, normalDelay, blinks) {
-    this.element = elt;
-    if (!color) color = "#FFFF80"; // yellow
-    if (!hltDelay) hltDelay = 100;
-    if (!normalDelay) normalDelay = 100;
-    if (!blinks) blinks = 2;
-    
-    this.hltColor = color;
-    this.hltDelay = hltDelay;
-    this.normalDelay = normalDelay;
-    this.normalColor = Fader.getBgColor(elt);
-    this.maxBlinks = blinks * 2;
-    this.blink = 0;
-}
-
-Blinker.prototype.start = function() {
-   this.blink = 0;
-   this._doBlink();
-}
-
-Blinker.blink = function(elt) {
-   new Blinker(elt).start();
-}
-
-Blinker.prototype._doBlink = function() {
-   var hlt = (this.blink % 2 == 0);
-   this.element.style.backgroundColor = hlt ? this.hltColor : this.normalColor;;
-   if (this.blink <= this.maxBlinks) {
-      var blinker = this;
-      setTimeout(function() {blinker._doBlink();}, hlt ? this.hltDelay : this.normalDelay);
-   }
-   this.blink++;
-}
-

Modified: cocoon/blocks/forms/trunk/samples/sitemap.xmap
URL: http://svn.apache.org/viewcvs/cocoon/blocks/forms/trunk/samples/sitemap.xmap?rev=293104&r1=293103&r2=293104&view=diff
==============================================================================
--- cocoon/blocks/forms/trunk/samples/sitemap.xmap (original)
+++ cocoon/blocks/forms/trunk/samples/sitemap.xmap Sun Oct  2 05:41:05 2005
@@ -467,7 +467,7 @@
      <map:match type="regexp" pattern="resources/(ajax)/(.*)">
        <map:read src="resource://org/apache/cocoon/{1}/resources/{2}"/>
      </map:match>
-
+     
      <map:match pattern="resources/**">
        <map:read src="resource://org/apache/cocoon/forms/{0}"/>
      </map:match>