Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- package;
- import flixel.math.FlxRect;
- import openfl.display.Graphics;
- import flixel.math.FlxVector;
- import flixel.math.FlxPoint;
- import flixel.FlxCamera;
- import flixel.FlxG;
- import flixel.FlxObject;
- import flixel.FlxSprite;
- import flixel.math.FlxVelocity;
- using zero.ext.FloatExt;
- using zero.ext.flx.FlxPointExt;
- class Dolly extends FlxObject {
- var target:Null<BaseEntity>;
- var zoom:Float;
- var lerp:Float;
- var mode:Mode;
- var radius:Float = 20;
- var forward_offset:Float = 5;
- public function new(target:BaseEntity) {
- super(0, 0, radius * 2, radius * 2);
- lerp = 0.25;
- switch_target(target, true);
- init();
- }
- function init() {
- FlxG.camera.follow(this, FlxCameraFollowStyle.LOCKON);
- // FlxG.camera.followLead.set(0, 20);
- FlxG.camera.deadzone.set((FlxG.camera.width - width).half(), (FlxG.camera.height - height).half(), width, height);
- }
- function focus(position:FlxPoint) {
- x = position.x - width.half();
- y = position.y - height.half();
- }
- /**
- * Switches the camera target
- * @param target the target to follow
- * @param snap whether or not to snap to target immediately
- */
- public function switch_target(?target:BaseEntity, snap:Bool = false):Void {
- this.target = target;
- if (target == null) return;
- if (snap) focus(target.getPosition().add(target.width.half(), target.height));
- }
- override public function update(dt:Float):Void {
- if (target == null) {
- super.update(dt);
- return;
- }
- var pos = getMidpoint();
- var tarPos = target.getMidpoint();
- forward_focus(pos, tarPos);
- update_position(pos, tarPos);
- camera_angle();
- super.update(dt);
- pos.put();
- tarPos.put();
- }
- function forward_focus(pos:FlxPoint, tarPos:FlxPoint) {
- var v = FlxVelocity.velocityFromAngle(target.relative_rotation, forward_offset);
- setPosition(x + (v.x * 0.3), y + (v.y * 0.3));
- v.put();
- }
- function update_position(pos:FlxPoint, tarPos:FlxPoint) {
- var d = pos.distance(tarPos);
- if (d > radius) {
- var a = pos.get_angle_between(tarPos);
- var o = (d - radius) * 1.5;
- var v = FlxVelocity.velocityFromAngle(a, o);
- setPosition(x + (v.x * lerp), y + (v.y * lerp));
- v.put();
- }
- }
- /**
- * Sets the angle of the camera based on:
- * - if the target is looking at another sprite
- * - The target's velocity
- */
- function camera_angle() {
- var lerp_angle:Float = 0;
- if (target.target != null) {
- lerp_angle = 0.09;
- } else if (target.rotation > 175 || target.rotation < 5) {
- lerp_angle = target.velocity.vector_length() > 0.5 ? 0.009 : 0.01;
- } else {
- lerp_angle = target.velocity.vector_length() > 0.5 ? 0 : 0.09;
- }
- if (lerp_angle != 0) {
- FlxG.camera.angle = FlxG.camera.angle.translate_to_nearest_angle(-target.relative_rotation - 90);
- FlxG.camera.angle += (-target.relative_rotation - 90 - FlxG.camera.angle) * lerp_angle;
- }
- }
- /**
- * Tells if a point 'p' lies within a ellipse of center 'c' and dimensions 'wh'.
- */
- function targetInEllipse():Bool {
- // Get Center
- var c = FlxVector.get();
- getMidpoint(c);
- // Get Target Center
- var p = FlxVector.get();
- target.getMidpoint(p);
- // Get Angle Between
- var pc = p.subtractNew(c);
- var a = pc.degrees;
- // Recycle all our FlxVectors
- pc.put();
- c.put();
- p.put();
- // Do our math
- var ca = Math.cos(a) * radius;
- var sa = Math.sin(a) * radius;
- return p.distSquared(c) <= ca * ca + sa * sa;
- }
- #if FLX_DEBUG
- /**
- * Override this function to draw custom "debug mode" graphics to the
- * specified camera while the debugger's `drawDebug` mode is toggled on.
- *
- * @param Camera Which camera to draw the debug visuals to.
- */
- override public function drawDebugOnCamera(camera:FlxCamera):Void {
- if (!camera.visible || !camera.exists || !isOnScreen(camera))
- return;
- var rect = getBoundingBox(camera);
- var gfx:Graphics = beginDrawDebug(camera);
- drawDebugBoundingEllipse(gfx, rect, allowCollisions, immovable);
- endDrawDebug(camera);
- }
- function drawDebugBoundingEllipse(gfx:Graphics, rect:FlxRect, allowCollisions:Int, partial:Bool) {
- // Find the color to use
- var color:Null<Int> = debugBoundingBoxColor;
- if (color == null) {
- if (target != null)
- color = targetInEllipse() ? debugBoundingBoxColorPartial : debugBoundingBoxColorSolid;
- else
- color = debugBoundingBoxColorNotSolid;
- }
- // fill static graphics object with square shape
- gfx.lineStyle(1, color, 0.5);
- gfx.drawEllipse(rect.x, rect.y, rect.width, rect.height);
- }
- #end
- }
- @:enum
- abstract Mode(Int) from Int to Int {
- var FOLLOW = 0;
- var TARGET = 1;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement