net.rim.ejde.internal.ui.editors.model.BlackBerryProjectPropertiesPage.java Source code

Java tutorial

Introduction

Here is the source code for net.rim.ejde.internal.ui.editors.model.BlackBerryProjectPropertiesPage.java

Source

/*
* Copyright (c) 2010-2012 Research In Motion Limited. All rights reserved.
*
* This program and the accompanying materials are made available
* under the terms of the Eclipse Public License, Version 1.0,
* which accompanies this distribution and is available at
*
* http://www.eclipse.org/legal/epl-v10.html
*
*/
package net.rim.ejde.internal.ui.editors.model;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.Map;

import net.rim.ejde.internal.core.IConstants;
import net.rim.ejde.internal.model.BasicBlackBerryProperties.Icon;
import net.rim.ejde.internal.model.BasicBlackBerryProperties.PreprocessorTag;
import net.rim.ejde.internal.model.BlackBerryProject;
import net.rim.ejde.internal.util.Messages;

import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.Path;
import org.eclipse.jface.dialogs.IMessageProvider;
import org.eclipse.jface.viewers.StructuredSelection;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.swt.events.FocusEvent;
import org.eclipse.swt.events.FocusListener;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.TableItem;
import org.eclipse.ui.forms.AbstractFormPart;
import org.eclipse.ui.forms.SectionPart;
import org.eclipse.ui.forms.editor.FormEditor;
import org.eclipse.ui.forms.editor.FormPage;

/**
 * This is the base class for all pages within the project application descriptor editor. It provides various helper methods used
 * through out the pages.
 *
 * @author cmalinescu, jkeshavarzi
 *
 */
public abstract class BlackBerryProjectPropertiesPage extends FormPage {
    public static final String CONTROL_TITLE_KEY = "TITLE"; //$NON-NLS-1$
    public static final String TABLE_TEXT_INDEX_KEY = "TEXT_COLUMN"; //$NON-NLS-1$
    public static final String SECTION_PART_KEY = "part"; //$NON-NLS-1$

    private final BlackBerryProject _blackBerryProject;
    private ArrayList<SectionPart> sections = new ArrayList<SectionPart>();

    /**
     * The actions associated with each button event used in the editor
     *
     * @author jkeshavarzi
     *
     */
    public static enum Action {
        ADD, ADD_FROM_PROJECT, ADD_FROM_EXTERNAL, REMOVE, EDIT, SELECT_ALL, SELECT_NONE, BROWSE, MOVE_UP, MOVE_DOWN;

        public String getButtonLabel() {
            switch (this) {
            case ADD:
                return Messages.BlackBerryProjectPropertiesPage_Add_Button_Label;
            case REMOVE:
                return Messages.BlackBerryProjectPropertiesPage_Remove_Button_Label;
            case EDIT:
                return Messages.BlackBerryProjectPropertiesPage_Edit_Button_Label;
            case ADD_FROM_PROJECT:
                return Messages.BlackBerryProjectPropertiesPage_Add_From_Project_Button_Label;
            case ADD_FROM_EXTERNAL:
                return Messages.BlackBerryProjectPropertiesPage_Add_From_External_Button_Label;
            case SELECT_ALL:
                return Messages.BlackBerryProjectPropertiesPage_Select_All_Button_Label;
            case SELECT_NONE:
                return Messages.BlackBerryProjectPropertiesPage_Deselect_All_Button_Label;
            case BROWSE:
                return Messages.BlackBerryProjectPropertiesPage_Browse_Button_Label_Ellipsis;
            case MOVE_UP:
                return Messages.BlackBerryProjectPropertiesPage_MoveUp_Button_Label;
            case MOVE_DOWN:
                return Messages.BlackBerryProjectPropertiesPage_MoveDown_Button_Label;
            default:
                return IConstants.EMPTY_STRING;
            }
        }
    }

    /**
     * @param editor
     * @param id
     * @param title
     */
    public BlackBerryProjectPropertiesPage(FormEditor editor, String id, String title) {
        super(editor, id, title);
        _blackBerryProject = ((BlackBerryProjectFormEditor) editor).getBlackBerryProject();
    }

    protected void addSection(SectionPart part) {
        getManagedForm().addPart(part);
        sections.add(part);
    }

    protected SectionPart[] getSections() {
        return sections.toArray(new SectionPart[sections.size()]);
    }

    protected AbstractSection getSectionPartProperty(Composite body) {
        AbstractSection section = null;

        Object parent = body.getParent().getData(SECTION_PART_KEY);
        if (parent == null) {
            // if part cannot be found, check higher. Used in packaging section where there is another level of composite parents
            parent = body.getParent().getParent().getData(SECTION_PART_KEY);
        }
        if ((parent != null) && (parent instanceof AbstractSection)) {
            section = (AbstractSection) parent;
        }
        return section;
    }

    /**
     * @param keyTable
     * @return An array of he resource keys in the passed in resource
     */
    protected String[] getResourceKeys(Hashtable<String, String> keyTable) {
        if (keyTable == null) {
            return new String[] {};
        }
        ArrayList<String> keys = new ArrayList<String>();

        // Add blank entry to key list to allow user to select none.
        keys.add(""); //$NON-NLS-1$

        for (Iterator<String> iterator = keyTable.keySet().iterator(); iterator.hasNext();) {
            keys.add(iterator.next());
        }

        return keys.toArray(new String[keys.size()]);
    }

    /**
     * Creates an error marker in the editor with the given key
     *
     * @param key
     * @param message
     * @param control
     */
    public void createEditorErrorMarker(Object key, String message, Control control) {
        getManagedForm().getMessageManager().addMessage(key, message, null, IMessageProvider.ERROR, control);

    }

    /**
     * Creates a warning marker in the editor with the given key
     *
     * @param key
     * @param message
     * @param control
     */
    public void createEditorWarnMarker(Object key, String message, Control control) {
        getManagedForm().getMessageManager().addMessage(key, message, null, IMessageProvider.WARNING, control);
    }

    /**
     * Removes an error marker in the editor specified by the given key
     *
     * @param key
     * @param control
     */
    public void removeEditorErrorMarker(Object key, Control control) {
        getManagedForm().getMessageManager().removeMessage(key, control);
    }

    /**
     * Sets the editor and managed forms to dirty
     */
    protected void notifyModelChanged() {
        ((BlackBerryProjectFormEditor) getEditor()).setDirty(true);
        getManagedForm().dirtyStateChanged();
    }

    /**
     * Adds the given object item to the given table if and only if the object does not already exist. Also updates button
     * controls.
     *
     * @param viewer
     * @param item
     * @param actionButtons
     */
    public boolean addTableItem(TableViewer viewer, Object item, Map<Action, Button> actionButtons,
            boolean updateUIOnly) {
        if (updateUIOnly) {
            if (actionButtons.containsKey(Action.EDIT)) {
                actionButtons.get(Action.EDIT).setEnabled(true);
            }

            if (actionButtons.containsKey(Action.REMOVE)) {
                actionButtons.get(Action.REMOVE).setEnabled(true);
            }

            return true;
        } else {
            if (getObjectIndexInViewer(viewer, item) == -1) {
                if (item != null) {
                    viewer.add(item);
                    Table table = viewer.getTable();
                    table.select(table.getItemCount() - 1);

                    // Used to fire any selection events
                    viewer.setSelection(viewer.getSelection());
                }
                if (actionButtons.containsKey(Action.EDIT)) {
                    actionButtons.get(Action.EDIT).setEnabled(true);
                }

                if (actionButtons.containsKey(Action.REMOVE)) {
                    actionButtons.get(Action.REMOVE).setEnabled(true);
                }

                return true;
            }

            return false;
        }
    }

