Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
90 changes: 59 additions & 31 deletions core/src/bms/player/beatoraja/audio/AbstractAudioDriver.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import bms.model.*;
import bms.player.beatoraja.ResourcePool;

import java.io.File;
import java.nio.file.InvalidPathException;
import java.nio.file.Path;
import java.nio.file.Paths;
Expand Down Expand Up @@ -65,6 +66,7 @@ public abstract class AbstractAudioDriver<T> implements AudioDriver {
public AbstractAudioDriver(int maxgen) {
cache = new AudioCache(Math.max(maxgen, 1));
}

/**
* パスで指定された効果音ファイルの音源データを取得する
*
Expand All @@ -74,6 +76,14 @@ public AbstractAudioDriver(int maxgen) {
*/
protected abstract T getKeySound(Path p);

/**
* Load a specified sound file from a 7z archive file
*
* @param ctx 7z file context
* @param fileName sound file name (can have arbitrary extension name)
*/
protected abstract T getKeySound(SevenZArchiveContext ctx, String fileName);

/**
* PCMオブジェクトで指定されたキー音の音源データを取得する
*
Expand Down Expand Up @@ -254,6 +264,17 @@ public synchronized void setModel(BMSModel model) {
noteMapSize = 0;
// BMS格納ディレクトリ
Path dpath = Paths.get(model.getPath()).getParent();
// NOTE: Load all files from 'resource.7z' file. The file name is forced to be hard-coded, apparently we don't
// want to load any archive files from disk :)
Path resourcePath = dpath.resolve("resource.7z");
try {
SevenZArchiveContext ctx = SevenZArchiveContext.create(resourcePath);
if (ctx != null) {
cache.setCtx(ctx);
}
} catch (Exception e) {
logger.error("Failed to load resource package: ", e);
}

if (model.getVolwav() > 0 && model.getVolwav() < 100) {
volume = model.getVolwav() / 100f;
Expand Down Expand Up @@ -585,57 +606,64 @@ public SliceWav(Note note, T wav) {
}

class AudioCache extends ResourcePool<AudioKey, T> {
private SevenZArchiveContext ctx;

public AudioCache(int maxgen) {
super(maxgen);
}

public void setCtx(SevenZArchiveContext ctx) {
this.ctx = ctx;
}

private ObjectMap<String, PCM> pcmMap = new ObjectMap<String, PCM>();

private T loadSlice(AudioKey key) {
PCM wav = null;
synchronized(pcmMap) {
wav = pcmMap.get(key.path);
if (wav == null) {
wav = PCM.load(key.path, AbstractAudioDriver.this);
if(wav != null) {
pcmMap.put(key.path, wav);
}
}
}

if (wav != null) {
try {
final PCM slicewav = wav.slice(key.start, key.duration);
return slicewav != null ? getKeySound(slicewav) : null;
// System.out.println("WAV slicing - Name:"
// + name + " ID:" + note.getWav() +
// " start:" + note.getStarttime() +
// " duration:" + note.getDuration());
} catch (Throwable e) {
PCM wav = null;
synchronized(pcmMap) {
wav = pcmMap.get(key.path);
if (wav == null) {
wav = PCM.load(key.path, AbstractAudioDriver.this);
if(wav != null) {
pcmMap.put(key.path, wav);
}
}
}

if (wav != null) {
try {
final PCM slicewav = wav.slice(key.start, key.duration);
return slicewav != null ? getKeySound(slicewav) : null;
// System.out.println("WAV slicing - Name:"
// + name + " ID:" + note.getWav() +
// " start:" + note.getStarttime() +
// " duration:" + note.getDuration());
} catch (Throwable e) {
logger.warn("音源(wav)ファイルスライシング失敗。{}", e.getMessage());
e.printStackTrace();
}
}
e.printStackTrace();
}
}

return null;
}
return null;
}

@Override
protected T load(AudioKey key) {
logger.trace("音源ファイルを読み込む中:{}", key.path);

T sound = key.start == 0 && key.duration == 0
? getKeySound(Paths.get(key.path)) // 音切りなしのケース
: loadSlice(key);
String fileName = new File(key.path).getName();
boolean loadFromArchive = ctx != null && ctx.hasEntry(fileName);

T sound = key.start == 0 && key.duration == 0
? (loadFromArchive ? getKeySound(ctx, fileName) : getKeySound(Paths.get(key.path))) // 音切りなしのケース
: loadSlice(key);

if (sound == null) {
if (sound == null) {
logger.warn("音源ファイル読み込み失敗:{}", key.path);
}
}
return sound;
}


@Override
public synchronized void disposeOld() {
pcmMap.clear();
Expand Down
8 changes: 8 additions & 0 deletions core/src/bms/player/beatoraja/audio/BMSRenderer.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.*;

import org.apache.commons.compress.archivers.sevenz.SevenZArchiveEntry;
import org.apache.commons.compress.archivers.sevenz.SevenZFile;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

Expand Down Expand Up @@ -277,6 +280,11 @@ protected PCM getKeySound(Path p) {
return PCM.load(p, this);
}

@Override
protected PCM getKeySound(SevenZArchiveContext ctx, String fileName) {
return PCM.load(ctx, fileName, this);
}

@Override
protected PCM getKeySound(PCM pcm) {
return pcm;
Expand Down
6 changes: 6 additions & 0 deletions core/src/bms/player/beatoraja/audio/GdxAudioDeviceDriver.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,12 @@ protected Object getKeySound(Path p) {
return null;
}

@Override
protected Object getKeySound(SevenZArchiveContext ctx, String fileName) {
// TODO Auto-generated method stub
return null;
}

@Override
protected Object getKeySound(PCM pcm) {
// TODO Auto-generated method stub
Expand Down
44 changes: 35 additions & 9 deletions core/src/bms/player/beatoraja/audio/GdxSoundDriver.java
Original file line number Diff line number Diff line change
@@ -1,19 +1,21 @@
package bms.player.beatoraja.audio;

import java.io.InputStream;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import java.nio.file.*;
import java.util.Locale;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import bms.player.beatoraja.Config;
import bms.tool.util.Pair;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.audio.Sound;
import com.badlogic.gdx.files.FileHandle;
import com.badlogic.gdx.files.FileHandleStream;
import com.badlogic.gdx.utils.GdxRuntimeException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.InputStream;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Locale;

/**
* libGDX Sound(OpenAL)サウンドドライバ
Expand Down Expand Up @@ -57,6 +59,11 @@ protected Sound getKeySound(Path p) {
return null;
}

@Override
protected Sound getKeySound(SevenZArchiveContext ctx, String fileName) {
return getKeySound(ArchiveHandleStream.create(ctx, fileName));
}

private Sound getKeySound(String name, String ext) {
switch (ext.toLowerCase(Locale.ROOT)) {
case ".wav":
Expand All @@ -74,7 +81,7 @@ private Sound getKeySound(FileHandle handle) {
try {
return Gdx.audio.newSound(handle);
} catch (GdxRuntimeException e) {
logger.warn("音源ファイル読み込み失敗" + e.getMessage());
logger.error("音源ファイル読み込み失敗: ", e);
}
return null;
}
Expand Down Expand Up @@ -282,6 +289,25 @@ public OutputStream write(boolean overwrite) {
return null;
}
}

private static class ArchiveHandleStream extends FileHandleStream {
private final InputStream inputStream;

private ArchiveHandleStream(String fileName, InputStream inputStream) {
super(fileName);
this.inputStream = inputStream;
}

public static ArchiveHandleStream create(SevenZArchiveContext ctx, String resourceName) {
Pair<String, InputStream> _p = ctx.getInputStream(resourceName);
return new ArchiveHandleStream(_p.getFirst(), _p.getSecond());
}

@Override
public InputStream read() {
return inputStream;
}
}

static class WavFileInputStream extends InputStream {

Expand Down
Loading