- Added clean-tomcat target to build

- Added new features to dialog framework
- Fixed bug in error message in Add Content Dialog
- Fixed typos is sample custom config file

git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@3413 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
Gavin Cornwell
2006-07-26 12:15:53 +00:00
parent 4ef626f371
commit 1b3901c2f5
18 changed files with 776 additions and 24 deletions

View File

@@ -2,6 +2,7 @@ package org.alfresco.web.bean.dialog;
import java.text.MessageFormat;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.faces.context.FacesContext;
@@ -18,6 +19,7 @@ import org.alfresco.web.app.context.UIContextService;
import org.alfresco.web.bean.BrowseBean;
import org.alfresco.web.bean.NavigationBean;
import org.alfresco.web.bean.repository.Repository;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
import org.alfresco.web.ui.common.Utils;
/**
@@ -102,6 +104,11 @@ public abstract class BaseDialogBean implements IDialogBean
return outcome;
}
public List<DialogButtonConfig> getAdditionalButtons()
{
return null;
}
public String getCancelButtonLabel()
{

View File

@@ -1,5 +1,7 @@
package org.alfresco.web.bean.dialog;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import javax.faces.component.UIComponent;
@@ -9,6 +11,7 @@ import javax.faces.event.ActionEvent;
import org.alfresco.error.AlfrescoRuntimeException;
import org.alfresco.web.app.Application;
import org.alfresco.web.app.servlet.FacesHelper;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
import org.alfresco.web.config.DialogsConfigElement.DialogConfig;
import org.alfresco.web.ui.common.component.UIActionLink;
@@ -147,6 +150,17 @@ public class DialogManager
return desc;
}
/**
* Returns the id of a configured action group representing the actions to
* display for the dialog.
*
* @return The action group id
*/
public String getActions()
{
return this.currentDialogConfig.getActionsConfigId();
}
/**
* Returns the page the dialog will use
*
@@ -157,6 +171,51 @@ public class DialogManager
return this.currentDialogConfig.getPage();
}
/**
* Determines whether the current dialog's OK button is visible
*
* @return true if the OK button is visible, false if it's not
*/
public boolean isOKButtonVisible()
{
return this.currentDialogConfig.isOKButtonVisible();
}
/**
* Returns a list of additional buttons to display in the dialog
*
* @return List of button configurations
*/
public List<DialogButtonConfig> getAdditionalButtons()
{
List<DialogButtonConfig> buttons = null;
// get a list of buttons to display from the configuration
List<DialogButtonConfig> cfgButtons = this.currentDialogConfig.getButtons();
// get a list of buttons added dynamically by the dialog
List<DialogButtonConfig> dynButtons = this.currentDialog.getAdditionalButtons();
if (cfgButtons != null && dynButtons != null)
{
// combine the two lists
buttons = new ArrayList<DialogButtonConfig>(
cfgButtons.size() + dynButtons.size());
buttons.addAll(cfgButtons);
buttons.addAll(dynButtons);
}
else if (cfgButtons != null && dynButtons == null)
{
buttons = cfgButtons;
}
else if (cfgButtons == null && dynButtons != null)
{
buttons = dynButtons;
}
return buttons;
}
/**
* Returns the label to use for the cancel button
*

View File

@@ -1,7 +1,10 @@
package org.alfresco.web.bean.dialog;
import java.util.List;
import java.util.Map;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
/**
* Interface that defines the contract for a dialog backing bean
*
@@ -30,6 +33,13 @@ public interface IDialogBean
*/
public String finish();
/**
* Returns a list of additional buttons to display in the dialog.
*
* @return List of button configurations, null if there are no buttons
*/
public List<DialogButtonConfig> getAdditionalButtons();
/**
* Returns the label to use for the cancel button
*

View File

@@ -0,0 +1,67 @@
package org.alfresco.web.bean.workflow;
import java.util.ArrayList;
import java.util.List;
import javax.faces.context.FacesContext;
import org.alfresco.web.bean.dialog.BaseDialogBean;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* Bean implementation for the "Manage WorkItem" dialog.
*
* @author gavinc
*/
public class ManageWorkItemDialog extends BaseDialogBean
{
private static final Log logger = LogFactory.getLog(ManageWorkItemDialog.class);
// ------------------------------------------------------------------------------
// Dialog implementation
@Override
protected String finishImpl(FacesContext context, String outcome)
throws Exception
{
return null;
}
@Override
public List<DialogButtonConfig> getAdditionalButtons()
{
List<DialogButtonConfig> buttons = new ArrayList<DialogButtonConfig>(1);
buttons.add(new DialogButtonConfig("reassign-button",
"Reassign", null, "#{ManageWorkItemDialog.reassign}", "false", null));
return buttons;
}
// ------------------------------------------------------------------------------
// Event handlers
public void approve()
{
logger.info("approve button was pressed");
}
public void reject()
{
logger.info("reject button was pressed");
}
public void reassign()
{
logger.info("reassign button was pressed");
}
// ------------------------------------------------------------------------------
// Bean Getters and Setters
public boolean getApproveDisabled()
{
return true;
}
}

View File

@@ -131,12 +131,15 @@ public class DialogsConfigElement extends ConfigElementAdapter
protected String description;
protected String descriptionId;
protected String errorMsgId = "error_dialog";
protected boolean isOKButtonVisible = true;
protected List<DialogButtonConfig> buttons;
public DialogConfig(String name, String page, String bean,
String actionsConfigId, String icon,
String title, String titleId,
String description, String descriptionId,
String errorMsgId)
String errorMsgId, boolean isOKButtonVisible,
List<DialogButtonConfig> buttons)
{
// check the mandatory parameters are present
ParameterCheck.mandatoryString("name", name);
@@ -152,6 +155,8 @@ public class DialogsConfigElement extends ConfigElementAdapter
this.titleId = titleId;
this.description = description;
this.descriptionId = descriptionId;
this.isOKButtonVisible = isOKButtonVisible;
this.buttons = buttons;
if (errorMsgId != null && errorMsgId.length() > 0)
{
@@ -209,6 +214,16 @@ public class DialogsConfigElement extends ConfigElementAdapter
return this.errorMsgId;
}
public boolean isOKButtonVisible()
{
return this.isOKButtonVisible;
}
public List<DialogButtonConfig> getButtons()
{
return this.buttons;
}
/**
* @see java.lang.Object#toString()
*/
@@ -225,7 +240,98 @@ public class DialogsConfigElement extends ConfigElementAdapter
buffer.append(" titleId=").append(this.titleId);
buffer.append(" description=").append(this.description);
buffer.append(" descriptionId=").append(this.descriptionId);
buffer.append(" errorMsgId=").append(this.errorMsgId).append(")");
buffer.append(" errorMsgId=").append(this.errorMsgId);
buffer.append(" isOKButtonVisible=").append(this.isOKButtonVisible);
buffer.append(" buttons=").append(this.buttons).append(")");
return buffer.toString();
}
}
/**
* Inner class representing the configuration for an additional
* dialog button.
*
* @author gavinc
*/
public static class DialogButtonConfig
{
private String id;
private String label;
private String labelId;
private String action;
private String disabled;
private String onclick;
public DialogButtonConfig(String id, String label, String labelId,
String action, String disabled, String onclick)
{
this.id = id;
this.label = label;
this.labelId = labelId;
this.action = action;
this.disabled = disabled;
this.onclick = onclick;
if ((this.label == null || this.label.length() == 0) &&
(this.labelId == null || this.labelId.length() == 0))
{
throw new ConfigException("A dialog button needs to have a label or a label-id");
}
if (this.action == null || this.action.length() == 0)
{
throw new ConfigException("A dialog button requires an action");
}
else if (this.action.startsWith("#{") == false)
{
throw new ConfigException("The action for a dialog button must be a method binding expression, '"
+ this.action + "' is not!");
}
}
public String getAction()
{
return action;
}
public String getDisabled()
{
return disabled;
}
public String getId()
{
return id;
}
public String getLabel()
{
return label;
}
public String getLabelId()
{
return labelId;
}
public String getOnclick()
{
return onclick;
}
/**
* @see java.lang.Object#toString()
*/
@Override
public String toString()
{
StringBuilder buffer = new StringBuilder(super.toString());
buffer.append(" (id=").append(this.id);
buffer.append(" label=").append(this.label);
buffer.append(" label-id=").append(this.labelId);
buffer.append(" action=").append(this.action);
buffer.append(" disabled=").append(this.disabled);
buffer.append(" onclick=").append(this.onclick).append(")");
return buffer.toString();
}
}

View File

