summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKlaus Schmidinger <vdr@tvdr.de>2013-10-10 13:13:30 +0200
committerKlaus Schmidinger <vdr@tvdr.de>2013-10-10 13:13:30 +0200
commit2bdb599fbcfea5bac49fcf5550cd0fd1bc328d4a (patch)
tree88e9d6c0b7505f1c4d9374c26a4c3ee27dd6ee90
parent3971cc6e8845f2a70018b20706f4a30d71edd41d (diff)
downloadvdr-2bdb599fbcfea5bac49fcf5550cd0fd1bc328d4a.tar.gz
vdr-2bdb599fbcfea5bac49fcf5550cd0fd1bc328d4a.tar.bz2
Added renaming and moving recordings and folders, and editing a recording's priority and lifetime; added cutting queue
-rw-r--r--CONTRIBUTORS5
-rw-r--r--HISTORY22
-rw-r--r--MANUAL24
-rw-r--r--cutter.c92
-rw-r--r--cutter.h40
-rw-r--r--menu.c387
-rw-r--r--menu.h6
-rw-r--r--osdbase.c10
-rw-r--r--osdbase.h4
-rw-r--r--po/ar.po63
-rw-r--r--po/ca_ES.po63
-rw-r--r--po/cs_CZ.po63
-rw-r--r--po/da_DK.po63
-rw-r--r--po/de_DE.po63
-rw-r--r--po/el_GR.po63
-rw-r--r--po/es_ES.po63
-rw-r--r--po/et_EE.po63
-rw-r--r--po/fi_FI.po63
-rw-r--r--po/fr_FR.po63
-rw-r--r--po/hr_HR.po63
-rw-r--r--po/hu_HU.po63
-rw-r--r--po/it_IT.po63
-rw-r--r--po/lt_LT.po63
-rw-r--r--po/mk_MK.po63
-rw-r--r--po/nl_NL.po63
-rw-r--r--po/nn_NO.po63
-rw-r--r--po/pl_PL.po63
-rw-r--r--po/pt_PT.po63
-rw-r--r--po/ro_RO.po63
-rw-r--r--po/ru_RU.po63
-rw-r--r--po/sk_SK.po63
-rw-r--r--po/sl_SI.po63
-rw-r--r--po/sr_RS.po63
-rw-r--r--po/sv_SE.po63
-rw-r--r--po/tr_TR.po63
-rw-r--r--po/uk_UA.po63
-rw-r--r--po/zh_CN.po63
-rw-r--r--recording.c524
-rw-r--r--recording.h129
-rw-r--r--shutdown.c8
-rw-r--r--svdrp.c94
-rw-r--r--svdrp.h3
-rw-r--r--tools.c71
-rw-r--r--tools.h7
-rw-r--r--vdr.c14
-rw-r--r--videodir.c14
46 files changed, 3036 insertions, 182 deletions
diff --git a/CONTRIBUTORS b/CONTRIBUTORS
index 5ba76e0c..775455d3 100644
--- a/CONTRIBUTORS
+++ b/CONTRIBUTORS
@@ -1170,6 +1170,7 @@ Rolf Ahrenberg <Rolf.Ahrenberg@sci.fi>
for a patch that was used to rename the "plp id" to a more general "stream id"
and add support for DVB-S2 "Input Stream Identifier" (ISI)
for helping to debug and understand subtitle page refreshes
+ for a patch that was used to implement the SVDRP command RENR
Ralf Klueber <ralf.klueber@vodafone.com>
for reporting a bug in cutting a recording if there is only a single editing mark
@@ -3180,3 +3181,7 @@ Manfred Völkel <mvoelkel@digitaldevices.de>
Thomas Maass <mase@setho.org>
for reporting a difference in the internal sequence of actions when pressing the Blue
and the Back key, respectively, during replay
+
+Martin Prochnow <nordlicht@martins-kabuff.de>
+ for writing the "extrecmenu" plugin, which inspired the implementation of editing
+ recording properties
diff --git a/HISTORY b/HISTORY
index 3f880fce..80e01096 100644
--- a/HISTORY
+++ b/HISTORY
@@ -7920,7 +7920,7 @@ Video Disk Recorder Revision History
- Fixed cleaning up old EPG events in case no epg data file is given (reported by
Dave Pickles).
-2013-09-07: Version 2.1.2
+2013-10-10: Version 2.1.2
- Updated the Finnish OSD texts (thanks to Rolf Ahrenberg).
- Fixed displaying DVB subtitles (thanks to Rolf Ahrenberg for helping to debug and
@@ -7966,3 +7966,23 @@ Video Disk Recorder Revision History
#define DEPRECATED_VIDEODIR
in videodir.h and recompile your plugins to see whether your code will work without
this variable. If you get a compile error, replace it with cVideoDirectory::Name().
+- Added renaming and moving recordings and folders, editing a recording's priority and
+ lifetime, and queueing cutting jobs (inspired by the "extrecmenu" plugin from Martin
+ Prochnow).
+ + The "Recording info" menu now has a new Blue button named "Edit", which opens a
+ dialog in which several properties of the selected recording can be changed. It can
+ be renamed or moved into another folder and its priority and lifetime can be
+ modified (inspired by the "extrecmenu" plugin from Martin Prochnow).
+ The new blue "Edit" button in the "Recordings" menu opens a dialog in which a folder
+ can be renamed or moved. See MANUAL, section "Managing folders".
+ + In the "Edit recording" menu the Yellow button ("Delete marks") allows you to delete
+ all editing marks of the selected recording.
+ + cCutter is no longer a static class. Cutting requests should now be invoked by
+ calling RecordingsHandler.Add(ruCut, FileName). See the new cRecordingsHandler
+ class in recording.h.
+ + Cutting jobs are now placed in a queue (together with any move or copy jobs) and
+ are processed one by one.
+ + The new SVDRP command RENR can be used to rename a recording (suggested by Rolf
+ Ahrenberg).
+ + Note that in several places in the source code a "copy" operation is mentioned,
+ however there is no user interface for this, yet.
diff --git a/MANUAL b/MANUAL
index e698085d..5ba44448 100644
--- a/MANUAL
+++ b/MANUAL
@@ -504,6 +504,30 @@ Version 2.0
folder, or enters a sub folder. Once a folder has been selected, the entire
path of the timer's file name will be replaced with the selected folder.
+ In the "Recordings" menu the folders of existing recordings can be renamed or
+ moved by pressing the "Blue" key ("Edit") while the cursor is positioned on
+ a folder. This will open a menu in which the folder's name and location (the
+ "parent" folder) can be edited. If such an operation will result in moving
+ more than one recording, you will be asked for confirmation.
+ The name, folder, priority and lifetime of an individual recording can be
+ changed by pressing the "Blue" key ("Info") while the cursor is positioned
+ on a recording, and in the resulting Info menu pressing the "Blue" key again
+ to bring up the "Edit recording" menu.
+ In the "Edit recording" menu the Red button ("Folder") allows you to select one
+ of your predefined folders. The Green button has multiple functions, depending
+ on what is currently going on with the recording. It can either stop or cancel
+ a cut, move or copy operation. If the button reads "Stop..." it means that the
+ respective operation is already happening, while "Cancel..." means that the
+ operation is still pending execution. If no operation is currently happening
+ and the recording has editing marks, the Button will read "Cut" and triggers
+ cutting the recording (same as pressing '2' while replaying the recording).
+ The Yellow button ("Delete marks") allows you to delete all editing marks from
+ the selected recording (if there are any and the recording is not currently
+ being cut). To directly edit the folder or name of the recording, position the
+ cursor to the respective line and press the Right key to start editing (press
+ Ok to confirm the edit, or Back to return to the previous value). Once you are
+ finished with editing the recording properties, press Ok to confirm the changes.
+
* Parameters in the "Setup" menu
Select "Setup" from the "VDR" menu to enter the setup menu. From there you can
diff --git a/cutter.c b/cutter.c
index ccb145a3..9aee66b9 100644
--- a/cutter.c
+++ b/cutter.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: cutter.c 3.3 2013/09/10 14:51:45 kls Exp $
+ * $Id: cutter.c 3.4 2013/10/02 13:18:02 kls Exp $
*/
#include "cutter.h"
@@ -642,34 +642,47 @@ void cCuttingThread::Action(void)
// --- cCutter ---------------------------------------------------------------
-cMutex cCutter::mutex;
-cString cCutter::originalVersionName;
-cString cCutter::editedVersionName;
-cCuttingThread *cCutter::cuttingThread = NULL;
-bool cCutter::error = false;
-bool cCutter::ended = false;
+cCutter::cCutter(const char *FileName)
+{
+ cuttingThread = NULL;
+ error = false;
+ originalVersionName = FileName;
+}
-bool cCutter::Start(const char *FileName)
+cCutter::~cCutter()
{
- cMutexLock MutexLock(&mutex);
- if (!cuttingThread) {
- error = false;
- ended = false;
- originalVersionName = FileName;
- cRecording Recording(FileName);
+ Stop();
+}
- cMarks FromMarks;
- FromMarks.Load(FileName, Recording.FramesPerSecond(), Recording.IsPesRecording());
- if (cMark *First = FromMarks.GetNextBegin())
+cString cCutter::EditedFileName(const char *FileName)
+{
+ cRecording Recording(FileName);
+ cMarks Marks;
+ if (Marks.Load(FileName, Recording.FramesPerSecond(), Recording.IsPesRecording())) {
+ if (cMark *First = Marks.GetNextBegin())
Recording.SetStartTime(Recording.Start() + (int(First->Position() / Recording.FramesPerSecond() + 30) / 60) * 60);
+ return Recording.PrefixFileName('%');
+ }
+ return NULL;
+}
- const char *evn = Recording.PrefixFileName('%');
- if (evn && cVideoDirectory::RemoveVideoFile(evn) && MakeDirs(evn, true)) {
- editedVersionName = evn;
- Recording.WriteInfo();
- Recordings.AddByName(editedVersionName, false);
- cuttingThread = new cCuttingThread(FileName, editedVersionName);
- return true;
+bool cCutter::Start(void)
+{
+ if (!cuttingThread) {
+ error = false;
+ if (*originalVersionName) {
+ cRecording Recording(originalVersionName);
+ editedVersionName = EditedFileName(originalVersionName);
+ if (*editedVersionName) {
+ if (strcmp(originalVersionName, editedVersionName) != 0) { // names must be different!
+ if (cVideoDirectory::RemoveVideoFile(editedVersionName) && MakeDirs(editedVersionName, true)) {
+ Recording.WriteInfo(editedVersionName);
+ Recordings.AddByName(editedVersionName, false);
+ cuttingThread = new cCuttingThread(originalVersionName, editedVersionName);
+ return true;
+ }
+ }
+ }
}
}
return false;
@@ -677,7 +690,6 @@ bool cCutter::Start(const char *FileName)
void cCutter::Stop(void)
{
- cMutexLock MutexLock(&mutex);
bool Interrupted = cuttingThread && cuttingThread->Active();
const char *Error = cuttingThread ? cuttingThread->Error() : NULL;
delete cuttingThread;
@@ -694,37 +706,22 @@ void cCutter::Stop(void)
}
}
-bool cCutter::Active(const char *FileName)
+bool cCutter::Active(void)
{
- cMutexLock MutexLock(&mutex);
if (cuttingThread) {
if (cuttingThread->Active())
- return !FileName || strcmp(FileName, originalVersionName) == 0 || strcmp(FileName, editedVersionName) == 0;
+ return true;
error = cuttingThread->Error();
Stop();
if (!error)
cRecordingUserCommand::InvokeCommand(RUC_EDITEDRECORDING, editedVersionName, originalVersionName);
- originalVersionName = NULL;
- editedVersionName = NULL;
- ended = true;
}
return false;
}
bool cCutter::Error(void)
{
- cMutexLock MutexLock(&mutex);
- bool result = error;
- error = false;
- return result;
-}
-
-bool cCutter::Ended(void)
-{
- cMutexLock MutexLock(&mutex);
- bool result = ended;
- ended = false;
- return result;
+ return error;
}
#define CUTTINGCHECKINTERVAL 500 // ms between checks for the active cutting process
@@ -737,10 +734,13 @@ bool CutRecording(const char *FileName)
cMarks Marks;
if (Marks.Load(FileName, Recording.FramesPerSecond(), Recording.IsPesRecording()) && Marks.Count()) {
if (Marks.GetNumSequences()) {
- if (cCutter::Start(FileName)) {
- while (cCutter::Active())
+ cCutter Cutter(FileName);
+ if (Cutter.Start()) {
+ while (Cutter.Active())
cCondWait::SleepMs(CUTTINGCHECKINTERVAL);
- return true;
+ if (!Cutter.Error())
+ return true;
+ fprintf(stderr, "error while cutting\n");
}
else
fprintf(stderr, "can't start editing process\n");
diff --git a/cutter.h b/cutter.h
index f48ae3fc..c67429a1 100644
--- a/cutter.h
+++ b/cutter.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: cutter.h 2.3 2012/02/16 12:05:33 kls Exp $
+ * $Id: cutter.h 3.1 2013/10/05 11:34:55 kls Exp $
*/
#ifndef __CUTTER_H
@@ -17,21 +17,31 @@ class cCuttingThread;
class cCutter {
private:
- static cMutex mutex;
- static cString originalVersionName;
- static cString editedVersionName;
- static cCuttingThread *cuttingThread;
- static bool error;
- static bool ended;
+ cString originalVersionName;
+ cString editedVersionName;
+ cCuttingThread *cuttingThread;
+ bool error;
public:
- static bool Start(const char *FileName);
- static void Stop(void);
- static bool Active(const char *FileName = NULL);
- ///< Returns true if the cutter is currently active.
- ///< If a FileName is given, true is only returned if either the
- ///< original or the edited file name is equal to FileName.
- static bool Error(void);
- static bool Ended(void);
+ cCutter(const char *FileName);
+ ///< Sets up a new cutter for the given FileName, which must be the full path
+ ///< name of an existing recording directory.
+ ~cCutter();
+ static cString EditedFileName(const char *FileName);
+ ///< Returns the full path name of the edited version of the recording with
+ ///< the given FileName. This static function can be used independent of any
+ ///< cCutter object, to determine the file name beforehand.
+ ///< Returns NULL in case of error.
+ bool Start(void);
+ ///< Starts the actual cutting process.
+ ///< Returns true if successful.
+ ///< If Start() is called while the cutting process is already active, nothing
+ ///< happens and false will be returned.
+ void Stop(void);
+ ///< Stops an ongoing cutting process.
+ bool Active(void);
+ ///< Returns true if the cutter is currently active.
+ bool Error(void);
+ ///< Returns true if an error occurred while cutting the recording.
};
bool CutRecording(const char *FileName);
diff --git a/menu.c b/menu.c
index f7629092..99ca4a66 100644
--- a/menu.c
+++ b/menu.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: menu.c 3.6 2013/09/10 13:16:40 kls Exp $
+ * $Id: menu.c 3.7 2013/10/10 12:31:08 kls Exp $
*/
#include "menu.h"
@@ -16,7 +16,6 @@
#include <string.h>
#include "channels.h"
#include "config.h"
-#include "cutter.h"
#include "eitscan.h"
#include "i18n.h"
#include "interface.h"
@@ -828,8 +827,7 @@ eOSState cMenuFolder::Edit(void)
eOSState cMenuFolder::SetFolder(void)
{
- cMenuEditFolder *mef = (cMenuEditFolder *)SubMenu();
- if (mef) {
+ if (cMenuEditFolder *mef = dynamic_cast<cMenuEditFolder *>(SubMenu())) {
Set(mef->GetFolder());
SetHelpKeys();
Display();
@@ -843,8 +841,7 @@ cString cMenuFolder::GetFolder(void)
if (firstFolder) {
cMenuFolderItem *Folder = (cMenuFolderItem *)Get(Current());
if (Folder) {
- cMenuFolder *mf = (cMenuFolder *)SubMenu();
- if (mf)
+ if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu()))
return cString::sprintf("%s%c%s", Folder->Folder()->Text(), FOLDERDELIMCHAR, *mf->GetFolder());
return Folder->Folder()->Text();
}
@@ -930,8 +927,7 @@ void cMenuEditTimer::SetFirstDayItem(void)
eOSState cMenuEditTimer::SetFolder(void)
{
- cMenuFolder *mf = (cMenuFolder *)SubMenu();
- if (mf) {
+ if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu())) {
cString Folder = mf->GetFolder();
char *p = strrchr(data.file, FOLDERDELIMCHAR);
if (p)
@@ -2105,26 +2101,302 @@ bool CamMenuActive(void)
return CamMenuIsOpen;
}
+// --- cMenuPathEdit ---------------------------------------------------------
+
+class cMenuPathEdit : public cOsdMenu {
+private:
+ cString path;
+ char folder[PATH_MAX];
+ char name[NAME_MAX];
+ cMenuEditStrItem *folderItem;
+ int pathIsInUse;
+ eOSState SetFolder(void);
+ eOSState Folder(void);
+ eOSState ApplyChanges(void);
+public:
+ cMenuPathEdit(const char *Path);
+ virtual eOSState ProcessKey(eKeys Key);
+ };
+
+cMenuPathEdit::cMenuPathEdit(const char *Path)
+:cOsdMenu(tr("Edit path"), 12)
+{
+ SetMenuCategory(mcRecording);
+ path = Path;
+ *folder = 0;
+ *name = 0;
+ const char *s = strrchr(path, FOLDERDELIMCHAR);
+ if (s) {
+ strn0cpy(folder, cString(path, s), sizeof(folder));
+ s++;
+ }
+ else
+ s = path;
+ strn0cpy(name, s, sizeof(name));
+ pathIsInUse = Recordings.PathIsInUse(path);
+ if (pathIsInUse) {
+ Add(new cOsdItem(tr("This folder is currently in use - no changes are possible!"), osUnknown, false));
+ Add(new cOsdItem("", osUnknown, false));
+ }
+ cOsdItem *p;
+ Add(p = folderItem = new cMenuEditStrItem(tr("Folder"), folder, sizeof(folder)));
+ p->SetSelectable(!pathIsInUse);
+ Add(p = new cMenuEditStrItem(tr("Name"), name, sizeof(name)));
+ p->SetSelectable(!pathIsInUse);
+ Display();
+ if (!pathIsInUse)
+ SetHelp(tr("Button$Folder"));
+}
+
+eOSState cMenuPathEdit::SetFolder(void)
+{
+ if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu())) {
+ strn0cpy(folder, mf->GetFolder(), sizeof(folder));
+ SetCurrent(folderItem);
+ Display();
+ }
+ return CloseSubMenu();
+}
+
+eOSState cMenuPathEdit::Folder(void)
+{
+ return AddSubMenu(new cMenuFolder(tr("Select folder"), &Folders, path));
+}
+
+eOSState cMenuPathEdit::ApplyChanges(void)
+{
+ if (!*name)
+ *name = ' '; // name must not be empty!
+ cString NewPath = *folder ? cString::sprintf("%s%c%s", folder, FOLDERDELIMCHAR, name) : name;
+ NewPath.CompactChars(FOLDERDELIMCHAR);
+ if (strcmp(NewPath, path)) {
+ int NumRecordings = Recordings.GetNumRecordingsInPath(path);
+ if (NumRecordings > 1 && !Interface->Confirm(cString::sprintf(tr("Move entire folder containing %d recordings?"), NumRecordings)))
+ return osContinue;
+ if (!Recordings.MoveRecordings(path, NewPath)) {
+ Skins.Message(mtError, tr("Error while moving folder!"));
+ return osContinue;
+ }
+ cMenuRecordings::SetPath(NewPath); // makes sure the Recordings menu will reposition to the new path
+ return osUser1;
+ }
+ return osBack;
+}
+
+eOSState cMenuPathEdit::ProcessKey(eKeys Key)
+{
+ eOSState state = cOsdMenu::ProcessKey(Key);
+ if (state == osUnknown) {
+ if (!pathIsInUse) {
+ switch (Key) {
+ case kRed: return Folder();
+ case kOk: return ApplyChanges();
+ default: break;
+ }
+ }
+ else if (Key == kOk)
+ return osBack;
+ }
+ else if (state == osEnd && HasSubMenu())
+ state = SetFolder();
+ return state;
+}
+
+// --- cMenuRecordingEdit ----------------------------------------------------
+
+class cMenuRecordingEdit : public cOsdMenu {
+private:
+ cRecording *recording;
+ char folder[PATH_MAX];
+ char name[NAME_MAX];
+ int priority;
+ int lifetime;
+ cMenuEditStrItem *folderItem;
+ const char *buttonFolder;
+ const char *buttonAction;
+ const char *buttonDeleteMarks;
+ const char *actionCancel;
+ const char *doCut;
+ int recordingIsInUse;
+ void Set(void);
+ void SetHelpKeys(void);
+ eOSState SetFolder(void);
+ eOSState Folder(void);
+ eOSState Action(void);
+ eOSState DeleteMarks(void);
+ eOSState ApplyChanges(void);
+public:
+ cMenuRecordingEdit(cRecording *Recording);
+ virtual eOSState ProcessKey(eKeys Key);
+ };
+
+cMenuRecordingEdit::cMenuRecordingEdit(cRecording *Recording)
+:cOsdMenu(tr("Edit recording"), 12)
+{
+ SetMenuCategory(mcRecording);
+ recording = Recording;
+ strn0cpy(folder, recording->Folder(), sizeof(folder));
+ strn0cpy(name, recording->BaseName(), sizeof(name));
+ priority = recording->Priority();
+ lifetime = recording->Lifetime();
+ folderItem = NULL;
+ buttonFolder = NULL;
+ buttonAction = NULL;
+ buttonDeleteMarks = NULL;
+ actionCancel = NULL;
+ doCut = NULL;
+ recordingIsInUse = recording->IsInUse();
+ Set();
+}
+
+void cMenuRecordingEdit::Set(void)
+{
+ Clear();
+ if (recordingIsInUse) {
+ Add(new cOsdItem(tr("This recording is currently in use - no changes are possible!"), osUnknown, false));
+ Add(new cOsdItem("", osUnknown, false));
+ }
+ cOsdItem *p;
+ Add(p = folderItem = new cMenuEditStrItem(tr("Folder"), folder, sizeof(folder)));
+ p->SetSelectable(!recordingIsInUse);
+ Add(p = new cMenuEditStrItem(tr("Name"), name, sizeof(name)));
+ p->SetSelectable(!recordingIsInUse);
+ Add(p = new cMenuEditIntItem(tr("Priority"), &priority, 0, MAXPRIORITY));
+ p->SetSelectable(!recordingIsInUse);
+ Add(p = new cMenuEditIntItem(tr("Lifetime"), &lifetime, 0, MAXLIFETIME));
+ p->SetSelectable(!recordingIsInUse);
+ Display();
+ SetHelpKeys();
+}
+
+void cMenuRecordingEdit::SetHelpKeys(void)
+{
+ buttonFolder = !recordingIsInUse ? tr("Button$Folder") : NULL;
+ buttonAction = NULL;
+ buttonDeleteMarks = NULL;
+ actionCancel = NULL;
+ doCut = NULL;
+ if ((recordingIsInUse & ruCut) != 0)
+ buttonAction = actionCancel = ((recordingIsInUse & ruPending) != 0) ? tr("Button$Stop cutting") : tr("Button$Cancel cutting");
+ else if ((recordingIsInUse & ruMove) != 0)
+ buttonAction = actionCancel = ((recordingIsInUse & ruPending) != 0) ? tr("Button$Stop moving") : tr("Button$Cancel moving");
+ else if ((recordingIsInUse & ruCopy) != 0)
+ buttonAction = actionCancel = ((recordingIsInUse & ruPending) != 0) ? tr("Button$Stop copying") : tr("Button$Cancel copying");
+ else if (recording->HasMarks()) {
+ buttonAction = doCut = tr("Button$Cut");
+ buttonDeleteMarks = tr("Button$Delete marks");
+ }
+ SetHelp(buttonFolder, buttonAction, buttonDeleteMarks);
+}
+
+eOSState cMenuRecordingEdit::SetFolder(void)
+{
+ if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu())) {
+ strn0cpy(folder, mf->GetFolder(), sizeof(folder));
+ SetCurrent(folderItem);
+ Display();
+ }
+ return CloseSubMenu();
+}
+
+eOSState cMenuRecordingEdit::Folder(void)
+{
+ return AddSubMenu(new cMenuFolder(tr("Select folder"), &Folders, recording->Name()));
+}
+
+eOSState cMenuRecordingEdit::Action(void)
+{
+ if (actionCancel)
+ RecordingsHandler.Del(recording->FileName());
+ else if (doCut) {
+ if (!RecordingsHandler.Add(ruCut, recording->FileName()))
+ Skins.Message(mtError, tr("Error while queueing recording for cutting!"));
+ }
+ recordingIsInUse = recording->IsInUse();
+ SetHelpKeys();
+ return osContinue;
+}
+
+eOSState cMenuRecordingEdit::DeleteMarks(void)
+{
+ if (buttonDeleteMarks && Interface->Confirm(tr("Delete editing marks for this recording?"))) {
+ if (recording->DeleteMarks())
+ SetHelpKeys();
+ else
+ Skins.Message(mtError, tr("Error while deleting editing marks!"));
+ }
+ return osContinue;
+}
+
+eOSState cMenuRecordingEdit::ApplyChanges(void)
+{
+ bool Modified = false;
+ if (priority != recording->Priority() || lifetime != recording->Lifetime()) {
+ if (!recording->ChangePriorityLifetime(priority, lifetime)) {
+ Skins.Message(mtError, tr("Error while changing priority/lifetime!"));
+ return osContinue;
+ }
+ Modified = true;
+ }
+ if (!*name)
+ *name = ' '; // name must not be empty!
+ cString NewName = *folder ? cString::sprintf("%s%c%s", folder, FOLDERDELIMCHAR, name) : name;
+ NewName.CompactChars(FOLDERDELIMCHAR);
+ if (strcmp(NewName, recording->Name())) {
+ if (!recording->ChangeName(NewName)) {
+ Skins.Message(mtError, tr("Error while changing folder/name!"));
+ return osContinue;
+ }
+ Modified = true;
+ }
+ if (Modified) {
+ cMenuRecordings::SetRecording(recording->FileName()); // makes sure the Recordings menu will reposition to the renamed recording
+ return osUser1;
+ }
+ return osBack;
+}
+
+eOSState cMenuRecordingEdit::ProcessKey(eKeys Key)
+{
+ eOSState state = cOsdMenu::ProcessKey(Key);
+ if (state == osUnknown) {
+ if (!recordingIsInUse) {
+ switch (Key) {
+ case kRed: return Folder();
+ case kGreen: return Action();
+ case kYellow: return DeleteMarks();
+ case kOk: return ApplyChanges();
+ default: break;
+ }
+ }
+ else if (Key == kOk)
+ return osBack;
+ }
+ else if (state == osEnd && HasSubMenu())
+ state = SetFolder();
+ return state;
+}
+
// --- cMenuRecording --------------------------------------------------------
class cMenuRecording : public cOsdMenu {
private:
- const cRecording *recording;
+ cRecording *recording;
bool withButtons;
public:
- cMenuRecording(const cRecording *Recording, bool WithButtons = false);
+ cMenuRecording(cRecording *Recording, bool WithButtons = false);
virtual void Display(void);
virtual eOSState ProcessKey(eKeys Key);
};
-cMenuRecording::cMenuRecording(const cRecording *Recording, bool WithButtons)
+cMenuRecording::cMenuRecording(cRecording *Recording, bool WithButtons)
:cOsdMenu(tr("Recording info"))
{
SetMenuCategory(mcRecordingInfo);
recording = Recording;
withButtons = WithButtons;
if (withButtons)
- SetHelp(tr("Button$Play"), tr("Button$Rewind"));
+ SetHelp(tr("Button$Play"), tr("Button$Rewind"), NULL, tr("Button$Edit"));
}
void cMenuRecording::Display(void)
@@ -2137,6 +2409,12 @@ void cMenuRecording::Display(void)
eOSState cMenuRecording::ProcessKey(eKeys Key)
{
+ if (HasSubMenu()) {
+ eOSState state = cOsdMenu::ProcessKey(Key);
+ if (state == osUser1)
+ CloseSubMenu();
+ return state;
+ }
switch (int(Key)) {
case kUp|k_Repeat:
case kUp:
@@ -2164,6 +2442,9 @@ eOSState cMenuRecording::ProcessKey(eKeys Key)
cRemote::Put(Key, true);
// continue with osBack to close the info menu and process the key
case kOk: return osBack;
+ case kBlue: if (withButtons)
+ return AddSubMenu(new cMenuRecordingEdit(recording));
+ break;
default: break;
}
}
@@ -2183,6 +2464,7 @@ public:
~cMenuRecordingItem();
void IncrementCounter(bool New);
const char *Name(void) { return name; }
+ int Level(void) { return level; }
cRecording *Recording(void) { return recording; }
bool IsDirectory(void) { return name != NULL; }
virtual void SetMenuItem(cSkinDisplayMenu *DisplayMenu, int Index, bool Current, bool Selectable);
@@ -2220,6 +2502,9 @@ void cMenuRecordingItem::SetMenuItem(cSkinDisplayMenu *DisplayMenu, int Index, b
// --- cMenuRecordings -------------------------------------------------------
+cString cMenuRecordings::path;
+cString cMenuRecordings::fileName;
+
cMenuRecordings::cMenuRecordings(const char *Base, int Level, bool OpenSubMenus)
:cOsdMenu(Base ? Base : tr("Recordings"), 9, 6, 6)
{
@@ -2232,8 +2517,12 @@ cMenuRecordings::cMenuRecordings(const char *Base, int Level, bool OpenSubMenus)
Set();
if (Current() < 0)
SetCurrent(First());
- else if (OpenSubMenus && cReplayControl::LastReplayed() && Open(true))
- return;
+ else if (OpenSubMenus && (cReplayControl::LastReplayed() || *path || *fileName)) {
+ if (!*path || Level < strcountchr(path, FOLDERDELIMCHAR)) {
+ if (Open(true))
+ return;
+ }
+ }
Display();
SetHelpKeys();
}
@@ -2251,18 +2540,14 @@ void cMenuRecordings::SetHelpKeys(void)
if (ri) {
if (ri->IsDirectory())
NewHelpKeys = 1;
- else {
+ else
NewHelpKeys = 2;
- if (ri->Recording()->Info()->Title())
- NewHelpKeys = 3;
- }
}
if (NewHelpKeys != helpKeys) {
switch (NewHelpKeys) {
case 0: SetHelp(NULL); break;
- case 1: SetHelp(tr("Button$Open")); break;
- case 2:
- case 3: SetHelp(RecordingCommands.Count() ? tr("Commands") : tr("Button$Play"), tr("Button$Rewind"), tr("Button$Delete"), NewHelpKeys == 3 ? tr("Button$Info") : NULL);
+ case 1: SetHelp(tr("Button$Open"), NULL, NULL, tr("Button$Edit")); break;
+ case 2: SetHelp(RecordingCommands.Count() ? tr("Commands") : tr("Button$Play"), tr("Button$Rewind"), tr("Button$Delete"), tr("Button$Info"));
default: ;
}
helpKeys = NewHelpKeys;
@@ -2271,7 +2556,7 @@ void cMenuRecordings::SetHelpKeys(void)
void cMenuRecordings::Set(bool Refresh)
{
- const char *CurrentRecording = cReplayControl::LastReplayed();
+ const char *CurrentRecording = *fileName ? *fileName : cReplayControl::LastReplayed();
cMenuRecordingItem *LastItem = NULL;
cThreadLock RecordingsLock(&Recordings);
if (Refresh) {
@@ -2303,7 +2588,11 @@ void cMenuRecordings::Set(bool Refresh)
else
delete Item;
if (LastItem || LastDir) {
- if (CurrentRecording && strcmp(CurrentRecording, recording->FileName()) == 0)
+ if (*path) {
+ if (strcmp(path, recording->Folder()) == 0)
+ SetCurrent(LastDir ? LastDir : LastItem);
+ }
+ else if (CurrentRecording && strcmp(CurrentRecording, recording->FileName()) == 0)
SetCurrent(LastDir ? LastDir : LastItem);
}
if (LastDir)
@@ -2314,6 +2603,16 @@ void cMenuRecordings::Set(bool Refresh)
Display();
}
+void cMenuRecordings::SetPath(const char *Path)
+{
+ path = Path;
+}
+
+void cMenuRecordings::SetRecording(const char *FileName)
+{
+ fileName = FileName;
+}
+
cString cMenuRecordings::DirectoryName(void)
{
cString d(cVideoDirectory::Name());
@@ -2328,11 +2627,11 @@ cString cMenuRecordings::DirectoryName(void)
bool cMenuRecordings::Open(bool OpenSubMenus)
{
cMenuRecordingItem *ri = (cMenuRecordingItem *)Get(Current());
- if (ri && ri->IsDirectory()) {
+ if (ri && ri->IsDirectory() && (!*path || strcountchr(path, FOLDERDELIMCHAR) > 0)) {
const char *t = ri->Name();
cString buffer;
if (base) {
- buffer = cString::sprintf("%s~%s", base, t);
+ buffer = cString::sprintf("%s%c%s", base, FOLDERDELIMCHAR, t);
t = buffer;
}
AddSubMenu(new cMenuRecordings(t, level + 1, OpenSubMenus));
@@ -2395,10 +2694,10 @@ eOSState cMenuRecordings::Delete(void)
}
cRecording *recording = ri->Recording();
cString FileName = recording->FileName();
- if (cCutter::Active(ri->Recording()->FileName())) {
+ if (RecordingsHandler.GetUsage(FileName)) {
if (Interface->Confirm(tr("Recording is being edited - really delete?"))) {
- cCutter::Stop();
- recording = Recordings.GetByName(FileName); // cCutter::Stop() might have deleted it if it was the edited version
+ RecordingsHandler.Del(FileName);
+ recording = Recordings.GetByName(FileName); // RecordingsHandler.Del() might have deleted it if it was the edited version
// we continue with the code below even if recording is NULL,
// in order to have the menu updated etc.
}
@@ -2428,9 +2727,12 @@ eOSState cMenuRecordings::Info(void)
{
if (HasSubMenu() || Count() == 0)
return osContinue;
- cMenuRecordingItem *ri = (cMenuRecordingItem *)Get(Current());
- if (ri && !ri->IsDirectory() && ri->Recording()->Info()->Title())
- return AddSubMenu(new cMenuRecording(ri->Recording(), true));
+ if (cMenuRecordingItem *ri = (cMenuRecordingItem *)Get(Current())) {
+ if (ri->IsDirectory())
+ return AddSubMenu(new cMenuPathEdit(cString(ri->Recording()->Name(), strchrn(ri->Recording()->Name(), FOLDERDELIMCHAR, ri->Level() + 1))));
+ else
+ return AddSubMenu(new cMenuRecording(ri->Recording(), true));
+ }
return osContinue;
}
@@ -2481,6 +2783,17 @@ eOSState cMenuRecordings::ProcessKey(eKeys Key)
default: break;
}
}
+ else if (state == osUser1) {
+ // a recording or path was renamed, so let's refresh the menu
+ CloseSubMenu(false);
+ if (base)
+ return state; // closes all recording menus except for the top one
+ Set(); // this is the top level menu, so we refresh it...
+ Open(true); // ...and open any necessary submenus to show the new name
+ Display();
+ path = NULL;
+ fileName = NULL;
+ }
if (Key == kYellow && HadSubMenu && !HasSubMenu()) {
// the last recording in a subdirectory was deleted, so let's go back up
cOsdMenu::Del(Current());
@@ -3462,13 +3775,13 @@ bool cMenuMain::Update(bool Force)
}
// Editing control:
- bool CutterActive = cCutter::Active();
- if (CutterActive && !cancelEditingItem) {
+ bool EditingActive = RecordingsHandler.Active();
+ if (EditingActive && !cancelEditingItem) {
// TRANSLATORS: note the leading blank!
Add(cancelEditingItem = new cOsdItem(tr(" Cancel editing"), osCancelEdit));
result = true;
}
- else if (cancelEditingItem && !CutterActive) {
+ else if (cancelEditingItem && !EditingActive) {
Del(cancelEditingItem->Index());
cancelEditingItem = NULL;
result = true;
@@ -3518,7 +3831,7 @@ eOSState cMenuMain::ProcessKey(eKeys Key)
}
break;
case osCancelEdit: if (Interface->Confirm(tr("Cancel editing?"))) {
- cCutter::Stop();
+ RecordingsHandler.DelAll();
return osEnd;
}
break;
@@ -4853,12 +5166,12 @@ void cReplayControl::EditCut(void)
{
if (*fileName) {
Hide();
- if (!cCutter::Active()) {
+ if (!RecordingsHandler.GetUsage(fileName)) {
if (!marks.Count())
Skins.Message(mtError, tr("No editing marks defined!"));
else if (!marks.GetNumSequences())
Skins.Message(mtError, tr("No editing sequences defined!"));
- else if (!cCutter::Start(fileName))
+ else if (!RecordingsHandler.Add(ruCut, fileName))
Skins.Message(mtError, tr("Can't start editing process!"));
else
Skins.Message(mtInfo, tr("Editing process started"));
diff --git a/menu.h b/menu.h
index db17f983..03e91715 100644
--- a/menu.h
+++ b/menu.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: menu.h 3.1 2013/06/01 13:44:57 kls Exp $
+ * $Id: menu.h 3.2 2013/09/22 10:47:32 kls Exp $
*/
#ifndef __MENU_H
@@ -198,6 +198,8 @@ private:
int level;
int recordingsState;
int helpKeys;
+ static cString path;
+ static cString fileName;
void SetHelpKeys(void);
void Set(bool Refresh = false);
bool Open(bool OpenSubMenus = false);
@@ -213,6 +215,8 @@ public:
cMenuRecordings(const char *Base = NULL, int Level = 0, bool OpenSubMenus = false);
~cMenuRecordings();
virtual eOSState ProcessKey(eKeys Key);
+ static void SetPath(const char *Path);
+ static void SetRecording(const char *FileName);
};
class cRecordControl {
diff --git a/osdbase.c b/osdbase.c
index baadc0e6..b788edb0 100644
--- a/osdbase.c
+++ b/osdbase.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: osdbase.c 3.1 2013/05/24 10:19:31 kls Exp $
+ * $Id: osdbase.c 3.2 2013/09/22 14:01:17 kls Exp $
*/
#include "osdbase.h"
@@ -502,12 +502,14 @@ eOSState cOsdMenu::AddSubMenu(cOsdMenu *SubMenu)
return osContinue; // convenience return value
}
-eOSState cOsdMenu::CloseSubMenu()
+eOSState cOsdMenu::CloseSubMenu(bool ReDisplay)
{
delete subMenu;
subMenu = NULL;
- RefreshCurrent();
- Display();
+ if (ReDisplay) {
+ RefreshCurrent();
+ Display();
+ }
return osContinue; // convenience return value
}
diff --git a/osdbase.h b/osdbase.h
index 46351841..07dce352 100644
--- a/osdbase.h
+++ b/osdbase.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: osdbase.h 2.5 2012/12/07 09:49:35 kls Exp $
+ * $Id: osdbase.h 3.1 2013/09/22 14:00:47 kls Exp $
*/
#ifndef __OSDBASE_H
@@ -119,7 +119,7 @@ protected:
void Mark(void);
eOSState HotKey(eKeys Key);
eOSState AddSubMenu(cOsdMenu *SubMenu);
- eOSState CloseSubMenu();
+ eOSState CloseSubMenu(bool ReDisplay = true);
bool HasSubMenu(void) { return subMenu; }
cOsdMenu *SubMenu(void) { return subMenu; }
void SetStatus(const char *s);
diff --git a/po/ar.po b/po/ar.po
index 1676dcbe..224bbe98 100644
--- a/po/ar.po
+++ b/po/ar.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-10-16 11:16-0400\n"
"Last-Translator: Osama Alrawab <alrawab@hotmail.com>\n"
"Language-Team: Arabic <ar@li.org>\n"
@@ -727,6 +727,67 @@ msgstr "الرجاء ادخال %d رقم!"
msgid "CAM not responding!"
msgstr "الكامة لا تستجيب"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "معلومات التسجبل"
diff --git a/po/ca_ES.po b/po/ca_ES.po
index 0362cd83..a1808cf8 100644
--- a/po/ca_ES.po
+++ b/po/ca_ES.po
@@ -10,7 +10,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-03-02 19:02+0100\n"
"Last-Translator: Luca Olivetti <luca@ventoso.org>\n"
"Language-Team: Catalan <vdr@linuxtv.org>\n"
@@ -726,6 +726,67 @@ msgstr "Si us plau introdueixi %d digitos"
msgid "CAM not responding!"
msgstr "CAM no respon"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Informació de la gravació"
diff --git a/po/cs_CZ.po b/po/cs_CZ.po
index 2bd4a8e4..899559aa 100644
--- a/po/cs_CZ.po
+++ b/po/cs_CZ.po
@@ -10,7 +10,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2010-05-06 11:00+0200\n"
"Last-Translator: Aleš Juřík <ajurik@quick.cz>\n"
"Language-Team: Czech <vdr@linuxtv.org>\n"
@@ -726,6 +726,67 @@ msgstr "ProsĂ­m vloĹžte %d znakĹŻ!"
msgid "CAM not responding!"
msgstr "CAM neodpovĂ­dĂĄ!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Detail nahrĂĄvky"
diff --git a/po/da_DK.po b/po/da_DK.po
index edd0f5f4..a9bb5dea 100644
--- a/po/da_DK.po
+++ b/po/da_DK.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
"Last-Translator: Mogens Elneff <mogens@elneff.dk>\n"
"Language-Team: Danish <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Indtast venligst %d cifre!"
msgid "CAM not responding!"
msgstr "CAM svarer ikke!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Optagelses info"
diff --git a/po/de_DE.po b/po/de_DE.po
index 4cc8e844..54ec37e7 100644
--- a/po/de_DE.po
+++ b/po/de_DE.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2010-01-16 16:46+0100\n"
"Last-Translator: Klaus Schmidinger <vdr@tvdr.de>\n"
"Language-Team: German <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Bitte geben Sie %d Ziffern ein!"
msgid "CAM not responding!"
msgstr "CAM antwortet nicht!"
+msgid "Edit path"
+msgstr "Pfad editieren"
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr "Dieser Ordner ist zur Zeit in Verwendung - es sind keine Änderungen möglich!"
+
+msgid "Folder"
+msgstr "Ordner"
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr "Ganzen Ordner mit %d Aufnahmen verschieben?"
+
+msgid "Error while moving folder!"
+msgstr "Fehler beim Verschieben des Ordners!"
+
+msgid "Edit recording"
+msgstr "Aufnahme editieren"
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr "Diese Aufnahme ist zur Zeit in Verwendung - es sind keine Änderungen möglich!"
+
+msgid "Button$Stop cutting"
+msgstr "Schnitt beenden"
+
+msgid "Button$Cancel cutting"
+msgstr "Schnitt abbrechen"
+
+msgid "Button$Stop moving"
+msgstr "Verschieben beenden"
+
+msgid "Button$Cancel moving"
+msgstr "Verschieben abbrechen"
+
+msgid "Button$Stop copying"
+msgstr "Kopieren beenden"
+
+msgid "Button$Cancel copying"
+msgstr "Kopieren abbrechen"
+
+msgid "Button$Cut"
+msgstr "Schneiden"
+
+msgid "Button$Delete marks"
+msgstr "Marken löschen"
+
+msgid "Error while queueing recording for cutting!"
+msgstr "Fehler beim Hinzufügen der Aufnahme zur Schnittwarteschlange"
+
+msgid "Delete editing marks for this recording?"
+msgstr "Schnittmarken für diese Aufnahme löschen?"
+
+msgid "Error while deleting editing marks!"
+msgstr "Fehler beim Löschen der Schnittmarken!"
+
+msgid "Error while changing priority/lifetime!"
+msgstr "Fehler beim Ändern der Priorität bzw. Lebensdauer!"
+
+msgid "Error while changing folder/name!"
+msgstr "Fehler beim Ändern des Ordners bzw. Namens!"
+
msgid "Recording info"
msgstr "Aufzeichnung"
diff --git a/po/el_GR.po b/po/el_GR.po
index 8df5b786..37486a2f 100644
--- a/po/el_GR.po
+++ b/po/el_GR.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
"Last-Translator: Dimitrios Dimitrakos <mail@dimitrios.de>\n"
"Language-Team: Greek <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr ""
msgid "CAM not responding!"
msgstr ""
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Đëçńďöďńßĺň EăăńáöŢň"
diff --git a/po/es_ES.po b/po/es_ES.po
index 023871ec..9b87401c 100644
--- a/po/es_ES.po
+++ b/po/es_ES.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-03-02 19:02+0100\n"
"Last-Translator: Luca Olivetti <luca@ventoso.org>\n"
"Language-Team: Spanish <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "ĄIntroduzca %d dígitos!"
msgid "CAM not responding!"
msgstr "ĄCAM no responde!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Información de grabación"
diff --git a/po/et_EE.po b/po/et_EE.po
index 5ab2d101..94b65fc1 100644
--- a/po/et_EE.po
+++ b/po/et_EE.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
"Last-Translator: Arthur Konovalov <artlov@gmail.com>\n"
"Language-Team: Estonian <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Palun sisestada %d numbrit!"
msgid "CAM not responding!"
msgstr "CAM ei vasta"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Salvestuse info"
diff --git a/po/fi_FI.po b/po/fi_FI.po
index d67f1f10..c159accb 100644
--- a/po/fi_FI.po
+++ b/po/fi_FI.po
@@ -11,7 +11,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2007-08-15 15:52+0200\n"
"Last-Translator: Matti Lehtimäki <matti.lehtimaki@gmail.com>\n"
"Language-Team: Finnish <vdr@linuxtv.org>\n"
@@ -727,6 +727,67 @@ msgstr "SyÜtä %d numeroa!"
msgid "CAM not responding!"
msgstr "CA-moduuli ei vastaa!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Tallenteen tiedot"
diff --git a/po/fr_FR.po b/po/fr_FR.po
index a4eda2fb..b7b4f40b 100644
--- a/po/fr_FR.po
+++ b/po/fr_FR.po
@@ -17,7 +17,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-02-24 12:56+0100\n"
"Last-Translator: Dominique Plu <dplu@free.fr>\n"
"Language-Team: French <vdr@linuxtv.org>\n"
@@ -733,6 +733,67 @@ msgstr "Veuillez entrer %d chiffres !"
msgid "CAM not responding!"
msgstr "Pas de rĂŠponse du CAM"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Infos sur l'enregistrement"
diff --git a/po/hr_HR.po b/po/hr_HR.po
index baafe9d5..09298ee8 100644
--- a/po/hr_HR.po
+++ b/po/hr_HR.po
@@ -9,7 +9,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-03-17 19:00+0100\n"
"Last-Translator: Adrian Caval <anrxc@sysphere.org>\n"
"Language-Team: Croatian <vdr@linuxtv.org>\n"
@@ -725,6 +725,67 @@ msgstr "Molim unesite %d znamenki!"
msgid "CAM not responding!"
msgstr "CAM ne odgovara!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Detalji snimanja"
diff --git a/po/hu_HU.po b/po/hu_HU.po
index b3c17b0c..c341ce0a 100644
--- a/po/hu_HU.po
+++ b/po/hu_HU.po
@@ -10,7 +10,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-01 19:22+0200\n"
"Last-Translator: IstvĂĄn FĂźley <ifuley@tigercomp.ro>\n"
"Language-Team: Hungarian <vdr@linuxtv.org>\n"
@@ -727,6 +727,67 @@ msgstr "Üssön be %d számot!"
msgid "CAM not responding!"
msgstr "A CAM nem vĂĄlaszol!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "FelvĂŠtel infĂł"
diff --git a/po/it_IT.po b/po/it_IT.po
index e579885f..0ff2a37d 100644
--- a/po/it_IT.po
+++ b/po/it_IT.po
@@ -11,7 +11,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-02-11 23:46+0100\n"
"Last-Translator: Diego Pierotto <vdr-italian@tiscali.it>\n"
"Language-Team: Italian <vdr@linuxtv.org>\n"
@@ -730,6 +730,67 @@ msgstr "Inserisci %d cifre!"
msgid "CAM not responding!"
msgstr "La CAM non risponde!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Info registrazione"
diff --git a/po/lt_LT.po b/po/lt_LT.po
index 34e273c7..a6fb50e1 100644
--- a/po/lt_LT.po
+++ b/po/lt_LT.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2010-10-30 11:55+0200\n"
"Last-Translator: Valdemaras Pipiras <varas@ambernet.lt>\n"
"Language-Team: Lithuanian <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Ďveskite %d skaičius!"
msgid "CAM not responding!"
msgstr "Dekodavimo modulis (CAM) neveikia!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Informacija apie ÄŻraĹĄus"
diff --git a/po/mk_MK.po b/po/mk_MK.po
index a398b3ca..d4600fbb 100644
--- a/po/mk_MK.po
+++ b/po/mk_MK.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2012-11-19 15:18+0100\n"
"Last-Translator: Dimitar Petrovski <dimeptr@gmail.com>\n"
"Language-Team: Macedonian <en@li.org>\n"
@@ -724,6 +724,67 @@ msgstr "Внеси %d цифри!"
msgid "CAM not responding!"
msgstr "CAM не одговара!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Детали на снимката"
diff --git a/po/nl_NL.po b/po/nl_NL.po
index e9b9a001..56ff33b3 100644
--- a/po/nl_NL.po
+++ b/po/nl_NL.po
@@ -12,7 +12,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-02-26 17:20+0100\n"
"Last-Translator: Cedric Dewijs <cedric.dewijs@telfort.nl>\n"
"Language-Team: Dutch <vdr@linuxtv.org>\n"
@@ -728,6 +728,67 @@ msgstr "Vul %d cijfers in!"
msgid "CAM not responding!"
msgstr "CAM reageert niet!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Opname info"
diff --git a/po/nn_NO.po b/po/nn_NO.po
index a05410fa..29f1486b 100644
--- a/po/nn_NO.po
+++ b/po/nn_NO.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
"Last-Translator: Truls Slevigen <truls@slevigen.no>\n"
"Language-Team: Norwegian Nynorsk <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr ""
msgid "CAM not responding!"
msgstr ""
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr ""
diff --git a/po/pl_PL.po b/po/pl_PL.po
index f240894f..9ad56a3b 100644
--- a/po/pl_PL.po
+++ b/po/pl_PL.po
@@ -9,7 +9,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-03-09 12:59+0100\n"
"Last-Translator: Marek Nazarko <mnazarko@gmail.com>\n"
"Language-Team: Polish <vdr@linuxtv.org>\n"
@@ -725,6 +725,67 @@ msgstr "Proszę podać %d cyfr!"
msgid "CAM not responding!"
msgstr "CAM nie reaguje!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Informacje o nagraniu"
diff --git a/po/pt_PT.po b/po/pt_PT.po
index 7dde8c56..62b8a9fa 100644
--- a/po/pt_PT.po
+++ b/po/pt_PT.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2010-03-28 22:49+0100\n"
"Last-Translator: Cris Silva <hudokkow@gmail.com>\n"
"Language-Team: Portuguese <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "Por favor introduza %d dígitos!"
msgid "CAM not responding!"
msgstr "A CAM năo responde!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Informaçăo da gravaçăo"
diff --git a/po/ro_RO.po b/po/ro_RO.po
index f49c4523..b4e5c284 100644
--- a/po/ro_RO.po
+++ b/po/ro_RO.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-02-09 23:01+0100\n"
"Last-Translator: Lucian Muresan <lucianm@users.sorceforge.net>\n"
"Language-Team: Romanian <vdr@linuxtv.org>\n"
@@ -725,6 +725,67 @@ msgstr "Vă rog introduceţi %d cifre!"
msgid "CAM not responding!"
msgstr "CAM-ul nu reacţionează!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Detaliile Înregistrării"
diff --git a/po/ru_RU.po b/po/ru_RU.po
index 78565601..42a7b007 100644
--- a/po/ru_RU.po
+++ b/po/ru_RU.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-10 17:13+0100\n"
"Last-Translator: Oleg Roitburd <oroitburd@gmail.com>\n"
"Language-Team: Russian <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "˝ĐÖÜŘâŐ %d ćŘäŕë"
msgid "CAM not responding!"
msgstr "CAM ÝŐ ŢâŇŐçĐŐâ"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "¸ÝäŢ Ţ ×ĐßŘáŘ"
diff --git a/po/sk_SK.po b/po/sk_SK.po
index 6e849b0b..208c2419 100644
--- a/po/sk_SK.po
+++ b/po/sk_SK.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-04 21:24+0100\n"
"Last-Translator: Milan Hrala <hrala.milan@gmail.com>\n"
"Language-Team: Slovak <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Prosím vložte %d znakov!"
msgid "CAM not responding!"
msgstr "CAM neodpovedá!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Podrobnosti nahrávky"
diff --git a/po/sl_SI.po b/po/sl_SI.po
index 6e9ca323..0d40510f 100644
--- a/po/sl_SI.po
+++ b/po/sl_SI.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-04 12:46+0100\n"
"Last-Translator: Matjaz Thaler <matjaz.thaler@guest.arnes.si>\n"
"Language-Team: Slovenian <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "Prosim vnesite %d številk!"
msgid "CAM not responding!"
msgstr "CAM se ne odziva!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Podatki o snemanju"
diff --git a/po/sr_RS.po b/po/sr_RS.po
index 12586f77..36c9dbba 100644
--- a/po/sr_RS.po
+++ b/po/sr_RS.po
@@ -8,7 +8,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-16 15:05+0100\n"
"Last-Translator: Zoran Turalija <zoran.turalija@gmail.com>\n"
"Language-Team: Serbian <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "Molimo unesite %d brojeve!"
msgid "CAM not responding!"
msgstr "CAM ne reaguje!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Detalji snimanja"
diff --git a/po/sv_SE.po b/po/sv_SE.po
index 58492c49..cee61560 100644
--- a/po/sv_SE.po
+++ b/po/sv_SE.po
@@ -11,7 +11,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-02-18 17:04+0100\n"
"Last-Translator: Richard Lithvall <r-vdr@boomer.se>\n"
"Language-Team: Swedish <vdr@linuxtv.org>\n"
@@ -727,6 +727,67 @@ msgstr "Mata in %d siffror!"
msgid "CAM not responding!"
msgstr "CAM svarar inte!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Inspelningsinformation"
diff --git a/po/tr_TR.po b/po/tr_TR.po
index d9201803..d672db68 100644
--- a/po/tr_TR.po
+++ b/po/tr_TR.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2008-02-28 00:33+0100\n"
"Last-Translator: Oktay Yolgeçen <oktay_73@yahoo.de>\n"
"Language-Team: Turkish <vdr@linuxtv.org>\n"
@@ -723,6 +723,67 @@ msgstr "Lütfen %d rakam veriniz!"
msgid "CAM not responding!"
msgstr "CAM yanýt vermiyor!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Kayýt bilgisi"
diff --git a/po/uk_UA.po b/po/uk_UA.po
index 829921d4..80087568 100644
--- a/po/uk_UA.po
+++ b/po/uk_UA.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-02-09 16:00+0100\n"
"Last-Translator: Yarema aka Knedlyk <yupadmin@gmail.com>\n"
"Language-Team: Ukrainian <vdr@linuxtv.org>\n"
@@ -724,6 +724,67 @@ msgstr "Введіть %d цифри!"
msgid "CAM not responding!"
msgstr "CAM не відповідає!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "Про запис"
diff --git a/po/zh_CN.po b/po/zh_CN.po
index 8ba5e4dd..0d7c9755 100644
--- a/po/zh_CN.po
+++ b/po/zh_CN.po
@@ -7,7 +7,7 @@ msgid ""
msgstr ""
"Project-Id-Version: VDR 2.0.0\n"
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
-"POT-Creation-Date: 2013-06-10 12:16+0200\n"
+"POT-Creation-Date: 2013-10-10 14:32+0200\n"
"PO-Revision-Date: 2013-03-04 14:52+0800\n"
"Last-Translator: NFVDR <nfvdr@live.com>\n"
"Language-Team: Chinese (simplified) <nfvdr@live.com>\n"
@@ -725,6 +725,67 @@ msgstr "请输入 %d 数字!"
msgid "CAM not responding!"
msgstr "CAM 没有响应!"
+msgid "Edit path"
+msgstr ""
+
+msgid "This folder is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Folder"
+msgstr ""
+
+#, c-format
+msgid "Move entire folder containing %d recordings?"
+msgstr ""
+
+msgid "Error while moving folder!"
+msgstr ""
+
+msgid "Edit recording"
+msgstr ""
+
+msgid "This recording is currently in use - no changes are possible!"
+msgstr ""
+
+msgid "Button$Stop cutting"
+msgstr ""
+
+msgid "Button$Cancel cutting"
+msgstr ""
+
+msgid "Button$Stop moving"
+msgstr ""
+
+msgid "Button$Cancel moving"
+msgstr ""
+
+msgid "Button$Stop copying"
+msgstr ""
+
+msgid "Button$Cancel copying"
+msgstr ""
+
+msgid "Button$Cut"
+msgstr ""
+
+msgid "Button$Delete marks"
+msgstr ""
+
+msgid "Error while queueing recording for cutting!"
+msgstr ""
+
+msgid "Delete editing marks for this recording?"
+msgstr ""
+
+msgid "Error while deleting editing marks!"
+msgstr ""
+
+msgid "Error while changing priority/lifetime!"
+msgstr ""
+
+msgid "Error while changing folder/name!"
+msgstr ""
+
msgid "Recording info"
msgstr "录像信息"
diff --git a/recording.c b/recording.c
index 5cbf1070..31eb25b5 100644
--- a/recording.c
+++ b/recording.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: recording.c 3.3 2013/09/11 08:28:27 kls Exp $
+ * $Id: recording.c 3.4 2013/10/09 11:53:37 kls Exp $
*/
#include "recording.h"
@@ -20,8 +20,10 @@
#include <sys/stat.h>
#include <unistd.h>
#include "channels.h"
+#include "cutter.h"
#include "i18n.h"
#include "interface.h"
+#include "menu.h"
#include "remux.h"
#include "ringbuffer.h"
#include "skins.h"
@@ -422,6 +424,13 @@ void cRecordingInfo::SetFramesPerSecond(double FramesPerSecond)
framesPerSecond = FramesPerSecond;
}
+void cRecordingInfo::SetFileName(const char *FileName)
+{
+ bool IsPesRecording = fileName && endswith(fileName, ".vdr");
+ free(fileName);
+ fileName = strdup(cString::sprintf("%s%s", FileName, IsPesRecording ? INFOFILESUFFIX ".vdr" : INFOFILESUFFIX));
+}
+
bool cRecordingInfo::Read(FILE *f)
{
if (ownEvent) {
@@ -769,7 +778,7 @@ cRecording::cRecording(cTimer *Timer, const cEvent *Event)
else if (Timer->IsSingleEvent() || !Setup.UseSubtitle)
name = strdup(Timer->File());
else
- name = strdup(cString::sprintf("%s~%s", Timer->File(), Subtitle));
+ name = strdup(cString::sprintf("%s%c%s", Timer->File(), FOLDERDELIMCHAR, Subtitle));
// substitute characters that would cause problems in file names:
strreplace(name, '\n', ' ');
start = Timer->StartTime();
@@ -963,8 +972,9 @@ char *cRecording::SortName(void) const
void cRecording::ClearSortName(void)
{
- DELETENULL(sortBufferName);
- DELETENULL(sortBufferTime);
+ free(sortBufferName);
+ free(sortBufferTime);
+ sortBufferName = sortBufferTime = NULL;
}
int cRecording::GetResume(void) const
@@ -982,6 +992,28 @@ int cRecording::Compare(const cListObject &ListObject) const
return strcasecmp(SortName(), r->SortName());
}
+bool cRecording::IsInPath(const char *Path)
+{
+ if (isempty(Path))
+ return true;
+ int l = strlen(Path);
+ return strncmp(Path, name, l) == 0 && (name[l] == FOLDERDELIMCHAR);
+}
+
+cString cRecording::Folder(void) const
+{
+ if (char *s = strrchr(name, FOLDERDELIMCHAR))
+ return cString(name, s);
+ return "";
+}
+
+cString cRecording::BaseName(void) const
+{
+ if (char *s = strrchr(name, FOLDERDELIMCHAR))
+ return cString(s + 1);
+ return name;
+}
+
const char *cRecording::FileName(void) const
{
if (!fileName) {
@@ -1097,6 +1129,22 @@ bool cRecording::IsOnVideoDirectoryFileSystem(void) const
return isOnVideoDirectoryFileSystem;
}
+bool cRecording::HasMarks(void)
+{
+ return access(cMarks::MarksFileName(this), F_OK) == 0;
+}
+
+bool cRecording::DeleteMarks(void)
+{
+ if (remove(cMarks::MarksFileName(this)) < 0) {
+ if (errno != ENOENT) {
+ LOG_ERROR_STR(fileName);
+ return false;
+ }
+ }
+ return true;
+}
+
void cRecording::ReadInfo(void)
{
info->Read();
@@ -1105,13 +1153,13 @@ void cRecording::ReadInfo(void)
framesPerSecond = info->framesPerSecond;
}
-bool cRecording::WriteInfo(void)
+bool cRecording::WriteInfo(const char *OtherFileName)
{
- cString InfoFileName = cString::sprintf("%s%s", fileName, isPesRecording ? INFOFILESUFFIX ".vdr" : INFOFILESUFFIX);
- FILE *f = fopen(InfoFileName, "w");
- if (f) {
+ cString InfoFileName = cString::sprintf("%s%s", OtherFileName ? OtherFileName : FileName(), isPesRecording ? INFOFILESUFFIX ".vdr" : INFOFILESUFFIX);
+ cSafeFile f(InfoFileName);
+ if (f.Open()) {
info->Write(f);
- fclose(f);
+ f.Close();
}
else
LOG_ERROR_STR(*InfoFileName);
@@ -1125,6 +1173,58 @@ void cRecording::SetStartTime(time_t Start)
fileName = NULL;
}
+bool cRecording::ChangePriorityLifetime(int NewPriority, int NewLifetime)
+{
+ if (NewPriority != Priority() || NewLifetime != Lifetime()) {
+ dsyslog("changing priority/lifetime of '%s' to %d/%d", Name(), NewPriority, NewLifetime);
+ if (IsPesRecording()) {
+ cString OldFileName = FileName();
+ priority = NewPriority;
+ lifetime = NewLifetime;
+ free(fileName);
+ fileName = NULL;
+ cString NewFileName = FileName();
+ if (!cVideoDirectory::RenameVideoFile(OldFileName, NewFileName))
+ return false;
+ info->SetFileName(NewFileName);
+ }
+ else {
+ priority = info->priority = NewPriority;
+ lifetime = info->lifetime = NewLifetime;
+ if (!WriteInfo())
+ return false;
+ }
+ Recordings.ChangeState();
+ Recordings.TouchUpdate();
+ }
+ return true;
+}
+
+bool cRecording::ChangeName(const char *NewName)
+{
+ if (strcmp(NewName, Name())) {
+ dsyslog("changing name of '%s' to '%s'", Name(), NewName);
+ cString OldName = Name();
+ cString OldFileName = FileName();
+ free(fileName);
+ fileName = NULL;
+ free(name);
+ name = strdup(NewName);
+ cString NewFileName = FileName();
+ if (!(MakeDirs(NewFileName, true) && cVideoDirectory::MoveVideoFile(OldFileName, NewFileName))) {
+ free(name);
+ name = strdup(OldName);
+ free(fileName);
+ fileName = strdup(OldFileName);
+ return false;
+ }
+ ClearSortName();
+ Recordings.ChangeState();
+ Recordings.TouchUpdate();
+ }
+ return true;
+}
+
bool cRecording::Delete(void)
{
bool result = true;
@@ -1188,6 +1288,17 @@ bool cRecording::Undelete(void)
return result;
}
+int cRecording::IsInUse(void) const
+{
+ int Use = ruNone;
+ if (cRecordControls::GetRecordControl(FileName()))
+ Use |= ruTimer;
+ if (cReplayControl::NowReplaying() && strcmp(cReplayControl::NowReplaying(), FileName()) == 0)
+ Use |= ruReplay;
+ Use |= RecordingsHandler.GetUsage(FileName());
+ return Use;
+}
+
void cRecording::ResetResume(void) const
{
resume = RESUME_NOT_INITIALIZED;
@@ -1426,6 +1537,46 @@ double cRecordings::MBperMinute(void)
return (size && length) ? double(size) * 60 / length : -1;
}
+int cRecordings::PathIsInUse(const char *Path)
+{
+ LOCK_THREAD;
+ int Use = ruNone;
+ for (cRecording *recording = First(); recording; recording = Next(recording)) {
+ if (recording->IsInPath(Path))
+ Use |= recording->IsInUse();
+ }
+ return Use;
+}
+
+int cRecordings::GetNumRecordingsInPath(const char *Path)
+{
+ LOCK_THREAD;
+ int n = 0;
+ for (cRecording *recording = First(); recording; recording = Next(recording)) {
+ if (recording->IsInPath(Path))
+ n++;
+ }
+ return n;
+}
+
+bool cRecordings::MoveRecordings(const char *OldPath, const char *NewPath)
+{
+ if (OldPath && NewPath && strcmp(OldPath, NewPath)) {
+ LOCK_THREAD;
+ dsyslog("moving '%s' to '%s'", OldPath, NewPath);
+ for (cRecording *recording = First(); recording; recording = Next(recording)) {
+ if (recording->IsInPath(OldPath)) {
+ const char *p = recording->Name() + strlen(OldPath);
+ cString NewName = cString::sprintf("%s%s", NewPath, p);
+ if (!recording->ChangeName(NewName))
+ return false;
+ ChangeState();
+ }
+ }
+ }
+ return true;
+}
+
void cRecordings::ResetResume(const char *ResumeFileName)
{
LOCK_THREAD;
@@ -1443,6 +1594,356 @@ void cRecordings::ClearSortNames(void)
recording->ClearSortName();
}
+// --- cDirCopier ------------------------------------------------------------
+
+class cDirCopier : public cThread {
+private:
+ cString dirNameSrc;
+ cString dirNameDst;
+ bool error;
+ bool suspensionLogged;
+ bool Throttled(void);
+ virtual void Action(void);
+public:
+ cDirCopier(const char *DirNameSrc, const char *DirNameDst);
+ virtual ~cDirCopier();
+ void Stop(void);
+ bool Error(void) { return error; }
+ };
+
+cDirCopier::cDirCopier(const char *DirNameSrc, const char *DirNameDst)
+:cThread("file copier", true)
+{
+ dirNameSrc = DirNameSrc;
+ dirNameDst = DirNameDst;
+ error = false;
+ suspensionLogged = false;
+}
+
+cDirCopier::~cDirCopier()
+{
+ Stop();
+}
+
+bool cDirCopier::Throttled(void)
+{
+ if (cIoThrottle::Engaged()) {
+ if (!suspensionLogged) {
+ dsyslog("suspending copy thread");
+ suspensionLogged = true;
+ }
+ return true;
+ }
+ else if (suspensionLogged) {
+ dsyslog("resuming copy thread");
+ suspensionLogged = false;
+ }
+ return false;
+}
+
+void cDirCopier::Action(void)
+{
+ if (DirectoryOk(dirNameDst, true)) {
+ cReadDir d(dirNameSrc);
+ if (d.Ok()) {
+ dsyslog("copying directory '%s' to '%s'", *dirNameSrc, *dirNameDst);
+ dirent *e = NULL;
+ cString FileNameSrc;
+ cString FileNameDst;
+ int From = -1;
+ int To = -1;
+ size_t BufferSize = BUFSIZ;
+ while (Running()) {
+ // Suspend cutting if we have severe throughput problems:
+ if (Throttled()) {
+ cCondWait::SleepMs(100);
+ continue;
+ }
+ // Copy all files in the source directory to the destination directory:
+ if (e) {
+ // We're currently copying a file:
+ uchar Buffer[BufferSize];
+ size_t Read = safe_read(From, Buffer, sizeof(Buffer));
+ if (Read > 0) {
+ size_t Written = safe_write(To, Buffer, Read);
+ if (Written != Read) {
+ esyslog("ERROR: can't write to destination file '%s': %m", *FileNameDst);
+ break;
+ }
+ }
+ else if (Read == 0) { // EOF on From
+ e = NULL; // triggers switch to next entry
+ if (fsync(To) < 0) {
+ esyslog("ERROR: can't sync destination file '%s': %m", *FileNameDst);
+ break;
+ }
+ if (close(From) < 0) {
+ esyslog("ERROR: can't close source file '%s': %m", *FileNameSrc);
+ break;
+ }
+ if (close(To) < 0) {
+ esyslog("ERROR: can't close destination file '%s': %m", *FileNameDst);
+ break;
+ }
+ // Plausibility check:
+ off_t FileSizeSrc = FileSize(FileNameSrc);
+ off_t FileSizeDst = FileSize(FileNameDst);
+ if (FileSizeSrc != FileSizeDst) {
+ esyslog("ERROR: file size discrepancy: %lld != %lld", FileSizeSrc, FileSizeDst);
+ break;
+ }
+ }
+ else {
+ esyslog("ERROR: can't read from source file '%s': %m", *FileNameSrc);
+ break;
+ }
+ }
+ else if ((e = d.Next()) != NULL) {
+ // We're switching to the next directory entry:
+ FileNameSrc = AddDirectory(dirNameSrc, e->d_name);
+ FileNameDst = AddDirectory(dirNameDst, e->d_name);
+ struct stat st;
+ if (stat(FileNameSrc, &st) < 0) {
+ esyslog("ERROR: can't access source file '%s': %m", *FileNameSrc);
+ break;
+ }
+ if (!(S_ISREG(st.st_mode) || S_ISLNK(st.st_mode))) {
+ esyslog("ERROR: source file '%s' is neither a regular file nor a symbolic link", *FileNameSrc);
+ break;
+ }
+ dsyslog("copying file '%s' to '%s'", *FileNameSrc, *FileNameDst);
+ BufferSize = max(size_t(st.st_blksize * 10), size_t(BUFSIZ));
+ if (access(FileNameDst, F_OK) == 0) {
+ esyslog("ERROR: destination file '%s' already exists", *FileNameDst);
+ break;
+ }
+ if ((From = open(FileNameSrc, O_RDONLY)) < 0) {
+ esyslog("ERROR: can't open source file '%s': %m", *FileNameSrc);
+ break;
+ }
+ if ((To = open(FileNameDst, O_WRONLY | O_CREAT | O_EXCL, DEFFILEMODE)) < 0) {
+ esyslog("ERROR: can't open destination file '%s': %m", *FileNameDst);
+ close(From);
+ break;
+ }
+ }
+ else {
+ // We're done:
+ dsyslog("done copying directory '%s' to '%s'", *dirNameSrc, *dirNameDst);
+ return;
+ }
+ }
+ close(From); // just to be absolutely sure
+ close(To);
+ esyslog("ERROR: copying directory '%s' to '%s' ended prematurely", *dirNameSrc, *dirNameDst);
+ }
+ else
+ esyslog("ERROR: can't open '%s'", *dirNameSrc);
+ }
+ else
+ esyslog("ERROR: can't access '%s'", *dirNameDst);
+ error = true;
+}
+
+void cDirCopier::Stop(void)
+{
+ Cancel(3);
+ if (error) {
+ cVideoDirectory::RemoveVideoFile(dirNameDst);
+ Recordings.DelByName(dirNameDst);
+ }
+}
+
+// --- cRecordingsHandlerEntry -----------------------------------------------
+
+class cRecordingsHandlerEntry : public cListObject {
+private:
+ int usage;
+ cString fileNameSrc;
+ cString fileNameDst;
+ cCutter *cutter;
+ cDirCopier *copier;
+ void ClearPending(void) { usage &= ~ruPending; }
+public:
+ cRecordingsHandlerEntry(int Usage, const char *FileNameSrc, const char *FileNameDst);
+ ~cRecordingsHandlerEntry();
+ int Usage(const char *FileName = NULL) const;
+ const char *FileNameSrc(void) const { return fileNameSrc; }
+ const char *FileNameDst(void) const { return fileNameDst; }
+ bool Active(bool &Error);
+ };
+
+cRecordingsHandlerEntry::cRecordingsHandlerEntry(int Usage, const char *FileNameSrc, const char *FileNameDst)
+{
+ usage = Usage;
+ fileNameSrc = FileNameSrc;
+ fileNameDst = FileNameDst;
+ cutter = NULL;
+ copier = NULL;
+}
+
+cRecordingsHandlerEntry::~cRecordingsHandlerEntry()
+{
+ delete cutter;
+ delete copier;
+}
+
+int cRecordingsHandlerEntry::Usage(const char *FileName) const
+{
+ int u = usage;
+ if (FileName && *FileName) {
+ if (strcmp(FileName, fileNameSrc) == 0)
+ u |= ruSrc;
+ else if (strcmp(FileName, fileNameDst) == 0)
+ u |= ruDst;
+ }
+ return u;
+}
+
+bool cRecordingsHandlerEntry::Active(bool &Error)
+{
+ bool CopierFinishedOk = false;
+ // First test whether there is an ongoing operation:
+ if (cutter) {
+ if (cutter->Active())
+ return true;
+ Error |= cutter->Error();
+ delete cutter;
+ cutter = NULL;
+ }
+ else if (copier) {
+ if (copier->Active())
+ return true;
+ Error |= copier->Error();
+ CopierFinishedOk = !copier->Error();
+ delete copier;
+ copier = NULL;
+ }
+ // Now check if there is something to start:
+ if ((Usage() & ruPending) != 0) {
+ if ((Usage() & ruCut) != 0) {
+ cutter = new cCutter(FileNameSrc());
+ cutter->Start();
+ }
+ else if ((Usage() & (ruMove | ruCopy)) != 0) {
+ copier = new cDirCopier(FileNameSrc(), FileNameDst());
+ copier->Start();
+ }
+ ClearPending();
+ return true;
+ }
+ else {
+ if (CopierFinishedOk && (Usage() & ruMove) != 0) {
+ cRecording Recording(FileNameSrc());
+ Recording.Delete();
+ Recordings.ChangeState();
+ Recordings.TouchUpdate();
+ }
+ }
+ return false;
+}
+
+// --- cRecordingsHandler ----------------------------------------------------
+
+cRecordingsHandler RecordingsHandler;
+
+cRecordingsHandler::cRecordingsHandler(void)
+{
+ finished = true;
+ error = false;
+}
+
+cRecordingsHandler::~cRecordingsHandler()
+{
+}
+
+cRecordingsHandlerEntry *cRecordingsHandler::Get(const char *FileName)
+{
+ if (FileName && *FileName) {
+ for (cRecordingsHandlerEntry *r = operations.First(); r; r = operations.Next(r)) {
+ if (strcmp(FileName, r->FileNameSrc()) == 0 || strcmp(FileName, r->FileNameDst()) == 0)
+ return r;
+ }
+ }
+ return NULL;
+}
+
+bool cRecordingsHandler::Add(int Usage, const char *FileNameSrc, const char *FileNameDst)
+{
+ dsyslog("recordings handler add %d '%s' '%s'", Usage, FileNameSrc, FileNameDst);
+ cMutexLock MutexLock(&mutex);
+ if (Usage == ruCut || Usage == ruMove || Usage == ruCopy) {
+ if (FileNameSrc && *FileNameSrc) {
+ if (Usage == ruCut || FileNameDst && *FileNameDst) {
+ cString fnd;
+ if (Usage == ruCut && !FileNameDst)
+ FileNameDst = fnd = cCutter::EditedFileName(FileNameSrc);
+ if (!Get(FileNameSrc) && !Get(FileNameDst)) {
+ Usage |= ruPending;
+ operations.Add(new cRecordingsHandlerEntry(Usage, FileNameSrc, FileNameDst));
+ finished = false;
+ Active(); // start it right away if possible
+ return true;
+ }
+ else
+ esyslog("ERROR: file name already present in recordings handler add %d '%s' '%s'", Usage, FileNameSrc, FileNameDst);
+ }
+ else
+ esyslog("ERROR: missing dst file name in recordings handler add %d '%s' '%s'", Usage, FileNameSrc, FileNameDst);
+ }
+ else
+ esyslog("ERROR: missing src file name in recordings handler add %d '%s' '%s'", Usage, FileNameSrc, FileNameDst);
+ }
+ else
+ esyslog("ERROR: invalid usage in recordings handler add %d '%s' '%s'", Usage, FileNameSrc, FileNameDst);
+ return false;
+}
+
+void cRecordingsHandler::Del(const char *FileName)
+{
+ cMutexLock MutexLock(&mutex);
+ if (cRecordingsHandlerEntry *r = Get(FileName))
+ operations.Del(r);
+}
+
+void cRecordingsHandler::DelAll(void)
+{
+ cMutexLock MutexLock(&mutex);
+ operations.Clear();
+}
+
+int cRecordingsHandler::GetUsage(const char *FileName)
+{
+ cMutexLock MutexLock(&mutex);
+ if (cRecordingsHandlerEntry *r = Get(FileName))
+ return r->Usage(FileName);
+ return ruNone;
+}
+
+bool cRecordingsHandler::Active(void)
+{
+ cMutexLock MutexLock(&mutex);
+ while (cRecordingsHandlerEntry *r = operations.First()) {
+ if (r->Active(error))
+ return true;
+ else
+ operations.Del(r);
+ }
+ return false;
+}
+
+bool cRecordingsHandler::Finished(bool &Error)
+{
+ cMutexLock MutexLock(&mutex);
+ if (!finished && operations.Count() == 0) {
+ finished = true;
+ Error = error;
+ error = false;
+ return true;
+ }
+ return false;
+}
+
// --- cMark -----------------------------------------------------------------
double MarkFramesPerSecond = DEFAULTFRAMESPERSECOND;
@@ -1485,6 +1986,11 @@ bool cMark::Save(FILE *f)
// --- cMarks ----------------------------------------------------------------
+cString cMarks::MarksFileName(const cRecording *Recording)
+{
+ return AddDirectory(Recording->FileName(), Recording->IsPesRecording() ? MARKSFILESUFFIX ".vdr" : MARKSFILESUFFIX);
+}
+
bool cMarks::Load(const char *RecordingFileName, double FramesPerSecond, bool IsPesRecording)
{
recordingFileName = RecordingFileName;
diff --git a/recording.h b/recording.h
index ff3119da..3b00c71b 100644
--- a/recording.h
+++ b/recording.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: recording.h 2.46 2013/03/04 14:01:23 kls Exp $
+ * $Id: recording.h 3.1 2013/10/10 12:08:15 kls Exp $
*/
#ifndef __RECORDING_H
@@ -25,6 +25,21 @@ extern int DirectoryNameMax;
extern bool DirectoryEncoding;
extern int InstanceId;
+enum eRecordingUsage {
+ ruNone = 0x0000, // the recording is currently unused
+ ruTimer = 0x0001, // the recording is currently written to by a timer
+ ruReplay = 0x0002, // the recording is being replayed
+ // mutually exclusive:
+ ruCut = 0x0004, // the recording is being cut
+ ruMove = 0x0008, // the recording is being moved
+ ruCopy = 0x0010, // the recording is being copied
+ // mutually exclusive:
+ ruSrc = 0x0020, // the recording is the source of a cut, move or copy process
+ ruDst = 0x0040, // the recording is the destination of a cut, move or copy process
+ //
+ ruPending = 0x0080, // the recording is pending a cut, move or copy process
+ };
+
void RemoveDeletedRecordings(void);
void AssertFreeDiskSpace(int Priority = 0, bool Force = false);
///< The special Priority value -1 means that we shall get rid of any
@@ -73,6 +88,7 @@ public:
const char *Aux(void) const { return aux; }
double FramesPerSecond(void) const { return framesPerSecond; }
void SetFramesPerSecond(double FramesPerSecond);
+ void SetFileName(const char *FileName);
bool Write(FILE *f, const char *Prefix = "") const;
bool Read(void);
bool Write(void) const;
@@ -114,8 +130,21 @@ public:
int Lifetime(void) const { return lifetime; }
time_t Deleted(void) const { return deleted; }
virtual int Compare(const cListObject &ListObject) const;
+ bool IsInPath(const char *Path);
+ ///< Returns true if this recording is stored anywhere under the given Path.
+ ///< If Path is NULL or an empty string, the entire video directory is checked.
+ cString Folder(void) const;
+ ///< Returns the name of the folder this recording is stored in (without the
+ ///< video directory). For use in menus etc.
+ cString BaseName(void) const;
+ ///< Returns the base name of this recording (without the
+ ///< video directory and folder). For use in menus etc.
const char *Name(void) const { return name; }
+ ///< Returns the full name of the recording (without the video directory.
+ ///< For use in menus etc.
const char *FileName(void) const;
+ ///< Returns the full path name to the recording directory, including the
+ ///< video directory and the actual '*.rec'. For disk file access use.
const char *Title(char Delimiter = ' ', bool NewIndicator = false, int Level = -1) const;
const cRecordingInfo *Info(void) const { return info; }
const char *PrefixFileName(char Prefix);
@@ -134,8 +163,17 @@ public:
bool IsEdited(void) const;
bool IsPesRecording(void) const { return isPesRecording; }
bool IsOnVideoDirectoryFileSystem(void) const;
+ bool HasMarks(void);
+ ///< Returns true if this recording has any editing marks.
+ bool DeleteMarks(void);
+ ///< Deletes the editing marks from this recording (if any).
+ ///< Returns true if the operation was successful. If there is no marks file
+ ///< for this recording, it also returns true.
void ReadInfo(void);
- bool WriteInfo(void);
+ bool WriteInfo(const char *OtherFileName = NULL);
+ ///< Writes in info file of this recording. If OtherFileName is given, the info
+ ///< file will be written under that recording file name instead of this
+ ///< recording's file name.
void SetStartTime(time_t Start);
///< Sets the start time of this recording to the given value.
///< If a filename has already been set for this recording, it will be
@@ -144,6 +182,17 @@ public:
///< Use this function with care - it does not check whether a recording with
///< this new name already exists, and if there is one, results may be
///< unexpected!
+ bool ChangePriorityLifetime(int NewPriority, int NewLifetime);
+ ///< Changes the priority and lifetime of this recording to the given values.
+ ///< If the new values are the same as the old ones, nothing happens.
+ ///< Returns false in case of error.
+ bool ChangeName(const char *NewName);
+ ///< Changes the name of this recording to the given value. NewName is in the
+ ///< same format as the one returned by Name(), i.e. without the video directory
+ ///< and the actual '*.rec' part, and using FOLDERDELIMCHAR as the directory
+ ///< delimiter.
+ ///< If the new name is the same as the old one, nothing happens.
+ ///< Returns false in case of error.
bool Delete(void);
///< Changes the file name so that it will no longer be visible in the "Recordings" menu
///< Returns false in case of error
@@ -154,6 +203,14 @@ public:
///< Changes the file name so that it will be visible in the "Recordings" menu again and
///< not processed by cRemoveDeletedRecordingsThread.
///< Returns false in case of error
+ int IsInUse(void) const;
+ ///< Checks whether this recording is currently in use and therefore shall not
+ ///< be tampered with. Returns 0 (ruNone) if the recording is not in use.
+ ///< The return value may consist of several or'd eRecordingUsage flags. If the
+ ///< caller is just interested in whether the recording is in use or not, the
+ ///< return value can be used like a boolean value.
+ ///< A recording may be in use for several reasons (like being recorded and replayed,
+ ///< as in time-shift).
};
class cRecordings : public cList<cRecording>, public cThread {
@@ -197,11 +254,76 @@ public:
double MBperMinute(void);
///< Returns the average data rate (in MB/min) of all recordings, or -1 if
///< this value is unknown.
+ int PathIsInUse(const char *Path);
+ ///< Checks whether any recording in the given Path is currently in use and therefore
+ ///< the whole Path shall not be tampered with. Returns 0 (ruNone) if no recording
+ ///< is in use.
+ ///< See cRecording::IsInUse() for details about the possible non-zero return values.
+ ///< If several recordings in the Path are currently in use, the return value will
+ ///< be the combination of all individual recordings' flags.
+ ///< If Path is NULL or an empty string, the entire video directory is checked.
+ int GetNumRecordingsInPath(const char *Path);
+ ///< Returns the total number of recordings in the given Path, including all
+ ///< sub-folders of Path.
+ ///< If Path is NULL or an empty string, the entire video directory is checked.
+ bool MoveRecordings(const char *OldPath, const char *NewPath);
+ ///< Moves all recordings in OldPath to NewPath.
+ ///< Returns true if all recordings were successfully moved.
+ ///< As soon as the operation fails for one recording, the whole
+ ///< action is aborted and false will be returned. Any recordings that
+ ///< have been successfully moved thus far will keep their new name.
+ ///< If OldPath and NewPath are on different file systems, the recordings
+ ///< will be moved in a background process and this function returns true
+ ///< if all recordings have been successfully added to the RecordingsHandler.
};
extern cRecordings Recordings;
extern cRecordings DeletedRecordings;
+class cRecordingsHandlerEntry;
+
+class cRecordingsHandler {
+private:
+ cMutex mutex;
+ cList<cRecordingsHandlerEntry> operations;
+ bool finished;
+ bool error;
+ cRecordingsHandlerEntry *Get(const char *FileName);
+public:
+ cRecordingsHandler(void);
+ ~cRecordingsHandler();
+ bool Add(int Usage, const char *FileNameSrc, const char *FileNameDst = NULL);
+ ///< Adds the given FileNameSrc to the recordings handler for (later)
+ ///< processing. Usage can be either ruCut, ruMove or ruCopy. FileNameDst
+ ///< is only applicable for ruMove and ruCopy.
+ ///< At any given time there can be only one operation for any FileNameSrc
+ ///< or FileNameDst in the list. An attempt to add a file name twice will
+ ///< result in an error.
+ ///< Returns true if the operation was successfully added to the list.
+ void Del(const char *FileName);
+ ///< Deletes the given FileName from the list of operations.
+ ///< If an action is already in progress, it will be terminated.
+ ///< FileName can be either the FileNameSrc or FileNameDst (if applicable)
+ ///< that was given when the operation was added with Add().
+ void DelAll(void);
+ ///< Deletes/terminates all operations.
+ int GetUsage(const char *FileName);
+ ///< Returns the usage type for the given FileName.
+ bool Active(void);
+ ///< Checks whether there is currently any operation running and starts
+ ///> the next one form the list if the previous one has finished.
+ ///< This function must be called regularly to trigger switching to the
+ ///< next operation in the list.
+ ///< Returns true if there are any operations in the list.
+ bool Finished(bool &Error);
+ ///< Returns true if all operations in the list have been finished.
+ ///< If there have been any errors, Errors will be set to true.
+ ///< This function will only return true once if the list of operations
+ ///< has actually become empty since the last call.
+ };
+
+extern cRecordingsHandler RecordingsHandler;
+
#define DEFAULTFRAMESPERSECOND 25.0
class cMark : public cListObject {
@@ -232,6 +354,9 @@ private:
time_t lastFileTime;
time_t lastChange;
public:
+ static cString MarksFileName(const cRecording *Recording);
+ ///< Returns the marks file name for the given Recording (regardless whether such
+ ///< a file actually exists).
bool Load(const char *RecordingFileName, double FramesPerSecond = DEFAULTFRAMESPERSECOND, bool IsPesRecording = false);
bool Update(void);
bool Save(void);
diff --git a/shutdown.c b/shutdown.c
index 445ed6f2..97d056e9 100644
--- a/shutdown.c
+++ b/shutdown.c
@@ -6,7 +6,7 @@
*
* Original version written by Udo Richter <udo_richter@gmx.de>.
*
- * $Id: shutdown.c 2.1 2013/02/18 10:33:26 kls Exp $
+ * $Id: shutdown.c 3.1 2013/10/02 09:02:01 kls Exp $
*/
#include "shutdown.h"
@@ -16,11 +16,11 @@
#include <sys/wait.h>
#include "channels.h"
#include "config.h"
-#include "cutter.h"
#include "i18n.h"
#include "interface.h"
#include "menu.h"
#include "plugin.h"
+#include "recording.h"
#include "timers.h"
#include "tools.h"
@@ -167,7 +167,7 @@ bool cShutdownHandler::ConfirmShutdown(bool Interactive)
Skins.Message(mtError, tr("Can't shutdown - option '-s' not given!"));
return false;
}
- if (cCutter::Active()) {
+ if (RecordingsHandler.Active()) {
if (!Interactive || !Interface->Confirm(tr("Editing - shut down anyway?")))
return false;
}
@@ -210,7 +210,7 @@ bool cShutdownHandler::ConfirmShutdown(bool Interactive)
bool cShutdownHandler::ConfirmRestart(bool Interactive)
{
- if (cCutter::Active()) {
+ if (RecordingsHandler.Active()) {
if (!Interactive || !Interface->Confirm(tr("Editing - restart anyway?")))
return false;
}
diff --git a/svdrp.c b/svdrp.c
index ef1296d9..1d2593a2 100644
--- a/svdrp.c
+++ b/svdrp.c
@@ -10,7 +10,7 @@
* and interact with the Video Disk Recorder - or write a full featured
* graphical interface that sits on top of an SVDRP connection.
*
- * $Id: svdrp.c 3.1 2013/09/10 13:21:38 kls Exp $
+ * $Id: svdrp.c 3.2 2013/10/10 12:18:12 kls Exp $
*/
#include "svdrp.h"
@@ -28,7 +28,6 @@
#include <unistd.h>
#include "channels.h"
#include "config.h"
-#include "cutter.h"
#include "device.h"
#include "eitscan.h"
#include "keys.h"
@@ -305,6 +304,11 @@ const char *HelpPages[] = {
"REMO [ on | off ]\n"
" Turns the remote control on or off. Without a parameter, the current\n"
" status of the remote control is reported.",
+ "RENR <number> <new name>\n"
+ " Rename the recording with the given number. Before a recording can be\n"
+ " renamed, an LSTR command must have been executed in order to retrieve\n"
+ " the recording numbers. The numbers don't change during subsequent RENR\n"
+ " commands.n",
"SCAN\n"
" Forces an EPG scan. If this is a single DVB device system, the scan\n"
" will be done on the primary device unless it is currently recording.",
@@ -659,27 +663,38 @@ void cSVDRP::CmdDELC(const char *Option)
Reply(501, "Missing channel number");
}
+static cString RecordingInUseMessage(int Reason, const char *RecordingId, cRecording *Recording)
+{
+ cRecordControl *rc;
+ if ((Reason & ruTimer) != 0 && (rc = cRecordControls::GetRecordControl(Recording->FileName())) != NULL)
+ return cString::sprintf("Recording \"%s\" is in use by timer %d", RecordingId, rc->Timer()->Index() + 1);
+ else if ((Reason & ruReplay) != 0)
+ return cString::sprintf("Recording \"%s\" is being replayed", RecordingId);
+ else if ((Reason & ruCut) != 0)
+ return cString::sprintf("Recording \"%s\" is being edited", RecordingId);
+ else if ((Reason & (ruMove | ruCopy)) != 0)
+ return cString::sprintf("Recording \"%s\" is being copied/moved", RecordingId);
+ else if (Reason)
+ return cString::sprintf("Recording \"%s\" is in use", RecordingId);
+ return NULL;
+}
+
void cSVDRP::CmdDELR(const char *Option)
{
if (*Option) {
if (isnumber(Option)) {
cRecording *recording = recordings.Get(strtol(Option, NULL, 10) - 1);
if (recording) {
- cRecordControl *rc = cRecordControls::GetRecordControl(recording->FileName());
- if (!rc) {
- if (!cCutter::Active(recording->FileName())) {
- if (recording->Delete()) {
- Reply(250, "Recording \"%s\" deleted", Option);
- Recordings.DelByName(recording->FileName());
- }
- else
- Reply(554, "Error while deleting recording!");
+ if (int RecordingInUse = recording->IsInUse())
+ Reply(550, RecordingInUseMessage(RecordingInUse, Option, recording));
+ else {
+ if (recording->Delete()) {
+ Reply(250, "Recording \"%s\" deleted", Option);
+ Recordings.DelByName(recording->FileName());
}
else
- Reply(550, "Recording \"%s\" is being edited", Option);
+ Reply(554, "Error while deleting recording!");
}
- else
- Reply(550, "Recording \"%s\" is in use by timer %d", Option, rc->Timer()->Index() + 1);
}
else
Reply(550, "Recording \"%s\" not found%s", Option, recordings.Count() ? "" : " (use LSTR before deleting)");
@@ -728,14 +743,10 @@ void cSVDRP::CmdEDIT(const char *Option)
if (recording) {
cMarks Marks;
if (Marks.Load(recording->FileName(), recording->FramesPerSecond(), recording->IsPesRecording()) && Marks.Count()) {
- if (!cCutter::Active()) {
- if (cCutter::Start(recording->FileName()))
- Reply(250, "Editing recording \"%s\" [%s]", Option, recording->Title());
- else
- Reply(554, "Can't start editing process");
- }
+ if (RecordingsHandler.Add(ruCut, recording->FileName()))
+ Reply(250, "Editing recording \"%s\" [%s]", Option, recording->Title());
else
- Reply(554, "Editing process already active");
+ Reply(554, "Can't start editing process");
}
else
Reply(554, "No editing marks defined");
@@ -1539,6 +1550,46 @@ void cSVDRP::CmdREMO(const char *Option)
Reply(250, "Remote control is %s", cRemote::Enabled() ? "enabled" : "disabled");
}
+void cSVDRP::CmdRENR(const char *Option)
+{
+ if (*Option) {
+ char *opt = strdup(Option);
+ char *num = skipspace(opt);
+ char *option = num;
+ while (*option && !isspace(*option))
+ option++;
+ char c = *option;
+ *option = 0;
+ if (isnumber(num)) {
+ cRecording *recording = recordings.Get(strtol(num, NULL, 10) - 1);
+ if (recording) {
+ if (int RecordingInUse = recording->IsInUse())
+ Reply(550, RecordingInUseMessage(RecordingInUse, Option, recording));
+ else {
+ if (c)
+ option = skipspace(++option);
+ if (*option) {
+ cString oldName = recording->Name();
+ if (recording->ChangeName(option))
+ Reply(250, "Recording \"%s\" renamed to \"%s\"", *oldName, recording->Name());
+ else
+ Reply(554, "Error while renaming recording \"%s\" to \"%s\"!", *oldName, option);
+ }
+ else
+ Reply(501, "Missing new recording name");
+ }
+ }
+ else
+ Reply(550, "Recording \"%s\" not found%s", num, recordings.Count() ? "" : " (use LSTR before renaming)");
+ }
+ else
+ Reply(501, "Error in recording number \"%s\"", num);
+ free(opt);
+ }
+ else
+ Reply(501, "Missing recording number");
+}
+
void cSVDRP::CmdSCAN(const char *Option)
{
EITScanner.ForceScan();
@@ -1666,6 +1717,7 @@ void cSVDRP::Execute(char *Cmd)
else if (CMD("PLUG")) CmdPLUG(s);
else if (CMD("PUTE")) CmdPUTE(s);
else if (CMD("REMO")) CmdREMO(s);
+ else if (CMD("RENR")) CmdRENR(s);
else if (CMD("SCAN")) CmdSCAN(s);
else if (CMD("STAT")) CmdSTAT(s);
else if (CMD("UPDR")) CmdUPDR(s);
diff --git a/svdrp.h b/svdrp.h
index 5ec9bc76..96247e52 100644
--- a/svdrp.h
+++ b/svdrp.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: svdrp.h 2.3 2012/04/26 10:30:06 kls Exp $
+ * $Id: svdrp.h 3.1 2013/09/14 13:24:50 kls Exp $
*/
#ifndef __SVDRP_H
@@ -78,6 +78,7 @@ private:
void CmdPLUG(const char *Option);
void CmdPUTE(const char *Option);
void CmdREMO(const char *Option);
+ void CmdRENR(const char *Option);
void CmdSCAN(const char *Option);
void CmdSTAT(const char *Option);
void CmdUPDT(const char *Option);
diff --git a/tools.c b/tools.c
index f690fb8a..a2055ec8 100644
--- a/tools.c
+++ b/tools.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: tools.c 3.1 2013/05/23 10:10:00 kls Exp $
+ * $Id: tools.c 3.2 2013/09/22 13:19:19 kls Exp $
*/
#include "tools.h"
@@ -173,6 +173,31 @@ char *strreplace(char *s, const char *s1, const char *s2)
return s;
}
+const char *strchrn(const char *s, char c, size_t n)
+{
+ if (n == 0)
+ return s;
+ if (s) {
+ for ( ; *s; s++) {
+ if (*s == c && --n == 0)
+ return s;
+ }
+ }
+ return NULL;
+}
+
+int strcountchr(const char *s, char c)
+{
+ int n = 0;
+ if (s && c) {
+ for ( ; *s; s++) {
+ if (*s == c)
+ n++;
+ }
+ }
+ return n;
+}
+
char *stripspace(char *s)
{
if (s && *s) {
@@ -202,6 +227,30 @@ char *compactspace(char *s)
return s;
}
+char *compactchars(char *s, char c)
+{
+ if (s && *s && c) {
+ char *t = s;
+ char *p = s;
+ int n = 0;
+ while (*p) {
+ if (*p != c) {
+ *t++ = *p;
+ n = 0;
+ }
+ else if (t != s && n == 0) {
+ *t++ = *p;
+ n++;
+ }
+ p++;
+ }
+ if (n)
+ t--; // the last character was c
+ *t = 0;
+ }
+ return s;
+}
+
cString strescape(const char *s, const char *chars)
{
char *buffer;
@@ -970,6 +1019,20 @@ cString::cString(const char *S, bool TakePointer)
s = TakePointer ? (char *)S : S ? strdup(S) : NULL;
}
+cString::cString(const char *S, const char *To)
+{
+ if (!S)
+ s = NULL;
+ else if (!To)
+ s = strdup(S);
+ else {
+ int l = To - S;
+ s = MALLOC(char, l + 1);
+ strncpy(s, S, l);
+ s[l] = 0;
+ }
+}
+
cString::cString(const cString &String)
{
s = String.s ? strdup(String.s) : NULL;
@@ -1008,6 +1071,12 @@ cString &cString::Truncate(int Index)
return *this;
}
+cString &cString::CompactChars(char c)
+{
+ compactchars(s, c);
+ return *this;
+}
+
cString cString::sprintf(const char *fmt, ...)
{
va_list ap;
diff --git a/tools.h b/tools.h
index 9cfd152b..358f75e3 100644
--- a/tools.h
+++ b/tools.h
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: tools.h 3.2 2013/08/23 10:32:51 kls Exp $
+ * $Id: tools.h 3.3 2013/09/22 13:30:14 kls Exp $
*/
#ifndef __TOOLS_H
@@ -170,6 +170,7 @@ private:
char *s;
public:
cString(const char *S = NULL, bool TakePointer = false);
+ cString(const char *S, const char *To); ///< Copies S up to To (exclusive). To must be a valid pointer into S. If To is NULL, everything is copied.
cString(const cString &String);
virtual ~cString();
operator const void * () const { return s; } // to catch cases where operator*() should be used
@@ -178,6 +179,7 @@ public:
cString &operator=(const cString &String);
cString &operator=(const char *String);
cString &Truncate(int Index); ///< Truncate the string at the given Index (if Index is < 0 it is counted from the end of the string).
+ cString &CompactChars(char c); ///< Compact any sequence of characters 'c' to a single character, and strip all of them from the beginning and end of this string.
static cString sprintf(const char *fmt, ...) __attribute__ ((format (printf, 1, 2)));
static cString vsprintf(const char *fmt, va_list &ap);
};
@@ -193,6 +195,8 @@ char *strcpyrealloc(char *dest, const char *src);
char *strn0cpy(char *dest, const char *src, size_t n);
char *strreplace(char *s, char c1, char c2);
char *strreplace(char *s, const char *s1, const char *s2); ///< re-allocates 's' and deletes the original string if necessary!
+const char *strchrn(const char *s, char c, size_t n); ///< returns a pointer to the n'th occurrence (counting from 1) of c in s, or NULL if no such character was found. If n is 0, s is returned.
+int strcountchr(const char *s, char c); ///< returns the number of occurrences of 'c' in 's'.
inline char *skipspace(const char *s)
{
if ((uchar)*s > ' ') // most strings don't have any leading space, so handle this case as fast as possible
@@ -203,6 +207,7 @@ inline char *skipspace(const char *s)
}
char *stripspace(char *s);
char *compactspace(char *s);
+char *compactchars(char *s, char c); ///< removes all occurrences of 'c' from the beginning an end of 's' and replaces sequences of multiple 'c's with a single 'c'.
cString strescape(const char *s, const char *chars);
bool startswith(const char *s, const char *p);
bool endswith(const char *s, const char *p);
diff --git a/vdr.c b/vdr.c
index 3fc44d35..9769b0f2 100644
--- a/vdr.c
+++ b/vdr.c
@@ -22,7 +22,7 @@
*
* The project's page is at http://www.tvdr.de
*
- * $Id: vdr.c 3.2 2013/09/10 13:58:34 kls Exp $
+ * $Id: vdr.c 3.3 2013/10/10 12:25:03 kls Exp $
*/
#include <getopt.h>
@@ -1320,8 +1320,9 @@ int main(int argc, char *argv[])
if (!Menu) {
if (!InhibitEpgScan)
EITScanner.Process();
- if (!cCutter::Active() && cCutter::Ended()) {
- if (cCutter::Error())
+ bool Error = false;
+ if (RecordingsHandler.Finished(Error)) {
+ if (Error)
Skins.Message(mtError, tr("Editing process failed!"));
else
Skins.Message(mtInfo, tr("Editing process finished"));
@@ -1341,7 +1342,10 @@ int main(int argc, char *argv[])
ShutdownHandler.countdown.Cancel();
}
- if ((Now - LastInteract) > ACTIVITYTIMEOUT && !cRecordControls::Active() && !cCutter::Active() && !Interface->HasSVDRPConnection() && (Now - cRemote::LastActivity()) > ACTIVITYTIMEOUT) {
+ // Keep the recordings handler alive:
+ RecordingsHandler.Active();
+
+ if ((Now - LastInteract) > ACTIVITYTIMEOUT && !cRecordControls::Active() && !RecordingsHandler.Active() && !Interface->HasSVDRPConnection() && (Now - cRemote::LastActivity()) > ACTIVITYTIMEOUT) {
// Handle housekeeping tasks
// Shutdown:
@@ -1390,7 +1394,7 @@ Exit:
PluginManager.StopPlugins();
cRecordControls::Shutdown();
- cCutter::Stop();
+ RecordingsHandler.DelAll();
delete Menu;
cControl::Shutdown();
delete Interface;
diff --git a/videodir.c b/videodir.c
index cd739ea1..1885a1a7 100644
--- a/videodir.c
+++ b/videodir.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: videodir.c 3.2 2013/09/11 12:20:37 kls Exp $
+ * $Id: videodir.c 3.3 2013/10/08 13:26:41 kls Exp $
*/
#include "videodir.h"
@@ -79,6 +79,7 @@ bool cVideoDirectory::Register(const char *FileName)
bool cVideoDirectory::Rename(const char *OldName, const char *NewName)
{
+ dsyslog("renaming '%s' to '%s'", OldName, NewName);
if (rename(OldName, NewName) == -1) {
LOG_ERROR_STR(NewName);
return false;
@@ -88,10 +89,15 @@ bool cVideoDirectory::Rename(const char *OldName, const char *NewName)
bool cVideoDirectory::Move(const char *FromName, const char *ToName)
{
- if (rename(FromName, ToName) == -1) {
- LOG_ERROR_STR(ToName);
- return false;
+ dsyslog("moving '%s' to '%s'", FromName, ToName);
+ if (EntriesOnSameFileSystem(FromName, ToName)) {
+ if (rename(FromName, ToName) == -1) {
+ LOG_ERROR_STR(ToName);
+ return false;
+ }
}
+ else
+ return RecordingsHandler.Add(ruMove, FromName, ToName);
return true;
}