/* * SPL - The SPL Programming Language * Copyright (C) 2004, 2005 Clifford Wolf * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * * mod_wsf_action.spl: A WSF Component with on-the-fly created callbacks */ /** * A module which implements a WSF Component with support for dynamically * registered callbacks (usually using closures) in the templates. */ load "wsf"; /** * A WSF Component with support for dynamically registered callbacks. * An example: * * var mywsfaction = new WsfAction(function() { * return #file-as-template *demotpl; }, undef); * * #embedded-file demotpl EOT *
* FooBar * action("foobar", function() { debug "FooBar!!"; }); *
* EOT * * Usually the callbacks are created on-demand by a more complex logic and * detailed information for the context of the callback is passed using a * closure. * * This object is derived from [[wsf:WsfComponent]]. */ object WsfAction WsfComponent { /** * A hash containing the function pointers for the registered actions. */ var action_list; /** * The function pointer passed to the constructor. */ var template_function; /** * The options hash passed to the constructor. */ var template_options; /** * This variable can be used to save persistent data between calls * of [[.template_function]]. */ var data; /** * This method must be executed by [[.get_html()]] before evaluating * the template. It resets [[.action_list]]. */ method action_reset() { action_list = undef; } /** * Registeres an action. If the name is set as CGI parameter, the * callback is called from [[.main()]]. * * When the callback is called, the following named arguments are * passed to it: * * - action: * the name under which this callback has been registered * * - obj: * this WsfAction instance * * - all the options in the [[.template_options]] variable */ method action(name, callback) { action_list[name] = callback; } /** * Overloaded [[wsf:WsfComponent.main()]]. * * Calls the registered actions and sets the dirty flag. The calling * convention for the actions is described in the section about the * [[.action()]] method above. */ method main() { while(1) { task_co_return(); var did_something = 0; foreach a (action_list) { if (a ~!= "" and declared cgi.param[a]) { action_list[a](action: a, obj: this, %template_options); did_something = 1; dirty = 1; } } if (!did_something and declared action_list[""]) { action_list[""](action: "", obj: this, %template_options); dirty = 1; } } } /** * Overloaded [[wsf:WsfComponent.get_html()]]. * * This calls [[.template_function()]] to generate the html text for * this component. The named arguments declared in [[.template_options]] * are passed to [[.template_function()]]. The function is called in * the context of this WsfAction instance. */ method get_html() { action_reset(); return *template_function(obj: this, %template_options); } /** * The Constructor. */ method init(_template_function, %_template_options) { template_function = _template_function; template_options = _template_options; return *WsfComponent.init(); } }