📄 statusline.java
字号:
/******************************************************************************* * Copyright (c) 2000, 2006 IBM Corporation 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: * IBM Corporation - initial API and implementation *******************************************************************************/package org.eclipse.jface.action;import org.eclipse.core.runtime.IProgressMonitor;import org.eclipse.jface.dialogs.ProgressIndicator;import org.eclipse.jface.resource.ImageDescriptor;import org.eclipse.jface.resource.JFaceColors;import org.eclipse.jface.resource.JFaceResources;import org.eclipse.swt.SWT;import org.eclipse.swt.custom.CLabel;import org.eclipse.swt.events.DisposeEvent;import org.eclipse.swt.events.DisposeListener;import org.eclipse.swt.events.SelectionAdapter;import org.eclipse.swt.events.SelectionEvent;import org.eclipse.swt.graphics.Cursor;import org.eclipse.swt.graphics.Font;import org.eclipse.swt.graphics.Image;import org.eclipse.swt.graphics.Point;import org.eclipse.swt.graphics.Rectangle;import org.eclipse.swt.layout.GridData;import org.eclipse.swt.layout.GridLayout;import org.eclipse.swt.widgets.Composite;import org.eclipse.swt.widgets.Control;import org.eclipse.swt.widgets.Display;import org.eclipse.swt.widgets.Layout;import org.eclipse.swt.widgets.ToolBar;import org.eclipse.swt.widgets.ToolItem;/** * A StatusLine control is a SWT Composite with a horizontal layout which hosts * a number of status indication controls. * Typically it is situated below the content area of the window. * <p> * By default a StatusLine has two predefined status controls: a MessageLine and a * ProgressIndicator and it provides API for easy access. * </p> * <p> * This is an internal class, not intended to be used outside the JFace framework. * </p> *//* package */class StatusLine extends Composite implements IProgressMonitor { /** Horizontal gaps between items. */ public static final int GAP = 3; /** Progress bar creation is delayed by this ms */ public static final int DELAY_PROGRESS = 500; // state protected boolean fProgressIsVisible = false; protected boolean fCancelButtonIsVisible = false; protected boolean fCancelEnabled = false; protected String fTaskName; protected boolean fIsCanceled; protected long fStartTime; private Cursor fStopButtonCursor; protected String fMessageText; protected Image fMessageImage; protected String fErrorText; protected Image fErrorImage; // SWT widgets protected CLabel fMessageLabel; protected Composite fProgressBarComposite; protected ProgressIndicator fProgressBar; protected ToolBar fToolBar; protected ToolItem fCancelButton; protected static ImageDescriptor fgStopImage = ImageDescriptor .createFromFile(StatusLine.class, "images/stop.gif");//$NON-NLS-1$ static { JFaceResources.getImageRegistry().put( "org.eclipse.jface.parts.StatusLine.stopImage", fgStopImage);//$NON-NLS-1$ } /** * Layout the contribution item controls on the status line. */ public class StatusLineLayout extends Layout { private final StatusLineLayoutData DEFAULT_DATA = new StatusLineLayoutData(); public Point computeSize(Composite composite, int wHint, int hHint, boolean changed) { if (wHint != SWT.DEFAULT && hHint != SWT.DEFAULT) { return new Point(wHint, hHint); } Control[] children = composite.getChildren(); int totalWidth = 0; int maxHeight = 0; int totalCnt = 0; for (int i = 0; i < children.length; i++) { boolean useWidth = true; Control w = children[i]; if (w == fProgressBarComposite && !fProgressIsVisible) { useWidth = false; } else if (w == fToolBar && !fCancelButtonIsVisible) { useWidth = false; } StatusLineLayoutData data = (StatusLineLayoutData) w .getLayoutData(); if (data == null) { data = DEFAULT_DATA; } Point e = w.computeSize(data.widthHint, data.heightHint, changed); if (useWidth) { totalWidth += e.x; totalCnt++; } maxHeight = Math.max(maxHeight, e.y); } if (totalCnt > 0) { totalWidth += (totalCnt - 1) * GAP; } if (totalWidth <= 0) { totalWidth = maxHeight * 4; } return new Point(totalWidth, maxHeight); } public void layout(Composite composite, boolean flushCache) { if (composite == null) { return; } // StatusLineManager skips over the standard status line widgets // in its update method. There is thus a dependency // between the layout of the standard widgets and the update method. // Make sure cancel button and progress bar are before contributions. fMessageLabel.moveAbove(null); fToolBar.moveBelow(fMessageLabel); fProgressBarComposite.moveBelow(fToolBar); Rectangle rect = composite.getClientArea(); Control[] children = composite.getChildren(); int count = children.length; int ws[] = new int[count]; int h = rect.height; int totalWidth = -GAP; for (int i = 0; i < count; i++) { Control w = children[i]; if (w == fProgressBarComposite && !fProgressIsVisible) { continue; } if (w == fToolBar && !fCancelButtonIsVisible) { continue; } StatusLineLayoutData data = (StatusLineLayoutData) w .getLayoutData(); if (data == null) { data = DEFAULT_DATA; } int width = w.computeSize(data.widthHint, h, flushCache).x; ws[i] = width; totalWidth += width + GAP; } int diff = rect.width - totalWidth; ws[0] += diff; // make the first StatusLabel wider // Check against minimum recommended width final int msgMinWidth = rect.width / 3; if (ws[0] < msgMinWidth) { diff = ws[0] - msgMinWidth; ws[0] = msgMinWidth; } else { diff = 0; } // Take space away from the contributions first. for (int i = count - 1; i >= 0 && diff < 0; --i) { int min = Math.min(ws[i], -diff); ws[i] -= min; diff += min + GAP; } int x = rect.x; int y = rect.y; for (int i = 0; i < count; i++) { Control w = children[i]; /* * Workaround for Linux Motif: * Even if the progress bar and cancel button are * not set to be visible ad of width 0, they still * draw over the first pixel of the editor * contributions. * * The fix here is to draw the progress bar and * cancel button off screen if they are not visible. */ if (w == fProgressBarComposite && !fProgressIsVisible || w == fToolBar && !fCancelButtonIsVisible) { w.setBounds(x + rect.width, y, ws[i], h); continue; } w.setBounds(x, y, ws[i], h); if (ws[i] > 0) { x += ws[i] + GAP; } } } } /** * Create a new StatusLine as a child of the given parent. * * @param parent the parent for this Composite * @param style the style used to create this widget */ public StatusLine(Composite parent, int style) { super(parent, style); addDisposeListener(new DisposeListener() { public void widgetDisposed(DisposeEvent e) { handleDispose(); } }); // StatusLineManager skips over the standard status line widgets // in its update method. There is thus a dependency // between this code defining the creation and layout of the standard // widgets and the update method. setLayout(new StatusLineLayout()); fMessageLabel = new CLabel(this, SWT.NONE);//SWT.SHADOW_IN); // Color[] colors = new Color[2]; // colors[0] = parent.getDisplay().getSystemColor(SWT.COLOR_WIDGET_LIGHT_SHADOW); // colors[1] = fMessageLabel.getBackground(); // int[] gradient = new int[] {JFaceColors.STATUS_PERCENT}; // fMessageLabel.setBackground(colors, gradient); fProgressIsVisible = false; fCancelEnabled = false; fToolBar = new ToolBar(this, SWT.FLAT); fCancelButton = new ToolItem(fToolBar, SWT.PUSH); fCancelButton.setImage(fgStopImage.createImage()); fCancelButton.setToolTipText(JFaceResources .getString("Cancel_Current_Operation")); //$NON-NLS-1$ fCancelButton.addSelectionListener(new SelectionAdapter() { public void widgetSelected(SelectionEvent e) { setCanceled(true); } }); fCancelButton.addDisposeListener(new DisposeListener() { public void widgetDisposed(DisposeEvent e) { Image i = fCancelButton.getImage(); if ((i != null) && (!i.isDisposed())) { i.dispose(); } } }); // We create a composite to create the progress bar in // so that it can be centered. See bug #32331 fProgressBarComposite = new Composite(this, SWT.NONE); GridLayout layout = new GridLayout(); layout.horizontalSpacing = 0; layout.verticalSpacing = 0; layout.marginHeight = 0; layout.marginWidth = 0; fProgressBarComposite.setLayout(layout); fProgressBar = new ProgressIndicator(fProgressBarComposite); fProgressBar.setLayoutData(new GridData(GridData.GRAB_HORIZONTAL | GridData.GRAB_VERTICAL)); fStopButtonCursor = new Cursor(getDisplay(), SWT.CURSOR_ARROW); } /** * Notifies that the main task is beginning. * * @param name the name (or description) of the main task * @param totalWork the total number of work units into which * the main task is been subdivided. If the value is 0 or UNKNOWN the * implemenation is free to indicate progress in a way which doesn't * require the total number of work units in advance. In general users * should use the UNKNOWN value if they don't know the total amount of * work units. */ public void beginTask(String name, int totalWork) { final long timestamp = System.currentTimeMillis(); fStartTime = timestamp; final boolean animated = (totalWork == UNKNOWN || totalWork == 0); // make sure the progress bar is made visible while // the task is running. Fixes bug 32198 for the non-animated case. Runnable timer = new Runnable() { public void run() { StatusLine.this.startTask(timestamp, animated);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -