more on GenericView; added FormController
git-svn-id: svn://svn.cy55.de/Zope3/src/cybertools/trunk@1353 fd906abe-77d9-0310-91a1-e0d9ade77398
This commit is contained in:
parent
eea19cc7ea
commit
903c8382fb
4 changed files with 87 additions and 0 deletions
|
@ -206,3 +206,39 @@ packages.
|
||||||
|
|
||||||
>>> gvc = component.getUtility(IViewConfigurator)
|
>>> gvc = component.getUtility(IViewConfigurator)
|
||||||
|
|
||||||
|
|
||||||
|
Processing form input
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
GenericView also provides an update() method that may be called from
|
||||||
|
templates that might receive form information.
|
||||||
|
|
||||||
|
>>> view.update()
|
||||||
|
True
|
||||||
|
|
||||||
|
Real work can only be done by an adapter to GenericView that provides the
|
||||||
|
IFormController interface with its update(). There also must be a
|
||||||
|
form variable (typically coming from a hidden field) with the name
|
||||||
|
'form.action' that provides the name under which the form controller is
|
||||||
|
registered.
|
||||||
|
|
||||||
|
>>> from cybertools.browser.controller import IFormController, FormController
|
||||||
|
>>> class MyController(FormController):
|
||||||
|
... def update(self):
|
||||||
|
... print 'updating...'
|
||||||
|
|
||||||
|
>>> component.provideAdapter(MyController, (View, IBrowserRequest),
|
||||||
|
... IFormController, name='save')
|
||||||
|
|
||||||
|
>>> request = TestRequest(form={'form.action': 'save'})
|
||||||
|
>>> view = View(obj, request)
|
||||||
|
>>> view.update()
|
||||||
|
updating...
|
||||||
|
True
|
||||||
|
|
||||||
|
The update() method will only be executed once:
|
||||||
|
|
||||||
|
>>> view.update()
|
||||||
|
True
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -23,12 +23,15 @@ $Id$
|
||||||
"""
|
"""
|
||||||
|
|
||||||
from zope import component
|
from zope import component
|
||||||
|
from zope.interface import Interface, implements
|
||||||
from zope.app.pagetemplate import ViewPageTemplateFile
|
from zope.app.pagetemplate import ViewPageTemplateFile
|
||||||
from zope.cachedescriptors.property import Lazy
|
from zope.cachedescriptors.property import Lazy
|
||||||
|
|
||||||
from cybertools.browser.configurator import IViewConfigurator, IMacroViewProperty
|
from cybertools.browser.configurator import IViewConfigurator, IMacroViewProperty
|
||||||
|
|
||||||
|
|
||||||
|
# layout controller: collects information about head elements, skins, portlets, etc
|
||||||
|
|
||||||
class Controller(object):
|
class Controller(object):
|
||||||
|
|
||||||
def __init__(self, context, request):
|
def __init__(self, context, request):
|
||||||
|
@ -115,3 +118,29 @@ class Macro(object):
|
||||||
def __call__(self):
|
def __call__(self):
|
||||||
return self.macro
|
return self.macro
|
||||||
|
|
||||||
|
|
||||||
|
# form processing:
|
||||||
|
# the part of the model/view/controller pattern that deals with
|
||||||
|
# form input
|
||||||
|
|
||||||
|
class IFormController(Interface):
|
||||||
|
""" Used as a named adapter by GenericView for processing form input.
|
||||||
|
"""
|
||||||
|
|
||||||
|
def update():
|
||||||
|
""" Processing form input...
|
||||||
|
"""
|
||||||
|
|
||||||
|
|
||||||
|
class FormController(object):
|
||||||
|
|
||||||
|
implements(IFormController)
|
||||||
|
|
||||||
|
def __init__(self, context, request):
|
||||||
|
self.view = view = context # the controller is adapted to a view
|
||||||
|
self.context = context.context
|
||||||
|
self.request = request
|
||||||
|
|
||||||
|
def update(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
i18n:domain="zope"
|
i18n:domain="zope"
|
||||||
tal:define="controller nocall:view/@@controller;
|
tal:define="controller nocall:view/@@controller;
|
||||||
resourceBase controller/resourceBase;
|
resourceBase controller/resourceBase;
|
||||||
|
dummy view/update;
|
||||||
body view/pageBody">
|
body view/pageBody">
|
||||||
|
|
||||||
<head metal:define-macro="head">
|
<head metal:define-macro="head">
|
||||||
|
|
|
@ -51,6 +51,8 @@ class GenericView(object):
|
||||||
|
|
||||||
template = macro = menu = skin = None
|
template = macro = menu = skin = None
|
||||||
|
|
||||||
|
_updated = False
|
||||||
|
|
||||||
def setController(self, controller):
|
def setController(self, controller):
|
||||||
# make the (one and only controller) available via the request
|
# make the (one and only controller) available via the request
|
||||||
viewAnnotations = self.request.annotations.setdefault('cybertools.browser', {})
|
viewAnnotations = self.request.annotations.setdefault('cybertools.browser', {})
|
||||||
|
@ -68,11 +70,30 @@ class GenericView(object):
|
||||||
def __init__(self, context, request):
|
def __init__(self, context, request):
|
||||||
self.context = context
|
self.context = context
|
||||||
self.request = request
|
self.request = request
|
||||||
|
#cont = self.controller # check: leads to strange AttributeError in doctest
|
||||||
|
#if cont is not None:
|
||||||
|
# self.setupController()
|
||||||
|
|
||||||
def __call__(self, *args, **kw):
|
def __call__(self, *args, **kw):
|
||||||
return self.index(*args, **kw)
|
return self.index(*args, **kw)
|
||||||
|
|
||||||
|
#def render(self, *args, **kw):
|
||||||
|
# return self.index(*args, **kw)
|
||||||
|
|
||||||
|
def update(self):
|
||||||
|
if not self._updated:
|
||||||
|
action = self.request.form.get('form.action')
|
||||||
|
if action:
|
||||||
|
fc = component.getMultiAdapter((self, self.request),
|
||||||
|
name=action)
|
||||||
|
fc.update()
|
||||||
|
self._updated = True
|
||||||
|
return True
|
||||||
|
|
||||||
def setupController(self):
|
def setupController(self):
|
||||||
|
""" May be called by __init__() if there is already a controller
|
||||||
|
or when the controller is set. May be implemented by subclass.
|
||||||
|
"""
|
||||||
pass
|
pass
|
||||||
|
|
||||||
@Lazy
|
@Lazy
|
||||||
|
|
Loading…
Add table
Reference in a new issue