]> git.saurik.com Git - wxWidgets.git/blobdiff - utils/wxMMedia2/lib/sndfile.cpp
Ok. Vidwin works again on Windows.
[wxWidgets.git] / utils / wxMMedia2 / lib / sndfile.cpp
index 55f1c15e758bf297a3349915cccfbce1adbf2819..c92ea71d9e32988168320f869d989a5087971443 100644 (file)
@@ -2,7 +2,7 @@
 // Name: sndfile.cpp
 // Purpose:
 // Date: 08/11/1999
-// Author: Guilhem Lavaux <lavaux@easynet.fr> (C) 1999
+// Author: Guilhem Lavaux <lavaux@easynet.fr> (C) 1999, 2000
 // CVSID: $Id$
 // --------------------------------------------------------------------------
 #include <wx/wxprec.h>
 wxSoundRouterStream::wxSoundRouterStream(wxSoundStream& sndio)
   : wxSoundStreamCodec(sndio)
 {
-  m_router = NULL;
+    m_router = NULL;
 }
 
 wxSoundRouterStream::~wxSoundRouterStream()
 {
-  if (m_router)
-    delete m_router;
+    if (m_router)
+        delete m_router;
 }
 
 // --------------------------------------------------------------------------
@@ -42,16 +42,16 @@ wxSoundRouterStream::~wxSoundRouterStream()
 // --------------------------------------------------------------------------
 wxSoundStream& wxSoundRouterStream::Read(void *buffer, wxUint32 len)
 {
-  if (m_router) {
-    m_router->Read(buffer, len);
-    m_snderror  = m_router->GetError();
-    m_lastcount = m_router->GetLastAccess();
-  } else {
-    m_sndio->Read(buffer, len);
-    m_snderror  = m_sndio->GetError();
-    m_lastcount = m_sndio->GetLastAccess();
-  }
-  return *this;
+    if (m_router) {
+        m_router->Read(buffer, len);
+        m_snderror  = m_router->GetError();
+        m_lastcount = m_router->GetLastAccess();
+    } else {
+        m_sndio->Read(buffer, len);
+        m_snderror  = m_sndio->GetError();
+        m_lastcount = m_sndio->GetLastAccess();
+    }
+    return *this;
 }
 
 // --------------------------------------------------------------------------
