Skip to content

Commit

Permalink
Merge pull request #330 from phunkyfish/recordings-paths
Browse files Browse the repository at this point in the history
Recordings paths
  • Loading branch information
phunkyfish authored Feb 28, 2021
2 parents 00bc960 + 7d10596 commit 848a96f
Show file tree
Hide file tree
Showing 13 changed files with 172 additions and 53 deletions.
10 changes: 6 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -203,10 +203,11 @@ The following configuration is available on the Recordings tab of the addon sett
* **Share last played across**: The options are:
- `Kodi instances` - Only use the value in kodi and will not affect last played on the E2 device.
- `Kodi/E2 instances` - Use the value across kodi and the E2 device so they stay in sync. Last played will be synced with the E2 device once every 5-10 minutes per recording if the PVR menus are in use. Note that only a single kodi instance is required to have this option enabled.
* **Recording folder on receiver**: Per default the addon does not specify the recording folder in newly created timers, so the default set in the set-top box will be used. If you want to specify a different folder (i.e. because you want all recordings scheduled via Kodi to be stored in a separate folder), then you need to set this option.
* **Use only the DVB boxes' current recording path**: If this option is not set the addon will fetch all available recordings from all configured paths from the set-top box. If this option is set then it will only list recordings that are stored within the "current recording path" on the set-top box.
* **Keep folder structure for records**: If enabled do not specify a recording folder, when disabled (defaut), check if the recording is in it's own folder or in the root of the recording path.
* **Use recursive listing for recording locations**By default only the root of the location will be used to list recordings. When enabled the contents of child folders will be included.
* **Group recordings into folders by title**: Create a virtual structure grouping recordings with the same name into folders. Will be applied to all recordings unless keeping the folder structure on the backend. In that case it will only be applied to the recordings in the root of each recording location.
* **Keep folder structure for recordings**: If enabled use the real path from the backend to dictate the folder structure.
* **Omit location path from recording directory**: When using the folder structure from the backend omit the location path from the directory. Useful as it can remove the need to traverse unused folders each time recordings are accessed.
* **Use recursive listing for recording locations**: By default only the root of the location will be used to list recordings. When enabled the contents of child folders will be included.
* **Only use current recording path from backend**: If this option is not set the addon will fetch all available recordings from all configured paths from the set-top box. If this option is set then it will only list recordings that are stored within the "current recording path" on the set-top box.
* **Enable EDLs support**: EDLs are used to define commericals etc. in recordings. If a tool like [Comskip]() is used to generate EDL files enabling this will allow Kodi PVR to use them. E.g. if there is a file called ```my recording.ts``` the EDL file should be call ```my recording.edl```. Note: enabling this setting has no effect if the files are not present.
* **EDL start time padding**: Padding to use at an EDL stop. I.e. use a negative number to start the cut earlier and positive to start the cut later. Default 0.
* **EDL stop time padding**: Padding to use at an EDL stop. I.e. use a negative number to stop the cut earlier and positive to stop the cut later. Default 0.
Expand Down Expand Up @@ -245,6 +246,7 @@ The following are the settings in the Timers tab:
* **Enable generate repeat timers**: Repeat timers will display as timer rules. Enabling this will make Kodi generate regular timers to match the repeat timer rules so the UI can show what's scheduled and currently recording for each repeat timer.
* **Number of repeat timers to generate**: The number of Kodi PVR timers to generate.
* **Automatic timerlist cleanup**: If this option is set then the addon will send the command to delete completed timers from the set-top box after each update interval.
* **New timer default recording folder**: Per default the addon does not specify the recording folder in newly created timers, so the default set in the set-top box will be used. If you want to specify a different folder (i.e. because you want all recordings scheduled via Kodi to be stored in a separate folder), then you need to set this option.
* **Enable autotimers**: When this is enabled there are some settings required on the set-top box to enable linking of AutoTimers (Timer Rules) to Timers in the Kodi UI. The addon attempts to set these automatically on boot. To set manually on the set-top box enable the following options (note that this feature supports OpenWebIf 1.3.x and higher):
1. Hit `Menu` on the remote and go to `Timers->AutoTimers`
2. Hit `Menu` again and then select `6 Setup`
Expand Down
11 changes: 9 additions & 2 deletions pvr.vuplus/addon.xml.in
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<addon
id="pvr.vuplus"
version="7.3.3"
version="7.4.0"
name="Enigma2 Client"
provider-name="Joerg Dembski and Ross Nicholson">
<requires>@ADDON_DEPENDS@
<import addon="inputstream.ffmpegdirect" minversion="1.18.0" optional="true"/>
<import addon="inputstream.ffmpegdirect" minversion="1.19.0"/>
</requires>
<extension
point="kodi.pvrclient"
Expand Down Expand Up @@ -183,6 +183,13 @@
<icon>icon.png</icon>
</assets>
<news>
v7.4.0
- Added: Add setting to omit recording location base dir from recording path
- Added: Correctly store the directory of a recording from the backend
- Update: Move new timer recording path to timer settings and refactor other settings
- Added: Split keep recordings folders into keep structure and group by title - this allows combining both options instead of one or the other
- Update: Make ffmpegdirect a hard dependency

