Как я могу удерживать клетки суставов от переполнения бумаги?
Я использую jointjs для создания диаграмм, которые будут редактироваться пользователем. Пользователь может перетащить их и переместить каждую ячейку. Однако, когда ячейка перетаскивается к краю, она переполняется и обрезается. Я хочу, чтобы это не происходило, вместо того, чтобы клетка останавливалась, прежде чем она попала на край бумаги, и ей не разрешили пересечь край, таким образом, всегда оставаясь полностью в бумаге. Поведение можно увидеть в собственных собственных демонах:
http://www.jointjs.com/tutorial/ports
Попробуйте перетащить ячейку на край, и вы увидите, что она со временем становится скрытой, когда она пересекает край бумажного элемента.
Во-вторых, я использую плагин для направленного макета графа, который находится здесь:
http://jointjs.com/rappid/docs/layout/directedGraph
Как вы можете видеть, позиция дерева автоматически перемещается в верхнем левом углу элемента бумаги всякий раз, когда вы нажимаете кнопку. Как изменить эти позиции по умолчанию? Единственными параметрами, которые я вижу для предоставленной функции, являются пространство между рангами и пространством между узлами, без начального положения. Скажем, я хотел, чтобы дерево появилось в середине бумаги, щелкнув "макет", где мне нужно было внести изменения? Заранее благодарим за любую помощь.
Ответы
Ответ 1
Я думаю, что мой предыдущий ответ по-прежнему возможен, но именно так я реализовал его в своем проекте. Он имеет преимущество перед другим ответом в том, что он не требует от вас использования пользовательского elementView
и кажется более простым (для меня).
(Работает jsfiddle: http://jsfiddle.net/pL68gs2m/2/)
На paper
обработайте событие cell:pointermove
. В обработчике событий создайте ограничивающий прямоугольник cellView
, на котором было инициировано событие, и используйте его для ограничения движения.
var graph = new joint.dia.Graph;
var width = 400;
var height = 400;
var gridSize = 1;
var paper = new joint.dia.Paper({
el: $('#paper'),
width: width,
height: height,
model: graph,
gridSize: gridSize
});
paper.on('cell:pointermove', function (cellView, evt, x, y) {
var bbox = cellView.getBBox();
var constrained = false;
var constrainedX = x;
if (bbox.x <= 0) { constrainedX = x + gridSize; constrained = true }
if (bbox.x + bbox.width >= width) { constrainedX = x - gridSize; constrained = true }
var constrainedY = y;
if (bbox.y <= 0) { constrainedY = y + gridSize; constrained = true }
if (bbox.y + bbox.height >= height) { constrainedY = y - gridSize; constrained = true }
//if you fire the event all the time you get a stack overflow
if (constrained) { cellView.pointermove(evt, constrainedX, constrainedY) }
});
Ответ 2
я. Чтобы предотвратить переполнение элементов на бумаге, вы можете использовать опцию restrictTranslate
для бумаги (JointJS v0.9.7 +).
paper.options.restrictTranslate = function(cellView) {
// move element inside the bounding box of the paper element only
return cellView.paper.getArea();
}
http://jointjs.com/api#joint.dia.Paper:options
II. Используйте опции marginX
и marginY
DirectedGraph для перемещения левого верхнего угла результирующего графика, то есть добавьте маржу слева и сверху.
http://jointjs.com/rappid/docs/layout/directedGraph#configuration
Ответ 3
В качестве дополнения к римскому ответу restrictTranslate
также можно настроить как true
, чтобы ограничить перемещение элементов до границы области бумаги.
Пример:
var paper = new joint.dia.Paper({
el: $('#paper'),
width: 600,
height: 400,
model: graph,
restrictTranslate: true
})
Ответ 4
Изменить: Я думаю, что этот подход по-прежнему возможен, но теперь я думаю, что мой другой ответ проще/лучше.
Документы JointJS предоставляют образец, в котором перемещение формы ограничено, чтобы лежать на эллипсе:
http://www.jointjs.com/tutorial/constraint-move-to-circle
Работает
- Определение нового представления для вашего элемента, расширение
joint.dia.ElementView
- Перекрытие событий
pointerdown
и pointermove
в представлении для реализации ограничения. Это делается путем вычисления новой позиции на основе положения мыши и ограничения, а затем передачи этого в базовый обработчик событий ElementView
- Принудительное использование
paper
для использования пользовательского представления элемента
Этот подход может быть легко адаптирован для предотвращения вытягивания фигуры с края бумаги. На шаге 2 вместо вычисления пересечения с эллипсом, как в учебнике, вы должны использовать Math.min()
или Math.max()
для вычисления новой позиции.