288 lines
10 KiB
JavaScript
288 lines
10 KiB
JavaScript
/*
|
|
* Copyright [2011] [wisemapping]
|
|
*
|
|
* Licensed under WiseMapping Public License, Version 1.0 (the "License").
|
|
* It is basically the Apache License, Version 2.0 (the "License") plus the
|
|
* "powered by wisemapping" text requirement on every single page;
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the license at
|
|
*
|
|
* http://www.wisemapping.org/license
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
mindplot.FixedDistanceBoard = new Class({
|
|
Extends:mindplot.Board,
|
|
initialize:function(defaultHeight, topic, layoutManager) {
|
|
this._topic = topic;
|
|
this._layoutManager = layoutManager;
|
|
var reference = topic.getPosition();
|
|
this.parent(defaultHeight, reference);
|
|
this._height = defaultHeight;
|
|
this._entries = [];
|
|
},
|
|
|
|
getHeight : function() {
|
|
return this._height;
|
|
},
|
|
|
|
lookupEntryByOrder : function(order) {
|
|
var result = null;
|
|
var entries = this._entries;
|
|
if (order < entries.length) {
|
|
result = entries[order];
|
|
}
|
|
|
|
if (result == null) {
|
|
var defaultHeight = this._defaultWidth;
|
|
var reference = this.getReferencePoint();
|
|
if (entries.length == 0) {
|
|
var yReference = reference.y;
|
|
result = this.createBoardEntry(yReference - (defaultHeight / 2), yReference + (defaultHeight / 2), 0);
|
|
} else {
|
|
var entriesLenght = entries.length;
|
|
var lastEntry = entries[entriesLenght - 1];
|
|
var lowerLimit = lastEntry.getUpperLimit();
|
|
var upperLimit = lowerLimit + defaultHeight;
|
|
result = this.createBoardEntry(lowerLimit, upperLimit, entriesLenght + 1);
|
|
}
|
|
}
|
|
return result;
|
|
},
|
|
|
|
createBoardEntry : function(lowerLimit, upperLimit, order) {
|
|
var result = new mindplot.BoardEntry(lowerLimit, upperLimit, order);
|
|
var xPos = this.workoutXBorderDistance();
|
|
result.setXPosition(xPos);
|
|
return result;
|
|
},
|
|
|
|
updateReferencePoint : function() {
|
|
var entries = this._entries;
|
|
var parentTopic = this.getTopic();
|
|
var parentPosition = parentTopic.workoutIncomingConnectionPoint(parentTopic.getPosition());
|
|
var referencePoint = this.getReferencePoint();
|
|
var yOffset = parentPosition.y - referencePoint.y;
|
|
|
|
for (var i = 0; i < entries.length; i++) {
|
|
var entry = entries[i];
|
|
|
|
if ($defined(entry)) {
|
|
var upperLimit = entry.getUpperLimit() + yOffset;
|
|
var lowerLimit = entry.getLowerLimit() + yOffset;
|
|
entry.setUpperLimit(upperLimit);
|
|
entry.setLowerLimit(lowerLimit);
|
|
|
|
// Fix x position ...
|
|
var xPos = this.workoutXBorderDistance();
|
|
entry.setXPosition(xPos);
|
|
entry.update();
|
|
}
|
|
}
|
|
this._referencePoint = parentPosition.clone();
|
|
|
|
},
|
|
|
|
/**
|
|
* This x distance doesn't take into account the size of the shape.
|
|
*/
|
|
workoutXBorderDistance : function() {
|
|
var topic = this.getTopic();
|
|
|
|
var topicPosition = topic.getPosition();
|
|
var topicSize = topic.getSize();
|
|
var halfTargetWidth = topicSize.width / 2;
|
|
var result;
|
|
if (topicPosition.x >= 0) {
|
|
// It's at right.
|
|
result = topicPosition.x + halfTargetWidth + mindplot.FixedDistanceBoard.MAIN_TOPIC_TO_MAIN_TOPIC_DISTANCE;
|
|
} else {
|
|
result = topicPosition.x - (halfTargetWidth + mindplot.FixedDistanceBoard.MAIN_TOPIC_TO_MAIN_TOPIC_DISTANCE);
|
|
}
|
|
return result;
|
|
},
|
|
|
|
getTopic : function() {
|
|
return this._topic;
|
|
},
|
|
|
|
freeEntry : function(entry) {
|
|
var newEntries = [];
|
|
var entries = this._entries;
|
|
var order = 0;
|
|
for (var i = 0; i < entries.length; i++) {
|
|
var e = entries[i];
|
|
if (e == entry) {
|
|
order++;
|
|
}
|
|
newEntries[order] = e;
|
|
order++;
|
|
}
|
|
this._entries = newEntries;
|
|
},
|
|
|
|
repositionate : function() {
|
|
// Workout width and update topic height.
|
|
var entries = this._entries;
|
|
var height = 0;
|
|
var model = this._topic.getModel();
|
|
if (entries.length >= 1 && !model.areChildrenShrinked()) {
|
|
for (var i = 0; i < entries.length; i++) {
|
|
var e = entries[i];
|
|
if (e && e.getTopic()) {
|
|
var topic = e.getTopic();
|
|
var topicBoard = this._layoutManager.getTopicBoardForTopic(topic);
|
|
var topicBoardHeight = topicBoard.getHeight();
|
|
|
|
|
|
height += topicBoardHeight + mindplot.FixedDistanceBoard.INTER_TOPIC_DISTANCE;
|
|
}
|
|
}
|
|
}
|
|
else {
|
|
var topic = this._topic;
|
|
height = topic.getSize().height + mindplot.FixedDistanceBoard.INTER_TOPIC_DISTANCE;
|
|
}
|
|
|
|
var oldHeight = this._height;
|
|
this._height = height;
|
|
|
|
// I must update all the parent nodes first...
|
|
if (oldHeight != this._height) {
|
|
var topic = this._topic;
|
|
var parentTopic = topic.getParent();
|
|
if (parentTopic != null) {
|
|
var board = this._layoutManager.getTopicBoardForTopic(parentTopic);
|
|
board.repositionate();
|
|
}
|
|
}
|
|
|
|
|
|
// @todo: Esto hace backtraking. Hay que cambiar la implementacion del set position de
|
|
// forma tal que no se mande a hacer el update de todos los hijos.
|
|
|
|
// Workout center the new topic center...
|
|
var refence = this.getReferencePoint();
|
|
var lowerLimit;
|
|
if (entries.length > 0) {
|
|
var l = 0;
|
|
for (l = 0; l < entries.length; l++) {
|
|
if ($defined(entries[l]))
|
|
break;
|
|
}
|
|
var topic = entries[l].getTopic();
|
|
var firstNodeHeight = topic.getSize().height;
|
|
lowerLimit = refence.y - (height / 2) - (firstNodeHeight / 2) + 1;
|
|
}
|
|
|
|
var upperLimit = null;
|
|
|
|
// Start moving all the elements ...
|
|
var newEntries = [];
|
|
var order = 0;
|
|
for (var i = 0; i < entries.length; i++) {
|
|
var e = entries[i];
|
|
if (e && e.getTopic()) {
|
|
|
|
var currentTopic = e.getTopic();
|
|
e.setLowerLimit(lowerLimit);
|
|
|
|
// Update entry ...
|
|
var topicBoard = this._layoutManager.getTopicBoardForTopic(currentTopic);
|
|
var topicBoardHeight = topicBoard.getHeight();
|
|
|
|
upperLimit = lowerLimit + topicBoardHeight + mindplot.FixedDistanceBoard.INTER_TOPIC_DISTANCE;
|
|
e.setUpperLimit(upperLimit);
|
|
lowerLimit = upperLimit;
|
|
|
|
e.setOrder(order);
|
|
currentTopic.setOrder(order);
|
|
|
|
e.update();
|
|
newEntries[order] = e;
|
|
order++;
|
|
}
|
|
}
|
|
this._entries = newEntries;
|
|
},
|
|
|
|
removeTopic : function(topic) {
|
|
var order = topic.getOrder();
|
|
var entry = this.lookupEntryByOrder(order);
|
|
$assert(!entry.isAvailable(), "Illegal state");
|
|
|
|
entry.setTopic(null);
|
|
topic.setOrder(null);
|
|
this._entries.erase(entry);
|
|
|
|
// Repositionate all elements ...
|
|
this.repositionate();
|
|
},
|
|
|
|
addTopic : function(order, topic) {
|
|
|
|
// If the entry is not available, I must swap the the entries...
|
|
var entry = this.lookupEntryByOrder(order);
|
|
if (!entry.isAvailable()) {
|
|
this.freeEntry(entry);
|
|
// Create a dummy entry ...
|
|
// Puaj, do something with this...
|
|
entry = this.createBoardEntry(-1, 0, order);
|
|
this._entries[order] = entry;
|
|
}
|
|
this._entries[order] = entry;
|
|
|
|
// Add to the board ...
|
|
entry.setTopic(topic, false);
|
|
|
|
// Repositionate all elements ...
|
|
this.repositionate();
|
|
},
|
|
|
|
lookupEntryByPosition : function(pos) {
|
|
$assert(pos, 'position can not be null');
|
|
|
|
var entries = this._entries;
|
|
var result = null;
|
|
for (var i = 0; i < entries.length; i++) {
|
|
var entry = entries[i];
|
|
if (pos.y < entry.getUpperLimit() && pos.y >= entry.getLowerLimit()) {
|
|
result = entry;
|
|
}
|
|
}
|
|
|
|
if (result == null) {
|
|
var defaultHeight = this._defaultWidth;
|
|
if (entries.length == 0) {
|
|
var reference = this.getReferencePoint();
|
|
var yReference = reference.y;
|
|
result = this.createBoardEntry(yReference - (defaultHeight / 2), yReference + (defaultHeight / 2), 0);
|
|
} else {
|
|
var firstEntry = entries[0];
|
|
if (pos.y < firstEntry.getLowerLimit()) {
|
|
var upperLimit = firstEntry.getLowerLimit();
|
|
var lowerLimit = upperLimit - defaultHeight;
|
|
result = this.createBoardEntry(lowerLimit, upperLimit, 0);
|
|
} else {
|
|
var entriesLenght = entries.length;
|
|
var lastEntry = entries[entriesLenght - 1];
|
|
var lowerLimit = lastEntry.getUpperLimit();
|
|
var upperLimit = lowerLimit + defaultHeight;
|
|
result = this.createBoardEntry(lowerLimit, upperLimit, entriesLenght);
|
|
}
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
})
|
|
;
|
|
mindplot.FixedDistanceBoard.INTER_TOPIC_DISTANCE = 6;
|
|
mindplot.FixedDistanceBoard.MAIN_TOPIC_TO_MAIN_TOPIC_DISTANCE = 60;
|
|
|