FIX: 11 bugs bảo mật/ổn định (static mount chặn dotfile, delete traversal, cleanup giữ clips serverFileId, upload whitelist, password strength, auth audio endpoints, pedalboard==0.9.19, vendor CDN local) + FEATURE: Carla bridge preview/export MIDI notes âm VSTi (POST /midi-render, /carla-play-notes, nút Preview VSTi/Export MIDI->Audio; pedalboard 0.9.19 raw MIDI bytes; SONICFORGE_STORAGE_DIR cô lập test storage)
This commit is contained in:
+13
-12
@@ -85,7 +85,7 @@ def ensure_pyfluidsynth():
|
||||
|
||||
if HAS_PEDALBOARD:
|
||||
try:
|
||||
from pedalboard import VST3Plugin, Pedalboard, Gain, MidiMessage
|
||||
from pedalboard import VST3Plugin, Pedalboard, Gain
|
||||
except Exception:
|
||||
HAS_PEDALBOARD = False
|
||||
|
||||
@@ -383,22 +383,23 @@ class PluginManager:
|
||||
if not HAS_PEDALBOARD:
|
||||
return []
|
||||
beat_duration_sec = 60.0 / max(30.0, bpm)
|
||||
# pedalboard >= 0.9: MIDI messages là tuple (bytes, timestamp_seconds)
|
||||
# (MidiMessage class đã bị bỏ). bytes là raw MIDI event:
|
||||
# 0x9n note_on, 0x8n note_off, 0xB0 control_change, 0xC0 program_change
|
||||
messages = []
|
||||
if bank is not None:
|
||||
messages.append(MidiMessage(control_change=0, value=bank, sample_offset=0))
|
||||
messages.append((bytes([0xB0, 0, int(bank) & 0x7F]), 0.0))
|
||||
if program is not None:
|
||||
messages.append(MidiMessage(program_change=program, sample_offset=0))
|
||||
messages.append((bytes([0xC0, int(program) & 0x7F]), 0.0))
|
||||
for ev in midi_events:
|
||||
note = ev.get("note", 60)
|
||||
velocity = ev.get("velocity", 100)
|
||||
start_beat = ev.get("start_beat", 0.0)
|
||||
dur_beats = ev.get("duration_beats", 1.0)
|
||||
note = int(ev.get("note", 60)) & 0x7F
|
||||
velocity = max(0, min(127, int(ev.get("velocity", 100))))
|
||||
start_beat = float(ev.get("start_beat", 0.0))
|
||||
dur_beats = float(ev.get("duration_beats", 1.0))
|
||||
start_sec = start_beat * beat_duration_sec
|
||||
dur_sec = dur_beats * beat_duration_sec
|
||||
sample_offset = int(start_sec * sr)
|
||||
end_sample_offset = int((start_sec + dur_sec) * sr)
|
||||
messages.append(MidiMessage(note_on=note, velocity=velocity, sample_offset=sample_offset))
|
||||
messages.append(MidiMessage(note_off=note, velocity=0, sample_offset=end_sample_offset))
|
||||
end_sec = (start_beat + dur_beats) * beat_duration_sec
|
||||
messages.append((bytes([0x90, note, velocity]), start_sec))
|
||||
messages.append((bytes([0x80, note, 0]), end_sec))
|
||||
return messages
|
||||
|
||||
@staticmethod
|
||||
|
||||
Reference in New Issue
Block a user