flixel icon indicating copy to clipboard operation
flixel copied to clipboard

Calling filterFrames.applyToSprite multiple times on the same sprite makes the offset of that sprite to grow each time

Open JasperHorn opened this issue 2 years ago • 0 comments

  • Haxe version: 4.3.1
  • Flixel version: 5.3.1
  • OpenFL version: 9.2.2
  • Lime version: 8.0.2
  • Affected targets: Tested html, but probably any

Code snippet reproducing the issue:

package;

import flixel.FlxG;
import flixel.FlxSprite;
import flixel.FlxState;
import flixel.graphics.frames.FlxFilterFrames;
import flixel.tweens.FlxTween;
import flixel.util.FlxColor;
import openfl.filters.GlowFilter;

class PlayState extends FlxState
{
	static inline var SIZE_INCREASE:Int = 5;

	var spr:FlxSprite;
	var filterFrames:FlxFilterFrames;

	var running:Bool = false;
	var tween:FlxTween;

	override public function create():Void
	{
		FlxG.camera.bgColor = 0xFF01355F;

		var glowFilter = new GlowFilter(0xFF0000, 1, 50, 50, 1.5, 1);
		spr = new FlxSprite(200, 200);
		spr.makeGraphic(10, 10, FlxColor.BROWN);
		add(spr);
		filterFrames = FlxFilterFrames.fromFrames(spr.frames, SIZE_INCREASE, SIZE_INCREASE, [glowFilter]);

		// The tween isn't necessary for the bug, but without it, reapplying the
		// filter frames doesn't really make sense...
		tween = FlxTween.tween(glowFilter, {blurX: 4, blurY: 4}, 1, {type: PINGPONG});
		tween.active = true;
	}

	override public function update(elapsed:Float):Void
	{
		// The whole running thing isn't necessary for the bug
		// I added it because it makes the bug easier to see
		if (FlxG.mouse.justPressed)
		{
			running = true;
		}

		super.update(elapsed);

		if (running)
		{
			filterFrames.applyToSprite(spr, false, true);
		}
	}
}

(Note: this is just https://haxeflixel.com/demos/FlxSpriteFilters/ cut down to a minimal sample for this bug)


Observed behavior:

After you click, the screen, the sprite flies off the screen.

Expected behavior:

After you click the screen, the sprite stays where it is supposed to, and an animated blur filter starts being applied to it.

Cause of problem:

This bug was introduced with this change: https://github.com/HaxeFlixel/flixel/pull/2176

Before that change, you could call FlxFilterFrames.applyToSprite() repeatedly on the same sprite, but calling it on a sprite that had a non-zero offset would lead to wrong result. After the change, non-zero offsets would work as expected, but calling it repeatedly no longer did.

I don't see a simple solution that keeps the behavior as expected in both situations. The best I can come up with is keeping a list of sprites that the frames have been applied to, but that doesn't eliminate the bug but just pushes it to a more complicated spot (namely, if you call it again after changing the graphics, but do have an offset). Perhaps the way to go is to create two methods - or an extra argument - and leave discerning the two situations to the user. But that's a more architectural choice.

JasperHorn avatar Aug 26 '23 11:08 JasperHorn