/* * Copyright (c) 2013, the Dart project authors. * * Licensed under the Eclipse Public License v1.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.eclipse.org/legal/epl-v10.html * * 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 com.google.dart.ui.test.util; import com.google.dart.ui.test.Condition; import com.google.dart.ui.test.WaitTimedOutException; import com.google.dart.ui.test.internal.runtime.ConditionHandler; import com.google.dart.ui.test.matchers.WidgetMatcher; import com.google.dart.ui.test.runnable.Result; import com.google.dart.ui.test.runnable.UIThreadRunnable; import com.google.dart.ui.test.runnable.VoidResult; import static com.google.dart.ui.test.matchers.WidgetMatchers.and; import static com.google.dart.ui.test.matchers.WidgetMatchers.ofClass; import static com.google.dart.ui.test.matchers.WidgetMatchers.withText; import org.eclipse.core.runtime.Assert; import org.eclipse.jface.action.IAction; import org.eclipse.swt.SWT; import org.eclipse.swt.custom.StyledText; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Button; import org.eclipse.swt.widgets.Control; import org.eclipse.swt.widgets.Display; import org.eclipse.swt.widgets.Event; import org.eclipse.swt.widgets.Label; import org.eclipse.swt.widgets.Shell; import org.eclipse.swt.widgets.Table; import org.eclipse.swt.widgets.Text; import org.eclipse.swt.widgets.Tree; import org.eclipse.swt.widgets.TreeItem; import org.eclipse.swt.widgets.Widget; /** * Helper for testing SWT UI from non-UI thread. */ public class UiContext2 { /** * Sends {@link SWT#Selection} event to given {@link Widget}. */ public static void click(final Widget widget) { UIThreadRunnable.syncExec(new VoidResult() { @Override public void run() { _click(widget); } }); } /** * Clicks the {@link Button} with matching text. */ public static void clickButton(Widget start, String text) { Button button = findButton(start, text); Assert.isNotNull(button, "Cannot find button: " + text); click(button); } /** * Asynchronously clicks the {@link Button} with matching text. */ public static void clickButtonAsync(Widget start, String text) { final Button button = findButton(start, text); Assert.isNotNull(button, "Cannot find button: " + text); UIThreadRunnable.asyncExec(new VoidResult() { @Override public void run() { _click(button); } }); } /** * @return the {@link Button} with matching text. */ public static Button findButton(Widget start, String text) { return findWidget(start, and(ofClass(Button.class), withText(text))); } /** * @return the {@link Label} with matching text. */ public static Label findLabel(Widget start, String text) { return findWidget(start, and(ofClass(Label.class), withText(text))); } /** * @return the first {@link Table} widget. */ public static Table findTable(Widget start) { return findWidget(start, ofClass(Table.class)); } /** * @return the {@link Text} widget that has {@link Label} with given text, may be {@code null}. */ public static Text findTextByLabel(Widget start, String labelText) { return (Text) findWidgetByLabel(start, labelText); } /** * @return the first {@link Tree} widget. */ public static Tree findTree(Widget start) { return findWidget(start, ofClass(Tree.class)); } /** * @return the matching {@link Widget}, may be {@code null}. */ public static <T extends Widget> T findWidget(final Widget start, final WidgetMatcher matcher) { return UIThreadRunnable.syncExec(new Result<T>() { @Override public T run() { return WidgetFinder.findWidget(start, matcher); } }); } /** * @return the {@link Widget} that has {@link Label} with given text, may be {@code null}. */ public static <T extends Widget> T findWidgetByLabel(final Widget start, final String labelText) { return UIThreadRunnable.syncExec(new Result<T>() { @Override public T run() { return WidgetFinder.findWidgetByLabel(start, labelText); } }); } /** * @return the {@link Button#getSelection()} result. */ public static boolean getSelection(final Button button) { return UIThreadRunnable.syncExec(new Result<Boolean>() { @Override public Boolean run() { return button.getSelection(); } }); } /** * @return the text of the given {@link Widget}, may be {@code null} is this type of the * {@link Widget} has no text. */ public static String getText(final Widget widget) { return UIThreadRunnable.syncExec(new Result<String>() { @Override public String run() { if (widget instanceof Button) { return ((Button) widget).getText(); } if (widget instanceof Label) { return ((Label) widget).getText(); } if (widget instanceof StyledText) { return ((StyledText) widget).getText(); } if (widget instanceof Text) { return ((Text) widget).getText(); } if (widget instanceof TreeItem) { return ((TreeItem) widget).getText(); } return null; } }); } /** * @return the text of the {@link Widget} that has {@link Label} with given text. */ public static String getTextByLabel(Widget start, String labelText) { Widget textWidget = findWidgetByLabel(start, labelText); return getText(textWidget); } /** * @return the {@link TreeItem}s of the given {@link Tree}. */ public static TreeItem[] getTreeItems(final Tree tree) { return UIThreadRunnable.syncExec(new Result<TreeItem[]>() { @Override public TreeItem[] run() { return tree.getItems(); } }); } /** * @return the {@link TreeItem} children of the given {@link TreeItem}. */ public static TreeItem[] getTreeItems(final TreeItem item) { return UIThreadRunnable.syncExec(new Result<TreeItem[]>() { @Override public TreeItem[] run() { return item.getItems(); } }); } /** * @return the {@link Control#isEnabled()} result. */ public static boolean isEnabled(final Control control) { return UIThreadRunnable.syncExec(new Result<Boolean>() { @Override public Boolean run() { return control.isEnabled(); } }); } /** * Asynchronously runs the given {@link IAction}. */ public static void runAction(final IAction action) { UIThreadRunnable.asyncExec(new VoidResult() { @Override public void run() { action.run(); } }); } /** * Sends the {@link SWT#DefaultSelection} to the parent {@link Tree}. */ public static void sendDefaultSelection(final TreeItem item) { UIThreadRunnable.syncExec(new VoidResult() { @Override public void run() { Tree tree = item.getParent(); Event event = new Event(); event.widget = tree; event.item = item; Rectangle bounds = item.getBounds(); event.x = bounds.x + 1; event.y = bounds.y + 1; tree.notifyListeners(SWT.DefaultSelection, event); } }); } /** * Calls {@link Button#setSelection(boolean)}. */ public static void setButtonSelection(Widget start, String text, boolean selection) { Button button = findButton(start, text); setSelection(button, selection); } /** * Calls {@link Button#setSelection(boolean)}. */ public static void setSelection(final Button button, final boolean selection) { UIThreadRunnable.syncExec(new VoidResult() { @Override public void run() { button.setSelection(selection); click(button); } }); } /** * Sets text for the given {@link Text} widget. */ public static void setText(final Text textWidget, final String text) { UIThreadRunnable.syncExec(new VoidResult() { @Override public void run() { textWidget.setText(text); } }); } /** * Sets the text for {@link Text} widget that has {@link Label} with given text. */ public static void setTextByLabel(Widget start, String labelText, String newText) { Text textWidget = findTextByLabel(start, labelText); setText(textWidget, newText); } /** * Waits until the given {@link IAction} will enabled. */ public static void waitForActionEnabled(final IAction action) { ConditionHandler.DEFAULT.waitFor(new Condition() { @Override public boolean test() { return action.isEnabled(); } }); } /** * Waits for the {@link Shell} with matching text. */ public static Shell waitForShell(final String text) throws WaitTimedOutException { final Shell foundShell[] = {null}; ConditionHandler.DEFAULT.waitFor(new Condition() { @Override public boolean test() { UIThreadRunnable.syncExec(new VoidResult() { @Override public void run() { Display display = Display.getCurrent(); for (Shell shell : display.getShells()) { if (text.equals(shell.getText()) && shell.isVisible()) { foundShell[0] = shell; } } } }); return foundShell[0] != null; } @Override public String toString() { return "Shell " + text; } }); return foundShell[0]; } /** * Waits until the given {@link Shell} is closed. */ public static void waitForShellClosed(final Shell shell) { ConditionHandler.DEFAULT.waitFor(new Condition() { @Override public boolean test() { return UIThreadRunnable.syncExec(new Result<Boolean>() { @Override public Boolean run() { return shell.isDisposed(); } }); } }); } /** * Sends {@link SWT#Selection} event to given {@link Widget}. */ private static void _click(Widget widget) { widget.notifyListeners(SWT.Selection, new Event()); } }