[Libreoffice-commits] online.git: 2 commits - bundled/include loleaflet/src

Libreoffice Gerrit user logerrit at kemper.freedesktop.org
Mon May 20 08:40:10 UTC 2019


 bundled/include/LibreOfficeKit/LibreOfficeKitEnums.h |   37 +++-
 loleaflet/src/layer/tile/TileLayer.js                |  164 +++++++++++--------
 loleaflet/src/layer/vector/Path.Drag.js              |   28 +++
 loleaflet/src/layer/vector/SVGGroup.js               |    6 
 4 files changed, 166 insertions(+), 69 deletions(-)

New commits:
commit 502dc97cb235a76f9c3a44a8bd7326219907e3b0
Author:     Marco Cecchetti <mrcekets at gmail.com>
AuthorDate: Tue Mar 26 15:19:20 2019 +0100
Commit:     Marco Cecchetti <mrcekets at gmail.com>
CommitDate: Mon May 20 10:40:05 2019 +0200

    lok: update graphic selection callback description
    
    Change-Id: Iebc3d17ac8e81ea99dda64cd97807656f5941637
    Reviewed-on: https://gerrit.libreoffice.org/70574
    Reviewed-by: Marco Cecchetti <mrcekets at gmail.com>
    Tested-by: Marco Cecchetti <mrcekets at gmail.com>

diff --git a/bundled/include/LibreOfficeKit/LibreOfficeKitEnums.h b/bundled/include/LibreOfficeKit/LibreOfficeKitEnums.h
index af4952566..f3fc91b2f 100644
--- a/bundled/include/LibreOfficeKit/LibreOfficeKitEnums.h
+++ b/bundled/include/LibreOfficeKit/LibreOfficeKitEnums.h
@@ -162,11 +162,40 @@ typedef enum
      */
     LOK_CALLBACK_CURSOR_VISIBLE = 5,
     /**
-     * The size and/or the position of the graphic selection changed and
-     * the rotation angle of the embedded graphic object
+     * The size and/or the position of the graphic selection changed,
+     * the rotation angle of the embedded graphic object, and a property list
+     * which can be used for informing the client about severl properties.
      *
-     * Format is "x, y, width, height, angle", where angle is in 100th
-     * of degree.
+     * Format is "x, y, width, height, angle, { list of properties }",
+     * where angle is in 100th of degree, and the property list is optional.
+     *
+     * The "{ list of properties }" part is in JSON format.
+     * Follow some examples of the property list part:
+     *
+     * 1) when the selected object is an image inserted in Writer:
+     *
+     *      { "isWriterGraphic": true }
+     *
+     * 2) when the selected object is a chart legend:
+     *
+     *      { "isDraggable": true, "isResizable": true, "isRotatable": false }
+     *
+     * 3) when the selected object is a pie segment in a chart:
+     *
+     *      {
+     *          "isDraggable": true,
+     *          "isResizable": false,
+     *          "isRotatable": false,
+     *          "dragInfo": {
+     *              "dragMethod": "PieSegmentDragging",
+     *              "initialOffset": 50,
+     *              "dragDirection": [x, y],
+     *              "svg": "<svg ..."
+     *          }
+     *      }
+     *
+     *      where the "svg" property is a string containing an svg document
+     *      which is a rapresentation of the pie segment.
      */
     LOK_CALLBACK_GRAPHIC_SELECTION = 6,
 
commit ba4cd1563d8ecfc3749c6a512cccf6334bc31108
Author:     Marco Cecchetti <mrcekets at gmail.com>
AuthorDate: Wed Apr 10 23:44:35 2019 +0200
Commit:     Marco Cecchetti <mrcekets at gmail.com>
CommitDate: Mon May 20 10:39:52 2019 +0200

    loleaflet: constrained dragging for pie segment
    
    The extra information for the graphic selection is now formatted
    according to JSON syntax so that is easier to parse.
    
    Dragging a pie segment now is constrained as on desktop and there is
    also a preview of the pie segment while it is dragged.
    
    On drag end a msg is sent to core with the new pie segment offset
    from the pie center, which allows core to move the pie segment to
    the correct position.
    
    Change-Id: I7f76d21d622006fca5d0922c5932daec50b13836
    Reviewed-on: https://gerrit.libreoffice.org/70573
    Reviewed-by: Marco Cecchetti <mrcekets at gmail.com>
    Tested-by: Marco Cecchetti <mrcekets at gmail.com>

