23
23
24
24
package com .iluwatar .event .queue ;
25
25
26
+ import org .slf4j .Logger ;
27
+ import org .slf4j .LoggerFactory ;
28
+
26
29
import java .io .File ;
27
30
import java .io .IOException ;
28
31
38
41
*
39
42
*/
40
43
public class Audio {
44
+ private static final Logger LOGGER = LoggerFactory .getLogger (Audio .class );
45
+ private static final Audio INSTANCE = new Audio ();
41
46
42
47
private static final int MAX_PENDING = 16 ;
43
48
44
- private static int headIndex ;
49
+ private int headIndex ;
50
+
51
+ private int tailIndex ;
45
52
46
- private static int tailIndex ;
53
+ private volatile Thread updateThread = null ;
47
54
48
- private static Thread updateThread = null ;
55
+ private PlayMessage [] pendingAudio = new PlayMessage [ MAX_PENDING ] ;
49
56
50
- private static PlayMessage [] pendingAudio = new PlayMessage [MAX_PENDING ];
57
+ // Visible only for testing purposes
58
+ Audio () {
59
+
60
+ }
61
+
62
+ public static Audio getInstance () {
63
+ return INSTANCE ;
64
+ }
51
65
52
66
/**
53
- * This method stops the Update Method's thread.
67
+ * This method stops the Update Method's thread and waits till service stops.
54
68
*/
55
- public static synchronized void stopService () {
69
+ public synchronized void stopService () throws InterruptedException {
56
70
if (updateThread != null ) {
57
71
updateThread .interrupt ();
58
72
}
73
+ updateThread .join ();
74
+ updateThread = null ;
59
75
}
60
76
61
77
/**
62
78
* This method check the Update Method's thread is started.
63
79
* @return boolean
64
80
*/
65
- public static synchronized boolean isServiceRunning () {
66
- if (updateThread != null && updateThread .isAlive () ) {
67
- return true ;
68
- } else {
69
- return false ;
70
- }
81
+ public synchronized boolean isServiceRunning () {
82
+ return updateThread != null && updateThread .isAlive ();
71
83
}
72
84
73
85
/**
74
86
* Starts the thread for the Update Method pattern if it was not started previously.
75
87
* Also when the thread is is ready initializes the indexes of the queue
76
88
*/
77
- public static void init () {
89
+ public void init () {
78
90
if (updateThread == null ) {
79
- updateThread = new Thread (new Runnable () {
80
- public void run () {
81
- while (!Thread .currentThread ().isInterrupted ()) {
82
- Audio .update ();
83
- }
91
+ updateThread = new Thread (() -> {
92
+ while (!Thread .currentThread ().isInterrupted ()) {
93
+ update ();
84
94
}
85
95
});
86
96
}
@@ -90,7 +100,7 @@ public void run() {
90
100
/**
91
101
* This is a synchronized thread starter
92
102
*/
93
- public static synchronized void startThread () {
103
+ private synchronized void startThread () {
94
104
if (!updateThread .isAlive ()) {
95
105
updateThread .start ();
96
106
headIndex = 0 ;
@@ -103,7 +113,7 @@ public static synchronized void startThread() {
103
113
* @param stream is the AudioInputStream for the method
104
114
* @param volume is the level of the audio's volume
105
115
*/
106
- public static void playSound (AudioInputStream stream , float volume ) {
116
+ public void playSound (AudioInputStream stream , float volume ) {
107
117
init ();
108
118
// Walk the pending requests.
109
119
for (int i = headIndex ; i != tailIndex ; i = (i + 1 ) % MAX_PENDING ) {
@@ -123,7 +133,7 @@ public static void playSound(AudioInputStream stream, float volume) {
123
133
* This method uses the Update Method pattern.
124
134
* It takes the audio from the queue and plays it
125
135
*/
126
- public static void update () {
136
+ private void update () {
127
137
// If there are no pending requests, do nothing.
128
138
if (headIndex == tailIndex ) {
129
139
return ;
@@ -136,13 +146,11 @@ public static void update() {
136
146
clip .open (audioStream );
137
147
clip .start ();
138
148
} catch (LineUnavailableException e ) {
139
- System .err .println ("Error occoured while loading the audio: The line is unavailable" );
140
- e .printStackTrace ();
149
+ LOGGER .trace ("Error occoured while loading the audio: The line is unavailable" , e );
141
150
} catch (IOException e ) {
142
- System .err .println ("Input/Output error while loading the audio" );
143
- e .printStackTrace ();
151
+ LOGGER .trace ("Input/Output error while loading the audio" , e );
144
152
} catch (IllegalArgumentException e ) {
145
- System . err . println ("The system doesn't support the sound: " + e .getMessage ());
153
+ LOGGER . trace ("The system doesn't support the sound: " + e .getMessage (), e );
146
154
}
147
155
}
148
156
@@ -153,7 +161,7 @@ public static void update() {
153
161
* @throws UnsupportedAudioFileException when the audio file is not supported
154
162
* @throws IOException when the file is not readable
155
163
*/
156
- public static AudioInputStream getAudioStream (String filePath )
164
+ public AudioInputStream getAudioStream (String filePath )
157
165
throws UnsupportedAudioFileException , IOException {
158
166
return AudioSystem .getAudioInputStream (new File (filePath ).getAbsoluteFile ());
159
167
}
@@ -162,7 +170,7 @@ public static AudioInputStream getAudioStream(String filePath)
162
170
* Returns with the message array of the queue
163
171
* @return PlayMessage[]
164
172
*/
165
- public static PlayMessage [] getPendingAudio () {
173
+ public PlayMessage [] getPendingAudio () {
166
174
return pendingAudio ;
167
175
}
168
176
0 commit comments