org.eclipse.mylyn.internal.github.ui.issue.IssueRepositoryQueryPage.java Source code

Java tutorial

Introduction

Here is the source code for org.eclipse.mylyn.internal.github.ui.issue.IssueRepositoryQueryPage.java

Source

/*******************************************************************************
 * Copyright (c) 2011 Red Hat and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     David Green <david.green@tasktop.com> - initial contribution
 *     Christian Trutz <christian.trutz@gmail.com> - initial contribution
 *     Chris Aniszczyk <caniszczyk@gmail.com> - initial contribution
 *******************************************************************************/
package org.eclipse.mylyn.internal.github.ui.issue;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.LinkedList;
import java.util.List;

import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.egit.github.core.Milestone;
import org.eclipse.egit.github.core.service.IssueService;
import org.eclipse.egit.github.core.util.LabelComparator;
import org.eclipse.jface.dialogs.ErrorDialog;
import org.eclipse.jface.layout.GridDataFactory;
import org.eclipse.jface.layout.GridLayoutFactory;
import org.eclipse.jface.operation.IRunnableContext;
import org.eclipse.jface.viewers.ArrayContentProvider;
import org.eclipse.jface.viewers.CheckboxTableViewer;
import org.eclipse.jface.viewers.ISelectionChangedListener;
import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.SelectionChangedEvent;
import org.eclipse.mylyn.commons.core.ICoreRunnable;
import org.eclipse.mylyn.commons.net.Policy;
import org.eclipse.mylyn.commons.ui.CommonUiUtil;
import org.eclipse.mylyn.internal.github.core.QueryUtils;
import org.eclipse.mylyn.internal.github.core.issue.IssueConnector;
import org.eclipse.mylyn.internal.github.ui.GitHubImages;
import org.eclipse.mylyn.internal.github.ui.GitHubRepositoryQueryPage;
import org.eclipse.mylyn.tasks.core.IRepositoryQuery;
import org.eclipse.mylyn.tasks.core.TaskRepository;
import org.eclipse.mylyn.tasks.ui.TasksUiImages;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.DisposeEvent;
import org.eclipse.swt.events.DisposeListener;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Group;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Text;
import org.eclipse.swt.widgets.ToolBar;
import org.eclipse.swt.widgets.ToolItem;
import org.eclipse.ui.PlatformUI;

/**
 * GitHub issue repository query page class.
 */
public class IssueRepositoryQueryPage extends GitHubRepositoryQueryPage {

    private Button openButton;
    private Button closedButton;
    private Text titleText;
    private Text assigneeText;
    private Text mentionText;
    private Combo milestoneCombo;
    private CheckboxTableViewer labelsViewer;
    private List<Milestone> milestones;

    private SelectionListener completeListener = new SelectionAdapter() {

        public void widgetSelected(SelectionEvent e) {
            setPageComplete(isPageComplete());
        }

    };

    /**
     * @param pageName
     * @param taskRepository
     * @param query
     */
    public IssueRepositoryQueryPage(String pageName, TaskRepository taskRepository, IRepositoryQuery query) {
        super(pageName, taskRepository, query);
        setDescription(Messages.IssueRepositoryQueryPage_Description);
        setPageComplete(false);
    }

    /**
     * @param taskRepository
     * @param query
     */
    public IssueRepositoryQueryPage(TaskRepository taskRepository, IRepositoryQuery query) {
        this("issueQueryPage", taskRepository, query); //$NON-NLS-1$
    }

