Commit 39bceb5

Nick Faro committed on
Implement VGM looping support
commit 39bceb54adfe6c8c565b9783831aff9eeb7ea682 parent 3b526df
1 changed files +20−8
Modifiedvgm.pas +20−8
@@ -5,7 +5,7 @@ unit VGM;
5 interface 5 interface
6 6
7 uses 7 uses
8 Classes, SysUtils, gvector, vars, mainloop, sound, constants; 8 Classes, SysUtils, vars, mainloop, sound, constants;
9 9
10 type 10 type
11 // Header for a v1.61 VGM file. 11 // Header for a v1.61 VGM file.
@@ -92,11 +92,15 @@ type
92 end; 92 end;
93 93
94 var 94 var
95 SeenOrders: array of Integer; 95 SeenOrders: array of record
96 TimesSeen: Integer;
97 SampsToReach: Integer;
98 DataOffset: Integer;
99 end;
96 OrderChecker: TOrderChecker; 100 OrderChecker: TOrderChecker;
97 StartOfSong, CurrentOrder: Integer; 101 StartOfSong: Integer;
98 VGMFile: TFileStream; 102 VGMFile: TFileStream;
99 TotalWaitSamps, LoopWaitSamps: LongInt; 103 TotalWaitSamps: Integer;
100 CyclesSinceLastTick: Integer; 104 CyclesSinceLastTick: Integer;
101 105
102 procedure WriteUtf16String(S: String); 106 procedure WriteUtf16String(S: String);
@@ -134,7 +138,6 @@ begin
134 138
135 SetLength(SeenOrders, PeekSymbol(SYM_ORDER_COUNT) div 2); 139 SetLength(SeenOrders, PeekSymbol(SYM_ORDER_COUNT) div 2);
136 StartOfSong := -1; 140 StartOfSong := -1;
137 CurrentOrder := -1;
138 141
139 WritingVGM := True; 142 WritingVGM := True;
140 VGMFile := TFileStream.Create(F, fmCreate); 143 VGMFile := TFileStream.Create(F, fmCreate);
@@ -191,11 +194,16 @@ begin
191 Header.VGMdataoffset := $8C; 194 Header.VGMdataoffset := $8C;
192 Header.TotalNumsamples := TotalWaitSamps; 195 Header.TotalNumsamples := TotalWaitSamps;
193 196
197 Header.LoopNumsamples := TotalWaitSamps - SeenOrders[StartOfSong].SampsToReach;
198 Header.Loopoffset := SeenOrders[StartOfSong].DataOffset - $1C;
199
194 VGMFile.Seek(0, soBeginning); 200 VGMFile.Seek(0, soBeginning);
195 VGMFile.WriteBuffer(Header, SizeOf(Header)); 201 VGMFile.WriteBuffer(Header, SizeOf(Header));
196 202
197 VGMFile.Free; 203 VGMFile.Free;
198 204
205 SetLength(SeenOrders, 0);
206
199 F4Callback := OldF4; 207 F4Callback := OldF4;
200 FDCallback := OldFD; 208 FDCallback := OldFD;
201 FCCallback := OldFC; 209 FCCallback := OldFC;
@@ -223,11 +231,15 @@ var
223 begin 231 begin
224 Ord := (PeekSymbol(SYM_CURRENT_ORDER) div 2); 232 Ord := (PeekSymbol(SYM_CURRENT_ORDER) div 2);
225 233
226 if (SeenOrders[Ord] <> 0) and (StartOfSong = -1) then 234 if (SeenOrders[Ord].TimesSeen = 0) then begin
235 SeenOrders[Ord].SampsToReach := TotalWaitSamps;
236 SeenOrders[Ord].DataOffset := VGMFile.Position;
237 end;
238
239 if (SeenOrders[Ord].TimesSeen <> 0) and (StartOfSong = -1) then
227 StartOfSong := Ord; 240 StartOfSong := Ord;
228 241
229 Inc(SeenOrders[Ord]); 242 Inc(SeenOrders[Ord].TimesSeen);
230 CurrentOrder := Ord;
231 end; 243 end;
232 244
233 procedure TOrderChecker.TickCallback; 245 procedure TOrderChecker.TickCallback;