I added a new attribute 'actionListener' to tag 'outputFile' in file nxweb-util.tld, in class UIOutputFile I added in String field named 'actionListener' and its getter/setter, in method encodeBegin I create an object of class methodBinding like this :
                Application app = context.getApplication();
MethodBinding meth = app.createMethodBinding(getActionListener(),
                                new Class[] { ActionEvent.class });
                downloadComp.setActionListener(meth);


The problem is that method getActionListener() seems to return null, here it is :
        public String getActionListener() {
        if (actionListener != null) {
            return actionListener;
        }
        ValueBinding vb = getValueBinding("actionListener");
String v = vb != null ? (String) vb.getValue(getFacesContext()) : null;
        return v;
        }



What am I doing wrong ? Did I forget something ?
(I attached the class)

Regards.

Anahide Tchertchian wrote:
Hi,

Vincent Dutat a écrit :
For that part too, I am a bit lost. I found the taglib file and tld file where I can create my own tag but I dont know what type I can use for the attribute actionListener. By 'type', I suppose it's a class I have to specify.

You should not need to write a new tag to do that.
The commandLink tag takes an actionListener attribute for instance. From
the documentation: "actionListener: String. MethodBinding representing
an action listener method that will be notified when this component is
activated by the user. The expression must evaluate to a public method
that takes an ActionEvent parameters, with a return type of void."

The nxd:documentLink tag should accept the same attribute (but I admit I
never tested it) so you could write:

<nxd:documentLink title="#{currentDocument.dublincore.title}" document="#{document}" actionListener="#{myBean.countDocumentClick}" />

If you'd like to count when an user clicks on an attached file, in theory you could write:

<nxd:outputFile value="#{currentDocument.file.content}" actionListener="#{myBean.countFileClick}" />

But this is not implemented, so you can add a feature request in jira or try to code it :) You can have a look at the UIOutpoutFile component : a command link component is created on the fly, copying the outout file attributes / bindings to the command link component would be the solution.

Regards,


/*
 * Copyright 2004 The Apache Software Foundation.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * 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.nuxeo.ecm.platform.ui.web.component;

import java.io.IOException;

import javax.faces.component.UICommand;
import javax.faces.component.UIComponent;
import javax.faces.component.UIOutput;
import javax.faces.component.html.HtmlCommandLink;
import javax.faces.context.FacesContext;
import javax.faces.context.ResponseWriter;
import javax.faces.el.MethodBinding;
import javax.faces.el.ValueBinding;

import org.nuxeo.ecm.core.api.Blob;
import org.nuxeo.ecm.platform.mimetype.NXMimeType;
import org.nuxeo.ecm.platform.mimetype.interfaces.MimetypeEntry;
import org.nuxeo.ecm.platform.mimetype.service.MimetypeRegistryService;
import org.nuxeo.ecm.platform.ui.web.binding.DownloadMethodBinding;
import org.nuxeo.ecm.platform.ui.web.util.ComponentUtils;

/**
 * UIOutput file
 *
 * Attribute named value is the file to be displayed. Its sumitted value as well
 * as filename are handled by sub components in facets. Rendering is handled
 * here.
 *
 * If convertction and editOnlineAction method bindings are set, corresponding
 * links are rendered. The editOnlineActionRendered is used to filter action
 * visibility.
 *
 * XXX AT: sub component creation is a hack, need to fix it
 *
 * @author <a href="mailto:[EMAIL PROTECTED]">Anahide Tchertchian</a>
 */
public class UIOutputFile extends UIOutput {

    public static final String COMPONENT_TYPE = "org.nuxeo.ecm.UIOutputFile";

    public static final String COMPONENT_FAMILY = "javax.faces.Output";

    private static final String DOWNLOAD_FACET_NAME = "download";

    private static final String CONVERT_PDF_FACET_NAME = "convertToPdf";

    private static final String EDITONLINE_FACET_NAME = "editOnline";

    private String filename;

    private MethodBinding convertAction;

    private MethodBinding editOnlineAction;

    // to perform test on rights or service availability
    private Boolean editOnlineActionRendered;

    private String separator = " | ";

    // XXX AT: maybe add action listeners

    public UIOutputFile() {
        ComponentUtils.initiateSubComponent(this, DOWNLOAD_FACET_NAME,
                new HtmlCommandLink());
        ComponentUtils.initiateSubComponent(this, CONVERT_PDF_FACET_NAME,
                new HtmlCommandLink());
        ComponentUtils.initiateSubComponent(this, EDITONLINE_FACET_NAME,
                new HtmlCommandLink());
    }

    // component will render itself
    @Override
    public String getRendererType() {
        return null;
    }

    // getters and setters

    public String getFilename() {
        if (filename != null) {
            return filename;
        }
        ValueBinding vb = getValueBinding("filename");
        String v = vb != null ? (String) vb.getValue(getFacesContext()) : null;
        return v;
    }

    public void setFilename(String filename) {
        this.filename = filename;
    }

    public MethodBinding getConvertAction() {
        return convertAction;
    }

    public void setConvertAction(MethodBinding convertToPdfAction) {
        this.convertAction = convertToPdfAction;
    }