    private void createLabelsArea(Composite parent) {
        Group labelsArea = new Group(parent, SWT.NONE);
        labelsArea.setText(Messages.IssueRepositoryQueryPage_LabelsLabel);
        GridDataFactory.fillDefaults().grab(true, true).applyTo(labelsArea);
        GridLayoutFactory.swtDefaults().applyTo(labelsArea);

        labelsViewer = CheckboxTableViewer.newCheckList(labelsArea, SWT.BORDER | SWT.V_SCROLL | SWT.H_SCROLL);
        GridDataFactory.fillDefaults().grab(true, true).hint(100, 80).applyTo(labelsViewer.getControl());
        labelsViewer.setContentProvider(ArrayContentProvider.getInstance());
        labelsViewer.setLabelProvider(new LabelProvider() {

            public Image getImage(Object element) {
                return GitHubImages.get(GitHubImages.GITHUB_ISSUE_LABEL_OBJ);
            }

        });
        labelsViewer.addSelectionChangedListener(new ISelectionChangedListener() {

            public void selectionChanged(SelectionChangedEvent event) {
                setPageComplete(isPageComplete());
            }
        });
    }

    private void createOptionsArea(Composite parent) {
        Composite optionsArea = new Composite(parent, SWT.NONE);
        GridLayoutFactory.fillDefaults().numColumns(2).applyTo(optionsArea);
        GridDataFactory.fillDefaults().grab(true, true).applyTo(optionsArea);

        Composite statusArea = new Composite(optionsArea, SWT.NONE);
        GridLayoutFactory.fillDefaults().numColumns(4).equalWidth(false).applyTo(statusArea);
        GridDataFactory.fillDefaults().grab(true, false).span(2, 1).applyTo(statusArea);

        new Label(statusArea, SWT.NONE).setText(Messages.IssueRepositoryQueryPage_StatusLabel);

        openButton = new Button(statusArea, SWT.CHECK);
        openButton.setSelection(true);
        openButton.setText(Messages.IssueRepositoryQueryPage_StatusOpen);
        openButton.addSelectionListener(completeListener);

        closedButton = new Button(statusArea, SWT.CHECK);
        closedButton.setSelection(true);
        closedButton.setText(Messages.IssueRepositoryQueryPage_StatusClosed);
        closedButton.addSelectionListener(completeListener);

        ToolBar toolbar = new ToolBar(statusArea, SWT.FLAT);
        ToolItem updateItem = new ToolItem(toolbar, SWT.PUSH);
        final Image updateImage = TasksUiImages.REPOSITORY_UPDATE_CONFIGURATION.createImage();
        toolbar.addDisposeListener(new DisposeListener() {

            public void widgetDisposed(DisposeEvent e) {
                updateImage.dispose();
            }
        });
        updateItem.setImage(updateImage);
        updateItem.setToolTipText(Messages.IssueRepositoryQueryPage_TooltipUpdateRepository);
        GridDataFactory.fillDefaults().align(SWT.END, SWT.FILL).grab(true, false).applyTo(toolbar);
        updateItem.addSelectionListener(new SelectionAdapter() {

            public void widgetSelected(SelectionEvent e) {
                refreshRepository();
            }

        });

        Label milestonesLabel = new Label(optionsArea, SWT.NONE);
        milestonesLabel.setText(Messages.IssueRepositoryQueryPage_MilestoneLabel);

        milestoneCombo = new Combo(optionsArea, SWT.DROP_DOWN | SWT.READ_ONLY);
        GridDataFactory.fillDefaults().grab(true, false).applyTo(milestoneCombo);

        Label assigneeLabel = new Label(optionsArea, SWT.NONE);
        assigneeLabel.setText(Messages.IssueRepositoryQueryPage_AssigneeLabel);

        assigneeText = new Text(optionsArea, SWT.BORDER | SWT.SINGLE);
        GridDataFactory.fillDefaults().grab(true, false).applyTo(assigneeText);

        Label mentionLabel = new Label(optionsArea, SWT.NONE);
        mentionLabel.setText(Messages.IssueRepositoryQueryPage_MentionsLabel);

        mentionText = new Text(optionsArea, SWT.BORDER | SWT.SINGLE);
        GridDataFactory.fillDefaults().grab(true, false).applyTo(mentionText);

    }

