mirror of
https://github.com/VDR4Arch/vdr.git
synced 2023-10-10 13:36:52 +02:00
Implemented "Pattern Timers"
This commit is contained in:
parent
d2e0087c4e
commit
2b3556b460
6
HISTORY
6
HISTORY
@ -9562,3 +9562,9 @@ Video Disk Recorder Revision History
|
|||||||
- Fixed a compiler warning (thanks to Winfried Köhler).
|
- Fixed a compiler warning (thanks to Winfried Köhler).
|
||||||
- Fixed convertCharacterTable() in case iconv_open() fails (thanks to Helmut Binder).
|
- Fixed convertCharacterTable() in case iconv_open() fails (thanks to Helmut Binder).
|
||||||
- Official release.
|
- Official release.
|
||||||
|
|
||||||
|
2020-12-26: Version 2.5.1
|
||||||
|
|
||||||
|
- Implemented "Pattern Timers" (see MANUAL, vdr.1 and vdr.5 for details).
|
||||||
|
- Events in the past are no longer marked as having a timer in the Schedules
|
||||||
|
menu.
|
||||||
|
125
MANUAL
125
MANUAL
@ -480,6 +480,8 @@ Version 2.4
|
|||||||
"forever", and a value of 0 means that this recording can be
|
"forever", and a value of 0 means that this recording can be
|
||||||
deleted any time if a recording with a higher priority needs disk
|
deleted any time if a recording with a higher priority needs disk
|
||||||
space.
|
space.
|
||||||
|
Pattern: The pattern to use for recordings matching events (only available
|
||||||
|
for pattern timers). See section "Pattern timers" below.
|
||||||
File: The name under which a recording created through this timer will
|
File: The name under which a recording created through this timer will
|
||||||
be stored on disk (the actual name will also contain the date and
|
be stored on disk (the actual name will also contain the date and
|
||||||
time, so it is possible to have a "repeating timer" store all its
|
time, so it is possible to have a "repeating timer" store all its
|
||||||
@ -511,6 +513,129 @@ Version 2.4
|
|||||||
The "Red" key in the "Edit timer" menu opens a list of folders, which can be
|
The "Red" key in the "Edit timer" menu opens a list of folders, which can be
|
||||||
used to define the file name in which the recording will be stored.
|
used to define the file name in which the recording will be stored.
|
||||||
|
|
||||||
|
The "Yellow" key in the "Edit timer" menu toggles the timer between "Pattern"
|
||||||
|
and "Regular".
|
||||||
|
|
||||||
|
When editing the "File" field, the "Blue" key in can be used to insert useful
|
||||||
|
macros.
|
||||||
|
|
||||||
|
* Pattern timers
|
||||||
|
|
||||||
|
There are cases where it would make sense to have a more flexible kind of
|
||||||
|
recording timer. For instance, some channels that provide VPS don't always
|
||||||
|
use the exact same VPS time for a series, which is extremely annoying.
|
||||||
|
Or you might want to record all films that have a certain pattern in their
|
||||||
|
title, no matter when they are broadcast. In such cases, "pattern timers"
|
||||||
|
can help.
|
||||||
|
|
||||||
|
In the "Edit timer" menu press the Yellow button to turn a regular timer into
|
||||||
|
a pattern timer. Pressing this button again switches back to regular.
|
||||||
|
|
||||||
|
The following rules apply to pattern timers:
|
||||||
|
|
||||||
|
- Pattern timers can only work for channels that provide EPG data.
|
||||||
|
- When using pattern timers, there should always be at least one free device that
|
||||||
|
can be used to regularly receive the EPG of the pattern timer's channel.
|
||||||
|
- A pattern timer records every matching event on the given channel that overlaps
|
||||||
|
with the given start/stop time. Overlapping events are recorded in full,
|
||||||
|
even if they extend outside the given start/stop interval.
|
||||||
|
- In order to actually record an event, a pattern timer "spawns" a separate timer
|
||||||
|
that does the recording. At most two timers are spawned from a pattern timer at
|
||||||
|
any given time, one for the next upcoming matching event, and one for
|
||||||
|
the event immediately following that one, in case it also matches.
|
||||||
|
- Spawned timers are marked with the flag tfSpawned.
|
||||||
|
- Spawned timers take the Priority, Lifetime and VPS settings from the pattern timer.
|
||||||
|
- The special pattern "*" matches every event. So a timer with
|
||||||
|
a start/stop time of 00:00/23:59 will record every event of that day
|
||||||
|
into separate recordings. Note that when using this pattern there should
|
||||||
|
be no other timers for the same channel, because these might interfere.
|
||||||
|
- Once a timer has been spawned, it is treated like any other regular
|
||||||
|
timer. Any changes made to the corresponding pattern timer thereafter will have
|
||||||
|
no effect on spawned timers. Note that after deleting a spawned timer,
|
||||||
|
the corresponding pattern timer may respawn it.
|
||||||
|
- Recording is done according to the event's begin/end times, either
|
||||||
|
by adding the start/stop margins (for non-VPS timers) or by using the
|
||||||
|
event's running status (for VPS timers).
|
||||||
|
- The recording of a pattern timer is stored under the given file name, just like
|
||||||
|
regular timers do. In addition to the "TITLE" and "EPISODE" macros the file
|
||||||
|
name of a pattern timer can also use "{<}" and "{>}" to reference the part of the
|
||||||
|
event's title before and after the pattern, respectively. For instance,
|
||||||
|
if the event's title is "Abc def ghi" and the pattern is "def ", "{<}"
|
||||||
|
would contain "Abc " and "{>}" would contain "ghi" (note the matching of the
|
||||||
|
blanks). For completeness, "{=}" can be used to reference the matching
|
||||||
|
pattern itself.
|
||||||
|
- In the "Timers" menu pressing the Red button on a pattern timer only toggles the
|
||||||
|
timer between "on" and "off", even if this is a repeating timer.
|
||||||
|
- In the "Timers" menu pattern timers are sorted alphabetically to the end of the
|
||||||
|
list of timers.
|
||||||
|
- A regular timer that is currently recording can't be changed into a pattern timer.
|
||||||
|
- In the "Edit timer" menu the file name and pattern are displayed as
|
||||||
|
separate items. The Yellow button can be used to toggle between a regular
|
||||||
|
timer and a pattern timer. When going from regular to pattern, the Pattern item will
|
||||||
|
be initialized with the base part of the file name.
|
||||||
|
- The characters '^' and '$' can be used at the very beginning and end of
|
||||||
|
the pattern to anchor the pattern to the begin or end of the title.
|
||||||
|
Using both of these will match only titles that consist of exactly the given pattern,
|
||||||
|
with nothing before and nothing after it.
|
||||||
|
- The Pattern field in the "Edit timer" menu allows blanks at the end of the string,
|
||||||
|
which may help to separate the text after the matching pattern.
|
||||||
|
- If the first character of the pattern is '@', an event that matches the
|
||||||
|
rest of the pattern is only recorded if the resulting recording's file
|
||||||
|
name (without any folders) is not contained in the donerecs.data file.
|
||||||
|
This avoids duplicate recordings of the same programme. Timers spawned from
|
||||||
|
such a pattern timer are marked with the flag tfAvoid.
|
||||||
|
- When editing the "File" field of a timer, the Blue button can be pressed to
|
||||||
|
insert one of the macros "TITLE", "EPISODE", "{<}", "{=}" or "{>}",
|
||||||
|
respectively. Pressing the Blue button repeatedly loops through the available
|
||||||
|
macros. The "{...}" macros are only available for pattern timers.
|
||||||
|
- In the "Schedule" and "What's on...?" menus the events that will be recorded
|
||||||
|
by a pattern timer are marked in the same way as regular timers.
|
||||||
|
- The TIMERS column in the LCARS skin doesn't show the basic definitions of
|
||||||
|
pattern timers, it only shows timers actually spawned from pattern timers.
|
||||||
|
|
||||||
|
If the pattern is prepended with '@', the name of the resulting recording (everything
|
||||||
|
after the rightmost '~', or the entire file name, if there is no '~') will be stored
|
||||||
|
in the file donerecs.data, so that multiple recordings of the same programme can be
|
||||||
|
avoided. When using this feature, special care must be taken regarding the recording's
|
||||||
|
file name. For instance, with a combination of
|
||||||
|
|
||||||
|
pattern file name
|
||||||
|
@Columbo Movies~TITLE
|
||||||
|
|
||||||
|
if the event's title is just "Columbo", this pattern timer would only record once,
|
||||||
|
and ignore any future events with that title, even if the episode would be different.
|
||||||
|
So you may want to use the episode name, as in
|
||||||
|
|
||||||
|
pattern file name
|
||||||
|
@Columbo Movies~TITLE - EPISODE
|
||||||
|
|
||||||
|
to make the file name unique. If you have several pattern timers for the same show on
|
||||||
|
different channels, chances are that the broadcasters handle title and episode
|
||||||
|
differently, as for example in
|
||||||
|
|
||||||
|
TITLE EPISODE pattern file name
|
||||||
|
Columbo Blueprint for Murder @^Columbo$ TITLE - EPISODE
|
||||||
|
Columbo - Blueprint for Murder @^Columbo TITLE
|
||||||
|
Columbo: Blueprint for Murder @^Columbo:_ Columbo - {>}
|
||||||
|
|
||||||
|
(note the '_' in the pattern of the third example; this is just used to visualize
|
||||||
|
the blank at the end of the pattern)
|
||||||
|
|
||||||
|
In order to have the same episode result in the same recording file name on all
|
||||||
|
channels, the file name needs to be generated differently for each channel. First
|
||||||
|
you need to decide on a proper combination of title and episode name, preferably
|
||||||
|
one that is already used by one of your channels (let's say the second one).
|
||||||
|
In the first case, title and episode name are correctly put in their respective
|
||||||
|
places, and "TITLE - EPISODE" as file name will do. The second case is our common
|
||||||
|
version, where everything is in the title, so TITLE is just fine. The third case
|
||||||
|
poses a problem, because everything is in the title, but with a different separator.
|
||||||
|
Here the special macro "{>}" can be used in the file name, which contains everything
|
||||||
|
following the matching pattern. There are three macros that can be used here:
|
||||||
|
|
||||||
|
{<} everything before the matching pattern
|
||||||
|
{>} everything after the matching pattern
|
||||||
|
{=} the matching pattern itself (just for completeness)
|
||||||
|
|
||||||
* Managing folders
|
* Managing folders
|
||||||
|
|
||||||
The "Select folder" menu, which can be accessed by pressing the "Red" key in
|
The "Select folder" menu, which can be accessed by pressing the "Red" key in
|
||||||
|
17
config.h
17
config.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: config.h 4.21 2020/12/22 17:23:51 kls Exp $
|
* $Id: config.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __CONFIG_H
|
#ifndef __CONFIG_H
|
||||||
@ -22,13 +22,13 @@
|
|||||||
|
|
||||||
// VDR's own version number:
|
// VDR's own version number:
|
||||||
|
|
||||||
#define VDRVERSION "2.4.6"
|
#define VDRVERSION "2.5.1"
|
||||||
#define VDRVERSNUM 20406 // Version * 10000 + Major * 100 + Minor
|
#define VDRVERSNUM 20501 // Version * 10000 + Major * 100 + Minor
|
||||||
|
|
||||||
// The plugin API's version number:
|
// The plugin API's version number:
|
||||||
|
|
||||||
#define APIVERSION "2.4.6"
|
#define APIVERSION "2.5.1"
|
||||||
#define APIVERSNUM 20406 // Version * 10000 + Major * 100 + Minor
|
#define APIVERSNUM 20501 // Version * 10000 + Major * 100 + Minor
|
||||||
|
|
||||||
// When loading plugins, VDR searches them by their APIVERSION, which
|
// When loading plugins, VDR searches them by their APIVERSION, which
|
||||||
// may be smaller than VDRVERSION in case there have been no changes to
|
// may be smaller than VDRVERSION in case there have been no changes to
|
||||||
@ -46,6 +46,13 @@
|
|||||||
|
|
||||||
#define TIMERMACRO_TITLE "TITLE"
|
#define TIMERMACRO_TITLE "TITLE"
|
||||||
#define TIMERMACRO_EPISODE "EPISODE"
|
#define TIMERMACRO_EPISODE "EPISODE"
|
||||||
|
#define TIMERMACRO_BEFORE "{<}"
|
||||||
|
#define TIMERMACRO_MATCH "{=}"
|
||||||
|
#define TIMERMACRO_AFTER "{>}"
|
||||||
|
|
||||||
|
#define TIMERPATTERN_AVOID "@"
|
||||||
|
#define TIMERPATTERN_BEGIN "^"
|
||||||
|
#define TIMERPATTERN_END "$"
|
||||||
|
|
||||||
#define MINOSDWIDTH 480
|
#define MINOSDWIDTH 480
|
||||||
#define MAXOSDWIDTH 1920
|
#define MAXOSDWIDTH 1920
|
||||||
|
86
menu.c
86
menu.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menu.c 4.88 2020/12/12 22:01:01 kls Exp $
|
* $Id: menu.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "menu.h"
|
#include "menu.h"
|
||||||
@ -993,6 +993,23 @@ eOSState cMenuFolder::ProcessKey(eKeys Key)
|
|||||||
|
|
||||||
// --- cMenuEditTimer --------------------------------------------------------
|
// --- cMenuEditTimer --------------------------------------------------------
|
||||||
|
|
||||||
|
static const char *TimerFileMacrosForPattern[] = {
|
||||||
|
TIMERMACRO_TITLE,
|
||||||
|
TIMERMACRO_EPISODE,
|
||||||
|
TIMERMACRO_BEFORE,
|
||||||
|
TIMERMACRO_MATCH,
|
||||||
|
TIMERMACRO_AFTER,
|
||||||
|
"",
|
||||||
|
NULL
|
||||||
|
};
|
||||||
|
|
||||||
|
static const char *TimerFileMacros[] = {
|
||||||
|
TIMERMACRO_TITLE,
|
||||||
|
TIMERMACRO_EPISODE,
|
||||||
|
"",
|
||||||
|
NULL
|
||||||
|
};
|
||||||
|
|
||||||
const cTimer *cMenuEditTimer::addedTimer = NULL;
|
const cTimer *cMenuEditTimer::addedTimer = NULL;
|
||||||
|
|
||||||
cMenuEditTimer::cMenuEditTimer(cTimer *Timer, bool New)
|
cMenuEditTimer::cMenuEditTimer(cTimer *Timer, bool New)
|
||||||
@ -1000,6 +1017,7 @@ cMenuEditTimer::cMenuEditTimer(cTimer *Timer, bool New)
|
|||||||
{
|
{
|
||||||
SetMenuCategory(mcTimerEdit);
|
SetMenuCategory(mcTimerEdit);
|
||||||
addedTimer = NULL;
|
addedTimer = NULL;
|
||||||
|
pattern = NULL;
|
||||||
file = NULL;
|
file = NULL;
|
||||||
day = firstday = NULL;
|
day = firstday = NULL;
|
||||||
timer = Timer;
|
timer = Timer;
|
||||||
@ -1019,6 +1037,7 @@ cMenuEditTimer::cMenuEditTimer(cTimer *Timer, bool New)
|
|||||||
Add(new cMenuEditIntItem( tr("Lifetime"), &data.lifetime, 0, MAXLIFETIME));
|
Add(new cMenuEditIntItem( tr("Lifetime"), &data.lifetime, 0, MAXLIFETIME));
|
||||||
Add(file = new cMenuEditStrItem( tr("File"), data.file, sizeof(data.file)));
|
Add(file = new cMenuEditStrItem( tr("File"), data.file, sizeof(data.file)));
|
||||||
SetFirstDayItem();
|
SetFirstDayItem();
|
||||||
|
SetPatternItem(true);
|
||||||
if (data.remote)
|
if (data.remote)
|
||||||
strn0cpy(remote, data.remote, sizeof(remote));
|
strn0cpy(remote, data.remote, sizeof(remote));
|
||||||
else
|
else
|
||||||
@ -1047,7 +1066,7 @@ const cTimer *cMenuEditTimer::AddedTimer(void)
|
|||||||
|
|
||||||
void cMenuEditTimer::SetHelpKeys(void)
|
void cMenuEditTimer::SetHelpKeys(void)
|
||||||
{
|
{
|
||||||
SetHelp(tr("Button$Folder"), data.weekdays ? tr("Button$Single") : tr("Button$Repeating"));
|
SetHelp(tr("Button$Folder"), data.weekdays ? tr("Button$Single") : tr("Button$Repeating"), *data.pattern ? tr("Button$Regular") : tr("Button$Pattern"));
|
||||||
}
|
}
|
||||||
|
|
||||||
void cMenuEditTimer::SetFirstDayItem(void)
|
void cMenuEditTimer::SetFirstDayItem(void)
|
||||||
@ -1063,6 +1082,40 @@ void cMenuEditTimer::SetFirstDayItem(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cMenuEditTimer::SetPatternItem(bool Initial)
|
||||||
|
{
|
||||||
|
if (Initial && !*data.pattern) {
|
||||||
|
file->SetMacros(TimerFileMacros);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!pattern) {
|
||||||
|
if (data.HasFlags(tfRecording)) {
|
||||||
|
Skins.Message(mtWarning, tr("Timer is recording!"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!*data.pattern) {
|
||||||
|
char *p = strrchr(data.file, FOLDERDELIMCHAR);
|
||||||
|
if (p)
|
||||||
|
p++;
|
||||||
|
else
|
||||||
|
p = data.file;
|
||||||
|
strn0cpy(data.pattern, p, sizeof(data.pattern));
|
||||||
|
}
|
||||||
|
Ins(pattern = new cMenuEditStrItem( tr("Pattern"), data.pattern, sizeof(data.pattern)), true, file);
|
||||||
|
pattern->SetKeepSpace();
|
||||||
|
file->SetMacros(TimerFileMacrosForPattern);
|
||||||
|
Display();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
Del(pattern->Index());
|
||||||
|
pattern = NULL;
|
||||||
|
*data.pattern = 0;
|
||||||
|
file->SetMacros(TimerFileMacros);
|
||||||
|
Display();
|
||||||
|
}
|
||||||
|
SetHelpKeys();
|
||||||
|
}
|
||||||
|
|
||||||
eOSState cMenuEditTimer::SetFolder(void)
|
eOSState cMenuEditTimer::SetFolder(void)
|
||||||
{
|
{
|
||||||
if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu())) {
|
if (cMenuFolder *mf = dynamic_cast<cMenuFolder *>(SubMenu())) {
|
||||||
@ -1142,6 +1195,8 @@ eOSState cMenuEditTimer::ProcessKey(eKeys Key)
|
|||||||
cRecordControls::Stop(timer);
|
cRecordControls::Stop(timer);
|
||||||
if (timer->Remote() && data.Remote())
|
if (timer->Remote() && data.Remote())
|
||||||
Timers->SetSyncStateKey(StateKeySVDRPRemoteTimersPoll);
|
Timers->SetSyncStateKey(StateKeySVDRPRemoteTimersPoll);
|
||||||
|
if (data.Local() && !timer->IsPatternTimer() && data.IsPatternTimer())
|
||||||
|
data.SetEvent(NULL);
|
||||||
*timer = data;
|
*timer = data;
|
||||||
}
|
}
|
||||||
LOCK_SCHEDULES_READ;
|
LOCK_SCHEDULES_READ;
|
||||||
@ -1159,7 +1214,8 @@ eOSState cMenuEditTimer::ProcessKey(eKeys Key)
|
|||||||
Display();
|
Display();
|
||||||
}
|
}
|
||||||
return osContinue;
|
return osContinue;
|
||||||
case kYellow:
|
case kYellow: SetPatternItem();
|
||||||
|
return osContinue;
|
||||||
case kBlue: return osContinue;
|
case kBlue: return osContinue;
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
@ -1212,12 +1268,19 @@ void cMenuTimerItem::Set(void)
|
|||||||
strftime(buffer, sizeof(buffer), "%Y%m%d", &tm_r);
|
strftime(buffer, sizeof(buffer), "%Y%m%d", &tm_r);
|
||||||
day = buffer;
|
day = buffer;
|
||||||
}
|
}
|
||||||
const char *File = Setup.FoldersInTimerMenu ? NULL : strrchr(timer->File(), FOLDERDELIMCHAR);
|
const char *File = timer->Pattern();
|
||||||
|
if (!*File) {
|
||||||
|
if (timer->HasFlags(tfSpawned) && timer->Event() && timer->Event()->Title())
|
||||||
|
File = timer->Event()->Title();
|
||||||
|
else {
|
||||||
|
File = Setup.FoldersInTimerMenu ? NULL : strrchr(timer->File(), FOLDERDELIMCHAR);
|
||||||
if (File && strcmp(File + 1, TIMERMACRO_TITLE) && strcmp(File + 1, TIMERMACRO_EPISODE))
|
if (File && strcmp(File + 1, TIMERMACRO_TITLE) && strcmp(File + 1, TIMERMACRO_EPISODE))
|
||||||
File++;
|
File++;
|
||||||
else
|
else
|
||||||
File = timer->File();
|
File = timer->File();
|
||||||
SetText(cString::sprintf("%c\t%d\t%s%s%s\t%02d:%02d\t%02d:%02d\t%s%s",
|
}
|
||||||
|
}
|
||||||
|
SetText(cString::sprintf("%c\t%d\t%s%s%s\t%02d:%02d\t%02d:%02d\t%s%s%s%s",
|
||||||
!(timer->HasFlags(tfActive)) ? ' ' : timer->FirstDay() ? '!' : timer->Recording() ? '#' : '>',
|
!(timer->HasFlags(tfActive)) ? ' ' : timer->FirstDay() ? '!' : timer->Recording() ? '#' : '>',
|
||||||
timer->Channel()->Number(),
|
timer->Channel()->Number(),
|
||||||
*name,
|
*name,
|
||||||
@ -1228,7 +1291,9 @@ void cMenuTimerItem::Set(void)
|
|||||||
timer->Stop() / 100,
|
timer->Stop() / 100,
|
||||||
timer->Stop() % 100,
|
timer->Stop() % 100,
|
||||||
timer->Remote() ? *cString::sprintf("@%s: ", timer->Remote()) : "",
|
timer->Remote() ? *cString::sprintf("@%s: ", timer->Remote()) : "",
|
||||||
File));
|
timer->IsPatternTimer() ? "{" : "",
|
||||||
|
File,
|
||||||
|
timer->IsPatternTimer() ? "}" : ""));
|
||||||
}
|
}
|
||||||
|
|
||||||
void cMenuTimerItem::SetMenuItem(cSkinDisplayMenu *DisplayMenu, int Index, bool Current, bool Selectable)
|
void cMenuTimerItem::SetMenuItem(cSkinDisplayMenu *DisplayMenu, int Index, bool Current, bool Selectable)
|
||||||
@ -1544,6 +1609,8 @@ bool cMenuScheduleItem::Update(const cTimers *Timers, bool Force)
|
|||||||
eTimerMatch OldTimerMatch = timerMatch;
|
eTimerMatch OldTimerMatch = timerMatch;
|
||||||
bool OldTimerActive = timerActive;
|
bool OldTimerActive = timerActive;
|
||||||
const cTimer *Timer = Timers->GetMatch(event, &timerMatch);
|
const cTimer *Timer = Timers->GetMatch(event, &timerMatch);
|
||||||
|
if (event->EndTime() < time(NULL) && !event->IsRunning())
|
||||||
|
timerMatch = tmNone;
|
||||||
timerActive = Timer && Timer->HasFlags(tfActive);
|
timerActive = Timer && Timer->HasFlags(tfActive);
|
||||||
if (Force || timerMatch != OldTimerMatch || timerActive != OldTimerActive) {
|
if (Force || timerMatch != OldTimerMatch || timerActive != OldTimerActive) {
|
||||||
cString buffer;
|
cString buffer;
|
||||||
@ -5354,8 +5421,13 @@ void cRecordControl::Stop(bool ExecuteUserCommand)
|
|||||||
bool cRecordControl::Process(time_t t)
|
bool cRecordControl::Process(time_t t)
|
||||||
{
|
{
|
||||||
if (!recorder || !recorder->IsAttached() || !timer || !timer->Matches(t)) {
|
if (!recorder || !recorder->IsAttached() || !timer || !timer->Matches(t)) {
|
||||||
if (timer)
|
if (timer) {
|
||||||
timer->SetPending(false);
|
timer->SetPending(false);
|
||||||
|
if (timer->HasFlags(tfAvoid)) {
|
||||||
|
const char *p = strgetlast(timer->File(), FOLDERDELIMCHAR);
|
||||||
|
DoneRecordingsPattern.Append(p);
|
||||||
|
}
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
4
menu.h
4
menu.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menu.h 4.8 2018/04/14 10:24:41 kls Exp $
|
* $Id: menu.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __MENU_H
|
#ifndef __MENU_H
|
||||||
@ -79,11 +79,13 @@ private:
|
|||||||
bool addIfConfirmed;
|
bool addIfConfirmed;
|
||||||
cStringList svdrpServerNames;
|
cStringList svdrpServerNames;
|
||||||
char remote[HOST_NAME_MAX];
|
char remote[HOST_NAME_MAX];
|
||||||
|
cMenuEditStrItem *pattern;
|
||||||
cMenuEditStrItem *file;
|
cMenuEditStrItem *file;
|
||||||
cMenuEditDateItem *day;
|
cMenuEditDateItem *day;
|
||||||
cMenuEditDateItem *firstday;
|
cMenuEditDateItem *firstday;
|
||||||
eOSState SetFolder(void);
|
eOSState SetFolder(void);
|
||||||
void SetFirstDayItem(void);
|
void SetFirstDayItem(void);
|
||||||
|
void SetPatternItem(bool Initial = false);
|
||||||
void SetHelpKeys(void);
|
void SetHelpKeys(void);
|
||||||
public:
|
public:
|
||||||
cMenuEditTimer(cTimer *Timer, bool New = false);
|
cMenuEditTimer(cTimer *Timer, bool New = false);
|
||||||
|
51
menuitems.c
51
menuitems.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menuitems.c 4.3 2018/03/23 15:37:02 kls Exp $
|
* $Id: menuitems.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "menuitems.h"
|
#include "menuitems.h"
|
||||||
@ -390,6 +390,10 @@ cMenuEditStrItem::cMenuEditStrItem(const char *Name, char *Value, int Length, co
|
|||||||
allowed = Allowed ? Allowed : tr(FileNameChars);
|
allowed = Allowed ? Allowed : tr(FileNameChars);
|
||||||
pos = -1;
|
pos = -1;
|
||||||
offset = 0;
|
offset = 0;
|
||||||
|
keepSpace = false;
|
||||||
|
macro = -1;
|
||||||
|
lastMacro = -1;
|
||||||
|
macros = NULL;
|
||||||
insert = uppercase = false;
|
insert = uppercase = false;
|
||||||
newchar = true;
|
newchar = true;
|
||||||
lengthUtf8 = 0;
|
lengthUtf8 = 0;
|
||||||
@ -408,6 +412,13 @@ cMenuEditStrItem::~cMenuEditStrItem()
|
|||||||
delete[] charMapUtf8;
|
delete[] charMapUtf8;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cMenuEditStrItem::SetMacros(const char **Macros)
|
||||||
|
{
|
||||||
|
macros = Macros;
|
||||||
|
macro = 0;
|
||||||
|
lastMacro = -1;
|
||||||
|
}
|
||||||
|
|
||||||
void cMenuEditStrItem::EnterEditMode(void)
|
void cMenuEditStrItem::EnterEditMode(void)
|
||||||
{
|
{
|
||||||
if (!valueUtf8) {
|
if (!valueUtf8) {
|
||||||
@ -430,6 +441,7 @@ void cMenuEditStrItem::LeaveEditMode(bool SaveValue)
|
|||||||
if (valueUtf8) {
|
if (valueUtf8) {
|
||||||
if (SaveValue) {
|
if (SaveValue) {
|
||||||
Utf8FromArray(valueUtf8, value, length);
|
Utf8FromArray(valueUtf8, value, length);
|
||||||
|
if (!keepSpace)
|
||||||
stripspace(value);
|
stripspace(value);
|
||||||
}
|
}
|
||||||
lengthUtf8 = 0;
|
lengthUtf8 = 0;
|
||||||
@ -448,7 +460,7 @@ void cMenuEditStrItem::LeaveEditMode(bool SaveValue)
|
|||||||
void cMenuEditStrItem::SetHelpKeys(void)
|
void cMenuEditStrItem::SetHelpKeys(void)
|
||||||
{
|
{
|
||||||
if (InEditMode())
|
if (InEditMode())
|
||||||
SetHelp(tr("Button$ABC/abc"), insert ? tr("Button$Overwrite") : tr("Button$Insert"), tr("Button$Delete"));
|
SetHelp(tr("Button$ABC/abc"), insert ? tr("Button$Overwrite") : tr("Button$Insert"), tr("Button$Delete"), macros ? tr("Button$Macro") : NULL);
|
||||||
else
|
else
|
||||||
SetHelp(NULL);
|
SetHelp(NULL);
|
||||||
}
|
}
|
||||||
@ -581,11 +593,39 @@ void cMenuEditStrItem::Delete(void)
|
|||||||
lengthUtf8--;
|
lengthUtf8--;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cMenuEditStrItem::InsertMacro(void)
|
||||||
|
{
|
||||||
|
if (!macros)
|
||||||
|
return;
|
||||||
|
if (lastMacro >= 0) {
|
||||||
|
int l = strlen(macros[lastMacro]);
|
||||||
|
while (l-- > 0)
|
||||||
|
Delete();
|
||||||
|
}
|
||||||
|
const char *p = macros[macro];
|
||||||
|
int oldPos = pos;
|
||||||
|
bool oldInsert = insert;
|
||||||
|
insert = true;
|
||||||
|
newchar = true;
|
||||||
|
while (*p) {
|
||||||
|
Type(*p);
|
||||||
|
p++;
|
||||||
|
}
|
||||||
|
insert = oldInsert;
|
||||||
|
pos = oldPos;
|
||||||
|
lastMacro = macro;
|
||||||
|
if (!macros[++macro])
|
||||||
|
macro = 0;
|
||||||
|
}
|
||||||
|
|
||||||
eOSState cMenuEditStrItem::ProcessKey(eKeys Key)
|
eOSState cMenuEditStrItem::ProcessKey(eKeys Key)
|
||||||
{
|
{
|
||||||
bool SameKey = NORMALKEY(Key) == lastKey;
|
bool SameKey = NORMALKEY(Key) == lastKey;
|
||||||
if (Key != kNone)
|
if (Key != kNone) {
|
||||||
lastKey = NORMALKEY(Key);
|
lastKey = NORMALKEY(Key);
|
||||||
|
if (Key != kBlue)
|
||||||
|
lastMacro = -1;
|
||||||
|
}
|
||||||
else if (!newchar && k0 <= lastKey && lastKey <= k9 && autoAdvanceTimeout.TimedOut()) {
|
else if (!newchar && k0 <= lastKey && lastKey <= k9 && autoAdvanceTimeout.TimedOut()) {
|
||||||
AdvancePos();
|
AdvancePos();
|
||||||
newchar = true;
|
newchar = true;
|
||||||
@ -635,8 +675,9 @@ eOSState cMenuEditStrItem::ProcessKey(eKeys Key)
|
|||||||
return osUnknown;
|
return osUnknown;
|
||||||
break;
|
break;
|
||||||
case kBlue|k_Repeat:
|
case kBlue|k_Repeat:
|
||||||
case kBlue: // consume the key only if in edit-mode
|
case kBlue: if (InEditMode())
|
||||||
if (!InEditMode())
|
InsertMacro();
|
||||||
|
else
|
||||||
return osUnknown;
|
return osUnknown;
|
||||||
break;
|
break;
|
||||||
case kLeft|k_Repeat:
|
case kLeft|k_Repeat:
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: menuitems.h 4.1 2015/09/06 10:38:37 kls Exp $
|
* $Id: menuitems.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __MENUITEMS_H
|
#ifndef __MENUITEMS_H
|
||||||
@ -111,6 +111,9 @@ private:
|
|||||||
int length;
|
int length;
|
||||||
const char *allowed;
|
const char *allowed;
|
||||||
int pos, offset;
|
int pos, offset;
|
||||||
|
bool keepSpace;
|
||||||
|
const char **macros;
|
||||||
|
int macro, lastMacro;
|
||||||
bool insert, newchar, uppercase;
|
bool insert, newchar, uppercase;
|
||||||
int lengthUtf8;
|
int lengthUtf8;
|
||||||
uint *valueUtf8;
|
uint *valueUtf8;
|
||||||
@ -127,6 +130,7 @@ private:
|
|||||||
void Type(uint c);
|
void Type(uint c);
|
||||||
void Insert(void);
|
void Insert(void);
|
||||||
void Delete(void);
|
void Delete(void);
|
||||||
|
void InsertMacro(void);
|
||||||
protected:
|
protected:
|
||||||
void EnterEditMode(void);
|
void EnterEditMode(void);
|
||||||
void LeaveEditMode(bool SaveValue = false);
|
void LeaveEditMode(bool SaveValue = false);
|
||||||
@ -134,6 +138,8 @@ protected:
|
|||||||
public:
|
public:
|
||||||
cMenuEditStrItem(const char *Name, char *Value, int Length, const char *Allowed = NULL);
|
cMenuEditStrItem(const char *Name, char *Value, int Length, const char *Allowed = NULL);
|
||||||
~cMenuEditStrItem();
|
~cMenuEditStrItem();
|
||||||
|
void SetKeepSpace(void) { keepSpace = true; }
|
||||||
|
void SetMacros(const char **Macros);
|
||||||
virtual eOSState ProcessKey(eKeys Key);
|
virtual eOSState ProcessKey(eKeys Key);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
17
po/ar.po
17
po/ar.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2008-10-16 11:16-0400\n"
|
"PO-Revision-Date: 2008-10-16 11:16-0400\n"
|
||||||
"Last-Translator: Osama Alrawab <alrawab@hotmail.com>\n"
|
"Last-Translator: Osama Alrawab <alrawab@hotmail.com>\n"
|
||||||
"Language-Team: Arabic <ar@li.org>\n"
|
"Language-Team: Arabic <ar@li.org>\n"
|
||||||
@ -691,9 +691,21 @@ msgstr "Single"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Repeating"
|
msgstr "Repeating"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "اليوم الاول"
|
msgstr "اليوم الاول"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1495,6 +1507,9 @@ msgstr "اعادة الكتابة"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "ادراج"
|
msgstr "ادراج"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "الملحق"
|
msgstr "الملحق"
|
||||||
|
|
||||||
|
17
po/ca_ES.po
17
po/ca_ES.po
@ -10,7 +10,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2008-03-02 19:02+0100\n"
|
"PO-Revision-Date: 2008-03-02 19:02+0100\n"
|
||||||
"Last-Translator: Luca Olivetti <luca@ventoso.org>\n"
|
"Last-Translator: Luca Olivetti <luca@ventoso.org>\n"
|
||||||
"Language-Team: Catalan <vdr@linuxtv.org>\n"
|
"Language-Team: Catalan <vdr@linuxtv.org>\n"
|
||||||
@ -690,9 +690,21 @@ msgstr "Individual"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Repetitiu"
|
msgstr "Repetitiu"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Primer dia"
|
msgstr "Primer dia"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1494,6 +1506,9 @@ msgstr "Sobrescriure"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Inserir"
|
msgstr "Inserir"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/cs_CZ.po
17
po/cs_CZ.po
@ -10,7 +10,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2010-05-06 11:00+0200\n"
|
"PO-Revision-Date: 2010-05-06 11:00+0200\n"
|
||||||
"Last-Translator: Aleš Juřík <ajurik@quick.cz>\n"
|
"Last-Translator: Aleš Juřík <ajurik@quick.cz>\n"
|
||||||
"Language-Team: Czech <vdr@linuxtv.org>\n"
|
"Language-Team: Czech <vdr@linuxtv.org>\n"
|
||||||
@ -690,9 +690,21 @@ msgstr "Bez opakování"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "S opakováním"
|
msgstr "S opakováním"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "První den"
|
msgstr "První den"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1494,6 +1506,9 @@ msgstr "Přepsat"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Vložit"
|
msgstr "Vložit"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Modul"
|
msgstr "Modul"
|
||||||
|
|
||||||
|
17
po/da_DK.po
17
po/da_DK.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
||||||
"Last-Translator: Mogens Elneff <mogens@elneff.dk>\n"
|
"Last-Translator: Mogens Elneff <mogens@elneff.dk>\n"
|
||||||
"Language-Team: Danish <vdr@linuxtv.org>\n"
|
"Language-Team: Danish <vdr@linuxtv.org>\n"
|
||||||
@ -687,9 +687,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Første dag"
|
msgstr "Første dag"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1491,6 +1503,9 @@ msgstr "Overskriv"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Indsæt"
|
msgstr "Indsæt"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/de_DE.po
17
po/de_DE.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-10 13:45+0100\n"
|
"PO-Revision-Date: 2015-02-10 13:45+0100\n"
|
||||||
"Last-Translator: Klaus Schmidinger <vdr@tvdr.de>\n"
|
"Last-Translator: Klaus Schmidinger <vdr@tvdr.de>\n"
|
||||||
"Language-Team: German <vdr@linuxtv.org>\n"
|
"Language-Team: German <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Einmalig"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Wiederholend"
|
msgstr "Wiederholend"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr "Normal"
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr "Muster"
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Erster Tag"
|
msgstr "Erster Tag"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr "Timer nimmt auf!"
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr "Muster"
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Fehler beim Ansprechen des fernen Timers"
|
msgstr "Fehler beim Ansprechen des fernen Timers"
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Einfügen"
|
msgstr "Einfügen"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr "Makro"
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/el_GR.po
17
po/el_GR.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
||||||
"Last-Translator: Dimitrios Dimitrakos <mail@dimitrios.de>\n"
|
"Last-Translator: Dimitrios Dimitrakos <mail@dimitrios.de>\n"
|
||||||
"Language-Team: Greek <vdr@linuxtv.org>\n"
|
"Language-Team: Greek <vdr@linuxtv.org>\n"
|
||||||
@ -687,9 +687,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Ðñþôç ìÝñá"
|
msgstr "Ðñþôç ìÝñá"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1491,6 +1503,9 @@ msgstr "
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "ÅéóáãùãÞ"
|
msgstr "ÅéóáãùãÞ"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "ÅðÝêôáóç"
|
msgstr "ÅðÝêôáóç"
|
||||||
|
|
||||||
|
17
po/es_ES.po
17
po/es_ES.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-19 23:00+0100\n"
|
"PO-Revision-Date: 2015-02-19 23:00+0100\n"
|
||||||
"Last-Translator: Gabriel Bonich <gbonich@gmail.com>\n"
|
"Last-Translator: Gabriel Bonich <gbonich@gmail.com>\n"
|
||||||
"Language-Team: Spanish <vdr@linuxtv.org>\n"
|
"Language-Team: Spanish <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Individual"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Periódico"
|
msgstr "Periódico"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Primer día"
|
msgstr "Primer día"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Sobreescribir"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Insertar"
|
msgstr "Insertar"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/et_EE.po
17
po/et_EE.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
||||||
"Last-Translator: Arthur Konovalov <artlov@gmail.com>\n"
|
"Last-Translator: Arthur Konovalov <artlov@gmail.com>\n"
|
||||||
"Language-Team: Estonian <vdr@linuxtv.org>\n"
|
"Language-Team: Estonian <vdr@linuxtv.org>\n"
|
||||||
@ -687,9 +687,21 @@ msgstr "Üksik"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Korduv"
|
msgstr "Korduv"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "1. päev"
|
msgstr "1. päev"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Kaugtaimeri viga"
|
msgstr "Kaugtaimeri viga"
|
||||||
|
|
||||||
@ -1491,6 +1503,9 @@ msgstr "Asenda (OVR)"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Lisa (INS)"
|
msgstr "Lisa (INS)"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/fi_FI.po
17
po/fi_FI.po
@ -11,7 +11,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2007-08-15 15:52+0200\n"
|
"PO-Revision-Date: 2007-08-15 15:52+0200\n"
|
||||||
"Last-Translator: Matti Lehtimäki <matti.lehtimaki@gmail.com>\n"
|
"Last-Translator: Matti Lehtimäki <matti.lehtimaki@gmail.com>\n"
|
||||||
"Language-Team: Finnish <vdr@linuxtv.org>\n"
|
"Language-Team: Finnish <vdr@linuxtv.org>\n"
|
||||||
@ -691,9 +691,21 @@ msgstr "Yksittäinen"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Toistuva"
|
msgstr "Toistuva"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "1. päivä"
|
msgstr "1. päivä"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Etäajastimen hakeminen epäonnistui"
|
msgstr "Etäajastimen hakeminen epäonnistui"
|
||||||
|
|
||||||
@ -1495,6 +1507,9 @@ msgstr "Korvaa"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Lisää"
|
msgstr "Lisää"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Laajennos"
|
msgstr "Laajennos"
|
||||||
|
|
||||||
|
17
po/fr_FR.po
17
po/fr_FR.po
@ -18,7 +18,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-04-14 10:16+0100\n"
|
"PO-Revision-Date: 2018-04-14 10:16+0100\n"
|
||||||
"Last-Translator: Bernard Jaulin <bernard.jaulin@gmail.com>\n"
|
"Last-Translator: Bernard Jaulin <bernard.jaulin@gmail.com>\n"
|
||||||
"Language-Team: French <vdr@linuxtv.org>\n"
|
"Language-Team: French <vdr@linuxtv.org>\n"
|
||||||
@ -698,9 +698,21 @@ msgstr "Simple"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Périodique"
|
msgstr "Périodique"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Premier jour"
|
msgstr "Premier jour"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Erreur pendant l'accès à la programmation"
|
msgstr "Erreur pendant l'accès à la programmation"
|
||||||
|
|
||||||
@ -1502,6 +1514,9 @@ msgstr "Écraser"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Insérer"
|
msgstr "Insérer"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Module"
|
msgstr "Module"
|
||||||
|
|
||||||
|
17
po/hr_HR.po
17
po/hr_HR.po
@ -9,7 +9,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2008-03-17 19:00+0100\n"
|
"PO-Revision-Date: 2008-03-17 19:00+0100\n"
|
||||||
"Last-Translator: Adrian Caval <anrxc@sysphere.org>\n"
|
"Last-Translator: Adrian Caval <anrxc@sysphere.org>\n"
|
||||||
"Language-Team: Croatian <vdr@linuxtv.org>\n"
|
"Language-Team: Croatian <vdr@linuxtv.org>\n"
|
||||||
@ -689,9 +689,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Prvi dan"
|
msgstr "Prvi dan"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1493,6 +1505,9 @@ msgstr "Prepi
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Umetni"
|
msgstr "Umetni"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Dodatak"
|
msgstr "Dodatak"
|
||||||
|
|
||||||
|
17
po/hu_HU.po
17
po/hu_HU.po
@ -11,7 +11,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-04-09 21:42+0300\n"
|
"PO-Revision-Date: 2018-04-09 21:42+0300\n"
|
||||||
"Last-Translator: István Füley <ifuley@tigercomp.ro>\n"
|
"Last-Translator: István Füley <ifuley@tigercomp.ro>\n"
|
||||||
"Language-Team: Hungarian <vdr@linuxtv.org>\n"
|
"Language-Team: Hungarian <vdr@linuxtv.org>\n"
|
||||||
@ -692,9 +692,21 @@ msgstr "Egyszeri"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Ismétlődő"
|
msgstr "Ismétlődő"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Első nap"
|
msgstr "Első nap"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Távoli időzítő nem elérhető"
|
msgstr "Távoli időzítő nem elérhető"
|
||||||
|
|
||||||
@ -1496,6 +1508,9 @@ msgstr "Felülírás"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Beillesztés"
|
msgstr "Beillesztés"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/it_IT.po
17
po/it_IT.po
@ -11,7 +11,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-04-06 19:13+0100\n"
|
"PO-Revision-Date: 2018-04-06 19:13+0100\n"
|
||||||
"Last-Translator: Gringo <vdr-italian@tiscali.it>\n"
|
"Last-Translator: Gringo <vdr-italian@tiscali.it>\n"
|
||||||
"Language-Team: Italian <vdr@linuxtv.org>\n"
|
"Language-Team: Italian <vdr@linuxtv.org>\n"
|
||||||
@ -693,9 +693,21 @@ msgstr "Una volta"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Repliche"
|
msgstr "Repliche"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "1° giorno"
|
msgstr "1° giorno"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Errore durante l'accesso al timer remoto"
|
msgstr "Errore durante l'accesso al timer remoto"
|
||||||
|
|
||||||
@ -1497,6 +1509,9 @@ msgstr "Sovrascrivi"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Inserisci"
|
msgstr "Inserisci"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/lt_LT.po
17
po/lt_LT.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-11 14:02+0200\n"
|
"PO-Revision-Date: 2015-02-11 14:02+0200\n"
|
||||||
"Last-Translator: Valdemaras Pipiras <varas@ambernet.lt>\n"
|
"Last-Translator: Valdemaras Pipiras <varas@ambernet.lt>\n"
|
||||||
"Language-Team: Lithuanian <vdr@linuxtv.org>\n"
|
"Language-Team: Lithuanian <vdr@linuxtv.org>\n"
|
||||||
@ -687,9 +687,21 @@ msgstr "Vienas"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Kartotinas"
|
msgstr "Kartotinas"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Pirma diena"
|
msgstr "Pirma diena"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1491,6 +1503,9 @@ msgstr "Perrąšyti"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Įterpti"
|
msgstr "Įterpti"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Įskiepas"
|
msgstr "Įskiepas"
|
||||||
|
|
||||||
|
17
po/mk_MK.po
17
po/mk_MK.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-03-31 21:47+0100\n"
|
"PO-Revision-Date: 2018-03-31 21:47+0100\n"
|
||||||
"Last-Translator: Dimitar Petrovski <dimeptr@gmail.com>\n"
|
"Last-Translator: Dimitar Petrovski <dimeptr@gmail.com>\n"
|
||||||
"Language-Team: Macedonian <kde-i18n-doc@kde.org>\n"
|
"Language-Team: Macedonian <kde-i18n-doc@kde.org>\n"
|
||||||
@ -689,9 +689,21 @@ msgstr "Единчен"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Периодичен"
|
msgstr "Периодичен"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Прв ден"
|
msgstr "Прв ден"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Грешка при пристап на далечен тајмер"
|
msgstr "Грешка при пристап на далечен тајмер"
|
||||||
|
|
||||||
@ -1493,6 +1505,9 @@ msgstr "Препиши"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Вметни"
|
msgstr "Вметни"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Додаток"
|
msgstr "Додаток"
|
||||||
|
|
||||||
|
17
po/nl_NL.po
17
po/nl_NL.po
@ -13,7 +13,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-10 19:43+0100\n"
|
"PO-Revision-Date: 2015-02-10 19:43+0100\n"
|
||||||
"Last-Translator: Erik Oomen <oomen.e@gmail.com>\n"
|
"Last-Translator: Erik Oomen <oomen.e@gmail.com>\n"
|
||||||
"Language-Team: Dutch <vdr@linuxtv.org>\n"
|
"Language-Team: Dutch <vdr@linuxtv.org>\n"
|
||||||
@ -693,9 +693,21 @@ msgstr "Eenmalig"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Herhalen"
|
msgstr "Herhalen"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Eerste dag"
|
msgstr "Eerste dag"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1497,6 +1509,9 @@ msgstr "Overschrijven"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Invoegen"
|
msgstr "Invoegen"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/nn_NO.po
17
po/nn_NO.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
"PO-Revision-Date: 2007-08-12 14:17+0200\n"
|
||||||
"Last-Translator: Truls Slevigen <truls@slevigen.no>\n"
|
"Last-Translator: Truls Slevigen <truls@slevigen.no>\n"
|
||||||
"Language-Team: Norwegian Nynorsk <vdr@linuxtv.org>\n"
|
"Language-Team: Norwegian Nynorsk <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Første dag"
|
msgstr "Første dag"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr ""
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/pl_PL.po
17
po/pl_PL.po
@ -10,7 +10,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-02-19 00:42+0100\n"
|
"PO-Revision-Date: 2018-02-19 00:42+0100\n"
|
||||||
"Last-Translator: Tomasz Maciej Nowak <tmn505@gmail.com>\n"
|
"Last-Translator: Tomasz Maciej Nowak <tmn505@gmail.com>\n"
|
||||||
"Language-Team: Polish <vdr@linuxtv.org>\n"
|
"Language-Team: Polish <vdr@linuxtv.org>\n"
|
||||||
@ -692,9 +692,21 @@ msgstr "Pojedynczy"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Powtarzanie"
|
msgstr "Powtarzanie"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Pierwszy dzień"
|
msgstr "Pierwszy dzień"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Błąd podczas dostępu do zdalnego timera"
|
msgstr "Błąd podczas dostępu do zdalnego timera"
|
||||||
|
|
||||||
@ -1496,6 +1508,9 @@ msgstr "Nadpisz"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Wstaw"
|
msgstr "Wstaw"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Wtyczka"
|
msgstr "Wtyczka"
|
||||||
|
|
||||||
|
17
po/pt_PT.po
17
po/pt_PT.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2010-03-28 22:49+0100\n"
|
"PO-Revision-Date: 2010-03-28 22:49+0100\n"
|
||||||
"Last-Translator: Cris Silva <hudokkow@gmail.com>\n"
|
"Last-Translator: Cris Silva <hudokkow@gmail.com>\n"
|
||||||
"Language-Team: Portuguese <vdr@linuxtv.org>\n"
|
"Language-Team: Portuguese <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "1° dia"
|
msgstr "1° dia"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Sobrescrever"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Inserir"
|
msgstr "Inserir"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/ro_RO.po
17
po/ro_RO.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-11 22:26+0100\n"
|
"PO-Revision-Date: 2015-02-11 22:26+0100\n"
|
||||||
"Last-Translator: Lucian Muresan <lucianm@users.sourceforge.net>\n"
|
"Last-Translator: Lucian Muresan <lucianm@users.sourceforge.net>\n"
|
||||||
"Language-Team: Romanian <vdr@linuxtv.org>\n"
|
"Language-Team: Romanian <vdr@linuxtv.org>\n"
|
||||||
@ -689,9 +689,21 @@ msgstr "Odată"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Repetitiv"
|
msgstr "Repetitiv"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Prima zi"
|
msgstr "Prima zi"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1493,6 +1505,9 @@ msgstr "Suprascrie"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Inserează"
|
msgstr "Inserează"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Plugin"
|
msgstr "Plugin"
|
||||||
|
|
||||||
|
17
po/ru_RU.po
17
po/ru_RU.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2016-12-27 17:13+0100\n"
|
"PO-Revision-Date: 2016-12-27 17:13+0100\n"
|
||||||
"Last-Translator: Pridvorov Andrey <ua0lnj@bk.ru>\n"
|
"Last-Translator: Pridvorov Andrey <ua0lnj@bk.ru>\n"
|
||||||
"Language-Team: Russian <vdr@linuxtv.org>\n"
|
"Language-Team: Russian <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Один раз"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Повтор"
|
msgstr "Повтор"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Первый день"
|
msgstr "Первый день"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Ошибка доступа к таймеру"
|
msgstr "Ошибка доступа к таймеру"
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Замена"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Вставка"
|
msgstr "Вставка"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Модуль"
|
msgstr "Модуль"
|
||||||
|
|
||||||
|
17
po/sk_SK.po
17
po/sk_SK.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-17 18:59+0100\n"
|
"PO-Revision-Date: 2015-02-17 18:59+0100\n"
|
||||||
"Last-Translator: Milan Hrala <hrala.milan@gmail.com>\n"
|
"Last-Translator: Milan Hrala <hrala.milan@gmail.com>\n"
|
||||||
"Language-Team: Slovak <vdr@linuxtv.org>\n"
|
"Language-Team: Slovak <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "bez opakovania"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "s opakovaním"
|
msgstr "s opakovaním"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Odo dòa"
|
msgstr "Odo dòa"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Prep
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Vlo¾i»"
|
msgstr "Vlo¾i»"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Modul"
|
msgstr "Modul"
|
||||||
|
|
||||||
|
17
po/sl_SI.po
17
po/sl_SI.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2013-03-04 12:46+0100\n"
|
"PO-Revision-Date: 2013-03-04 12:46+0100\n"
|
||||||
"Last-Translator: Matjaz Thaler <matjaz.thaler@guest.arnes.si>\n"
|
"Last-Translator: Matjaz Thaler <matjaz.thaler@guest.arnes.si>\n"
|
||||||
"Language-Team: Slovenian <vdr@linuxtv.org>\n"
|
"Language-Team: Slovenian <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Enkraten"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Ponavljajoèe"
|
msgstr "Ponavljajoèe"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Prvi dan"
|
msgstr "Prvi dan"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Prepi
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Vstavi"
|
msgstr "Vstavi"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Vstavek"
|
msgstr "Vstavek"
|
||||||
|
|
||||||
|
17
po/sr_RS.po
17
po/sr_RS.po
@ -8,7 +8,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2013-03-16 15:05+0100\n"
|
"PO-Revision-Date: 2013-03-16 15:05+0100\n"
|
||||||
"Last-Translator: Zoran Turalija <zoran.turalija@gmail.com>\n"
|
"Last-Translator: Zoran Turalija <zoran.turalija@gmail.com>\n"
|
||||||
"Language-Team: Serbian <vdr@linuxtv.org>\n"
|
"Language-Team: Serbian <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Jedinstven"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Ponavljajuæi"
|
msgstr "Ponavljajuæi"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Prvi dan"
|
msgstr "Prvi dan"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Zameni"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Ubaci"
|
msgstr "Ubaci"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Dodatak"
|
msgstr "Dodatak"
|
||||||
|
|
||||||
|
17
po/sv_SE.po
17
po/sv_SE.po
@ -12,7 +12,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2015-02-12 21:58+0100\n"
|
"PO-Revision-Date: 2015-02-12 21:58+0100\n"
|
||||||
"Last-Translator: Magnus Sirviö <sirwio@hotmail.com>\n"
|
"Last-Translator: Magnus Sirviö <sirwio@hotmail.com>\n"
|
||||||
"Language-Team: Swedish <vdr@linuxtv.org>\n"
|
"Language-Team: Swedish <vdr@linuxtv.org>\n"
|
||||||
@ -692,9 +692,21 @@ msgstr "Enskilld"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Repeterande"
|
msgstr "Repeterande"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Första dag"
|
msgstr "Första dag"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1496,6 +1508,9 @@ msgstr "Skriv
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Infoga"
|
msgstr "Infoga"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Modul"
|
msgstr "Modul"
|
||||||
|
|
||||||
|
17
po/tr_TR.po
17
po/tr_TR.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2008-02-28 00:33+0100\n"
|
"PO-Revision-Date: 2008-02-28 00:33+0100\n"
|
||||||
"Last-Translator: Oktay Yolgeçen <oktay_73@yahoo.de>\n"
|
"Last-Translator: Oktay Yolgeçen <oktay_73@yahoo.de>\n"
|
||||||
"Language-Team: Turkish <vdr@linuxtv.org>\n"
|
"Language-Team: Turkish <vdr@linuxtv.org>\n"
|
||||||
@ -687,9 +687,21 @@ msgstr ""
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Ýlk gün"
|
msgstr "Ýlk gün"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1491,6 +1503,9 @@ msgstr "
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Ekle"
|
msgstr "Ekle"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Eklenti"
|
msgstr "Eklenti"
|
||||||
|
|
||||||
|
17
po/uk_UA.po
17
po/uk_UA.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2018-03-18 20:00+0100\n"
|
"PO-Revision-Date: 2018-03-18 20:00+0100\n"
|
||||||
"Last-Translator: Yarema aka Knedlyk <yupadmin@gmail.com>\n"
|
"Last-Translator: Yarema aka Knedlyk <yupadmin@gmail.com>\n"
|
||||||
"Language-Team: Ukrainian <vdr@linuxtv.org>\n"
|
"Language-Team: Ukrainian <vdr@linuxtv.org>\n"
|
||||||
@ -688,9 +688,21 @@ msgstr "Одинарне"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "Повтор"
|
msgstr "Повтор"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "Перший день"
|
msgstr "Перший день"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr "Помилка доступу до віддаленого таймера"
|
msgstr "Помилка доступу до віддаленого таймера"
|
||||||
|
|
||||||
@ -1492,6 +1504,9 @@ msgstr "Заміна"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "Вставка"
|
msgstr "Вставка"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "Модуль"
|
msgstr "Модуль"
|
||||||
|
|
||||||
|
17
po/zh_CN.po
17
po/zh_CN.po
@ -7,7 +7,7 @@ msgid ""
|
|||||||
msgstr ""
|
msgstr ""
|
||||||
"Project-Id-Version: VDR 2.4.0\n"
|
"Project-Id-Version: VDR 2.4.0\n"
|
||||||
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
"Report-Msgid-Bugs-To: <vdr-bugs@tvdr.de>\n"
|
||||||
"POT-Creation-Date: 2020-06-15 17:50+0200\n"
|
"POT-Creation-Date: 2020-12-24 17:42+0100\n"
|
||||||
"PO-Revision-Date: 2013-03-04 14:52+0800\n"
|
"PO-Revision-Date: 2013-03-04 14:52+0800\n"
|
||||||
"Last-Translator: NFVDR <nfvdr@live.com>\n"
|
"Last-Translator: NFVDR <nfvdr@live.com>\n"
|
||||||
"Language-Team: Chinese (simplified) <nfvdr@live.com>\n"
|
"Language-Team: Chinese (simplified) <nfvdr@live.com>\n"
|
||||||
@ -689,9 +689,21 @@ msgstr "单个"
|
|||||||
msgid "Button$Repeating"
|
msgid "Button$Repeating"
|
||||||
msgstr "重复"
|
msgstr "重复"
|
||||||
|
|
||||||
|
msgid "Button$Regular"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Button$Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "First day"
|
msgid "First day"
|
||||||
msgstr "第一天"
|
msgstr "第一天"
|
||||||
|
|
||||||
|
msgid "Timer is recording!"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
|
msgid "Pattern"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Error while accessing remote timer"
|
msgid "Error while accessing remote timer"
|
||||||
msgstr ""
|
msgstr ""
|
||||||
|
|
||||||
@ -1493,6 +1505,9 @@ msgstr "覆盖"
|
|||||||
msgid "Button$Insert"
|
msgid "Button$Insert"
|
||||||
msgstr "插入"
|
msgstr "插入"
|
||||||
|
|
||||||
|
msgid "Button$Macro"
|
||||||
|
msgstr ""
|
||||||
|
|
||||||
msgid "Plugin"
|
msgid "Plugin"
|
||||||
msgstr "插件"
|
msgstr "插件"
|
||||||
|
|
||||||
|
70
recording.c
70
recording.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: recording.c 4.29 2020/10/30 16:08:29 kls Exp $
|
* $Id: recording.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "recording.h"
|
#include "recording.h"
|
||||||
@ -3050,6 +3050,74 @@ cUnbufferedFile *cFileName::NextFile(void)
|
|||||||
return SetOffset(fileNumber + 1);
|
return SetOffset(fileNumber + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// --- cDoneRecordings -------------------------------------------------------
|
||||||
|
|
||||||
|
cDoneRecordings DoneRecordingsPattern;
|
||||||
|
|
||||||
|
bool cDoneRecordings::Load(const char *FileName)
|
||||||
|
{
|
||||||
|
fileName = FileName;
|
||||||
|
if (*fileName && access(fileName, F_OK) == 0) {
|
||||||
|
isyslog("loading %s", *fileName);
|
||||||
|
FILE *f = fopen(fileName, "r");
|
||||||
|
if (f) {
|
||||||
|
char *s;
|
||||||
|
cReadLine ReadLine;
|
||||||
|
while ((s = ReadLine.Read(f)) != NULL)
|
||||||
|
Add(s);
|
||||||
|
fclose(f);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
LOG_ERROR_STR(*fileName);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cDoneRecordings::Save(void) const
|
||||||
|
{
|
||||||
|
bool result = true;
|
||||||
|
cSafeFile f(fileName);
|
||||||
|
if (f.Open()) {
|
||||||
|
for (int i = 0; i < doneRecordings.Size(); i++) {
|
||||||
|
if (fputs(doneRecordings[i], f) == EOF || fputc('\n', f) == EOF) {
|
||||||
|
result = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!f.Close())
|
||||||
|
result = false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
result = false;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
void cDoneRecordings::Add(const char *Title)
|
||||||
|
{
|
||||||
|
doneRecordings.Append(strdup(Title));
|
||||||
|
}
|
||||||
|
|
||||||
|
void cDoneRecordings::Append(const char *Title)
|
||||||
|
{
|
||||||
|
if (!Contains(Title)) {
|
||||||
|
Add(Title);
|
||||||
|
if (FILE *f = fopen(fileName, "a")) {
|
||||||
|
fputs(Title, f);
|
||||||
|
fputc('\n', f);
|
||||||
|
fclose(f);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
esyslog("ERROR: can't open '%s' for appending '%s'", *fileName, Title);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cDoneRecordings::Contains(const char *Title) const
|
||||||
|
{
|
||||||
|
return doneRecordings.Find(Title) >= 0;
|
||||||
|
}
|
||||||
|
|
||||||
// --- Index stuff -----------------------------------------------------------
|
// --- Index stuff -----------------------------------------------------------
|
||||||
|
|
||||||
cString IndexToHMSF(int Index, bool WithFrame, double FramesPerSecond)
|
cString IndexToHMSF(int Index, bool WithFrame, double FramesPerSecond)
|
||||||
|
16
recording.h
16
recording.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: recording.h 4.10 2020/09/16 13:48:33 kls Exp $
|
* $Id: recording.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __RECORDING_H
|
#ifndef __RECORDING_H
|
||||||
@ -504,6 +504,20 @@ public:
|
|||||||
cUnbufferedFile *NextFile(void);
|
cUnbufferedFile *NextFile(void);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class cDoneRecordings {
|
||||||
|
private:
|
||||||
|
cString fileName;
|
||||||
|
cStringList doneRecordings;
|
||||||
|
void Add(const char *Title);
|
||||||
|
public:
|
||||||
|
bool Load(const char *FileName);
|
||||||
|
bool Save(void) const;
|
||||||
|
void Append(const char *Title);
|
||||||
|
bool Contains(const char *Title) const;
|
||||||
|
};
|
||||||
|
|
||||||
|
extern cDoneRecordings DoneRecordingsPattern;
|
||||||
|
|
||||||
cString IndexToHMSF(int Index, bool WithFrame = false, double FramesPerSecond = DEFAULTFRAMESPERSECOND);
|
cString IndexToHMSF(int Index, bool WithFrame = false, double FramesPerSecond = DEFAULTFRAMESPERSECOND);
|
||||||
// Converts the given index to a string, optionally containing the frame number.
|
// Converts the given index to a string, optionally containing the frame number.
|
||||||
int HMSFToIndex(const char *HMSF, double FramesPerSecond = DEFAULTFRAMESPERSECOND);
|
int HMSFToIndex(const char *HMSF, double FramesPerSecond = DEFAULTFRAMESPERSECOND);
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: skinlcars.c 4.7 2020/05/18 16:47:29 kls Exp $
|
* $Id: skinlcars.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// "Star Trek: The Next Generation"(R) is a registered trademark of Paramount Pictures,
|
// "Star Trek: The Next Generation"(R) is a registered trademark of Paramount Pictures,
|
||||||
@ -1264,7 +1264,9 @@ void cSkinLCARSDisplayMenu::DrawTimers(void)
|
|||||||
if (y + lineHeight > ys05)
|
if (y + lineHeight > ys05)
|
||||||
break;
|
break;
|
||||||
if (const cTimer *Timer = SortedTimers[i]) {
|
if (const cTimer *Timer = SortedTimers[i]) {
|
||||||
if (Timer->Recording()) {
|
if (Timer->IsPatternTimer())
|
||||||
|
SortedTimers[i] = NULL;
|
||||||
|
else if (Timer->Recording()) {
|
||||||
if (Timer->Remote()) {
|
if (Timer->Remote()) {
|
||||||
if (!Device && Timer->HasFlags(tfActive)) {
|
if (!Device && Timer->HasFlags(tfActive)) {
|
||||||
DrawTimer(Timer, y, false);
|
DrawTimer(Timer, y, false);
|
||||||
|
8
svdrp.c
8
svdrp.c
@ -10,7 +10,7 @@
|
|||||||
* and interact with the Video Disk Recorder - or write a full featured
|
* and interact with the Video Disk Recorder - or write a full featured
|
||||||
* graphical interface that sits on top of an SVDRP connection.
|
* graphical interface that sits on top of an SVDRP connection.
|
||||||
*
|
*
|
||||||
* $Id: svdrp.c 4.43 2020/06/22 20:59:49 kls Exp $
|
* $Id: svdrp.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "svdrp.h"
|
#include "svdrp.h"
|
||||||
@ -2048,6 +2048,10 @@ void cSVDRPServer::CmdMODT(const char *Option)
|
|||||||
Reply(501, "Error in timer settings");
|
Reply(501, "Error in timer settings");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (IsRecording && t.IsPatternTimer()) {
|
||||||
|
Reply(550, "Timer is recording");
|
||||||
|
return;
|
||||||
|
}
|
||||||
*Timer = t;
|
*Timer = t;
|
||||||
if (IsRecording)
|
if (IsRecording)
|
||||||
Timer->SetFlags(tfRecording);
|
Timer->SetFlags(tfRecording);
|
||||||
@ -2055,6 +2059,8 @@ void cSVDRPServer::CmdMODT(const char *Option)
|
|||||||
Timer->ClrFlags(tfRecording);
|
Timer->ClrFlags(tfRecording);
|
||||||
Timers->SetModified();
|
Timers->SetModified();
|
||||||
isyslog("SVDRP %s < %s modified timer %s (%s)", Setup.SVDRPHostName, *clientName, *Timer->ToDescr(), Timer->HasFlags(tfActive) ? "active" : "inactive");
|
isyslog("SVDRP %s < %s modified timer %s (%s)", Setup.SVDRPHostName, *clientName, *Timer->ToDescr(), Timer->HasFlags(tfActive) ? "active" : "inactive");
|
||||||
|
if (Timer->IsPatternTimer())
|
||||||
|
Timer->SetEvent(NULL);
|
||||||
Reply(250, "%d %s", Timer->Id(), *Timer->ToText(true));
|
Reply(250, "%d %s", Timer->Id(), *Timer->ToText(true));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
244
timers.c
244
timers.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: timers.c 4.20 2020/09/16 13:48:33 kls Exp $
|
* $Id: timers.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "timers.h"
|
#include "timers.h"
|
||||||
@ -31,6 +31,7 @@ cTimer::cTimer(bool Instant, bool Pause, const cChannel *Channel)
|
|||||||
deferred = 0;
|
deferred = 0;
|
||||||
pending = inVpsMargin = false;
|
pending = inVpsMargin = false;
|
||||||
flags = tfNone;
|
flags = tfNone;
|
||||||
|
*pattern = 0;
|
||||||
*file = 0;
|
*file = 0;
|
||||||
aux = NULL;
|
aux = NULL;
|
||||||
remote = NULL;
|
remote = NULL;
|
||||||
@ -81,7 +82,94 @@ cTimer::cTimer(bool Instant, bool Pause, const cChannel *Channel)
|
|||||||
snprintf(file, sizeof(file), "%s%s", Setup.MarkInstantRecord ? "@" : "", *Setup.NameInstantRecord ? Setup.NameInstantRecord : channel->Name());
|
snprintf(file, sizeof(file), "%s%s", Setup.MarkInstantRecord ? "@" : "", *Setup.NameInstantRecord ? Setup.NameInstantRecord : channel->Name());
|
||||||
}
|
}
|
||||||
|
|
||||||
cTimer::cTimer(const cEvent *Event)
|
static bool MatchPattern(const char *Pattern, const char *Title, cString *Before = NULL, cString *Match = NULL, cString *After = NULL)
|
||||||
|
{
|
||||||
|
if (Title) {
|
||||||
|
bool AvoidDuplicates = startswith(Pattern, TIMERPATTERN_AVOID);
|
||||||
|
if (AvoidDuplicates)
|
||||||
|
Pattern++;
|
||||||
|
if (strcmp(Pattern, "*") == 0) {
|
||||||
|
if (Before)
|
||||||
|
*Before = "";
|
||||||
|
if (Match)
|
||||||
|
*Match = Title;
|
||||||
|
if (After)
|
||||||
|
*After = "";
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
bool AnchorBegin = startswith(Pattern, TIMERPATTERN_BEGIN);
|
||||||
|
if (AnchorBegin)
|
||||||
|
Pattern++;
|
||||||
|
bool AnchorEnd = endswith(Pattern, TIMERPATTERN_END);
|
||||||
|
cNullTerminate nt;
|
||||||
|
if (AnchorEnd)
|
||||||
|
nt.Set(const_cast<char *>(Pattern + strlen(Pattern) - 1));
|
||||||
|
if (AnchorBegin && AnchorEnd) {
|
||||||
|
if (strcmp(Title, Pattern) == 0) {
|
||||||
|
if (Before)
|
||||||
|
*Before = "";
|
||||||
|
if (Match)
|
||||||
|
*Match = Title;
|
||||||
|
if (After)
|
||||||
|
*After = "";
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (AnchorBegin) {
|
||||||
|
if (strstr(Title, Pattern) == Title) {
|
||||||
|
if (Before)
|
||||||
|
*Before = "";
|
||||||
|
if (Match)
|
||||||
|
*Match = Pattern;
|
||||||
|
if (After)
|
||||||
|
*After = cString(Title + strlen(Pattern));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (AnchorEnd) {
|
||||||
|
if (endswith(Title, Pattern)) {
|
||||||
|
if (Before)
|
||||||
|
*Before = cString(Title, Title + strlen(Title) - strlen(Pattern));
|
||||||
|
if (Match)
|
||||||
|
*Match = Pattern;
|
||||||
|
if (After)
|
||||||
|
*After = "";
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (const char *p = strstr(Title, Pattern)) {
|
||||||
|
if (Before)
|
||||||
|
*Before = cString(Title, p);
|
||||||
|
if (Match)
|
||||||
|
*Match = Pattern;
|
||||||
|
if (After)
|
||||||
|
*After = cString(p + strlen(Pattern));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static cString MakePatternFileName(const char *Pattern, const char *Title, const char *Episode, const char *File)
|
||||||
|
{
|
||||||
|
if (!Pattern || !Title || !File)
|
||||||
|
return NULL;
|
||||||
|
cString Before = "";
|
||||||
|
cString Match = "";
|
||||||
|
cString After = "";
|
||||||
|
if (MatchPattern(Pattern, Title, &Before, &Match, &After)) {
|
||||||
|
char *Result = strdup(File);
|
||||||
|
Result = strreplace(Result, TIMERMACRO_TITLE, Title);
|
||||||
|
Result = strreplace(Result, TIMERMACRO_EPISODE, Episode);
|
||||||
|
Result = strreplace(Result, TIMERMACRO_BEFORE, Before);
|
||||||
|
Result = strreplace(Result, TIMERMACRO_MATCH, Match);
|
||||||
|
Result = strreplace(Result, TIMERMACRO_AFTER, After);
|
||||||
|
return cString(Result, true);;
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
cTimer::cTimer(const cEvent *Event, const char *FileName, const cTimer *PatternTimer)
|
||||||
{
|
{
|
||||||
id = 0;
|
id = 0;
|
||||||
startTime = stopTime = 0;
|
startTime = stopTime = 0;
|
||||||
@ -89,12 +177,15 @@ cTimer::cTimer(const cEvent *Event)
|
|||||||
deferred = 0;
|
deferred = 0;
|
||||||
pending = inVpsMargin = false;
|
pending = inVpsMargin = false;
|
||||||
flags = tfActive;
|
flags = tfActive;
|
||||||
|
*pattern = 0;
|
||||||
*file = 0;
|
*file = 0;
|
||||||
aux = NULL;
|
aux = NULL;
|
||||||
remote = NULL;
|
remote = NULL;
|
||||||
event = NULL;
|
event = NULL;
|
||||||
|
if (!PatternTimer || PatternTimer->HasFlags(tfVps)) {
|
||||||
if (Event->Vps() && Setup.UseVps)
|
if (Event->Vps() && Setup.UseVps)
|
||||||
SetFlags(tfVps);
|
SetFlags(tfVps);
|
||||||
|
}
|
||||||
LOCK_CHANNELS_READ;
|
LOCK_CHANNELS_READ;
|
||||||
channel = Channels->GetByChannelID(Event->ChannelID(), true);
|
channel = Channels->GetByChannelID(Event->ChannelID(), true);
|
||||||
time_t tstart = (flags & tfVps) ? Event->Vps() : Event->StartTime();
|
time_t tstart = (flags & tfVps) ? Event->Vps() : Event->StartTime();
|
||||||
@ -112,11 +203,12 @@ cTimer::cTimer(const cEvent *Event)
|
|||||||
stop = time->tm_hour * 100 + time->tm_min;
|
stop = time->tm_hour * 100 + time->tm_min;
|
||||||
if (stop >= 2400)
|
if (stop >= 2400)
|
||||||
stop -= 2400;
|
stop -= 2400;
|
||||||
priority = Setup.DefaultPriority;
|
priority = PatternTimer ? PatternTimer->Priority() : Setup.DefaultPriority;
|
||||||
lifetime = Setup.DefaultLifetime;
|
lifetime = PatternTimer ? PatternTimer->Lifetime() : Setup.DefaultLifetime;
|
||||||
const char *Title = Event->Title();
|
if (!FileName)
|
||||||
if (!isempty(Title))
|
FileName = Event->Title();
|
||||||
Utf8Strn0Cpy(file, Event->Title(), sizeof(file));
|
if (!isempty(FileName))
|
||||||
|
Utf8Strn0Cpy(file, FileName, sizeof(file));
|
||||||
SetEvent(Event);
|
SetEvent(Event);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -156,6 +248,7 @@ cTimer& cTimer::operator= (const cTimer &Timer)
|
|||||||
stop = Timer.stop;
|
stop = Timer.stop;
|
||||||
priority = Timer.priority;
|
priority = Timer.priority;
|
||||||
lifetime = Timer.lifetime;
|
lifetime = Timer.lifetime;
|
||||||
|
strncpy(pattern, Timer.pattern, sizeof(pattern));
|
||||||
strncpy(file, Timer.file, sizeof(file));
|
strncpy(file, Timer.file, sizeof(file));
|
||||||
free(aux);
|
free(aux);
|
||||||
aux = Timer.aux ? strdup(Timer.aux) : NULL;
|
aux = Timer.aux ? strdup(Timer.aux) : NULL;
|
||||||
@ -178,20 +271,37 @@ int cTimer::Compare(const cListObject &ListObject) const
|
|||||||
int r = t1 - t2;
|
int r = t1 - t2;
|
||||||
if (r == 0)
|
if (r == 0)
|
||||||
r = ti->priority - priority;
|
r = ti->priority - priority;
|
||||||
|
if (IsPatternTimer() ^ ti->IsPatternTimer()) {
|
||||||
|
if (IsPatternTimer())
|
||||||
|
r = 1;
|
||||||
|
else
|
||||||
|
r = -1;
|
||||||
|
}
|
||||||
|
else if (IsPatternTimer() && ti->IsPatternTimer())
|
||||||
|
r = strcoll(Pattern(), ti->Pattern());
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cString cTimer::PatternAndFile(void) const
|
||||||
|
{
|
||||||
|
if (IsPatternTimer())
|
||||||
|
return cString::sprintf("{%s}%s", pattern, file);
|
||||||
|
return file;
|
||||||
|
}
|
||||||
|
|
||||||
cString cTimer::ToText(bool UseChannelID) const
|
cString cTimer::ToText(bool UseChannelID) const
|
||||||
{
|
{
|
||||||
|
strreplace(pattern, ':', '|');
|
||||||
strreplace(file, ':', '|');
|
strreplace(file, ':', '|');
|
||||||
cString buffer = cString::sprintf("%u:%s:%s:%04d:%04d:%d:%d:%s:%s", flags, UseChannelID ? *Channel()->GetChannelID().ToString() : *itoa(Channel()->Number()), *PrintDay(day, weekdays, true), start, stop, priority, lifetime, file, aux ? aux : "");
|
cString buffer = cString::sprintf("%u:%s:%s:%04d:%04d:%d:%d:%s:%s", flags, UseChannelID ? *Channel()->GetChannelID().ToString() : *itoa(Channel()->Number()), *PrintDay(day, weekdays, true), start, stop, priority, lifetime, *PatternAndFile(), aux ? aux : "");
|
||||||
|
strreplace(pattern, '|', ':');
|
||||||
strreplace(file, '|', ':');
|
strreplace(file, '|', ':');
|
||||||
return buffer;
|
return buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
cString cTimer::ToDescr(void) const
|
cString cTimer::ToDescr(void) const
|
||||||
{
|
{
|
||||||
return cString::sprintf("%d%s%s (%d %04d-%04d %s'%s')", Id(), remote ? "@" : "", remote ? remote : "", Channel()->Number(), start, stop, HasFlags(tfVps) ? "VPS " : "", file);
|
return cString::sprintf("%d%s%s (%d %04d-%04d %s'%s')", Id(), remote ? "@" : "", remote ? remote : "", Channel()->Number(), start, stop, HasFlags(tfVps) ? "VPS " : "", *PatternAndFile());
|
||||||
}
|
}
|
||||||
|
|
||||||
int cTimer::TimeToInt(int t)
|
int cTimer::TimeToInt(int t)
|
||||||
@ -332,7 +442,18 @@ bool cTimer::Parse(const char *s)
|
|||||||
}
|
}
|
||||||
//TODO add more plausibility checks
|
//TODO add more plausibility checks
|
||||||
result = ParseDay(daybuffer, day, weekdays);
|
result = ParseDay(daybuffer, day, weekdays);
|
||||||
Utf8Strn0Cpy(file, filebuffer, sizeof(file));
|
char *fb = filebuffer;
|
||||||
|
if (*fb == '{') {
|
||||||
|
if (char *p = strchr(fb, '}')) {
|
||||||
|
*p = 0;
|
||||||
|
Utf8Strn0Cpy(pattern, fb + 1, sizeof(pattern));
|
||||||
|
strreplace(pattern, '|', ':');
|
||||||
|
fb = p + 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
*pattern = 0;
|
||||||
|
Utf8Strn0Cpy(file, fb, sizeof(file));
|
||||||
strreplace(file, '|', ':');
|
strreplace(file, '|', ':');
|
||||||
LOCK_CHANNELS_READ;
|
LOCK_CHANNELS_READ;
|
||||||
if (isnumber(channelbuffer))
|
if (isnumber(channelbuffer))
|
||||||
@ -404,6 +525,11 @@ time_t cTimer::SetTime(time_t t, int SecondsFromMidnight)
|
|||||||
return mktime(&tm);
|
return mktime(&tm);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cTimer::SetPattern(const char *Pattern)
|
||||||
|
{
|
||||||
|
Utf8Strn0Cpy(pattern, Pattern, sizeof(pattern));
|
||||||
|
}
|
||||||
|
|
||||||
void cTimer::SetFile(const char *File)
|
void cTimer::SetFile(const char *File)
|
||||||
{
|
{
|
||||||
if (!isempty(File))
|
if (!isempty(File))
|
||||||
@ -451,6 +577,9 @@ bool cTimer::Matches(time_t t, bool Directly, int Margin) const
|
|||||||
day = 0;
|
day = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (IsPatternTimer())
|
||||||
|
return false; // we only need to have start/stopTime initialized
|
||||||
|
|
||||||
if (t < deferred)
|
if (t < deferred)
|
||||||
return false;
|
return false;
|
||||||
deferred = 0;
|
deferred = 0;
|
||||||
@ -483,6 +612,21 @@ eTimerMatch cTimer::Matches(const cEvent *Event, int *Overlap) const
|
|||||||
// gets 200 added to the FULLMATCH.
|
// gets 200 added to the FULLMATCH.
|
||||||
if (channel->GetChannelID() == Event->ChannelID()) {
|
if (channel->GetChannelID() == Event->ChannelID()) {
|
||||||
bool UseVps = HasFlags(tfVps) && Event->Vps();
|
bool UseVps = HasFlags(tfVps) && Event->Vps();
|
||||||
|
if (IsPatternTimer()) {
|
||||||
|
if (startswith(Pattern(), TIMERPATTERN_AVOID)) {
|
||||||
|
cString FileName = MakePatternFileName(Pattern(), Event->Title(), Event->ShortText(), File());
|
||||||
|
if (*FileName) {
|
||||||
|
const char *p = strgetlast(*FileName, FOLDERDELIMCHAR);
|
||||||
|
if (DoneRecordingsPattern.Contains(p))
|
||||||
|
return tmNone;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return tmNone;
|
||||||
|
}
|
||||||
|
else if (!MatchPattern(Pattern(), Event->Title()))
|
||||||
|
return tmNone;
|
||||||
|
UseVps = false;
|
||||||
|
}
|
||||||
Matches(UseVps ? Event->Vps() : Event->StartTime(), true);
|
Matches(UseVps ? Event->Vps() : Event->StartTime(), true);
|
||||||
int overlap = 0;
|
int overlap = 0;
|
||||||
if (UseVps) {
|
if (UseVps) {
|
||||||
@ -499,8 +643,11 @@ eTimerMatch cTimer::Matches(const cEvent *Event, int *Overlap) const
|
|||||||
overlap = FULLMATCH;
|
overlap = FULLMATCH;
|
||||||
else if (stopTime <= Event->StartTime() || Event->EndTime() <= startTime)
|
else if (stopTime <= Event->StartTime() || Event->EndTime() <= startTime)
|
||||||
overlap = 0;
|
overlap = 0;
|
||||||
else
|
else {
|
||||||
overlap = (min(stopTime, Event->EndTime()) - max(startTime, Event->StartTime())) * FULLMATCH / max(Event->Duration(), 1);
|
overlap = (min(stopTime, Event->EndTime()) - max(startTime, Event->StartTime())) * FULLMATCH / max(Event->Duration(), 1);
|
||||||
|
if (IsPatternTimer() && overlap > 0)
|
||||||
|
overlap = FULLMATCH;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
startTime = stopTime = 0;
|
startTime = stopTime = 0;
|
||||||
if (Overlap)
|
if (Overlap)
|
||||||
@ -542,8 +689,60 @@ void cTimer::SetId(int Id)
|
|||||||
id = Id;
|
id = Id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void cTimer::SpawnPatternTimer(const cEvent *Event, cTimers *Timers)
|
||||||
|
{
|
||||||
|
cString FileName = MakePatternFileName(Pattern(), Event->Title(), Event->ShortText(), File());
|
||||||
|
isyslog("spawning timer %s for event %s", *ToDescr(), *Event->ToDescr());
|
||||||
|
cTimer *t = new cTimer(Event, FileName, this);
|
||||||
|
t->SetFlags(tfSpawned);
|
||||||
|
if (startswith(Pattern(), TIMERPATTERN_AVOID))
|
||||||
|
t->SetFlags(tfAvoid);
|
||||||
|
Timers->Add(t);
|
||||||
|
HandleRemoteTimerModifications(t);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cTimer::SpawnPatternTimers(const cSchedules *Schedules, cTimers *Timers)
|
||||||
|
{
|
||||||
|
bool TimersSpawned = false;
|
||||||
|
const cSchedule *Schedule = Schedules->GetSchedule(Channel());
|
||||||
|
if (Schedule && Schedule->Events()->First()) {
|
||||||
|
if (Schedule->Modified(scheduleState)) {
|
||||||
|
time_t Now = time(NULL);
|
||||||
|
for (const cEvent *e = Schedule->Events()->First(); e; e = Schedule->Events()->Next(e)) {
|
||||||
|
if (Matches(e) != tmNone) {
|
||||||
|
bool CheckThis = false;
|
||||||
|
bool CheckNext = false;
|
||||||
|
if (e->HasTimer()) // a matching event that already has a timer
|
||||||
|
CheckNext = true;
|
||||||
|
else if (e->EndTime() > Now) { // only look at events that have not yet ended
|
||||||
|
CheckThis = true;
|
||||||
|
CheckNext = true;
|
||||||
|
}
|
||||||
|
if (CheckThis) {
|
||||||
|
SpawnPatternTimer(e, Timers);
|
||||||
|
TimersSpawned = true;
|
||||||
|
}
|
||||||
|
if (CheckNext) {
|
||||||
|
// We also check the event immediately following this one:
|
||||||
|
e = Schedule->Events()->Next(e);
|
||||||
|
if (e && !e->HasTimer() && Matches(e) != tmNone) {
|
||||||
|
SpawnPatternTimer(e, Timers);
|
||||||
|
TimersSpawned = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (CheckThis || CheckNext)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return TimersSpawned;
|
||||||
|
}
|
||||||
|
|
||||||
bool cTimer::SetEventFromSchedule(const cSchedules *Schedules)
|
bool cTimer::SetEventFromSchedule(const cSchedules *Schedules)
|
||||||
{
|
{
|
||||||
|
if (IsPatternTimer())
|
||||||
|
return SetEvent(NULL);
|
||||||
const cSchedule *Schedule = Schedules->GetSchedule(Channel());
|
const cSchedule *Schedule = Schedules->GetSchedule(Channel());
|
||||||
if (Schedule && Schedule->Events()->First()) {
|
if (Schedule && Schedule->Events()->First()) {
|
||||||
if (Schedule->Modified(scheduleState)) {
|
if (Schedule->Modified(scheduleState)) {
|
||||||
@ -707,7 +906,7 @@ void cTimer::Skip(void)
|
|||||||
|
|
||||||
void cTimer::OnOff(void)
|
void cTimer::OnOff(void)
|
||||||
{
|
{
|
||||||
if (IsSingleEvent())
|
if (IsSingleEvent() || IsPatternTimer())
|
||||||
InvFlags(tfActive);
|
InvFlags(tfActive);
|
||||||
else if (day) {
|
else if (day) {
|
||||||
day = 0;
|
day = 0;
|
||||||
@ -718,6 +917,8 @@ void cTimer::OnOff(void)
|
|||||||
else
|
else
|
||||||
SetFlags(tfActive);
|
SetFlags(tfActive);
|
||||||
SetEvent(NULL);
|
SetEvent(NULL);
|
||||||
|
if (HasFlags(tfActive))
|
||||||
|
scheduleState = -1; // have pattern timers spawn if necessary
|
||||||
Matches(); // refresh start and end time
|
Matches(); // refresh start and end time
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -831,7 +1032,7 @@ const cTimer *cTimers::GetNextActiveTimer(void) const
|
|||||||
{
|
{
|
||||||
const cTimer *t0 = NULL;
|
const cTimer *t0 = NULL;
|
||||||
for (const cTimer *ti = First(); ti; ti = Next(ti)) {
|
for (const cTimer *ti = First(); ti; ti = Next(ti)) {
|
||||||
if (!ti->Remote()) {
|
if (!ti->Remote() && !ti->IsPatternTimer()) {
|
||||||
ti->Matches();
|
ti->Matches();
|
||||||
if ((ti->HasFlags(tfActive)) && (!t0 || ti->StopTime() > time(NULL) && ti->Compare(*t0) < 0))
|
if ((ti->HasFlags(tfActive)) && (!t0 || ti->StopTime() > time(NULL) && ti->Compare(*t0) < 0))
|
||||||
t0 = ti;
|
t0 = ti;
|
||||||
@ -882,8 +1083,22 @@ const cTimer *cTimers::UsesChannel(const cChannel *Channel) const
|
|||||||
bool cTimers::SetEvents(const cSchedules *Schedules)
|
bool cTimers::SetEvents(const cSchedules *Schedules)
|
||||||
{
|
{
|
||||||
bool TimersModified = false;
|
bool TimersModified = false;
|
||||||
for (cTimer *ti = First(); ti; ti = Next(ti))
|
for (cTimer *ti = First(); ti; ti = Next(ti)) {
|
||||||
|
if (!ti->IsPatternTimer())
|
||||||
TimersModified |= ti->SetEventFromSchedule(Schedules);
|
TimersModified |= ti->SetEventFromSchedule(Schedules);
|
||||||
|
}
|
||||||
|
return TimersModified;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool cTimers::SpawnPatternTimers(const cSchedules *Schedules)
|
||||||
|
{
|
||||||
|
bool TimersModified = false;
|
||||||
|
for (cTimer *ti = First(); ti; ti = Next(ti)) {
|
||||||
|
if (ti->IsPatternTimer() && ti->Local()) {
|
||||||
|
if (ti->HasFlags(tfActive))
|
||||||
|
TimersModified |= ti->SpawnPatternTimers(Schedules, this);
|
||||||
|
}
|
||||||
|
}
|
||||||
return TimersModified;
|
return TimersModified;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -896,6 +1111,7 @@ bool cTimers::DeleteExpired(void)
|
|||||||
while (ti) {
|
while (ti) {
|
||||||
cTimer *next = Next(ti);
|
cTimer *next = Next(ti);
|
||||||
if (!ti->Remote() && ti->Expired()) {
|
if (!ti->Remote() && ti->Expired()) {
|
||||||
|
ti->SetEvent(NULL); // Del() doesn't call ~cTimer() right away, so this is necessary here
|
||||||
isyslog("deleting timer %s", *ti->ToDescr());
|
isyslog("deleting timer %s", *ti->ToDescr());
|
||||||
Del(ti);
|
Del(ti);
|
||||||
TimersModified = true;
|
TimersModified = true;
|
||||||
|
16
timers.h
16
timers.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: timers.h 4.12 2019/05/23 09:47:19 kls Exp $
|
* $Id: timers.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __TIMERS_H
|
#ifndef __TIMERS_H
|
||||||
@ -20,10 +20,14 @@ enum eTimerFlags { tfNone = 0x0000,
|
|||||||
tfInstant = 0x0002,
|
tfInstant = 0x0002,
|
||||||
tfVps = 0x0004,
|
tfVps = 0x0004,
|
||||||
tfRecording = 0x0008,
|
tfRecording = 0x0008,
|
||||||
|
tfSpawned = 0x0010,
|
||||||
|
tfAvoid = 0x0020,
|
||||||
tfAll = 0xFFFF,
|
tfAll = 0xFFFF,
|
||||||
};
|
};
|
||||||
enum eTimerMatch { tmNone, tmPartial, tmFull };
|
enum eTimerMatch { tmNone, tmPartial, tmFull };
|
||||||
|
|
||||||
|
class cTimers;
|
||||||
|
|
||||||
class cTimer : public cListObject {
|
class cTimer : public cListObject {
|
||||||
friend class cMenuEditTimer;
|
friend class cMenuEditTimer;
|
||||||
private:
|
private:
|
||||||
@ -40,13 +44,14 @@ private:
|
|||||||
int stop;
|
int stop;
|
||||||
int priority;
|
int priority;
|
||||||
int lifetime;
|
int lifetime;
|
||||||
|
mutable char pattern[NAME_MAX * 2 + 1]; // same size as 'file', to be able to initially fill 'pattern' with 'file' in the 'Edit timer' menu
|
||||||
mutable char file[NAME_MAX * 2 + 1]; // *2 to be able to hold 'title' and 'episode', which can each be up to 255 characters long
|
mutable char file[NAME_MAX * 2 + 1]; // *2 to be able to hold 'title' and 'episode', which can each be up to 255 characters long
|
||||||
char *aux;
|
char *aux;
|
||||||
char *remote;
|
char *remote;
|
||||||
const cEvent *event;
|
const cEvent *event;
|
||||||
public:
|
public:
|
||||||
cTimer(bool Instant = false, bool Pause = false, const cChannel *Channel = NULL);
|
cTimer(bool Instant = false, bool Pause = false, const cChannel *Channel = NULL);
|
||||||
cTimer(const cEvent *Event);
|
cTimer(const cEvent *Event, const char *FileName = NULL, const cTimer *PatternTimer = NULL);
|
||||||
cTimer(const cTimer &Timer);
|
cTimer(const cTimer &Timer);
|
||||||
virtual ~cTimer();
|
virtual ~cTimer();
|
||||||
cTimer& operator= (const cTimer &Timer);
|
cTimer& operator= (const cTimer &Timer);
|
||||||
@ -63,12 +68,14 @@ public:
|
|||||||
int Stop(void) const { return stop; }
|
int Stop(void) const { return stop; }
|
||||||
int Priority(void) const { return priority; }
|
int Priority(void) const { return priority; }
|
||||||
int Lifetime(void) const { return lifetime; }
|
int Lifetime(void) const { return lifetime; }
|
||||||
|
const char *Pattern(void) const { return pattern; }
|
||||||
const char *File(void) const { return file; }
|
const char *File(void) const { return file; }
|
||||||
time_t FirstDay(void) const { return weekdays ? day : 0; }
|
time_t FirstDay(void) const { return weekdays ? day : 0; }
|
||||||
const char *Aux(void) const { return aux; }
|
const char *Aux(void) const { return aux; }
|
||||||
const char *Remote(void) const { return remote; }
|
const char *Remote(void) const { return remote; }
|
||||||
bool Local(void) const { return !remote; } // convenience
|
bool Local(void) const { return !remote; } // convenience
|
||||||
time_t Deferred(void) const { return deferred; }
|
time_t Deferred(void) const { return deferred; }
|
||||||
|
cString PatternAndFile(void) const;
|
||||||
cString ToText(bool UseChannelID = false) const;
|
cString ToText(bool UseChannelID = false) const;
|
||||||
cString ToDescr(void) const;
|
cString ToDescr(void) const;
|
||||||
const cEvent *Event(void) const { return event; }
|
const cEvent *Event(void) const { return event; }
|
||||||
@ -80,13 +87,17 @@ public:
|
|||||||
bool DayMatches(time_t t) const;
|
bool DayMatches(time_t t) const;
|
||||||
static time_t IncDay(time_t t, int Days);
|
static time_t IncDay(time_t t, int Days);
|
||||||
static time_t SetTime(time_t t, int SecondsFromMidnight);
|
static time_t SetTime(time_t t, int SecondsFromMidnight);
|
||||||
|
void SetPattern(const char *Pattern);
|
||||||
void SetFile(const char *File);
|
void SetFile(const char *File);
|
||||||
|
bool IsPatternTimer(void) const { return *pattern; }
|
||||||
bool Matches(time_t t = 0, bool Directly = false, int Margin = 0) const;
|
bool Matches(time_t t = 0, bool Directly = false, int Margin = 0) const;
|
||||||
eTimerMatch Matches(const cEvent *Event, int *Overlap = NULL) const;
|
eTimerMatch Matches(const cEvent *Event, int *Overlap = NULL) const;
|
||||||
bool Expired(void) const;
|
bool Expired(void) const;
|
||||||
time_t StartTime(void) const;
|
time_t StartTime(void) const;
|
||||||
time_t StopTime(void) const;
|
time_t StopTime(void) const;
|
||||||
void SetId(int Id);
|
void SetId(int Id);
|
||||||
|
void SpawnPatternTimer(const cEvent *Event, cTimers *Timers);
|
||||||
|
bool SpawnPatternTimers(const cSchedules *Schedules, cTimers *Timers);
|
||||||
bool SetEventFromSchedule(const cSchedules *Schedules);
|
bool SetEventFromSchedule(const cSchedules *Schedules);
|
||||||
bool SetEvent(const cEvent *Event);
|
bool SetEvent(const cEvent *Event);
|
||||||
void SetRecording(bool Recording);
|
void SetRecording(bool Recording);
|
||||||
@ -182,6 +193,7 @@ public:
|
|||||||
const cTimer *GetNextActiveTimer(void) const;
|
const cTimer *GetNextActiveTimer(void) const;
|
||||||
const cTimer *UsesChannel(const cChannel *Channel) const;
|
const cTimer *UsesChannel(const cChannel *Channel) const;
|
||||||
bool SetEvents(const cSchedules *Schedules);
|
bool SetEvents(const cSchedules *Schedules);
|
||||||
|
bool SpawnPatternTimers(const cSchedules *Schedules);
|
||||||
bool DeleteExpired(void);
|
bool DeleteExpired(void);
|
||||||
void Add(cTimer *Timer, cTimer *After = NULL);
|
void Add(cTimer *Timer, cTimer *After = NULL);
|
||||||
void Ins(cTimer *Timer, cTimer *Before = NULL);
|
void Ins(cTimer *Timer, cTimer *Before = NULL);
|
||||||
|
8
tools.c
8
tools.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: tools.c 4.13 2020/11/22 13:32:05 kls Exp $
|
* $Id: tools.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "tools.h"
|
#include "tools.h"
|
||||||
@ -198,6 +198,12 @@ int strcountchr(const char *s, char c)
|
|||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char *strgetlast(const char *s, char c)
|
||||||
|
{
|
||||||
|
const char *p = strrchr(s, c);
|
||||||
|
return p ? p + 1 : s;
|
||||||
|
}
|
||||||
|
|
||||||
char *stripspace(char *s)
|
char *stripspace(char *s)
|
||||||
{
|
{
|
||||||
if (s && *s) {
|
if (s && *s) {
|
||||||
|
30
tools.h
30
tools.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: tools.h 4.18 2020/09/16 13:48:33 kls Exp $
|
* $Id: tools.h 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __TOOLS_H
|
#ifndef __TOOLS_H
|
||||||
@ -193,6 +193,33 @@ public:
|
|||||||
static cString vsprintf(const char *fmt, va_list &ap);
|
static cString vsprintf(const char *fmt, va_list &ap);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class cNullTerminate {
|
||||||
|
private:
|
||||||
|
char *p;
|
||||||
|
char c;
|
||||||
|
public:
|
||||||
|
cNullTerminate(void) {
|
||||||
|
p = NULL;
|
||||||
|
c = 0;
|
||||||
|
}
|
||||||
|
cNullTerminate(char *s) {
|
||||||
|
Set(s);
|
||||||
|
}
|
||||||
|
~cNullTerminate() {
|
||||||
|
if (p)
|
||||||
|
*p = c;
|
||||||
|
}
|
||||||
|
void Set(char *s) {
|
||||||
|
if (s) {
|
||||||
|
p = s;
|
||||||
|
c = *s;
|
||||||
|
*s = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
p = NULL;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
ssize_t safe_read(int filedes, void *buffer, size_t size);
|
ssize_t safe_read(int filedes, void *buffer, size_t size);
|
||||||
ssize_t safe_write(int filedes, const void *buffer, size_t size);
|
ssize_t safe_write(int filedes, const void *buffer, size_t size);
|
||||||
void writechar(int filedes, char c);
|
void writechar(int filedes, char c);
|
||||||
@ -206,6 +233,7 @@ 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!
|
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.
|
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'.
|
int strcountchr(const char *s, char c); ///< returns the number of occurrences of 'c' in 's'.
|
||||||
|
const char *strgetlast(const char *s, char c); // returns the part of 's' after the last occurrence of 'c', or 's' if there is no 'c'.
|
||||||
inline char *skipspace(const char *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
|
if ((uchar)*s > ' ') // most strings don't have any leading space, so handle this case as fast as possible
|
||||||
|
7
vdr.1
7
vdr.1
@ -8,7 +8,7 @@
|
|||||||
.\" License as specified in the file COPYING that comes with the
|
.\" License as specified in the file COPYING that comes with the
|
||||||
.\" vdr distribution.
|
.\" vdr distribution.
|
||||||
.\"
|
.\"
|
||||||
.\" $Id: vdr.1 4.4 2018/04/10 13:58:06 kls Exp $
|
.\" $Id: vdr.1 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
.\"
|
.\"
|
||||||
.TH vdr 1 "15 Apr 2018" "2.4" "Video Disk Recorder"
|
.TH vdr 1 "15 Apr 2018" "2.4" "Video Disk Recorder"
|
||||||
.SH NAME
|
.SH NAME
|
||||||
@ -305,6 +305,11 @@ The actual data files of a recording.
|
|||||||
Contains all current EPG data. Can be used for external processing and will
|
Contains all current EPG data. Can be used for external processing and will
|
||||||
also be read at program startup to have the full EPG data available immediately.
|
also be read at program startup to have the full EPG data available immediately.
|
||||||
.TP
|
.TP
|
||||||
|
.I donerecs.data
|
||||||
|
Contains the names of recordings that have been done by pattern timers with '@'
|
||||||
|
as the first character of the pattern. File names are appended to this file after
|
||||||
|
a recording has finished, and the entire file is read upon startup of VDR.
|
||||||
|
.TP
|
||||||
.I .update
|
.I .update
|
||||||
If this file is present in the video directory, its last modification time will
|
If this file is present in the video directory, its last modification time will
|
||||||
be used to trigger an update of the list of recordings in the "Recordings" menu.
|
be used to trigger an update of the list of recordings in the "Recordings" menu.
|
||||||
|
43
vdr.5
43
vdr.5
@ -8,7 +8,7 @@
|
|||||||
.\" License as specified in the file COPYING that comes with the
|
.\" License as specified in the file COPYING that comes with the
|
||||||
.\" vdr distribution.
|
.\" vdr distribution.
|
||||||
.\"
|
.\"
|
||||||
.\" $Id: vdr.5 4.8 2018/04/10 13:58:16 kls Exp $
|
.\" $Id: vdr.5 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
.\"
|
.\"
|
||||||
.TH vdr 5 "15 Apr 2018" "2.4" "Video Disk Recorder Files"
|
.TH vdr 5 "15 Apr 2018" "2.4" "Video Disk Recorder Files"
|
||||||
.SH NAME
|
.SH NAME
|
||||||
@ -317,10 +317,12 @@ The individual bits in this field have the following meaning:
|
|||||||
.TS
|
.TS
|
||||||
tab (@);
|
tab (@);
|
||||||
l l.
|
l l.
|
||||||
\fB1\fR@the timer is active (and will record if it hits)
|
\fB0x0001\fR@the timer is active (and will record if it hits)
|
||||||
\fB2\fR@this is an instant recording timer
|
\fB0x0002\fR@this is an instant recording timer
|
||||||
\fB4\fR@this timer uses VPS
|
\fB0x0004\fR@this timer uses VPS
|
||||||
\fB8\fR@this timer is currently recording (may only be up-to-date with SVDRP)
|
\fB0x0008\fR@this timer is currently recording (may only be up-to-date with SVDRP)
|
||||||
|
\fB0x0010\fR@this timer was spawned from a pattern timer
|
||||||
|
\fB0x0020\fR@this timer will store the recording's name in donerecs.data
|
||||||
.TE
|
.TE
|
||||||
|
|
||||||
All other bits are reserved for future use.
|
All other bits are reserved for future use.
|
||||||
@ -425,6 +427,37 @@ by the title and episode information from the EPG data at the time of
|
|||||||
recording (if that data is available). If at the time of recording either
|
recording (if that data is available). If at the time of recording either
|
||||||
of these cannot be determined, \fBTITLE\fR will default to the channel name, and
|
of these cannot be determined, \fBTITLE\fR will default to the channel name, and
|
||||||
\fBEPISODE\fR will default to a blank.
|
\fBEPISODE\fR will default to a blank.
|
||||||
|
|
||||||
|
The file name can be prepended with a pattern, enclosed in curly braces, as in
|
||||||
|
|
||||||
|
{Columbo}Movies~TITLE
|
||||||
|
|
||||||
|
which makes this a "pattern timer". A pattern timer records every event on the
|
||||||
|
given channel where the title contains the pattern (case sensitive).
|
||||||
|
The following special characters can be used in a pattern:
|
||||||
|
.TS
|
||||||
|
tab (;);
|
||||||
|
l l.
|
||||||
|
\fB^\fR;anchor to the beginning of the event's title
|
||||||
|
\fB$\fR;anchor to the end of the event's title
|
||||||
|
\fB*\fR;match every event
|
||||||
|
\fB@\fR;avoid duplicate recordings
|
||||||
|
.TE
|
||||||
|
|
||||||
|
If \fB@\fR is used, it must be the very first character of the pattern.
|
||||||
|
If both \fB@\fR and \fB^\fR are used, \fB@\fR must come first.
|
||||||
|
If \fB*\fR is used, it must be the only character in the pattern and may only be
|
||||||
|
prepended with \fB@\fR.
|
||||||
|
|
||||||
|
In addition to TITLE and EPISODE you can use the following macros to compose the file
|
||||||
|
name (the curly braces are part of the macros):
|
||||||
|
.TS
|
||||||
|
tab (@);
|
||||||
|
l l.
|
||||||
|
{<}@everything before the matching pattern
|
||||||
|
{>}@everything after the matching pattern
|
||||||
|
{=}@the matching pattern itself (just for completeness)
|
||||||
|
.TE
|
||||||
.TP
|
.TP
|
||||||
.B Auxiliary data
|
.B Auxiliary data
|
||||||
An arbitrary string that can be used by external applications to store any
|
An arbitrary string that can be used by external applications to store any
|
||||||
|
10
vdr.c
10
vdr.c
@ -22,7 +22,7 @@
|
|||||||
*
|
*
|
||||||
* The project's page is at http://www.tvdr.de
|
* The project's page is at http://www.tvdr.de
|
||||||
*
|
*
|
||||||
* $Id: vdr.c 4.34 2020/11/20 13:49:58 kls Exp $
|
* $Id: vdr.c 5.1 2020/12/26 15:49:01 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <getopt.h>
|
#include <getopt.h>
|
||||||
@ -784,6 +784,7 @@ int main(int argc, char *argv[])
|
|||||||
KeyMacros.Load(AddDirectory(ConfigDirectory, "keymacros.conf"), true);
|
KeyMacros.Load(AddDirectory(ConfigDirectory, "keymacros.conf"), true);
|
||||||
Folders.Load(AddDirectory(ConfigDirectory, "folders.conf"));
|
Folders.Load(AddDirectory(ConfigDirectory, "folders.conf"));
|
||||||
CamResponsesLoad(AddDirectory(ConfigDirectory, "camresponses.conf"), true);
|
CamResponsesLoad(AddDirectory(ConfigDirectory, "camresponses.conf"), true);
|
||||||
|
DoneRecordingsPattern.Load(AddDirectory(CacheDirectory, "donerecs.data"));
|
||||||
|
|
||||||
if (!*cFont::GetFontFileName(Setup.FontOsd)) {
|
if (!*cFont::GetFontFileName(Setup.FontOsd)) {
|
||||||
const char *msg = "no fonts available - OSD will not show any text!";
|
const char *msg = "no fonts available - OSD will not show any text!";
|
||||||
@ -1098,15 +1099,20 @@ int main(int argc, char *argv[])
|
|||||||
static cStateKey TimersStateKey;
|
static cStateKey TimersStateKey;
|
||||||
cTimers *Timers = cTimers::GetTimersWrite(TimersStateKey);
|
cTimers *Timers = cTimers::GetTimersWrite(TimersStateKey);
|
||||||
{
|
{
|
||||||
|
LOCK_CHANNELS_READ; // Channels are needed for spawning pattern timers!
|
||||||
// Assign events to timers:
|
// Assign events to timers:
|
||||||
static cStateKey SchedulesStateKey;
|
static cStateKey SchedulesStateKey;
|
||||||
if (TimersStateKey.StateChanged())
|
if (TimersStateKey.StateChanged())
|
||||||
SchedulesStateKey.Reset(); // we assign events if either the Timers or the Schedules have changed
|
SchedulesStateKey.Reset(); // we assign events if either the Timers or the Schedules have changed
|
||||||
bool TimersModified = false;
|
bool TimersModified = false;
|
||||||
if (const cSchedules *Schedules = cSchedules::GetSchedulesRead(SchedulesStateKey)) {
|
if (const cSchedules *Schedules = cSchedules::GetSchedulesRead(SchedulesStateKey)) {
|
||||||
Timers->SetSyncStateKey(StateKeySVDRPRemoteTimersPoll);
|
Timers->SetSyncStateKey(StateKeySVDRPRemoteTimersPoll); // setting events shall not trigger a remote timer poll...
|
||||||
if (Timers->SetEvents(Schedules))
|
if (Timers->SetEvents(Schedules))
|
||||||
TimersModified = true;
|
TimersModified = true;
|
||||||
|
if (Timers->SpawnPatternTimers(Schedules)) {
|
||||||
|
StateKeySVDRPRemoteTimersPoll.Reset(); // ...but spawning new timers must!
|
||||||
|
TimersModified = true;
|
||||||
|
}
|
||||||
SchedulesStateKey.Remove();
|
SchedulesStateKey.Remove();
|
||||||
}
|
}
|
||||||
TimersStateKey.Remove(TimersModified); // we need to remove the key here, so that syncing StateKeySVDRPRemoteTimersPoll takes effect!
|
TimersStateKey.Remove(TimersModified); // we need to remove the key here, so that syncing StateKeySVDRPRemoteTimersPoll takes effect!
|
||||||
|
Loading…
Reference in New Issue
Block a user