Index: lams_central/web/author2.jsp =================================================================== diff -u -r91846a63ca7f8b611b2acb7a09cd42bb522fd305 -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/author2.jsp (.../author2.jsp) (revision 91846a63ca7f8b611b2acb7a09cd42bb522fd305) +++ lams_central/web/author2.jsp (.../author2.jsp) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -203,8 +203,21 @@ - + +
+ + + + + +
+ Title: + + +
+
+
Index: lams_central/web/includes/javascript/authoring/authoringActivity.js =================================================================== diff -u -r668a627903b72826f7dffa148a7e775139af8b5e -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/includes/javascript/authoring/authoringActivity.js (.../authoringActivity.js) (revision 668a627903b72826f7dffa148a7e775139af8b5e) +++ lams_central/web/includes/javascript/authoring/authoringActivity.js (.../authoringActivity.js) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -3,6 +3,27 @@ */ var ActivityLib = { + + /** + * Constructor for a Transition + */ + Transition : function(id, uiid, fromActivity, toActivity, title) { + this.id = +id; + this.uiid = +uiid || ++layout.ld.maxUIID; + this.fromActivity = fromActivity; + this.toActivity = toActivity; + if (title) { + this.title = title; + this.loadPropertiesDialogContent = PropertyLib.transitionProperties; + } + + this.draw = ActivityLib.draw.transition; + this.draw(); + + // set up references in activities and the transition + fromActivity.transitions.from.push(this); + toActivity.transitions.to.push(this); + }, /** * Constructor for a Tool Activity. @@ -124,16 +145,59 @@ BranchActivity : function(id, uiid, title, branchingActivity, transitionFrom) { this.id = +id; this.uiid = +uiid || ++layout.ld.maxUIID; - this.title = title; - this.transitionFrom = transitionFrom; + this.title = title || ('Branch ' + (branchingActivity.branches.length + 1)); this.branchingActivity = branchingActivity; + this.transitionFrom = transitionFrom; }, /** * Mehtods for drawing various kinds of activities. */ draw : { + + transition : function() { + if (this.items) { + this.items.remove(); + } + + // calculate middle points of each activity + var points = ActivityLib.findTransitionPoints(this.fromActivity, this.toActivity); + + // create transition SVG elements + paper.setStart(); + paper.path(Raphael.format('M {0} {1} L {2} {3}', points.startX, points.startY, points.endX, points.endY)) + .attr({ + 'stroke' : layout.colors.transition, + 'stroke-width' : 2 + }); + + // draw the arrow and turn it in the same direction as the line + var angle = 90 + Math.atan2(points.endY - points.startY, points.endX - points.startX) * 180 / Math.PI, + arrowPath = Raphael.transformPath(Raphael.format('M {0} {1}' + layout.defs.transArrow, points.middleX, points.middleY), + Raphael.format('R {0} {1} {2}', angle, points.middleX, points.middleY)); + paper.path(arrowPath) + .attr({ + 'stroke' : layout.colors.transition, + 'fill' : layout.colors.transition + }); + if (this.title) { + // adjust X & Y depending on the angle, so the lable does not overlap with the transition + // angle is -90 <= a <= 270 + paper.text(points.middleX + ((angle > -45 && angle < 45) || (angle > 135 && angle < 225) ? 20 : 0), + points.middleY + ((angle > 45 && angle < 135) || angle > 225 || angle < 45 ? -20 : 0), + this.title); + } + this.items = paper.setFinish(); + + this.items.toBack(); + this.items.attr('cursor', 'pointer'); + this.items.data('parentObject', this); + this.items.mousedown(HandlerLib.transitionMousedownHandler); + this.items.click(HandlerLib.itemClickHandler); + }, + + tool : function(x, y) { if (x == undefined || y == undefined) { // just redraw the activity @@ -270,10 +334,9 @@ activityHandlersInit : function(activity) { // set all the handlers activity.items - .data('activity', activity) + .data('parentObject', activity) .mousedown(HandlerLib.activityMousedownHandler) - .touchmove(HandlerLib.dragItemsMoveHandler) - .click(HandlerLib.activityClickHandler) + .click(HandlerLib.itemClickHandler) .dblclick(HandlerLib.activityDblclickHandler) .attr({ 'cursor' : 'pointer' @@ -335,7 +398,7 @@ /** * Draws a transition between two activities. */ - drawTransition : function(fromActivity, toActivity, redraw, id, uiid) { + addTransition : function(fromActivity, toActivity, redraw, id, uiid, title) { // only converge points are allowed to have few inbound transitions if (!redraw && toActivity.transitions.to.length > 0 @@ -356,55 +419,30 @@ return; } + var branch = null; // remove the existing transition $.each(fromActivity.transitions.from, function(index) { if (this.toActivity == toActivity) { + id = this.id; uiid = this.uiid; + branch = this.branch; ActivityLib.removeTransition(this); return false; } }); - // calculate middle points of each activity - var points = ActivityLib.findTransitionPoints(fromActivity, toActivity); + if (!branch && fromActivity.type == 'branchingEdge' && fromActivity.isStart) { + // create a new branch + branch = new ActivityLib.BranchActivity(null, null, null, fromActivity.branchingActivity); + } - // do the actual drawing - paper.setStart(); - paper.path(Raphael.format('M {0} {1} L {2} {3}', points.startX, points.startY, points.endX, points.endY)) - .attr({ - 'stroke' : layout.colors.transition, - 'stroke-width' : 2 - }); + var transition = new ActivityLib.Transition(id, uiid, fromActivity, toActivity, + branch ? branch.title : null); - // draw the arrow and turn it in the same direction as the line - var angle = 90 + Math.atan2(points.endY - points.startY, points.endX - points.startX) * 180 / Math.PI; - var arrowPath = Raphael.transformPath(Raphael.format('M {0} {1}' + layout.defs.transArrow, points.middleX, points.middleY), - Raphael.format('R {0} {1} {2}', angle, points.middleX, points.middleY)); - paper.path(arrowPath) - .attr({ - 'stroke' : layout.colors.transition, - 'fill' : layout.colors.transition - }); - var transition = paper.setFinish(); - transition.uiid = uiid || ++layout.ld.maxUIID; - transition.id = id; - transition.data('transition', transition); - - // set up references in activities and the transition - fromActivity.transitions.from.push(transition); - toActivity.transitions.to.push(transition); - transition.fromActivity = fromActivity; - transition.toActivity = toActivity; - transition.toBack(); - transition.mousedown(HandlerLib.transitionMousedownHandler); - - if (!redraw && fromActivity.type == 'branchingEdge' && fromActivity.isStart - && (toActivity.type != 'branchingEdge' - || fromActivity.branchingActivity != toActivity.branchingActivity)) { - // create a new branch - var branch = new ActivityLib.BranchActivity(null, null, null, fromActivity.branchingActivity, transition); + if (branch) { + branch.transitionFrom = transition; + transition.branch = branch; fromActivity.branchingActivity.branches.push(branch); - transition.data('branch', branch); } return transition; @@ -421,13 +459,12 @@ transitions = transition.toActivity.transitions.to; transitions.splice(transitions.indexOf(transition), 1); - var branch = transition[0].data('branch'); - if (branch) { - var branches = branch.branchingActivity.branches; - branches.splice(branches.indexOf(branch), 1); + if (transition.branch) { + var branches = transition.branch.branchingActivity.branches; + branches.splice(branches.indexOf(transition.branch), 1); } - transition.remove(); + transition.items.remove(); }, @@ -460,7 +497,7 @@ branchPoints2 = ActivityLib.findTransitionPoints(fromActivity, toActivity2), branchEdgeStartX = branchPoints1.middleX + (branchPoints2.middleX - branchPoints1.middleX)/2, branchEdgeStartY = branchPoints1.middleY + (branchPoints2.middleY - branchPoints1.middleY)/2, - branchingEdgeStart = new ActivityLib.BranchingEdgeActivity(null, branchEdgeStartX, + branchingEdgeStart = new ActivityLib.BranchingEdgeActivity(null, null, branchEdgeStartX, branchEdgeStartY, null, null, null); layout.activities.push(branchingEdgeStart); @@ -470,67 +507,86 @@ }; var convergePoints = ActivityLib.findTransitionPoints(convergeActivity1, convergeActivity2), - branchingEdgeEnd = new ActivityLib.BranchingEdgeActivity(null, convergePoints.middleX, + branchingEdgeEnd = new ActivityLib.BranchingEdgeActivity(null, null, convergePoints.middleX, convergePoints.middleY, null, null, branchingEdgeStart.branchingActivity); layout.activities.push(branchingEdgeEnd); // draw all required transitions - ActivityLib.drawTransition(fromActivity, branchingEdgeStart); - ActivityLib.drawTransition(branchingEdgeStart, toActivity2); - ActivityLib.drawTransition(convergeActivity2, branchingEdgeEnd); + ActivityLib.addTransition(fromActivity, branchingEdgeStart); + ActivityLib.addTransition(branchingEdgeStart, toActivity2); + ActivityLib.addTransition(convergeActivity2, branchingEdgeEnd); } - ActivityLib.drawTransition(branchingEdgeStart, toActivity1); - ActivityLib.drawTransition(convergeActivity1, branchingEdgeEnd); + ActivityLib.addTransition(branchingEdgeStart, toActivity1); + ActivityLib.addTransition(convergeActivity1, branchingEdgeEnd); }, /** * Draws an extra border around the selected activity. */ - addSelectEffect : function (activity) { + addSelectEffect : function (object) { // do not draw twice - if (!activity.items.selectEffect) { - var box = activity.items.getBBox(); + if (!object.items.selectEffect) { + if (object instanceof ActivityLib.Transition) { + // show only if Transition is selectable, i.e. has a title + if (object.loadPropertiesDialogContent) { + object.items.attr({ + 'stroke' : layout.colors.selectEffect, + 'fill' : layout.colors.selectEffect + }); + + object.items.selectEffect = true; + } + } else { + var box = object.items.getBBox(); + + // a simple rectange a bit wider than the actual activity boundaries + object.items.selectEffect = paper.rect( + box.x - 7, + box.y - 7, + box.width + 14, + box.height + 14) + .attr({ + 'stroke' : layout.colors.selectEffect, + 'stroke-dasharray' : '-' + }); + object.items.push(object.items.selectEffect); + } - // a simple rectange a bit wider than the actual activity boundaries - activity.items.selectEffect = paper.rect( - box.x - 7, - box.y - 7, - box.width + 14, - box.height + 14) - .attr({ - 'stroke' : layout.colors.selectEffect, - 'stroke-dasharray' : '-' - }); - activity.items.push(activity.items.selectEffect); - layout.items.selectedActivity = activity; - - // show the properties dialog for the selected activity - if (activity.loadPropertiesDialogContent) { - activity.loadPropertiesDialogContent(); - var dialog = layout.items.propertiesDialog; - dialog.children().detach(); - dialog.append(activity.propertiesContent); - dialog.dialog('open'); - dialog.find('input').blur(); + if (object.items.selectEffect){ + layout.items.selectedObject = object; + // show the properties dialog for the selected object + if (object.loadPropertiesDialogContent) { + object.loadPropertiesDialogContent(); + var dialog = layout.items.propertiesDialog; + dialog.children().detach(); + dialog.append(object.propertiesContent); + dialog.dialog('open'); + dialog.find('input').blur(); + } } } }, removeSelectEffect : function() { - var selectedActivity = layout.items.selectedActivity; + var selectedObject = layout.items.selectedObject; // does selection exist at all? - if (selectedActivity) { - if (selectedActivity.items.selectEffect) { - selectedActivity.items.selectEffect.remove(); - selectedActivity.items.selectEffect = null; + if (selectedObject) { + if (selectedObject.items.selectEffect) { + if (selectedObject instanceof ActivityLib.Transition) { + // just redraw, it's easier + selectedObject.draw(); + } else { + selectedObject.items.selectEffect.remove(); + } + selectedObject.items.selectEffect = null; } // no selected activity = no properties dialog layout.items.propertiesDialog.dialog('close'); - layout.items.selectedActivity = null; + layout.items.selectedObject = null; } }, @@ -576,10 +632,10 @@ // redraw transitions $.each(activity.transitions.from.slice(), function(){ - ActivityLib.drawTransition(activity, this.toActivity, true); + ActivityLib.addTransition(activity, this.toActivity, true); }); $.each(activity.transitions.to.slice(), function(){ - ActivityLib.drawTransition(this.fromActivity, activity, true); + ActivityLib.addTransition(this.fromActivity, activity, true); }); }, @@ -621,16 +677,6 @@ /** - * Drop the dragged transition. - */ - dropTransition : function(transition) { - // if the transition was over rubbish bin, remove it - transition.transform(''); - transition.toBack(); - }, - - - /** * Calculates start, middle and end points of a line between two activities. */ findTransitionPoints : function(fromActivity, toActivity) { @@ -677,6 +723,12 @@ // include the first activity var branchLength = 1, activity = this.transitionFrom.toActivity; + if (activity.type == 'branchingEdge' + && branchingActivity == activity.branchingActivity){ + // branch with no activities + return true; + } + while (activity.transitions.from.length > 0) { activity = activity.transitions.from[0].toActivity; // check if reached the end of branch Index: lams_central/web/includes/javascript/authoring/authoringGeneral.js =================================================================== diff -u -r91846a63ca7f8b611b2acb7a09cd42bb522fd305 -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/includes/javascript/authoring/authoringGeneral.js (.../authoringGeneral.js) (revision 91846a63ca7f8b611b2acb7a09cd42bb522fd305) +++ lams_central/web/includes/javascript/authoring/authoringGeneral.js (.../authoringGeneral.js) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -8,12 +8,13 @@ // configuration and storage of various elements layout = { + 'drawMode' : false, // 'isZoomed' : false, 'activities' : null, 'items' : { 'bin' : null, - 'selectedActivity' : null, + 'selectedObject' : null, 'copiedActivity' : null, 'propertiesDialog' : null, @@ -614,9 +615,9 @@ branchData = branchToActivities[branch.id]; // add reference to the transition inside branch - branch.transitionFrom = ActivityLib.drawTransition(branchingActivity.start, - branchData.firstActivity, true); - ActivityLib.drawTransition(branchData.lastActivity, branchingActivity.end, true); + branch.transitionFrom = ActivityLib.addTransition(branchingActivity.start, + branchData.firstActivity, true, null, null, branch.title); + ActivityLib.addTransition(branchData.lastActivity, branchingActivity.end, true); }); } }); @@ -644,7 +645,7 @@ // found both transition ends, draw it and stop the iteration if (fromActivity && toActivity) { - ActivityLib.drawTransition(fromActivity, toActivity, true, + ActivityLib.addTransition(fromActivity, toActivity, true, transition.transitionID, transition.transitionUIID); return false; } Index: lams_central/web/includes/javascript/authoring/authoringHandler.js =================================================================== diff -u -r72d667eddbe49aaf0dfebe27c0e18fd09b96036f -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/includes/javascript/authoring/authoringHandler.js (.../authoringHandler.js) (revision 72d667eddbe49aaf0dfebe27c0e18fd09b96036f) +++ lams_central/web/includes/javascript/authoring/authoringHandler.js (.../authoringHandler.js) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -8,6 +8,8 @@ * Default mode for canvas. Run after special mode is no longer needed. */ resetCanvasMode : function(){ + layout.drawMode = false; + // remove selection if exists ActivityLib.removeSelectEffect(); @@ -36,8 +38,7 @@ dialog.lastRun = thisRun; // is the dialog visible at all? - var activity = layout.items.selectedActivity; - if (activity) { + if (layout.items.selectedObject) { // calculate dim/show threshold var container = dialog.container, dialogPosition = container.offset(), @@ -60,11 +61,12 @@ canvasClickHandler : function(event) { // check if user clicked on empty space on canvas // or on some element on top of it - var defaultPrevented = event.originalEvent ? - event.originalEvent.defaultPrevented : event.defaultPrevented; - if (!defaultPrevented) { - ActivityLib.removeSelectEffect(); + if (layout.drawMode || (event.originalEvent ? + event.originalEvent.defaultPrevented : event.defaultPrevented)){ + return; } + + ActivityLib.removeSelectEffect(); }, @@ -80,6 +82,11 @@ clearTimeout(items.dragStarter); } + if (layout.drawMode || (event.originalEvent ? + event.originalEvent.defaultPrevented : event.defaultPrevented)){ + return; + } + // run only if "click" event was not generated, i.e. user really wants to drag items.dragStarter = setTimeout(function(){ items.dragStarter = null; @@ -187,8 +194,9 @@ * Finalise transition drawing. */ drawTransitionEndHandler : function(activity, event) { - // prevent triggering event on several activity items; we just need on transition + // prevent triggering event on several activity items; we just need it on transition event.stopImmediatePropagation(); + event.preventDefault(); HandlerLib.resetCanvasMode(); //remove the temporary transition (dashed line) @@ -200,11 +208,11 @@ var endActivity = null, targetElement = paper.getElementByPoint(event.pageX, event.pageY); if (targetElement) { - endActivity = targetElement.data('activity'); + endActivity = targetElement.data('parentObject'); } if (endActivity && activity != endActivity) { - ActivityLib.drawTransition(activity, endActivity); + ActivityLib.addTransition(activity, endActivity); } }, @@ -213,7 +221,7 @@ * Lighthens up branching edges in the same colour for identifictation. */ branchingEdgeMouseoverHandler : function() { - var branchingActivity = this.data('activity').branchingActivity, + var branchingActivity = this.data('parentObject').branchingActivity, startItems = branchingActivity.start.items, endItems = branchingActivity.end.items; if (!startItems.isDragged && !endItems.isDragged) { @@ -227,7 +235,7 @@ * Return branching edges to their normal colours. */ branchingEdgeMouseoutHandler : function() { - var branchingActivity = this.data('activity').branchingActivity, + var branchingActivity = this.data('parentObject').branchingActivity, startItems = branchingActivity.start.items, endItems = branchingActivity.end.items; @@ -242,7 +250,12 @@ * Starts drawing a transition or dragging an activity. */ activityMousedownHandler : function(event, x, y){ - var activity = this.data('activity'); + if (layout.drawMode || (event.originalEvent ? + event.originalEvent.defaultPrevented : event.defaultPrevented)){ + return; + } + + var activity = this.data('parentObject'); if (event.ctrlKey) { // when CTRL is held down, start drawing a transition HandlerLib.drawTransitionStartHandler(activity, event, x, y); @@ -258,20 +271,27 @@ // start dragging the activity HandlerLib.dragItemsStartHandler(activity.items, this, mouseupHandler, event, x, y); } + }, /** * Selects an activity. */ - activityClickHandler : function(event) { - var activity = this.data('activity'); + itemClickHandler : function(event) { + if (layout.drawMode || (event.originalEvent ? + event.originalEvent.defaultPrevented : event.defaultPrevented)){ + return; + } + + var parentObject = this.data('parentObject'); // inform that user wants to select, not drag the activity - activity.items.clicked = true; - if (activity != layout.items.selectedActivity) { + parentObject.items.clicked = true; + if (parentObject != layout.items.selectedObject) { HandlerLib.canvasClickHandler(event); - ActivityLib.addSelectEffect(activity); - } + ActivityLib.addSelectEffect(parentObject); + } + // so canvas handler unselectActivityHandler() is not run event.preventDefault(); }, @@ -281,7 +301,7 @@ * Opens activity authoring. */ activityDblclickHandler : function(event) { - var activity = this.data('activity'); + var activity = this.data('parentObject'); // inform that user wants to open, not drag the activity activity.items.clicked = true; ActivityLib.openActivityAuthoring(activity); @@ -292,18 +312,18 @@ * Starts dragging a transition. */ transitionMousedownHandler : function(event, x, y){ - var transition = this.data('transition'); + var transition = this.data('parentObject'); // allow transition dragging var mouseupHandler = function(event){ if (HandlerLib.isElemenentBinned(event)) { // if the transition was over rubbish bin, remove it ActivityLib.removeTransition(transition); } else { - ActivityLib.dropTransition(transition); + transition.draw(); } } - HandlerLib.dragItemsStartHandler(transition, this, mouseupHandler, event, x, y); + HandlerLib.dragItemsStartHandler(transition.items, this, mouseupHandler, event, x, y); }, Index: lams_central/web/includes/javascript/authoring/authoringMenu.js =================================================================== diff -u -r91846a63ca7f8b611b2acb7a09cd42bb522fd305 -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/includes/javascript/authoring/authoringMenu.js (.../authoringMenu.js) (revision 91846a63ca7f8b611b2acb7a09cd42bb522fd305) +++ lams_central/web/includes/javascript/authoring/authoringMenu.js (.../authoringMenu.js) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -57,7 +57,7 @@ y = translatedEvent[1] - 8; // if it is start point, branchingActivity is null and constructor acts accordingly - var branchingEdge = new ActivityLib.BranchingEdgeActivity(null, x, y, null, null, branchingActivity); + var branchingEdge = new ActivityLib.BranchingEdgeActivity(null, null, x, y, null, null, branchingActivity); layout.activities.push(branchingEdge); if (branchingActivity) { @@ -103,14 +103,15 @@ canvas.css('cursor', 'pointer').click(function(event){ HandlerLib.resetCanvasMode(); + layout.drawMode = true; dialog.text(''); dialog.dialog('close'); var startActivity = null, targetElement = paper.getElementByPoint(event.pageX, event.pageY); if (targetElement) { - startActivity = targetElement.data('activity'); + startActivity = targetElement.data('parentObject'); if (startActivity) { HandlerLib.drawTransitionStartHandler(startActivity, null, event.pageX, event.pageY); } @@ -132,7 +133,7 @@ x = translatedEvent[0], y = translatedEvent[1] + 2; - layout.activities.push(new ActivityLib.GateActivity(null, x, y)); + layout.activities.push(new ActivityLib.GateActivity(null, null, x, y)); }); }, @@ -333,53 +334,70 @@ } // markers for complex activity processing - var branchIndex = null, - complexActivityEnd = null; + var complex = null; // crawl through a sequence of activities while (activity) { if (activity.type == 'branchingEdge') { - // draw branching edges straight away and remove them from normall processing - branchingActivity = activity.branchingActivity; + if (activity.isStart) { + // draw branching edges straight away and remove them from normall processing + var branchingActivity = activity.branchingActivity, + start = branchingActivity.start, + end = branchingActivity.end, + complex = { + end : end + }, + // can the whole branching fit in curren canvas width? + branchingFits = column + branchingActivity.longestBranchLength + 2 <= maxColumns; + if (!branchingFits) { + // start branching from the left side of canvas + row++; + column = 0; + } + // store the column of converge point + end.column = column + branchingActivity.longestBranchLength + 1; + + complex.branchingRow = row + Math.floor(branchingActivity.branches.length / 2); + // edge points go to middle of rows with branches + var startX = layout.conf.arrangeHorizontalPadding + + column * layout.conf.arrangeHorizontalSpace + 54, + edgeY = layout.conf.arrangeVerticalPadding + + complex.branchingRow * layout.conf.arrangeVerticalSpace + 17, + endX = layout.conf.arrangeHorizontalPadding + + end.column * layout.conf.arrangeHorizontalSpace + 54; + + activitiesCopy.splice(activitiesCopy.indexOf(start), 1); + activitiesCopy.splice(activitiesCopy.indexOf(end), 1); + + // start point goes to very left, end goes wherever the longes branch ends + start.draw(startX, edgeY); + end.draw(endX, edgeY); + + complex.branchingColumn = column; + column++; - var start = branchingActivity.start, - end = branchingActivity.end, - complexActivityEnd = end, - // can the whole branching fit in curren canvas width? - branchingFits = column + branchingActivity.longestBranchLength + 2 <= maxColumns; - if (!branchingFits) { - // start branching from the left side of canvas - row++; - column = 0; + $.each(branchingActivity.branches, function(){ + if (this.transitionFrom.toActivity == branchingActivity.end) { + complex.emptyBranch = this; + return false; + } + }); + + if (branchingActivity.branches.length > (complex.emptyBranch ? 1 : 0)) { + // set up branch drawing + // skip the first branch if it is the empty one + complex.branchIndex = + complex.emptyBranch == branchingActivity.branches[0] ? 1 : 0; + // next activity for normal processing will be first one from the first branch + activity = branchingActivity.branches[complex.branchIndex].transitionFrom.toActivity; + continue; + } else { + // no branches, nothing to do, carry on with normal activity processing + activity = complex.end; + activity.column = null; + complex = null; + } } - // store the column of converge point - end.column = column + branchingActivity.longestBranchLength + 1; - - // edge points go to middle of rows with branches - var branchingRow = row + Math.floor(branchingActivity.branches.length / 2), - startX = layout.conf.arrangeHorizontalPadding + column * layout.conf.arrangeHorizontalSpace + 54, - edgeY = layout.conf.arrangeVerticalPadding + branchingRow * layout.conf.arrangeVerticalSpace + 17, - endX = layout.conf.arrangeHorizontalPadding + end.column * layout.conf.arrangeHorizontalSpace + 54; - - activitiesCopy.splice(activitiesCopy.indexOf(start), 1); - activitiesCopy.splice(activitiesCopy.indexOf(end), 1); - - // start point goes to very left, end goes wherever the longes branch ends - start.draw(startX, edgeY); - end.draw(endX, edgeY); - - column++; - if (branchingActivity.branches.length > 0) { - // set up branch drawing - branchIndex = 0; - // next activity for normal processing will be first one from the first branch - activity = branchingActivity.branches[branchIndex].transitionFrom.toActivity; - continue; - } else { - // no branches, nothing to do, carry on with normal activity processing - activity = complexActivityEnd; - complexActivityEnd = null; - } } else { // it is a simple activity, so redraw it var x = layout.conf.arrangeHorizontalPadding + column * layout.conf.arrangeHorizontalSpace, @@ -409,26 +427,38 @@ activity = null; } - if (complexActivityEnd && (!activity || activity == complexActivityEnd)) { + if (complex && (!activity || activity == complex.end)) { // end of branch - branchIndex++; + complex.branchIndex++; - if (complexActivityEnd.branchingActivity.branches.length > branchIndex) { + var branches = complex.end.branchingActivity.branches; + if (branches.length > complex.branchIndex) { + if (branches[complex.branchIndex] == complex.emptyBranch) { + // skip the empty branch + complex.branchIndex++; + } + } + + if (branches.length > complex.branchIndex) { // there is another branch to process - activity = complexActivityEnd.branchingActivity.branches[branchIndex].transitionFrom.toActivity; + activity = branches[complex.branchIndex].transitionFrom.toActivity; // go back to left side of canvas and draw next branch row++; - column = 1; + if (complex.emptyBranch && complex.branchingRow == row) { + row++; + } + + column = complex.branchingColumn + 1; } else { // no more branches, return to normal activity processing - activity = complexActivityEnd.transitions.from.length == 0 ? - null : complexActivityEnd.transitions.from[0].toActivity; - column = (complexActivityEnd.column + 1) % maxColumns; + activity = complex.end.transitions.from.length == 0 ? + null : complex.end.transitions.from[0].toActivity; + column = (complex.end.column + 1) % maxColumns; if (column == 0) { row++; } - branchIndex = null; - complexActivityEnd = null; + complex.end.column = null; + complex = null; } } @@ -442,7 +472,7 @@ // redraw transitions one by one $.each(layout.activities, function(){ $.each(this.transitions.from.slice(), function(){ - ActivityLib.drawTransition(this.fromActivity, this.toActivity, true); + ActivityLib.addTransition(this.fromActivity, this.toActivity, true); }); }); }, @@ -483,7 +513,7 @@ * Mark an activity as ready for pasting. */ copyActivity : function(){ - layout.items.copiedActivity = layout.items.selectedActivity; + layout.items.copiedActivity = layout.items.selectedObject; }, @@ -529,7 +559,7 @@ // draw the new activity next to the existing one var x = activity.items.shape.getBBox().x + 10, y = activity.items.shape.getBBox().y + 10, - newActivity = new ActivityLib.ToolActivity(null, activity.toolID, x, y, title); + newActivity = new ActivityLib.ToolActivity(null, null, null, activity.toolID, x, y, title); layout.activities.push(newActivity); if (activity.grouping) { Index: lams_central/web/includes/javascript/authoring/authoringProperty.js =================================================================== diff -u -r668a627903b72826f7dffa148a7e775139af8b5e -rc051edc3328ffc90c5c902f938370a974a4e26d8 --- lams_central/web/includes/javascript/authoring/authoringProperty.js (.../authoringProperty.js) (revision 668a627903b72826f7dffa148a7e775139af8b5e) +++ lams_central/web/includes/javascript/authoring/authoringProperty.js (.../authoringProperty.js) (revision c051edc3328ffc90c5c902f938370a974a4e26d8) @@ -44,7 +44,7 @@ 'text' : 'OK', 'click' : function() { var dialog = $(this), - activity = dialog.dialog('option', 'activity'); + activity = dialog.dialog('option', 'parentObject'); // extract group names from text fields $('input', dialog).each(function(index){ @@ -142,6 +142,40 @@ /** + * Properties dialog content for transitions. + */ + transitionProperties : function() { + var transition = this, + content = transition.propertiesContent; + if (!content) { + // first run, create the content + content = transition.propertiesContent = $('#propertiesContentTransition').clone().attr('id', null) + .show().data('parentObject', transition); + $('.propertiesContentFieldTitle', content).val(transition.title); + + $('input', content).change(function(){ + // extract changed properties and redraw the transition + var content = $(this).closest('.dialogContainer'), + transition = content.data('parentObject'), + redrawNeeded = false, + newTitle = $('.propertiesContentFieldTitle', content).val(); + if (newTitle != transition.title) { + transition.title = newTitle; + if (transition.branch) { + transition.branch.title = newTitle; + } + redrawNeeded = true; + } + + if (redrawNeeded) { + transition.draw(); + } + }); + } + }, + + + /** * Properties dialog content for Tool activities. */ toolProperties : function() { @@ -150,13 +184,13 @@ if (!content) { // first run, create the content content = activity.propertiesContent = $('#propertiesContentTool').clone().attr('id', null) - .show().data('activity', activity); + .show().data('parentObject', activity); $('.propertiesContentFieldTitle', content).val(activity.title); $('input, select', content).change(function(){ // extract changed properties and redraw the activity var content = $(this).closest('.dialogContainer'), - activity = content.data('activity'), + activity = content.data('parentObject'), redrawNeeded = false, newTitle = $('.propertiesContentFieldTitle', content).val(); if (newTitle != activity.title) { @@ -192,7 +226,7 @@ var changeFunction = function(){ // extract changed properties and redraw the activity, if needed var content = $(this).closest('.dialogContainer'), - activity = content.data('activity'), + activity = content.data('parentObject'), redrawNeeded = false, newTitle = $('.propertiesContentFieldTitle', content).val(); if (newTitle != activity.title) { @@ -231,7 +265,7 @@ // first run, create the content content = activity.propertiesContent = $('#propertiesContentGrouping').clone().attr('id', null) - .show().data('activity', activity); + .show().data('parentObject', activity); // init widgets $('.propertiesContentFieldTitle', content).val(activity.title); @@ -276,14 +310,14 @@ if (!content) { // first run, create the content content = activity.propertiesContent = $('#propertiesContentGate').clone().attr('id', null) - .show().data('activity', activity); + .show().data('parentObject', activity); $('.propertiesContentFieldTitle', content).val(activity.title); $('.propertiesContentFieldGateType', content).val(activity.gateType); $('input, select', content).change(function(){ // extract changed properties and redraw the activity var content = $(this).closest('.dialogContainer'), - activity = content.data('activity'), + activity = content.data('parentObject'), redrawNeeded = false, newTitle = $('.propertiesContentFieldTitle', content).val(); if (newTitle != activity.title) { @@ -317,15 +351,15 @@ if (!content) { // first run, create the content content = activity.propertiesContent = $('#propertiesContentBranching').clone().attr('id', null) - .show().data('activity', activity); + .show().data('parentObject', activity); $('.propertiesContentFieldMatchGroups', content).button().click(function(){ PropertyLib.openGroupsToBranchesMappingDialog(activity); }); var changeFunction = function(){ // extract changed properties and redraw the activity var content = $(this).closest('.dialogContainer'), - activity = content.data('activity'), + activity = content.data('parentObject'), branchingActivity = activity.branchingActivity, redrawNeeded = false, newTitle = $('.propertiesContentFieldTitle', content).val(); @@ -349,7 +383,7 @@ var inputRow = $('.propertiesContentFieldInput', content).closest('tr'); if (branchingActivity.branchingType == 'tool') { branchingActivity.input = inputRow.show() - .find('option:selected').data('activity'); + .find('option:selected').data('parentObject'); } else { inputRow.hide(); branchingActivity.input = null; @@ -407,7 +441,7 @@ var option = $('