    /**
     * @see org.eclipse.jface.dialogs.IDialogPage#createControl(org.eclipse.swt.widgets.Composite)
     */
    public void createControl(Composite parent) {
        Composite displayArea = new Composite(parent, SWT.NONE);
        GridLayoutFactory.fillDefaults().numColumns(2).equalWidth(true).applyTo(displayArea);
        GridDataFactory.fillDefaults().grab(true, true).applyTo(displayArea);

        if (!inSearchContainer()) {
            Composite titleArea = new Composite(displayArea, SWT.NONE);
            GridLayoutFactory.fillDefaults().numColumns(2).applyTo(titleArea);
            GridDataFactory.fillDefaults().grab(true, false).span(2, 1).applyTo(titleArea);

            new Label(titleArea, SWT.NONE).setText(Messages.IssueRepositoryQueryPage_TitleLabel);
            titleText = new Text(titleArea, SWT.SINGLE | SWT.BORDER);
            GridDataFactory.fillDefaults().grab(true, false).applyTo(titleText);
            titleText.addModifyListener(new ModifyListener() {

                public void modifyText(ModifyEvent e) {
                    setPageComplete(isPageComplete());
                }
            });
        }

        createOptionsArea(displayArea);

        createLabelsArea(displayArea);

        loadRepository();

        initialize();
        setControl(displayArea);
    }

    private void initialize() {
        IRepositoryQuery query = getQuery();
        if (query == null)
            return;

        String milestoneNumber = query.getAttribute(IssueService.FILTER_MILESTONE);
        if (milestoneNumber != null && milestones != null) {
            int index = 0;
            for (Milestone milestone : milestones) {
                index++;
                if (milestoneNumber.equals(Integer.toString(milestone.getNumber()))) {
                    milestoneCombo.select(index);
                    break;
                }
            }
        }

        titleText.setText(query.getSummary());
        labelsViewer.setCheckedElements(QueryUtils.getAttributes(IssueService.FILTER_LABELS, query).toArray());
        List<String> status = QueryUtils.getAttributes(IssueService.FILTER_STATE, query);
        closedButton.setSelection(status.contains(IssueService.STATE_CLOSED));
        openButton.setSelection(status.contains(IssueService.STATE_OPEN));

        String assignee = query.getAttribute(IssueService.FILTER_ASSIGNEE);
        if (assignee != null)
            assigneeText.setText(assignee);

        String mentioning = query.getAttribute(IssueService.FILTER_MENTIONED);
        if (mentioning != null)
            mentionText.setText(mentioning);
    }

    private boolean updateLabels() {
        if (labelsViewer.getControl().isDisposed())
            return false;

        IssueConnector connector = IssueConnectorUi.getCoreConnector();
        TaskRepository repository = getTaskRepository();
        boolean hasLabels = connector.hasCachedLabels(repository);
        if (hasLabels) {
            List<org.eclipse.egit.github.core.Label> labels = connector.getLabels(repository);
            Collections.sort(labels, new LabelComparator());
            List<String> labelNames = new ArrayList<String>(labels.size());
            for (org.eclipse.egit.github.core.Label label : labels)
                labelNames.add(label.getName());
            labelsViewer.setInput(labelNames);
        }
        return hasLabels;
    }

    private boolean updateMilestones() {
        if (milestoneCombo.isDisposed())
            return false;

        IssueConnector connector = IssueConnectorUi.getCoreConnector();
        TaskRepository repository = getTaskRepository();
        boolean hasMilestones = connector.hasCachedMilestones(repository);
        if (hasMilestones) {
            milestones = connector.getMilestones(repository);
            milestoneCombo.removeAll();
            milestoneCombo.add(Messages.IssueRepositoryQueryPage_MilestoneNone);
            Collections.sort(milestones, new Comparator<Milestone>() {

                public int compare(Milestone m1, Milestone m2) {
                    return m1.getTitle().compareToIgnoreCase(m2.getTitle());
                }
            });
            for (Milestone milestone : milestones)
                milestoneCombo.add(milestone.getTitle());

            milestoneCombo.select(0);
        }
        return hasMilestones;
    }

