Ver código fonte

Set the default volume to 100%, and add a fast path to volume control.

Paul Lietar 9 anos atrás
pai
commit
526c54702b
1 arquivos alterados com 19 adições e 9 exclusões
  1. 19 9
      src/player.rs

+ 19 - 9
src/player.rs

@@ -1,5 +1,6 @@
 use eventual::{self, Async};
 use portaudio;
+use std::borrow::Cow;
 use std::sync::{mpsc, Mutex, Arc, MutexGuard};
 use std::thread;
 use vorbis;
@@ -55,7 +56,7 @@ impl Player {
             position_ms: 0,
             position_measured_at: 0,
             update_time: util::now_ms(),
-            volume: 0x8000,
+            volume: 0xFFFF,
             end_of_track: false,
         }));
 
@@ -114,6 +115,21 @@ impl Player {
     }
 }
 
+fn apply_volume(volume: u16, data: &[i16]) -> Cow<[i16]> {
+    // Fast path when volume is 100%
+    if volume == 0xFFFF {
+        Cow::Borrowed(data)
+    } else {
+        Cow::Owned(data.iter()
+                       .map(|&x| {
+                           (x as i32
+                            * volume as i32
+                            / 0xFFFF) as i16
+                       })
+                       .collect())
+    }
+}
+
 impl PlayerInternal {
     fn run(self) {
         portaudio::initialize().unwrap();
@@ -247,14 +263,8 @@ impl PlayerInternal {
             if self.state.lock().unwrap().status == PlayStatus::kPlayStatusPlay {
                 match decoder.as_mut().unwrap().packets().next() {
                     Some(Ok(packet)) => {
-                        let buffer = packet.data
-                                           .iter()
-                                           .map(|&x| {
-                                               (x as i32
-                                                * self.state.lock().unwrap().volume as i32
-                                                / 0xFFFF) as i16
-                                           })
-                                           .collect::<Vec<i16>>();
+                        let buffer = apply_volume(self.state.lock().unwrap().volume,
+                                                  &packet.data);
                         match stream.write(&buffer) {
                             Ok(_) => (),
                             Err(portaudio::PaError::OutputUnderflowed) => eprintln!("Underflow"),