    /**
     * Sets the given viewer to the given input. Convenience method that removes all existing data before setting the input.
     *
     * @param viewer
     * @param input
     */
    public void setViewerInput(TableViewer viewer, Object[] input) {
        Arrays.sort(input);

        // Remove existing data
        viewer.setInput(null);
        viewer.getTable().removeAll();

        viewer.setInput(input);
        viewer.refresh(true);
    }

    /**
     * Helper method that locates the given itemText and if found selects it.
     *
     * @param viewer
     * @param itemText
     * @param actionButtons
     */
    public void selectItemInViewer(TableViewer viewer, String itemText, Map<Action, Button> actionButtons) {
        Integer index = getItemIndex(viewer.getTable(), itemText);

        if (index != -1) {
            viewer.getTable().select(index);

            // Used to fire any selection events
            viewer.setSelection(viewer.getSelection());

            if (actionButtons != null) {
                if (actionButtons.containsKey(Action.EDIT)) {
                    actionButtons.get(Action.EDIT).setEnabled(true);
                }
                if (actionButtons.containsKey(Action.REMOVE)) {
                    actionButtons.get(Action.REMOVE).setEnabled(true);
                }
                if (actionButtons.containsKey(Action.MOVE_UP)) {
                    if (viewer.getTable().getItemCount() > 1) {
                        actionButtons.get(Action.MOVE_UP).setEnabled(true);
                    }
                }
                if (actionButtons.containsKey(Action.MOVE_DOWN)) {
                    actionButtons.get(Action.MOVE_DOWN)
                            .setEnabled(index < viewer.getTable().getItemCount() - 1 ? true : false);
                }
            }
        }
    }

    /**
     * Removes the currently selected table item from the viewer and updates controls accordingly
     *
     * @param viewer
     * @param actionButtons
     * @param updateUIOnly
     *            <code>true</code> only update UI but not remove items from the table; <code>false</code> update UI and remove
     *            items from the table;
     */
    public void removeSelectedTableItem(TableViewer viewer, Map<Action, Button> actionButtons,
            boolean updateUIOnly) {
        StructuredSelection selection = (StructuredSelection) viewer.getSelection();
        Table table = viewer.getTable();
        int selectionIndex = table.getSelectionIndex();
        Boolean entryRemoved = false;

        if (!updateUIOnly) {
            for (Iterator<?> iter = selection.iterator(); iter.hasNext();) {
                Object selectedElement = iter.next();

                if (selectedElement != null) {

                    viewer.remove(selectedElement);

                    if (!entryRemoved) {
                        entryRemoved = true;
                    }
                }
            }
        }

        if (updateUIOnly || entryRemoved) {
            int itemCount = table.getItemCount();
            if (itemCount != 0) {
                table.select(itemCount - 1 > selectionIndex ? selectionIndex : itemCount - 1);

                if (actionButtons.containsKey(Action.MOVE_DOWN)) {
                    if (selectionIndex == itemCount - 1) {
                        actionButtons.get(Action.MOVE_DOWN).setEnabled(false);
                    }

                    actionButtons.get(Action.MOVE_UP).setEnabled(itemCount > 1 ? true : false);
                }

                // Used to fire any selection events
                viewer.setSelection(viewer.getSelection());
            } else {
                if (actionButtons.containsKey(Action.EDIT)) {
                    actionButtons.get(Action.EDIT).setEnabled(false);
                }
                if (actionButtons.containsKey(Action.REMOVE)) {
                    actionButtons.get(Action.REMOVE).setEnabled(false);
                }
                if (actionButtons.containsKey(Action.MOVE_UP)) {
                    actionButtons.get(Action.MOVE_UP).setEnabled(false);
                }
                if (actionButtons.containsKey(Action.MOVE_DOWN)) {
                    actionButtons.get(Action.MOVE_DOWN).setEnabled(false);
                }
                if (actionButtons.containsKey(Action.SELECT_ALL)) {
                    actionButtons.get(Action.SELECT_ALL).setEnabled(false);
                }
                if (actionButtons.containsKey(Action.SELECT_NONE)) {
                    actionButtons.get(Action.SELECT_NONE).setEnabled(false);
                }
            }

            // Enable any disabled add buttons - icon scenarios where only 2 icons can be added.
            if (actionButtons.containsKey(Action.ADD)) {
                actionButtons.get(Action.ADD).setEnabled(true);
            }
            if (actionButtons.containsKey(Action.ADD_FROM_PROJECT)) {
                actionButtons.get(Action.ADD_FROM_PROJECT).setEnabled(true);
            }
            if (actionButtons.containsKey(Action.ADD_FROM_EXTERNAL)) {
                actionButtons.get(Action.ADD_FROM_EXTERNAL).setEnabled(true);
            }

            if (table.getColumnCount() > 1) {
                table.getColumn(1).pack();
            }
        }
    }