    public MethodBinding getEditOnlineAction() {
        return editOnlineAction;
    }

    public void setEditOnlineAction(MethodBinding editOnlineAction) {
        this.editOnlineAction = editOnlineAction;
    }

    public Boolean getEditOnlineActionRendered() {
        if (editOnlineActionRendered != null) {
            return editOnlineActionRendered;
        }
        ValueBinding vb = getValueBinding("editOnlineActionRendered");
        Boolean v = vb != null ? (Boolean) vb.getValue(getFacesContext())
                : false;
        return v;
    }

    public void setEditOnlineActionRendered(Boolean editOnlineActionRendered) {
        this.editOnlineActionRendered = editOnlineActionRendered;
    }

    public String getSeparator() {
        if (separator != null) {
            return separator;
        }
        ValueBinding vb = getValueBinding("separator");
        String v = vb != null ? (String) vb.getValue(getFacesContext()) : null;
        return v;
    }

    public void setSeparator(String actionsSeparator) {
        this.separator = actionsSeparator;
    }

    // rendering methods

    protected String getDownloadLinkValue(FacesContext context, Blob blob,
            String filename) {
        String linkValue = (String) ComponentUtils.getAttributeValue(this,
                "downloadLabel", null);
        if (linkValue == null && filename == null) {
            linkValue = ComponentUtils.translate(context,
                    "label.outputFile.download");
        } else {
            linkValue = filename;
        }
        // XXX AT: LazyBlob always returns 0
        // if (blob != null) {
        // Long size = blob.getLength();
        // if (size != null) {
        // DecimalFormatSymbols dfs = new DecimalFormatSymbols();
        // dfs.setDecimalSeparator('.');
        // DecimalFormat df = new DecimalFormat("########.0", dfs);
        // String stringSize = df.format(size / 1024.);
        // linkValue += " (" + stringSize + "Ko)";
        // }
        // }
        return linkValue;
    }

    // encode component with its sub components
    @Override
    public void encodeBegin(FacesContext context) throws IOException {
        Object value = getValue();
        if (value != null && value instanceof Blob) {
            Boolean previousSet = false;
            Blob blob = (Blob) value;
            String filenameSet = getFilename();
            UIComponent downloadFacet = getFacet(DOWNLOAD_FACET_NAME);
            if (downloadFacet != null) {
                UICommand downloadComp = (UICommand) downloadFacet;
                ComponentUtils.hookSubComponent(context, this, downloadComp);
                downloadComp.setAction(new DownloadMethodBinding(blob,
                        filenameSet));
                downloadComp.setValue(getDownloadLinkValue(context, blob,
                        filenameSet));
                downloadComp.setImmediate(true);
                // encode icon
                encodeFileIcon(context, blob);
                // encode component
                ComponentUtils.encodeComponent(context, downloadComp);
                previousSet = true;
            }
        }
    }

    public void encodeFileIcon(FacesContext context, Blob blob)
            throws IOException {
        String iconPath = "";
        try {
            // XXX hack: should not access the service directly
            MimetypeRegistryService mimeService = NXMimeType
                    .getMimetypeRegistryService();
            MimetypeEntry mimeEntry = mimeService
                    .getMimetypeEntryByMimeType(blob.getMimeType());
            if (mimeEntry != null) {
                if (mimeEntry.getIconURL() != null) {
                    iconPath = mimeEntry.getIconURL().getPath();
                } else if (mimeEntry.getIconPath() != null) {
                    // FIXME: above Context should find it
                    iconPath = "/icons/" + mimeEntry.getIconPath();
                }
            }
        } catch (Exception err) {
        }
        if (iconPath != null && iconPath.length() > 0) {
            ResponseWriter writer = context.getResponseWriter();
            writer.startElement("img", this);
            String src = context.getApplication().getViewHandler()
                    .getResourceURL(context, iconPath);
            writer.writeURIAttribute("src", context.getExternalContext()
                    .encodeResourceURL(src), null);
            writer.writeAttribute("alt", blob.getMimeType(), null);
            writer.endElement("img");
            writer.write("&nbsp;");
            writer.flush();
        }
    }

    private void encodeSeparator(FacesContext context) throws IOException {
        ResponseWriter writer = context.getResponseWriter();
        writer.write(getSeparator());
        writer.flush();
    }

    // state holder

    @Override
    public Object saveState(FacesContext context) {
        Object values[] = new Object[5];
        values[0] = super.saveState(context);
        values[1] = filename;
        values[2] = convertAction;
        values[3] = editOnlineAction;
        values[4] = editOnlineActionRendered;
        return values;
    }

    @Override
    public void restoreState(FacesContext context, Object state) {
        Object values[] = (Object[]) state;
        super.restoreState(context, values[0]);
        filename = (String) values[1];
        convertAction = (MethodBinding) values[2];
        editOnlineAction = (MethodBinding) values[3];
        editOnlineActionRendered = (Boolean) values[4];
    }

}
_______________________________________________
ECM mailing list
[email protected]
http://lists.nuxeo.com/mailman/listinfo/ecm

Reply via email to