diff --git a/source/ChanSort.Api/Controller/Editor.cs b/source/ChanSort.Api/Controller/Editor.cs
index 399561a..57dac19 100644
--- a/source/ChanSort.Api/Controller/Editor.cs
+++ b/source/ChanSort.Api/Controller/Editor.cs
@@ -208,7 +208,7 @@ namespace ChanSort.Api
log.AppendFormat("Skipped reference list {0}\r\n", refList.ShortCaption);
continue;
}
- ApplyReferenceList(refDataRoot, refList, tvList, true);
+ ApplyReferenceList(refDataRoot, refList, -1, tvList, -1, true);
}
}
@@ -225,7 +225,7 @@ namespace ChanSort.Api
///
/// controls whether Pr# will be reassigned to the reference channel when they are already in-use in the TV list
/// when true, consecutive numbers will be used instead of the Pr# in the reference list when applying the order
- public void ApplyReferenceList(DataRoot refDataRoot, ChannelList refList, ChannelList tvList, bool addProxyChannels = true, int positionOffset = 0, Func chanFilter = null, bool overwrite = true, bool consecutive = false)
+ public void ApplyReferenceList(DataRoot refDataRoot, ChannelList refList, int refListPosIndex, ChannelList tvList, int tvListPosIndex, bool addProxyChannels = true, int positionOffset = 0, Func chanFilter = null, bool overwrite = true, bool consecutive = false)
{
// create Hashtable for exact channel lookup
// the UID of a TV channel list contains a source-indicator (Analog, Cable, Sat), which may be undefined in the reference list)
@@ -245,39 +245,12 @@ namespace ChanSort.Api
}
var incNr = 1 + positionOffset;
- foreach (var refChannel in refList.Channels.OrderBy(ch => ch.OldProgramNr))
+ foreach (var refChannel in refList.Channels.OrderBy(ch => ch.GetOldPosition(refListPosIndex)))
{
if (!(chanFilter?.Invoke(refChannel, true) ?? true))
continue;
- var tvChannels = refChannel.Uid == "0-0-0" ? null : tvList.GetChannelByUid(refChannel.Uid);
-
- // try to find matching channels based on ONID+TSID+SID
- if ((tvChannels?.Count ?? 0) == 0)
- {
- var key = DvbKey(refChannel.OriginalNetworkId, refChannel.TransportStreamId, refChannel.ServiceId);
- if (key != 0 && onidTsidSid.TryGetValue(key, out var candidates))
- {
- tvChannels = candidates;
-
- // narrow the list down further when a transponder is also provided (i.e. the same TV channel can be received on multiple DVB-T frequencies)
- if (tvChannels.Count > 1 && !string.IsNullOrEmpty(refChannel.ChannelOrTransponder))
- {
- candidates = tvChannels.Where(ch => ch.ChannelOrTransponder == refChannel.ChannelOrTransponder).ToList();
- if (candidates.Count > 0)
- tvChannels = candidates;
- }
- }
- }
-
- // try to find matching channels by name
- if ((tvChannels?.Count ?? 0) == 0 && !string.IsNullOrWhiteSpace(refChannel.Name))
- tvChannels = tvList.GetChannelByName(refChannel.Name).ToList();
-
- // get the first unassigned channel from the candidates (e.g. when matching by non-unique names), or fall back to the first matching channel (e.g. by unique ID)
- ChannelInfo tvChannel = tvChannels.FirstOrDefault(c => c.GetPosition(0) == -1);
- if (tvChannel == null && tvChannels.Count > 0)
- tvChannel = tvChannels[0];
+ var tvChannel = FindChannel(tvList, refChannel, onidTsidSid);
if (tvChannel != null)
{
@@ -293,7 +266,7 @@ namespace ChanSort.Api
foreach (var chan in curChans)
chan.NewProgramNr = -1;
- tvChannel.SetPosition(0, newNr);
+ tvChannel.SetPosition(tvListPosIndex, newNr);
if (refDataRoot.CanSkip && this.DataRoot.CanSkip)
tvChannel.Skip = refChannel.Skip;
if (refDataRoot.CanLock && this.DataRoot.CanLock)
@@ -308,7 +281,8 @@ namespace ChanSort.Api
tvChannel.IsNameModified = true;
}
- ApplyFavorites(refDataRoot, refChannel, tvChannel);
+ if (tvListPosIndex == -1)
+ ApplyFavorites(refDataRoot, refChannel, tvChannel);
}
else if (addProxyChannels)
{
@@ -318,6 +292,39 @@ namespace ChanSort.Api
}
}
+ private ChannelInfo FindChannel(ChannelList tvList, ChannelInfo refChannel, Dictionary> onidTsidSid)
+ {
+ var tvChannels = refChannel.Uid == "0-0-0" ? null : tvList.GetChannelByUid(refChannel.Uid);
+
+ // try to find matching channels based on ONID+TSID+SID
+ if ((tvChannels?.Count ?? 0) == 0)
+ {
+ var key = DvbKey(refChannel.OriginalNetworkId, refChannel.TransportStreamId, refChannel.ServiceId);
+ if (key != 0 && onidTsidSid.TryGetValue(key, out var candidates))
+ {
+ tvChannels = candidates;
+
+ // narrow the list down further when a transponder is also provided (i.e. the same TV channel can be received on multiple DVB-T frequencies)
+ if (tvChannels.Count > 1 && !string.IsNullOrEmpty(refChannel.ChannelOrTransponder))
+ {
+ candidates = tvChannels.Where(ch => ch.ChannelOrTransponder == refChannel.ChannelOrTransponder).ToList();
+ if (candidates.Count > 0)
+ tvChannels = candidates;
+ }
+ }
+ }
+
+ // try to find matching channels by name
+ if ((tvChannels?.Count ?? 0) == 0 && !string.IsNullOrWhiteSpace(refChannel.Name))
+ tvChannels = tvList.GetChannelByName(refChannel.Name).ToList();
+
+ // get the first unassigned channel from the candidates (e.g. when matching by non-unique names), or fall back to the first matching channel (e.g. by unique ID)
+ ChannelInfo tvChannel = tvChannels.FirstOrDefault(c => c.GetPosition(0) == -1);
+ if (tvChannel == null && tvChannels.Count > 0)
+ tvChannel = tvChannels[0];
+ return tvChannel;
+ }
+
long DvbKey(int onid, int tsid, int sid)
{
return ((long)onid << 32) | ((long)tsid << 16) | (long)sid;
@@ -332,9 +339,9 @@ namespace ChanSort.Api
tvChannel.Favorites = refChannel.Favorites & DataRoot.SupportedFavorites;
if (refDataRoot.SortedFavorites)
{
- var c = Math.Min(refChannel.FavIndex.Count, tvChannel.OldFavIndex.Count);
+ var c = Math.Min(refDataRoot.FavListCount, this.DataRoot.FavListCount);
for (int i = 0; i < c; i++)
- tvChannel.FavIndex[i] = refChannel.OldFavIndex[i];
+ tvChannel.SetPosition(i+1, refChannel.GetOldPosition(i+1));
}
else
this.ApplyPrNrToFavLists(tvChannel);
@@ -363,13 +370,13 @@ namespace ChanSort.Api
if (sortedFav)
{
foreach (var channel in favList.Channels)
- maxPosition = Math.Max(maxPosition, channel.FavIndex[favIndex]);
+ maxPosition = Math.Max(maxPosition, channel.GetPosition(favIndex+1));
}
foreach (var channel in list)
{
- if (sortedFav && channel.FavIndex[favIndex] == -1)
- channel.FavIndex[favIndex] = ++maxPosition;
+ if (sortedFav && channel.GetPosition(favIndex+1) == -1)
+ channel.SetPosition(favIndex+1,++maxPosition);
channel.Favorites |= favMask;
}
}
@@ -377,8 +384,8 @@ namespace ChanSort.Api
{
foreach (var channel in list)
{
- if (sortedFav && channel.FavIndex[favIndex] != -1)
- channel.FavIndex[favIndex] = -1;
+ if (sortedFav && channel.GetPosition(favIndex+1) != -1)
+ channel.SetPosition(favIndex+1, -1);
channel.Favorites &= ~favMask;
}
@@ -386,10 +393,10 @@ namespace ChanSort.Api
if (sortedFav && !this.DataRoot.AllowGapsInFavNumbers)
{
int i = 0;
- foreach (var channel in favList.Channels.OrderBy(c => c.FavIndex[favIndex]))
+ foreach (var channel in favList.Channels.OrderBy(c => c.GetPosition(favIndex + 1)))
{
- if (channel.FavIndex[favIndex] != -1)
- channel.FavIndex[favIndex] = ++i;
+ if (channel.GetPosition(favIndex+1) != -1)
+ channel.SetPosition(favIndex+1, ++i);
}
}
}
@@ -419,7 +426,7 @@ namespace ChanSort.Api
var refMask = (ulong)tvChannel.Favorites;
for (int i = 0; supMask != 0; i++)
{
- tvChannel.FavIndex[i] = (refMask & 0x01) == 0 ? -1 : tvChannel.NewProgramNr;
+ tvChannel.SetPosition(i+1, (refMask & 0x01) == 0 ? -1 : tvChannel.NewProgramNr);
supMask >>= 1;
refMask >>= 1;
}
@@ -439,13 +446,13 @@ namespace ChanSort.Api
bool changed = false;
for (int fav = 0; fav < favCount; fav++)
{
- var list = channelList.Channels.Where(c => c.FavIndex[fav] >= 0).OrderBy(c => c.FavIndex[fav]).ToList();
+ var list = channelList.Channels.Where(c => c.GetPosition(fav+1) >= 0).OrderBy(c => c.GetPosition(fav+1)).ToList();
int i = 1;
foreach (var channel in list)
{
- if (channel.FavIndex[fav] != i)
+ if (channel.GetPosition(fav+1) != i)
{
- channel.FavIndex[fav] = ++i;
+ channel.SetPosition(fav+1, ++i);
changed = true;
}
}
diff --git a/source/ChanSort.Api/Model/ChannelInfo.cs b/source/ChanSort.Api/Model/ChannelInfo.cs
index 266cb2f..3b3897b 100644
--- a/source/ChanSort.Api/Model/ChannelInfo.cs
+++ b/source/ChanSort.Api/Model/ChannelInfo.cs
@@ -72,11 +72,11 @@ namespace ChanSort.Api
///
/// current number of the channel in the various favorite lists (if individual sorting is supported)
///
- public List FavIndex { get; }
+ private List FavIndex { get; }
///
/// original number of the channel in the various favorite lists (if individual sorting is supported)
///
- public List OldFavIndex { get; }
+ private List OldFavIndex { get; }
///
/// predefined LCN (logical channel number) assigned by TV firmware or cable/sat operator
@@ -330,7 +330,7 @@ namespace ChanSort.Api
this.NewProgramNr = newPos;
else
{
- for (int i=this.FavIndex.Count; i<=subListIndex;i++)
+ for (int i = this.FavIndex.Count; i < subListIndex; i++)
this.FavIndex.Add(-1);
this.FavIndex[subListIndex - 1] = newPos;
int mask = 1 << (subListIndex - 1);
@@ -352,7 +352,7 @@ namespace ChanSort.Api
this.OldProgramNr = oldPos;
else
{
- for (int i = this.OldFavIndex.Count; i <= subListIndex; i++)
+ for (int i = this.OldFavIndex.Count; i < subListIndex; i++)
this.OldFavIndex.Add(-1);
this.OldFavIndex[subListIndex - 1] = oldPos;
}
diff --git a/source/ChanSort.Api/Model/ChannelList.cs b/source/ChanSort.Api/Model/ChannelList.cs
index 94e40c0..cce962c 100644
--- a/source/ChanSort.Api/Model/ChannelList.cs
+++ b/source/ChanSort.Api/Model/ChannelList.cs
@@ -12,8 +12,6 @@ namespace ChanSort.Api
private int insertProgramNr = 1;
private int duplicateUidCount;
private int duplicateProgNrCount;
- public int FavListCount { get; set; }
-
public static List DefaultVisibleColumns { get; set; } = new List(); // initialized by MainForm
diff --git a/source/ChanSort.Api/Model/DataRoot.cs b/source/ChanSort.Api/Model/DataRoot.cs
index bf1a027..ba2eacd 100644
--- a/source/ChanSort.Api/Model/DataRoot.cs
+++ b/source/ChanSort.Api/Model/DataRoot.cs
@@ -27,6 +27,8 @@ namespace ChanSort.Api
public bool CanHide => this.loader.Features.CanHideChannels;
public bool CanEditFavListName => this.loader.Features.CanEditFavListNames;
+ public int FavListCount { get; private set; }
+
public DataRoot(SerializerBase loader)
{
this.loader = loader;
@@ -108,14 +110,12 @@ namespace ChanSort.Api
#region ValidateAfterLoad()
public virtual void ValidateAfterLoad()
{
+ this.FavListCount = 0;
+ for (ulong m = (ulong)this.loader.Features.SupportedFavorites; m != 0; m >>= 1)
+ ++this.FavListCount;
+
foreach (var list in this.ChannelLists)
{
- if (list.FavListCount == 0)
- {
- for (ulong m = (ulong) this.loader.Features.SupportedFavorites; m != 0; m >>= 1)
- ++list.FavListCount;
- }
-
if (list.IsMixedSourceFavoritesList)
{
loader.Features.SortedFavorites = true; // all mixed source favorite lists must support ordering
@@ -144,18 +144,11 @@ namespace ChanSort.Api
#region ApplyCurrentProgramNumbers()
public void ApplyCurrentProgramNumbers()
{
- int c = 0;
- if (this.MixedSourceFavorites || this.SortedFavorites)
- {
- for (ulong m = (ulong) this.SupportedFavorites; m != 0; m >>= 1)
- ++c;
- }
-
foreach (var list in this.ChannelLists)
{
foreach (var channel in list.Channels)
{
- for (int i = 0; i <= c; i++)
+ for (int i = 0; i <= this.FavListCount; i++)
channel.SetPosition(i, channel.GetOldPosition(i));
}
}
@@ -247,9 +240,8 @@ namespace ChanSort.Api
chan.NewProgramNr = -1;
}
- chan.OldProgramNr = chan.NewProgramNr;
- chan.OldFavIndex.Clear();
- chan.OldFavIndex.AddRange(chan.FavIndex);
+ for (int j=0; j<=this.FavListCount; j++)
+ chan.SetOldPosition(j, chan.GetPosition(j));
}
}
}
diff --git a/source/ChanSort.Loader.Enigma2/Channel.cs b/source/ChanSort.Loader.Enigma2/Channel.cs
index cca83db..b65b7c1 100644
--- a/source/ChanSort.Loader.Enigma2/Channel.cs
+++ b/source/ChanSort.Loader.Enigma2/Channel.cs
@@ -7,7 +7,7 @@ namespace ChanSort.Loader.Enigma2
///
/// first two fields of the lamedb entry
///
- public string Prefix { get; set; }
+ public string Prefix { get; set; } = "1:0";
///
/// For DVB-S it is the orbital position * 10 (e.g. 192 for Astra 19.2E) * 65536
@@ -15,11 +15,11 @@ namespace ChanSort.Loader.Enigma2
public int DvbNamespace { get; set; }
public int ServiceNumber { get; set; }
-
+
///
/// all fields after the DVB-namespace in the lamedb entry
///
- public string Suffix { get; set; }
+ public string Suffix { get; set; } = ":0:0:0:";
///
/// #DESCRIPTION of the userbouquet entry
diff --git a/source/ChanSort.Loader.Enigma2/Serializer.cs b/source/ChanSort.Loader.Enigma2/Serializer.cs
index c6abbc0..56baec2 100644
--- a/source/ChanSort.Loader.Enigma2/Serializer.cs
+++ b/source/ChanSort.Loader.Enigma2/Serializer.cs
@@ -84,14 +84,14 @@ namespace ChanSort.Loader.Enigma2
LoadBouquets(path, ref favIndex);
// load all unlisted userbouquet files
- foreach (var file in Directory.GetFiles(Path.GetDirectoryName(this.FileName), "userbouquet.*"))
- {
- var ext = Path.GetExtension(file);
- if (ext != ".tv" && ext != ".radio") // ignore .del, .bak and other irrelevant files
- continue;
- if (!this.favListFileNames.Contains(file))
- this.LoadUserBouquet(file, ref favIndex);
- }
+ //foreach (var file in Directory.GetFiles(Path.GetDirectoryName(this.FileName), "userbouquet.*"))
+ //{
+ // var ext = Path.GetExtension(file);
+ // if (ext != ".tv" && ext != ".radio") // ignore .del, .bak and other irrelevant files
+ // continue;
+ // if (!this.favListFileNames.Contains(file))
+ // this.LoadUserBouquet(file, ref favIndex);
+ //}
}
#endregion
@@ -188,7 +188,6 @@ namespace ChanSort.Loader.Enigma2
ch.RecordIndex = chanId;
ch.RecordOrder = chanId;
ch.OldProgramNr = ++chanId;
- ch.NewProgramNr = chanId;
ch.IsDeleted = false;
ch.ServiceId = FromHex(parts[0]);
ch.DvbNamespace = FromHex(parts[1]);
@@ -254,7 +253,7 @@ namespace ChanSort.Loader.Enigma2
#region LoadUserBoquet
private void LoadUserBouquet(string file, ref int favIndex)
{
- if (!File.Exists(file))
+ if (!File.Exists(file) || this.favListFileNames.Contains(file))
return;
using var r = new StreamReader(File.OpenRead(file), utf8WithoutBom);
diff --git a/source/ChanSort.Loader.Grundig/Serializer.cs b/source/ChanSort.Loader.Grundig/Serializer.cs
index 74c08a6..2ac9b9b 100644
--- a/source/ChanSort.Loader.Grundig/Serializer.cs
+++ b/source/ChanSort.Loader.Grundig/Serializer.cs
@@ -194,7 +194,10 @@ namespace ChanSort.Loader.Grundig
return;
}
- foreach (XmlNode networkNode in digital["channels"].ChildNodes)
+ var channels = digital["channels"];
+ if (channels == null)
+ return;
+ foreach (XmlNode networkNode in channels.ChildNodes)
{
if (networkNode.LocalName != "network")
continue;
@@ -361,7 +364,7 @@ namespace ChanSort.Loader.Grundig
if (ch.IsNameModified)
att["name"].Value = ch.Name;
for (int i=1; i<=4; i++)
- att["f"+i].Value = Math.Max(0, ch.FavIndex[i-1]).ToString(); // convert -1 to 0
+ att["f"+i].Value = Math.Max(0, ch.GetPosition(i)).ToString(); // convert -1 to 0
att["skp"].InnerText = ch.Skip ? "1" : "0";
att["lck"].InnerText = ch.Lock ? "1" : "0";
if ((ch.SignalSource & SignalSource.Digital) != 0)
diff --git a/source/ChanSort.Loader.Hisense/ChannelDb/ChannelDbSerializer.cs b/source/ChanSort.Loader.Hisense/ChannelDb/ChannelDbSerializer.cs
index fcb6a27..867865d 100644
--- a/source/ChanSort.Loader.Hisense/ChannelDb/ChannelDbSerializer.cs
+++ b/source/ChanSort.Loader.Hisense/ChannelDb/ChannelDbSerializer.cs
@@ -442,7 +442,7 @@ namespace ChanSort.Loader.Hisense.ChannelDb
var id = ((long) r.GetInt32(0) << 32) | (uint) r.GetInt32(1);
var ci = this.channelsById.TryGet(id);
if (ci != null)
- ci.OldFavIndex[i - 1] = r.GetInt32(2);
+ ci.SetOldPosition(i, r.GetInt32(2));
}
}
}
@@ -608,7 +608,7 @@ namespace ChanSort.Loader.Hisense.ChannelDb
{
for (int i = 0; i < 4; i++)
{
- if (ci.FavIndex[i] <= 0)
+ if (ci.GetPosition(i+1) <= 0)
{
cmd.CommandText = $"delete from fav_{i + 1} where ui2_svc_id={ci.RecordIndex >> 32} and ui2_svc_rec_id={ci.RecordIndex & 0xFFFFFFFF}";
cmd.ExecuteNonQuery();
@@ -621,7 +621,7 @@ namespace ChanSort.Loader.Hisense.ChannelDb
cmd.Parameters.Add("@name", DbType.String);
cmd.Parameters.Add("@svcid", DbType.Int32);
cmd.Parameters.Add("@recid", DbType.Int32);
- cmd.Parameters["@chnr"].Value = ci.FavIndex[i].ToString();
+ cmd.Parameters["@chnr"].Value = ci.GetPosition(i+1).ToString();
cmd.Parameters["@name"].Value = ci.Name;
cmd.Parameters["@svcid"].Value = ci.RecordIndex >> 32;
cmd.Parameters["@recid"].Value = ci.RecordIndex & 0xFFFF;
@@ -640,7 +640,7 @@ namespace ChanSort.Loader.Hisense.ChannelDb
{
for (int i = 0; i < 4; i++)
{
- if (ci.FavIndex[i] <= 0)
+ if (ci.GetPosition(i+1) <= 0)
continue;
cmd.CommandText = $"insert into fav_{i + 1} (sortId, channelId, svlId, channelName, svlRecId, nwMask) values (@chnr,@chanid,@svcid,@name,@recid,@nwmask)";
@@ -651,7 +651,7 @@ namespace ChanSort.Loader.Hisense.ChannelDb
cmd.Parameters.Add("@name", DbType.String);
cmd.Parameters.Add("@recid", DbType.Int32);
cmd.Parameters.Add("@nwmask", DbType.Int32);
- cmd.Parameters["@chnr"].Value = ci.FavIndex[i];
+ cmd.Parameters["@chnr"].Value = ci.GetPosition(i+1);
cmd.Parameters["@chanid"].Value = ci.ChannelId;
cmd.Parameters["@name"].Value = ci.Name;
cmd.Parameters["@svcid"].Value = ci.RecordIndex >> 32;
diff --git a/source/ChanSort.Loader.Hisense/ServicelistDb/ServicelistDbSerializer.cs b/source/ChanSort.Loader.Hisense/ServicelistDb/ServicelistDbSerializer.cs
index 6edbcbc..1cd3f1f 100644
--- a/source/ChanSort.Loader.Hisense/ServicelistDb/ServicelistDbSerializer.cs
+++ b/source/ChanSort.Loader.Hisense/ServicelistDb/ServicelistDbSerializer.cs
@@ -358,7 +358,7 @@ left outer join Lcn l on l.ServiceId=fi.ServiceId and l.FavoriteId=fi.FavoriteId
int favListIdx = favListIdToFavIndex.TryGet(favListId, -1);
if (favListIdx >= 0)
- ci.OldFavIndex[favListIdx] = r.GetInt32(2);
+ ci.SetOldPosition(favListIdx+1, r.GetInt32(2));
ci.SetOldPosition(favListIdx + 1, r.GetInt32(2)); // 0=main nr, 1-4=fav 1-4
if (favListIdx < 0)
diff --git a/source/ChanSort.Loader.Panasonic/DbChannel.cs b/source/ChanSort.Loader.Panasonic/DbChannel.cs
index 17cf98f..f34a297 100644
--- a/source/ChanSort.Loader.Panasonic/DbChannel.cs
+++ b/source/ChanSort.Loader.Panasonic/DbChannel.cs
@@ -69,7 +69,7 @@ namespace ChanSort.Loader.Panasonic
if (favIndex > 0)
{
this.Favorites |= (Favorites) (1 << i);
- this.OldFavIndex[i] = favIndex;
+ this.SetOldPosition(i, favIndex);
}
}
}
diff --git a/source/ChanSort.Loader.Panasonic/Serializer.cs b/source/ChanSort.Loader.Panasonic/Serializer.cs
index c5cedec..8343f34 100644
--- a/source/ChanSort.Loader.Panasonic/Serializer.cs
+++ b/source/ChanSort.Loader.Panasonic/Serializer.cs
@@ -358,7 +358,7 @@ order by s.ntype,major_channel
cmd.Parameters["@progNr"].Value = channel.NewProgramNr;
cmd.Parameters["@sname"].Value = channel.RawName;
for (int fav = 0; fav < 4; fav++)
- cmd.Parameters["@fav" + (fav + 1)].Value = Math.Max(0, channel.FavIndex[fav]);
+ cmd.Parameters["@fav" + (fav + 1)].Value = Math.Max(0, channel.GetPosition(fav+1));
cmd.Parameters["@lock"].Value = channel.Lock;
cmd.Parameters["@skip"].Value = channel.Skip;
cmd.ExecuteNonQuery();
diff --git a/source/ChanSort.Loader.Philips/BinarySerializer.cs b/source/ChanSort.Loader.Philips/BinarySerializer.cs
index 90c9cbe..faa08d2 100644
--- a/source/ChanSort.Loader.Philips/BinarySerializer.cs
+++ b/source/ChanSort.Loader.Philips/BinarySerializer.cs
@@ -901,7 +901,7 @@ namespace ChanSort.Loader.Philips
var recordSize = 4;
var recordCount = (dataSize - 4) / recordSize;
- var favList = this.dvbsChannels.Channels.Where(c => c.FavIndex[0] != -1).OrderBy(c => c.FavIndex[0]).ToList();
+ var favList = this.dvbsChannels.Channels.Where(c => c.GetPosition(1) != -1).OrderBy(c => c.GetPosition(1)).ToList();
var favCount = favList.Count;
var firstFavIndex = favCount == 0 ? -1 : (int)favList[0].RecordIndex;
data.SetInt16(4, firstFavIndex);
diff --git a/source/ChanSort.Loader.Philips/XmlSerializer.cs b/source/ChanSort.Loader.Philips/XmlSerializer.cs
index 1ec88be..2e1af13 100644
--- a/source/ChanSort.Loader.Philips/XmlSerializer.cs
+++ b/source/ChanSort.Loader.Philips/XmlSerializer.cs
@@ -432,7 +432,7 @@ namespace ChanSort.Loader.Philips
foreach (var chan in rootList.Channels)
{
favChannels.Channels.Add(chan);
- for (int i=0; i= 0)
{
channel.Favorites |= (Favorites) (1 << fav);
- channel.OldFavIndex[fav] = pos;
+ channel.SetOldPosition(fav+1, pos);
}
}
}
@@ -634,7 +634,7 @@ namespace ChanSort.Loader.Samsung.Zip
cmdDeleteFav.ExecuteNonQuery();
}
- channel.FavIndex[i] = newPos;
+ channel.SetPosition(i+1, newPos);
}
}
}
diff --git a/source/ChanSort.Loader.Sony/Serializer.cs b/source/ChanSort.Loader.Sony/Serializer.cs
index f46d1e6..a7c31df 100644
--- a/source/ChanSort.Loader.Sony/Serializer.cs
+++ b/source/ChanSort.Loader.Sony/Serializer.cs
@@ -358,7 +358,7 @@ namespace ChanSort.Loader.Sony
for (int j = 0; j < 4 && j < favNumbers.Length; j++)
{
if (int.TryParse(favNumbers[j], out var favNr) && favNr > 0)
- chan.OldFavIndex[j] = favNr;
+ chan.SetOldPosition(j+1, favNr);
}
}
var muxId = int.Parse(svcData["MuxID"][i]) + idAdjustment;
@@ -752,7 +752,7 @@ namespace ChanSort.Loader.Sony
{
var vals = value.Split(' ');
for (int i = 0; i < 4; i++)
- vals[i] = ch.FavIndex[i] <= 0 ? "0" : ch.FavIndex[i].ToString();
+ vals[i] = ch.GetPosition(i+1) <= 0 ? "0" : ch.GetPosition(i+1).ToString();
return string.Join(" ", vals);
}
}
diff --git a/source/ChanSort.Loader.Toshiba/SettingsDbSerializer.cs b/source/ChanSort.Loader.Toshiba/SettingsDbSerializer.cs
index c9d6993..83e383a 100644
--- a/source/ChanSort.Loader.Toshiba/SettingsDbSerializer.cs
+++ b/source/ChanSort.Loader.Toshiba/SettingsDbSerializer.cs
@@ -19,6 +19,8 @@ namespace ChanSort.Loader.Toshiba
{
private readonly ChannelList channels = new ChannelList(SignalSource.All, "All");
+ private readonly HashSet tableNames = new();
+
#region ctor()
public SettingsDbSerializer(string inputFile) : base(inputFile)
{
@@ -32,6 +34,15 @@ namespace ChanSort.Loader.Toshiba
this.Features.SupportedFavorites = 0;
this.DataRoot.AddChannelList(this.channels);
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.Lock));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.Skip));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.Hidden));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.Encrypted));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.PcrPid));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.VideoPid));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.AudioPid));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.Satellite));
+ channels.VisibleColumnFieldNames.Remove(nameof(ChannelInfo.ShortName));
}
#endregion
@@ -63,12 +74,19 @@ namespace ChanSort.Loader.Toshiba
string sysDataConnString = "Data Source=" + this.FileName;
using var conn = new SQLiteConnection(sysDataConnString);
conn.Open();
+
using var cmd = conn.CreateCommand();
this.RepairCorruptedDatabaseImage(cmd);
- cmd.CommandText = "SELECT count(1) FROM sqlite_master WHERE type = 'table' and name='EASISerTable'";
- if (Convert.ToInt32(cmd.ExecuteScalar()) != 1)
+ cmd.CommandText = "SELECT name FROM sqlite_master WHERE type = 'table'";
+ using (var r = cmd.ExecuteReader())
+ {
+ while (r.Read())
+ this.tableNames.Add(r.GetString(0).ToLowerInvariant());
+ }
+
+ if (!this.tableNames.Contains("easisertable"))
throw new FileLoadException("File doesn't contain the expected tables");
this.ReadSatellites(cmd);
@@ -135,23 +153,27 @@ namespace ChanSort.Loader.Toshiba
{
int ixE = 0;
int ixD = 3;
- int ixA = 8;
- int ixT = 9;
+ int ixA = 9;
int ixDC = 10;
+ int ixT = 12;
- cmd.CommandText = @"
+ var hasTADTunerDataTable = this.tableNames.Contains("tadtunerdatatable");
+ string analogTunerFields = hasTADTunerDataTable ? ",t.frequency_in_multiples_of_10Hz" : "";
+ string analogTunerTable = hasTADTunerDataTable ? " left outer join TADTunerDataTable t on t.channel=ac.channel_no" : "";
+ cmd.CommandText = $@"
select
e.m_handle, e.m_rsn, e.m_name_serialized,
- d.m_onid, d.m_tsid, d.m_id, d.m_type, d.m_name_serialized,
+ d.m_onid, d.m_tsid, d.m_id, d.m_type, d.m_name_serialized, d.m_provider_serialized,
a.m_name_serialized,
- t.frequency_in_multiples_of_10Hz,
- dc.frequency
+ dc.frequency, dc.symbol_rate
+ {analogTunerFields}
from EASISerTable e
left outer join DVBSerTable d on d.m_handle=e.m_handle
left outer join AnalogSerTable a on a.m_handle=e.m_handle
left outer join ChanDataTable dc on dc.handle=d.m_channel_no
left outer join ChanDataTable ac on ac.handle=a.m_channel_no
-left outer join TADTunerDataTable t on t.channel=ac.channel_no";
+{analogTunerTable}";
+
using var r = cmd.ExecuteReader();
while (r.Read())
{
@@ -166,12 +188,16 @@ left outer join TADTunerDataTable t on t.channel=ac.channel_no";
channel.OriginalNetworkId = r.GetInt32(ixD + 0) & 0x1FFF;
channel.TransportStreamId = r.GetInt32(ixD + 1) & 0x1FFF;
channel.ServiceId = r.GetInt32(ixD + 2) & 0x1FFF;
- channel.ServiceType = r.GetInt32(ixD + 3);
+ channel.ServiceType = r.GetInt32(ixD + 3) & 0x1FFF;
+ channel.Provider = r.GetString(ixD + 5);
channel.FreqInMhz = (decimal) r.GetInt32(ixDC + 0) / 1000;
+ channel.SymbolRate = r.GetInt32(ixDC + 1);
+ if (channel.FreqInMhz > 10000)
+ channel.FreqInMhz = (int) channel.FreqInMhz;
}
// analog
- if (!r.IsDBNull(ixA + 0))
+ if (!r.IsDBNull(ixA + 0) && hasTADTunerDataTable)
{
channel.FreqInMhz = (decimal) r.GetInt32(ixT + 0) / 100000;
}
diff --git a/source/ChanSort/MainForm.cs b/source/ChanSort/MainForm.cs
index be0f5d3..f97417d 100644
--- a/source/ChanSort/MainForm.cs
+++ b/source/ChanSort/MainForm.cs
@@ -479,7 +479,7 @@ namespace ChanSort.Ui
this.tabSubList.TabPages[i].Text = this.DataRoot.GetFavListCaption(i - 1, true);
this.tabSubList.EndUpdate();
- if (!this.DataRoot.SortedFavorites || this.subListIndex >= favCount)
+ if (!this.DataRoot.SortedFavorites || this.subListIndex > favCount)
{
this.tabSubList.SelectedTabPageIndex = 0;
this.subListIndex = 0;
diff --git a/source/ChanSort/ReferenceListForm.cs b/source/ChanSort/ReferenceListForm.cs
index 62dd364..103f5a9 100644
--- a/source/ChanSort/ReferenceListForm.cs
+++ b/source/ChanSort/ReferenceListForm.cs
@@ -20,7 +20,6 @@ namespace ChanSort.Ui
class ListOption
{
- private DataRoot root;
public ChannelList ChannelList { get; }
public int PosIndex { get; }
@@ -125,6 +124,7 @@ namespace ChanSort.Ui
this.edFile.Text = serializer.FileName;
this.rbAuto.Enabled = this.rbManual.Enabled = true;
ser.DataRoot.ApplyCurrentProgramNumbers();
+ ser.DataRoot.ValidateAfterLoad();
this.comboSource.EditValue = null;
this.comboSource.Properties.Items.Clear();
@@ -132,13 +132,12 @@ namespace ChanSort.Ui
{
if (list.Channels.Count == 0)
continue;
- if (list.IsMixedSourceFavoritesList)
- {
- for (int i = 0; i <= list.FavListCount; i++)
- this.comboSource.Properties.Items.Add(new ListOption(list, i, list + (i==0 ? "" : " - " + serializer.DataRoot.GetFavListCaption(i-1))));
- }
- else
+
+ if (!list.IsMixedSourceFavoritesList)
this.comboSource.Properties.Items.Add(new ListOption(list, 0, list.Caption));
+
+ for (int i = 1; i <= serializer.DataRoot.FavListCount; i++)
+ this.comboSource.Properties.Items.Add(new ListOption(list, i, list + " - " + serializer.DataRoot.GetFavListCaption(i-1)));
}
this.comboTarget.EditValue = null;
@@ -149,7 +148,7 @@ namespace ChanSort.Ui
continue;
if (list.IsMixedSourceFavoritesList)
{
- for (int i = 0; i <= list.FavListCount; i++)
+ for (int i = 0; i <= main.DataRoot.FavListCount; i++)
this.comboTarget.Properties.Items.Add(new ListOption(list, i, list + (i==0 ? "" : " - " + main.DataRoot.GetFavListCaption(i-1))));
}
else
@@ -341,7 +340,7 @@ namespace ChanSort.Ui
switch (dlg.ShowDialog(this))
{
case DialogResult.OK:
- target.ChannelList.Channels.ForEach(ch => ch.NewProgramNr = -1);
+ target.ChannelList.Channels.ForEach(ch => ch.SetPosition(target.PosIndex, -1));
break;
case DialogResult.Yes:
//overwrite = true;
@@ -355,7 +354,7 @@ namespace ChanSort.Ui
}
}
- main.Editor.ApplyReferenceList(this.serializer.DataRoot, src.ChannelList, target.ChannelList, false, offset, FilterChannel, overwrite, this.cbConsecutive.Checked);
+ main.Editor.ApplyReferenceList(this.serializer.DataRoot, src.ChannelList, src.PosIndex, target.ChannelList, target.PosIndex, false, offset, FilterChannel, overwrite, this.cbConsecutive.Checked);
main.RefreshGrids();
}
diff --git a/source/Test.Loader.M3u/M3uTest.cs b/source/Test.Loader.M3u/M3uTest.cs
index 8958087..4922a5d 100644
--- a/source/Test.Loader.M3u/M3uTest.cs
+++ b/source/Test.Loader.M3u/M3uTest.cs
@@ -39,7 +39,7 @@ namespace Test.Loader.M3u
ed.DataRoot = ser.DataRoot;
ed.ChannelList = lists[0];
//ed.ApplyReferenceList(refSer.DataRoot);
- ed.ApplyReferenceList(refSer.DataRoot, refSer.DataRoot.ChannelLists.First(), lists[0], false, 0, null, true, false);
+ ed.ApplyReferenceList(refSer.DataRoot, refSer.DataRoot.ChannelLists.First(), 0, lists[0], 0,false, 0, null, true, false);
Assert.AreEqual(1, chans[5].NewProgramNr);
Assert.AreEqual(2, chans[4].NewProgramNr);
diff --git a/source/Test.Loader.Philips/PhilipsBinS2channellibTest.cs b/source/Test.Loader.Philips/PhilipsBinS2channellibTest.cs
index 475e6a6..61db45c 100644
--- a/source/Test.Loader.Philips/PhilipsBinS2channellibTest.cs
+++ b/source/Test.Loader.Philips/PhilipsBinS2channellibTest.cs
@@ -88,9 +88,9 @@ namespace Test.Loader.Philips
var ch8 = list.Channels.FirstOrDefault(ch => ch.RecordIndex == 8);
Assert.IsTrue(ch8.IsDeleted);
- Assert.AreEqual(1, ch4.OldFavIndex[0]);
- Assert.AreEqual(2, ch7.OldFavIndex[0]);
- Assert.AreEqual(3, ch3.OldFavIndex[0]);
+ Assert.AreEqual(1, ch4.GetOldPosition(1));
+ Assert.AreEqual(2, ch7.GetOldPosition(1));
+ Assert.AreEqual(3, ch3.GetOldPosition(1));
}
}
diff --git a/source/changelog.md b/source/changelog.md
index 92386a9..680b782 100644
--- a/source/changelog.md
+++ b/source/changelog.md
@@ -1,6 +1,13 @@
ChanSort Change Log
===================
+2021-03-13 (alpha)
+- Enigma2 lamedb / bouquets support for Linux based Set-Top-Boxes (Dreambox, VU+, Octagon, ...)
+- Toshiba settingsDB.db: support for lists without analog tuner data (missing TADTunerDataTable)
+- Grunding: failed to load lists where the element did not contain a child element
+- W.I.P: reworking the reference list system so that a given flat list of channels can be applied to the
+ main channel numbers or a particular favorite list.
+
2021-02-24
- Philips ChannelMap\_45: TV did not remember last selected favorite list when first fav list was created by ChanSort.
- Philips ChannelMap\_100 and later: "Channel" XML elements inside the DVB\*.xml files are now reordered by program nr.