mirror of
https://github.com/ninjamuffin99/Funkin.git
synced 2025-09-01 03:15:53 +00:00
323 lines
8.1 KiB
Haxe
323 lines
8.1 KiB
Haxe
package funkin.util.plugins;
|
|
|
|
import flixel.FlxG;
|
|
import flixel.FlxSprite;
|
|
import flixel.FlxCamera;
|
|
import flixel.group.FlxSpriteGroup.FlxTypedSpriteGroup;
|
|
import flixel.input.touch.FlxTouch;
|
|
import flixel.math.FlxAngle;
|
|
import flixel.math.FlxPoint;
|
|
import flixel.system.FlxAssets.FlxGraphicAsset;
|
|
import flixel.tweens.FlxEase;
|
|
import flixel.tweens.FlxTween;
|
|
import flixel.util.FlxColor;
|
|
import flixel.util.FlxTimer;
|
|
import funkin.graphics.FunkinCamera;
|
|
|
|
// TODO: Replace all the touchBuddy littered around the game's code with the ACTUAL touchBuddy.
|
|
// Thnk u agua and toffee <3
|
|
|
|
/**
|
|
* @author moondroidcoder
|
|
* Tracks your touch points in your game.
|
|
*/
|
|
class TouchPointerPlugin extends FlxTypedSpriteGroup<TouchPointer>
|
|
{
|
|
/**
|
|
* Whether the plugin is enabled.
|
|
*/
|
|
public static var enabled(default, set):Bool = true;
|
|
|
|
/**
|
|
* A singleton instance of the plugin.
|
|
*/
|
|
private static var instance:TouchPointerPlugin = null;
|
|
|
|
/**
|
|
* A camera dedicated to displaying the pointers.
|
|
*/
|
|
private static var pointerCamera:FlxCamera;
|
|
|
|
public function new()
|
|
{
|
|
super();
|
|
}
|
|
|
|
/**
|
|
* Initializes the TouchPointerPlugin by creating a new camera and setting it up to be drawn on top of other elements.
|
|
*/
|
|
public static function initialize():Void
|
|
{
|
|
pointerCamera = new FlxCamera();
|
|
pointerCamera.bgColor.alpha = 0;
|
|
instance = new TouchPointerPlugin();
|
|
instance.cameras = [pointerCamera];
|
|
|
|
FlxG.cameras.add(pointerCamera, false);
|
|
FlxG.plugins.drawOnTop = true;
|
|
FlxG.plugins.addPlugin(instance);
|
|
|
|
function moveCameraToTop(camera:FlxCamera):Void
|
|
{
|
|
if (camera == pointerCamera && pointerCamera == null) return;
|
|
|
|
// If there aren't any cameras then the CameraFrontEnd got reset so we have to wait for that finish (which is most of the time after state switch)
|
|
if (FlxG.cameras.list.length == 0)
|
|
{
|
|
FlxG.signals.postStateSwitch.addOnce(moveCameraToTop.bind(null));
|
|
return;
|
|
}
|
|
|
|
if (FlxG.cameras.list.contains(pointerCamera))
|
|
{
|
|
FlxG.cameras.list.remove(pointerCamera);
|
|
}
|
|
|
|
if (FlxG.game.contains(pointerCamera.flashSprite))
|
|
{
|
|
FlxG.game.removeChild(pointerCamera.flashSprite);
|
|
}
|
|
|
|
@:privateAccess
|
|
FlxG.game.addChildAt(pointerCamera.flashSprite, FlxG.game.getChildIndex(FlxG.game._inputContainer));
|
|
FlxG.cameras.list.push(pointerCamera);
|
|
}
|
|
|
|
FlxG.cameras.cameraAdded.add(moveCameraToTop);
|
|
|
|
FlxG.cameras.cameraRemoved.add(function(camera:FlxCamera) {
|
|
if (camera == pointerCamera)
|
|
{
|
|
if (!camera.exists) // The camera got destroyed, we make a new one!
|
|
{
|
|
instance.cameras = [pointerCamera = new FlxCamera()];
|
|
moveCameraToTop(null);
|
|
pointerCamera.bgColor.alpha = 0;
|
|
pointerCamera.ID = FlxG.cameras.list.length - 1;
|
|
}
|
|
else // It's not destroyed so just move it to the top!
|
|
{
|
|
moveCameraToTop(null);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
moveCameraToTop(null);
|
|
}
|
|
});
|
|
|
|
FlxG.signals.preStateSwitch.add(function() {
|
|
instance.removeAll();
|
|
});
|
|
}
|
|
|
|
override public function update(elapsed:Float):Void
|
|
{
|
|
super.update(elapsed);
|
|
|
|
for (touch in FlxG.touches.list)
|
|
{
|
|
if (touch == null) continue;
|
|
|
|
if (touch.justPressed) removeAll(true);
|
|
|
|
var pointer:TouchPointer = findPointerByTouchId(touch.touchPointID);
|
|
|
|
if (pointer == null)
|
|
{
|
|
pointer = recycle(TouchPointer);
|
|
pointer.initialize(touch.touchPointID);
|
|
add(pointer);
|
|
}
|
|
|
|
pointer.updateFromTouch(touch, pointerCamera);
|
|
}
|
|
|
|
for (pointer in members)
|
|
{
|
|
if (pointer == null || touchExists(pointer.touchId)) continue;
|
|
if (pointer.touchId != -2)
|
|
{
|
|
pointer.alpha = 0.8;
|
|
FlxTween.tween(pointer, {alpha: 0}, FlxG.random.float(0.8, 0.9),
|
|
{
|
|
ease: FlxEase.cubeIn,
|
|
onComplete: function(_) {
|
|
remove(pointer, true);
|
|
}
|
|
});
|
|
pointer.touchId = -2;
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Finds a TouchPointer object in the members list by its touch ID.
|
|
*
|
|
* @param touchId The ID of the touch to find.
|
|
* @return The TouchPointer object with the specified touch ID, or null if not found.
|
|
*/
|
|
private function findPointerByTouchId(touchId:Int):TouchPointer
|
|
{
|
|
for (pointer in members)
|
|
{
|
|
if (pointer == null || pointer.touchId != touchId) continue;
|
|
|
|
return pointer;
|
|
}
|
|
return null;
|
|
}
|
|
|
|
/**
|
|
* Checks if a touch with the specified ID exists in the current touch list.
|
|
*
|
|
* @param touchId The ID of the touch to check for.
|
|
* @return True if a touch with the specified ID exists, false otherwise.
|
|
*/
|
|
private function touchExists(touchId:Int):Bool
|
|
{
|
|
for (touch in FlxG.touches.list)
|
|
{
|
|
if (touch.touchPointID != touchId) continue;
|
|
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
@:noCompletion
|
|
private static function set_enabled(value:Bool):Bool
|
|
{
|
|
if (instance != null)
|
|
{
|
|
instance.exists = instance.visible = instance.active = instance.alive = value;
|
|
}
|
|
|
|
return enabled = value;
|
|
}
|
|
|
|
public function removeAll(skipTween:Bool = false)
|
|
{
|
|
for (pointer in members)
|
|
{
|
|
if (pointer == null) continue;
|
|
|
|
if (skipTween)
|
|
{
|
|
FlxTween.cancelTweensOf(pointer);
|
|
remove(pointer, true);
|
|
continue;
|
|
}
|
|
|
|
pointer.alpha = 0.8;
|
|
FlxTween.tween(pointer, {alpha: 0}, FlxG.random.float(0.8, 1),
|
|
{
|
|
ease: FlxEase.quadIn,
|
|
onComplete: function(_) {
|
|
remove(pointer, true);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Represents a touch pointer in the game.
|
|
*/
|
|
class TouchPointer extends FlxSprite
|
|
{
|
|
/**
|
|
* Represents a touch pointer plugin.
|
|
*/
|
|
public var touchId:Int = -1;
|
|
|
|
/**
|
|
* An internal point for grabbing the view position of the camera.
|
|
* Useful for reducing point allocation.
|
|
*/
|
|
private var viewPoint:FlxPoint;
|
|
|
|
/**
|
|
* Stores the last position of the touch pointer.
|
|
*/
|
|
private var lastPosition:FlxPoint;
|
|
|
|
/**
|
|
* Constructor for the TouchPointerPlugin class.
|
|
* Initializes the touch pointer graphic and sets the scroll factor.
|
|
*/
|
|
public function new()
|
|
{
|
|
super();
|
|
makeGraphic(16, 16, FlxColor.RED);
|
|
scrollFactor.set(0, 0);
|
|
viewPoint = FlxPoint.get();
|
|
lastPosition = FlxPoint.get();
|
|
}
|
|
|
|
/**
|
|
* Initializes the touch pointer object itself with the specified touch ID.
|
|
* Loads the graphic for the touch pointer.
|
|
*
|
|
* @param touchId The ID of the touch event to initialize.
|
|
*/
|
|
public function initialize(touchId:Int):Void
|
|
{
|
|
this.touchId = touchId;
|
|
loadGraphic("assets/images/cursor/michael.png");
|
|
}
|
|
|
|
/**
|
|
* Updates the position and angle of the touch pointer based on the given touch input.
|
|
* Used in TouchPointerPlugin's update method.
|
|
*
|
|
* @param touch The FlxTouch object containing the current touch input data.
|
|
* @param camera The FlxCamera to grab the touch's view position from.
|
|
*/
|
|
public function updateFromTouch(touch:FlxTouch, camera:FlxCamera):Void
|
|
{
|
|
// Grab the view coordinates
|
|
touch.getViewPosition(camera, viewPoint);
|
|
|
|
// Update position
|
|
x = viewPoint.x - width / 2;
|
|
y = viewPoint.y - height / 2;
|
|
|
|
if (camera.target != null)
|
|
{
|
|
x -= camera.target.x;
|
|
y -= camera.target.y;
|
|
}
|
|
|
|
// Calculate angle if moving
|
|
if (lastPosition.distanceTo(FlxPoint.weak(viewPoint.x, viewPoint.y)) > 3)
|
|
{
|
|
var angle = FlxAngle.angleBetweenPoint(this, lastPosition, true);
|
|
this.angle = angle;
|
|
loadGraphic("assets/images/cursor/kevin.png");
|
|
}
|
|
else
|
|
{
|
|
angle = 0;
|
|
loadGraphic("assets/images/cursor/michael.png");
|
|
}
|
|
|
|
lastPosition.copyFrom(viewPoint);
|
|
}
|
|
|
|
override public function destroy():Void
|
|
{
|
|
viewPoint.put();
|
|
lastPosition.put();
|
|
super.destroy();
|
|
}
|
|
|
|
override public function loadGraphic(graphic:FlxGraphicAsset, animated = false, frameWidth = 0, frameHeight = 0, unique = false, ?key:String):FlxSprite
|
|
{
|
|
super.loadGraphic(graphic, animated, frameWidth, frameHeight, unique, key);
|
|
color = 0xff6666e1;
|
|
blend = "screen";
|
|
return this;
|
|
}
|
|
}
|