@@ -59,14 +59,14 @@ wxSoundStream& wxSoundRouterStream::Read(void *buffer, wxUint32 len)
 // --------------------------------------------------------------------------
 wxSoundStream& wxSoundRouterStream::Write(const void *buffer, wxUint32 len)
 {
-  if (m_router) {
-    m_router->Write(buffer, len);
-    m_snderror  = m_router->GetError();
-    m_lastcount = m_router->GetLastAccess();
-  } else {
-    m_sndio->Write(buffer, len);
-    m_snderror  = m_sndio->GetError();
-    m_lastcount = m_sndio->GetLastAccess();
+    if (m_router) {
+        m_router->Write(buffer, len);
+        m_snderror  = m_router->GetError();
+        m_lastcount = m_router->GetLastAccess();
+    } else {
+        m_sndio->Write(buffer, len);
+        m_snderror  = m_sndio->GetError();
+        m_lastcount = m_sndio->GetLastAccess();
   }
   return *this;
 }
@@ -80,32 +80,34 @@ wxSoundStream& wxSoundRouterStream::Write(const void *buffer, wxUint32 len)
 // --------------------------------------------------------------------------
 bool wxSoundRouterStream::SetSoundFormat(const wxSoundFormatBase& format)
 {
-  if (m_router)
-    delete m_router;
-
-  if (m_sndio->SetSoundFormat(format)) {
-    wxSoundStream::SetSoundFormat(m_sndio->GetSoundFormat());
+    if (m_router)
+        delete m_router;
+    
+    // First, we try to setup the sound device
+    if (m_sndio->SetSoundFormat(format)) {
+        // We are lucky, it is working.
+        wxSoundStream::SetSoundFormat(m_sndio->GetSoundFormat());
+        return TRUE;
+    }
+    
+    switch(format.GetType()) {
+        case wxSOUND_NOFORMAT:
+            return FALSE;
+        case wxSOUND_PCM:
+            m_router = new wxSoundStreamPcm(*m_sndio);
+            m_router->SetSoundFormat(format);
+            break;
+        case wxSOUND_ULAW:
+            m_router = new wxSoundStreamUlaw(*m_sndio);
+            m_router->SetSoundFormat(format);
+            break;
+        case wxSOUND_G72X:
+            m_router = new wxSoundStreamG72X(*m_sndio);
+            m_router->SetSoundFormat(format);
+            break;
+    }
+    wxSoundStream::SetSoundFormat(m_router->GetSoundFormat());
     return TRUE;
-  }
-
-  switch(format.GetType()) {
-  case wxSOUND_NOFORMAT:
-    return FALSE;
-  case wxSOUND_PCM:
-    m_router = new wxSoundStreamPcm(*m_sndio);
-    m_router->SetSoundFormat(format);
-    break;
-  case wxSOUND_ULAW:
-    m_router = new wxSoundStreamUlaw(*m_sndio);
-    m_router->SetSoundFormat(format);
-    break;
-  case wxSOUND_G72X:
-    m_router = new wxSoundStreamG72X(*m_sndio);
-    m_router->SetSoundFormat(format);
-    break;
-  }
-  wxSoundStream::SetSoundFormat(m_router->GetSoundFormat());
-  return TRUE;
 }
 
 // --------------------------------------------------------------------------
@@ -126,21 +128,21 @@ wxUint32 wxSoundRouterStream::GetBestSize() const
 // --------------------------------------------------------------------------
 bool wxSoundRouterStream::StartProduction(int evt)
 {
-  if (!m_router) {
-    if (m_sndio->StartProduction(evt))
-      return TRUE;
-
-    m_snderror = m_sndio->GetError();
-    m_lastcount = m_sndio->GetLastAccess();
+    if (!m_router) {
+        if (m_sndio->StartProduction(evt))
+            return TRUE;
+        
+        m_snderror = m_sndio->GetError();
+        m_lastcount = m_sndio->GetLastAccess();
+        return FALSE;
+    }
+    
+    if (m_router->StartProduction(evt))
+        return TRUE;
+    
+    m_snderror = m_router->GetError();
+    m_lastcount = m_router->GetLastAccess();
     return FALSE;
-  }
-
-  if (m_router->StartProduction(evt))
-    return TRUE;
-
-  m_snderror = m_router->GetError();
-  m_lastcount = m_router->GetLastAccess();
-  return FALSE;
 } 
 
 // --------------------------------------------------------------------------
@@ -148,23 +150,22 @@ bool wxSoundRouterStream::StartProduction(int evt)
 // --------------------------------------------------------------------------
 bool wxSoundRouterStream::StopProduction()
 {
-  if (!m_router) {
-    if (m_sndio->StopProduction())
-      return TRUE;
-
-    m_snderror = m_sndio->GetError();
-    m_lastcount = m_sndio->GetLastAccess();
+    if (!m_router) {
+        if (m_sndio->StopProduction())
+            return TRUE;
+        
+        m_snderror = m_sndio->GetError();
+        m_lastcount = m_sndio->GetLastAccess();
+        return FALSE;
+    }
+    
+    if (m_router->StopProduction())
+        return TRUE;
+    
+    m_snderror = m_router->GetError();
+    m_lastcount = m_router->GetLastAccess();
     return FALSE;
-  }
-
-  if (m_router->StopProduction())
-    return TRUE;
-
-  m_snderror = m_router->GetError();
-  m_lastcount = m_router->GetLastAccess();
-  return FALSE;
 }
 
 // --------------------------------------------------------------------------
 // wxSoundFileStream: generic reader
@@ -172,9 +173,12 @@ bool wxSoundRouterStream::StopProduction()
 
 wxSoundFileStream::wxSoundFileStream(wxInputStream& stream,
                                      wxSoundStream& io_sound)
-  : m_codec(io_sound), m_sndio(&io_sound),
-    m_input(&stream), m_output(NULL), m_state(wxSOUND_FILE_STOPPED)
+        : m_codec(io_sound), m_sndio(&io_sound),
+          m_input(&stream), m_output(NULL), m_state(wxSOUND_FILE_STOPPED)
 {
+    m_length = 0;
+    m_bytes_left = 0;
+    m_prepared = FALSE;
 }
 
 wxSoundFileStream::wxSoundFileStream(wxOutputStream& stream,
@@ -182,6 +186,9 @@ wxSoundFileStream::wxSoundFileStream(wxOutputStream& stream,
   : m_codec(io_sound), m_sndio(&io_sound),
     m_input(NULL), m_output(&stream), m_state(wxSOUND_FILE_STOPPED)
 {
+  m_length = 0;
+  m_bytes_left = 0;
+  m_prepared = FALSE;
 }
 
 wxSoundFileStream::~wxSoundFileStream()
@@ -195,8 +202,9 @@ bool wxSoundFileStream::Play()
   if (m_state != wxSOUND_FILE_STOPPED)
     return FALSE;
 
-  if (!PrepareToPlay())
-    return FALSE;
+  if (!m_prepared)
+    if (!PrepareToPlay())
+      return FALSE;
 
   m_state = wxSOUND_FILE_PLAYING;
 
@@ -206,7 +214,7 @@ bool wxSoundFileStream::Play()
   return TRUE;
 }
 
-bool wxSoundFileStream::Record(unsigned long time)
+bool wxSoundFileStream::Record(wxUint32 time)
 {
   if (m_state != wxSOUND_FILE_STOPPED)
     return FALSE;
@@ -214,7 +222,7 @@ bool wxSoundFileStream::Record(unsigned long time)
   if (!PrepareToRecord(time))
     return FALSE;
 
-  m_len = m_sndformat->GetBytesFromTime(time);
+  FinishPreparation(m_sndformat->GetBytesFromTime(time));
 
   m_state = wxSOUND_FILE_RECORDING;
   if (!StartProduction(wxSOUND_INPUT))
@@ -231,6 +239,8 @@ bool wxSoundFileStream::Stop()
   if (!StopProduction())
     return FALSE;
 
+  m_prepared = FALSE;
+
   if (m_state == wxSOUND_FILE_RECORDING)
     if (!FinishRecording()) {
       m_state = wxSOUND_FILE_STOPPED;
@@ -287,10 +297,6 @@ wxSoundStream& wxSoundFileStream::Write(const void *buffer, wxUint32 len)
   return *this;
 }
 
-void wxSoundFileStream::SetDuplexMode(bool duplex)
-{
-}
-
 bool wxSoundFileStream::StartProduction(int evt)
 {
   m_sndio->SetEventHandler(this);
@@ -306,6 +312,53 @@ bool wxSoundFileStream::StopProduction()
   return m_codec.StopProduction();
 }
 
+void wxSoundFileStream::FinishPreparation(wxUint32 len)
+{
+  m_bytes_left = m_length = len;
+  m_prepared = TRUE;
+}
+
+wxString wxSoundFileStream::GetCodecName() const
+{
+    return wxString(wxT("wxSoundFileStream base codec"));
+}
+
+wxUint32 wxSoundFileStream::GetLength()
+{
+  if (m_input && !m_prepared && GetError() == wxSOUND_NOERR)
+    return (PrepareToPlay()) ? m_length : 0;
+
+  return m_length;
+}
+
+wxUint32 wxSoundFileStream::GetPosition()
+{
+  if (!m_prepared && m_input != NULL && GetError() == wxSOUND_NOERR)
+    PrepareToPlay();
+
+  return m_length-m_bytes_left;
+}
+
+wxUint32 wxSoundFileStream::SetPosition(wxUint32 new_position)
+{
+  if (!m_prepared && m_input != NULL && GetError() == wxSOUND_NOERR)
+    PrepareToPlay();
+
+  if (!m_prepared)
+    return 0;
+
+  if (!RepositionStream(new_position))
+      return m_length-m_bytes_left;
+  
+  if (new_position >= m_length) {
+    m_bytes_left = 0;
+    return m_length;
+  }
+
+  m_bytes_left = m_length-new_position;
+  return new_position;
+}
+
 void wxSoundFileStream::OnSoundEvent(int evt)
 {
   wxUint32 len = m_codec.GetBestSize();
@@ -317,21 +370,25 @@ void wxSoundFileStream::OnSoundEvent(int evt)
   while (!m_sndio->QueueFilled()) {
     switch(evt) {
     case wxSOUND_INPUT:
-      if (len > m_len)
-        len = m_len;
+      if (len > m_bytes_left)
+        len = m_bytes_left;
 
       len = m_codec.Read(buffer, len).GetLastAccess();
       PutData(buffer, len);
-      m_len -= len;
-      if (m_len == 0) {
+      m_bytes_left -= len;
+      if (m_bytes_left == 0) {
         Stop();
         delete[] buffer;
         return;
       }
       break;
     case wxSOUND_OUTPUT:
+      if (len > m_bytes_left)
+        len = m_bytes_left;
+
       len = GetData(buffer, len);
-      if (len == 0) {
+      m_bytes_left -= len;
+      if (m_bytes_left == 0) {
         Stop();
         delete[] buffer;
         return;