@@ -16,11 +16,14 @@
*/
package org.alfresco.web.config;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import org.alfresco.config.ConfigElement;
import org.alfresco.config.ConfigException;
import org.alfresco.config.xml.elementreader.ConfigElementReader;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
import org.dom4j.Element;
/**
@@ -32,6 +35,8 @@ public class DialogsElementReader implements ConfigElementReader
{
public static final String ELEMENT_DIALOGS = "dialogs";
public static final String ELEMENT_DIALOG = "dialog";
public static final String ELEMENT_BUTTONS = "buttons";
public static final String ELEMENT_BUTTON = "button";
public static final String ATTR_NAME = "name";
public static final String ATTR_PAGE = "page";
public static final String ATTR_MANAGED_BEAN = "managed-bean";
@@ -42,10 +47,18 @@ public class DialogsElementReader implements ConfigElementReader
public static final String ATTR_DESCRIPTION = "description";
public static final String ATTR_DESCRIPTION_ID = "description-id";
public static final String ATTR_ERROR_MSG_ID = "error-message-id";
public static final String ATTR_SHOW_OK_BUTTON = "show-ok-button";
public static final String ATTR_ID = "id";
public static final String ATTR_LABEL = "label";
public static final String ATTR_LABEL_ID = "label-id";
public static final String ATTR_ACTION = "action";
public static final String ATTR_DISABLED = "disabled";
public static final String ATTR_ONCLICK = "onclick";
/**
* @see org.alfresco.config.xml.elementreader.ConfigElementReader#parse(org.dom4j.Element)
*/
@SuppressWarnings("unchecked")
public ConfigElement parse(Element element)
{
DialogsConfigElement configElement = null;
@@ -62,7 +75,7 @@ public class DialogsElementReader implements ConfigElementReader
configElement = new DialogsConfigElement();
// go through the items to show
// go through the dialogs
Iterator<Element> items = element.elementIterator(ELEMENT_DIALOG);
while (items.hasNext())
{
@@ -78,10 +91,20 @@ public class DialogsElementReader implements ConfigElementReader
String description = item.attributeValue(ATTR_DESCRIPTION);
String descriptionId = item.attributeValue(ATTR_DESCRIPTION_ID);
String errorMsgId = item.attributeValue(ATTR_ERROR_MSG_ID);
String showOK = item.attributeValue(ATTR_SHOW_OK_BUTTON);
boolean isOKButtonVisible = true;
if (showOK != null)
{
isOKButtonVisible = Boolean.parseBoolean(showOK);
}
// parse any buttons that may be present
List<DialogButtonConfig> buttons = parseButtons(item);
DialogsConfigElement.DialogConfig cfg = new DialogsConfigElement.DialogConfig(
name, page, bean, actions, icon, title, titleId, description,
descriptionId, errorMsgId);
descriptionId, errorMsgId, isOKButtonVisible, buttons);
configElement.addDialog(cfg);
}
@@ -90,4 +113,44 @@ public class DialogsElementReader implements ConfigElementReader
return configElement;
}
/**
* Retrieve the configuration for additional buttons.
*
* @param dialog The dialog XML element
* @return List of configured buttons
*/
@SuppressWarnings("unchecked")
protected List<DialogButtonConfig> parseButtons(Element dialog)
{
List<DialogButtonConfig> buttons = null;
// iterate over any configured buttons
Element buttonsConfig = dialog.element(ELEMENT_BUTTONS);
if (buttonsConfig != null)
{
buttons = new ArrayList<DialogButtonConfig>(4);
Iterator<Element> children = buttonsConfig.elementIterator(ELEMENT_BUTTON);
while (children.hasNext())
{
Element button = children.next();
String id = button.attributeValue(ATTR_ID);
String label = button.attributeValue(ATTR_LABEL);
String labelId = button.attributeValue(ATTR_LABEL_ID);
String action = button.attributeValue(ATTR_ACTION);
String disabled = button.attributeValue(ATTR_DISABLED);
String onclick = button.attributeValue(ATTR_ONCLICK);
// create the button config object
DialogButtonConfig btnCfg = new DialogButtonConfig(id, label,
labelId, action, disabled, onclick);
// add the button to the list
buttons.add(btnCfg);
}
}
return buttons;
}
}

View File

@@ -31,6 +31,7 @@ public final class ComponentConstants
public static final String JAVAX_FACES_GRAPHIC = "javax.faces.Graphic";
public static final String JAVAX_FACES_PARAMETER = "javax.faces.Parameter";
public static final String JAVAX_FACES_MENU = "javax.faces.Menu";
public static final String JAVAX_FACES_BUTTON = "javax.faces.Button";
/**
* Private constructor

View File

@@ -0,0 +1,292 @@
package org.alfresco.web.ui.repo.component;
import java.io.IOException;
import java.util.Iterator;
import java.util.List;
import javax.faces.component.UICommand;
import javax.faces.component.UIComponent;
import javax.faces.component.UIOutput;
import javax.faces.component.html.HtmlCommandButton;
import javax.faces.context.FacesContext;
import javax.faces.context.ResponseWriter;
import javax.faces.el.MethodBinding;
import javax.faces.el.ValueBinding;
import org.alfresco.web.app.Application;
import org.alfresco.web.app.servlet.FacesHelper;
import org.alfresco.web.config.DialogsConfigElement.DialogButtonConfig;
import org.alfresco.web.ui.common.ComponentConstants;
import org.alfresco.web.ui.common.Utils;
import org.alfresco.web.ui.common.component.SelfRenderingComponent;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* Component that displays the buttons for a dialog.
* <p>
* The standard <code>OK</code> and <code>Cancel</code> buttons
* are always generated. Any additional buttons, either configured
* or generated dynamically by the dialog, are generated in between
* the standard buttons.
*
* @author gavinc
*/
public class UIDialogButtons extends SelfRenderingComponent
{
protected static final String BINDING_EXPRESSION_START = "#{";
private static final Log logger = LogFactory.getLog(UIDialogButtons.class);
@Override
public String getFamily()
{
return "org.alfresco.faces.DialogButtons";
}
@Override
public void encodeBegin(FacesContext context) throws IOException
{
if (!isRendered()) return;
if (this.getChildCount() == 0)
{
// generate all the required buttons the first time
generateButtons(context);
}
ResponseWriter out = context.getResponseWriter();
out.write("<table cellpadding=\"1\" cellspacing=\"1\" border=\"0\">");
}
@Override
public void encodeChildren(FacesContext context) throws IOException
{
if (!isRendered()) return;
ResponseWriter out = context.getResponseWriter();
// render the buttons
for (Iterator i = getChildren().iterator(); i.hasNext(); /**/)
{
out.write("<tr><td align=\"center\">");
UIComponent child = (UIComponent)i.next();
Utils.encodeRecursive(context, child);
out.write("</td></tr>");
}
}
@Override
public void encodeEnd(FacesContext context) throws IOException
{
if (!isRendered()) return;
ResponseWriter out = context.getResponseWriter();
out.write("</table>");
}
@Override
public boolean getRendersChildren()
{
return true;
}
/**
* Generates the buttons for the dialog currently being shown.
*
* @param context Faces context
*/
@SuppressWarnings("unchecked")
protected void generateButtons(FacesContext context)
{
// generate the OK button, if necessary
if (Application.getDialogManager().isOKButtonVisible())
{
UICommand okButton = (UICommand)context.getApplication().
createComponent(HtmlCommandButton.COMPONENT_TYPE);
okButton.setRendererType(ComponentConstants.JAVAX_FACES_BUTTON);
FacesHelper.setupComponentId(context, okButton, "finish-button");
// create the binding for the finish button label
ValueBinding valueBinding = context.getApplication().createValueBinding(
"#{DialogManager.finishButtonLabel}");
okButton.setValueBinding("value", valueBinding);
// create the action binding
MethodBinding methodBinding = context.getApplication().createMethodBinding(
"#{DialogManager.finish}", null);
okButton.setAction(methodBinding);
// create the binding for whether the button is disabled
valueBinding = context.getApplication().createValueBinding(
"#{DialogManager.finishButtonDisabled}");
okButton.setValueBinding("disabled", valueBinding);
// setup CSS class for button
String styleClass = (String)this.getAttributes().get("styleClass");
if (styleClass != null)
{
okButton.getAttributes().put("styleClass", styleClass);
}
// add the OK button
this.getChildren().add(okButton);
}
// generate the additional buttons
generateAdditionalButtons(context);
// generate the OK button
UICommand cancelButton = (UICommand)context.getApplication().
createComponent(HtmlCommandButton.COMPONENT_TYPE);
cancelButton.setRendererType(ComponentConstants.JAVAX_FACES_BUTTON);
FacesHelper.setupComponentId(context, cancelButton, "cancel-button");
// create the binding for the cancel button label
ValueBinding valueBinding = context.getApplication().createValueBinding(
"#{DialogManager.cancelButtonLabel}");
cancelButton.setValueBinding("value", valueBinding);
// create the action binding
MethodBinding methodBinding = context.getApplication().createMethodBinding(
"#{DialogManager.cancel}", null);
cancelButton.setAction(methodBinding);
// setup CSS class for button
String styleClass = (String)this.getAttributes().get("styleClass");
if (styleClass != null)
{
cancelButton.getAttributes().put("styleClass", styleClass);
}
// set the immediate flag to true
cancelButton.getAttributes().put("immediate", Boolean.TRUE);
// add the Cancel button
this.getChildren().add(cancelButton);
}
/**
* If there are any additional buttons to add as defined by the dialog
* configuration and the dialog at runtime they are generated in this
* method.
*
* @param context Faces context
*/
@SuppressWarnings("unchecked")
protected void generateAdditionalButtons(FacesContext context)
{
// get potential list of additional buttons
List<DialogButtonConfig> buttons = Application.getDialogManager().getAdditionalButtons();
if (buttons != null && buttons.size() > 0)
{
if (logger.isDebugEnabled())
logger.debug("Adding " + buttons.size() + " additional buttons: " + buttons);
for (DialogButtonConfig buttonCfg : buttons)
{
UICommand button = (UICommand)context.getApplication().
createComponent(HtmlCommandButton.COMPONENT_TYPE);
button.setRendererType(ComponentConstants.JAVAX_FACES_BUTTON);
FacesHelper.setupComponentId(context, button, buttonCfg.getId());
// setup the value of the button (the label)
String label = buttonCfg.getLabel();
if (label != null)
{
// see if the label represents a value binding
if (label.startsWith(BINDING_EXPRESSION_START))
{
ValueBinding binding = context.getApplication().createValueBinding(label);
button.setValueBinding("value", binding);
}
else
{
button.setValue(label);
}
}
else
{
// NOTE: the config checks that a label or a label id
// is present so we can assume there is an id
// if there isn't a label
String labelId = buttonCfg.getLabelId();
label = Application.getMessage(context, labelId);
button.setValue(label);
}
// setup the action binding, the config checks that an action
// is present so no need to check for NullPointer. It also checks
// it represents a method binding expression.
String action = buttonCfg.getAction();
MethodBinding methodBinding = context.getApplication().
createMethodBinding(action, null);
button.setAction(methodBinding);
// setup the disabled attribute, check for null and
// binding expressions
String disabled = buttonCfg.getDisabled();
if (disabled != null && disabled.length() > 0)
{
if (disabled.startsWith(BINDING_EXPRESSION_START))
{
ValueBinding binding = context.getApplication().
createValueBinding(disabled);
button.setValueBinding("disabled", binding);
}
else
{
button.getAttributes().put("disabled",
Boolean.parseBoolean(disabled));
}
}
// setup CSS class for the button
String styleClass = (String)this.getAttributes().get("styleClass");
if (styleClass != null)
{
button.getAttributes().put("styleClass", styleClass);
}
// setup the onclick handler for the button
String onclick = buttonCfg.getOnclick();
if (onclick != null && onclick.length() > 0)
{
button.getAttributes().put("onclick", onclick);
}
// add the button
this.getChildren().add(button);
if (logger.isDebugEnabled())
logger.debug("Added button with id of: " + button.getId());
}
// add a spacing row to separate the additional buttons from the Cancel button
addSpacingRow(context);
}
}
/**
* Creates an output text component to represent a spacing row.
*
* @param context Faces context
*/
@SuppressWarnings("unchecked")
protected void addSpacingRow(FacesContext context)
{
UIOutput spacingRow = (UIOutput)context.getApplication().createComponent(
ComponentConstants.JAVAX_FACES_OUTPUT);
spacingRow.setRendererType(ComponentConstants.JAVAX_FACES_TEXT);
FacesHelper.setupComponentId(context, spacingRow, null);
spacingRow.setValue("<div class=\"wizardButtonSpacing\" />");
spacingRow.getAttributes().put("escape", Boolean.FALSE);
this.getChildren().add(spacingRow);
}
}

View File

@@ -0,0 +1,43 @@
/*
* Copyright (C) 2005 Alfresco, Inc.
*
* Licensed under the Mozilla Public License version 1.1
* with a permitted attribution clause. You may obtain a
* copy of the License at
*
* http://www.alfresco.org/legal/license.txt
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific
* language governing permissions and limitations under the
* License.
*/
package org.alfresco.web.ui.repo.tag;
import org.alfresco.web.ui.common.tag.HtmlComponentTag;
/**
* Tag class that allows the UIDialogButtons component to be placed on a JSP.
*
* @author gavinc
*/
public class DialogButtonsTag extends HtmlComponentTag
{
/**
* @see javax.faces.webapp.UIComponentTag#getComponentType()
*/
public String getComponentType()
{
return "org.alfresco.faces.DialogButtons";
}
/**
* @see javax.faces.webapp.UIComponentTag#getRendererType()
*/
public String getRendererType()
{
return null;
}
}