au.gov.ga.earthsci.application.parts.retrieve.RetrievePart.java Source code

Java tutorial

Introduction

Here is the source code for au.gov.ga.earthsci.application.parts.retrieve.RetrievePart.java

Source

/*******************************************************************************
 * Copyright 2012 Geoscience Australia
 * 
 * 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 au.gov.ga.earthsci.application.parts.retrieve;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import javax.annotation.PreDestroy;
import javax.inject.Inject;

import org.eclipse.e4.ui.model.application.ui.basic.MPart;
import org.eclipse.jface.viewers.ArrayContentProvider;
import org.eclipse.jface.viewers.ColumnLabelProvider;
import org.eclipse.jface.viewers.OwnerDrawLabelProvider;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.viewers.TableViewerColumn;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.GC;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.TableItem;

import au.gov.ga.earthsci.common.ui.util.SWTUtil;
import au.gov.ga.earthsci.core.retrieve.IRetrieval;
import au.gov.ga.earthsci.core.retrieve.IRetrievalListener;
import au.gov.ga.earthsci.core.retrieve.IRetrievalService;
import au.gov.ga.earthsci.core.retrieve.IRetrievalServiceListener;
import au.gov.ga.earthsci.core.retrieve.RetrievalAdapter;

/**
 * Part that displays progress of {@link IRetrieval}s running in the
 * {@link IRetrievalService}.
 * 
 * @author Michael de Hoog (michael.dehoog@ga.gov.au)
 */
public class RetrievePart implements IRetrievalServiceListener {
    @Inject
    private IRetrievalService retrievalService;

    private TableViewer viewer;

    private final List<IRetrieval> retrievals = new ArrayList<IRetrieval>();
    private final Set<Object> updatingElements = new HashSet<Object>();

    private Color downloadBackgroundColor;

    @Inject
    public void init(Composite parent, MPart part) {
        Color listBackground = parent.getDisplay().getSystemColor(SWT.COLOR_LIST_BACKGROUND);
        downloadBackgroundColor = SWTUtil.shouldDarken(listBackground) ? SWTUtil.darker(listBackground)
                : SWTUtil.lighter(listBackground);

        retrievalService.addListener(this);

        viewer = new TableViewer(parent, SWT.V_SCROLL);
        viewer.setContentProvider(ArrayContentProvider.getInstance());
        viewer.setInput(retrievals);
        viewer.getTable().setLinesVisible(true);
        viewer.getTable().setHeaderVisible(true);
        /*viewer.setSorter(new ViewerSorter()
        {
           @Override
           public int category(Object element)
           {
        return ((JobInfo) element).job.getState();
           }
            
           @Override
           public int compare(Viewer viewer, Object e1, Object e2)
           {
        return ((JobInfo) e1).job.getPriority() - ((JobInfo) e2).job.getPriority();
           }
        });
        viewer.addFilter(new ViewerFilter()
        {
           @Override
           public boolean select(Viewer viewer, Object parentElement, Object element)
           {
        return ((JobInfo) element).job.getState() != Job.SLEEPING;
           }
            
        });*/

        createColumns();
    }

    @PreDestroy
    public void packup() {
        retrievalService.removeListener(this);
        downloadBackgroundColor.dispose();
    }

    private void createColumns() {
        TableViewerColumn column = new TableViewerColumn(viewer, SWT.NONE);
        column.getColumn().setText("URL");
        column.getColumn().setWidth(300);
        column.setLabelProvider(new ColumnLabelProvider() {
            @Override
            public String getText(Object element) {
                IRetrieval retrieval = (IRetrieval) element;
                return retrieval.getURL().toString();
            }
        });

        column = new TableViewerColumn(viewer, SWT.NONE);
        column.getColumn().setText("Caller(s)");
        column.getColumn().setWidth(200);
        column.setLabelProvider(new ColumnLabelProvider() {
            @Override
            public String getText(Object element) {
                IRetrieval retrieval = (IRetrieval) element;
                StringBuilder sb = new StringBuilder();
                for (Object caller : retrieval.getCallers()) {
                    sb.append(", " + caller.toString()); //$NON-NLS-1$
                }
                if (sb.length() == 0) {
                    return sb.toString();
                }
                return sb.substring(2);
            }
        });

        column = new TableViewerColumn(viewer, SWT.NONE);
        column.getColumn().setText("Progress");
        column.getColumn().setWidth(150);
        column.setLabelProvider(new OwnerDrawLabelProvider() {
            @Override
            protected void paint(Event event, Object element) {
                GC gc = event.gc;
                Color foreground = gc.getForeground();
                Color background = gc.getBackground();

                IRetrieval retrieval = (IRetrieval) element;
                float percentage = Math.max(0, retrieval.getPercentage());
                String text = positionString(retrieval);

                Rectangle bounds = ((TableItem) event.item).getBounds(event.index);
                int width = (int) ((bounds.width - 1) * percentage);
                gc.setBackground(downloadBackgroundColor);
                gc.fillRectangle(event.x, event.y, width, event.height);

                Point size = event.gc.textExtent(text);
                int offset = Math.max(0, (event.height - size.y) / 2);
                gc.setForeground(event.display.getSystemColor(SWT.COLOR_LIST_FOREGROUND));
                gc.drawText(text, event.x + 2, event.y + offset, true);

                gc.setForeground(background);
                gc.setBackground(foreground);
            }

            @Override
            protected void measure(Event event, Object element) {
            }
        });
    }