    /**
     * Searches the given viewer for the given object and returns its index or -1 if the object was not found
     *
     * @param viewer
     * @param obj
     * @return
     */
    public Integer getObjectIndexInViewer(TableViewer viewer, Object obj) {
        for (int i = 0; i < viewer.getTable().getItemCount(); i++) {
            Object element = viewer.getElementAt(i);
            if ((obj instanceof Icon) && (element instanceof Icon)) {
                IProject project = _blackBerryProject.getProject();

                IPath iconPath = new Path(((Icon) element).getCanonicalFileName());
                IResource iconRes = project.findMember(iconPath);

                IPath projectPath = project.getLocation(), iconRelPath, iconAbsPath;
                if (iconRes != null) {
                    iconRelPath = projectPath.append(iconRes.getProjectRelativePath());
                    iconAbsPath = iconRes.getLocation();
                } else {
                    iconRelPath = null;
                    iconAbsPath = projectPath.append(iconPath);
                }

                IPath newIconPath = projectPath.append(((Icon) obj).getCanonicalFileName());

                if (newIconPath.equals(iconRelPath) || newIconPath.equals(iconAbsPath)) {
                    return i;
                }
            } else if ((obj instanceof PreprocessorTag) && (element instanceof PreprocessorTag)) {
                PreprocessorTag o1 = (PreprocessorTag) obj;
                PreprocessorTag o2 = (PreprocessorTag) element;

                if (o1.getPreprocessorDefine().equals(o2.getPreprocessorDefine())) {
                    return i;
                }
            } else {
                if (obj.equals(element)) {
                    return i;
                }
            }
        }
        return -1;
    }

    /**
     * Checks the given table for any items with the given text and returns the first found index
     *
     * @param table
     * @param itemText
     * @return The index or -1 if the text was not found
     */
    public static Integer getItemIndex(Table table, String itemText) {
        Object obj = table.getData(TABLE_TEXT_INDEX_KEY);
        Integer textColumn = null;

        if ((obj != null) && (obj instanceof Integer)) {
            textColumn = (Integer) obj;

            for (int i = 0; i < table.getItemCount(); i++) {
                TableItem item = table.getItem(i);
                if (item.getText(textColumn).equals(itemText)) {
                    return i;
                }
            }
        }
        return -1;
    }

    /**
     * Returns an instance of BlackBerryProject
     *
     * @return Instance of BlackBerryProject
     */
    public BlackBerryProject getBlackBerryProject() {
        return _blackBerryProject;
    }

    public static boolean isImage(String fileName) {
        if (fileName.toLowerCase().matches(".*[.](gif|png|xpm|bmp|jpg|jpeg|tiff)")) { //$NON-NLS-1$
            return true;
        }
        return false;
    }

    public static boolean isAlx(String fileName) {
        if (fileName.toLowerCase().matches(".*[.](alx)")) { //$NON-NLS-1$
            return true;
        }
        return false;
    }

