diff --git a/scripts/NoteHandler.gd b/scripts/NoteHandler.gd index f328371..026494e 100644 --- a/scripts/NoteHandler.gd +++ b/scripts/NoteHandler.gd @@ -202,14 +202,7 @@ func make_slide_trail_mesh(note) -> ArrayMesh: vertices[i*3] = offset + uv1o vertices[i*3+1] = offset + uv2o vertices[i*3+2] = offset + uv3o - Note.SlideType.ARC_CW: - for i in trail_length: - var angle : float = note.get_angle((i+1)/float(trail_length)) - var offset : Vector2 = note.get_position((i+1)/float(trail_length)) - vertices[i*3] = offset + polar2cartesian(size, angle) - vertices[i*3+1] = offset + polar2cartesian(size, angle+PI/2.0) - vertices[i*3+2] = offset + polar2cartesian(size, angle-PI/2.0) - Note.SlideType.ARC_ACW: + _: for i in trail_length: var angle : float = note.get_angle((i+1)/float(trail_length)) var offset : Vector2 = note.get_position((i+1)/float(trail_length)) diff --git a/singletons/FileLoader.gd b/singletons/FileLoader.gd index 3ea31d7..a8910e6 100644 --- a/singletons/FileLoader.gd +++ b/singletons/FileLoader.gd @@ -231,26 +231,28 @@ class RGT: 'h': Note.NOTE_HOLD, 's': Note.NOTE_STAR, 'e': Note.NOTE_SLIDE, - 'b': Note.NOTE_TAP # Break + 'b': Note.NOTE_TAP, # Break + 'x': Note.NOTE_STAR # Break star } const SLIDE_TYPES = { '0': null, # Seems to be used for stars without slides attached '1': Note.SlideType.CHORD, - '2': Note.SlideType.ARC_ACW, # From Cirno master - '3': Note.SlideType.ARC_CW, # From Cirno master - '4': Note.SlideType.CHORD, # Probably some weird loop etc. - '5': Note.SlideType.CHORD, # Probably some weird loop etc. - '6': Note.SlideType.CHORD, # Probably some weird loop etc. - '7': Note.SlideType.CHORD, # Probably some weird loop etc. - '8': Note.SlideType.CHORD, # Probably some weird loop etc. - '9': Note.SlideType.CHORD, # Probably some weird loop etc. - 'a': Note.SlideType.CHORD, # Probably some weird loop etc. - 'b': Note.SlideType.CHORD, # Probably some weird loop etc. - 'c': Note.SlideType.CHORD, # Probably some weird loop etc. + '2': Note.SlideType.ARC_ACW, + '3': Note.SlideType.ARC_CW, + '4': Note.SlideType.COMPLEX, # From nekomatsuri master - Loop ACW around center. Size of loop is roughly inscribed in chords of 0-3, 1-4, 2-5... NB: doesn't loop if directly opposite col + '5': Note.SlideType.COMPLEX, # CW of above + '6': Note.SlideType.COMPLEX, # S zigzag through center + '7': Note.SlideType.COMPLEX, # Z zigzag through center + '8': Note.SlideType.COMPLEX, # V into center + '9': Note.SlideType.COMPLEX, # From nekomatsuri master - Seems to loop around to center ACW to make a + to the end + 'a': Note.SlideType.COMPLEX, # CW of above + 'b': Note.SlideType.COMPLEX, # V into column 2 places ACW + 'c': Note.SlideType.COMPLEX, # V into column 2 places CW 'd': Note.SlideType.CHORD_TRIPLE, # Triple cone. Spreads out to the adjacent receptors of the target. - 'e': Note.SlideType.CHORD, # Probably some weird loop etc. - 'f': Note.SlideType.CHORD, # Probably some weird loop etc. + 'e': Note.SlideType.CHORD, # Not used in any of our charts + 'f': Note.SlideType.CHORD, # Not used in any of our charts } + const SLIDE_IN_R := sin(PI/8) # Circle radius circumscribed by chords 0-3, 1-4, 2-5 etc. static func load_file(filename: String): var extension = filename.rsplit('.', false, 1)[1] @@ -353,6 +355,32 @@ class RGT: slide_ids[slide_id].column_release = column slide_ids[slide_id].slide_type = SLIDE_TYPES[slide_type] slide_ids[slide_id].update_slide_variables() + if SLIDE_TYPES[slide_type] == Note.SlideType.COMPLEX: + var col_hit = slide_ids[slide_id].column + var RUV = GameTheme.RADIAL_UNIT_VECTORS + slide_ids[slide_id].values.curve2d.add_point(RUV[col_hit]) # Start col + match slide_type: + '4': # TODO: Loop ACW around center. Size of loop is roughly inscribed in chords of 0-3, 1-4, 2-5... NB: doesn't loop if directly opposite col + slide_ids[slide_id].values.curve2d.add_point((RUV[posmod(col_hit-3, Rules.COLS)] + RUV[col_hit]) * 0.5) + '5': # TODO: CW of above + slide_ids[slide_id].values.curve2d.add_point((RUV[posmod(col_hit+3, Rules.COLS)] + RUV[col_hit]) * 0.5) + '6': # S zigzag through center + slide_ids[slide_id].values.curve2d.add_point(RUV[posmod(col_hit-2, Rules.COLS)] * SLIDE_IN_R) + slide_ids[slide_id].values.curve2d.add_point(RUV[posmod(col_hit+2, Rules.COLS)] * SLIDE_IN_R) + '7': # Z zigzag through center + slide_ids[slide_id].values.curve2d.add_point(RUV[posmod(col_hit+2, Rules.COLS)] * SLIDE_IN_R) + slide_ids[slide_id].values.curve2d.add_point(RUV[posmod(col_hit-2, Rules.COLS)] * SLIDE_IN_R) + '8': # V into center + slide_ids[slide_id].values.curve2d.add_point(Vector2.ZERO) + '9': # TODO: From nekomatsuri master - Seems to loop around to center ACW to make a + to the end + slide_ids[slide_id].values.curve2d.add_point(Vector2.ZERO) + 'a': # TODO: CW of above + slide_ids[slide_id].values.curve2d.add_point(Vector2.ZERO) + 'b': # V into column 2 places ACW + slide_ids[slide_id].values.curve2d.add_point(GameTheme.RADIAL_UNIT_VECTORS[posmod(col_hit-2, Rules.COLS)]) + 'c': # V into column 2 places CW + slide_ids[slide_id].values.curve2d.add_point(GameTheme.RADIAL_UNIT_VECTORS[posmod(col_hit+2, Rules.COLS)]) + slide_ids[slide_id].values.curve2d.add_point(GameTheme.RADIAL_UNIT_VECTORS[column]) # End col else: # Naked slide start if last_star[column] != null: slide_stars[slide_id] = last_star[column] diff --git a/singletons/Note.gd b/singletons/Note.gd index fac6ad2..4ea94f5 100644 --- a/singletons/Note.gd +++ b/singletons/Note.gd @@ -4,7 +4,7 @@ extends Node #class_name Note enum {NOTE_TAP, NOTE_HOLD, NOTE_STAR=2, NOTE_SLIDE=-2, NOTE_TOUCH=3, NOTE_TOUCH_HOLD=4, NOTE_ARROW, NOTE_ROLL} -enum SlideType {CHORD, ARC_CW, ARC_ACW, CHORD_TRIPLE} +enum SlideType {CHORD, ARC_CW, ARC_ACW, CHORD_TRIPLE, COMPLEX} const DEATH_DELAY := 1.0 # This is touchy with the judgement windows and variable bpm. const RELEASE_SCORE_TYPES := { NOTE_HOLD: -NOTE_HOLD, @@ -136,6 +136,9 @@ class NoteSlide extends NoteBase: # Fancy charts have naked slides which necess values.end_a = GameTheme.RADIAL_COL_ANGLES[column_release] if values.end_a > values.start_a: values.end_a -= TAU + Note.SlideType.COMPLEX: + values.curve2d = Curve2D.new() + values.curve2d.bake_interval = 0.005 # TODO: play around with this func get_position(progress: float) -> Vector2: match slide_type: @@ -147,6 +150,9 @@ class NoteSlide extends NoteBase: # Fancy charts have naked slides which necess Note.SlideType.ARC_ACW: var circle_angle : float = lerp(values.start_a, values.end_a, progress) return polar2cartesian(GameTheme.receptor_ring_radius, circle_angle) + Note.SlideType.COMPLEX: + progress *= values.curve2d.get_baked_length() + return values.curve2d.interpolate_baked(progress) * GameTheme.receptor_ring_radius return Vector2(0.0, 0.0) func get_angle(progress: float) -> float: @@ -159,6 +165,11 @@ class NoteSlide extends NoteBase: # Fancy charts have naked slides which necess Note.SlideType.ARC_ACW: var circle_angle : float = lerp(values.start_a, values.end_a, progress) return circle_angle - PI/2.0 + Note.SlideType.COMPLEX: + # TODO: get a better tangent maybe? + progress = clamp(progress, 0.001, 0.999) # Yes this is scuffed + var l = values.curve2d.get_baked_length() + return (values.curve2d.interpolate_baked((progress+0.001)*l) - values.curve2d.interpolate_baked((progress-0.001)*l)).angle() return 0.0 func get_slide_length() -> float: @@ -170,6 +181,8 @@ class NoteSlide extends NoteBase: # Fancy charts have naked slides which necess return fposmod(GameTheme.RADIAL_COL_ANGLES[column_release] - GameTheme.RADIAL_COL_ANGLES[column], TAU) Note.SlideType.ARC_ACW: return fposmod(GameTheme.RADIAL_COL_ANGLES[column] - GameTheme.RADIAL_COL_ANGLES[column_release], TAU) + Note.SlideType.COMPLEX: + return values.curve2d.get_baked_length() return 0.0 static func copy_note(note: NoteBase): @@ -184,6 +197,8 @@ static func copy_note(note: NoteBase): newnote = NoteHold.new(note.time_hit, note.column, note.duration) NOTE_SLIDE: newnote = NoteSlide.new(note.time_hit, note.column, note.duration, note.column_release, note.slide_type) + if note.slide_type == Note.SlideType.COMPLEX: + newnote.values.curve2d = note.values.curve2d NOTE_ROLL: newnote = NoteRoll.new(note.time_hit, note.column, note.duration) newnote.double_hit = note.double_hit