use of edu.mit.blocks.renderable.RenderableBlock in project openblocks by mikaelhg.
the class BlockStackSorterUtil method getSaveNode.
public Node getSaveNode(Document document) {
Element pageElement = document.createElement("Page");
pageElement.setAttribute("page-name", getPageName());
pageElement.setAttribute("page-color", getPageColor().getRed() + " " + getPageColor().getGreen() + " " + getPageColor().getBlue());
pageElement.setAttribute("page-width", String.valueOf((int) getAbstractWidth()));
if (fullview) {
pageElement.setAttribute("page-infullview", "yes");
} else {
pageElement.setAttribute("page-infullview", "no");
}
if (pageDrawer != null) {
pageElement.setAttribute("page-drawer", pageDrawer);
}
if (pageId != null) {
pageElement.setAttribute("page-id", pageId);
}
// retrieve save strings of blocks within this Page
Collection<RenderableBlock> blocks = this.getBlocks();
if (blocks.size() > 0) {
Element pageBlocksElement = document.createElement("PageBlocks");
for (RenderableBlock rb : blocks) {
pageBlocksElement.appendChild(rb.getSaveNode(document));
}
pageElement.appendChild(pageBlocksElement);
}
return pageElement;
}
use of edu.mit.blocks.renderable.RenderableBlock in project openblocks by mikaelhg.
the class MiniMap method blockDropped.
/**
* @param block
* @modifies block
* @effects Set block to whatever page it is on is one exist.
* Otherwise, set it to whatever Widget is currently underneath
* it.
*/
public void blockDropped(RenderableBlock block) {
// TODO - djwendel - this needs to choose the widget of the top block of the stack, not the widget under the block necessarily
Point location = block.getLocation();
if (location.getY() <= 0) {
location.setLocation(location.getX(), 1);
}
// find page that it should drop on. w could be null. so watch out.
WorkspaceWidget w = workspace.getWidgetAt(location);
for (Page page : this.blockCanvas.getPages()) {
if (page.contains(SwingUtilities.convertPoint(block.getParent(), location, page.getJComponent()))) {
w = page;
}
}
/* before dropping, check if any connected blocks were dropped elsewhere.
if they were, drop there instead. (this relies on the fact that stacks
of blocks are dropped bottom-first, so the place to check is at the
socket blocks. If stacks were dropped top-first, this would check the
blocks up the stack rather than down the stack. TODO - this doesn't
always work, because there can be multiple "branches" that might get
dropped on different places. Need to find a way to drop according the
widget of the top block of the stack...*/
RenderableBlock socketBlock;
for (BlockConnector con : (workspace.getEnv().getBlock(block.getBlockID()).getSockets())) {
socketBlock = block.getWorkspace().getEnv().getRenderableBlock(con.getBlockID());
if (socketBlock != null) {
w = socketBlock.getParentWidget();
}
}
w.blockDropped(block);
this.repaint();
}
use of edu.mit.blocks.renderable.RenderableBlock in project openblocks by mikaelhg.
the class InfixBlockShape method makeBottomSide.
/**
* Overrided from BlockShape.
* Takes into account the need to resize the dimensions of an infix block for various cases.
*/
@Override
protected void makeBottomSide() {
// Reset the maximum X-coordinate so the infix block can resize if you remove blocks within it
maxX = 0;
// start bottom-right
setEndPoint(gpBottom, botLeftCorner, topLeftCorner, true);
// curve down and right
BlockShapeUtil.cornerTo(gpBottom, botLeftCorner, botRightCorner, blockCornerRadius);
// / BOTTOM SOCKETS
// for each socket in the iterator
// need to use this to determine which socket we're on
int socketCounter = 0;
for (BlockConnector curSocket : block.getSockets()) {
// if bottom socket
if (curSocket.getPositionType() == BlockConnector.PositionType.BOTTOM) {
// move away from bottom left corner
if (socketCounter > 0) {
gpBottom.lineTo((float) gpBottom.getCurrentPoint().getX() + BOTTOM_SOCKET_MIDDLE_SPACER, (float) gpBottom.getCurrentPoint().getY());
} else {
gpBottom.lineTo((float) gpBottom.getCurrentPoint().getX() + BOTTOM_SOCKET_SIDE_SPACER, (float) gpBottom.getCurrentPoint().getY());
}
// move down so bevel doesn't screw up from connecting infinitely sharp corner
// as occurs from a curved port
BlockShapeUtil.lineToRelative(gpBottom, 0, -0.1f);
if (curSocket.getBlockID() == Block.NULL) {
// draw first socket - up left side
Point2D leftSocket = BCS.addDataSocketUp(gpBottom, curSocket.getKind(), true);
rb.updateSocketPoint(curSocket, leftSocket);
// System.out.println("socket poitn: "+rb.getSocketPoint(curSocket));
// System.out.println("socket poitn leftsocket: "+leftSocket);
// draw left standard empty socket space - top side
gpBottom.lineTo((float) gpBottom.getCurrentPoint().getX() + BOTTOM_SOCKET_SIDE_SPACER, (float) gpBottom.getCurrentPoint().getY());
// draw first socket - down right side
BCS.addDataSocket(gpBottom, curSocket.getKind(), false);
// rb.updateSocketPoint(curSocket, rightSocket);
} else {
// there is a connected block
Block connectedBlock = rb.getWorkspace().getEnv().getBlock(curSocket.getBlockID());
RenderableBlock connectedRBlock = rb.getWorkspace().getEnv().getRenderableBlock(curSocket.getBlockID());
// calculate and update the new socket point
// update the socket point of this cursocket which should now adopt the plug socket point of its
// connected block since we're also adopting the left side of its shape
// Use coordinates when the zoom level is 1.0 to calculate socket point
double unzoomX = connectedRBlock.getSocketPixelPoint(connectedBlock.getPlug()).getX() / connectedRBlock.getZoom();
double unzoomY = connectedRBlock.getSocketPixelPoint(connectedBlock.getPlug()).getY() / connectedRBlock.getZoom();
Point2D connectedBlockSocketPoint = new Point2D.Double(unzoomX, unzoomY);
Point2D currentPoint = gpBottom.getCurrentPoint();
double newX = connectedBlockSocketPoint.getX() + Math.abs(connectedBlockSocketPoint.getX() - currentPoint.getX());
double newY = connectedBlockSocketPoint.getY() + Math.abs(connectedRBlock.getBlockHeight() / connectedRBlock.getZoom() - currentPoint.getY());
rb.updateSocketPoint(curSocket, new Point2D.Double(newX, newY));
BlockShape connectedBlockShape = rb.getWorkspace().getEnv().getRenderableBlock(curSocket.getBlockID()).getBlockShape();
// append left side of connected block
appendPath(gpBottom, connectedBlockShape.getLeftSide(), false);
// append right side of connected block (more complicated)
if (connectedBlock.getNumSockets() == 0 || connectedBlock.isInfix()) {
// append top side of connected block
appendPath(gpBottom, connectedBlockShape.getTopSide(), false);
appendPath(gpBottom, connectedBlockShape.getRightSide(), false);
} else {
// iterate through the sockets of the connected block, checking if
// it has blocks connected to them
appendRightSidePath(gpBottom, connectedBlock, connectedBlockShape);
}
// Updates the maximum X-coordinate and sets the current point to maxX
if (maxX < (float) gpBottom.getCurrentPoint().getX()) {
maxX = (float) gpBottom.getCurrentPoint().getX();
}
gpBottom.lineTo(maxX, (float) gpBottom.getCurrentPoint().getY());
}
// bump down so bevel doesn't screw up
BlockShapeUtil.lineToRelative(gpBottom, 0, 0.1f);
// // draw RIGHT to create divider ////
if (socketCounter < block.getNumSockets() - 1) {
// need to add the width of the block label. warning: this assumes that there is only one block label
gpBottom.lineTo((float) gpBottom.getCurrentPoint().getX() + BOTTOM_SOCKET_MIDDLE_SPACER + rb.accomodateLabelsWidth(), (float) gpBottom.getCurrentPoint().getY());
} else {
gpBottom.lineTo((float) gpBottom.getCurrentPoint().getX() + BOTTOM_SOCKET_SIDE_SPACER, (float) gpBottom.getCurrentPoint().getY());
}
socketCounter++;
}
}
// curve right and up
BlockShapeUtil.cornerTo(gpBottom, botRightCorner, topRightCorner, blockCornerRadius);
// end bottom
setEndPoint(gpBottom, botRightCorner, topRightCorner, false);
}
use of edu.mit.blocks.renderable.RenderableBlock in project openblocks by mikaelhg.
the class BlockLinkChecker method getWeakLink.
/**
* NOTE: ALWAYS prefer BlockLinkChecker.getLink over this method.
*
* Checks to see if a <code>RenderableBlock</code>s can connect
* to other <code>RenderableBlock</code>s, implying that rblock1
* has at least one <code>BlockConnector</code>s that satisfies at
* least one of the <code>LinkRule</code>s.
*
* Does not require close proximity.
*
* @param workspace The workspace in use
* @param rblock1 one of the blocks to check
* @param otherBlocks the other blocks to check against
* @return a <code>BlockLink</code> object that gives the two closest matching <code>BlockConnector</code>s in these blocks,
* or null if no such matching exists.
*/
public static BlockLink getWeakLink(Workspace workspace, RenderableBlock rblock1, Iterable<RenderableBlock> otherBlocks) {
Block block1 = workspace.getEnv().getBlock(rblock1.getBlockID());
BlockConnector closestSocket1 = null;
BlockConnector closestSocket2 = null;
Block closestBlock2 = null;
double closestDistance = Double.POSITIVE_INFINITY;
double currentDistance;
for (RenderableBlock rblock2 : otherBlocks) {
BlockConnector currentPlug = getPlugEquivalent(block1);
Block block2 = workspace.getEnv().getBlock(rblock2.getBlockID());
if (block1.equals(block2) || !rblock1.isVisible() || !rblock2.isVisible()) {
continue;
}
Point2D currentPlugPoint = null;
Point2D currentSocketPoint = null;
if (currentPlug != null) {
currentPlugPoint = getAbsoluteSocketPoint(rblock1, currentPlug);
for (BlockConnector currentSocket : getSocketEquivalents(block2)) {
currentSocketPoint = getAbsoluteSocketPoint(rblock2, currentSocket);
currentDistance = currentPlugPoint.distance(currentSocketPoint);
if ((currentDistance < closestDistance) && checkRules(block1, block2, currentPlug, currentSocket)) {
closestBlock2 = block2;
closestSocket1 = currentPlug;
closestSocket2 = currentSocket;
closestDistance = currentDistance;
}
}
}
currentPlug = getPlugEquivalent(block2);
if (currentPlug != null) {
currentPlugPoint = getAbsoluteSocketPoint(rblock2, currentPlug);
for (BlockConnector currentSocket : getSocketEquivalents(block1)) {
currentSocketPoint = getAbsoluteSocketPoint(rblock1, currentSocket);
currentDistance = currentPlugPoint.distance(currentSocketPoint);
if ((currentDistance < closestDistance) && checkRules(block1, block2, currentSocket, currentPlug)) {
closestBlock2 = block2;
closestSocket1 = currentSocket;
closestSocket2 = currentPlug;
closestDistance = currentDistance;
}
}
}
}
if (closestSocket1 == null) {
return null;
}
return BlockLink.getBlockLink(workspace, block1, closestBlock2, closestSocket1, closestSocket2);
}
use of edu.mit.blocks.renderable.RenderableBlock in project openblocks by mikaelhg.
the class BlockLinkChecker method getLink.
/**
* Checks to see if a <code>RenderableBlock</code>s can connect to other <code>RenderableBlock</code>s.
* This would mean that they have <code>BlockConnector</code>s that satisfy at least one of the <code>LinkRule</code>s,
* and that these sockets are in close proximity.
* @param workspace The workspace in use
* @param rblock1 one of the blocks to check
* @param otherBlocks the other blocks to check against
* @return a <code>BlockLink</code> object that gives the two closest matching <code>BlockConnector</code>s in these blocks,
* or null if no such matching exists.
*/
public static BlockLink getLink(Workspace workspace, RenderableBlock rblock1, Iterable<RenderableBlock> otherBlocks) {
Block block1 = workspace.getEnv().getBlock(rblock1.getBlockID());
BlockConnector closestSocket1 = null;
BlockConnector closestSocket2 = null;
Block closestBlock2 = null;
double closestDistance = MAX_LINK_DISTANCE;
double currentDistance;
for (RenderableBlock rblock2 : otherBlocks) {
BlockConnector currentPlug = getPlugEquivalent(block1);
Block block2 = workspace.getEnv().getBlock(rblock2.getBlockID());
if (block1.equals(block2) || !rblock1.isVisible() || !rblock2.isVisible() || rblock1.isCollapsed() || rblock2.isCollapsed()) {
continue;
}
Point2D currentPlugPoint = null;
Point2D currentSocketPoint = null;
if (currentPlug != null) {
currentPlugPoint = getAbsoluteSocketPoint(rblock1, currentPlug);
for (BlockConnector currentSocket : getSocketEquivalents(block2)) {
currentSocketPoint = getAbsoluteSocketPoint(rblock2, currentSocket);
currentDistance = currentPlugPoint.distance(currentSocketPoint);
if ((currentDistance < closestDistance) && checkRules(block1, block2, currentPlug, currentSocket)) {
closestBlock2 = block2;
closestSocket1 = currentPlug;
closestSocket2 = currentSocket;
closestDistance = currentDistance;
}
}
}
currentPlug = getPlugEquivalent(block2);
if (currentPlug != null) {
currentPlugPoint = getAbsoluteSocketPoint(rblock2, currentPlug);
for (BlockConnector currentSocket : getSocketEquivalents(block1)) {
currentSocketPoint = getAbsoluteSocketPoint(rblock1, currentSocket);
currentDistance = currentPlugPoint.distance(currentSocketPoint);
if ((currentDistance < closestDistance) && checkRules(block1, block2, currentSocket, currentPlug)) {
closestBlock2 = block2;
closestSocket1 = currentSocket;
closestSocket2 = currentPlug;
closestDistance = currentDistance;
}
}
}
}
if (closestSocket1 == null) {
return null;
}
return BlockLink.getBlockLink(workspace, block1, closestBlock2, closestSocket1, closestSocket2);
}
Aggregations