diff --git a/images/game/splashes/hold/holdCoverBlue.png b/images/game/splashes/hold/holdCoverBlue.png
new file mode 100644
index 0000000..4bb90ef
Binary files /dev/null and b/images/game/splashes/hold/holdCoverBlue.png differ
diff --git a/images/game/splashes/hold/holdCoverBlue.xml b/images/game/splashes/hold/holdCoverBlue.xml
new file mode 100644
index 0000000..de9fac5
--- /dev/null
+++ b/images/game/splashes/hold/holdCoverBlue.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/images/game/splashes/hold/holdCoverGreen.png b/images/game/splashes/hold/holdCoverGreen.png
new file mode 100644
index 0000000..59055b0
Binary files /dev/null and b/images/game/splashes/hold/holdCoverGreen.png differ
diff --git a/images/game/splashes/hold/holdCoverGreen.xml b/images/game/splashes/hold/holdCoverGreen.xml
new file mode 100644
index 0000000..a5d7762
--- /dev/null
+++ b/images/game/splashes/hold/holdCoverGreen.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/images/game/splashes/hold/holdCoverPurple.png b/images/game/splashes/hold/holdCoverPurple.png
new file mode 100644
index 0000000..1f0b427
Binary files /dev/null and b/images/game/splashes/hold/holdCoverPurple.png differ
diff --git a/images/game/splashes/hold/holdCoverPurple.xml b/images/game/splashes/hold/holdCoverPurple.xml
new file mode 100644
index 0000000..ea51246
--- /dev/null
+++ b/images/game/splashes/hold/holdCoverPurple.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/images/game/splashes/hold/holdCoverRed.png b/images/game/splashes/hold/holdCoverRed.png
new file mode 100644
index 0000000..7fc1091
Binary files /dev/null and b/images/game/splashes/hold/holdCoverRed.png differ
diff --git a/images/game/splashes/hold/holdCoverRed.xml b/images/game/splashes/hold/holdCoverRed.xml
new file mode 100644
index 0000000..f8e5931
--- /dev/null
+++ b/images/game/splashes/hold/holdCoverRed.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/songs/vslice_uiShits.hx b/songs/vslice_uiShits.hx
index 751bbf3..76c84ad 100644
--- a/songs/vslice_uiShits.hx
+++ b/songs/vslice_uiShits.hx
@@ -1,6 +1,24 @@
//
+import game.NoteCoverHandler;
+
+/*
+ * Whether to init the note hold covers if set to true (to set before onStrumCreation).
+*/
+public var initHoldCovers:Bool = true;
+public var noteCoversHandler:NoteCoverHandler;
+
public var ratingScaleDiff:Float = 0.1;
+function onPostStrumCreation(e)
+{
+ if (!hideHoldCovers) return;
+
+ if (noteCoversHandler == null)
+ add(noteCoversHandler = new NoteCoverHandler());
+
+ noteCoversHandler.cacheStuff(e.strumID);
+}
+
function create() {
comboGroup.x = 560;
comboGroup.y = 290;
@@ -22,7 +40,18 @@ function onPostCountdown(event) {
function onNoteHit(event) {
event.numScale -= ratingScaleDiff;
event.ratingScale -= ratingScaleDiff;
+
+ if (!e.cancelled && e.note.isSustainNote && e.note.__strum != null && noteCoversHandler != null) {
+ noteCoversHandler.showCover();
+
+ if (e.note.animation.name == "holdend")
+ noteCoversHandler.coverSpark(e.note.__strum, e.note.height / 3.5, e.player);
+ }
}
+function onPlayerMiss(e)
+ if (noteCoversHandler.cacheStuff(e.note.__strum.ID).cover.visible)
+ noteCoversHandler.coverSpark(e.note.__strum, null);
+
function update()
comboGroup.forEachAlive(function(spr) if (spr.camera != camHUD) spr.camera = camHUD);
\ No newline at end of file
diff --git a/source/game/NoteCoverHandler.hx b/source/game/NoteCoverHandler.hx
new file mode 100644
index 0000000..3628d98
--- /dev/null
+++ b/source/game/NoteCoverHandler.hx
@@ -0,0 +1,113 @@
+import flixel.group.FlxTypedSpriteGroup;
+
+import funkin.game.Strum;
+import notes.NoteHoldCover;
+import notes.NoteHoldSplash;
+
+class NoteCoverHandler extends FlxTypedGroup
+{
+ /*
+ * Array of the color directions for the strumlines.
+ */
+ public static var directions:Array = ['Purple', 'Blue', 'Green', 'Red'];
+
+ public static function getDirectionName(direction:Int)
+ return NoteCoverHandler.directions[direction % NoteCoverHandler.directions.length];
+
+ /**
+ * Array containing all of the covers group (index = direction).
+ */
+ public var datas:Array = [];
+
+ public function new() {
+ super();
+ }
+
+ /**
+ * Caches Hold Covers/Splashes.
+ */
+ public function cacheStuff(direction:Int):CoverData {
+ if (datas[i] == null) datas[i] = CoverData.initNcache(direction);
+ return datas[i];
+ }
+
+ public override function destroy() {
+ super.destroy();
+ for(data in datas)
+ data.destroy();
+ datas = null;
+ }
+
+ var _firstDraw:Bool = true;
+ public override function draw() {
+ super.draw();
+ if (_firstDraw != (_firstDraw = false))
+ for(sprs in datas)
+ sprs.draw();
+ }
+
+ public function showCover(strum:Strum) {
+ var __spr = cacheStuff(strum.ID).cover;
+ __spr.cameras = strum.lastDrawCameras;
+
+ __spr.updatePosition(strum);
+ __spr.start();
+ add(__spr);
+
+ // max 16 rendered covers
+ while(members.length > 16)
+ remove(members[0], true);
+ }
+
+ function coverSpark(strum:Strum, delay:Float = 0, showSplash:Bool) {
+ var __data = cacheStuff(strum.ID);
+
+ new FlxTimer().start(0.01 * delay, function() {
+ if (!showSplash)
+ {
+ var splash = __data.splash.start();
+ splash.setPosition(cover.x = strum.x + cover.posX, cover.y = strum.y + cover.posY);
+ splash.angle = cover.angle = strum.angle;
+ splash.antialiasing = cover.antialiasing;
+ splash.visible = cover.visible;
+ splash.cameras = cover.cameras;
+ add(splash);
+ }
+
+ cover.visible = false;
+ });
+ }
+}
+
+class CoverData
+{
+ public var cover:NoteHoldCover;
+ public var splash:NoteHoldSplash;
+
+ function new(cover:NoteHoldCover, splash:NoteHoldSplash):Void
+ {
+ super();
+
+ this.cover = cover;
+ this.splash = splash;
+
+ // immediatly draw once and put image in GPU to prevent freezes - Nex
+ cover.drawComplex(FlxG.camera);
+ splash.drawComplex(FlxG.camera);
+ }
+
+ public function draw()
+ {
+ cover.draw();
+ splash.draw();
+ }
+
+ public function destroy()
+ {
+ cover.destroy();
+ splash.destroy();
+ }
+
+ public static function initNcache(direction:Int):CoverData
+ return new CoverData(new NoteHoldCover(direction), new NoteHoldSplash(direction));
+}
\ No newline at end of file
diff --git a/source/notes/NoteHoldCover.hx b/source/notes/NoteHoldCover.hx
new file mode 100644
index 0000000..86ec849
--- /dev/null
+++ b/source/notes/NoteHoldCover.hx
@@ -0,0 +1,50 @@
+import game.NoteCoverHandler;
+
+class NoteHoldCover extends funkin.backend.FunkinSprite
+{
+ /*
+ * X Position of the hold cover.
+ */
+ public var posX:Float = -107.5;
+
+ /*
+ * Array of the Y Position for the hold cover.
+ */
+ public var posY:Float = 0;
+
+ public function new(direction:Int):Void
+ {
+ var suffix = NoteCoverHandler.getDirectionName(direction);
+ frames = Paths.getSparrowAtlas("game/splashes/hold/holdCover" + suffix);
+ animation.addByPrefix("start", "holdCoverStart" + suffix, 24, false);
+ animation.addByPrefix("hold", "holdCover" + suffix, 24, true);
+
+ antialiasing = true;
+ visible = false;
+
+ animation.finishCallback = this.onAnimationFinished;
+ }
+
+ public function updatePosition(object:FlxObject) {
+ x = object.x + posX;
+ y = object.y + posY;
+ angle = object.angle;
+ alpha = object.alpha;
+ }
+
+ public function onAnimationFinished(animName:String):Void
+ if (animName == 'start') playHold();
+
+ public function start() {
+ if (!visible && animation.name == "hold") playStart();
+ else playHold();
+ }
+
+ public function playStart() {
+ visible = true;
+ playAnim('start');
+ }
+
+ public function playHold()
+ playAnim('hold');
+}
\ No newline at end of file
diff --git a/source/notes/NoteHoldSplash.hx b/source/notes/NoteHoldSplash.hx
new file mode 100644
index 0000000..908daf2
--- /dev/null
+++ b/source/notes/NoteHoldSplash.hx
@@ -0,0 +1,15 @@
+import game.NoteCoverHandler;
+
+class NoteHoldSplash extends funkin.backend.FunkinSprite
+{
+ public function new(direction:Int) {
+ var suffix = NoteCoverHandler.getDirectionName(direction);
+ frames = Paths.getSparrowAtlas("game/splashes/hold/holdCover" + suffix);
+ animation.addByPrefix("holdEnd", "holdCoverEnd" + suffix, 24, false);
+ }
+
+ public function start() {
+ playAnim('holdEnd', true);
+ animation.finishCallback = () -> visible = false;
+ }
+}
\ No newline at end of file