package org.gudy.azureus2.ui.swt.shells;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Display;
import org.eclipse.swt.widgets.Monitor;
import org.eclipse.swt.widgets.Shell;
import org.gudy.azureus2.core3.util.AERunnable;
public class ShellSlider
{
private final boolean DEBUG = false;
private int STEP = 8;
private int PAUSE = 30;
private Shell shell;
private Rectangle shellBounds = null;
private Rectangle endBounds;
private final int direction;
private final boolean slideIn;
/**
* Slide In
*
* @param shell
* @param direction
* @param endBounds
*/
public ShellSlider(final Shell shell, int direction, final Rectangle endBounds) {
this.shell = shell;
this.endBounds = endBounds;
this.slideIn = true;
this.direction = direction;
if (shell == null || shell.isDisposed())
return;
Display display = shell.getDisplay();
display.syncExec(new Runnable() {
public void run() {
if (shell.isDisposed())
return;
switch (ShellSlider.this.direction) {
case SWT.UP:
default:
shell.setLocation(endBounds.x, endBounds.y);
Rectangle displayBounds = null;
try {
boolean ok = false;
Monitor[] monitors = shell.getDisplay().getMonitors();
for (int i = 0; i < monitors.length; i++) {
Monitor monitor = monitors[i];
displayBounds = monitor.getBounds();
if (displayBounds.contains(endBounds.x, endBounds.y)) {
ok = true;
break;
}
}
if (!ok) {
displayBounds = shell.getMonitor().getBounds();
}
} catch (Throwable t) {
displayBounds = shell.getDisplay().getBounds();
}
shellBounds = new Rectangle(endBounds.x, displayBounds.y
+ displayBounds.height, endBounds.width, 0);
break;
}
shell.setBounds(shellBounds);
shell.setVisible(true);
if (DEBUG)
System.out.println("Slide In: " + shell.getText());
}
});
}
/**
* Slide Out
*
* @param shell
* @param direction
*/
public ShellSlider(final Shell shell, int direction) {
this.shell = shell;
this.slideIn = false;
this.direction = direction;
if (DEBUG && canContinue())
shell.getDisplay().syncExec(new Runnable() {
public void run() {
System.out.println("Slide Out: " + shell.getText());
}
});
}
private boolean canContinue() {
if (shell == null || shell.isDisposed())
return false;
if (shellBounds == null)
return true;
//System.out.println((slideIn ? "In" : "Out") + ";" + direction + ";S:" + shellBounds + ";" + endBounds);
if (slideIn) {
if (direction == SWT.UP) {
return shellBounds.y > endBounds.y;
}
// TODO: Other directions
} else {
if (direction == SWT.RIGHT) {
// stop early, because some OSes have trim, and won't allow the window
// to go smaller than it.
return shellBounds.width > 10;
}
}
return false;
}
public void run() {
while (canContinue()) {
long lStartedAt = System.currentTimeMillis();
shell.getDisplay().syncExec(new AERunnable() {
public void runSupport() {
if (shell == null || shell.isDisposed()) {
return;
}
if (shellBounds == null) {
shellBounds = shell.getBounds();
}
int delta;
if (slideIn) {
switch (direction) {
case SWT.UP:
delta = Math.min(endBounds.height - shellBounds.height, STEP);
shellBounds.height += delta;
delta = Math.min(shellBounds.y - endBounds.y, STEP);
shellBounds.y -= delta;
break;
default:
break;
}
} else {
switch (direction) {
case SWT.RIGHT:
delta = Math.min(shellBounds.width, STEP);
shellBounds.width -= delta;
shellBounds.x += delta;
if (shellBounds.width == 0) {
shell.dispose();
return;
}
break;
default:
break;
}
}
shell.setBounds(shellBounds);
shell.update();
}
});
try {
long lDrawTime = System.currentTimeMillis() - lStartedAt;
long lSleepTime = PAUSE - lDrawTime;
if (lSleepTime < 15) {
double d = (lDrawTime + 15.0) / PAUSE;
PAUSE *= d;
STEP *= d;
lSleepTime = 15;
}
Thread.sleep(lSleepTime);
} catch (Exception e) {
}
}
}
}