v7.3.3
- Update: Readme - update description for Kodi 19 and add table of contents

Expand Down
7 changes: 7 additions & 0 deletions pvr.vuplus/changelog.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,10 @@
v7.4.0
- Added: Add setting to omit recording location base dir from recording path
- Added: Correctly store the directory of a recording from the backend
- Update: Move new timer recording path to timer settings and refactor other settings
- Added: Split keep recordings folders into keep structure and group by title - this allows combining both options instead of one or the other
- Update: Make ffmpegdirect a hard dependency

v7.3.3
- Update: Readme - update description for Kodi 19 and add table of contents

Expand Down
50 changes: 39 additions & 11 deletions pvr.vuplus/resources/language/resource.language.en_gb/strings.po
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ msgstr ""

#. label: Recordings - onlycurrent
msgctxt "#30017"
msgid "Use only the DVB boxes' current recording path"
msgid "Only use current recording path from backend"
msgstr ""

#. label-category: general
Expand All @@ -128,9 +128,9 @@ msgctxt "#30022"
msgid "Use recursive listing for recording locations"
msgstr ""

#. label: Recordings - recordingpath
#. label: Timers - recordingpath
msgctxt "#30023"
msgid "Recording folder on the receiver"
msgid "New timer default recording folder"
msgstr ""

#. label: Advanced - powerstatemode
Expand Down Expand Up @@ -163,9 +163,9 @@ msgctxt "#30029"
msgid "Enable automatic configuration for live streams"
msgstr ""

#. label: Reordings - keepfolders
#. label: Recordings - keepfolders
msgctxt "#30030"
msgid "Keep folder structure for records"
msgid "Keep folder structure for recordings"
msgstr ""

#. label-group: EPG - Seasons and Episodes
Expand Down Expand Up @@ -441,7 +441,15 @@ msgctxt "#30083"
msgid "addon error"
msgstr ""

#empty strings from id 30084 to 30085
#. label: Recordings - keepfoldersomitlocation
msgctxt "#30084"
msgid "Omit location path from recording directory"
msgstr ""

#. label: Recordings - virtualfolders
msgctxt "#30085"
msgid "Group recordings into folders by title"
msgstr ""

#. label-category: backend
msgctxt "#30086"
Expand Down Expand Up @@ -795,7 +803,17 @@ msgctxt "#30155"
msgid "{0:.1f} GiB"
msgstr ""

#empty strings from id 30156 to 30409
#. label-group: Recordings - Recording Paths
msgctxt "#30157"
msgid "Recording Paths"
msgstr ""

#. label-group: Recordings - Recording Locations
msgctxt "#30158"
msgid "Recording Locations"
msgstr ""

#empty strings from id 30159 to 30409

#. ##############
#. application #
Expand Down Expand Up @@ -1212,7 +1230,7 @@ msgctxt "#30682"
msgid "The options are: [B]Kodi instances[/B] Only use the value in kodi and will not affect last played on the E2 device; [B]Kodi/E2 instances[/B] Use the value across kodi and the E2 device so they stay in sync. Last played will be synced with the E2 device once every 5-10 minutes per recording if the PVR menus are in use. Note that only a single kodi instance is required to have this option enabled."
msgstr ""

#. help: Recordings - recordingpath
#. help: Timers - recordingpath
msgctxt "#30683"
msgid "Per default the addon does not specify the recording folder in newly created timers, so the default set in the set-top box will be used. If you want to specify a different folder (i.e. because you want all recordings scheduled via Kodi to be stored in a separate folder), then you need to set this option."
msgstr ""
Expand All @@ -1222,9 +1240,9 @@ msgctxt "#30684"
msgid "If this option is not set the addon will fetch all available recordings from all configured paths from the set-top box. If this option is set then it will only list recordings that are stored within the 'current recording path' on the set-top box."
msgstr ""

#. help: Reordings - keepfolders
#. help: Recordings - keepfolders
msgctxt "#30685"
msgid "If enabled do not specify a recording folder, when disabled (defaut), check if the recording is in it's own folder or in the root of the recording path."
msgid "If enabled use the real path from the backend to dictate the folder structure."
msgstr ""

#. help: Recordings - enablerecordingedls
Expand All @@ -1247,7 +1265,17 @@ msgctxt "#30689"
msgid "By default only the root of the location will be used to list recordings. When enabled the contents of child folders will be included."
msgstr ""

#empty strings from id 30690 to 30699
#. help: Recordings - keepfoldersomitlocation
msgctxt "#30690"
msgid "When using the folder structure from the backend omit the location path from the directory. Useful as it can remove the need to traverse unused folders each time recordings are accessed."
msgstr ""

#. help: Recordings - virtualfolders
msgctxt "#30691"
msgid "Create a virtual structure grouping recordings with the same name into folders. Will be applied to all recordings unless keeping the folder structure on the backend. In that case it will only be applied to the recordings in the root of each recording location."
msgstr ""

#empty strings from id 30692 to 30699

#. help info - Timers

Expand Down
41 changes: 30 additions & 11 deletions pvr.vuplus/resources/settings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -654,32 +654,43 @@
</constraints>
<control type="spinner" format="integer" />
</setting>
<setting id="recordingpath" type="string" label="30023" help="30683">
</group>

<group id="2" label="30157">
<setting id="virtualfolders" type="boolean" label="30085" help="30691">
<level>2</level>
<default></default>
<constraints>
<allowempty>true</allowempty>
</constraints>
<control type="edit" format="string" />
<default>true</default>
<control type="toggle" />
</setting>
<setting id="onlycurrent" type="boolean" label="30017" help="30684">
<setting id="keepfolders" type="boolean" label="30030" help="30685">
<level>2</level>
<default>false</default>
<default>true</default>
<control type="toggle" />
</setting>
<setting id="keepfolders" type="boolean" label="30030" help="30685">
<setting id="keepfoldersomitlocation" type="boolean" parent="keepfolders" label="30084" help="30690">
<level>2</level>
<default>false</default>
<default>true</default>
<dependencies>
<dependency type="visible" setting="keepfolders">true</dependency>
</dependencies>
<control type="toggle" />
</setting>
</group>

<group id="3" label="30158">
<setting id="recordingsrecursive" type="boolean" label="30022" help="30689">
<level>2</level>
<default>true</default>
<control type="toggle" />
</setting>
<setting id="onlycurrent" type="boolean" label="30017" help="30684">
<level>2</level>
<default>false</default>
<control type="toggle" />
</setting>
</group>

<group id="2" label="30107">
<group id="4" label="30107">
<setting id="enablerecordingedls" type="boolean" label="30108" help="30686">
<level>0</level>
<default>false</default>
Expand Down Expand Up @@ -746,6 +757,14 @@
<default>false</default>
<control type="toggle" />
</setting>
<setting id="recordingpath" type="string" label="30023" help="30683">
<level>2</level>
<default></default>
<constraints>
<allowempty>true</allowempty>
</constraints>
<control type="edit" format="string" />
</setting>
</group>
<group id="2" label="30123">
<setting id="enableautotimers" type="boolean" label="30034" help="30704">
Expand Down
2 changes: 1 addition & 1 deletion src/Enigma2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,7 @@ void Enigma2::Process()
{
Logger::Log(LEVEL_INFO, "%s Perform Updates!", __func__);

if (m_settings.GetAutoTimerListCleanupEnabled())
if (m_settings.GetAutomaticTimerListCleanupEnabled())
{
m_timers.RunAutoTimerListCleanup();
}
Expand Down
27 changes: 21 additions & 6 deletions src/enigma2/Recordings.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
#include "utilities/XMLUtils.h"

#include <algorithm>
#include <chrono>
#include <iostream>
#include <regex>
#include <sstream>
Expand Down Expand Up @@ -47,7 +48,7 @@ void Recordings::GetRecordings(std::vector<kodi::addon::PVRRecording>& kodiRecor
Logger::Log(LEVEL_DEBUG, "%s - Transfer recording '%s', Recording Id '%s'", __func__, recording.GetTitle().c_str(), recording.GetRecordingId().c_str());
kodi::addon::PVRRecording kodiRecording;

recording.UpdateTo(kodiRecording, m_channels, IsInRecordingFolder(recording.GetTitle(), deleted));
recording.UpdateTo(kodiRecording, m_channels, IsInVirtualRecordingFolder(recording, deleted));

kodiRecordings.emplace_back(kodiRecording);
}
Expand Down Expand Up @@ -134,20 +135,27 @@ RecordingEntry Recordings::GetRecording(const std::string& recordingId) const
return entry;
}