    private static String positionString(IRetrieval retrieval) {
        long position = retrieval.getPosition();
        long length = retrieval.getLength();
        float percentage = retrieval.getPercentage();
        StringBuilder sb = new StringBuilder();
        String unknown = "unknown";

        long max = Math.max(position, length);
        if (max >= 0) {
            int unitNumber = max == 0 ? 0 : (int) (Math.log10(max) / Math.log10(1024));

            String prefixes = "kMGTPEZY"; //$NON-NLS-1$
            if (unitNumber > prefixes.length()) {
                unitNumber = 0;
            }
            String unit = (unitNumber <= 0 ? "" : prefixes.charAt(unitNumber - 1)) + "B"; //$NON-NLS-1$ //$NON-NLS-2$

            long divisor = (long) Math.pow(1024, unitNumber);
            position /= divisor;
            length /= divisor;

            sb.append(position);
            sb.append(' ');
            sb.append(unit);

            sb.append(' ');
            sb.append("of");
            sb.append(' ');

            if (length <= 0) {
                sb.append(unknown);
            } else {
                sb.append(length);
                sb.append(' ');
                sb.append(unit);
            }
        } else {
            sb.append(unknown);
        }

        if (percentage >= 0) {
            sb.append(" ("); //$NON-NLS-1$
            sb.append((int) (percentage * 100));
            sb.append("%)"); //$NON-NLS-1$
        }

        return sb.toString();
    }

    @Override
    public void retrievalAdded(final IRetrieval retrieval) {
        synchronized (retrievals) {
            retrievals.add(retrieval);
        }
        retrieval.addListener(retrievalListener);
        if (viewer != null && !viewer.getControl().isDisposed()) {
            viewer.getControl().getDisplay().asyncExec(new Runnable() {
                @Override
                public void run() {
                    if (!viewer.getControl().isDisposed()) {
                        viewer.add(retrieval);
                    }
                }
            });
        }
    }

    @Override
    public void retrievalRemoved(final IRetrieval retrieval) {
        synchronized (retrievals) {
            retrievals.remove(retrieval);
        }
        retrieval.removeListener(retrievalListener);
        if (viewer != null && !viewer.getControl().isDisposed()) {
            viewer.getControl().getDisplay().asyncExec(new Runnable() {
                @Override
                public void run() {
                    if (!viewer.getControl().isDisposed()) {
                        viewer.remove(retrieval);
                    }
                }
            });
        }
    }

    private void asyncUpdate(final Object element) {
        //don't queue multiple updates for each retrieval, so we don't flood the UI thread with asyncExec's
        if (updatingElements.contains(element)) {
            return;
        }

        if (viewer != null && !viewer.getControl().isDisposed()) {
            updatingElements.add(element);
            viewer.getControl().getDisplay().asyncExec(new Runnable() {
                @Override
                public void run() {
                    if (!viewer.getControl().isDisposed()) {
                        viewer.update(element, null);
                    }
                    updatingElements.remove(element);
                }
            });
        }
    }

    private IRetrievalListener retrievalListener = new RetrievalAdapter() {
        @Override
        public void progress(IRetrieval retrieval) {
            asyncUpdate(retrieval);
        }

        @Override
        public void callersChanged(IRetrieval retrieval) {
            asyncUpdate(retrieval);
        }
    };
}