From: <pb...@fe...> - 2012-12-16 09:20:32
|
Author: pboy Date: 2012-12-16 09:20:21 +0000 (Sun, 16 Dec 2012) New Revision: 2372 Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageComponent.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageLibraryComponent.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageSelectPage.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageUploadComponent.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImagesPane.java Modified: trunk/ccm-cms/src/com/arsdigita/cms/ui/ContentSectionPage.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageBrowser.java trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageChooser.java Log: New image tab in content center, external page in Xinha plugin. Modified: trunk/ccm-cms/src/com/arsdigita/cms/ui/ContentSectionPage.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ContentSectionPage.java 2012-12-16 09:14:07 UTC (rev 2371) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ContentSectionPage.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -133,6 +133,7 @@ private FolderAdminPane m_folderPane; private BrowsePane m_browsePane; private LayoutPanel m_searchPane; + private ImagesPane m_imagesPane; private RoleAdminPane m_rolePane; private WorkflowAdminPane m_workflowPane; private LifecycleAdminPane m_lifecyclePane; @@ -165,6 +166,7 @@ m_folderPane = getFolderAdminPane(); m_browsePane = getBrowsePane(); m_searchPane = getSearchPane(); + m_imagesPane = getImagesPane(); m_rolePane = getRoleAdminPane(); m_workflowPane = getWorkflowAdminPane(); m_lifecyclePane = getLifecycleAdminPane(); @@ -247,6 +249,13 @@ return m_searchPane; } + protected ImagesPane getImagesPane() { + if(m_imagesPane == null) { + m_imagesPane = new ImagesPane(); + } + return m_imagesPane; + } + protected RoleAdminPane getRoleAdminPane() { if (m_rolePane == null) { m_rolePane = new RoleAdminPane(); @@ -366,6 +375,7 @@ //tab(pane, "cms.ui.folders", getFolderAdminPane()); tab(pane, "cms.ui.browse", getBrowsePane()); tab(pane, "cms.ui.search", getSearchPane()); + tab(pane, "cms.ui.images", getImagesPane()); tab(pane, "cms.ui.roles", getRoleAdminPane()); tab(pane, "cms.ui.workflows", getWorkflowAdminPane()); tab(pane, "cms.ui.lifecycles", getLifecycleAdminPane()); @@ -404,6 +414,8 @@ if (pane == m_searchPane) { m_searchPane.reset(state); + } else if (pane == m_imagesPane) { + m_imagesPane.reset(state); } else if (pane == m_folderPane) { m_folderPane.reset(state); } else if (pane == m_browsePane) { Modified: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageBrowser.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageBrowser.java 2012-12-16 09:14:07 UTC (rev 2371) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageBrowser.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -34,6 +34,7 @@ import com.arsdigita.cms.ImageAsset; import com.arsdigita.cms.SecurityManager; import com.arsdigita.cms.Service; +import com.arsdigita.cms.ui.ImageComponent; import com.arsdigita.domain.DataObjectNotFoundException; import com.arsdigita.domain.DomainObjectFactory; import com.arsdigita.mimetypes.MimeType; @@ -46,8 +47,8 @@ import org.apache.log4j.Logger; /** - * Displays a list of images in a Table. The table will look - * something like this: + * Displays a list of images in a Table. The table will look something like + * this: * * <blockquote><pre><code> * +-----------+-------+-------+------+----------+ @@ -73,7 +74,8 @@ private static final int TYPE = 3; private static final int LINK = 4; private static final int DELETE = 5; - private static final int NUM_COLUMNS = 6; + private int m_numColumns = -1; + private int m_mode; private Dimension m_thumbSize; private static final Logger s_log = Logger.getLogger(ImageBrowser.class); @@ -84,18 +86,24 @@ * component with its {@link ImageBrowserModel} during each request */ public ImageBrowser(ImageBrowserModelBuilder b) { + + this(b, ImageComponent.ATTACH_IMAGE); + } + + public ImageBrowser(ImageBrowserModelBuilder b, int mode) { super(new BuilderAdapter(b), HEADERS); + m_mode = mode; setThumbnailSize(CMS.getConfig().getImageBrowserThumbnailMaxWidth(), - CMS.getConfig().getImageBrowserThumbnailMaxHeight()); + CMS.getConfig().getImageBrowserThumbnailMaxHeight()); m_builder = b; getHeader().setDefaultRenderer(new DefaultTableCellRenderer(false)); - getColumn(0).setCellRenderer(new ThumbnailCellRenderer()); - getColumn(1).setCellRenderer(new DefaultTableCellRenderer(false)); - getColumn(2).setCellRenderer(new DefaultTableCellRenderer(false)); - getColumn(3).setCellRenderer(new DefaultTableCellRenderer(false)); - getColumn(4).setCellRenderer(new DefaultTableCellRenderer(true)); - getColumn(5).setCellRenderer(new DeleteCellRenderer()); + addColumn(new ThumbnailCellRenderer()); + addColumn(new DefaultTableCellRenderer(false)); + addColumn(new DefaultTableCellRenderer(false)); + addColumn(new DefaultTableCellRenderer(false)); + addColumn(new SelectCellRenderer()); + addColumn(new DeleteCellRenderer()); setCellPadding("4"); setBorder("1"); @@ -103,6 +111,14 @@ setClassAttr("imageBrowser"); } + private void addColumn(TableCellRenderer renderer) { + getColumn(++m_numColumns).setCellRenderer(renderer); + } + + public int getNumColumns() { + return m_numColumns; + } + /** * @return the size, in pixels, of the thumbnail images */ @@ -112,7 +128,8 @@ /** * Set the thumbnail size - * @param size the size, in pixels, of the thumbnail images + * + * @param size the size, in pixels, of the thumbnail images */ public final void setThumbnailSize(int width, int height) { m_thumbSize = new Dimension(width, height); @@ -127,17 +144,15 @@ /** * @param state The current page state - * @return the {@link ImageBrowserModel} used in the current - * request + * @return the {@link ImageBrowserModel} used in the current request */ public ImageBrowserModel getImageBrowserModel(PageState state) { return ((ImageModelAdapter) getTableModel(state)).getModel(); } /** - * An action listener that only gets fired when the "select" - * link is clicked. Child classes should override the - * linkClicked method. + * An action listener that only gets fired when the "select" link is + * clicked. Child classes should override the linkClicked method. */ public static abstract class LinkActionListener extends TableActionAdapter { @@ -192,6 +207,26 @@ } } + // Renders the select link if the mode needs one + private class SelectCellRenderer extends DefaultTableCellRenderer { + + public SelectCellRenderer() { + super(true); + } + + @Override + public Component getComponent(Table table, PageState state, Object value, + boolean isSelected, Object key, + int row, int column) { + + if (m_mode == ImageComponent.SELECT_IMAGE) { + return super.getComponent(table, state, value, isSelected, key, row, column); + } + + return new Label(""); + } + } + // Renders the delete link if the user has permission to delete // the asset and it's not used in an article. private class DeleteCellRenderer extends DefaultTableCellRenderer { @@ -204,27 +239,32 @@ public Component getComponent(Table table, PageState state, Object value, boolean isSelected, Object key, int row, int column) { - boolean canDelete = false; - // SecurityManager sm = Utilities.getSecurityManager(state); - SecurityManager sm = CMS.getSecurityManager(state); - if (sm.canAccess(state.getRequest(), SecurityManager.DELETE_IMAGES)) { - try { - ImageAsset asset = (ImageAsset) DomainObjectFactory.newInstance(new OID(ImageAsset.BASE_DATA_OBJECT_TYPE, (BigDecimal) key)); + + // Only show delete link in admin mode + if (m_mode == ImageComponent.ADMIN_IMAGES) { + + boolean canDelete = false; + // SecurityManager sm = Utilities.getSecurityManager(state); + SecurityManager sm = CMS.getSecurityManager(state); + if (sm.canAccess(state.getRequest(), SecurityManager.DELETE_IMAGES)) { + try { + ImageAsset asset = (ImageAsset) DomainObjectFactory.newInstance(new OID(ImageAsset.BASE_DATA_OBJECT_TYPE, (BigDecimal) key)); //XXX Find a new way to figure out, if this image is used by any CI so we can decide if it can be deleted // if (!GenericArticleImageAssociation.imageHasAssociation(asset)) { // canDelete = true; // } - } catch (DataObjectNotFoundException e) { - // can't find asset, can't delete it + } catch (DataObjectNotFoundException e) { + // can't find asset, can't delete it + } + } - + + // can delete image because it's not in use + if (canDelete) { + return super.getComponent(table, state, value, isSelected, key, row, column); + } } - - if (canDelete) { - return super.getComponent(table, state, value, isSelected, key, row, column); - } else { - return new Label(""); - } + return new Label(""); } } @@ -262,7 +302,8 @@ @Override public int getColumnCount() { - return ImageBrowser.NUM_COLUMNS; + return ((ImageBrowser)m_model).getNumColumns(); + // return ImageBrowser.s_numColumns; } @Override @@ -311,7 +352,7 @@ return m.getMimeType(); case ImageBrowser.LINK: - return "select"; + return "select"; case ImageBrowser.DELETE: return "delete"; Modified: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageChooser.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageChooser.java 2012-12-16 09:14:07 UTC (rev 2371) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageChooser.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -66,32 +66,47 @@ * * @param context the context for the retrieved items. Should be * {@link ContentItem#DRAFT} or {@link ContentItem#LIVE} + * @param mode the display mode for the ImageBrowser */ - public ImageChooser(String context) { + public ImageChooser(String context, int mode) { super(BoxPanel.VERTICAL); m_keyword = new StringParameter(KEYWORD); m_sel = new ParameterSingleSelectionModel(m_keyword); m_form = new ImageKeywordForm(m_sel); - DefaultImageBrowserModelBuilder modelBuilder = - new DefaultImageBrowserModelBuilder(m_sel, context); - m_browser = new ImageBrowser(modelBuilder); - modelBuilder.setImageBrowser(m_browser); + DefaultImageBrowserModelBuilder modelBuilder = + new DefaultImageBrowserModelBuilder(m_sel, context); + m_browser = new ImageBrowser(modelBuilder, mode); + modelBuilder.setImageBrowser(m_browser); - m_paginator = new Paginator - (modelBuilder, - LIST_SIZE); + m_paginator = new Paginator + (modelBuilder, + LIST_SIZE); super.add(m_form); - super.add(m_paginator); + super.add(m_paginator); super.add(m_browser); } /** * Construct a new ImageChooser + * + * @param context the context for the retrieved items. Should be + * {@link ContentItem#DRAFT} or {@link ContentItem#LIVE} */ + public ImageChooser(String context) { + this(context, ImageComponent.ATTACH_IMAGE); + } + + public ImageChooser(int mode) { + this(ContentItem.DRAFT, mode); + } + + /** + * Construct a new ImageChooser + */ public ImageChooser() { - this(ContentItem.DRAFT); + this(ContentItem.DRAFT, ImageComponent.ATTACH_IMAGE); } /** Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageComponent.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageComponent.java (rev 0) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageComponent.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -0,0 +1,41 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.arsdigita.cms.ui; + +import com.arsdigita.bebop.Form; +import com.arsdigita.bebop.FormProcessException; +import com.arsdigita.bebop.SaveCancelSection; +import com.arsdigita.bebop.event.FormSectionEvent; +import com.arsdigita.cms.ReusableImageAsset; + +/** + * + * @author Sören Bernstein (quasimodo) <sbe...@ze...> + */ +public interface ImageComponent { + + public static final int DISPLAY_ONLY = 0; + public static final int SELECT_IMAGE = 1; + public static final int ATTACH_IMAGE = 2; + public static final int ADMIN_IMAGES = 3; + + public static final String UPLOAD = "upload"; + public static final String LIBRARY = "library"; + + ReusableImageAsset getImage(FormSectionEvent event) throws FormProcessException; + + String getCaption(FormSectionEvent event); + + String getDescription(FormSectionEvent event); + + String getTitle(FormSectionEvent event); + + String getUseContext(FormSectionEvent event); + + SaveCancelSection getSaveCancelSection(); + + Form getForm(); + +} Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageLibraryComponent.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageLibraryComponent.java (rev 0) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageLibraryComponent.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -0,0 +1,161 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.arsdigita.cms.ui; + +import com.arsdigita.bebop.ActionLink; +import com.arsdigita.bebop.ColumnPanel; +import com.arsdigita.bebop.Form; +import com.arsdigita.bebop.Label; +import com.arsdigita.bebop.Page; +import com.arsdigita.bebop.PageState; +import com.arsdigita.bebop.SaveCancelSection; +import com.arsdigita.bebop.SimpleContainer; +import com.arsdigita.bebop.event.ActionEvent; +import com.arsdigita.bebop.event.ActionListener; +import com.arsdigita.bebop.event.FormSectionEvent; +import com.arsdigita.bebop.form.TextField; +import com.arsdigita.bebop.parameters.BigDecimalParameter; +import com.arsdigita.bebop.parameters.NotNullValidationListener; +import com.arsdigita.cms.ContentItem; +import com.arsdigita.cms.ItemSelectionModel; +import com.arsdigita.cms.ReusableImageAsset; +import com.arsdigita.domain.DataObjectNotFoundException; +import java.math.BigDecimal; + +/** + * + * @author Sören Bernstein (quasimodo) <sbe...@ze...> + */ +public class ImageLibraryComponent extends SimpleContainer implements ImageComponent { + + private final ImageChooser m_chooser; + private final ItemSelectionModel m_imageModel; + private final BigDecimalParameter m_imageID; + private final Form m_form; + private final TextField m_caption; + private final TextField m_description; + private final TextField m_title; + private final TextField m_useContext; + private final SaveCancelSection m_saveCancel; + private int m_mode; + + public ImageLibraryComponent() { + this(ImageComponent.SELECT_IMAGE); + } + + public ImageLibraryComponent(int mode) { + m_mode = mode; + m_imageID = new BigDecimalParameter("imageID"); + m_imageModel = new ItemSelectionModel(m_imageID); + m_chooser = new ImageChooser(ContentItem.DRAFT, m_mode); + m_chooser.addImageActionListener(new ImageBrowser.LinkActionListener() { + + public void deleteClicked(PageState ps, BigDecimal imageID) { + ImagesPane.s_log.debug("Clicked delete"); + ReusableImageAsset image = new ReusableImageAsset(imageID); + image.delete(); + } + + public void linkClicked(PageState ps, BigDecimal imageID) { + ImagesPane.s_log.debug("Clicked select"); + try { + ReusableImageAsset image = new ReusableImageAsset(imageID); + m_imageModel.setSelectedObject(ps, image); + } catch (DataObjectNotFoundException ex) { + ImagesPane.s_log.error("Selected non-existant image: " + imageID, ex); + } + } + }); + add(m_chooser); + + // Form for additional fields and submit + m_form = new Form("imageLibraryComponent", new ColumnPanel(2)); + add(m_form); + + // Initialize all wisgets + m_caption = new TextField("caption"); + m_description = new TextField("description"); + m_title = new TextField("title"); + m_useContext = new TextField("useContext"); + + // Show additional fields only in default mode a.k.a. ATTACH_IMAGE like + // in image-step + if (m_mode == ImageComponent.ATTACH_IMAGE) { + m_form.add(new Label("Caption")); + m_caption.addValidationListener(new NotNullValidationListener()); + m_caption.setSize(40); + m_form.add(m_caption); + m_description.addValidationListener(new NotNullValidationListener()); + m_description.setSize(40); + m_title.addValidationListener(new NotNullValidationListener()); + m_title.setSize(40); + // Only show the title and description fields where these have + // been explicitly requested. + /* + * if + * (ItemImageAttachment.getConfig().getIsImageStepDescriptionAndTitleShown()) + * { m_form.add(new Label("Description")); + * m_form.add(m_description); m_form.add(new Label("Title")); + * m_form.add(m_title); } + */ + m_form.add(new Label("Use Context")); + m_useContext.setSize(40); + m_form.add(m_useContext); + } + + // save and cancel buttons + m_saveCancel = new SaveCancelSection(); + m_form.add(m_saveCancel); + + } + + public ReusableImageAsset getImage(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (ReusableImageAsset) m_imageModel.getSelectedItem(ps); + } + + @Override + public void register(Page p) { + super.register(p); + p.addComponentStateParam(this, m_imageID); + } + + public String getCaption(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_caption.getValue(ps); + } + + public String getDescription(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_description.getValue(ps); + } + + public String getTitle(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_title.getValue(ps); + } + + public String getUseContext(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_useContext.getValue(ps); + } + + public Form getForm() { + return m_form; + } + + public SaveCancelSection getSaveCancelSection() { + return m_saveCancel; + } + + public void addUploadLink(ActionListener actionListener) { + // Add action link to image upload component + if (m_mode != ImageComponent.DISPLAY_ONLY) { + ActionLink upload = new ActionLink("Upload new image"); + upload.addActionListener(actionListener); + add(upload, ColumnPanel.FULL_WIDTH); + } + } +} Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageSelectPage.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageSelectPage.java (rev 0) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageSelectPage.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -0,0 +1,104 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.arsdigita.cms.ui; + +import com.arsdigita.bebop.Component; +import com.arsdigita.bebop.SimpleContainer; +import com.arsdigita.bebop.TabbedPane; +import com.arsdigita.bebop.parameters.BigDecimalParameter; +import com.arsdigita.cms.CMSConfig; +import com.arsdigita.cms.dispatcher.CMSPage; +import com.arsdigita.cms.util.GlobalizationUtil; + +/** + * + * @author Sören Bernstein (quasimodo) <sbe...@ze...> + */ +public class ImageSelectPage extends CMSPage { + + private final static String XSL_CLASS = "CMS Admin"; + private TabbedPane m_tabbedPane; + private ImageLibraryComponent m_imageLibrary; + private ImageUploadComponent m_imageUpload; + private BigDecimalParameter m_sectionId; + private static final CMSConfig s_conf = CMSConfig.getInstance(); + private static final boolean LIMIT_TO_CONTENT_SECTION = false; + public static final String CONTENT_SECTION = "section_id"; + + public ImageSelectPage() { + super(GlobalizationUtil.globalize("cms.ui.item_search.page_title").localize().toString(), new SimpleContainer()); + + setClassAttr("cms-admin"); + + m_sectionId = new BigDecimalParameter(CONTENT_SECTION); + addGlobalStateParam(m_sectionId); + + m_tabbedPane = createTabbedPane(); + m_tabbedPane.setIdAttr("page-body"); + add(m_tabbedPane); + + } + + protected ImageLibraryComponent getImageLibraryPane() { + if (m_imageLibrary == null) { + m_imageLibrary = new ImageLibraryComponent(ImageComponent.SELECT_IMAGE); +// library.getForm().addInitListener(this); +// library.getForm().addProcessListener(this); + } + return m_imageLibrary; + } + + protected ImageUploadComponent getImageUploadPane() { + + if (m_imageUpload == null) { + m_imageUpload = new ImageUploadComponent(ImageComponent.SELECT_IMAGE); +// upload.getForm().addInitListener(this); +// upload.getForm().addProcessListener(this); + } + return m_imageUpload; + } + + protected TabbedPane createTabbedPane() { + TabbedPane pane = new TabbedPane(); + pane.setClassAttr(XSL_CLASS); + + addToPane(pane, "library", getImageLibraryPane()); + addToPane(pane, "upload", getImageUploadPane()); + pane.setDefaultPane(m_imageLibrary); + + return pane; + } + + /** + * Adds the specified component, with the specified tab name, to the tabbed + * pane only if it is not null. + * + * @param pane The pane to which to add the tab + * @param tabName The name of the tab if it's added + * @param comp The component to add to the pane + */ + protected void addToPane(TabbedPane pane, String tabName, Component comp) { + if (comp != null) { + pane.addTab(GlobalizationUtil.globalize("cms.ui.item_search." + tabName).localize().toString(), comp); + } + } + + /* Listeners */ + + /** + * InitListener + * + * this init listener selects the object with the submitted oid + */ +// private init() { +// +// } + + /** + * ProcessListener + * + * this process listener + */ +} Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageUploadComponent.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageUploadComponent.java (rev 0) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImageUploadComponent.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -0,0 +1,144 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.arsdigita.cms.ui; + +import com.arsdigita.bebop.ColumnPanel; +import com.arsdigita.bebop.Form; +import com.arsdigita.bebop.FormProcessException; +import com.arsdigita.bebop.Label; +import com.arsdigita.bebop.PageState; +import com.arsdigita.bebop.SaveCancelSection; +import com.arsdigita.bebop.event.FormSectionEvent; +import com.arsdigita.bebop.form.TextArea; +import com.arsdigita.bebop.form.TextField; +import com.arsdigita.bebop.parameters.NotNullValidationListener; +import com.arsdigita.bebop.parameters.StringLengthValidationListener; +import com.arsdigita.cms.ImageAsset; +import com.arsdigita.cms.ReusableImageAsset; +import java.io.File; +import java.io.IOException; + +/** + * + * @author Sören Bernstein (quasimodo) <sbe...@ze...> + */ +public class ImageUploadComponent extends Form implements ImageComponent { + + private final FileUploadSection m_imageFile; + private final TextField m_caption; + private final TextField m_title; + private final TextArea m_description; + private final TextField m_useContext; + private final SaveCancelSection m_saveCancel; + private int m_mode; + + public ImageUploadComponent() { + this(ImageComponent.ATTACH_IMAGE); + } + + public ImageUploadComponent(int mode) { + super("imageUploadComponent", new ColumnPanel(2)); + m_mode = mode; + setEncType("multipart/form-data"); + // Ignoring deprecated constructor. + m_imageFile = new FileUploadSection("Image Type", "image", ImageAsset.MIME_JPEG); + m_imageFile.getFileUploadWidget().addValidationListener(new NotNullValidationListener()); + add(m_imageFile, ColumnPanel.FULL_WIDTH); + + // Initialize all widgets + m_caption = new TextField("caption"); + m_title = new TextField("title"); + m_description = new TextArea("description"); + m_useContext = new TextField("useContext"); + + // add widget only if we are in attach mode + if (m_mode == ImageComponent.ATTACH_IMAGE) { + add(new Label("Caption")); + m_caption.addValidationListener(new NotNullValidationListener()); + m_caption.addValidationListener(new StringLengthValidationListener(40)); + m_caption.setSize(40); + add(m_caption); + + // We only show the title and description fields in the case where + // getIsImageStepDescriptionAndTitleShown is false. + +// if (ItemImageAttachment.getConfig().getIsImageStepDescriptionAndTitleShown()) { +// add(new Label("Title")); +// m_title.addValidationListener(new NotNullValidationListener()); +// m_title.setSize(40); +// m_title.addValidationListener(new StringLengthValidationListener(40)); +// add(m_title); +// +// add(new Label("Description")); +// m_description.addValidationListener(new NotNullValidationListener()); +// m_description.addValidationListener(new StringLengthValidationListener(600)); +// m_description.setCols(30); +// m_description.setRows(5); +// add(m_description); +// +// } + + add(new Label("Use Context")); + m_useContext.setSize(40); + add(m_useContext); + } + m_saveCancel = new SaveCancelSection(); + add(m_saveCancel); + + /* + * Removed by Quasimodo: Changed editing workflow, so that library comes + * first Also, library mode has now a link to upload images which will + * link to this form. Consequently, this link will create a loop, which + * isn't fatal but confusing. ActionLink library = new ActionLink( + * "Select an existing image" ); library.addActionListener( new + * ActionListener() { public void actionPerformed( ActionEvent ev ) { + * setImageComponent( ev.getPageState(), LIBRARY ); } } ); add( library, + * ColumnPanel.FULL_WIDTH ); + */ + } + + public SaveCancelSection getSaveCancelSection() { + return m_saveCancel; + } + + public ReusableImageAsset getImage(FormSectionEvent event) throws FormProcessException { + PageState ps = event.getPageState(); + String filename = (String) m_imageFile.getFileName(event); + File imageFile = m_imageFile.getFile(event); + try { + ReusableImageAsset image = new ReusableImageAsset(); + image.loadFromFile(filename, imageFile, ImageAsset.MIME_JPEG); + image.setDescription((String) m_caption.getValue(ps)); + return image; + } catch (IOException ex) { + ImagesPane.s_log.error("Error loading image from file", ex); + throw new FormProcessException(ex.getMessage()); + } + } + + public String getCaption(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_caption.getValue(ps); + } + + public String getDescription(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_description.getValue(ps); + } + + public String getTitle(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_title.getValue(ps); + } + + public String getUseContext(FormSectionEvent event) { + PageState ps = event.getPageState(); + return (String) m_useContext.getValue(ps); + } + + public Form getForm() { + return this; + } +} Added: trunk/ccm-cms/src/com/arsdigita/cms/ui/ImagesPane.java =================================================================== --- trunk/ccm-cms/src/com/arsdigita/cms/ui/ImagesPane.java (rev 0) +++ trunk/ccm-cms/src/com/arsdigita/cms/ui/ImagesPane.java 2012-12-16 09:20:21 UTC (rev 2372) @@ -0,0 +1,173 @@ +/* + * To change this template, choose Tools | Templates + * and open the template in the editor. + */ +package com.arsdigita.cms.ui; + +import com.arsdigita.bebop.Component; +import com.arsdigita.bebop.FormProcessException; +import com.arsdigita.bebop.Label; +import com.arsdigita.bebop.MapComponentSelectionModel; +import com.arsdigita.bebop.Page; +import com.arsdigita.bebop.PageState; +import com.arsdigita.bebop.ParameterSingleSelectionModel; +import com.arsdigita.bebop.Resettable; +import com.arsdigita.bebop.SegmentedPanel; +import com.arsdigita.bebop.SimpleComponent; +import com.arsdigita.bebop.event.ActionEvent; +import com.arsdigita.bebop.event.ActionListener; +import com.arsdigita.bebop.event.FormInitListener; +import com.arsdigita.bebop.event.FormProcessListener; +import com.arsdigita.bebop.event.FormSectionEvent; +import com.arsdigita.bebop.event.FormSubmissionListener; +import com.arsdigita.bebop.parameters.StringParameter; +import com.arsdigita.cms.ContentItem; +import com.arsdigita.cms.ReusableImageAsset; +import com.arsdigita.cms.util.GlobalizationUtil; +import com.arsdigita.toolbox.ui.LayoutPanel; +import java.util.HashMap; +import java.util.Iterator; +import java.util.Map; +import org.apache.log4j.Logger; + +/** + * A LayoutPanel to insert into ContentSectionPage or ImageSelectPage + * + * @author Sören Bernstein (quasimodo) <sbe...@ze...> + */ +public class ImagesPane extends LayoutPanel implements Resettable, FormProcessListener, FormInitListener { + + public static final Logger s_log = Logger.getLogger(BrowsePane.class); + //private ImageChooser imageChooser; + private final StringParameter m_imageComponentKey; + private final MapComponentSelectionModel m_imageComponent; + + public ImagesPane() { + // Left column is empty, this is only to provide the same layout for all + // tabs in ContentSectionPage + setLeft(new SimpleComponent()); + + SegmentedPanel body = new SegmentedPanel(); + setBody(body); + + m_imageComponentKey = new StringParameter("imageComponent"); + + ParameterSingleSelectionModel componentModel = new ParameterSingleSelectionModel(m_imageComponentKey); + m_imageComponent = new MapComponentSelectionModel(componentModel, new HashMap()); + + Map selectors = m_imageComponent.getComponentsMap(); + + ImageUploadComponent upload = new ImageUploadComponent(ImageComponent.ADMIN_IMAGES); + upload.getForm().addInitListener(this); + upload.getForm().addProcessListener(this); + selectors.put(ImageComponent.UPLOAD, upload); + body.addSegment( + new Label(GlobalizationUtil.globalize("cms.ui.image_upload")), + upload); + + ImageLibraryComponent library = new ImageLibraryComponent(ImageComponent.ADMIN_IMAGES); + library.getForm().addInitListener(this); + library.getForm().addProcessListener(this); + library.addUploadLink(new ActionListener() { + + public void actionPerformed(ActionEvent ev) { + setImageComponent(ev.getPageState(), ImageComponent.UPLOAD); + } + }); + selectors.put(ImageComponent.LIBRARY, library); + body.addSegment( + new Label(GlobalizationUtil.globalize("cms.ui.image_browser")), + library); + + } + + @Override + public final void register(Page page) { + super.register(page); + } + + @Override + public final void reset(PageState state) { + super.reset(state); + } + + /* + * // Private classes and methods private final class ProcessListener + * implements FormProcessListener { + */ + public void process(FormSectionEvent event) throws FormProcessException { + PageState ps = event.getPageState(); +// ImageComponent component = getImageComponent(ps); +// +// if (!component.getSaveCancelSection().getSaveButton().isSelected(ps)) { +// return; +// } +// +// ContentItem item = m_imageStep.getItem(ps); +// if (null == item) { +// s_log.error("No item selected in ImageStepEdit", new RuntimeException()); +// return; +// } +// +// ReusableImageAsset image = component.getImage(event); +// +// ItemImageAttachment attachment = m_imageStep.getAttachment(ps); +// if (null +// == attachment) { +// attachment = new ItemImageAttachment(item, image); +// } +// attachment.setCaption(component.getCaption(event)); +// +// // We only set the description and title based on the UI in +// // the case where getIsImageStepDescriptionAndTitleShown is true. +// // Otherwise, we leave this as the default value. This means +// // existing values are not overwritten if the image is edited when +// // isImageStepDescriptionAndTitleShown is false. +// if (ItemImageAttachment.getConfig().getIsImageStepDescriptionAndTitleShown()) { +// attachment.setDescription(component.getDescription(event)); +// attachment.setTitle(component.getTitle(event)); +// } +// attachment.setUseContext(component.getUseContext(event)); + } + + private final class SubmissionListener implements FormSubmissionListener { + + public final void submitted(final FormSectionEvent e) { + final PageState s = e.getPageState(); + + } + } + + private void setImageComponent(PageState ps, final String activeKey) { + m_imageComponent.setSelectedKey(ps, activeKey); + + if (s_log.isDebugEnabled()) { + s_log.debug("Selected component: " + activeKey); + } + + Map componentsMap = m_imageComponent.getComponentsMap(); + Iterator i = componentsMap.keySet().iterator(); + while (i.hasNext()) { + Object key = i.next(); + Component component = (Component) componentsMap.get(key); + + boolean isVisible = activeKey.equals(key); + + if (s_log.isDebugEnabled()) { + s_log.debug("Key: " + key + "; Visibility: " + isVisible); + } + + ps.setVisible(component, isVisible); + } + } + + public void init(FormSectionEvent event) + throws FormProcessException { + PageState ps = event.getPageState(); + +// ItemImageAttachment attachment = m_imageStep.getAttachment(ps); +// if (null == attachment) { + // XXX: Do something +// } + } +} |