loading doesn't cause unavoidable lag (removed excessive blocking);

switched to a blocking queue list to manage album cover loading; threads
that should be daemons are daemons now;
This commit is contained in:
Harrison Deng 2018-08-23 22:21:33 -05:00
parent 211e37866e
commit b97d772ee9
3 changed files with 77 additions and 69 deletions

View File

@ -149,6 +149,7 @@ public class MusicList extends Observable {
@Override
public void run() {
Gdx.app.debug("MusicList", "recursive async search beginning.");
Array<FileHandle> obtainedAudioFiles = recursiveMusicSearch(directory);
Sort.instance().sort(obtainedAudioFiles, compare);
if (work) {
@ -164,6 +165,7 @@ public class MusicList extends Observable {
if (thread == null) {
work = true;
thread = new Thread(this, threadName);
thread.setDaemon(true);
thread.start();
return true;
} else {

View File

@ -40,6 +40,10 @@ public class MusicMetadataController extends Observable implements Disposable, O
}
}
/**
* if there is the same amount of metadata as there is music in the music list.
* @return whether or not both sizes are equal.
*/
public boolean isDone() {
return (metadataArray.size == musicList.getMusicArray().size);
}
@ -52,15 +56,11 @@ public class MusicMetadataController extends Observable implements Disposable, O
}
public int size() {
synchronized (loadingThread) {
return metadataArray.size;
}
return metadataArray.size;
}
public AudioMetadata getMetadata(int index) {
synchronized (loadingThread) {
return metadataArray.get(index);
}
return metadataArray.get(index);
}
@ -80,28 +80,25 @@ public class MusicMetadataController extends Observable implements Disposable, O
@Override
public void run() {
Gdx.app.debug(name, "loading...");
clear();
searching = true;
for (int i = 0; i < metadataArray.size; i++) {
metadataArray.get(i).dispose();
}
metadataArray.clear();
Array<AudioMetadata> tempMetadataArray = new Array<>();
for (int i = 0; i < musicList.getTotal() && work; i++) {
FileHandle musicFile = musicList.getMusicArray().get(i);
synchronized (this) {
switch (SupportedFormats.valueOf(musicFile.extension().toUpperCase())) {
case MP3:
metadataArray.add(new MP3Metadata(musicFile));
break;
case WAV:
metadataArray.add(new WAVMetadata(musicFile));
break;
default:
break;
}
switch (SupportedFormats.valueOf(musicFile.extension().toUpperCase())) {
case MP3:
tempMetadataArray.add(new MP3Metadata(musicFile));
break;
case WAV:
tempMetadataArray.add(new WAVMetadata(musicFile));
break;
default:
break;
}
}
if (work) {
metadataArray = tempMetadataArray;
searching = false;
Gdx.app.debug(name, "load complete.");
setChanged();
@ -130,4 +127,11 @@ public class MusicMetadataController extends Observable implements Disposable, O
loadAudioMetadata();
}
}
public void clear() {
for (int i = 0; i < metadataArray.size; i++) {
metadataArray.get(i).dispose();
}
metadataArray.clear();
}
}

View File

@ -2,6 +2,7 @@ package zero1hd.rhythmbullet.desktop.screens.main;
import java.util.Observable;
import java.util.Observer;
import java.util.concurrent.LinkedBlockingQueue;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Input.Keys;
@ -178,24 +179,27 @@ public class MusicSelectionPage extends Page implements Observer {
private synchronized void updateList(float delta) {
if (mc.getMusicList().isSearched()) {
if (mc.getMusicList().getTotal() != 0) {
if (selectables.size() != mmc.size()) {
MusicSelectable selectable = new MusicSelectable(mmc.getMetadata(selectables.size()));
selectables.add(selectable);
} else if (selectables.size() != vGroup.getChildren().size) {
vGroup.addActor(selectables.getButtons().get(vGroup.getChildren().size));
} else {
if (selectables.getChecked() == null) {
selectables.setMinCheckCount(1);
selectables.setChecked(mc.getCurrentMusicFileHandle());
scrollPane.scrollTo(selectables.getChecked().getX(), selectables.getChecked().getY(), selectables.getChecked().getWidth(), selectables.getChecked().getHeight());
} else if (selectables.getChecked().getMetadata().getFileHandle() != mc.getCurrentMusicFileHandle()) {
musicSelectDelay += delta;
if (musicSelectDelay >= 1f) {
mc.setMusicByFileHandle(selectables.getChecked().getMetadata().getFileHandle());
musicSelectDelay = 0;
if (mmc.isDone() && !mmc.isSearching()) {
if (selectables.size() != mmc.size()) {
MusicSelectable selectable = new MusicSelectable(mmc.getMetadata(selectables.size()));
selectables.add(selectable);
} else if (selectables.size() != vGroup.getChildren().size) {
vGroup.addActor(selectables.getButtons().get(vGroup.getChildren().size));
} else {
if (selectables.getChecked() == null) {
selectables.setMinCheckCount(1);
selectables.setChecked(mc.getCurrentMusicFileHandle());
scrollPane.scrollTo(selectables.getChecked().getX(), selectables.getChecked().getY(), selectables.getChecked().getWidth(), selectables.getChecked().getHeight());
} else if (selectables.getChecked().getMetadata().getFileHandle() != mc.getCurrentMusicFileHandle()) {
musicSelectDelay += delta;
if (musicSelectDelay >= 1f) {
mc.setMusicByFileHandle(selectables.getChecked().getMetadata().getFileHandle());
musicSelectDelay = 0;
}
}
}
}
} else {
//TODO: Error message reporting empty music list or something
}
@ -219,6 +223,7 @@ public class MusicSelectionPage extends Page implements Observer {
@Override
public void dispose() {
mc.getMusicList().deleteObserver(this);
selectionLoaderThread.stop();
super.dispose();
}
@ -231,13 +236,15 @@ public class MusicSelectionPage extends Page implements Observer {
selectables.setChecked(mc.getCurrentMusicFileHandle());
}
} else if (o == mc.getMusicList()) {
synchronized (this) {
if (arg == mc.getMusicList().states.LOADING) {
if (arg == mc.getMusicList().states.LOADING) {
synchronized (this) {
vGroup.clear();
selectables.clear();
musicInfoTable.setToDefault();
selectionLoaderThread.clear();
}
}
}
}
@ -250,31 +257,23 @@ public class MusicSelectionPage extends Page implements Observer {
private class musicSelectionLoaderThread implements Runnable {
private Thread thread;
private Array<AudioMetadata> queueList;
private String name = "Music-Selection-Loader-Thread";
private String name = "Music-Selection-Loader-Thread";
private volatile boolean work = true;
private LinkedBlockingQueue<AudioMetadata> queue;
public musicSelectionLoaderThread() {
queueList = new Array<>();
queue = new LinkedBlockingQueue<>();
}
@Override
public void run() {
while (work) {
while (queueList.size != 0) {
AudioMetadata metadata;
synchronized (this) {
metadata = queueList.pop();
metadata.loadAlbumCover();
simpleDebug("Loading " + metadata.getTitle());
}
}
synchronized (this) {
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
AudioMetadata metadata;
try {
metadata = queue.take();
metadata.loadAlbumCover();
simpleDebug("Loading " + metadata.getTitle());
} catch (InterruptedException e) {
simpleDebug("Thread was interupted.");
}
}
}
@ -282,21 +281,25 @@ public class MusicSelectionPage extends Page implements Observer {
public boolean start() {
if (thread == null) {
thread = new Thread(this, name);
thread.setDaemon(true);
thread.start();
return true;
} else {
synchronized (this) {
notify();
}
}
return false;
}
public void stop() {
clear();
thread.interrupt();
work = false;
}
public void clear() {
queue.clear();
}
public void queue(AudioMetadata metadata) {
if (!queueList.contains(metadata, true)) {
queueList.add(metadata);
start();
}
queue.add(metadata);
}
}
@ -348,7 +351,7 @@ public class MusicSelectionPage extends Page implements Observer {
actualCoords.x = getX() + getParent().getX();
actualCoords.y = getY() + getParent().getY();
if ((actualCoords.y < 0 - getHeight() || actualCoords.y > getStage().getHeight() || actualCoords.x < 0 - getWidth() || actualCoords.x > getStage().getWidth()) && selectables.getChecked() != this) {
if ((actualCoords.y < 0 - getHeight() - getStage().getHeight()*1.5f || actualCoords.y > getStage().getHeight()*1.5f) && selectables.getChecked() != this) {
offScreenAct(delta);
} else {
onScreenAct(delta);
@ -365,10 +368,9 @@ public class MusicSelectionPage extends Page implements Observer {
if (offScreen) {
offScreen = false;
timeSinceChanged = 0;
} else if (timeSinceChanged < 0.75f) {
} else if (timeSinceChanged < 0.075f) {
timeSinceChanged += delta;
}
if (timeSinceChanged >= 0.75f) {
} else {
if (!frameUsed && metadata.getAlbumCover() != null && !albumArtDisplayed) {
updateAlbumArtImage(metadata.getAlbumCover());
albumArtDisplayed = true;