Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Eclipse Projects » GEF » Adapt FlowLayoutEditPolicy for ToolbarLayout(or: How to limit FlowLayout to one row/column)
Adapt FlowLayoutEditPolicy for ToolbarLayout [message #547120] Thu, 15 July 2010 11:48 Go to next message
Chris  is currently offline Chris
Messages: 44
Registered: April 2010
Member
Hi,

this is a cross project question overlapping with draw2d. I basically want to have a FlowLayout in an ediable Node (i.e. the children should be manually movable by the user), that is limited to a single row/column filling the parent widget along the minor axis, just as the ToolbarLayout is. The trouble with the ToolbarLayout is, that I have not found any suitable LayoutEditPolicy for it. Vice versa I do not see any way to restrict the FlowLayout into a ToolbarLayout.

Any insights are greatly appreciated.

Regards,
Chris

[Updated on: Thu, 15 July 2010 11:56]

Report message to a moderator

Re: Adapt FlowLayoutEditPolicy for ToolbarLayout [message #547314 is a reply to message #547120] Fri, 16 July 2010 05:59 Go to previous message
Chris  is currently offline Chris
Messages: 44
Registered: April 2010
Member
Here is a very dirty Implementation of a FlowLayout rescricted to a single column/row. Had to copy and paste most of FlowLayout since the WorkingData class proviedes no protected/public constructor. Use, distribute and adapt as you see fit. If anyone implements a clean version, I'd be very interested.

/**
 * Copyright (c) 2010
 * by Christopher Kurtz
 * Media Computing Group
 * RWTH Aachen
 */
package edu.rwth.hci.codegestalt.view;

import java.util.Iterator;

import org.eclipse.draw2d.FlowLayout;
import org.eclipse.draw2d.IFigure;
import org.eclipse.draw2d.geometry.Dimension;
import org.eclipse.draw2d.geometry.Rectangle;

/**
 * Single Row/Column FlowLayout
 * @author Christopher Kurtz
 */
public class SingleRowFlowLayout extends FlowLayout {
	/**
	 * Holds the necessary information for layout calculations.
	 */
	protected class WorkingData {
		public int rowHeight, rowWidth, rowCount, rowX, rowY, maxWidth;
		public Rectangle bounds[], area;
		public IFigure row[];
	}
	
	protected WorkingData data = null;
	
	/**
	 * Constructs a SingleFlowLayout with horizontal orientation.
	 */
	public SingleRowFlowLayout(){
		super();
	}
	
	/**
	 * Constructs a SingleFlowLayout whose orientation is given in the input.
	 * @param isHorizontal <code>true</code> if the layout should be horizontal
	 */
	public SingleRowFlowLayout(boolean isHorizontal){
		super(isHorizontal);
	}
	
	/**
	 * Initializes the state of row data, which is internal to the layout process. 
	 */
	@Override
	protected void initRow() {
		data.rowX = 0;
		data.rowHeight = 0;
		data.rowWidth = 0;
		data.rowCount = 0;
	}

	/**
	 * Initializes state data for laying out children, based on the Figure given as input.
	 *
	 * @param parent the parent figure
	 * @since 2.0 
	 */
	@Override
	protected void initVariables(IFigure parent) {
		data.row = new IFigure[parent.getChildren().size()];
		data.bounds = new Rectangle[data.row.length];
		data.maxWidth = data.area.width;
	}
	
	/**
	 * @see org.eclipse.draw2d.LayoutManager#layout(IFigure)
	 */
	@SuppressWarnings("unchecked")
	@Override
	public void layout(IFigure parent) {
		data = new WorkingData();
		Rectangle relativeArea = parent.getClientArea();
		data.area = transposer.t(relativeArea);

		Iterator iterator = parent.getChildren().iterator();
		int dx;

		//Calculate the hints to be passed to children
		int wHint = -1;
		int hHint = -1;
		if (isHorizontal())
			wHint = parent.getClientArea().width;
		else
			hHint = parent.getClientArea().height;

		initVariables(parent);
		initRow();
		int i = 0; 
		while (iterator.hasNext()) {
			IFigure f = (IFigure)iterator.next();
			Dimension pref = transposer.t(getChildSize(f, wHint, hHint));
			Rectangle r = new Rectangle(0, 0, pref.width, pref.height);

			if (data.rowCount > 0) {
				if (data.rowWidth + pref.width > data.maxWidth)
					layoutRow(parent);
			}
			r.x = data.rowX;
			r.y = data.rowY;
			dx = r.width + getMinorSpacing();
			data.rowX += dx;
			data.rowWidth += dx;
			//data.rowHeight = Math.max(data.rowHeight, r.height);
			if (isHorizontal())
				data.rowHeight = parent.getClientArea().height;
			else
				data.rowHeight = parent.getClientArea().width;
			data.row [data.rowCount] = f;
			data.bounds[data.rowCount] = r;
			data.rowCount++;
			i++;
		}
		if (data.rowCount != 0)
			layoutRow(parent);
		data = null;
	}

	/**
	 * Layouts one row of components. This is done based on the layout's orientation, minor 
	 * alignment and major alignment.
	 *
	 * @param parent the parent figure
	 * @since 2.0
	 */
	@Override
	protected void layoutRow(IFigure parent) {
		int majorAdjustment = 0;
		int minorAdjustment = 0;
		int correctMajorAlignment = majorAlignment;
		int correctMinorAlignment = minorAlignment;

		majorAdjustment = data.area.width - data.rowWidth + getMinorSpacing();
		
		switch (correctMajorAlignment) {
			case ALIGN_LEFTTOP: 
				majorAdjustment = 0;
				break;
			case ALIGN_CENTER:
				majorAdjustment /= 2;
				break;
			case ALIGN_RIGHTBOTTOM:
				break;
		}

		for (int j = 0; j < data.rowCount; j++) {
			if (fill) {
				data.bounds[j].height = data.rowHeight;	
			} else {
				minorAdjustment = data.rowHeight - data.bounds[j].height;
				switch (correctMinorAlignment) {
					case ALIGN_LEFTTOP: 
						minorAdjustment = 0;
						break;
					case ALIGN_CENTER:
						minorAdjustment /= 2;
					break;
					case ALIGN_RIGHTBOTTOM:
						break;
				}
				data.bounds[j].y += minorAdjustment;
			}
			data.bounds[j].x += majorAdjustment;
			
			setBoundsOfChild(parent, data.row[j], transposer.t(data.bounds[j]));
		}
		data.rowY += getMajorSpacing() + data.rowHeight;
		initRow();
	}
}
Previous Topic:Can't show a popup during target feedback
Next Topic:Subclass of PolylineConnection instances are not visible
Goto Forum:
  


Current Time: Thu Aug 28 21:33:16 EDT 2014

Powered by FUDForum. Page generated in 0.02513 seconds