    /**
     * Dirty listener
     *
     * @author jkeshavarzi
     *
     */
    public class DirtyListener implements ModifyListener, SelectionListener {
        AbstractFormPart _section = null;

        public DirtyListener(AbstractFormPart section) {
            _section = section;
        }

        @Override
        public void modifyText(ModifyEvent e) {
            process();
        }

        @Override
        public void widgetDefaultSelected(SelectionEvent e) {
            process();
        }

        @Override
        public void widgetSelected(SelectionEvent e) {
            process();
        }

        public void process() {
            notifyModelChanged();

            // The dirty flag must be set on the details rather than section so that changes made on it can be committed
            // see ManagedForm.commit() logic
            if (BlackBerryProjectPropertiesPage.this instanceof BlackBerryProjectAlternateEntryPointPage) {
                AlternateEntryPointDetails details = ((BlackBerryProjectAlternateEntryPointPage) BlackBerryProjectPropertiesPage.this)
                        .getAlternateEntryPointDetails();
                if (details != null) {
                    details.markDirty();
                }
            } else {
                _section.markDirty();
            }
        }
    }

    /**
     * The parent listener to all button event listeners used in the editor
     *
     * @author jkeshavarzi
     *
     */
    protected abstract class FilePathOperationSelectionListener implements SelectionListener {
        AbstractFormPart _section = null;

        protected FilePathOperationSelectionListener(AbstractFormPart section) {
            _section = section;
        }

        @Override
        public void widgetDefaultSelected(SelectionEvent e) {
            apply(e);
        }

        @Override
        public void widgetSelected(SelectionEvent e) {
            apply(e);
        }

        private void apply(SelectionEvent e) {
            if (process(e)) {
                notifyModelChanged();

                if (_section != null) {
                    _section.markDirty();
                }
            }
        }

        protected abstract boolean process(SelectionEvent e);
    }

    /**
     * Project properties focus listener
     *
     * @author jkeshavarzi
     *
     */
    protected class ProjectPropertiesFocusListener implements FocusListener {
        @Override
        public void focusLost(FocusEvent e) {
            // TODO Future implementation
        }

        @Override
        public void focusGained(FocusEvent e) {
            // Will be used in future outline View
            // BlackBerryProjectFormEditor editor = (BlackBerryProjectFormEditor) getEditor();
            // editor.updateContentOutlinePageSelection( (Control) e.getSource() );
        }
    }

    /**
     * The basic listener used in editor tables
     *
     * @author jkeshavarzi
     *
     */
    protected static class TableSelectionListener implements SelectionListener {
        private Button remove, edit, moveUp, moveDown;

        public TableSelectionListener(Map<Action, Button> buttonMap) {
            remove = buttonMap.get(Action.REMOVE);
            edit = buttonMap.get(Action.EDIT);
            moveUp = buttonMap.get(Action.MOVE_UP);
            moveDown = buttonMap.get(Action.MOVE_DOWN);
        }

        @Override
        public void widgetDefaultSelected(SelectionEvent e) {
        }

        @Override
        public void widgetSelected(SelectionEvent e) {
            Table table = ((Table) e.getSource());
            int selectionCount = table.getSelectionCount();
            int selectionIndex = table.getSelectionIndex();
            int itemCount = table.getItemCount();

            if (edit != null) {
                if (selectionCount > 1) {
                    edit.setEnabled(false);
                } else {
                    edit.setEnabled(true);
                }
            }
            if (remove != null) {
                remove.setEnabled(true);
            }
            if (moveUp != null) {
                moveUp.setEnabled((itemCount > 1) && (selectionIndex > 0) ? true : false);
            }
            if (moveDown != null) {
                moveDown.setEnabled((itemCount > 1) && (selectionIndex < itemCount - 1) ? true : false);
            }
        }
    }
}