bool Recordings::IsInRecordingFolder(const std::string& recordingFolder, bool deleted) const
bool Recordings::IsInVirtualRecordingFolder(const RecordingEntry& recordingToCheck, bool deleted) const
{
if (Settings::GetInstance().GetKeepRecordingsFolders() && !recordingToCheck.InLocationRoot())
return false;

const std::string& recordingFolderToCheck = recordingToCheck.GetTitle();
const auto& recordings = (!deleted) ? m_recordings : m_deletedRecordings;

int iMatches = 0;
for (const auto& recording : recordings)
{
if (recordingFolder == recording.GetTitle())
if (Settings::GetInstance().GetKeepRecordingsFolders() && !recording.InLocationRoot())
continue;

if (recordingFolderToCheck == recording.GetTitle())
{
iMatches++;
Logger::Log(LEVEL_DEBUG, "%s Found Recording title '%s' in recordings vector!", __func__, recordingFolder.c_str());
Logger::Log(LEVEL_DEBUG, "%s Found Recording title '%s' in recordings vector!", __func__, recordingFolderToCheck.c_str());
if (iMatches > 1)
{
Logger::Log(LEVEL_DEBUG, "%s Found Recording title twice '%s' in recordings vector!", __func__, recordingFolder.c_str());
Logger::Log(LEVEL_DEBUG, "%s Found Recording title twice '%s' in recordings vector!", __func__, recordingFolderToCheck.c_str());
return true;
}
}
Expand Down Expand Up @@ -719,6 +727,10 @@ void Recordings::LoadRecordings(bool deleted)
std::vector<RecordingEntry> newRecordingsList;
std::unordered_map<std::string, enigma2::data::RecordingEntry> newRecordingsIdMap;
bool loadError = false;

auto started = std::chrono::high_resolution_clock::now();
Logger::Log(LEVEL_INFO, "%s Recordings Load Start: %s", __func__, deleted ? "deleted items" : "recordings");

for (std::string location : m_locations)
{
if (deleted)
Expand All @@ -740,6 +752,9 @@ void Recordings::LoadRecordings(bool deleted)
for (auto& pair : newRecordingsIdMap)
m_recordingsIdMap.insert(pair);
}

int milliseconds = std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - started).count();
Logger::Log(LEVEL_INFO, "%s Recordings Load: %s - %d (ms)", __func__, deleted ? "deleted items" : "recordings", milliseconds);
}

namespace
Expand Down Expand Up @@ -808,7 +823,7 @@ bool Recordings::GetRecordingsFromLocation(const std::string recordingLocation,

if (!pNode)
{
Logger::Log(LEVEL_DEBUG, "%s Could not find <e2movie> element, no movies at location: %s", directory.c_str(), __func__);
Logger::Log(LEVEL_DEBUG, "%s Could not find <e2movie> element, no movies at location: %s", __func__, directory.c_str());
}
else
{
Expand Down
2 changes: 1 addition & 1 deletion src/enigma2/Recordings.h
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ namespace enigma2
bool ReadExtaRecordingCutsInfo(const data::RecordingEntry& recordingEntry, std::vector<std::pair<int, int64_t>>& cuts, std::vector<std::string>& tags);
bool ReadExtraRecordingPlayCountInfo(const data::RecordingEntry& recordingEntry, std::vector<std::string>& tags);
void SetRecordingNextSyncTime(data::RecordingEntry& recordingEntry, time_t nextSyncTime, std::vector<std::string>& oldTags);
bool IsInRecordingFolder(const std::string& strRecordingFolder, bool deleted) const;
bool IsInVirtualRecordingFolder(const data::RecordingEntry& recordingEntry, bool deleted) const;
bool UpdateRecordingSizeFromMovieDetails(data::RecordingEntry& recordingEntry);

std::mt19937 m_randomGenerator;
Expand Down
Loading

0 comments on commit 848a96f

Please sign in to comment.