From ab71d9523c81209f86dc71c61c8d0562af8b4dbd Mon Sep 17 00:00:00 2001 From: Nat Quayle Nelson Date: Wed, 17 Aug 2022 22:48:24 +0000 Subject: [PATCH] drag to select works in many cases --- .../source/HabitState.kiss | 6 ++- .../src/kiss_flixel/DragToSelectPlugin.hx | 32 ++++++++++++---- .../src/kiss_flixel/KissExtendedSprite.hx | 37 +++++++++++++++++-- 3 files changed, 62 insertions(+), 13 deletions(-) diff --git a/projects/flixel-desktop-habit-puzzle-game/source/HabitState.kiss b/projects/flixel-desktop-habit-puzzle-game/source/HabitState.kiss index 33cd4136..ce0365d2 100644 --- a/projects/flixel-desktop-habit-puzzle-game/source/HabitState.kiss +++ b/projects/flixel-desktop-habit-puzzle-game/source/HabitState.kiss @@ -347,8 +347,7 @@ (set s.priorityID (+ 1 .priorityID (last (the kiss.List rewardSprites.members)))) (let [connectedPieces (recursivelyConnectedPieces s)] // Bring currently held pieces to the front: - (rewardSprites.bringAllToFront connectedPieces) - (set s.connectedSprites connectedPieces)) + (rewardSprites.bringAllToFront connectedPieces)) (set draggingSprite s) (set draggingLastPos (new FlxPoint s.x s.y)))) (set s.mouseStopDragCallback @@ -505,6 +504,9 @@ (thisConnectedPieces.push toSprite) (toConnectedPieces.push self) + (let [selfAndAttached (recursivelyConnectedPieces self)] + (doFor s selfAndAttached + (set s.connectedSprites selfAndAttached))) true)) (defMacro _checkMatch [side otherSide] diff --git a/projects/kiss-flixel/src/kiss_flixel/DragToSelectPlugin.hx b/projects/kiss-flixel/src/kiss_flixel/DragToSelectPlugin.hx index 1f61488e..00154c91 100644 --- a/projects/kiss-flixel/src/kiss_flixel/DragToSelectPlugin.hx +++ b/projects/kiss-flixel/src/kiss_flixel/DragToSelectPlugin.hx @@ -28,9 +28,9 @@ class DragToSelectPlugin extends FlxBasic { } public function enableSprite(s:KissExtendedSprite, ?state:FlxState, ?camera:FlxCamera) { + if (state == null) state = FlxG.state; + if (camera == null) camera = FlxG.camera; if (!dragStates.exists(state)) { - if (state == null) state = FlxG.state; - if (camera == null) camera = FlxG.camera; dragStates[state] = { camera: camera, debugLayer: new DebugLayer(), @@ -46,6 +46,14 @@ class DragToSelectPlugin extends FlxBasic { } } + public function selectedSprites() { + return dragStates[FlxG.state].selectedSprites; + } + + public function deselectSprites() { + dragStates[FlxG.state].selectedSprites = []; + } + public override function update(elapsed:Float) { if (dragStates.exists(FlxG.state)) { var dragState = dragStates[FlxG.state]; @@ -56,11 +64,9 @@ class DragToSelectPlugin extends FlxBasic { if (FlxMouseControl.dragTarget == null) { if (FlxG.mouse.justPressed) { dragState.firstCorner = FlxG.mouse.getWorldPosition(dragState.camera); - } else if (FlxG.mouse.justReleased) { - dragState.firstCorner = null; - } + } dragState.secondCorner = FlxG.mouse.getWorldPosition(dragState.camera); - if (dragState.firstCorner != null) { + if (dragState.firstCorner != null && dragState.selectedSprites.length == 0) { var rounded1 = dragState.firstCorner.copyTo(); var rounded2 = dragState.secondCorner.copyTo(); for (r in [rounded1, rounded2]) { @@ -68,8 +74,20 @@ class DragToSelectPlugin extends FlxBasic { r.y = Std.int(r.y); } var rect = new FlxRect().fromTwoPoints(rounded1, rounded2); - if (!rect.isEmpty) + if (FlxG.mouse.justReleased && dragState.selectedSprites.length == 0) { + dragState.firstCorner = null; + for (s in dragState.enabledSprites) { + if (s.scale.x != 1 || s.scale.y != 1) { + throw "DragToSelectPlugin can't handle scaled sprites yet!"; + } + if (!s.getRotatedBounds().intersection(rect).isEmpty) { + // TODO if pixel perfect is true, get the pixels in the intersection and hit test them for transparency + dragState.selectedSprites.push(s); + } + } + } else if (!rect.isEmpty) { dragState.debugLayer.drawFlxRect(rect); + } } } } diff --git a/projects/kiss-flixel/src/kiss_flixel/KissExtendedSprite.hx b/projects/kiss-flixel/src/kiss_flixel/KissExtendedSprite.hx index d7d08482..8233c525 100644 --- a/projects/kiss-flixel/src/kiss_flixel/KissExtendedSprite.hx +++ b/projects/kiss-flixel/src/kiss_flixel/KissExtendedSprite.hx @@ -22,20 +22,46 @@ class KissExtendedSprite extends flixel.addons.display.FlxExtendedSprite { var mouseStartPos:FlxPoint = null; public var connectedSprites:Array = []; + function connectedAndSelectedSprites() { + var l = connectedSprites; + var map = [for (s in l) s => true]; + if (_dragToSelectEnabled) { + var plugin = FlxG.plugins.get(DragToSelectPlugin); + for (s in plugin.selectedSprites()) { + map[s] = true; + for (c in s.connectedSprites) { + map[c] = true; + } + } + } + // Remove duplicates and return + l = [for (s => bool in map) s]; + return l; + } var connectedSpritesStartPos:Array = []; function resetStartPos() { dragStartPos = new FlxPoint(x, y); - connectedSpritesStartPos = [for (s in connectedSprites) new FlxPoint(s.x, s.y)]; + connectedSpritesStartPos = [for (s in connectedAndSelectedSprites()) new FlxPoint(s.x, s.y)]; mouseStartPos = FlxG.mouse.getWorldPosition(); } public override function startDrag() { super.startDrag(); + if (_dragToSelectEnabled) { + var plugin = FlxG.plugins.get(DragToSelectPlugin); + if (plugin.selectedSprites().indexOf(this) == -1) + plugin.deselectSprites(); + } + resetStartPos(); } + public override function stopDrag() { + super.stopDrag(); + } + private var rotationPadding = new FlxPoint(); public function getRotationPadding() { return rotationPadding.copyTo(); @@ -71,7 +97,7 @@ class KissExtendedSprite extends flixel.addons.display.FlxExtendedSprite { } } _rot(this, deg); - for (c in connectedSprites) { + for (c in connectedAndSelectedSprites()) { if (c != this) { _rot(c, deg); } @@ -79,6 +105,7 @@ class KissExtendedSprite extends flixel.addons.display.FlxExtendedSprite { resetStartPos(); } + var _dragToSelectEnabled = false; public function enableDragToSelect(?state:FlxState) { var plugin = FlxG.plugins.get(DragToSelectPlugin); if (plugin == null) { @@ -86,6 +113,7 @@ class KissExtendedSprite extends flixel.addons.display.FlxExtendedSprite { FlxG.plugins.add(plugin); } plugin.enableSprite(this, state, thisCamera()); + _dragToSelectEnabled = true; } override function update(elapsed:Float) { @@ -100,8 +128,9 @@ class KissExtendedSprite extends flixel.addons.display.FlxExtendedSprite { var nextPos = dragStartPos.copyTo().addPoint(mouseTotalMovement); x = nextPos.x; y = nextPos.y; - for (i in 0...connectedSprites.length) { - var sprite = connectedSprites[i]; + var l = connectedAndSelectedSprites(); + for (i in 0...l.length) { + var sprite = l[i]; var startPos = connectedSpritesStartPos[i]; var nextPos = startPos.copyTo().addPoint(mouseTotalMovement); sprite.x = nextPos.x;