rich:contextMenu contextMenu

Component identification parameters

Name | Value
--- | ---
component-type | org.richfaces.ContextMenu
component-class | org.richfaces.component.html.ContextMenu
component-family | org.richfaces.ContextMenu
renderer-type | org.richfaces.DropDownMenuRenderer
tag-class | org.richfaces.taglib.ContextMenuTagHandler

## Creating the Component with a Page Tag

To create the simplest variant on a page use the following syntax:

Example:

    ...
    <rich:contextMenu event="oncontextmenu" attached="true">
    ...

## Creating the Component Dynamically Using Java

Example:

    import org.richfaces.component.html.ContextMenu;
    ...
    html.ContextMenu myContextMenu = new html.ContextMenu();
    ...

## Details of Usage

<rich:contextMenu> is a support-like component. Context menu itself is an invisible panel that appears after a particular client side event (onmouseover, onclick, etc) occured on a parent component. The event is defined with an "event" attribute. The component uses "oncontextmenu" event by default to call a context menu by clicking on the right mouse button.

<rich:menuGroup> , <rich:menuItem> and <rich:menuSeparator> components are used as nested elements for <rich:contextMenu> in the same way as for <rich:dropDownMenu> .

If a value of the "attached" attribute is defined as "true", the component is attached to the parent component. An example is placed below.

Example:

    ...
            <h:panelGrid columns="1" columnClasses="cent">
                    <h:panelGroup id="picture">
                            <h:graphicImage value="/richfaces/jQuery/images/pic1.png" id="pic"/>
                            <rich:contextMenu event="oncontextmenu" attached="true" submitMode="none">
                                    <rich:menuItem value="Zoom In" onclick="enlarge();" id="zin"></rich:menuItem>
                                    <rich:menuItem value="Zoom Out" onclick="decrease();" id="zout"></rich:menuItem>
                            </rich:contextMenu>
                    </h:panelGroup>
            </h:panelGrid>
    ...

The "enlarge()" and "decrease()" functions definition is placed below.

    ...
            <script type="text/javascript">
                    function enlarge(){
                            document.getElementById('pic').width=document.getElementById('pic').width*1.1;
                            document.getElementById('pic').height=document.getElementById('pic').height*1.1;
                    }
                    function decrease(){
                            document.getElementById('pic').width=document.getElementById('pic').width*0.9;
                            document.getElementById('pic').height=document.getElementById('pic').height*0.9;
                    }
            </script>
    ...

In the example a picture zooming possibility with <rich:contextMenu> component usage was shown. The picture is placed on the <h:panelGroup> component. The <rich:contextMenu> component is defined as nested to <h:panelGroup> one and has a value of the "attached" attribute defined as "true". Thus, the context menu is attached to the parent component. The context menu has two items to zoom in (zoom out) a picture by "onclick" event. For earch item corresponding JavaScript function is defined to provide necessary action as a result of the clicking on it. For the menu is defined an "oncontextmenu" event to call the context menu on a right click mouse event.

In the example the context menu is defined for the parent <h:panelGroup> component with a value of "id" attribute equal to "picture". You should be careful with such definition, because a client context menu is looked for a DOM element with a client Id of a parent component on a server. If a parent component doesn't encode an Id on a client, it can't be found by the <rich:contextMenu> and it's attached to its closest parent in a DOM tree.

If the "attached" attribute has "false" value, component activates via JavaScript API with assistance of <rich:componentControl> . An example is placed below.

