Spaces:
Sleeping
Sleeping
| import gradio as gr | |
| import librosa | |
| import numpy as np | |
| import tempfile | |
| import zipfile | |
| import os | |
| import shutil | |
| def key_bpm_embedding(audio): | |
| y, sr = librosa.load(audio, sr=None, mono=True) | |
| bpm, _ = librosa.beat.beat_track(y=y, sr=sr) | |
| chroma = librosa.feature.chroma_cqt(y=y, sr=sr) | |
| chroma_mean = chroma.mean(axis=1) | |
| key_int = np.argmax(chroma_mean) | |
| key_list = ["C", "C#", "D", "D#", "E", "F", "F#", "G", "G#", "A", "A#", "B"] | |
| key = key_list[key_int] | |
| mfcc = librosa.feature.mfcc(y=y, sr=sr, n_mfcc=13) | |
| embedding = np.mean(mfcc, axis=1).tolist() | |
| return {"bpm": float(bpm), "key": key, "embedding": embedding} | |
| def order_tracks(zipfile_bytes): | |
| with tempfile.TemporaryDirectory() as td: | |
| zip_path = os.path.join(td, "tracks.zip") | |
| shutil.copy(zipfile_bytes.name, zip_path) | |
| with zipfile.ZipFile(zip_path, 'r') as zip_ref: | |
| zip_ref.extractall(td) | |
| filelist = sorted(zip_ref.namelist()) | |
| emb_map = {} | |
| for fname in filelist: | |
| audio_path = os.path.join(td, fname) | |
| try: | |
| y, sr = librosa.load(audio_path, sr=None, mono=True) | |
| mfcc = librosa.feature.mfcc(y=y, sr=sr, n_mfcc=13) | |
| emb_map[fname] = np.mean(mfcc, axis=1) | |
| except Exception: | |
| emb_map[fname] = None | |
| valid_files = [f for f in filelist if emb_map[f] is not None] | |
| if len(valid_files) == 0: | |
| return {"order": []} | |
| embs = np.stack([emb_map[f] for f in valid_files]) | |
| sim = np.matmul(embs, embs.T) | |
| out_order = [0] | |
| used = {0} | |
| for _ in range(1, len(valid_files)): | |
| last = out_order[-1] | |
| next_idx = np.argmax([sim[last, j] if j not in used else -1e9 for j in range(len(valid_files))]) | |
| out_order.append(next_idx) | |
| used.add(next_idx) | |
| ordered_files = [valid_files[i] for i in out_order] | |
| return {"order": ordered_files} | |
| track_analysis = gr.Interface( | |
| fn=key_bpm_embedding, | |
| inputs=gr.Audio(type="filepath", label="Audio"), | |
| outputs="json" | |
| ) | |
| track_orderer = gr.Interface( | |
| fn=order_tracks, | |
| inputs=gr.File(label="ZIP archive with tracks"), | |
| outputs="json" | |
| ) | |
| demo = gr.TabbedInterface( | |
| [track_analysis, track_orderer], | |
| ["Track Analysis", "Order Tracks"] | |
| ) | |
| if __name__ == "__main__": | |
| demo.launch() |