[Grok-dev] viewlets and application_root

Robert Marianski rmarianski at openplans.org
Wed Apr 23 22:25:13 EDT 2008


I put in a couple of notes inline to help get you started.

On Wed, Apr 23, 2008 at 06:50:47PM +0200, Joachim Schmitz wrote:
> hi,
>
> I am trying to build a navigation_tab_bar with a viewlet. This tab_bar 
> should always show the keys of the root-application-object. Till now I 
> have:
>
> import grok
> from zope import interface, schema
>
> class Campus(grok.Application, grok.Container):
>     def __init__(self):
>         super(Campus, self).__init__()

I'd assume you would want to generalize this to something like a
Section class, each one having different properties. If you need to
customize behavior, look into creating adapters for that.

>         self['academics'] = Academics()
>     pass
>
> class TabBarManager(grok.ViewletManager):
>     grok.name('tab_bar')
>     grok.context(interface.Interface)
>
> class TabBar(grok.Viewlet):
>     grok.context(interface.Interface)

I assume you mean tab_bar.pt here? If you name your template tabbar.pt
then you don't have to use the grok.template directive.

>     grok.template('tab_bar')
>
>     def update(self):
>         pass
> ......
>
>
>
> the tab_bar.pt looks like:
> <div class="corner-page-top"></div>
> <div class="navbar">
>   <!-- Navigation items -->
>   <ul tal:repeat="key python:context.keys()">
>     <li><a tal:define="section python:context[key]"
>            tal:attributes="href python:view.url(key)"
>            tal:content="python:section.title"></a>
>     </li>
>   </ul>
>   <!-- Navigation item -->
> </div>

See below for a simplified version.

> What do I have to put for context here to always show the keys of the 
> application-root ?

The trick is to walk up your parents to find the root application
object. I have this code below as well.

I find myself walking up parents looking for application objects often.
Is there a reason that this isn't a method on the grok.View class, or a
function in grok.util?

Hope that helps,
Robert

> -- 
> Gru? Joachim
> _______________________________________________
> Grok-dev mailing list
> Grok-dev at zope.org
> http://mail.zope.org/mailman/listinfo/grok-dev


import grok
from zope.interface import Interface

class Campus(grok.Application, grok.Container):
    def __init__(self):
        super(Campus, self).__init__()
        self['academics'] = Section(u'Academics')

class Index(grok.View):
    grok.context(Campus)

# I'm assuming that the section or Academics class would be passed on
# something like that
class Section(grok.Model):
    def __init__(self, title):
        self.title = title

class TabBarManager(grok.ViewletManager):
    # usually you namespace the name here, so you don't run into name
    # collisions
    grok.name('campus.tabbar')
    grok.context(Interface)

class TabBar(grok.Viewlet):
    grok.viewletmanager(TabBarManager)
    grok.context(Interface)

    def campus_sections(self):
        """
        Return all campus sections. These are currently all the objects
        on the application root.
        """
        obj = self.context
        while obj is not None:
            if isinstance(obj, grok.Application):
                return obj.values()
            obj = obj.__parent__
        raise ValueError("No application found.")



######################################
# and the viewlet's template
######################################

<div class="navbar">
  <ul>
    <li tal:repeat="section view/campus_sections">
      <a tal:attributes="href python:view.url(section)"
         tal:content="section/title"></a>
    </li>
  </ul>
</div>


More information about the Grok-dev mailing list