Browse Source

CDB: Fix move line with separators + move code from editor to table

LeoVgr 6 months ago
parent
commit
da7c4b5c23
3 changed files with 127 additions and 133 deletions
  1. 1 1
      hide/comp/cdb/Cursor.hx
  2. 8 128
      hide/comp/cdb/Editor.hx
  3. 118 4
      hide/comp/cdb/Table.hx

+ 1 - 1
hide/comp/cdb/Cursor.hx

@@ -85,7 +85,7 @@ class Cursor {
 				for (c in getSelectedCells())
 					if (!lines.contains(c.line))
 						lines.push(c.line);
-				editor.moveLines(lines, dy);
+				table.moveLines(lines, dy);
 			}
 			update();
 			return;

+ 8 - 128
hide/comp/cdb/Editor.hx

@@ -136,8 +136,8 @@ class Editor extends Component {
 		keys.register("redo", function() undo.redo());
 		keys.register("cdb.moveBack", () -> cursor.jump(true));
 		keys.register("cdb.moveAhead", () -> cursor.jump(false));
-		keys.register("cdb.insertLine", function() { insertLine(cursor.table,cursor.y); cursor.move(0,1,false,false,false); });
-		keys.register("duplicate", function() { duplicateLine(cursor.table,cursor.y); cursor.move(0,1,false,false,false); });
+		keys.register("cdb.insertLine", function() { cursor.table.insertLine(cursor.y); cursor.move(0,1,false,false,false); });
+		keys.register("duplicate", function() { cursor.table.duplicateLine(cursor.y); cursor.move(0,1,false,false,false); });
 		for( k in ["cdb.editCell","rename"] )
 			keys.register(k, function() {
 				var c = cursor.getCell();
@@ -1841,43 +1841,6 @@ class Editor extends Component {
 		newColumn(sheet,col);
 	}
 
-	public function insertLine( table : Table, index = 0 ) {
-		if( table == null || !table.canInsert() )
-			return;
-		if( table.displayMode == Properties ) {
-			var ins = table.element.find("select.insertField");
-			var options = [for( o in ins.find("option").elements() ) Element.getVal(o)];
-			ins.attr("size", options.length);
-			options.shift();
-			ins.focus();
-			var index = 0;
-			ins.val(options[0]);
-			ins.off();
-			ins.blur(function(_) table.refresh());
-			ins.keydown(function(e) {
-				switch( e.keyCode ) {
-				case K.ESCAPE:
-					element.focus();
-				case K.UP if( index > 0 ):
-					ins.val(options[--index]);
-				case K.DOWN if( index < options.length - 1 ):
-					ins.val(options[++index]);
-				case K.ENTER:
-					@:privateAccess table.insertProperty(Element.getVal(ins));
-				default:
-				}
-				e.stopPropagation();
-				e.preventDefault();
-			});
-			return;
-		}
-		beginChanges();
-		table.sheet.newLine(index);
-		table.refreshCellValue();
-		endChanges();
-		table.refresh();
-	}
-
 	public function ensureUniqueId(originalId : String, table : Table, column : cdb.Data.Column) {
 		var scope = table.getScope();
 		var idWithScope : String = if(column.scope != null)  table.makeId(scope, column.scope, originalId) else originalId;
@@ -1938,34 +1901,6 @@ class Editor extends Component {
         return newId;
 	}
 
-	public function duplicateLine( table : Table, index = 0 ) {
-		if( !table.canInsert() || table.displayMode != Table )
-			return;
-		var srcObj = table.sheet.lines[index];
-		beginChanges();
-		var obj = table.sheet.newLine(index);
-		table.refreshCellValue();
-		for(colId => c in table.columns ) {
-			var val = Reflect.field(srcObj, c.name);
-			if( val != null ) {
-				if( c.type != TId ) {
-					// Deep copy
-					Reflect.setField(obj, c.name, haxe.Json.parse(haxe.Json.stringify(val)));
-				} else {
-					// Increment the number at the end of the id if there is one
-
-					var newId = getNewUniqueId(val, table, c);
-					if (newId != null) {
-						Reflect.setField(obj, c.name, newId);
-					}
-				}
-			}
-		}
-		endChanges();
-		table.refresh();
-		table.getRealSheet().sync();
-	}
-
 	public function popupColumn( table : Table, col : cdb.Data.Column, ?cell : Cell ) {
 		if( view != null )
 			return;
@@ -2103,62 +2038,6 @@ class Editor extends Component {
 		// TODO : create single edit-all script view allowing global search & replace
 	}
 
-	public function moveLine( line : Line, delta : Int, exact = false ) {
-		if( !line.table.canInsert() )
-			return;
-		beginChanges();
-		var prevIndex = line.index;
-
-		var index : Null<Int> = null;
-		var currIndex : Null<Int> = line.index;
-		if (!exact) {
-			var distance = (delta >= 0 ? delta : -1 * delta);
-			for( _ in 0...distance ) {
-				currIndex = line.table.sheet.moveLine( currIndex, delta );
-				if( currIndex == null )
-					break;
-				else
-					index = currIndex;
-			}
-		}
-		else
-			while (index != prevIndex + delta) {
-				currIndex = line.table.sheet.moveLine( currIndex, delta );
-				if( currIndex == null )
-					break;
-				else
-					index = currIndex;
-			}
-
-		if( index != null ) {
-			if (index != prevIndex) {
-				if ( cursor.y == prevIndex ) cursor.set(cursor.table, cursor.x, index);
-				else if ( cursor.y > prevIndex && cursor.y <= index) cursor.set(cursor.table, cursor.x, cursor.y - 1);
-				else if ( cursor.y < prevIndex && cursor.y >= index) cursor.set(cursor.table, cursor.x, cursor.y + 1);
-			}
-			refresh();
-		}
-		endChanges();
-	}
-
-	function moveLines(lines : Array<Line>, delta : Int) {
-		if( lines.length == 0 || !lines[0].table.canInsert() || delta == 0 )
-			return;
-		beginChanges();
-		var newSelection = [{
-			x1: -1,
-			y1: lines[0].index + delta,
-			x2: -1,
-			y2: lines[lines.length - 1].index + delta
-		}];
-
-		lines.sort((a, b) -> { return (a.index - b.index) * delta * -1; });
-		for( l in lines )
-			moveLine(l, delta);
-
-		cursor.set(cursor.table, cursor.x, cursor.y, newSelection);
-		endChanges();
-	}
 
 	public function popupLine( line : Line ) {
 		if( !line.table.canInsert() ) return;
@@ -2206,10 +2085,11 @@ class Editor extends Component {
 				usedLine = lastLine;
 			}
 			var delta = lastOfGroup - usedLine.index + separatorCount(usedLine.index);
+			var linesToMove = isSelectedLine ? selectedLines : [usedLine];
 			moveSubmenu.push({
 				label : sep.title,
 				enabled : true,
-				click : isSelectedLine ? moveLines.bind(selectedLines, delta) : () -> moveLine(usedLine, delta),
+				click : () -> usedLine.table.moveLines(linesToMove, delta)
 			});
 		}
 
@@ -2233,22 +2113,22 @@ class Editor extends Component {
 			{
 				label : "Move Up",
 				enabled:  (firstLine.index > 0 || sepIndex >= 0),
-				click : isSelectedLine ? moveLines.bind(selectedLines, -1) : () -> moveLine(line, -1),
+				click : () -> line.table.moveLines(isSelectedLine ? [line] : selectedLines, -1),
 			},
 			{
 				label : "Move Down",
 				enabled:  (lastLine.index < sheet.lines.length - 1),
-				click : isSelectedLine ? moveLines.bind(selectedLines, 1) : () -> moveLine(line, 1),
+				click : () -> line.table.moveLines(isSelectedLine ? [line] : selectedLines, 1),
 			},
 			{ label : "Move to Group", enabled : moveSubmenu.length > 0, menu : moveSubmenu },
 			{ label : "", isSeparator : true },
 			{ label : "Insert", click : function() {
-				insertLine(line.table,line.index);
+				line.table.insertLine(line.index);
 				cursor.set(line.table, -1, line.index + 1);
 				focus();
 			}, keys : config.get("key.cdb.insertLine") },
 			{ label : "Duplicate", click : function() {
-				duplicateLine(line.table,line.index);
+				line.table.duplicateLine(line.index);
 				cursor.set(line.table, -1, line.index + 1);
 				focus();
 			}, keys : config.get("key.duplicate") },

+ 118 - 4
hide/comp/cdb/Table.hx

@@ -232,12 +232,12 @@ class Table extends Component {
 
 				var selection = editor.cursor.getSelectedAreaIncludingLine(line);
 				if (selection != null) {
-					editor.moveLines(editor.cursor.getLinesFromSelection(selection), selection.y1 > dropTarget.index ? dropTarget.index - selection.y1 : dropTarget.index - selection.y2);
+					moveLinesTo(editor.cursor.getLinesFromSelection(selection), dropTarget.index);
 					return true;
 				}
 
 				if (dropTarget != null) {
-					editor.moveLine(line, dropTarget.index - line.index, true);
+					line.table.moveLinesTo([line], dropTarget.index);
 					return true;
 				}
 
@@ -357,12 +357,12 @@ class Table extends Component {
 		} else if( sheet.lines.length == 0 && canInsert() ) {
 			var l = J('<tr><td colspan="${columns.length + 1}"><input class="default-cursor" type="button" value="Insert Line"/></td></tr>');
 			l.find("input").click(function(_) {
-				editor.insertLine(this);
+				insertLine();
 				editor.cursor.set(this);
 			});
 			l.find("input").keydown(function(e) {
 				if (e.keyCode != 13) return;
-				editor.insertLine(this);
+				insertLine();
 				editor.cursor.set(this);
 			});
 			element.append(l);
@@ -608,5 +608,119 @@ class Table extends Component {
 	function toString() {
 		return "Table#"+sheet.name;
 	}
+	
 
+	public function insertLine(index : Int = 0) {
+		if( !canInsert() )
+			return;
+		if( displayMode == Properties ) {
+			var ins = element.find("select.insertField");
+			var options = [for( o in ins.find("option").elements() ) Element.getVal(o)];
+			ins.attr("size", options.length);
+			options.shift();
+			ins.focus();
+			var index = 0;
+			ins.val(options[0]);
+			ins.off();
+			ins.blur(function(_) refresh());
+			ins.keydown(function(e) {
+				switch (e.keyCode) {
+					case hxd.Key.ESCAPE:
+						element.focus();
+					case hxd.Key.UP if( index > 0 ):
+						ins.val(options[--index]);
+					case hxd.Key.DOWN if( index < options.length - 1 ):
+						ins.val(options[++index]);
+					case hxd.Key.ENTER:
+						insertProperty(Element.getVal(ins));
+					default:
+				}
+				e.stopPropagation();
+				e.preventDefault();
+			});
+			return;
+		}
+		editor.beginChanges();
+		sheet.newLine(index);
+		refreshCellValue();
+		editor.endChanges();
+		refresh();
+	}
+
+	public function moveLines(lines : Array<Line>, delta : Int) {
+		if( !canInsert() )
+			return;
+		
+		editor.beginChanges();
+
+		lines.sort((a, b) -> { return (a.index - b.index) * delta * -1; });
+
+		var range = { min: 100000, max: 0 };
+		for (l in lines ) {
+			// var initialIdx = l.index;
+			var newIdx = l.index;
+			var distance = Std.int(hxd.Math.abs(delta));
+			for( _ in 0...distance ) {
+				newIdx = sheet.moveLine(newIdx, delta);
+				if( newIdx == null )
+					break;
+			
+				if (range.min > newIdx) range.min = newIdx;
+				if (range.max < newIdx) range.max = newIdx;
+			}
+		}
+
+		editor.endChanges();
+		
+		// Set cursor and selection on moved lines
+		editor.cursor.set(this, editor.cursor.x, range.min, [{ x1: -1, y1: range.min, x2: -1, y2: range.max }]);
+		
+		editor.refresh();
+	}
+
+	public function moveLinesTo(lines : Array<Line>, targetIdx : Int) {
+		var fromIdx = lines[0].index;
+		for (l in lines)
+			if (l.index < fromIdx)
+				fromIdx = l.index;
+
+		var movingUp = fromIdx > targetIdx;
+		var sepCount = 0;
+		for (s in separators) {
+			if ((movingUp && s.data.index > targetIdx && s.data.index <= fromIdx) || (!movingUp && s.data.index <= targetIdx && s.data.index > fromIdx))
+				sepCount++;
+		}
+		
+		moveLines(lines, movingUp ? (targetIdx - fromIdx) - sepCount : (targetIdx - fromIdx) + sepCount);
+
+		// Set cursor and selection on moved lines
+		editor.cursor.set(this, editor.cursor.x, targetIdx, [{ x1: -1, y1: targetIdx, x2: -1, y2: targetIdx + (lines.length - 1) }]);
+	}
+
+	public function duplicateLine(index : Int = 0) {
+		if( !canInsert() || displayMode != Table )
+			return;
+		var srcObj = sheet.lines[index];
+		editor.beginChanges();
+		var obj = sheet.newLine(index);
+		refreshCellValue();
+		for(colId => c in columns ) {
+			var val = Reflect.field(srcObj, c.name);
+			if( val != null ) {
+				if( c.type != TId ) {
+					// Deep copy
+					Reflect.setField(obj, c.name, haxe.Json.parse(haxe.Json.stringify(val)));
+				} else {
+					// Increment the number at the end of the id if there is one
+					var newId = editor.getNewUniqueId(val, this, c);
+					if (newId != null) {
+						Reflect.setField(obj, c.name, newId);
+					}
+				}
+			}
+		}
+		editor.endChanges();
+		refresh();
+		getRealSheet().sync();
+	}
 }