blob: eba8398ecabc0254f473db7f4bc33160c03988d3 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2010, 2018 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
******************************************************************************/
package org.eclipse.e4.ui.workbench.addons.minmax;
import org.eclipse.e4.ui.model.application.ui.menu.MToolControl;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.MouseAdapter;
import org.eclipse.swt.events.MouseEvent;
import org.eclipse.swt.events.MouseTrackListener;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.graphics.Rectangle;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Control;
import org.eclipse.swt.widgets.Layout;
/**
*
*/
public class TrimPaneLayout extends Layout {
private static int BORDER_WIDTH = 4;
private static final Rectangle EMPTY_RECT = new Rectangle(0, 0, 0, 0);
private int fixedCorner;
public Rectangle hSizingRect = EMPTY_RECT;
public Rectangle vSizingRect = EMPTY_RECT;
public Rectangle cornerRect = EMPTY_RECT;
private Rectangle clientRect = EMPTY_RECT;
private boolean resizeInstalled = false;
private static int NOT_SIZING = 0;
private static int HORIZONTAL_SIZING = 1;
private static int VERTICAL_SIZING = 2;
private static int CORNER_SIZING = 3;
int trackState = SWT.NONE;
protected Point curPos;
private MToolControl toolControl;
public TrimPaneLayout(MToolControl toolControl, int barSide) {
this.toolControl = toolControl;
this.fixedCorner = barSide;
}
@Override
protected Point computeSize(Composite composite, int wHint, int hHint, boolean flushCache) {
return new Point(600, 400);
}
@Override
protected void layout(Composite composite, boolean flushCache) {
installResize(composite);
if (composite.getChildren().length != 1) {
return;
}
if (fixedCorner == SWT.NONE) {
return;
}
Rectangle bounds = composite.getBounds();
if (isFixed(SWT.TOP)) {
if (isFixed(SWT.RIGHT)) {
hSizingRect = new Rectangle(0, 0, BORDER_WIDTH, bounds.height - BORDER_WIDTH);
vSizingRect = new Rectangle(BORDER_WIDTH, bounds.height - BORDER_WIDTH,
bounds.width - BORDER_WIDTH, BORDER_WIDTH);
cornerRect = new Rectangle(0, bounds.height - BORDER_WIDTH, BORDER_WIDTH,
BORDER_WIDTH);
clientRect = new Rectangle(BORDER_WIDTH, 0, bounds.width - BORDER_WIDTH,
bounds.height - BORDER_WIDTH);
} else {
hSizingRect = new Rectangle(bounds.width - BORDER_WIDTH, 0, BORDER_WIDTH,
bounds.height - BORDER_WIDTH);
vSizingRect = new Rectangle(0, bounds.height - BORDER_WIDTH, bounds.width
- BORDER_WIDTH, BORDER_WIDTH);
cornerRect = new Rectangle(bounds.width - BORDER_WIDTH, bounds.height
- BORDER_WIDTH, BORDER_WIDTH, BORDER_WIDTH);
clientRect = new Rectangle(0, 0, bounds.width - BORDER_WIDTH, bounds.height
- BORDER_WIDTH);
}
} else if (isFixed(SWT.BOTTOM)) {
if (isFixed(SWT.RIGHT)) {
hSizingRect = new Rectangle(0, BORDER_WIDTH, BORDER_WIDTH, bounds.height
- BORDER_WIDTH);
vSizingRect = new Rectangle(BORDER_WIDTH, 0, bounds.width - BORDER_WIDTH,
BORDER_WIDTH);
cornerRect = new Rectangle(0, 0, BORDER_WIDTH, BORDER_WIDTH);
clientRect = new Rectangle(BORDER_WIDTH, BORDER_WIDTH, bounds.width - BORDER_WIDTH,
bounds.height - BORDER_WIDTH);
} else {
hSizingRect = new Rectangle(bounds.width - BORDER_WIDTH, BORDER_WIDTH,
BORDER_WIDTH, bounds.height - BORDER_WIDTH);
vSizingRect = new Rectangle(0, 0, bounds.width - BORDER_WIDTH, BORDER_WIDTH);
cornerRect = new Rectangle(bounds.width - BORDER_WIDTH, 0, BORDER_WIDTH,
BORDER_WIDTH);
clientRect = new Rectangle(0, BORDER_WIDTH, bounds.width - BORDER_WIDTH,
bounds.height - BORDER_WIDTH);
}
}
Control child = composite.getChildren()[0];
child.setBounds(clientRect);
}
private void installResize(final Composite composite) {
if (resizeInstalled) {
return;
}
composite.addMouseMoveListener(e -> {
Point p = e.display.getCursorLocation();
if (trackState == NOT_SIZING) {
setCursor(composite, new Point(e.x, e.y));
} else if (trackState == HORIZONTAL_SIZING) {
dragHorizontal(composite, p);
} else if (trackState == VERTICAL_SIZING) {
dragVertical(composite, p);
} else if (trackState == CORNER_SIZING) {
dragCorner(composite, p);
}
});
composite.addMouseListener(new MouseAdapter() {
@Override
public void mouseUp(MouseEvent e) {
composite.setCapture(false);
// Persist the current size
Point size = composite.getSize();
toolControl.getPersistedState()
.put(TrimStack.STATE_XSIZE, Integer.toString(size.x));
toolControl.getPersistedState()
.put(TrimStack.STATE_YSIZE, Integer.toString(size.y));
trackState = NOT_SIZING;
}
@Override
public void mouseDown(MouseEvent e) {
Point p = new Point(e.x, e.y);
if (hSizingRect.contains(p)) {
curPos = e.display.getCursorLocation();
trackState = HORIZONTAL_SIZING;
composite.setCapture(true);
} else if (vSizingRect.contains(p)) {
curPos = e.display.getCursorLocation();
trackState = VERTICAL_SIZING;
composite.setCapture(true);
} else if (cornerRect.contains(p)) {
curPos = e.display.getCursorLocation();
trackState = CORNER_SIZING;
composite.setCapture(true);
}
}
});
composite.addMouseTrackListener(MouseTrackListener.mouseExitAdapter(e -> {
Composite comp = (Composite) e.widget;
comp.setCursor(null);
}));
resizeInstalled = true;
}
/**
* @param p
*/
protected void setCursor(Composite composite, Point p) {
if (hSizingRect.contains(p)) {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZEWE));
} else if (vSizingRect.contains(p)) {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZENS));
} else if (cornerRect.contains(p)) {
if (isFixed(SWT.TOP)) {
if (isFixed(SWT.RIGHT)) {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZESW));
} else {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZESE));
}
} else if (isFixed(SWT.BOTTOM)) {
if (isFixed(SWT.RIGHT)) {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZESE));
} else {
composite.setCursor(composite.getDisplay().getSystemCursor(SWT.CURSOR_SIZESW));
}
}
} else {
composite.setCursor(null);
}
}
protected void dragCorner(Composite composite, Point p) {
int dx = p.x - curPos.x;
int dy = p.y - curPos.y;
Rectangle bounds = composite.getBounds();
if (isFixed(SWT.RIGHT)) {
bounds.x += dx;
bounds.width -= dx;
} else {
bounds.width += dx;
}
if (isFixed(SWT.BOTTOM)) {
bounds.y += dy;
bounds.height -= dy;
} else {
bounds.height += dy;
}
composite.setBounds(bounds);
composite.getDisplay().update();
curPos = p;
}
protected void dragVertical(Composite composite, Point p) {
int dy = p.y - curPos.y;
Rectangle bounds = composite.getBounds();
if (isFixed(SWT.BOTTOM)) {
bounds.y += dy;
bounds.height -= dy;
} else {
bounds.height += dy;
}
composite.setBounds(bounds);
composite.getDisplay().update();
curPos = p;
}
protected void dragHorizontal(Composite composite, Point p) {
int dx = p.x - curPos.x;
Rectangle bounds = composite.getBounds();
if (isFixed(SWT.RIGHT)) {
bounds.x += dx;
bounds.width -= dx;
} else {
bounds.width += dx;
}
composite.setBounds(bounds);
composite.getDisplay().update();
curPos = p;
}
private boolean isFixed(int swtSide) {
return (fixedCorner & swtSide) != 0;
}
}