diff --git a/loleaflet/src/layer/tile/TileLayer.js b/loleaflet/src/layer/tile/TileLayer.js
index 6028fe3ad..e6c4aa0af 100644
--- a/loleaflet/src/layer/tile/TileLayer.js
+++ b/loleaflet/src/layer/tile/TileLayer.js
@@ -643,55 +643,49 @@ L.TileLayer = L.GridLayer.extend({
 	},
 
 	_onGraphicSelectionMsg: function (textMsg) {
-
 		if (textMsg.match('EMPTY')) {
 			this._graphicSelectionTwips = new L.Bounds(new L.Point(0, 0), new L.Point(0, 0));
 			this._graphicSelection = new L.LatLngBounds(new L.LatLng(0, 0), new L.LatLng(0, 0));
 		}
 		else {
-			var data = textMsg.split('{');
-			var strTwips = data[0].match(/\d+/g);
-			var topLeftTwips = new L.Point(parseInt(strTwips[0]), parseInt(strTwips[1]));
-			var offset = new L.Point(parseInt(strTwips[2]), parseInt(strTwips[3]));
+			textMsg = '[' + textMsg.substr('graphicselection:'.length) + ']';
+			var msgData = JSON.parse(textMsg);
+			var topLeftTwips = new L.Point(msgData[0], msgData[1]);
+			var offset = new L.Point(msgData[2], msgData[3]);
 			var bottomRightTwips = topLeftTwips.add(offset);
 			this._graphicSelectionTwips = new L.Bounds(topLeftTwips, bottomRightTwips);
 			this._graphicSelection = new L.LatLngBounds(
-							this._twipsToLatLng(topLeftTwips, this._map.getZoom()),
-							this._twipsToLatLng(bottomRightTwips, this._map.getZoom()));
-			this._graphicSelectionAngle = (strTwips.length > 4) ? parseInt(strTwips[4]) : 0;
-			this._isSelectionWriterGraphic = false;
-			this._isGraphicSelectionDraggable = true;
-			this._isGraphicSelectionResizable = true;
-			this._isGraphicSelectionRotatable = true;
-
-			if (data.length > 1) {
-				var properties = data[1].slice(0, -1).split(',');
-
-				var i;
-				for (i = 0; i < properties.length; ++i) {
-					var property = properties[i].split('=');
-					if (property.length !== 2)
-						continue;
-					var name = property[0].trim();
-					var value = property[1].trim() === 'true';
-					if (name === 'WriterGraphic') {
-						this._isSelectionWriterGraphic = value;
-					}
-					else if (name === 'Draggable') {
-						this._isGraphicSelectionDraggable = value;
-					}
-					else if (name === 'Resizable') {
-						this._isGraphicSelectionResizable = value;
-					}
-					else if (name === 'Rotatable') {
-						this._isGraphicSelectionRotatable = value;
-					}
+				this._twipsToLatLng(topLeftTwips, this._map.getZoom()),
+				this._twipsToLatLng(bottomRightTwips, this._map.getZoom()));
+
+			this._graphicSelectionAngle = (msgData.length > 4) ? msgData[4] : 0;
+
+			this._graphicSelection.extraInfo = {};
+			if (msgData.length > 5) {
+				this._graphicSelection.extraInfo = msgData[5];
+				var dragInfo = this._graphicSelection.extraInfo.dragInfo;
+				if (dragInfo && dragInfo.dragMethod === 'PieSegmentDragging') {
+					dragInfo.initialOffset /= 100.0;
+					var dragDir = dragInfo.dragDirection;
+					dragInfo.dragDirection = this._twipsToPixels(new L.Point(dragDir[0], dragDir[1]));
+					dragDir = dragInfo.dragDirection;
+					dragInfo.range2 = dragDir.x * dragDir.x + dragDir.y * dragDir.y;
 				}
 			}
+			
+			// defaults
+			var extraInfo = this._graphicSelection.extraInfo;
+			if (extraInfo.isDraggable === undefined)
+				extraInfo.isDraggable = true;
+			if (extraInfo.isResizable === undefined)
+				extraInfo.isResizable = true;
+			if (extraInfo.isRotatable === undefined)
+				extraInfo.isRotatable = true;
+
 			// Workaround for tdf#123874. For some reason the handling of the
 			// shapeselectioncontent messages that we get back causes the WebKit process
 			// to crash on iOS.
-			if (!window.ThisIsTheiOSApp && this._isGraphicSelectionDraggable) {
+			if (!window.ThisIsTheiOSApp && this._graphicSelection.extraInfo.isDraggable && !this._graphicSelection.extraInfo.svg) {
 				this._map._socket.sendMessage('rendershapeselection mimetype=image/svg+xml');
 			}
 		}
@@ -1852,30 +1846,66 @@ L.TileLayer = L.GridLayer.extend({
 				return;
 			}
 
-			var newPos = this._graphicSelectionTwips.min.add(deltaPos);
-			var size = this._graphicSelectionTwips.getSize();
+			var param;
+			var dragConstraint = this._graphicSelection.extraInfo.dragInfo;
+			if (dragConstraint) {
+				if (dragConstraint.dragMethod === 'PieSegmentDragging') {
+
+					deltaPos = this._twipsToPixels(deltaPos);
+					var dx = deltaPos.x;
+					var dy = deltaPos.y;
+
+					var initialOffset = dragConstraint.initialOffset;
+					var dragDirection = dragConstraint.dragDirection;
+					var additionalOffset = (dx * dragDirection.x + dy * dragDirection.y) / dragConstraint.range2;
+					if (additionalOffset < -initialOffset)
+						additionalOffset = -initialOffset;
+					else if (additionalOffset > (1.0 - initialOffset))
+						additionalOffset = 1.0 - initialOffset;
+
+					var offset = Math.round((initialOffset + additionalOffset) * 100);
+
+					// hijacking the uno:TransformDialog msg for sending the new offset value
+					// for the pie segment dragging method;
+					// indeed there isn't any uno msg dispatching on the core side, but a chart controller dispatching
+					param = {
+						Action: {
+							type: 'string',
+							value: 'PieSegmentDragging'
+						},
+						Offset: {
+							type: 'long',
+							value: offset
+						}
+					};
+				}
+			}
+			else {
+				var newPos = this._graphicSelectionTwips.min.add(deltaPos);
+				var size = this._graphicSelectionTwips.getSize();
 
-			// try to keep shape inside document
-			if (newPos.x + size.x > this._docWidthTwips)
-				newPos.x = this._docWidthTwips - size.x;
-			if (newPos.x < 0)
-				newPos.x = 0;
+				// try to keep shape inside document
+				if (newPos.x + size.x > this._docWidthTwips)
+					newPos.x = this._docWidthTwips - size.x;
+				if (newPos.x < 0)
+					newPos.x = 0;
 
-			if (newPos.y + size.y > this._docHeightTwips)
-				newPos.y = this._docHeightTwips - size.y;
-			if (newPos.y < 0)
-				newPos.y = 0;
+				if (newPos.y + size.y > this._docHeightTwips)
+					newPos.y = this._docHeightTwips - size.y;
+				if (newPos.y < 0)
+					newPos.y = 0;
 
-			var param = {
-				TransformPosX: {
-					type: 'long',
-					value: newPos.x
-				},
-				TransformPosY: {
-					type: 'long',
-					value: newPos.y
-				}
-			};
+				param = {
+					TransformPosX: {
+						type: 'long',
+						value: newPos.x
+					},
+					TransformPosY: {
+						type: 'long',
+						value: newPos.y
+					}
+				};
+			}
 			this._map.sendUnoCommand('.uno:TransformDialog ', param);
 			this._graphicMarker.isDragged = false;
 		}
@@ -1963,7 +1993,9 @@ L.TileLayer = L.GridLayer.extend({
 			// For an image in Writer we need to send the size of the image not of the selection box.
 			// So if the image has been rotated we need to compute its size starting from the size of the selection
 			// rectangle and the rotation angle.
-			if (this._isSelectionWriterGraphic) {
+			var isSelectionWriterGraphic =
+				this._graphicSelection.extraInfo ? this._graphicSelection.extraInfo.isWriterGraphic : false;
+			if (isSelectionWriterGraphic) {
 				if (this._isGraphicAngleDivisibleBy90()) {
 					var k = this._graphicSelectionAngle / 9000;
 					// if k is even we have nothing to do since the rotation is 0 or 180.
@@ -2015,7 +2047,7 @@ L.TileLayer = L.GridLayer.extend({
 
 			this._map.sendUnoCommand('.uno:TransformDialog ', param);
 
-			if (this._isSelectionWriterGraphic) {
+			if (isSelectionWriterGraphic) {
 				param = {
 					TransformPosX: {
 						type: 'long',
@@ -2130,8 +2162,10 @@ L.TileLayer = L.GridLayer.extend({
 				return;
 			}
 
+			var extraInfo = this._graphicSelection.extraInfo;
 			this._graphicMarker = L.svgGroup(this._graphicSelection, {
-				draggable: this._isGraphicSelectionDraggable,
+				draggable: extraInfo.isDraggable,
+				dragConstraint: extraInfo.dragInfo,
 				transform: true,
 				stroke: false,
 				fillOpacity: 0,
@@ -2147,12 +2181,16 @@ L.TileLayer = L.GridLayer.extend({
 			this._graphicMarker.on('scalestart scaleend', this._onGraphicEdit, this);
 			this._graphicMarker.on('rotatestart rotateend', this._onGraphicRotate, this);
 			this._map.addLayer(this._graphicMarker);
-			if (this._isGraphicSelectionDraggable)
+			if (extraInfo.isDraggable)
 				this._graphicMarker.dragging.enable();
 			this._graphicMarker.transform.enable({
-				scaling: this._isGraphicSelectionResizable,
-				rotation: this._isGraphicSelectionRotatable,
+				scaling: extraInfo.isResizable,
+				rotation: extraInfo.isRotatable,
 				uniformScaling: !this._isGraphicAngleDivisibleBy90()});
+			if (extraInfo.dragInfo && extraInfo.dragInfo.svg) {
+				this._graphicMarker.removeEmbeddedSVG();
+				this._graphicMarker.addEmbeddedSVG(extraInfo.dragInfo.svg);
+			}
 		}
 		else if (this._graphicMarker) {
 			this._graphicMarker.off('graphicmovestart graphicmoveend', this._onGraphicMove, this);
diff --git a/loleaflet/src/layer/vector/Path.Drag.js b/loleaflet/src/layer/vector/Path.Drag.js
index 04ab67373..b35c02b98 100644
--- a/loleaflet/src/layer/vector/Path.Drag.js
+++ b/loleaflet/src/layer/vector/Path.Drag.js
@@ -159,6 +159,32 @@ L.Handler.PathDrag = L.Handler.extend(/** @lends  L.Path.Drag.prototype */ {
 		var dx = x - this._startPoint.x;
 		var dy = y - this._startPoint.y;
 
+		if (isNaN(dx) || isNaN(dy))
+			return;
+
+		if (this.constraint) {
+			if (this.constraint.dragMethod === 'PieSegmentDragging') {
+				var initialOffset = this.constraint.initialOffset;
+				var dragDirection = this.constraint.dragDirection;
+
+				var dsx = x - this._dragStartPoint.x;
+				var dsy = y - this._dragStartPoint.y;
+				var additionalOffset = (dsx * dragDirection.x + dsy * dragDirection.y) / this.constraint.range2;
+				var currentOffset = (dx * dragDirection.x + dy * dragDirection.y) / this.constraint.range2;
+
+				if (additionalOffset < -initialOffset && currentOffset < 0)
+					currentOffset = 0;
+				else if (additionalOffset > (1.0 - initialOffset) && currentOffset > 0)
+					currentOffset = 0;
+
+				dx = currentOffset * dragDirection.x;
+				dy = currentOffset * dragDirection.y;
+
+				x = this._startPoint.x + dx;
+				y = this._startPoint.y + dy;
+			}
+		}
+
 		// Send events only if point was moved
 		if (dx || dy) {
 			if (!this._path._dragMoved) {
@@ -367,8 +393,10 @@ var fnInitHook = function() {
 			L.Handler.PathDrag.makeDraggable(this);
 			this.dragging.enable();
 		}
+		this.dragging.constraint = this.options.dragConstraint;
 	} else if (this.dragging) {
 		this.dragging.disable();
+		this.dragging.constraint = null;
 	}
 };
 
diff --git a/loleaflet/src/layer/vector/SVGGroup.js b/loleaflet/src/layer/vector/SVGGroup.js
index fb58fe528..48a1e5967 100644
--- a/loleaflet/src/layer/vector/SVGGroup.js
+++ b/loleaflet/src/layer/vector/SVGGroup.js
@@ -63,6 +63,7 @@ L.SVGGroup = L.Layer.extend({
 
 		L.DomEvent.on(this._dragShape, 'mousemove', this._onDrag, this);
 		L.DomEvent.on(this._dragShape, 'mouseup', this._onDragEnd, this);
+		L.DomEvent.on(this._dragShape, 'mouseout', this._onDragEnd, this);
 
 		L.DomEvent.on(this._dragShape, 'touchmove', this._onDrag, this);
 		L.DomEvent.on(this._dragShape, 'touchend', this._onDragEnd, this);
@@ -96,7 +97,6 @@ L.SVGGroup = L.Layer.extend({
 			containerPoint: this._map.mouseEventToContainerPoint(evt)
 		};
 		this.dragging._onDrag(data);
-
 	},
 
 	_onDragEnd: function(evt) {
@@ -107,6 +107,7 @@ L.SVGGroup = L.Layer.extend({
 			return;
 		L.DomEvent.off(this._dragShape, 'mousemove', this._onDrag, this);
 		L.DomEvent.off(this._dragShape, 'mouseup', this._onDragEnd, this);
+		L.DomEvent.off(this._dragShape, 'mouseout', this._onDragEnd, this);
 
 		L.DomEvent.off(this._dragShape, 'touchmove', this._onDrag, this);
 		L.DomEvent.off(this._dragShape, 'touchend', this._onDragEnd, this);
@@ -116,7 +117,8 @@ L.SVGGroup = L.Layer.extend({
 		var pos = this._map.mouseEventToLatLng(evt);
 		this.fire('graphicmoveend', {pos: pos});
 
-		this.dragging._onDragEnd(evt);
+		if (evt.type === 'mouseup')
+			this.dragging._onDragEnd(evt);
 	},
 
 	bringToFront: function () {


More information about the Libreoffice-commits mailing list