Example:

    ...
            <h:form id="form">
                    <rich:contextMenu attached="false" id="menu" submitMode="ajax">
                            <rich:menuItem ajaxSingle="true">
                                    <b>{car} {model}</b> details
                                    <a4j:actionParam name="det" assignTo="#{ddmenu.current}" value="{car} {model} details"/>
                            </rich:menuItem>
                            <rich:menuGroup value="Actions">
                                    <rich:menuItem ajaxSingle="true">
                                            Put <b>{car} {model}</b> To Basket
                                            <a4j:actionParam name="bask" assignTo="#{ddmenu.current}" value="Put {car} {model} To Basket"/>
                                    </rich:menuItem>
                                    <rich:menuItem value="Read Comments" ajaxSingle="true">
                                            <a4j:actionParam name="bask" assignTo="#{ddmenu.current}" value="Read Comments"/>
                                    </rich:menuItem>
                                    <rich:menuItem ajaxSingle="true">
                                            Go to <b>{car}</b> site
                                            <a4j:actionParam name="bask" assignTo="#{ddmenu.current}" value="Go to {car} site"/>
                                    </rich:menuItem>
                            </rich:menuGroup>
                    </rich:contextMenu>

                    <h:panelGrid columns="2">
                            <rich:dataTable value="#{dataTableScrollerBean.tenRandomCars}" var="car" id="table"
                                                            onRowMouseOver="this.style.backgroundColor='#F8F8F8'"
                                                            onRowMouseOut="this.style.backgroundColor='#{a4jSkin.tableBackgroundColor}'" rowClasses="cur">
                                    <rich:column>
                                            <f:facet name="header">Make</f:facet>
                                            <h:outputText value="#{car.make}"/>
                                    </rich:column>
                                    <rich:column>
                                            <f:facet name="header">Model</f:facet>
                                            <h:outputText value="#{car.model}"/>
                                    </rich:column>
                                    <rich:column>
                                            <f:facet name="header">Price</f:facet>
                                            <h:outputText value="#{car.price}" />
                                    </rich:column>

                                    <rich:componentControl event="onRowClick" for="menu" operation="show">
                                        <f:param value="#{car.model}" name="model"/>
                                        <f:param value="#{car.make}" name="car"/>
                                    </rich:componentControl>
                            </rich:dataTable>

                            <a4j:outputPanel ajaxRendered="true">
                                    <rich:panel>
                                            <f:facet name="header">Last Menu Action</f:facet>
                                            <h:outputText value="#{ddmenu.current}"></h:outputText>
                                    </rich:panel>
                            </a4j:outputPanel>
                    </h:panelGrid>
            </h:form>
     ...

This is a result:

The "attached" attribute usage

In the example the context menu is activated (by clicking on the left mouse button) on the table via JavaScript API with assistance of <rich:componentControl> . The attribute "for" contains a value of the <rich:contextMenu> Id. For menu appearance Java Script API function "Show" is used. It is defined with "operation" attribute for the <rich:componentControl> component. Context menu is recreated after the every call on a client and new {car} and {model} values are inserted in it. In the example for a menu customization macrosubstitutions were used.

The <rich:contextMenu> component can be defined once on a page and can be used as shared for different components (this is the main difference from the <rich:dropDownMenu> component). It's necessary to define it once on a page (as it was shown in the example above) and activate it on required components via JavaScript API with assistance of <rich:componentControl> .

The <rich:contextMenu> "submitMode" attribute can be set to three possible parameters:

- Server (default)

Regular form submition request is used

- Ajax

Ajax submission is used for switching

- None

The "action" and "actionListener" item's attributes are ignored. Menu items don't fire any submits themselves. The behavior is fully defined by the components nested inside items.

Note:

As the <rich:contextMenu> component doesn't provide its own form, use it between <h:form> and </h:form> tags.

## JavaScript API

JavaScript API

Function | Description | Apply to
--- | --- | ---
Hide() | Hide component or group | Component, group
Show() | Show component or group | Component, group

## Look-and-Feel Customization

For skinnability implementation, the components use a style class redefinition method. Default style classes are mapped on skin parameters.

There are two ways to redefine the appearance of all <rich:contextMenu> components at once:

- Redefine the corresponding skin parameters
- Add to your style sheets style classes used by a <rich:contextMenu> component

## Skin Parameters Redefinition

Skin parameters redefinition for a border

Skin parameters | CSS properties
--- | ---
panelBorderColor | border-color
additionalBackgroundColor | background-color

Skin parameters redefinition for a background

Skin parameters | CSS properties
--- | ---
additionalBackgroundColor | border-top-color
additionalBackgroundColor | border-left-color
additionalBackgroundColor | border-right-color

## Definition of Custom Style Classes

On the screenshot there are classes names that define styles for component elements.

Style classes

Classes names that define the contextMenu element

Class name | Description
--- | ---
rich-menu-list-border | Defines styles for borders
rich-menu-list-bg | Defines styles for a general background list
rich-menu-list-strut | Defines styles for a wrapper <div> element for a strut of a popup list

In order to redefine styles for all <rich:contextMenu> components on a page using CSS, it's enough to create classes with the same names (possible classes could be found in the tables above) and define necessary properties in them.

Example:

    ...
    .rich-menu-item{
            font-style:italic;
    }
    ...

This is a result:

Redefinition styles with predefined classes

In the example the font style for row items was changed.

Also it’s possible to change styles of particular <rich:contextMenu> component. In this case you should create own style classes and use them in corresponding <rich:contextMenu> styleClass attributes. An example is placed below:

Example:

    ...
    .myClass{
            font-weight:bold;
    }
    ...

The "rowClasses" attribute for <h:panelGrid> is defined as it’s shown in the example below:

Example:

    <h:panelGrid ... rowClasses="myClass"/>

This is a result:

Redefinition styles with own classes and styleClass attributes

As it could be seen on the picture above, the font weight for row items was changed.

## Relevant Resources Links

Here you can see an example of <rich:contextMenu> usage and sources for the given example.