package abbot.tester.swt;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.ScrollBar;
import org.eclipse.swt.widgets.Scrollable;
import abbot.Log;
import com.windowtester.runtime.WT;
import com.windowtester.runtime.swt.internal.abbot.SWTWorkarounds;
import com.windowtester.runtime.swt.internal.operation.SWTDisplayLocation;
import com.windowtester.runtime.swt.internal.operation.SWTMouseOperation;
/**
* Provides widget-specific actions for testing a scrollBar.
*
* @version $Id: ScrollBarTester.java,v 1.3 2007-11-27 17:17:39 pq Exp $
*/
public class ScrollBarTester extends WidgetTester {
public static final String copyright = "Licensed Materials -- Property of IBM\n"+
"(c) Copyright International Business Machines Corporation, 2003\nUS Government "+
"Users Restricted Rights - Use, duplication or disclosure restricted by GSA "+
"ADP Schedule Contract with IBM Corp.";
/**
* These getter methods return a particular property of the given widget.
* @see the corresponding member function in class Widget
*/
/* Begin getters */
/**
* Proxy for {@link ScrollBar#getEnabled()}.
* <p/>
* @param bar the bar under test.
* @return the enabled state.
*/
public boolean getEnabled(final ScrollBar bar) {
Boolean result = (Boolean) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return Boolean.valueOf(bar.getEnabled());
}
});
return result.booleanValue();
}
/**
* Proxy for {@link ScrollBar#getIncrement()}.
* <p/>
* @param bar the bar under test.
* @return the increment.
*/
public int getIncrement(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getIncrement());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getMaximum()}.
* <p/>
* @param bar the bar under test.
* @return the maximum.
*/
public int getMaximum(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getMaximum());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getMinimum()}.
* <p/>
* @param bar the bar under test.
* @return the minimum.
*/
public int getMinimum(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getMinimum());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getPageIncrement()}.
* <p/>
* @param bar the bar under test.
* @return the page increment.
*/
public int getPageIncrement(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getPageIncrement());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getParent()}.
* <p/>
* @param bar the bar under test.
* @return the parent.
*/
public Scrollable getParent(final ScrollBar bar) {
Scrollable result = (Scrollable) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return bar.getParent();
}
});
return result;
}
/**
* Proxy for {@link ScrollBar#getSelection()}.
* <p/>
* @param bar the bar under test.
* @return the selection.
*/
public int getSelection(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getSelection());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getSize()}.
* <p/>
* @param bar the bar under test.
* @return the point describing the size.
*/
public Point getSize(final ScrollBar bar) {
Point result = (Point) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return bar.getSize();
}
});
return result;
}
/**
* Proxy for {@link ScrollBar#getThumb()}.
* <p/>
* @param bar the bar under test.
* @return the thumb value.
*/
public int getThumb(final ScrollBar bar) {
Integer result = (Integer) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return new Integer(bar.getThumb());
}
});
return result.intValue();
}
/**
* Proxy for {@link ScrollBar#getVisible()}.
* <p/>
* @param bar the bar under test.
* @return the visible state.
*/
public boolean getVisible(final ScrollBar bar) {
Boolean result = (Boolean) Robot.syncExec(bar.getDisplay(), new RunnableWithResult() {
public Object runWithResult() {
return Boolean.valueOf(bar.getVisible());
}
});
return result.booleanValue();
}
/* End getters */
// platform-dependent fields based on the rendering of the scrollbar
public final static int BUTTON_SIZE = 17;
public final static int THUMB_OFFSET = 2;
/**
* Scroll the given amount, where amount==the number of
* times the arrow is pressed. Positive amounts scroll down
* for vertical scrollbars and right for horizontal ones.
*/
public void actionScroll(final ScrollBar bar, final int amount){
actionFocus(bar);
final Rectangle bounds = SWTWorkarounds.getBounds(bar);
// convert bounds to global bounds
Point p = getParent(bar).toDisplay(bounds.x,bounds.y);
bounds.x = p.x;
bounds.y = p.y;
Log.debug("BOUNDS: "+bounds);
if(amount<0){
mouseMove2(bounds.x+BUTTON_SIZE/2,bounds.y+BUTTON_SIZE/2);
for(int i=amount; i<=0; i++){
// mousePress2(SWT.BUTTON1);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1).execute();
}
}
else if(amount>0){
mouseMove2( bounds.x+bounds.width - BUTTON_SIZE/2,
bounds.y+bounds.height - BUTTON_SIZE/2);
for(int i=0; i<amount;i++){
// mousePress2(SWT.BUTTON1);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1).execute();
}
}
actionWaitForIdle(bar.getDisplay());
}
/**
* Page the given amount, where amount==# of times that the
* bar is clicked in the page area
**/
public synchronized void actionPageScroll(final ScrollBar bar, int amount){
actionFocus(bar);
final Rectangle bounds = SWTWorkarounds.getBounds(bar);
// convert bounds to global bounds
Point p = getParent(bar).toDisplay(bounds.x,bounds.y);
bounds.x = p.x;
bounds.y = p.y;
//System.out.println("BOUNDS: "+bounds);
int style = getStyle(bar);
if(amount<0){
if((style&SWT.HORIZONTAL)==SWT.HORIZONTAL)
mouseMove2(bounds.x+BUTTON_SIZE,bounds.y+BUTTON_SIZE/2);
else
mouseMove2(bounds.x+BUTTON_SIZE/2,bounds.y+BUTTON_SIZE);
for(int i=0; i<amount;i++){
// mousePress2(SWT.BUTTON1);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1).execute();
}
}
else if(amount > 0){
if((style&SWT.HORIZONTAL)==SWT.HORIZONTAL)
mouseMove2( bounds.x+bounds.width - BUTTON_SIZE,
bounds.y+bounds.height - BUTTON_SIZE/2);
else
mouseMove( bounds.x+bounds.width - BUTTON_SIZE/2,
bounds.y+bounds.height - BUTTON_SIZE);
for(int i=0; i<amount;i++){
// mousePress2(SWT.BUTTON1);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1).execute();
}
}
actionWaitForIdle(bar.getDisplay());
}
/**
* Sets the selection to the given value, or as close as possible, by dragging
* the slider. The smaller the ratio of bar.getThumb()/(bar.getMaximum()-bar.getMinimum()),
* the less accurate this method is.
**/
// TODO FIXME method loses the lock now between calls to syncExec, so
// we need to do everything in one big syncExec block
public synchronized void actionScrollSetSelection(final ScrollBar bar, final int val){
actionFocus(bar);
final Rectangle bounds = SWTWorkarounds.getBounds(bar);
// convert bounds to global bounds
Point p = getParent(bar).toDisplay(bounds.x,bounds.y);
bounds.x = p.x;
bounds.y = p.y;
// get info about current selection
int style = getStyle(bar);
int selection = getSelection(bar);
int increment = getIncrement(bar);
int minimum = getMinimum(bar);
int maximum = getMaximum(bar);
int thumb = getThumb(bar);
actionWaitForIdle(bar.getDisplay());
int setTo = val;
if(setTo<minimum)setTo = minimum;
else if(setTo>maximum-thumb)setTo = maximum-thumb;
if((style&SWT.HORIZONTAL)==SWT.HORIZONTAL){
double thumbEdge = (double)((double)selection/(double)(maximum-minimum));
double thumbWidth = (double)((double)thumb/(double)(maximum-minimum));
// double setEdge = (double)((double)setTo/(double)(maximum-minimum));
double delta = (double)((double)increment/(double)(maximum-minimum));
int stripWidth = bounds.width - 2*BUTTON_SIZE;
int thumbLocPixels = (int)(thumbEdge*stripWidth);
int thumbWidthPixels = (int)(thumbWidth*stripWidth);
// int setEdgePixels = (int)(setEdge*stripWidth);
int deltaPixels = (int)(delta*stripWidth+1);
//System.out.println(deltaPixels);
//System.out.println("THUMB:"+thumb+" MAX: "+max+"SELECTION:"+selection+" THUMBEDGE:"+thumbEdge+" stripWidth:"+stripWidth+" THUMBLOC: "+thumbLoc);
Point thumbPoint = new Point(bounds.x+BUTTON_SIZE+thumbLocPixels+thumbWidthPixels/2,bounds.y+bounds.height/2);
Point offset = new Point(0,0);
// Point moveTo = new Point(bounds.x+BUTTON_SIZE+setEdgePixels+thumbWidthPixels/2,bounds.y+bounds.height/2);
mouseMove2(thumbPoint.x,thumbPoint.y);
// mousePress(SWT.BUTTON1);
// mouseMove(moveTo.x,moveTo.y);
// mouseRelease(SWT.BUTTON1);
actionWaitForIdle(bar.getDisplay());
int oldSelection = setTo;
if(setTo<selection){
while(true){
selection = getSelection(bar);
if(oldSelection==selection){
//System.out.println("Exiting b/c oldSelection==selection");
break;
}
if(selection<=setTo){
//System.out.println("Exiting b/c selection<=setTo");
break;
}
offset.x-=deltaPixels;
// mousePress2(SWT.BUTTON1);
// mouseMove2(thumbPoint.x+offset.x,thumbPoint.y+offset.y);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1)
.at(new SWTDisplayLocation().offset(thumbPoint))
.dragTo(new SWTDisplayLocation().offset(thumbPoint.x + offset.x, thumbPoint.y + offset.y))
.execute();
actionWaitForIdle(bar.getDisplay());
oldSelection = selection;
}
}
else if(setTo>selection){
while(true){
selection = getSelection(bar);
if(oldSelection==selection)
break;
if(selection>=setTo)
break;
offset.x+=deltaPixels;
// mousePress2(SWT.BUTTON1);
// mouseMove2(thumbPoint.x+offset.x,thumbPoint.y+offset.y);
// mouseRelease2(SWT.BUTTON1);
new SWTMouseOperation(WT.BUTTON1)
.at(new SWTDisplayLocation().offset(thumbPoint))
.dragTo(new SWTDisplayLocation().offset(thumbPoint.x+offset.x, thumbPoint.y+offset.y))
.execute();
actionWaitForIdle(bar.getDisplay());
oldSelection = selection;
}
}
}
else{// style==SWT.VERTICAL
double thumbEdge = (double)((double)selection/(double)(maximum-minimum));
double thumbWidth = (double)((double)thumb/(double)(maximum-minimum));
double delta = (double)((double)increment/(double)(maximum-minimum));
int stripWidth = bounds.height - 2*BUTTON_SIZE;
int thumbLocPixels = (int)(thumbEdge*stripWidth);
int thumbWidthPixels = (int)(thumbWidth*stripWidth);
int deltaPixels = (int)(delta*stripWidth+1);
//System.out.println("THUMB:"+thumb+" MAX: "+max+"SELECTION:"+selection+" THUMBEDGE:"+thumbEdge+" stripWidth:"+stripWidth+" THUMBLOC: "+thumbLoc);
Point thumbPoint = new Point(bounds.x+bounds.width/2,bounds.y+BUTTON_SIZE+thumbLocPixels+thumbWidthPixels/2);
Point offset = new Point(0,0);
mouseMove(thumbPoint.x,thumbPoint.y);
actionWaitForIdle(bar.getDisplay());
int oldSelection = setTo;
if(setTo<selection){
while(true){
selection = getSelection(bar);
if(oldSelection==selection){
//System.out.println("Exiting b/c oldSelection==selection");
break;
}
if(selection<=setTo){
//System.out.println("Exiting b/c selection<=setTo");
break;
}
offset.y-=deltaPixels;
mousePress2(SWT.BUTTON1);
mouseMove2(thumbPoint.x+offset.x,thumbPoint.y+offset.y);
mouseRelease2(SWT.BUTTON1);
actionWaitForIdle(bar.getDisplay());
oldSelection = selection;
}
}
else if(setTo>selection){
while(true){
selection = getSelection(bar);
//System.out.println((thumbPoint.x+offset.x)+","+(thumbPoint.y+offset.y));
//System.out.println("setTo="+setTo+" selection="+selection);
if(oldSelection==selection){
//System.out.println("Exiting b/c oldSelection==selection");
break;
}
if(selection>=setTo){
//System.out.println("Exiting b/c selection>=setTo");
break;
}
offset.y+=deltaPixels;
mousePress2(SWT.BUTTON1);
//actionDelay(500);
mouseMove2(thumbPoint.x+offset.x,thumbPoint.y+offset.y);
mouseRelease2(SWT.BUTTON1);
//actionDelay(500);
actionWaitForIdle(bar.getDisplay());
oldSelection = selection;
}
}
}
// make sure that we actually changed the scroll position
selection = getSelection(bar);
// int rangeMin = setTo - increment;
// int rangeMax = setTo + increment;
// if( !(selection>=rangeMin && selection<=rangeMax) )
// Log.warn("Failed to set scrollbar appropriately (setTo="+setTo+" selection="+selection);
actionWaitForIdle(bar.getDisplay());
}
}