    private void refreshRepository() {
        try {
            ICoreRunnable runnable = new ICoreRunnable() {

                public void run(IProgressMonitor monitor) throws CoreException {
                    Policy.monitorFor(monitor);
                    monitor.beginTask("", 2); //$NON-NLS-1$
                    IssueConnector connector = IssueConnectorUi.getCoreConnector();
                    TaskRepository repository = getTaskRepository();

                    monitor.setTaskName(Messages.IssueRepositoryQueryPage_TaskLoadingLabels);
                    connector.refreshLabels(repository);
                    monitor.worked(1);

                    monitor.setTaskName(Messages.IssueRepositoryQueryPage_TaskLoadingMilestones);
                    connector.refreshMilestones(repository);
                    monitor.done();

                    PlatformUI.getWorkbench().getDisplay().asyncExec(new Runnable() {

                        public void run() {
                            updateLabels();
                            updateMilestones();
                            initialize();
                        }
                    });
                }
            };
            IRunnableContext context = getContainer();
            if (context == null)
                if (inSearchContainer())
                    context = getSearchContainer().getRunnableContext();
                else
                    context = PlatformUI.getWorkbench().getProgressService();
            CommonUiUtil.run(context, runnable);
        } catch (CoreException e) {
            IStatus status = e.getStatus();
            ErrorDialog.openError(getShell(), Messages.IssueRepositoryQueryPage_ErrorLoading,
                    e.getLocalizedMessage(), status);
        }
    }

    private void loadRepository() {
        boolean labelsLoaded = updateLabels();
        boolean milestonesLoaded = updateMilestones();
        if (!labelsLoaded || !milestonesLoaded)
            refreshRepository();
    }

    /**
     * @see org.eclipse.mylyn.tasks.ui.wizards.AbstractRepositoryQueryPage#isPageComplete()
     */
    public boolean isPageComplete() {
        boolean complete = inSearchContainer() ? true : super.isPageComplete();
        if (complete) {
            String message = null;
            if (!openButton.getSelection() && !closedButton.getSelection())
                message = Messages.IssueRepositoryQueryPage_ErrorStatus;

            setErrorMessage(message);
            complete = message == null;
        }
        return complete;
    }

    /**
     * @see org.eclipse.mylyn.tasks.ui.wizards.AbstractRepositoryQueryPage#getQueryTitle()
     */
    public String getQueryTitle() {
        return titleText != null ? titleText.getText() : null;
    }

    /**
     * @see org.eclipse.mylyn.tasks.ui.wizards.AbstractRepositoryQueryPage#applyTo(org.eclipse.mylyn.tasks.core.IRepositoryQuery)
     */
    public void applyTo(IRepositoryQuery query) {
        query.setSummary(getQueryTitle());

        List<String> statuses = new LinkedList<String>();
        if (openButton.getSelection())
            statuses.add(IssueService.STATE_OPEN);
        if (closedButton.getSelection())
            statuses.add(IssueService.STATE_CLOSED);
        QueryUtils.setAttribute(IssueService.FILTER_STATE, statuses, query);

        String assignee = assigneeText.getText().trim();
        if (assignee.length() > 0)
            query.setAttribute(IssueService.FILTER_ASSIGNEE, assignee);
        else
            query.setAttribute(IssueService.FILTER_ASSIGNEE, null);

        String mentions = mentionText.getText().trim();
        if (mentions.length() > 0)
            query.setAttribute(IssueService.FILTER_MENTIONED, mentions);
        else
            query.setAttribute(IssueService.FILTER_MENTIONED, null);

        int milestoneSelected = milestoneCombo.getSelectionIndex() - 1;
        if (milestoneSelected >= 0)
            query.setAttribute(IssueService.FILTER_MILESTONE,
                    Integer.toString(milestones.get(milestoneSelected).getNumber()));
        else
            query.setAttribute(IssueService.FILTER_MILESTONE, null);

        List<String> labels = new LinkedList<String>();
        for (Object label : labelsViewer.getCheckedElements())
            labels.add(label.toString());
        QueryUtils.setAttribute(IssueService.FILTER_LABELS, labels, query);
    }
}