Forum OpenACS Q&A: Portlets, Includelets and bright ideas!

I would very much appreciate some advice on the following:

Picture if you will a vanilla OpenACS 5.5.1 with calendar, file-storage, contacts, tasks and xowiki installed. The standard default index page has the list of installed applications displayed in a block on the left hand side, and a second block contains a list of subsites (in this case empty).

In the past I have simply set the subsite parameter to use an xowiki page as the site landing page. However I was wondering if this could be done differently.

I notice that in the repository we have an 'Xowiki Includelet' package and an 'Xowiki Portlet' package.

What do these do?

Would the 'Xowiki Portlet' allow me to display content from an xowiki instance in the default openacs index page template?

Does the 'Xowiki Includelet' enable you to include pages from one xowiki instance inside another?

Would I for example be able to take out the block containing the subsites, and replace this with content that is in fact an xowiki page displayed through a portlet on the default index page template.

Selection of links could then route the user to the xowiki instance itself or elsewhere on the site. Does anyone have any comments on this or know of a more elegant method?

Regards
Richard

Collapse
Posted by Claudio Pasolini on
Hi Richard,

OpenACS 5.5 introduced the new layout-manager package and a layout-managed-subsite package based on the former.

The admin UI allows you to define the format of your pages and to place the includelets as you want.

There is a small number of includelets already available (calendar-includelet, content-includelet, file-storage-includelet, forums-includelet, lorsm-includelet, news-includelet and xowiki-includelet). Furthermore building your own includelets is really easy compared to the dotlrn way.

The packages are well documented and if you want to play with the existing includelets or build your own you should really give them a try.

Collapse
Posted by Richard Hamilton on
Oh fantastic - thank you Claudio! That can come off my Christmas list then. 😊

I'll have a play.

Regards
Richard

Collapse
Posted by Richard Hamilton on
Claudio,

I have now installed the relevant packages and tried to set things up but have run into a few server errors and some confusion.

The function of Layout Manager is fairly self-explanitory.

The function of Layout-Subsite-Integration seems to be to provide a user interface to Layout-Manager. The first impression is that this provides all that is required.

However I now see that Layout-Managed-Subsites extends acs-subsite to make the whole thing work. Am I correct in assuming that all three are required? If so will the dependencies take care of the installation or must they be manually installed seperately?

Can you in fact use the layout-manager and layout-subsite-integration without using layout-managed-subsites? Is the order of installation important?

I have noticed that if you pre-install some includelets before installing layout-managed-subsites you end up with a failure of the postinstall script as it tries to install them again. I also couldn't delete the package (or unmount/delete in one operation) because the script somewhere calls db_flush which fails as an unknown call.

I also ran into trouble whilst running the wizard. After selecting the display options the wizard returned a 'no rows' failure - presumably because the includelets were installed before the application.

I will try again with an empty db and will install the layout manager first and report back! Hopefully I'll have more success.

Collapse
Posted by Don Baccus on
the includes should have package requires for their base application in every case, if you find one that doesn't, fix it please! (after posting so I can be properly embarrassed in public!)

