/******************************************************************************* * Copyright (c) 2000, 2007 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 * Chriss Gross (schtoo@schtoo.com) - fix for 61670 *******************************************************************************/ package org.eclipse.ui.internal.forms.widgets; //import com.ibm.icu.text.BreakIterator; import java.text.BreakIterator; import org.eclipse.rwt.graphics.Graphics; import org.eclipse.swt.SWT; import org.eclipse.swt.custom.ScrolledComposite; import org.eclipse.swt.graphics.*; import org.eclipse.swt.layout.GridData; import org.eclipse.swt.widgets.*; import org.eclipse.ui.forms.widgets.*; public class FormUtil { public static final String PLUGIN_ID = "org.eclipse.ui.forms"; //$NON-NLS-1$ static final int H_SCROLL_INCREMENT = 5; static final int V_SCROLL_INCREMENT = 64; public static final String DEBUG = PLUGIN_ID + "/debug"; //$NON-NLS-1$ public static final String DEBUG_TEXT = DEBUG + "/text"; //$NON-NLS-1$ public static final String DEBUG_TEXTSIZE = DEBUG + "/textsize"; //$NON-NLS-1$ public static final String DEBUG_FOCUS = DEBUG + "/focus"; //$NON-NLS-1$ public static final String FOCUS_SCROLLING = "focusScrolling"; //$NON-NLS-1$ public static final String IGNORE_BODY = "__ignore_body__"; //$NON-NLS-1$ public static Text createText(Composite parent, String label, FormToolkit factory) { return createText(parent, label, factory, 1); } public static Text createText(Composite parent, String label, FormToolkit factory, int span) { factory.createLabel(parent, label); Text text = factory.createText(parent, ""); //$NON-NLS-1$ int hfill = span == 1 ? GridData.FILL_HORIZONTAL : GridData.HORIZONTAL_ALIGN_FILL; GridData gd = new GridData(hfill | GridData.VERTICAL_ALIGN_CENTER); gd.horizontalSpan = span; text.setLayoutData(gd); return text; } public static Text createText(Composite parent, String label, FormToolkit factory, int span, int style) { Label l = factory.createLabel(parent, label); if ((style & SWT.MULTI) != 0) { GridData gd = new GridData(GridData.VERTICAL_ALIGN_BEGINNING); l.setLayoutData(gd); } Text text = factory.createText(parent, "", style); //$NON-NLS-1$ int hfill = span == 1 ? GridData.FILL_HORIZONTAL : GridData.HORIZONTAL_ALIGN_FILL; GridData gd = new GridData(hfill | GridData.VERTICAL_ALIGN_CENTER); gd.horizontalSpan = span; text.setLayoutData(gd); return text; } public static Text createText(Composite parent, FormToolkit factory, int span) { Text text = factory.createText(parent, ""); //$NON-NLS-1$ int hfill = span == 1 ? GridData.FILL_HORIZONTAL : GridData.HORIZONTAL_ALIGN_FILL; GridData gd = new GridData(hfill | GridData.VERTICAL_ALIGN_CENTER); gd.horizontalSpan = span; text.setLayoutData(gd); return text; } // public static int computeMinimumWidth(GC gc, String text) { // BreakIterator wb = BreakIterator.getWordInstance(); // wb.setText(text); // int last = 0; // // int width = 0; // // for (int loc = wb.first(); loc != BreakIterator.DONE; loc = wb.next()) { // String word = text.substring(last, loc); // Point extent = gc.textExtent(word); // width = Math.max(width, extent.x); // last = loc; // } // String lastWord = text.substring(last); // Point extent = gc.textExtent(lastWord); // width = Math.max(width, extent.x); // return width; // } //XXX Changed method signature // public static Point computeWrapSize(GC gc, String text, int wHint) { public static Point computeWrapSize(Font font, String text, int wHint) { // XXX RAP specific: RCP Forms uses BreakIterator from the com.ibm.icu // plug-in BreakIterator wb = BreakIterator.getWordInstance(); wb.setText(text); // FontMetrics fm = gc.getFontMetrics(); // int lineHeight = fm.getHeight(); int lineHeight = Graphics.getCharHeight( font ); int saved = 0; int last = 0; int height = lineHeight; int maxWidth = 0; for (int loc = wb.first(); loc != BreakIterator.DONE; loc = wb.next()) { String word = text.substring(saved, loc); // Point extent = gc.textExtent(word); Point extent = Graphics.stringExtent( font, word ); if (extent.x > wHint) { // overflow saved = last; height += extent.y; } else { maxWidth = Math.max(maxWidth, extent.x); } last = loc; } return new Point(maxWidth, height); } // public static void paintWrapText(GC gc, String text, Rectangle bounds) { // paintWrapText(gc, text, bounds, false); // } // // public static void paintWrapText(GC gc, String text, Rectangle bounds, // boolean underline) { // BreakIterator wb = BreakIterator.getWordInstance(); // wb.setText(text); // FontMetrics fm = gc.getFontMetrics(); // int lineHeight = fm.getHeight(); // int descent = fm.getDescent(); // // int saved = 0; // int last = 0; // int y = bounds.y; // int width = bounds.width; // // for (int loc = wb.first(); loc != BreakIterator.DONE; loc = wb.next()) { // String line = text.substring(saved, loc); // Point extent = gc.textExtent(line); // // if (extent.x > width) { // // overflow // String prevLine = text.substring(saved, last); // gc.drawText(prevLine, bounds.x, y, true); // if (underline) { // Point prevExtent = gc.textExtent(prevLine); // int lineY = y + lineHeight - descent + 1; // gc // .drawLine(bounds.x, lineY, bounds.x + prevExtent.x, // lineY); // } // // saved = last; // y += lineHeight; // } // last = loc; // } // // paint the last line // String lastLine = text.substring(saved, last); // gc.drawText(lastLine, bounds.x, y, true); // if (underline) { // int lineY = y + lineHeight - descent + 1; // Point lastExtent = gc.textExtent(lastLine); // gc.drawLine(bounds.x, lineY, bounds.x + lastExtent.x, lineY); // } // } public static ScrolledComposite getScrolledComposite(Control c) { Composite parent = c.getParent(); while (parent != null) { if (parent instanceof ScrolledComposite) { return (ScrolledComposite) parent; } parent = parent.getParent(); } return null; } public static void ensureVisible(Control c) { ScrolledComposite scomp = getScrolledComposite(c); if (scomp != null) { Object data = scomp.getData(FOCUS_SCROLLING); if (data == null || !data.equals(Boolean.FALSE)) FormUtil.ensureVisible(scomp, c); } } public static void ensureVisible(ScrolledComposite scomp, Control control) { Point controlSize = control.getSize(); Point controlOrigin = getControlLocation(scomp, control); ensureVisible(scomp, controlOrigin, controlSize); } public static void ensureVisible(ScrolledComposite scomp, Point controlOrigin, Point controlSize) { Rectangle area = scomp.getClientArea(); Point scompOrigin = scomp.getOrigin(); int x = scompOrigin.x; int y = scompOrigin.y; // horizontal right, but only if the control is smaller // than the client area if (controlSize.x < area.width && (controlOrigin.x + controlSize.x > scompOrigin.x + area.width)) { x = controlOrigin.x + controlSize.x - area.width; } // horizontal left - make sure the left edge of // the control is showing if (controlOrigin.x < x) { if (controlSize.x < area.width) x = controlOrigin.x + controlSize.x - area.width; else x = controlOrigin.x; } // vertical bottom if (controlSize.y < area.height && (controlOrigin.y + controlSize.y > scompOrigin.y + area.height)) { y = controlOrigin.y + controlSize.y - area.height; } // vertical top - make sure the top of // the control is showing if (controlOrigin.y < y) { if (controlSize.y < area.height) y = controlOrigin.y + controlSize.y - area.height; else y = controlOrigin.y; } if (scompOrigin.x != x || scompOrigin.y != y) { // scroll to reveal scomp.setOrigin(x, y); } } // public static void ensureVisible(ScrolledComposite scomp, Control control, // MouseEvent e) { // Point controlOrigin = getControlLocation(scomp, control); // int rX = controlOrigin.x + e.x; // int rY = controlOrigin.y + e.y; // Rectangle area = scomp.getClientArea(); // Point scompOrigin = scomp.getOrigin(); // // int x = scompOrigin.x; // int y = scompOrigin.y; // // System.out.println("Ensure: area="+area+", origin="+scompOrigin+", // // cloc="+controlOrigin+", csize="+controlSize+", x="+x+", y="+y); // // // horizontal right // if (rX > scompOrigin.x + area.width) { // x = rX - area.width; // } // // horizontal left // else if (rX < x) { // x = rX; // } // // vertical bottom // if (rY > scompOrigin.y + area.height) { // y = rY - area.height; // } // // vertical top // else if (rY < y) { // y = rY; // } // // if (scompOrigin.x != x || scompOrigin.y != y) { // // scroll to reveal // scomp.setOrigin(x, y); // } // } public static Point getControlLocation(ScrolledComposite scomp, Control control) { int x = 0; int y = 0; Control content = scomp.getContent(); Control currentControl = control; for (;;) { if (currentControl == content) break; Point location = currentControl.getLocation(); // if (location.x > 0) // x += location.x; // if (location.y > 0) // y += location.y; x += location.x; y += location.y; currentControl = currentControl.getParent(); } return new Point(x, y); } static void scrollVertical(ScrolledComposite scomp, boolean up) { scroll(scomp, 0, up ? -V_SCROLL_INCREMENT : V_SCROLL_INCREMENT); } static void scrollHorizontal(ScrolledComposite scomp, boolean left) { scroll(scomp, left ? -H_SCROLL_INCREMENT : H_SCROLL_INCREMENT, 0); } static void scrollPage(ScrolledComposite scomp, boolean up) { Rectangle clientArea = scomp.getClientArea(); int increment = up ? -clientArea.height : clientArea.height; scroll(scomp, 0, increment); } static void scroll(ScrolledComposite scomp, int xoffset, int yoffset) { Point origin = scomp.getOrigin(); Point contentSize = scomp.getContent().getSize(); int xorigin = origin.x + xoffset; int yorigin = origin.y + yoffset; xorigin = Math.max(xorigin, 0); xorigin = Math.min(xorigin, contentSize.x - 1); yorigin = Math.max(yorigin, 0); yorigin = Math.min(yorigin, contentSize.y - 1); scomp.setOrigin(xorigin, yorigin); } public static void updatePageIncrement(ScrolledComposite scomp) { // ScrollBar vbar = scomp.getVerticalBar(); // if (vbar != null) { // Rectangle clientArea = scomp.getClientArea(); // int increment = clientArea.height - 5; // vbar.setPageIncrement(increment); // } } public static void processKey(int keyCode, Control c) { // ScrolledComposite scomp = FormUtil.getScrolledComposite(c); // if (scomp != null) { // if (c instanceof Combo) // return; // switch (keyCode) { // case SWT.ARROW_DOWN: // if (scomp.getData("novarrows") == null) //$NON-NLS-1$ // FormUtil.scrollVertical(scomp, false); // break; // case SWT.ARROW_UP: // if (scomp.getData("novarrows") == null) //$NON-NLS-1$ // FormUtil.scrollVertical(scomp, true); // break; // case SWT.ARROW_LEFT: // FormUtil.scrollHorizontal(scomp, true); // break; // case SWT.ARROW_RIGHT: // FormUtil.scrollHorizontal(scomp, false); // break; // case SWT.PAGE_UP: // FormUtil.scrollPage(scomp, true); // break; // case SWT.PAGE_DOWN: // FormUtil.scrollPage(scomp, false); // break; // } // } } static boolean isWrapControl(Control c) { if ((c.getStyle() & SWT.WRAP) != 0) return true; if (c instanceof Composite) { return ((Composite) c).getLayout() instanceof ILayoutExtension; } return false; } public static int getWidthHint(int wHint, Control c) { boolean wrap = isWrapControl(c); return wrap ? wHint : SWT.DEFAULT; } public static int getHeightHint(int hHint, Control c) { if (c instanceof Composite) { Layout layout = ((Composite) c).getLayout(); if (layout instanceof ColumnLayout) return hHint; } return SWT.DEFAULT; } public static int computeMinimumWidth(Control c, boolean changed) { if (c instanceof Composite) { Layout layout = ((Composite) c).getLayout(); if (layout instanceof ILayoutExtension) return ((ILayoutExtension) layout).computeMinimumWidth( (Composite) c, changed); } return c.computeSize(FormUtil.getWidthHint(5, c), SWT.DEFAULT, changed).x; } public static int computeMaximumWidth(Control c, boolean changed) { if (c instanceof Composite) { Layout layout = ((Composite) c).getLayout(); if (layout instanceof ILayoutExtension) return ((ILayoutExtension) layout).computeMaximumWidth( (Composite) c, changed); } return c.computeSize(SWT.DEFAULT, SWT.DEFAULT, changed).x; } public static Form getForm(Control c) { Composite parent = c.getParent(); while (parent != null) { if (parent instanceof Form) { return (Form) parent; } parent = parent.getParent(); } return null; } // public static Image createAlphaMashImage(Device device, Image srcImage) { // Rectangle bounds = srcImage.getBounds(); // int alpha = 0; // int calpha = 0; // ImageData data = srcImage.getImageData(); // // Create a new image with alpha values alternating // // between fully transparent (0) and fully opaque (255). // // This image will show the background through the // // transparent pixels. // for (int i = 0; i < bounds.height; i++) { // // scan line // alpha = calpha; // for (int j = 0; j < bounds.width; j++) { // // column // data.setAlpha(j, i, alpha); // alpha = alpha == 255 ? 0 : 255; // } // calpha = calpha == 255 ? 0 : 255; // } // return new Image(device, data); // } public static Font createBoldFont(Display display, Font regularFont) { FontData[] fontDatas = regularFont.getFontData(); for (int i = 0; i < fontDatas.length; i++) { // fontDatas[i].setStyle(fontDatas[i].getStyle() | SWT.BOLD); fontDatas[ i ] = new FontData( fontDatas[ i ].getName(), fontDatas[ i ].getHeight(), fontDatas[ i ].getStyle() | SWT.BOLD ); } return Graphics.getFont( fontDatas[ 0 ] ); } public static boolean mnemonicMatch(String text, char key) { char mnemonic = findMnemonic(text); if (mnemonic == '\0') return false; return Character.toUpperCase(key) == Character.toUpperCase(mnemonic); } private static char findMnemonic(String string) { int index = 0; int length = string.length(); do { while (index < length && string.charAt(index) != '&') index++; if (++index >= length) return '\0'; if (string.charAt(index) != '&') return string.charAt(index); index++; } while (index < length); return '\0'; } public static void setFocusScrollingEnabled(Control c, boolean enabled) { ScrolledComposite scomp = null; if (c instanceof ScrolledComposite) scomp = (ScrolledComposite)c; else scomp = getScrolledComposite(c); if (scomp!=null) scomp.setData(FormUtil.FOCUS_SCROLLING, enabled?null:Boolean.FALSE); } // public static void setAntialias(GC gc, int style) { // if (!gc.getAdvanced()) { // gc.setAdvanced(true); // if (!gc.getAdvanced()) // return; // } // gc.setAntialias(style); // } }