using System; using System.Runtime.CompilerServices; using Manager; using MoreChartFormats.MaiSxt.Structures; namespace MoreChartFormats.MaiSxt; public class SxtReader(NotesReferences refs) : SxtReaderBase(refs) { [MethodImpl(MethodImplOptions.AggressiveInlining)] protected override void LoadRow(int rowIdx, in SxtRow row) { if (row.NoteType == 0) { if (row.SlideId == 0) { throw new Exception($"Slide head at row {rowIdx} does not declare a valid slide ID"); } SlideHeads[row.SlideId] = row; return; } var rowTime = row.NotesTime(Refs.Reader); var note = new NoteData { type = row.NoteType switch { 1 => NotesTypeID.Def.Tap, 2 => NotesTypeID.Def.Hold, 3 => NotesTypeID.Def.Break, 4 => NotesTypeID.Def.Star, 5 => NotesTypeID.Def.BreakStar, 128 => NotesTypeID.Def.Slide, _ => throw new Exception($"Unknown note type ID {row.NoteType} at row {rowIdx}, expected 1/2/3/4/5/128") }, startButtonPos = row.Position, time = rowTime, end = rowTime, beatType = ParserUtilities.GetBeatType(rowTime.grid), index = rowIdx, indexNote = NoteIndex }; if (note.type.isHold()) { note.end += ParserUtilities.NotesTimeFromBars(Refs, row.HoldDuration); note.end.calcMsec(Refs.Reader); } if (note.type.isSlide()) { if (!SlideHeads.TryGetValue(row.SlideId, out var slideHeadRow)) { throw new Exception($"Slide body (ID {row.SlideId}) declared without or before its head"); } note.startButtonPos = slideHeadRow.Position; note.slideData = new SlideData { type = (SlideType)row.SlidePattern, index = row.SlideId, targetNote = row.Position, shoot = new TimingBase { index = rowIdx }, arrive = new TimingBase { index = rowIdx }, }; note.time = slideHeadRow.NotesTime(Refs.Reader); note.beatType = ParserUtilities.GetBeatType(note.time.grid); note.slideData.shoot.time = note.time + slideHeadRow.SlideDelayNotesTime(Refs); note.slideData.shoot.time.calcMsec(Refs.Reader); note.slideData.arrive.time.copy(rowTime); note.end.copy(rowTime); } Refs.Notes._noteData.Add(note); NoteIndex++; } }