mirror of
https://github.com/curioustorvald/tsvm.git
synced 2026-06-06 05:28:31 +09:00
taut.js: fxNames update
This commit is contained in:
@@ -116,17 +116,17 @@ P:"UNIMPLEMENTED", // IT: panning slide. Use PanEff instead
|
|||||||
Q:"Retrigger ",
|
Q:"Retrigger ",
|
||||||
R:"Tremolo ",
|
R:"Tremolo ",
|
||||||
S:"Special ",
|
S:"Special ",
|
||||||
S0:"UNIMPLEMENTED", // PT: Set audio filter.
|
S0:"UNIMPLEMENTED", // PT: Set audio filter
|
||||||
S1:"Gliss. ctrl ",
|
S1:"Gliss. ctrl ",
|
||||||
S2:"Sample tune ",
|
S2:"Sample tune ",
|
||||||
S3:"Vibrato LFO ",
|
S3:"Vibrato LFO ",
|
||||||
S4:"Tremolo LFO ",
|
S4:"Tremolo LFO ",
|
||||||
S5:"Panbrello LFO",
|
S5:"Panbrello LFO",
|
||||||
S6:"UNIMPLEMENTED", // IT: Fine pattern delay.
|
S6:"Fine delay ",
|
||||||
S7:"UNIMPLEMENTED", // IT: misc. functions
|
S7:"Note action ",
|
||||||
S8:"Channel pan ", // Taud: 8-bit channel panning.
|
S8:"Channel pan ", // Taud: 8-bit channel panning
|
||||||
S9:"UNIMPLEMENTED", // IT: Sound control.
|
S9:"UNIMPLEMENTED", // IT: Sound control
|
||||||
SA:"UNIMPLEMENTED", // SC3: Stereo control. IT: Sample offset high twobyte.
|
SA:"UNIMPLEMENTED", // SC3: Stereo control. IT: Sample offset high twobyte (not applicable because Taud has 64k limit)
|
||||||
SB:"Pattern loop ",
|
SB:"Pattern loop ",
|
||||||
SC:"Note cut ",
|
SC:"Note cut ",
|
||||||
SD:"Note delay ",
|
SD:"Note delay ",
|
||||||
@@ -135,10 +135,10 @@ SF:"Funk it ",
|
|||||||
T:"Tempo ",
|
T:"Tempo ",
|
||||||
U:"Fine vibrato ",
|
U:"Fine vibrato ",
|
||||||
V:"Global volume",
|
V:"Global volume",
|
||||||
W:"UNIMPLEMENTED", // IT: Global volume slide.
|
W:"G.Vol Slide ",
|
||||||
X:"UNIMPLEMENTED", // IT: 8-bit channel panning. Use PanEff or S80xx instead
|
X:"UNIMPLEMENTED", // IT: 8-bit channel panning. Use S80xx instead
|
||||||
Y:"Panbrello ",
|
Y:"Panbrello ",
|
||||||
Z:"UNIMPLEMENTED", // IT: MIDI macro.
|
Z:"UNIMPLEMENTED", // IT: MIDI macro
|
||||||
}
|
}
|
||||||
const panFxNames = {
|
const panFxNames = {
|
||||||
0:"Set to",
|
0:"Set to",
|
||||||
|
|||||||
13
it2taud.py
13
it2taud.py
@@ -52,7 +52,7 @@ from taud_common import (
|
|||||||
EFF_K, EFF_L, EFF_M, EFF_N, EFF_O, EFF_P, EFF_Q, EFF_R, EFF_S, EFF_T,
|
EFF_K, EFF_L, EFF_M, EFF_N, EFF_O, EFF_P, EFF_Q, EFF_R, EFF_S, EFF_T,
|
||||||
EFF_U, EFF_V, EFF_W, EFF_X, EFF_Y, EFF_Z,
|
EFF_U, EFF_V, EFF_W, EFF_X, EFF_Y, EFF_Z,
|
||||||
J_SEMI_TABLE,
|
J_SEMI_TABLE,
|
||||||
d_arg_to_col, resample_linear, encode_cue, deduplicate_patterns,
|
d_arg_to_col, resample_linear, rescale_offset_effects, encode_cue, deduplicate_patterns,
|
||||||
normalise_sample, encode_song_entry,
|
normalise_sample, encode_song_entry,
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -1314,7 +1314,7 @@ def build_sample_inst_bin_it(samples_or_proxy: list,
|
|||||||
|
|
||||||
vprint(f" instrument[{taud_idx}] '{s.name}' ptr:{ptr} c5spd:{s.c5_speed}")
|
vprint(f" instrument[{taud_idx}] '{s.name}' ptr:{ptr} c5spd:{s.c5_speed}")
|
||||||
|
|
||||||
return bytes(sample_bin) + bytes(inst_bin), offsets
|
return bytes(sample_bin) + bytes(inst_bin), offsets, ratio
|
||||||
|
|
||||||
|
|
||||||
# ── Pattern builder ───────────────────────────────────────────────────────────
|
# ── Pattern builder ───────────────────────────────────────────────────────────
|
||||||
@@ -1682,7 +1682,7 @@ def assemble_taud(h: ITHeader, samples: list, instruments: list,
|
|||||||
'dct': inst.dct,
|
'dct': inst.dct,
|
||||||
'dca': inst.dca,
|
'dca': inst.dca,
|
||||||
}
|
}
|
||||||
sampleinst_raw, _ = build_sample_inst_bin_it(proxy, instr_data_by_slot)
|
sampleinst_raw, _, sample_ratio = build_sample_inst_bin_it(proxy, instr_data_by_slot)
|
||||||
else:
|
else:
|
||||||
# Samples referenced directly; proxy is samples list (0-based, slot 0 unused)
|
# Samples referenced directly; proxy is samples list (0-based, slot 0 unused)
|
||||||
proxy = [None] + list(samples)
|
proxy = [None] + list(samples)
|
||||||
@@ -1691,7 +1691,7 @@ def assemble_taud(h: ITHeader, samples: list, instruments: list,
|
|||||||
for i, s in enumerate(samples)
|
for i, s in enumerate(samples)
|
||||||
if s is not None
|
if s is not None
|
||||||
}
|
}
|
||||||
sampleinst_raw, _ = build_sample_inst_bin_it(proxy)
|
sampleinst_raw, _, sample_ratio = build_sample_inst_bin_it(proxy)
|
||||||
|
|
||||||
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
||||||
|
|
||||||
@@ -1723,8 +1723,11 @@ def assemble_taud(h: ITHeader, samples: list, instruments: list,
|
|||||||
pat_bin += build_pattern_it(cg, ch, default_pans[vi], inst_vols,
|
pat_bin += build_pattern_it(cg, ch, default_pans[vi], inst_vols,
|
||||||
amiga_mode=not h.linear_slides)
|
amiga_mode=not h.linear_slides)
|
||||||
|
|
||||||
|
# Rescale TOP_O sample-offset args if samples were globally downsampled.
|
||||||
|
pat_bin = rescale_offset_effects(bytes(pat_bin), sample_ratio)
|
||||||
|
|
||||||
orig_count = len(taud_cue_list) * C
|
orig_count = len(taud_cue_list) * C
|
||||||
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(bytes(pat_bin), orig_count)
|
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(pat_bin, orig_count)
|
||||||
vprint(f" patterns: {orig_count} → {num_taud_pats} unique "
|
vprint(f" patterns: {orig_count} → {num_taud_pats} unique "
|
||||||
f"({orig_count - num_taud_pats} deduplicated)")
|
f"({orig_count - num_taud_pats} deduplicated)")
|
||||||
|
|
||||||
|
|||||||
11
mod2taud.py
11
mod2taud.py
@@ -39,7 +39,7 @@ from taud_common import (
|
|||||||
TOP_J, TOP_K, TOP_L, TOP_O, TOP_Q, TOP_R, TOP_S, TOP_T, TOP_U, TOP_V, TOP_Y,
|
TOP_J, TOP_K, TOP_L, TOP_O, TOP_Q, TOP_R, TOP_S, TOP_T, TOP_U, TOP_V, TOP_Y,
|
||||||
SEL_SET, SEL_UP, SEL_DOWN, SEL_FINE,
|
SEL_SET, SEL_UP, SEL_DOWN, SEL_FINE,
|
||||||
J_SEMI_TABLE,
|
J_SEMI_TABLE,
|
||||||
d_arg_to_col, resample_linear, encode_cue, deduplicate_patterns,
|
d_arg_to_col, resample_linear, rescale_offset_effects, encode_cue, deduplicate_patterns,
|
||||||
encode_song_entry,
|
encode_song_entry,
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -546,7 +546,7 @@ def build_sample_inst_bin(samples: list) -> tuple:
|
|||||||
vprint(f" instrument[{taud_idx}] '{s.name}' ptr={ptr} c2spd={s.c2spd} "
|
vprint(f" instrument[{taud_idx}] '{s.name}' ptr={ptr} c2spd={s.c2spd} "
|
||||||
f"vol={s.volume} loop=({ls},{le},{'on' if loop_mode else 'off'})")
|
f"vol={s.volume} loop=({ls},{le},{'on' if loop_mode else 'off'})")
|
||||||
|
|
||||||
return bytes(sample_bin) + bytes(inst_bin), offsets
|
return bytes(sample_bin) + bytes(inst_bin), offsets, ratio
|
||||||
|
|
||||||
|
|
||||||
# ── Pattern build ────────────────────────────────────────────────────────────
|
# ── Pattern build ────────────────────────────────────────────────────────────
|
||||||
@@ -704,7 +704,7 @@ def assemble_taud(mod: dict) -> bytes:
|
|||||||
relocate_late_note_delays(patterns, order_list, n_channels, init_speed)
|
relocate_late_note_delays(patterns, order_list, n_channels, init_speed)
|
||||||
|
|
||||||
vprint(" building sample/instrument bin…")
|
vprint(" building sample/instrument bin…")
|
||||||
sampleinst_raw, _offsets = build_sample_inst_bin(samples)
|
sampleinst_raw, _offsets, sample_ratio = build_sample_inst_bin(samples)
|
||||||
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
||||||
|
|
||||||
compressed = gzip.compress(sampleinst_raw, compresslevel=9, mtime=0)
|
compressed = gzip.compress(sampleinst_raw, compresslevel=9, mtime=0)
|
||||||
@@ -742,9 +742,12 @@ def assemble_taud(mod: dict) -> bytes:
|
|||||||
pat_bin += build_pattern(grid, ch, default_pan, inst_vols)
|
pat_bin += build_pattern(grid, ch, default_pan, inst_vols)
|
||||||
assert len(pat_bin) == n_patterns * n_channels * PATTERN_BYTES
|
assert len(pat_bin) == n_patterns * n_channels * PATTERN_BYTES
|
||||||
|
|
||||||
|
# Rescale TOP_O sample-offset args if samples were globally downsampled.
|
||||||
|
pat_bin = rescale_offset_effects(bytes(pat_bin), sample_ratio)
|
||||||
|
|
||||||
vprint(" deduplicating patterns…")
|
vprint(" deduplicating patterns…")
|
||||||
orig_count = n_patterns * n_channels
|
orig_count = n_patterns * n_channels
|
||||||
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(bytes(pat_bin), orig_count)
|
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(pat_bin, orig_count)
|
||||||
vprint(f" patterns: {orig_count} → {num_taud_pats} unique "
|
vprint(f" patterns: {orig_count} → {num_taud_pats} unique "
|
||||||
f"({orig_count - num_taud_pats} deduplicated)")
|
f"({orig_count - num_taud_pats} deduplicated)")
|
||||||
|
|
||||||
|
|||||||
11
s3m2taud.py
11
s3m2taud.py
@@ -43,7 +43,7 @@ from taud_common import (
|
|||||||
EFF_K, EFF_L, EFF_M, EFF_N, EFF_O, EFF_P, EFF_Q, EFF_R, EFF_S, EFF_T,
|
EFF_K, EFF_L, EFF_M, EFF_N, EFF_O, EFF_P, EFF_Q, EFF_R, EFF_S, EFF_T,
|
||||||
EFF_U, EFF_V, EFF_W, EFF_X, EFF_Y, EFF_Z,
|
EFF_U, EFF_V, EFF_W, EFF_X, EFF_Y, EFF_Z,
|
||||||
J_SEMI_TABLE,
|
J_SEMI_TABLE,
|
||||||
d_arg_to_col, resample_linear, encode_cue, deduplicate_patterns,
|
d_arg_to_col, resample_linear, rescale_offset_effects, encode_cue, deduplicate_patterns,
|
||||||
normalise_sample, encode_song_entry,
|
normalise_sample, encode_song_entry,
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -528,7 +528,7 @@ def build_sample_inst_bin(instruments: list) -> tuple:
|
|||||||
if inst.c2spd > 65535:
|
if inst.c2spd > 65535:
|
||||||
vprint(f" warning: sampling rate of '{inst.name}' exceeds 65535 (got '{inst.c2spd}')")
|
vprint(f" warning: sampling rate of '{inst.name}' exceeds 65535 (got '{inst.c2spd}')")
|
||||||
|
|
||||||
return bytes(sample_bin) + bytes(inst_bin), offsets
|
return bytes(sample_bin) + bytes(inst_bin), offsets, ratio
|
||||||
|
|
||||||
|
|
||||||
def _default_channel_pan(ch_setting: int) -> int:
|
def _default_channel_pan(ch_setting: int) -> int:
|
||||||
@@ -740,7 +740,7 @@ def assemble_taud(h: S3MHeader, instruments: list, patterns: list) -> bytes:
|
|||||||
|
|
||||||
# Build sample+instrument bin
|
# Build sample+instrument bin
|
||||||
vprint(" building sample/instrument bin…")
|
vprint(" building sample/instrument bin…")
|
||||||
sampleinst_raw, _offsets = build_sample_inst_bin(instruments)
|
sampleinst_raw, _offsets, sample_ratio = build_sample_inst_bin(instruments)
|
||||||
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
assert len(sampleinst_raw) == SAMPLEINST_SIZE
|
||||||
|
|
||||||
# Compress
|
# Compress
|
||||||
@@ -787,10 +787,13 @@ def assemble_taud(h: S3MHeader, instruments: list, patterns: list) -> bytes:
|
|||||||
inst_vols, amiga_mode=not h.linear_slides)
|
inst_vols, amiga_mode=not h.linear_slides)
|
||||||
assert len(pat_bin) == num_taud_pats * PATTERN_BYTES
|
assert len(pat_bin) == num_taud_pats * PATTERN_BYTES
|
||||||
|
|
||||||
|
# Rescale TOP_O sample-offset args if samples were globally downsampled.
|
||||||
|
pat_bin = rescale_offset_effects(bytes(pat_bin), sample_ratio)
|
||||||
|
|
||||||
# Deduplicate identical patterns
|
# Deduplicate identical patterns
|
||||||
vprint(" deduplicating patterns…")
|
vprint(" deduplicating patterns…")
|
||||||
orig_count = num_taud_pats
|
orig_count = num_taud_pats
|
||||||
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(bytes(pat_bin), orig_count)
|
pat_bin, pat_remap, num_taud_pats = deduplicate_patterns(pat_bin, orig_count)
|
||||||
vprint(f" patterns: {orig_count} → {num_taud_pats} unique ({orig_count - num_taud_pats} deduplicated)")
|
vprint(f" patterns: {orig_count} → {num_taud_pats} unique ({orig_count - num_taud_pats} deduplicated)")
|
||||||
|
|
||||||
# Cue sheet (using remapped pattern indices)
|
# Cue sheet (using remapped pattern indices)
|
||||||
|
|||||||
@@ -131,6 +131,27 @@ def resample_linear(data: bytes, ratio: float) -> bytes:
|
|||||||
return bytes(out)
|
return bytes(out)
|
||||||
|
|
||||||
|
|
||||||
|
def rescale_offset_effects(pat_bin: bytes, ratio: float) -> bytes:
|
||||||
|
"""Scale TOP_O sample-offset args in raw pattern bytes by `ratio`.
|
||||||
|
|
||||||
|
Each row is 8 bytes; byte 5 is the effect opcode, bytes 6-7 are the
|
||||||
|
little-endian 16-bit arg (= byte offset into the sample). When the
|
||||||
|
sample bin overflows and every sample is downsampled globally, the
|
||||||
|
offset commands must shrink the same amount or O-jumps land past
|
||||||
|
the new end of sample.
|
||||||
|
"""
|
||||||
|
if ratio == 1.0 or not pat_bin:
|
||||||
|
return pat_bin
|
||||||
|
out = bytearray(pat_bin)
|
||||||
|
for i in range(0, len(out) - 7, 8):
|
||||||
|
if out[i + 5] == TOP_O:
|
||||||
|
arg = out[i + 6] | (out[i + 7] << 8)
|
||||||
|
arg = max(0, min(0xFFFF, int(arg * ratio + 0.5)))
|
||||||
|
out[i + 6] = arg & 0xFF
|
||||||
|
out[i + 7] = (arg >> 8) & 0xFF
|
||||||
|
return bytes(out)
|
||||||
|
|
||||||
|
|
||||||
def encode_cue(patterns12: list, instruction: int) -> bytearray:
|
def encode_cue(patterns12: list, instruction: int) -> bytearray:
|
||||||
"""Encode a 32-byte cue entry for up to 20 voices with 12-bit pattern numbers."""
|
"""Encode a 32-byte cue entry for up to 20 voices with 12-bit pattern numbers."""
|
||||||
pats = list(patterns12) + [0xFFF] * NUM_VOICES
|
pats = list(patterns12) + [0xFFF] * NUM_VOICES
|
||||||
|
|||||||
Reference in New Issue
Block a user