Home | History | Annotate | Download | only in execution
      1 /*******************************************************************************
      2  * Copyright (c) 2011 Google, Inc.
      3  * All rights reserved. This program and the accompanying materials
      4  * are made available under the terms of the Eclipse Public License v1.0
      5  * which accompanies this distribution, and is available at
      6  * http://www.eclipse.org/legal/epl-v10.html
      7  *
      8  * Contributors:
      9  *    Google, Inc. - initial API and implementation
     10  *******************************************************************************/
     11 package org.eclipse.wb.internal.core.utils.execution;
     12 
     13 import org.eclipse.swt.widgets.Display;
     14 import org.eclipse.wb.internal.core.DesignerPlugin;
     15 import org.eclipse.wb.internal.core.utils.reflect.ReflectionUtils;
     16 
     17 import java.beans.Beans;
     18 
     19 /**
     20  * Utilities for executing actions, such as {@link RunnableEx}.
     21  *
     22  * @author scheglov_ke
     23  * @coverage core.util
     24  */
     25 public class ExecutionUtils {
     26   ////////////////////////////////////////////////////////////////////////////
     27   //
     28   // Constructor
     29   //
     30   ////////////////////////////////////////////////////////////////////////////
     31   private ExecutionUtils() {
     32   }
     33 
     34   ////////////////////////////////////////////////////////////////////////////
     35   //
     36   // Sleep
     37   //
     38   ////////////////////////////////////////////////////////////////////////////
     39   /**
     40    * Sleeps given number of milliseconds, ignoring exceptions.
     41    */
     42   public static void sleep(final int millis) {
     43     runIgnore(new RunnableEx() {
     44       @Override
     45     public void run() throws Exception {
     46         Thread.sleep(millis);
     47       }
     48     });
     49   }
     50 
     51   /**
     52    * Waits given number of milliseconds and runs events loop every 1 millisecond. At least one
     53    * events loop will be executed. If current thread is not UI thread, then this method works just
     54    * as {@link #sleep(int)}.
     55    */
     56   public static void waitEventLoop(int millis) {
     57     Display display = Display.getCurrent();
     58     if (display != null) {
     59       long nanos = millis * 1000000L;
     60       long start = System.nanoTime();
     61       do {
     62         sleep(0);
     63         while (display.readAndDispatch()) {
     64           // do nothing
     65         }
     66       } while (System.nanoTime() - start < nanos);
     67     } else {
     68       sleep(millis);
     69     }
     70   }
     71 
     72   ////////////////////////////////////////////////////////////////////////////
     73   //
     74   // void
     75   //
     76   ////////////////////////////////////////////////////////////////////////////
     77   /**
     78    * Runs given {@link RunnableEx} and ignores exceptions.
     79    *
     80    * @return <code>true</code> if execution was finished without exception.
     81    */
     82   public static boolean runIgnore(RunnableEx runnable) {
     83     try {
     84       runnable.run();
     85       return true;
     86     } catch (Throwable e) {
     87       return false;
     88     }
     89   }
     90 
     91   /**
     92    * Runs given {@link RunnableEx} and logs exceptions using {@link DesignerPlugin#log(Throwable)}.
     93    *
     94    * @return <code>true</code> if execution was finished without exception.
     95    */
     96   public static boolean runLog(RunnableEx runnable) {
     97     try {
     98       runnable.run();
     99       return true;
    100     } catch (Throwable e) {
    101       DesignerPlugin.log(e);
    102       return false;
    103     }
    104   }
    105 
    106   /**
    107    * Runs given {@link RunnableEx} and re-throws exceptions using {@link RuntimeException}.
    108    */
    109   public static void runRethrow(RunnableEx runnable) {
    110     try {
    111       runnable.run();
    112     } catch (Throwable e) {
    113       throw ReflectionUtils.propagate(e);
    114     }
    115   }
    116 
    117   /**
    118    * Runs given {@link RunnableEx} and re-throws exceptions using {@link RuntimeException}.
    119    */
    120   public static void runRethrow(RunnableEx runnable, String format, Object... args) {
    121     try {
    122       runnable.run();
    123     } catch (Throwable e) {
    124       String message = String.format(format, args);
    125       throw new RuntimeException(message, e);
    126     }
    127   }
    128 
    129   /**
    130    * Ensures that {@link Beans#isDesignTime()} returns <code>true</code> and runs given
    131    * {@link RunnableEx}.
    132    */
    133   public static void runDesignTime(RunnableEx runnable) throws Exception {
    134     boolean old_designTime = Beans.isDesignTime();
    135     try {
    136       Beans.setDesignTime(true);
    137       runnable.run();
    138     } finally {
    139       Beans.setDesignTime(old_designTime);
    140     }
    141   }
    142 
    143   /**
    144    * Ensures that {@link Beans#isDesignTime()} returns <code>true</code> and runs given
    145    * {@link RunnableEx}.
    146    */
    147   public static <T> T runDesignTime(RunnableObjectEx<T> runnable) throws Exception {
    148     boolean old_designTime = Beans.isDesignTime();
    149     try {
    150       Beans.setDesignTime(true);
    151       return runnable.runObject();
    152     } finally {
    153       Beans.setDesignTime(old_designTime);
    154     }
    155   }
    156 
    157   ////////////////////////////////////////////////////////////////////////////
    158   //
    159   // UI
    160   //
    161   ////////////////////////////////////////////////////////////////////////////
    162   /**
    163    * Runs given {@link RunnableEx} inside of UI thread, using {@link Display#syncExec(Runnable)}.
    164    *
    165    * @return <code>true</code> if {@link RunnableEx} was executed without any {@link Exception}.
    166    */
    167   public static boolean runLogUI(final RunnableEx runnable) {
    168     final boolean[] success = new boolean[1];
    169     Display.getDefault().syncExec(new Runnable() {
    170       @Override
    171     public void run() {
    172         success[0] = ExecutionUtils.runLog(runnable);
    173       }
    174     });
    175     return success[0];
    176   }
    177 
    178   /**
    179    * Runs given {@link RunnableEx} inside of UI thread, using {@link Display#syncExec(Runnable)}.
    180    */
    181   public static void runRethrowUI(final RunnableEx runnable) {
    182     Display.getDefault().syncExec(new Runnable() {
    183       @Override
    184     public void run() {
    185         ExecutionUtils.runRethrow(runnable);
    186       }
    187     });
    188   }
    189 
    190   /**
    191    * Runs given {@link RunnableEx} within UI thread using {@link Display#asyncExec(Runnable)}. Logs
    192    * a {@link Throwable} which may occur.
    193    */
    194   public static void runAsync(final RunnableEx runnable) {
    195     Display.getDefault().asyncExec(new Runnable() {
    196       @Override
    197     public void run() {
    198         ExecutionUtils.runLog(runnable);
    199       }
    200     });
    201   }
    202 
    203   /**
    204    * Runs given {@link RunnableEx} inside of UI thread, using {@link Display#syncExec(Runnable)}.
    205    */
    206   @SuppressWarnings("unchecked")
    207   public static <T> T runObjectUI(final RunnableObjectEx<T> runnable) {
    208     final Object[] result = new Object[1];
    209     runRethrowUI(new RunnableEx() {
    210       @Override
    211     public void run() throws Exception {
    212         result[0] = runObject(runnable);
    213       }
    214     });
    215     return (T) result[0];
    216   }
    217 
    218   /**
    219    * Runs given {@link RunnableEx} as {@link #runLog(RunnableEx)}, but using
    220    * {@link Display#asyncExec(Runnable)}.
    221    */
    222   public static void runLogLater(final RunnableEx runnable) {
    223     Display.getDefault().asyncExec(new Runnable() {
    224       @Override
    225     public void run() {
    226         ExecutionUtils.runLog(runnable);
    227       }
    228     });
    229   }
    230 
    231   ////////////////////////////////////////////////////////////////////////////
    232   //
    233   // Object
    234   //
    235   ////////////////////////////////////////////////////////////////////////////
    236   /**
    237    * Runs given {@link RunnableEx} and re-throws exceptions using {@link RuntimeException}.
    238    *
    239    * @return the {@link Object} returned by {@link RunnableEx#run()}.
    240    */
    241   public static <T> T runObject(RunnableObjectEx<T> runnable) {
    242     try {
    243       return runnable.runObject();
    244     } catch (Throwable e) {
    245       throw ReflectionUtils.propagate(e);
    246     }
    247   }
    248 
    249   /**
    250    * Runs given {@link RunnableEx} and re-throws exceptions using {@link RuntimeException}.
    251    *
    252    * @return the {@link Object} returned by {@link RunnableEx#run()}.
    253    */
    254   public static <T> T runObject(RunnableObjectEx<T> runnable, String format, Object... args) {
    255     try {
    256       return runnable.runObject();
    257     } catch (Throwable e) {
    258       String message = String.format(format, args);
    259       throw new Error(message, e);
    260     }
    261   }
    262 
    263   /**
    264    * Runs given {@link RunnableEx} and ignores exceptions.
    265    *
    266    * @return the {@link Object} returned by {@link RunnableEx#run()} or <code>defaultValue</code> if
    267    *         exception happened.
    268    */
    269   public static <T> T runObjectIgnore(RunnableObjectEx<T> runnable, T defaultValue) {
    270     try {
    271       return runnable.runObject();
    272     } catch (Throwable e) {
    273       return defaultValue;
    274     }
    275   }
    276 
    277   /**
    278    * Runs given {@link RunnableEx} and logs exceptions using {@link DesignerPlugin#log(Throwable)}.
    279    *
    280    * @return the {@link Object} returned by {@link RunnableEx#run()} or <code>defaultValue</code> if
    281    *         exception was logged.
    282    */
    283   public static <T> T runObjectLog(RunnableObjectEx<T> runnable, T defaultValue) {
    284     try {
    285       return runnable.runObject();
    286     } catch (Throwable e) {
    287       DesignerPlugin.log(e);
    288       return defaultValue;
    289     }
    290   }
    291 
    292 }
    293