the db_flush call should be fixed in 5.5.1 final (it's supposed to be db_flush_cache) ... hmmm maybe it didn't make it in before release.

No. It's on HEAD for 5.6.0, not 5.5.1.

You may want to edit that locally ...

I have noticed that if you pre-install some includelets before installing layout-managed-subsites you end up with a failure of the postinstall script as it tries to install them again.

Oh, wait ... I think this is due because the now-obsolete layout-subsite-integration package created the same three includelets (that map the standard acs-subsite application box + subsite box include scripts, and a third layout manager admin includelet) that layout-managed-subsite does.

As I explained in another post, layout-subsite-integration is obsolete now that we support package extension and should not be used.

Collapse
Posted by Richard Hamilton on
Don,

Thanks yes, I realised that the error was because I had installed the wrong package, but sorry, only after posting! :-|

R.

Collapse
Posted by Gustaf Neumann on
Richard,

the pair "xowiki-portlet" and "dotlrn-xowiki" are here to make xowiki a first-class dotlrn citizen (dotlrn requires the "applet" and "portlet", the names are following those conventions). These are only here for dotlrn.

I have not had the time so far to look at the layout-manager, and i was not aware of the "xowiki includelet" so far. The term "includelet" is used in xowiki since a few years and refers to on-demand-generated chunks of HTML provided in an objects oriented manner (can be subclassed, etc.). These includelets have certain common properties like decorations, titles, and support different caching strategies.

With the introduction of the layout manager, we have another source for naming confusion.

Concerning your question about including contents of several xowiki instances): one can include pages from one xowiki instance in another one in various ways. One approach is to include contents of some other instance in a page via {{//someotherinstance/somepage}}. Another approach is to include pages from another instance to an xowiki instance via the "PackagePath" package parameter (only a few aggregating includelets are so far aware of the PackagePath). The PackagePath allows some pages of certain instances to show up in the context of several instances. The latter feature requires an xowiki version not older than half a year.

Collapse
Posted by Don Baccus on
I have not had the time so far to look at the layout-manager, and i was not aware of the "xowiki includelet" so far. The term "includelet" is used in xowiki since a few years and refers to on-demand-generated chunks of HTML provided in an objects oriented manner (can be subclassed, etc.). These includelets have certain common properties like decorations, titles, and support different caching strategies.

The term "includelet" has been used for years for bits of includable template within the toolkit. IIRC Lars Pind was the first to start using it.

See, for instance, "acs-lang/www/change-locale-include.tcl", written by one of Lars's ex-employees, Peter Marklund.

The layout manager is using it in the same sense as the old use, essentially a declaration can be made that identifies such an includelet so that the package can manage it.

Here's another example from the assessment doc:

An editor wants to conduct a poll on the site with
immediate publication of the result to get a feeling how users like the
new design of the website. The result can be displayed in an includelet
(see the below for details) on any page the editor wants.

They're not talking about xowiki.

I know the terms been used informally in discussions among team member for years, entirely outside the context of xowiki.

Collapse
Posted by Richard Hamilton on
Gustaf,

Although I have read all the documentation I can find about XoWiki, I remain a little unclear as to how I go about creating what in ETP would have been called 'custom applications'.

I'd like to set up a series of page types that are highly specific for a particular html/css page design so that users can edit their pages without having to see or understand the html underneath it.

For example, let's say we have to convert a highly specific existing design into an XoWiki based CMS. A design that is completely fixed in size, bounded on all four corners by a fixed border, with a product image display window containing up to five product images, with css pseudo-classes making child div blocks visible elsewhere on the page. Oh, and a css driven drop-down menu system to boot!

For this example I would need a form that had a banner photo upload field, a footer image upload field, five product image upload fields, five product info text fields, a title field, and a field for the single paragraph of sales blurb per page.

I'd ideally like to do this without customising any of the underlying OpenACS code, and want to be able to eliminate the default site name, members online and log-in components of the master template. In other words I need one instance of XoWiki to have control of the entire browser window, whilst the rest of the OpenACS site functions normally.

In the past with stuff like this I have hacked away at the templates and the tcl where necessary, but I am searching for a better way with XoWiki.

Regards
Richard

Collapse
Posted by Gustaf Neumann on
Sorry Don, i did in no way claim that xowiki has invented the term or has a copyright on it. The thread started out with xowiki, so i had to mention, that there is a "xowiki includelet" package which has little to do what xowiki calls an includelet in its documentation http://media.wu-wien.ac.at/download/xowiki-doc/#includelets
Collapse
Posted by Gustaf Neumann on
One can get full control over the browser window by using
https://openacs.org/xowiki/learning_content_tool?master=0 (compare with https://openacs.org/xowiki/learning_content_tool). In order to create a series of pages, i would recommend to use an ::xowiki::Form and define the content-fields as necessary. You can add a {{set-parameter master 0}} to the template part of the form. Look for example at the prototype pages "news-item" (defined the form) and "news" (summary page of news-items). I guess, you have seen already http://alice.wu-wien.ac.at:8000/s5-xowiki-tutorial/slides

In case, the entries of your "series of pages" have a state (e.g. a publishing workflow, different stages on a an entries life cycle, etc.), once can use xowiki content flow, where one workflow-definition can group all workflow instances. This is similar to the relation between ::xowiki::Form and an ::xowiki::FormPage, but with the workflow, every entry might have a different form in different states (see e.g. http://nm.wu-wien.ac.at/research/publications/b765.pdf)

Collapse
Posted by Richard Hamilton on
Gustaf,

Thank you for those two pointers, that is enormously helpful.

Now that I know that this is the correct direction, I can immerse myself in it without fear that my efforts will prove fruitless!

Regards
Richard

Collapse
Posted by Richard Hamilton on
Gustaf,

I had not in fact found those two documents you referred to so that you for providing the references. I will study them, they seem to cover precisely the things I want to try.

Thank you,
Richard

Collapse
Posted by Richard Hamilton on
Gustav,

Once I have created my ::xowiki::Form with the appropriate fields in it, where do I put the enclosing markup?

For example, suppose I have an OpenACS 5.5.1 installed with the site default page re-directed to the xowiki page called myindexpage which was created by completing the content entry form. This page is displayed with master=0.

I have no markup in the entered content. I am not wrapping the page in oacs site navigation (i.e. master=0). Where is the correct place to put (for example) a set of containing div blocks, a header, a menu bar and a footer? Do I have to hack at the default xowiki adp templates or is there an elegantly abstracted way to do this?

I realise that I can create a style sheet, enter it into the xowiki and refer to it, but what I am wondering is where the structural html to which that css will be applied should go?

Regards
Richard

Collapse
Posted by Richard Hamilton on
Gustaf,

Ok, WOW! I think the penny has dropped. Please disregard previous question.

I need to start experimenting! 😊

Once I have done so I think I might put together a brief step by step guide to entering a simple form spec and aesthetic design template to hand-hold through the initial process.

I was still in the mindset that I might have to write some .adp templates to surround the form fields in the final output, just as in the ETP application. I now realise that you have made the entire process dynamic! That was a dream documented about 5 years ago or more when Lee was writing the dynamic types package.

I see that you have made that dream a reality. Now all I have to do is learn how to use it!!

😊

R.

Collapse
Posted by Richard Hamilton on
I have an html template for a set of pages on a site, styled with a style sheet, into which I can simply place text and image references in order to create a sequence of similar pages with different content and all laid out the same way.

I have edited that html and substituted all the sequences of text with @suitably_named_var@ and all references to images with @suitably_named_img_var@.

I have clicked to 'add' a new xowiki::Form and have attempted to paste the resulting html+vars into the template field. On submit xowiki tells me that 'The attribute 'class' is not allowed for div tags'.

Am I on the right track here or completely missing the point? Although I have read the docs fully, I am also still not exactly clear what for example the 'Section' field is for, what 'Autoname' will do for me, whether I need to complete the form field or if xowiki will autogenerate a form for all unknown vars, and what 'Page Title' might mean for arbitrary xowiki objects (i.e. form intended to be a page template for creating other pages).

Sorry to be thick, but until I actually manage to enter something, I can't really experiment.

I feel as if there's a whole wide world out there if only I can get over the wall to start exploring it! :-|

Regards
Richard

Collapse
Posted by Gustaf Neumann on
Dear Richard,

Concerning 'The attribute 'class' is not allowed for div tags': Until Aug. 10, side-wide admins and package admins were allowed to enter 'insecure' HTML tags. Since this date, it is not allowed anymore. Since xowiki uses the standard HTML validation of acs-templating, this effects xowiki contents as well. AFAIK the problem was that an admin (package- or side-wide-admin) was able to enter e.g. a CSS class in an xowiki page, but an ordinary user was not allowed to change this page, "not even to fix a typo" (ask michael steigman for the details). So they decided it is better that no one can do it.

The main problem was most likely that the change was effecting all packages. The old change of mine was discussed with the oct years ago but reverted at Aug 10 http://fisheye.openacs.org/changelog/OpenACS/?cs=oacs-5-5%3Amichaels%3A20090810183511

It is certainly possible to program around this in xowiki, at least for forms. As you point out, xowiki-forms are rather limited in its power with the standard settings. I have not updated acs-templating on our installations after the change above. However, since the dangers of editing a CSS class of a page are rather limited you could add "class" to the AllowedParameters in the kernel parameters on your installation.

Concerning 'Section': see http://alice.wu-wien.ac.at:8000/xowiki-faq/#page_order
The page orders are available for all kind of pages, therefore for forms as well.

Concering 'Autoname': This field is used for controling whether "instances" of this form will be autonamed or not. If you have e.g. a form named Person, and you enter a person (an "instance", the first person will be named person1, the next person2, etc.

Hope, this helps
-gustaf neumann

Collapse
Posted by Richard Hamilton on
Gustaf,

Thank you for the reply. After posting last night, but before turning in(!), I managed to work out that I needed to add 'class' to allowed attributes, and 'IMG' to the allowed tags in the kernel paramaters in order to upload my code.

This at least allowed me at last to see the autogenerated forms and to try an xowiki::Form and an xowiki::Template.

I learned that I have to be careful with naming since every single variable specified must have a unique name which I presume is requirement imposed by the CR data model.

I have seen the 'import' button on the admin page which I presume will allow me to import some of your example form definitions. Hopefully these will allow me to see your form defs and work out how to do it.

Am I correct in thinking the following:

- The template field is for adding html/css markup that styles and lays out the page? There is an option to include @vars@ in the template which will be substituted for entered values when an instance of the form is rendered.

- The form field is optional and is for writing forms explicitly rather than relying on the automated form generation. This presumably is an interface to ad_form? I think that this field may be left blank if the auto generated form is adequate for the purpose. I am not clear on the syntax and semantics for entries in this field. I think this field would be used to for example specify that a textarea entry widget should be for example 80x10 rather than the default size, or to set styling.

- The constraints field is optional and is for specifying constraints in an exactly similar way to those specified for ad_page_contract?

I have created an initial test form that allowed for every content element of my page to be entered in a field. Whilst this eliminates the need for markup to be edited, it results in a huge form with over 20 fields to complete. I would therefore have to decide whether it is a good idea to do this, or whether the simple option of adding the content as markup is actually better and more flexible in the long run.

I have had to produce a simple CSS driven dropdown menu (don't you just hate designers!) which will appear on every page. Am I correct in thinking that I can create an xowiki page for this, and simply include it in the html template at the appropriate point so that it would only need to be edited once to reflect on all pages?

Sorry to ask so many questions.

R.

Collapse
19: Going great guns now! (response to 17)
Posted by Richard Hamilton on
xowiki::Form is now working a treat. Thank you Gustaf.

I have a question about wiki page includes.

I have implemented a dropdown menu using an unordered list and CSS pseudo-classes.

I want to have the menu as an xowiki page object so that I can include it 'inline'. This would avoid having to edit every page as a change to the master menu page would then be reflected in all other pages that use it.

I have tried to do this using {{en:mymenupage}} but this renders the page as a link inside what looks like a portal.

How to I tell xowiki that I want this page fully rendered 'inline'?

Regards
Richard

Collapse
Posted by Richard Hamilton on
I had been fighting shy of developing a fully integrated dropdown menu because I thought that the categories includelet was spitting out lots of javascript and my menu works with CSS pseudo-classes which I prefer.

Imagine my delight when I discovered that Gustaf's categories includelet delivers the data in precisely the same structure as I use - as an unordered list.

All I need to do is adapt my CSS and I should be in clover!

Collapse
Posted by Gustaf Neumann on
Concerning "How to I tell xowiki that I want this page fully rendered 'inline'?"

Use e.g. {{en:mymenupage -decoration none}}

In additions to the decorations listed in http://alice.wu-wien.ac.at:8000/xowiki-doc/#predfined_includelets newer xowiki versions have additionally a "-decoraton edit".

i have the impression, that you have figured out the answers to the other questions yourself...

Collapse
Posted by Richard Hamilton on
Gustaf,

Yes, thank you. Once I managed to find your examples to import I was away! I saw the -decoration none directive to the includelets in the docs, but nothing specific to the included wiki pages. I eventually concluded that this probably also worked for wiki pages as you have confirmed, {{en:page -decoration - none}}, however by that stage I had decided to bite the bullet and dive into making the menu system I have been forced to produce, work with the categories includelet!

I have done so, but want to suggest an ammendment to the <ul> that the includelet produces that will enhance its utility and interoperability with CSS.

I have been forced by a design to produce a horizontal menu with dropdowns. This requires the CSS selectors to be able to distinguish the top level list and display it 'inline', whilst all subsequent lists are displayed as 'block'.

The issue is that if you render the submenus as blocks, they are displayed as blocks inline to the top level list. This unrecoverably upsets the position of the subsequent inline top level menu items. The ONLY way to avoid this is to take the submenus out of the normal flow by using position: absolute. However if you do this without a containing <div> all the menus sit on top of one another adjacent to the left hand margin of the last absolutely positioned block element.

I therefore propose that every <ul> that is a child of <ul class="mktree"> be wrapped in a <div class="mkbranch"> or other suitable classname. The reason this works is that the <div> when set to position: absolute; width: 100% will sit beneath, and only be as wide as, the top level <li> that is its parent. You can then relatively position the <ul> submenu within the div block, without upsetting the top level menu item display flow.

I have posted below an example of the menu and the CSS. I realise that this is a specific applicaton for me, but this small change to the categories includelet itself would increase its flexibility, which surely can only be a good thing. I think this would add potential without breaking anything (although I confess I haven't studied the oacs-view template for the gory details of the treeview code). At least I would hope any change to that would be trivial.

The code posted below has taken quite a bit of time to get right, so I hope it will prove useful to anyone else who has to consort with the evil forces that demand horizontal drop-down menu bars! 😊 A bit of a fantasia on the use of CSS pseudo-classes.

Regards
Richard

Collapse
Posted by Richard Hamilton on
Sample Categories Structure HTML
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

<!-- Menu System Structure -->

<div class='categories'>
  <div class='portlet-wrapper'>
    <div class='portlet-header'>
      <div class='portlet-title-no-controls'>
        Categories
      </div>
    </div>
    <div  class='portlet'>
      <h3>Contents</h3>
      <ul class='mktree' id='Contents'>
        <li class='liClosed'>Tree Name
          <ul>
            <li class='liItem'><a href='/xowiki/forum'>item1</a></li>
            <li class='liItem'><a href='/xowiki/index'>item2</a></li>
            <li class='liClosed'>
              item3 
              <div class="submenu">
                <ul>
                  <li class='liItem'><a href='/xowiki/one'>one</a></li>
                  <li class='liItem'><a href='/xowiki/two'>two</a></li>
                  <li class='liItem'><a href='/xowiki/three'>three</a></li>
                  <li class='liClosed'>four
                    <div class="submenu">
                      <ul>
                        <li class='liItem'><a href='/xowiki/first'>first</a></li>
                        <li class='liItem'><a href='/xowiki/second'>second</a></li>
                        <li class='liItem'><a href='/xowiki/third'>third</a></li>
                        <li class='liItem'><a href='/xowiki/fourth'>fourth</a></li>
                        <li class='liItem'><a href='/xowiki/fifth'>fifth</a></li>
                        <li class='liItem'><a href='/xowiki/sixth'>sixth</a></li>
                      </ul>
                    </div>
                  </li>
                  <li class='liItem'><a href='/xowiki/five'>five</a></li>
                  <li class='liItem'><a href='/xowiki/six'>six</a></li>
                </ul>
              </div>
            </li> 
            <li class='liClosed'>
              item4 
              <div class="submenu">
                <ul>
                  <li class='liItem'><a href='/xowiki/another'>another</a></li>
                </ul>
              </div>
            </li>
          </ul>
        </li>
      </ul>
    </div>
  </div>
</div>

<!-- End of Menu System -->


CSS Classes Invoking Singing AND Dancing Bears
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

/* ################### */
/* Menu system classes */
/* ################### */


/* Set the style for links on the menu bar */
div.categories a:link {font-family: "Segoe UI", arial, sans-serif;
                       font-weight: bold;
                       font-size: 11pt}

/* Set style for visited links on the menu bar */
div.categories a:visited {font-family: "Segoe UI", arial, sans-serif;
                          font-weight: bold;
                          font-size: 11pt}

/* Vanish the bits of the OpenAcs Category tree that we don't want */
div.portlet-header {display: none}
div.portlet > h3 {display: none}

/* Hide top layer of Category tree by fiddling with font size */
div.portlet > ul.mktree > li.liClosed {font-size: 0pt;
                                       list-style: none}

/* Have to immediately reset explicitly to size required for menu bar */
div.portlet > ul.mktree > li.liClosed > ul {font-family: "Segoe UI", arial, sans-serif;
                                            font-weight: bold;
                                            font-size: 11pt;
                                            overflow: visible}
/* Use to set position of menubar */
div.portlet {position: absolute;
             width: 70%;
             top: 110px;
             left: 5px;
             margin: 0em;
             padding: 0em;
             color: #6d6f71;
             opacity: 0.85;
             z-index: 1}

/* The addition of this <div> is unavoidable because with a horizontal menubar */
/* you have to take the dropdown out of the flow whilst preserving its position */
/* relative to the top level option selected. A <div> block allows for relative */
/* positioning without upsetting the flow of the horizontal elements.           */
div.submenu {display: none;
             position: absolute;
             width: 100%;
             left: 0px;
             margin: 0em;
             padding: 0em;
             overflow: visible;
             color: #4a9a44;
             background: #ffffff;             
             -moz-border-radius: 12px;
             z-index: 1}

/* Make sure that the first layer is displayed horizontally */
ul.mktree > li > ul:first-child > li {position: relative;
                                      top: 0px;
                                      left: 0px;
                                      display: inline;
                                      padding: 2px 20px 5px 20px}

/* All subsequent descendents are block displayed submenus */
div.submenu ul {display: block;
                list-style: none;
                position: relative;  
                width: 70%;                                                 
                left: 0px;
                top: 0px;
                padding: 2px 0px 2px 0px;
                margin: 10px 20px 10px 20px;
                line-height: 0.9em;
                text-align: left;
                color: #4a9a44}

/* Adjust gap between seperate <li> entries, but not between wrapped entries */
ul.mktree > li > ul:first-child > li div.submenu > ul > li {margin: 12px 0px 12px 0px} 

/* Add in the horizontal menu item separator bars */
ul.mktree > li > ul:first-child > li +li {border-left: solid 2px;
                                          border-color: #4a9a44}
                
/* The following pushes sub-sub-menus to the right and down slightly*/
div.submenu div.submenu {left: 99%; top: 36%}

/* The following makes the menus appear when the mouse moves over the items */
li:hover > div.submenu:first-child {display: block}



Collapse
Posted by Richard Hamilton on
Gustaf,

I have spent a fair while studying the xowiki code to find where the html is created for the default-view of the categories includelet but so far have not identified it. I have not written any xotcl and so this is a little out of my box!

I wonder if you could give me a steer towards the location of the specific code that prepares the categories into nested unordered lists. Alternatively perhaps you might know of a better way to approach this change.

Regards
Richard

Collapse
25: Is this it? (response to 24)
Posted by Richard Hamilton on
nbsp; Category instproc render_category {{-open:boolean false} cat_content} {
    set open_state [expr {[my set open_requests]>0?"class='liOpen'" : "class='liClosed'"}]
    set c [expr {[my exists count] ? "<a href='[my href]'>([my count])</a>" : ""}]
    return "<li $open_state>[my label] $c\n <ul>$cat_content</ul>\n"
  }

If I change :

return "<li $open_state>[my label] $c\n <ul>$cat_content</ul>\n"

to :

return "<li $open_state>[my label] $c\n <div class="submenu"><ul>$cat_content</ul></div>\n"

Will that work?


Lets try and see!
Collapse
26: Aha!! (response to 25)
Posted by Richard Hamilton on
Hole in one!!

Goody goody gum drops! 😊

Happy chappy.

Sorry, in case any of you think I'm nuts (you're probably right) but my intention is to document these discoveries for the future reference of others (and probably me as well some months down the line).

Thank you Gustaf - what an absolutely FANTASTIC tool this xowiki contraption is! 😊

Richard

Collapse
27: Re: Is this it? (response to 25)
Posted by Steve Manning on
Why <div class="submenu">
    $cat_content
</div> instead of ?

- Steve
Collapse
28: Re: Is this it? (response to 27)
Posted by Steve Manning on
That'll teach me to use enhanced text :o( what I meant to say was...

Why

<div class="submenu"><ul>$cat_content</ul></div>

instead of

<ul class="submenu">$cat_content</ul>?


    - Steve

Collapse
29: Re: Is this it? (response to 25)
Posted by Gustaf Neumann on
As Steve asked, do you really need the div around the ul, would not be a CSS class for ul sufficient?

If yes, you would not need the class for ul either, when you use -decoration plain" for the includelet. Then you could address the ul via "div.categories ul" in CSS ("-decoration none" supresses even the surrounding div).

Collapse
30: Re: Is this it? (response to 29)
Posted by Richard Hamilton on
I fully understand the thrust of that comment, I spent hours working through it with that assumption in mind. However, I have explained in the comments that because the top level menu is to be rendered horizontally, it has to be:

display: inline;

This is fine until you add the vertically rendered submenus, i.e. setting the <ul> to display: block. What happens then is that the vertical menu is positioned inline to the top level menu, thereby displacing the subsequent horizontal menu items from their expected positions. This cannot (to the limit of my knowledge) be rectified by adjusting the <ul> class because its position cannot change the inline positions of its parent element.

If you remove the submenu <ul> from the inline display sequence by making it position absolute, your containing block for position reference is the grandparent <ul> rather than the parent <li> element! As the menu is dynamically generated, you cannot risk making absolute position adjustments because you don't know how many elements or subsubmenus there will be.

The containing <div> that I have proposed provides you with a new position reference for the <ul> block where 100% of the <div>'s width is equal to the width of its parent <li> element. This allows you to absolutely position the submenus and subsubmenus with reference to the left hand edge of the <li> that gives rise to it. Page 208, para 2 of the Lie & Bos CSS book refers. I don't think that there is a more minimal solution.

I agree that my style sheet could perhaps have been written to work with the -decoration none version, but actually some of the added classes and wrapping div blocks are useful for precision in the selectors.

I have had to alter a few details and will post back. However one thing I have found is that wherever a series of subcategories are rendered by xowiki inside a parent <li>, the rendered does not close the tag with a </li>. Now I know that under the HTML spec this omission is legitimate, however there are circumstances where this can cause ambiguity. I would therefore recommend a change to close the tags.

(Example; I have been asked to make the dropdowns about 80% opaque. If you reduce an element's opacity in CSS or javascript, all descendents are affected and the effect cannot be reversed by subsequent more specific rules. Therefore to add a partially transparent background without reducing the opacity of the text, I have to add another <div class="opaque"><div>which is sized and positioned to provide the transparent backdrop to the menu. Without the explicit closing </li> the browser assumes this <div> to be another top level <li> rather than a block element still in the previous one).

Sorry, this is all rather arcane detail, but it takes hours to thrash through and I may as well record it.

Regards
Richard

Collapse
32: Correction! (response to 29)
Posted by Richard Hamilton on
The example of ambiguity relating to the unclosed <li> tags is not correct. I had made an error - the lack of a closing tag makes no difference (except perhaps to my sense of symmetry!)

However, for the time being I stand by the rest of the previous posting!! 😊

R.

Collapse
Posted by Torben Brosten on
Richard, I see you're trying to reconcile a few different css styles.

Something I've learned with css that really helps with cross browser compatibility is to reverse the cascade of the style definitions by most specific first to least specific last. For example:

div.xowiki-content #wikicmds a {..
div.xowiki-content #wikicmds a:hover {..
div.xowiki-content #wikicmds a:active {..
div.xowiki-content #wikicmds {..

div.xowiki-content div.news-item .item-footer {..

div.xowiki-content pre, div.code {..
div.xowiki-content pre p i, div.code p i {..
div.xowiki-content pre i, div.code i {..
div.xowiki-content pre em, div.code p em {..
div.xowiki-content pre em, div.code em {..
div.xowiki-content pre, .code {..
div.xowiki-content .margin-form .form-button, .margin-form
div.xowiki-content a.external {..
div.xowiki-content a.file {..
div.xowiki-content a.glossary {..
div.xowiki-content h1 {..
div.xowiki-content h2 {..
div.xowiki-content h3 {..
div.xowiki-content h4 {..
div.xowiki-content .box {..
div.xowiki-content .hr {..
div.xowiki-content .item-footer {..
div.xowiki-content .content-chunk-footer {..
div.xowiki-content .image-button img {..
div.xowiki-content {..

from: http://dekkasupply.com/resources/xowiki/xowiki.css

when using this technique, you may experience:

1. a more consistent look between browsers, or have an easier time achieving it.

2. that you don't need to reference the LI directly in css.

At some point I'd like to see the css in xowiki's code moved to its style sheet, and organized this way. (I volunteer, if Gustaf says OK to it. Gustaf?).

Collapse
Posted by Richard Hamilton on
I like it. That's a very nice logical approach to a surprisingly difficult problem.

😊

R.

Collapse
34: Re: Correction! (response to 32)
Posted by Gustaf Neumann on
When i make an HTML document out of your example, using the usual openacs stylesheet + cattree.css and xowiki.css, nothing is displayed under FF 3.5.5 (because of the display nones and fontsize 0). When "cattree.css" + mktree.js are removed, it shows. anyhow, i see, your CSS markup is already quite tricky.

Anyhow, it is not likely that the mktree renderer is a good choice for rendering menus. Furthermore, "Category instproc render_category ... " is gone since early this year and has been replaced by some more generic tree renderer classes (in tree-procs.tcl) which are used for various purposes in xowiki (not only for categories). The right approach seems to be write your own tree renderer and pass the tree-renderer via "-style" to the categories includelet. This way, you can use arbitrary CSS classes and you can freely add / remove divs without breaking anything else.

Collapse
35: Re: Correction! (response to 34)
Posted by Richard Hamilton on
Gustav,

Yes, you're right. Piggybacking something not designed for the purpose was sloppy, but time is my enemy at the moment!

Also, I posted that code from a set of working static files rather than from a working installation and there were faults in it. I have refined my CSS quite considerably since I posted the code and will post it back here now that I have it working on a live system.

Perhaps to create a more general solution, when time is available, I will do as you recommend and create a custom renderer with a horiz-menu-view paramter option to activate it. That would be the better solution to post here.

Happily though, at least for this application, what I have done seems to work ok.

Is the deprecation of "Category instproc render_category" relevant to the current release OpenACS codebase or will this happen in the next release?

Regards
Richard

Collapse
36: Re: Correction! (response to 35)
Posted by Gustaf Neumann on
since xowiki is not part of any official OpenACS releases, and since xowiki in general tries to work with multiple OpenACS versions, you can use the version you have now as long as you are happy with it.

For testing i have added a small addition to xowiki head, which add a menu-renderer in the style i believe you want. One can use this via {{categories -style samplemenu}}.

  #
  # List-specific renderer based for some menus
  #
  TreeRenderer create TreeRenderer=samplemenu \
      -superclass TreeRenderer=list \
      -li_expanded_atts [list "class='menu-open'" "class='menu-closed'"] \
      -subtree_wrapper_class "submenu"

  TreeRenderer=samplemenu proc include_head_entries {args} {
    # add your CSS here...
  }
  TreeRenderer=samplemenu proc render {tree} {
    return "<ul class='menu' id='[$tree id]'>[next]</ul>"
  }
Collapse
37: Re: Correction! (response to 36)
Posted by Richard Hamilton on
Gustaf,

Oh, fantastic. Thank you very much indeed. That will make a great general purpose solution for this kind of menu.

I have finished working through the CSS changes required to make this work with {{categories -decoration none}} which I have posted below. I noticed that even with -decoration none the categories tree is still rendered with class="mktree" in the version I am using.

At the moment this assumes and requires a containing <div> with class="foregroundcontainer" which is my main page content container. The only reason this is needed in the CSS is to eliminate the <h3>@category_name@</h3> without destroying the general case of the <h3> tag. If a specific class is added to this <h3> tag the requirement for a containing div would be eliminated.

The root of the category tree <ul> for the menu bar is identified as class="mktree" which seems to be still there even with -decoration none. I don't know if this will be true in later versions.

This also still requires each <ul> block to be wrapped in a <div class"submenu">. This demo carries fonts and colours specific to the site I am working on but these can obviously be altered to taste.

I hope it works this time!

Regards
Richard

/* ################### */
/* Menu system classes */
/* ################### */

/* Set the style for links on the menu bar */
div.foregroundcontainer > ul.mktree a:link {font-family: "Segoe UI", arial, sans-serif;
                                            font-weight: bold;
                                            font-size: 10pt;
                                            background-color: transparent}

/* Set style for visited links on the menu bar */
div.foregroundcontainer > ul.mktree a:visited {font-family: "Segoe UI", arial, sans-serif;
                                              font-weight: bold;
                                              font-size: 10pt;
                                              background-color: transparent}

/* Vanish the bits of the OpenAcs Category tree that we don't want */
div.foregroundcontainer > img + img + img + img +h3 {display: none}

/* Hide top layer of PowerofAloe Category tree by fiddling with font size */
div.foregroundcontainer > ul.mktree > li {position: absolute;
                                          left: 40px;
                                          font-size: 0pt;
                                          color: #ffffff;
                                          margin: 0px;
                                          list-style: none}

/* Have to immediately more explicitly re set to size required for menu bar */
div.foregroundcontainer > ul.mktree > li > div.submenu {font-family: "Segoe UI", arial, sans-serif;
                                                        font-weight: bold;
                                                        font-size: 10pt;
                                                        overflow: visible}

/* Use to set position of menubar */
ul.mktree {position: absolute;
          border: none;
          width: 720px;
          top: 9em;
          left: 0em;
          margin: 0em;
          padding: 0em;
          z-index: 1}

/* Make sure that the first layer is displayed horizontally */
ul.mktree > li > div.submenu > ul:first-child > li {position: relative;
                                                    top: 0px;
                                                    left: 0px;
                                                    display: inline;
                                                    padding: 2px 20px 5px 20px;
                                                    color: #6d6f71}

/* Adjust gap between seperate <li> entries in submenus, but not between wrapped entries */
ul.mktree > li > div.submenu > ul:first-child > li div.submenu > ul > li {margin: 7px 0px 7px 6px}

/* Add in the horizontal menu item separator bars */
ul.mktree > li > div.submenu > ul:first-child > li + li {border-left: solid 2px;
                                                        border-color: #4a9a44}

/* The addition of this <div> is unavoidable because with a horizontal menubar */
/* you have to take the dropdown out of the flow whilst preserving its position */
/* relative to the top level option selected. A <div> block allows for relative */
/* positioning without upsetting the flow of the horizontal elements.          */
div.foregroundcontainer > ul.mktree > li > div.submenu div.submenu {display: none;
                                                                    position: absolute;
                                                                    width: 100%;
                                                                    top: 80%;
                                                                    left: 0%;
                                                                    margin: 0px;
                                                                    padding: 0px;
                                                                    overflow: visible;
                                                                    background-color: #ffffff;
                                                                    opacity: 0.90;
                                                                    filter:alpha(opacity=90);
                                                                    -moz-border-radius: 12px}

/* All subsequent descendents are block displayed submenus */
div.foregroundcontainer > ul.mktree > li > div.submenu > ul > li > div.submenu ul {display: block;
                                                                                  list-style: none;
                                                                                  position: relative;
                                                                                  width: 70%;
                                                                                  left: 0px;
                                                                                  top: 0px;
                                                                                  padding: 5px 7px 12px 17px;
                                                                                  margin: 0px;
                                                                                  line-height: 0.9em;
                                                                                  text-align: left;
                                                                                  color: #6d6f71;
                                                                                  z-index: 1}

/* The following pushes sub-sub-menus to the right and down slightly*/
ul.mktree > li > div.submenu > ul > li > div.submenu div.submenu {left: 7.1em; top: 4.3em}

/* The following makes the menus appear when the mouse moves over the items */
ul.mktree > li > div.submenu > ul li:hover > div.submenu {display: block}

Collapse
38: Re: Correction! (response to 37)
Posted by Gustaf Neumann on
Concerning "-decoration": This flag just controls the outer wrapper of an includelet and works exactly the same way for all kind of includelets in xowiki. The mktree markup is coming from the default renderer of the categories includelet. If a different renderer is specified for the categories, the inner markup of this includelet will look differently.
Collapse
Posted by Richard Hamilton on
I have two categories defined:

Site-Root and Dropdown


Under Site-Root I have content pages 1-4 as top level xowiki pages, and a dropdown menu containing five subordinate pages. The structure is:

Site-Root
    page01
    page02
    page03
    page04
    Dropdown
        paged01
        paged02
        paged03
        paged04
        paged05


Site-Root is an invisible category so that I get a horizontal menu. It looks like this:

page01  |  page02  |  page 03  |  page04  |  Dropdown
                                               paged01
                                               paged02
                                               paged03
                                               paged04
                                               paged05


For user interface design reasons I need the layout order to be:

page01  |  page02  |  page 03  |  Dropdown  |  page 04
                                    paged01
                                    paged02
                                    paged03
                                    paged04
                                    paged05

I have racked my brains and tried various ordering numbers in the Section field, but I cannot work out how to do this. 
The page ordering seems to work perfectly within a category, but is there a way of specifying that a subcategory
(and its children) should be listed in between sibling items that are not categories?

Richard

Collapse
40: Re: Correction! (response to 36)
Posted by Richard Hamilton on
Gustaf,

After checking out and playing with a HEAD version of xowiki, I thought I should take the opportunity to move my work across on the new version.

I have therefore adjusted my CSS to work with the samplemenu renderer that you so kindly provided, and it works beautifully. Thank you for posting that, it has really helped me to start to understand your code and the whole oo way of doing things.

I will strip out the project specific stylistic elements and will post a short samplemenu.css file (that could, if deemed suitable, be included in the distribution) and some brief documentation.

When I have more time I will work up a LHS vertical menu that works in a similar way. I will use your code as a boilerplate to create a renderer for the two styles - something like { -style horizontalmenu } and { -style vertical menu }.

I am a great believer in CSS, and where it can be used as a substitute for Javascript code I am all for having the choice.

Thank you so very much for all your help.

Regards
Richard