diff src/Modules/Output/Graphics/Devices/GraphicsOutputDeviceMovie.cc @ 141:bbf4728ffa0e

Windows build fixes.
author tomwalters
date Tue, 02 Nov 2010 23:46:56 +0000
parents 88df1647d1a0
children f03d4455b262
line wrap: on
line diff
--- a/src/Modules/Output/Graphics/Devices/GraphicsOutputDeviceMovie.cc	Mon Nov 01 01:36:44 2010 +0000
+++ b/src/Modules/Output/Graphics/Devices/GraphicsOutputDeviceMovie.cc	Tue Nov 02 23:46:56 2010 +0000
@@ -1,264 +1,264 @@
-// Copyright 2006, Willem van Engen
-//
-// AIM-C: A C++ implementation of the Auditory Image Model
-// http://www.acousticscale.org/AIMC
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-/*!
- * \file
- * \brief Output device for output to a movie
- *
- * \author Willem van Engen <cnbh@willem.engen.nl>
- * \date created 2006/10/16
- * \version \$Id: GraphicsOutputDeviceMovie.cpp 633 2008-09-11 04:20:16Z tom $
- */
-
-/*! \todo
- *  A recent experiment showed that the video was about an audioframe
- *  (something like 30 ms) behind the audio in rdct.wav. It seems odd
- *  to me, since I already output a frame at the beginning to compensate
- *  for the missed buffer.
- *  A solution that would solve this and be a broader improvement, is to
- *  include the source's time when Fire()ing. The outputdevice can then
- *  do audio/video synchronization. In the case of the movie, the very
- *  first gGrab() looks at the time and emits as much empty output frames
- *  as needed until the correct signal time is reached.
- */
-#include "Support/Common.h"
-
-#ifdef _WINDOWS
-#  include <direct.h> // for _mkdir&_rmdir
-#else
-#  include <sys/types.h>
-#  include <dirent.h> // for opendir&friends
-#endif
-#include <stdio.h>
-#include <string.h>
-
-#include "Modules/Output/Graphics/Devices/GraphicsOutputDeviceMovie.h"
-
-namespace aimc {
-
-GraphicsOutputDeviceMovie::GraphicsOutputDeviceMovie(Parameters *parameters)
-  : GraphicsOutputDeviceCairo(parameters) {
-  sound_filename_.clear();
-  movie_filename_.clear();
-}
-
-bool GraphicsOutputDeviceMovie::Initialize(Parameters *global_parameters) {
-  global_parameters_ = global_parameters;
-  sound_filename_ = global_parameters->GetString("input_filename");
-  string file_suffix = parameters_->DefaultString("filename_suffix", ".mov");
-  movie_filename_ = global_parameters->GetString("output_filename_base")
-                    + file_suffix;
-  
-  FILE *f;
-
-  // Check sound file exists
-  if ((f = fopen(sound_filename_.c_str(), "r")) == NULL) {
-    LOG_ERROR(_T("Couldn't open sound file '%s' for movie creation."),
-             sound_filename_.c_str());
-    sound_filename_.clear();
-    return false;
-  }
-  fclose(f);
-
-  // Check movie output file can be made
-  if ((f = fopen(movie_filename_.c_str(), "w")) == NULL) {
-    LOG_ERROR(_T("Couldn't open movie file '%s' to write to."),
-             movie_filename_.c_str());
-    movie_filename_.clear();
-    return false;
-  }
-  fclose(f);
-
-  // Get a temporary image output directory
-  //! \warning Not really safe ... but windows has no mkdtemp()
-  //! \todo Make build system check for mkdtemp() to use it when available. See TODO.txt.
-#ifdef _WINDOWS
-  char *temp_dir = NULL;
-  if ((temp_dir = _tempnam(NULL, AIM_NAME))
-      && _mkdir(temp_dir) >= 0) {
-    directory_ = temp_dir;
-    directory_ += "\\"; // Make sure to end with trailing slash
-  } else  {
-    LOG_ERROR(_T("Couldn't create a temporary directory for movie output."));
-    if (temp_dir) {
-      free(temp_dir);
-    }
-    return false;
-  }
-  if (temp_dir) {
-    free(temp_dir);
-  }
-#else
-  char temp_dir[PATH_MAX];
-  strcpy(temp_dir, "/tmp/"AIM_NAME"-movie.XXXXXX");
-  if (mkdtemp(temp_dir)) {
-    directory_ = temp_dir;
-    directory_ += "/"; // Make sure to end with trailing slash    
-  } else {
-    LOG_ERROR(_T("Couldn't create a temporary directory for movie output."));
-    return false;
-  }
-#endif
-  
-  // We want png for movie conversion
-  parameters_->SetString("output.img.format", "png");
-  if ( !GraphicsOutputDeviceCairo::Initialize(directory_) ) {
-    return false;
-  }
-  return true;
-}
-
-void GraphicsOutputDeviceMovie::Start() {
-  GraphicsOutputDeviceCairo::Start();
-  // Output a couple of frames to get audio/video in sync, put params in there.
-  gGrab();
-  PlotParameterScreen();
-  gRelease();
-  gGrab();
-  PlotParameterScreen();
-  gRelease();
-}
-
-void GraphicsOutputDeviceMovie::Reset(Parameters* global_parameters) {
-  Stop();
-  Initialize(global_parameters);
-}
-
-void GraphicsOutputDeviceMovie::Stop() {
-  GraphicsOutputDeviceCairo::Stop();
-  CloseFile();
-
-#ifdef __WX__
-  // GUI only: popup dialog
-#else
-  printf("Generating movie ... \n");
-#endif
-  AIM_ASSERT(parameters_);
-  // Convert images and sound file to a movie.
-  //! \warning Movie files are overwritten without warning.
-  char sffmpegPath[1024];
-  if (!parameters_->IsSet("output.ffmpeg_path")) {
-  strcpy(sffmpegPath,"ffmpeg");
-  } else {
-    strcpy(sffmpegPath, parameters_->GetString("output.ffmpeg_path"));
-  }
-  char sCodecOptions[1024];
-  if (!parameters_->IsSet("output.ffmpeg_codec_options")) {
-    strcpy(sCodecOptions,"");
-  } else {
-    strcpy(sCodecOptions, parameters_->GetString("output.ffmpeg_codec_options"));
-  }
-  float frame_rate = global_parameters_->DefaultFloat("frame_rate", -1.0);
-  char sCmdLine[1024]; //!\todo check that snprintf does not want a larger buffer
-  snprintf(sCmdLine, sizeof(sCmdLine)/sizeof(sCmdLine[0]),
-    "%s -r %.2f -y -i \"%s\" -i \"%s%%06d.png\" "
-    "-sameq -r %.2f -ar 44100 -acodec pcm_s16le %s \"%s\"",
-    sffmpegPath, frame_rate, sound_filename_.c_str(), directory_.c_str(),
-    frame_rate, sCodecOptions, movie_filename_.c_str());
-    printf(sCmdLine);
-    printf("\n");
-  if (system(sCmdLine)) {
-    LOG_ERROR(_T("Couldn't create movie output."));
-  }
-
-#ifdef __WX__
-  // GUI only: close dialog again
-#endif
-  // Remove files in temporary directory and the dir itself
-  //! \todo make portable function, possibly decided on by build system
-#ifdef _WINDOWS
-  HANDLE hList;
-  WIN32_FIND_DATA FileData;
-  snprintf(sCmdLine, sizeof(sCmdLine)/sizeof(sCmdLine[0]), "%s/*.*", m_sDir);
-  if ((hList = FindFirstFile(sCmdLine, &FileData)) == INVALID_HANDLE_VALUE) {
-    LOG_ERROR(_T("Couldn't remove files from temporary directory."));
-    return;
-  }
-  bool bRMfinished = false;
-  while (!bRMfinished) {
-    snprintf(sCmdLine,
-             sizeof(sCmdLine)/sizeof(sCmdLine[0]),
-             "%s%s",
-             m_sDir,
-             FileData.cFileName);
-    remove(sCmdLine);
-    if (!FindNextFile(hList, &FileData) && GetLastError() == ERROR_NO_MORE_FILES) {
-      bRMfinished = true;
-    }
-  }
-  FindClose(hList);
-  _rmdir(m_sDir);
-#else
-  DIR *dir;
-  struct dirent *dirent;
-  if (!(dir = opendir(directory_.c_str()))) {
-    LOG_ERROR(_T("Couldn't remove files in temporary directory."));
-    return;
-  }
-  while ((dirent = readdir(dir))) {
-    snprintf(sCmdLine,
-             sizeof(sCmdLine)/sizeof(sCmdLine[0]),
-             "%s%s",
-             directory_.c_str(),
-             dirent->d_name);
-    unlink(sCmdLine);
-  }
-  closedir(dir);
-  rmdir(directory_.c_str());
-#endif
-}
-
-void GraphicsOutputDeviceMovie::PlotParameterScreen() {
-  AIM_ASSERT(parameters_);
-  char sStr[50];
-  int lineno = 1;
-
-  float fMarL = parameters_->GetFloat(_S("graph.margin.left"));
-  float fMarT = parameters_->GetFloat(_S("graph.margin.top"));
-  float fTextHeight = 1.0f / 50.0f * 1.2; // change this when fontsizing is there!
-
-  gText2f(fMarL, 1-(fMarT+fTextHeight*lineno++),
-          _S("AIM-C"));
-  gText2f(fMarL,
-          1-(fMarT+fTextHeight*lineno++),
-          _S("(c) 2006-2010, Thomas Walters, Willem van Engen"));
-  gText2f(fMarL,
-          1-(fMarT+fTextHeight*lineno++),
-          _S("http://aimc.acousticscale.org/"));
-  lineno++;
-
-  static const char *pPlotParams[] = {
-    _S("input.buffersize"),
-    _S("input.samplerate"),
-    _S("bmm.freqstart"),
-    _S("bmm.freqend"),
-    _S("bmm.numchannels"),
-    _S("preset.name"),
-    _S("preset.title"),
-    NULL
-  };
-  for (int i = 0; pPlotParams[i]; i++) {
-    snprintf(sStr,
-             sizeof(sStr)/sizeof(sStr[0]), _S("%s=%s"),
-             pPlotParams[i],
-             parameters_->GetString(pPlotParams[i]));
-    gText2f(fMarL,
-            1-(fMarT+fTextHeight*lineno++),
-            sStr);
-  }
-}
-}  // namespace aimc
+// Copyright 2006, Willem van Engen
+//
+// AIM-C: A C++ implementation of the Auditory Image Model
+// http://www.acousticscale.org/AIMC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//     http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+/*!
+ * \file
+ * \brief Output device for output to a movie
+ *
+ * \author Willem van Engen <cnbh@willem.engen.nl>
+ * \date created 2006/10/16
+ * \version \$Id: GraphicsOutputDeviceMovie.cpp 633 2008-09-11 04:20:16Z tom $
+ */
+
+/*! \todo
+ *  A recent experiment showed that the video was about an audioframe
+ *  (something like 30 ms) behind the audio in rdct.wav. It seems odd
+ *  to me, since I already output a frame at the beginning to compensate
+ *  for the missed buffer.
+ *  A solution that would solve this and be a broader improvement, is to
+ *  include the source's time when Fire()ing. The outputdevice can then
+ *  do audio/video synchronization. In the case of the movie, the very
+ *  first gGrab() looks at the time and emits as much empty output frames
+ *  as needed until the correct signal time is reached.
+ */
+#include "Support/Common.h"
+
+#ifdef _WINDOWS
+#  include <direct.h> // for _mkdir&_rmdir
+#else
+#  include <sys/types.h>
+#  include <dirent.h> // for opendir&friends
+#endif
+#include <stdio.h>
+#include <string.h>
+
+#include "Modules/Output/Graphics/Devices/GraphicsOutputDeviceMovie.h"
+
+namespace aimc {
+
+GraphicsOutputDeviceMovie::GraphicsOutputDeviceMovie(Parameters *parameters)
+  : GraphicsOutputDeviceCairo(parameters) {
+  sound_filename_.clear();
+  movie_filename_.clear();
+}
+
+bool GraphicsOutputDeviceMovie::Initialize(Parameters *global_parameters) {
+  global_parameters_ = global_parameters;
+  sound_filename_ = global_parameters->GetString("input_filename");
+  string file_suffix = parameters_->DefaultString("filename_suffix", ".mov");
+  movie_filename_ = global_parameters->GetString("output_filename_base")
+                    + file_suffix;
+  
+  FILE *f;
+
+  // Check sound file exists
+  if ((f = fopen(sound_filename_.c_str(), "r")) == NULL) {
+    LOG_ERROR(_T("Couldn't open sound file '%s' for movie creation."),
+             sound_filename_.c_str());
+    sound_filename_.clear();
+    return false;
+  }
+  fclose(f);
+
+  // Check movie output file can be made
+  if ((f = fopen(movie_filename_.c_str(), "w")) == NULL) {
+    LOG_ERROR(_T("Couldn't open movie file '%s' to write to."),
+             movie_filename_.c_str());
+    movie_filename_.clear();
+    return false;
+  }
+  fclose(f);
+
+  // Get a temporary image output directory
+  //! \warning Not really safe ... but windows has no mkdtemp()
+  //! \todo Make build system check for mkdtemp() to use it when available. See TODO.txt.
+#ifdef _WINDOWS
+  char *temp_dir = NULL;
+  if ((temp_dir = _tempnam(NULL, AIM_NAME))
+      && _mkdir(temp_dir) >= 0) {
+    directory_ = temp_dir;
+    directory_ += "\\"; // Make sure to end with trailing slash
+  } else  {
+    LOG_ERROR(_T("Couldn't create a temporary directory for movie output."));
+    if (temp_dir) {
+      free(temp_dir);
+    }
+    return false;
+  }
+  if (temp_dir) {
+    free(temp_dir);
+  }
+#else
+  char temp_dir[PATH_MAX];
+  strcpy(temp_dir, "/tmp/"AIM_NAME"-movie.XXXXXX");
+  if (mkdtemp(temp_dir)) {
+    directory_ = temp_dir;
+    directory_ += "/"; // Make sure to end with trailing slash    
+  } else {
+    LOG_ERROR(_T("Couldn't create a temporary directory for movie output."));
+    return false;
+  }
+#endif
+  
+  // We want png for movie conversion
+  parameters_->SetString("output.img.format", "png");
+  if ( !GraphicsOutputDeviceCairo::Initialize(directory_) ) {
+    return false;
+  }
+  return true;
+}
+
+void GraphicsOutputDeviceMovie::Start() {
+  GraphicsOutputDeviceCairo::Start();
+  // Output a couple of frames to get audio/video in sync, put params in there.
+  gGrab();
+  PlotParameterScreen();
+  gRelease();
+  gGrab();
+  PlotParameterScreen();
+  gRelease();
+}
+
+void GraphicsOutputDeviceMovie::Reset(Parameters* global_parameters) {
+  Stop();
+  Initialize(global_parameters);
+}
+
+void GraphicsOutputDeviceMovie::Stop() {
+  GraphicsOutputDeviceCairo::Stop();
+  CloseFile();
+
+#ifdef __WX__
+  // GUI only: popup dialog
+#else
+  printf("Generating movie ... \n");
+#endif
+  AIM_ASSERT(parameters_);
+  // Convert images and sound file to a movie.
+  //! \warning Movie files are overwritten without warning.
+  char sffmpegPath[1024];
+  if (!parameters_->IsSet("output.ffmpeg_path")) {
+  strcpy(sffmpegPath,"ffmpeg");
+  } else {
+    strcpy(sffmpegPath, parameters_->GetString("output.ffmpeg_path"));
+  }
+  char sCodecOptions[1024];
+  if (!parameters_->IsSet("output.ffmpeg_codec_options")) {
+    strcpy(sCodecOptions,"");
+  } else {
+    strcpy(sCodecOptions, parameters_->GetString("output.ffmpeg_codec_options"));
+  }
+  float frame_rate = global_parameters_->DefaultFloat("frame_rate", -1.0);
+  char sCmdLine[1024]; //!\todo check that snprintf does not want a larger buffer
+  snprintf(sCmdLine, sizeof(sCmdLine)/sizeof(sCmdLine[0]),
+    "%s -r %.2f -y -i \"%s\" -i \"%s%%06d.png\" "
+    "-sameq -r %.2f -ar 44100 -acodec pcm_s16le %s \"%s\"",
+    sffmpegPath, frame_rate, sound_filename_.c_str(), directory_.c_str(),
+    frame_rate, sCodecOptions, movie_filename_.c_str());
+    printf(sCmdLine);
+    printf("\n");
+  if (system(sCmdLine)) {
+    LOG_ERROR(_T("Couldn't create movie output."));
+  }
+
+#ifdef __WX__
+  // GUI only: close dialog again
+#endif
+  // Remove files in temporary directory and the dir itself
+  //! \todo make portable function, possibly decided on by build system
+#ifdef _WINDOWS
+  HANDLE hList;
+  WIN32_FIND_DATA FileData;
+  snprintf(sCmdLine, sizeof(sCmdLine)/sizeof(sCmdLine[0]), "%s/*.*", directory_.c_str());
+  if ((hList = FindFirstFile(sCmdLine, &FileData)) == INVALID_HANDLE_VALUE) {
+    LOG_ERROR(_T("Couldn't remove files from temporary directory."));
+    return;
+  }
+  bool bRMfinished = false;
+  while (!bRMfinished) {
+    snprintf(sCmdLine,
+             sizeof(sCmdLine)/sizeof(sCmdLine[0]),
+             "%s%s",
+             directory_.c_str(),
+             FileData.cFileName);
+    remove(sCmdLine);
+    if (!FindNextFile(hList, &FileData) && GetLastError() == ERROR_NO_MORE_FILES) {
+      bRMfinished = true;
+    }
+  }
+  FindClose(hList);
+  _rmdir(directory_.c_str());
+#else
+  DIR *dir;
+  struct dirent *dirent;
+  if (!(dir = opendir(directory_.c_str()))) {
+    LOG_ERROR(_T("Couldn't remove files in temporary directory."));
+    return;
+  }
+  while ((dirent = readdir(dir))) {
+    snprintf(sCmdLine,
+             sizeof(sCmdLine)/sizeof(sCmdLine[0]),
+             "%s%s",
+             directory_.c_str(),
+             dirent->d_name);
+    unlink(sCmdLine);
+  }
+  closedir(dir);
+  rmdir(directory_.c_str());
+#endif
+}
+
+void GraphicsOutputDeviceMovie::PlotParameterScreen() {
+  AIM_ASSERT(parameters_);
+  char sStr[50];
+  int lineno = 1;
+
+  float fMarL = parameters_->GetFloat(_S("graph.margin.left"));
+  float fMarT = parameters_->GetFloat(_S("graph.margin.top"));
+  float fTextHeight = 1.0f / 50.0f * 1.2; // change this when fontsizing is there!
+
+  gText2f(fMarL, 1-(fMarT+fTextHeight*lineno++),
+          _S("AIM-C"));
+  gText2f(fMarL,
+          1-(fMarT+fTextHeight*lineno++),
+          _S("(c) 2006-2010, Thomas Walters, Willem van Engen"));
+  gText2f(fMarL,
+          1-(fMarT+fTextHeight*lineno++),
+          _S("http://aimc.acousticscale.org/"));
+  lineno++;
+
+  static const char *pPlotParams[] = {
+    _S("input.buffersize"),
+    _S("input.samplerate"),
+    _S("bmm.freqstart"),
+    _S("bmm.freqend"),
+    _S("bmm.numchannels"),
+    _S("preset.name"),
+    _S("preset.title"),
+    NULL
+  };
+  for (int i = 0; pPlotParams[i]; i++) {
+    snprintf(sStr,
+             sizeof(sStr)/sizeof(sStr[0]), _S("%s=%s"),
+             pPlotParams[i],
+             parameters_->GetString(pPlotParams[i]));
+    gText2f(fMarL,
+            1-(fMarT+fTextHeight*lineno++),
+            sStr);
+  }
+}
+}  // namespace aimc