mirror of
https://github.com/jellyfin/jellyfin.git
synced 2024-09-06 03:26:07 +02:00
add subtitle delivery methods to StreamBuilder
This commit is contained in:
parent
97c5b468a0
commit
b4b17d7717
87 changed files with 1887 additions and 504 deletions
|
@ -45,6 +45,16 @@ namespace MediaBrowser.Api.Sync
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Route("/Sync/Jobs", "POST", Summary = "Gets sync jobs.")]
|
||||||
|
public class CreateSyncJob : SyncJobRequest
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
[Route("/Sync/Schedules", "POST", Summary = "Gets sync schedules.")]
|
||||||
|
public class CreateSyncSchedule : SyncScheduleRequest
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
[Authenticated]
|
[Authenticated]
|
||||||
public class SyncService : BaseApiService
|
public class SyncService : BaseApiService
|
||||||
{
|
{
|
||||||
|
@ -102,5 +112,19 @@ namespace MediaBrowser.Api.Sync
|
||||||
|
|
||||||
Task.WaitAll(task);
|
Task.WaitAll(task);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void Post(CreateSyncJob request)
|
||||||
|
{
|
||||||
|
var task = _syncManager.CreateJob(request);
|
||||||
|
|
||||||
|
Task.WaitAll(task);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Post(CreateSyncSchedule request)
|
||||||
|
{
|
||||||
|
var task = _syncManager.CreateSchedule(request);
|
||||||
|
|
||||||
|
Task.WaitAll(task);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,4 +6,9 @@ namespace MediaBrowser.Controller.Channels
|
||||||
{
|
{
|
||||||
IEnumerable<IChannel> GetChannels();
|
IEnumerable<IChannel> GetChannels();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public interface IFactoryChannel
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -1,45 +1,91 @@
|
||||||
using MediaBrowser.Controller.Channels;
|
using MediaBrowser.Controller.Channels;
|
||||||
using MediaBrowser.Controller.Providers;
|
using MediaBrowser.Controller.Providers;
|
||||||
|
using MediaBrowser.Dlna.PlayTo;
|
||||||
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
using MediaBrowser.Model.Entities;
|
using MediaBrowser.Model.Entities;
|
||||||
|
using MediaBrowser.Model.Events;
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.Channels
|
namespace MediaBrowser.Dlna.Channels
|
||||||
{
|
{
|
||||||
public class DlnaChannelFactory : IChannelFactory
|
public class DlnaChannelFactory : IChannelFactory, IDisposable
|
||||||
{
|
{
|
||||||
|
private DeviceDiscovery _deviceDiscovery;
|
||||||
|
|
||||||
|
private readonly object _syncLock = new object();
|
||||||
|
private readonly List<Device> _servers = new List<Device>();
|
||||||
|
|
||||||
|
public static DlnaChannelFactory Instance;
|
||||||
|
|
||||||
|
public DlnaChannelFactory()
|
||||||
|
{
|
||||||
|
Instance = this;
|
||||||
|
}
|
||||||
|
|
||||||
|
internal void Start(DeviceDiscovery deviceDiscovery)
|
||||||
|
{
|
||||||
|
_deviceDiscovery = deviceDiscovery;
|
||||||
|
deviceDiscovery.DeviceDiscovered += deviceDiscovery_DeviceDiscovered;
|
||||||
|
}
|
||||||
|
|
||||||
|
void deviceDiscovery_DeviceDiscovered(object sender, GenericEventArgs<DeviceDiscoveryInfo> e)
|
||||||
|
{
|
||||||
|
var usn = e.Argument.Usn;
|
||||||
|
var nt = e.Argument.Nt;
|
||||||
|
|
||||||
|
// It has to report that it's a media renderer
|
||||||
|
if (usn.IndexOf("ContentDirectory:", StringComparison.OrdinalIgnoreCase) == -1 &&
|
||||||
|
nt.IndexOf("ContentDirectory:", StringComparison.OrdinalIgnoreCase) == -1)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_servers.Any(i => usn.IndexOf(i.Properties.UUID, StringComparison.OrdinalIgnoreCase) != -1))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
lock (_syncLock)
|
||||||
|
{
|
||||||
|
_servers.Add(e.Argument.Device);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public IEnumerable<IChannel> GetChannels()
|
public IEnumerable<IChannel> GetChannels()
|
||||||
{
|
{
|
||||||
// Check config here
|
return _servers.Select(i => new ServerChannel(i)).ToList();
|
||||||
// If user wants all channels separate, return them all
|
}
|
||||||
// If user wants one parent channel, return just that one
|
|
||||||
|
|
||||||
return new List<IChannel>()
|
public void Dispose()
|
||||||
|
{
|
||||||
|
if (_deviceDiscovery != null)
|
||||||
{
|
{
|
||||||
//new DummyChannel("test 1"),
|
_deviceDiscovery.DeviceDiscovered -= deviceDiscovery_DeviceDiscovered;
|
||||||
//new DummyChannel("test 2")
|
}
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class DummyChannel : IChannel
|
public class ServerChannel : IChannel, IFactoryChannel
|
||||||
{
|
{
|
||||||
private readonly string _name;
|
private readonly Device _device;
|
||||||
|
|
||||||
public DummyChannel(string name)
|
public ServerChannel(Device device)
|
||||||
{
|
{
|
||||||
_name = name;
|
_device = device;
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Name
|
public string Name
|
||||||
{
|
{
|
||||||
get { return _name; }
|
get { return _device.Properties.Name; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Description
|
public string Description
|
||||||
{
|
{
|
||||||
get { return "Dummy Channel"; }
|
get { return _device.Properties.ModelDescription; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public string DataVersion
|
public string DataVersion
|
||||||
|
@ -49,7 +95,7 @@ namespace MediaBrowser.Dlna.Channels
|
||||||
|
|
||||||
public string HomePageUrl
|
public string HomePageUrl
|
||||||
{
|
{
|
||||||
get { return "http://www.google.com"; }
|
get { return _device.Properties.ModelUrl; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public ChannelParentalRating ParentalRating
|
public ChannelParentalRating ParentalRating
|
||||||
|
|
|
@ -9,6 +9,7 @@ using MediaBrowser.Controller.Library;
|
||||||
using MediaBrowser.Controller.Persistence;
|
using MediaBrowser.Controller.Persistence;
|
||||||
using MediaBrowser.Controller.Plugins;
|
using MediaBrowser.Controller.Plugins;
|
||||||
using MediaBrowser.Controller.Session;
|
using MediaBrowser.Controller.Session;
|
||||||
|
using MediaBrowser.Dlna.Channels;
|
||||||
using MediaBrowser.Dlna.PlayTo;
|
using MediaBrowser.Dlna.PlayTo;
|
||||||
using MediaBrowser.Dlna.Ssdp;
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
using MediaBrowser.Model.Logging;
|
using MediaBrowser.Model.Logging;
|
||||||
|
@ -35,6 +36,7 @@ namespace MediaBrowser.Dlna.Main
|
||||||
private readonly IImageProcessor _imageProcessor;
|
private readonly IImageProcessor _imageProcessor;
|
||||||
|
|
||||||
private SsdpHandler _ssdpHandler;
|
private SsdpHandler _ssdpHandler;
|
||||||
|
private DeviceDiscovery _deviceDiscovery;
|
||||||
|
|
||||||
private readonly List<Guid> _registeredServerIds = new List<Guid>();
|
private readonly List<Guid> _registeredServerIds = new List<Guid>();
|
||||||
private bool _dlnaServerStarted;
|
private bool _dlnaServerStarted;
|
||||||
|
@ -60,6 +62,8 @@ namespace MediaBrowser.Dlna.Main
|
||||||
ReloadComponents();
|
ReloadComponents();
|
||||||
|
|
||||||
_config.NamedConfigurationUpdated += _config_NamedConfigurationUpdated;
|
_config.NamedConfigurationUpdated += _config_NamedConfigurationUpdated;
|
||||||
|
|
||||||
|
DlnaChannelFactory.Instance.Start(_deviceDiscovery);
|
||||||
}
|
}
|
||||||
|
|
||||||
void _config_NamedConfigurationUpdated(object sender, ConfigurationUpdateEventArgs e)
|
void _config_NamedConfigurationUpdated(object sender, ConfigurationUpdateEventArgs e)
|
||||||
|
@ -104,15 +108,28 @@ namespace MediaBrowser.Dlna.Main
|
||||||
_ssdpHandler = new SsdpHandler(_logger, _config, GenerateServerSignature());
|
_ssdpHandler = new SsdpHandler(_logger, _config, GenerateServerSignature());
|
||||||
|
|
||||||
_ssdpHandler.Start();
|
_ssdpHandler.Start();
|
||||||
|
|
||||||
|
_deviceDiscovery = new DeviceDiscovery(_logger, _config, _httpClient, _ssdpHandler);
|
||||||
|
|
||||||
|
_deviceDiscovery.Start();
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
_logger.ErrorException("Error starting Dlna server", ex);
|
_logger.ErrorException("Error starting ssdp handlers", ex);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void DisposeSsdpHandler()
|
private void DisposeSsdpHandler()
|
||||||
{
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
_deviceDiscovery.Dispose();
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error disposing device discovery", ex);
|
||||||
|
}
|
||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
_ssdpHandler.Dispose();
|
_ssdpHandler.Dispose();
|
||||||
|
@ -192,16 +209,15 @@ namespace MediaBrowser.Dlna.Main
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
_manager = new PlayToManager(_logger,
|
_manager = new PlayToManager(_logger,
|
||||||
_config,
|
|
||||||
_sessionManager,
|
_sessionManager,
|
||||||
_httpClient,
|
|
||||||
_itemRepo,
|
_itemRepo,
|
||||||
_libraryManager,
|
_libraryManager,
|
||||||
_userManager,
|
_userManager,
|
||||||
_dlnaManager,
|
_dlnaManager,
|
||||||
_appHost,
|
_appHost,
|
||||||
_imageProcessor,
|
_imageProcessor,
|
||||||
_ssdpHandler);
|
_ssdpHandler,
|
||||||
|
_deviceDiscovery);
|
||||||
|
|
||||||
_manager.Start();
|
_manager.Start();
|
||||||
}
|
}
|
||||||
|
|
|
@ -72,7 +72,8 @@
|
||||||
<Compile Include="Common\DeviceService.cs" />
|
<Compile Include="Common\DeviceService.cs" />
|
||||||
<Compile Include="Didl\DidlBuilder.cs" />
|
<Compile Include="Didl\DidlBuilder.cs" />
|
||||||
<Compile Include="PlayTo\PlayToController.cs" />
|
<Compile Include="PlayTo\PlayToController.cs" />
|
||||||
<Compile Include="PlayTo\Extensions.cs" />
|
<Compile Include="Ssdp\DeviceDiscoveryInfo.cs" />
|
||||||
|
<Compile Include="Ssdp\Extensions.cs" />
|
||||||
<Compile Include="PlayTo\PlaybackProgressEventArgs.cs" />
|
<Compile Include="PlayTo\PlaybackProgressEventArgs.cs" />
|
||||||
<Compile Include="PlayTo\PlaybackStoppedEventArgs.cs" />
|
<Compile Include="PlayTo\PlaybackStoppedEventArgs.cs" />
|
||||||
<Compile Include="PlayTo\PlaylistItem.cs">
|
<Compile Include="PlayTo\PlaylistItem.cs">
|
||||||
|
@ -99,6 +100,7 @@
|
||||||
<Compile Include="Service\ServiceXmlBuilder.cs" />
|
<Compile Include="Service\ServiceXmlBuilder.cs" />
|
||||||
<Compile Include="Ssdp\Datagram.cs" />
|
<Compile Include="Ssdp\Datagram.cs" />
|
||||||
<Compile Include="Server\DescriptionXmlBuilder.cs" />
|
<Compile Include="Server\DescriptionXmlBuilder.cs" />
|
||||||
|
<Compile Include="Ssdp\DeviceDiscovery.cs" />
|
||||||
<Compile Include="Ssdp\SsdpHelper.cs" />
|
<Compile Include="Ssdp\SsdpHelper.cs" />
|
||||||
<Compile Include="PlayTo\SsdpHttpClient.cs" />
|
<Compile Include="PlayTo\SsdpHttpClient.cs" />
|
||||||
<Compile Include="Common\StateVariable.cs" />
|
<Compile Include="Common\StateVariable.cs" />
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
using MediaBrowser.Common.Net;
|
using MediaBrowser.Common.Net;
|
||||||
using MediaBrowser.Controller.Configuration;
|
using MediaBrowser.Controller.Configuration;
|
||||||
using MediaBrowser.Dlna.Common;
|
using MediaBrowser.Dlna.Common;
|
||||||
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
using MediaBrowser.Model.Logging;
|
using MediaBrowser.Model.Logging;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
|
@ -1,51 +1,39 @@
|
||||||
using MediaBrowser.Common.Net;
|
using MediaBrowser.Controller;
|
||||||
using MediaBrowser.Controller;
|
|
||||||
using MediaBrowser.Controller.Configuration;
|
|
||||||
using MediaBrowser.Controller.Dlna;
|
using MediaBrowser.Controller.Dlna;
|
||||||
using MediaBrowser.Controller.Drawing;
|
using MediaBrowser.Controller.Drawing;
|
||||||
using MediaBrowser.Controller.Library;
|
using MediaBrowser.Controller.Library;
|
||||||
using MediaBrowser.Controller.Persistence;
|
using MediaBrowser.Controller.Persistence;
|
||||||
using MediaBrowser.Controller.Session;
|
using MediaBrowser.Controller.Session;
|
||||||
using MediaBrowser.Dlna.Ssdp;
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
|
using MediaBrowser.Model.Events;
|
||||||
using MediaBrowser.Model.Logging;
|
using MediaBrowser.Model.Logging;
|
||||||
using MediaBrowser.Model.Session;
|
using MediaBrowser.Model.Session;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Net;
|
using System.Net;
|
||||||
using System.Net.NetworkInformation;
|
|
||||||
using System.Net.Sockets;
|
|
||||||
using System.Text;
|
|
||||||
using System.Threading;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.PlayTo
|
namespace MediaBrowser.Dlna.PlayTo
|
||||||
{
|
{
|
||||||
class PlayToManager : IDisposable
|
class PlayToManager : IDisposable
|
||||||
{
|
{
|
||||||
private bool _disposed;
|
|
||||||
private readonly ILogger _logger;
|
private readonly ILogger _logger;
|
||||||
private readonly ISessionManager _sessionManager;
|
private readonly ISessionManager _sessionManager;
|
||||||
private readonly IHttpClient _httpClient;
|
|
||||||
private readonly CancellationTokenSource _tokenSource;
|
|
||||||
|
|
||||||
private readonly IItemRepository _itemRepository;
|
private readonly IItemRepository _itemRepository;
|
||||||
private readonly ILibraryManager _libraryManager;
|
private readonly ILibraryManager _libraryManager;
|
||||||
private readonly IUserManager _userManager;
|
private readonly IUserManager _userManager;
|
||||||
private readonly IDlnaManager _dlnaManager;
|
private readonly IDlnaManager _dlnaManager;
|
||||||
private readonly IServerConfigurationManager _config;
|
|
||||||
private readonly IServerApplicationHost _appHost;
|
private readonly IServerApplicationHost _appHost;
|
||||||
private readonly IImageProcessor _imageProcessor;
|
private readonly IImageProcessor _imageProcessor;
|
||||||
|
|
||||||
private readonly SsdpHandler _ssdpHandler;
|
private readonly SsdpHandler _ssdpHandler;
|
||||||
|
private readonly DeviceDiscovery _deviceDiscovery;
|
||||||
|
|
||||||
public PlayToManager(ILogger logger, IServerConfigurationManager config, ISessionManager sessionManager, IHttpClient httpClient, IItemRepository itemRepository, ILibraryManager libraryManager, IUserManager userManager, IDlnaManager dlnaManager, IServerApplicationHost appHost, IImageProcessor imageProcessor, SsdpHandler ssdpHandler)
|
public PlayToManager(ILogger logger, ISessionManager sessionManager, IItemRepository itemRepository, ILibraryManager libraryManager, IUserManager userManager, IDlnaManager dlnaManager, IServerApplicationHost appHost, IImageProcessor imageProcessor, SsdpHandler ssdpHandler, DeviceDiscovery deviceDiscovery)
|
||||||
{
|
{
|
||||||
_tokenSource = new CancellationTokenSource();
|
|
||||||
|
|
||||||
_logger = logger;
|
_logger = logger;
|
||||||
_sessionManager = sessionManager;
|
_sessionManager = sessionManager;
|
||||||
_httpClient = httpClient;
|
|
||||||
_itemRepository = itemRepository;
|
_itemRepository = itemRepository;
|
||||||
_libraryManager = libraryManager;
|
_libraryManager = libraryManager;
|
||||||
_userManager = userManager;
|
_userManager = userManager;
|
||||||
|
@ -53,118 +41,21 @@ namespace MediaBrowser.Dlna.PlayTo
|
||||||
_appHost = appHost;
|
_appHost = appHost;
|
||||||
_imageProcessor = imageProcessor;
|
_imageProcessor = imageProcessor;
|
||||||
_ssdpHandler = ssdpHandler;
|
_ssdpHandler = ssdpHandler;
|
||||||
_config = config;
|
_deviceDiscovery = deviceDiscovery;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Start()
|
public void Start()
|
||||||
{
|
{
|
||||||
foreach (var network in GetNetworkInterfaces())
|
_deviceDiscovery.DeviceDiscovered += _deviceDiscovery_DeviceDiscovered;
|
||||||
{
|
|
||||||
_logger.Debug("Found interface: {0}. Type: {1}. Status: {2}", network.Name, network.NetworkInterfaceType, network.OperationalStatus);
|
|
||||||
|
|
||||||
if (!network.SupportsMulticast || OperationalStatus.Up != network.OperationalStatus || !network.GetIPProperties().MulticastAddresses.Any())
|
|
||||||
continue;
|
|
||||||
|
|
||||||
var ipV4 = network.GetIPProperties().GetIPv4Properties();
|
|
||||||
if (null == ipV4)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
var localIp = network.GetIPProperties().UnicastAddresses
|
|
||||||
.Where(i => i.Address.AddressFamily == AddressFamily.InterNetwork)
|
|
||||||
.Select(i => i.Address)
|
|
||||||
.FirstOrDefault();
|
|
||||||
|
|
||||||
if (localIp != null)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
CreateListener(localIp, ipV4.Index);
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Failed to Initilize Socket", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private IEnumerable<NetworkInterface> GetNetworkInterfaces()
|
async void _deviceDiscovery_DeviceDiscovered(object sender, GenericEventArgs<DeviceDiscoveryInfo> e)
|
||||||
{
|
{
|
||||||
try
|
var device = e.Argument.Device;
|
||||||
{
|
var localIp = e.Argument.LocalIpAddress;
|
||||||
return NetworkInterface.GetAllNetworkInterfaces();
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Error in GetAllNetworkInterfaces", ex);
|
|
||||||
return new List<NetworkInterface>();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
var usn = e.Argument.Usn;
|
||||||
/// Creates a socket for the interface and listends for data.
|
var nt = e.Argument.Nt;
|
||||||
/// </summary>
|
|
||||||
/// <param name="localIp">The local ip.</param>
|
|
||||||
/// <param name="networkInterfaceIndex">Index of the network interface.</param>
|
|
||||||
private void CreateListener(IPAddress localIp, int networkInterfaceIndex)
|
|
||||||
{
|
|
||||||
Task.Factory.StartNew(async (o) =>
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var socket = GetMulticastSocket(networkInterfaceIndex);
|
|
||||||
|
|
||||||
var endPoint = new IPEndPoint(localIp, 1900);
|
|
||||||
|
|
||||||
socket.Bind(endPoint);
|
|
||||||
|
|
||||||
_logger.Info("Creating SSDP listener on {0}, network interface index {1}", localIp, networkInterfaceIndex);
|
|
||||||
|
|
||||||
var receiveBuffer = new byte[64000];
|
|
||||||
|
|
||||||
CreateNotifier(socket);
|
|
||||||
|
|
||||||
while (!_tokenSource.IsCancellationRequested)
|
|
||||||
{
|
|
||||||
var receivedBytes = await socket.ReceiveAsync(receiveBuffer, 0, 64000);
|
|
||||||
|
|
||||||
if (receivedBytes > 0)
|
|
||||||
{
|
|
||||||
var args = SsdpHelper.ParseSsdpResponse(receiveBuffer, endPoint);
|
|
||||||
|
|
||||||
TryCreateController(args, localIp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_logger.Info("SSDP listener - Task completed");
|
|
||||||
}
|
|
||||||
catch (OperationCanceledException)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Error in listener", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void TryCreateController(SsdpMessageEventArgs args, IPAddress localIp)
|
|
||||||
{
|
|
||||||
string nts;
|
|
||||||
args.Headers.TryGetValue("NTS", out nts);
|
|
||||||
|
|
||||||
string usn;
|
|
||||||
if (!args.Headers.TryGetValue("USN", out usn)) usn = string.Empty;
|
|
||||||
|
|
||||||
string nt;
|
|
||||||
if (!args.Headers.TryGetValue("NT", out nt)) nt = string.Empty;
|
|
||||||
|
|
||||||
// Don't create a new controller when a device is indicating it's shutting down
|
|
||||||
if (string.Equals(nts, "ssdp:byebye", StringComparison.OrdinalIgnoreCase))
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// It has to report that it's a media renderer
|
// It has to report that it's a media renderer
|
||||||
if (usn.IndexOf("MediaRenderer:", StringComparison.OrdinalIgnoreCase) == -1 &&
|
if (usn.IndexOf("MediaRenderer:", StringComparison.OrdinalIgnoreCase) == -1 &&
|
||||||
|
@ -173,125 +64,15 @@ namespace MediaBrowser.Dlna.PlayTo
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Need to be able to download device description
|
|
||||||
string location;
|
|
||||||
if (!args.Headers.TryGetValue("Location", out location) ||
|
|
||||||
string.IsNullOrEmpty(location))
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_config.GetDlnaConfiguration().EnableDebugLogging)
|
|
||||||
{
|
|
||||||
var headerTexts = args.Headers.Select(i => string.Format("{0}={1}", i.Key, i.Value));
|
|
||||||
var headerText = string.Join(",", headerTexts.ToArray());
|
|
||||||
|
|
||||||
_logger.Debug("{0} PlayTo message received from {1}. Headers: {2}", args.Method, args.EndPoint, headerText);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_sessionManager.Sessions.Any(i => usn.IndexOf(i.DeviceId, StringComparison.OrdinalIgnoreCase) != -1))
|
if (_sessionManager.Sessions.Any(i => usn.IndexOf(i.DeviceId, StringComparison.OrdinalIgnoreCase) != -1))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Task.Run(async () =>
|
if (device.RendererCommands != null)
|
||||||
{
|
{
|
||||||
try
|
var uri = e.Argument.Uri;
|
||||||
{
|
|
||||||
await CreateController(new Uri(location), localIp).ConfigureAwait(false);
|
|
||||||
}
|
|
||||||
catch (OperationCanceledException)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Error creating play to controller", ex);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
private void CreateNotifier(IPAddress localIp)
|
|
||||||
{
|
|
||||||
Task.Factory.StartNew(async (o) =>
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
_ssdpHandler.SendRendererSearchMessage(new IPEndPoint(localIp, 1900));
|
|
||||||
|
|
||||||
var delay = _config.GetDlnaConfiguration().ClientDiscoveryIntervalSeconds * 1000;
|
|
||||||
|
|
||||||
await Task.Delay(delay, _tokenSource.Token).ConfigureAwait(false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (OperationCanceledException)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Error in notifier", ex);
|
|
||||||
}
|
|
||||||
|
|
||||||
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private void CreateNotifier(Socket socket)
|
|
||||||
{
|
|
||||||
Task.Factory.StartNew(async (o) =>
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
var msg = new SsdpMessageBuilder().BuildRendererDiscoveryMessage();
|
|
||||||
var request = Encoding.UTF8.GetBytes(msg);
|
|
||||||
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
socket.SendTo(request, new IPEndPoint(IPAddress.Parse("239.255.255.250"), 1900));
|
|
||||||
|
|
||||||
var delay = _config.GetDlnaConfiguration().ClientDiscoveryIntervalSeconds * 1000;
|
|
||||||
|
|
||||||
await Task.Delay(delay).ConfigureAwait(false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (OperationCanceledException)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.ErrorException("Error in notifier", ex);
|
|
||||||
}
|
|
||||||
|
|
||||||
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Gets a socket configured for SDDP multicasting.
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
private Socket GetMulticastSocket(int networkInterfaceIndex)
|
|
||||||
{
|
|
||||||
var socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
|
|
||||||
socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
|
|
||||||
socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(IPAddress.Parse("239.255.255.250"), networkInterfaceIndex));
|
|
||||||
socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastTimeToLive, 4);
|
|
||||||
return socket;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// Creates a new DlnaSessionController.
|
|
||||||
/// and logs the session in SessionManager
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="uri">The URI.</param>
|
|
||||||
/// <returns></returns>
|
|
||||||
private async Task CreateController(Uri uri, IPAddress localIp)
|
|
||||||
{
|
|
||||||
var device = await Device.CreateuPnpDeviceAsync(uri, _httpClient, _config, _logger).ConfigureAwait(false);
|
|
||||||
|
|
||||||
if (device != null && device.RendererCommands != null)
|
|
||||||
{
|
|
||||||
var sessionInfo = await _sessionManager.LogSessionActivity(device.Properties.ClientType, _appHost.ApplicationVersion.ToString(), device.Properties.UUID, device.Properties.Name, uri.OriginalString, null)
|
var sessionInfo = await _sessionManager.LogSessionActivity(device.Properties.ClientType, _appHost.ApplicationVersion.ToString(), device.Properties.UUID, device.Properties.Name, uri.OriginalString, null)
|
||||||
.ConfigureAwait(false);
|
.ConfigureAwait(false);
|
||||||
|
|
||||||
|
@ -353,11 +134,7 @@ namespace MediaBrowser.Dlna.PlayTo
|
||||||
|
|
||||||
public void Dispose()
|
public void Dispose()
|
||||||
{
|
{
|
||||||
if (!_disposed)
|
_deviceDiscovery.DeviceDiscovered -= _deviceDiscovery_DeviceDiscovered;
|
||||||
{
|
|
||||||
_disposed = true;
|
|
||||||
_tokenSource.Cancel();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ using MediaBrowser.Dlna.Common;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Xml.Linq;
|
using System.Xml.Linq;
|
||||||
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.PlayTo
|
namespace MediaBrowser.Dlna.PlayTo
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Xml.Linq;
|
using System.Xml.Linq;
|
||||||
|
using MediaBrowser.Dlna.Ssdp;
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.PlayTo
|
namespace MediaBrowser.Dlna.PlayTo
|
||||||
{
|
{
|
||||||
|
|
|
@ -1,5 +1,4 @@
|
||||||
using MediaBrowser.Model.Dlna;
|
using MediaBrowser.Model.Dlna;
|
||||||
using MediaBrowser.Model.MediaInfo;
|
|
||||||
using System.Xml.Serialization;
|
using System.Xml.Serialization;
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.Profiles
|
namespace MediaBrowser.Dlna.Profiles
|
||||||
|
@ -28,6 +27,8 @@ namespace MediaBrowser.Dlna.Profiles
|
||||||
MaxAlbumArtHeight = 512;
|
MaxAlbumArtHeight = 512;
|
||||||
MaxAlbumArtWidth = 512;
|
MaxAlbumArtWidth = 512;
|
||||||
|
|
||||||
|
MaxBitrate = 8000000;
|
||||||
|
|
||||||
TranscodingProfiles = new[]
|
TranscodingProfiles = new[]
|
||||||
{
|
{
|
||||||
new TranscodingProfile
|
new TranscodingProfile
|
||||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -23,7 +23,7 @@
|
||||||
<MaxAlbumArtHeight>512</MaxAlbumArtHeight>
|
<MaxAlbumArtHeight>512</MaxAlbumArtHeight>
|
||||||
<MaxIconWidth xsi:nil="true" />
|
<MaxIconWidth xsi:nil="true" />
|
||||||
<MaxIconHeight xsi:nil="true" />
|
<MaxIconHeight xsi:nil="true" />
|
||||||
<MaxBitrate xsi:nil="true" />
|
<MaxBitrate>8000000</MaxBitrate>
|
||||||
<XDlnaDoc>DMS-1.50</XDlnaDoc>
|
<XDlnaDoc>DMS-1.50</XDlnaDoc>
|
||||||
<SonyAggregationFlags>10</SonyAggregationFlags>
|
<SonyAggregationFlags>10</SonyAggregationFlags>
|
||||||
<ProtocolInfo>http-get:*:audio/mpeg:DLNA.ORG_PN=MP3;DLNA.ORG_OP=01;DLNA.ORG_FLAGS=81500000000000000000000000000000,http-get:*:image/jpeg:DLNA.ORG_PN=JPEG_SM;DLNA.ORG_OP=00;DLNA.ORG_FLAGS=00D00000000000000000000000000000,http-get:*:video/mpeg:DLNA.ORG_PN=MPEG_PS_PAL;DLNA.ORG_OP=11;DLNA.ORG_FLAGS=81500000000000000000000000000000</ProtocolInfo>
|
<ProtocolInfo>http-get:*:audio/mpeg:DLNA.ORG_PN=MP3;DLNA.ORG_OP=01;DLNA.ORG_FLAGS=81500000000000000000000000000000,http-get:*:image/jpeg:DLNA.ORG_PN=JPEG_SM;DLNA.ORG_OP=00;DLNA.ORG_FLAGS=00D00000000000000000000000000000,http-get:*:video/mpeg:DLNA.ORG_PN=MPEG_PS_PAL;DLNA.ORG_OP=11;DLNA.ORG_FLAGS=81500000000000000000000000000000</ProtocolInfo>
|
||||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
278
MediaBrowser.Dlna/Ssdp/DeviceDiscovery.cs
Normal file
278
MediaBrowser.Dlna/Ssdp/DeviceDiscovery.cs
Normal file
|
@ -0,0 +1,278 @@
|
||||||
|
using MediaBrowser.Common.Events;
|
||||||
|
using MediaBrowser.Common.Net;
|
||||||
|
using MediaBrowser.Controller.Configuration;
|
||||||
|
using MediaBrowser.Dlna.PlayTo;
|
||||||
|
using MediaBrowser.Model.Events;
|
||||||
|
using MediaBrowser.Model.Logging;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Net;
|
||||||
|
using System.Net.NetworkInformation;
|
||||||
|
using System.Net.Sockets;
|
||||||
|
using System.Text;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
|
namespace MediaBrowser.Dlna.Ssdp
|
||||||
|
{
|
||||||
|
public class DeviceDiscovery : IDisposable
|
||||||
|
{
|
||||||
|
private bool _disposed;
|
||||||
|
|
||||||
|
private readonly ILogger _logger;
|
||||||
|
private readonly IServerConfigurationManager _config;
|
||||||
|
private readonly SsdpHandler _ssdpHandler;
|
||||||
|
private readonly CancellationTokenSource _tokenSource;
|
||||||
|
private readonly IHttpClient _httpClient;
|
||||||
|
|
||||||
|
public event EventHandler<GenericEventArgs<DeviceDiscoveryInfo>> DeviceDiscovered;
|
||||||
|
|
||||||
|
public DeviceDiscovery(ILogger logger, IServerConfigurationManager config, IHttpClient httpClient, SsdpHandler ssdpHandler)
|
||||||
|
{
|
||||||
|
_tokenSource = new CancellationTokenSource();
|
||||||
|
|
||||||
|
_logger = logger;
|
||||||
|
_config = config;
|
||||||
|
_httpClient = httpClient;
|
||||||
|
_ssdpHandler = ssdpHandler;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Start()
|
||||||
|
{
|
||||||
|
//_ssdpHandler.MessageReceived += _ssdpHandler_MessageReceived;
|
||||||
|
|
||||||
|
foreach (var network in GetNetworkInterfaces())
|
||||||
|
{
|
||||||
|
_logger.Debug("Found interface: {0}. Type: {1}. Status: {2}", network.Name, network.NetworkInterfaceType, network.OperationalStatus);
|
||||||
|
|
||||||
|
if (!network.SupportsMulticast || OperationalStatus.Up != network.OperationalStatus || !network.GetIPProperties().MulticastAddresses.Any())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
var ipV4 = network.GetIPProperties().GetIPv4Properties();
|
||||||
|
if (null == ipV4)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
var localIp = network.GetIPProperties().UnicastAddresses
|
||||||
|
.Where(i => i.Address.AddressFamily == AddressFamily.InterNetwork)
|
||||||
|
.Select(i => i.Address)
|
||||||
|
.FirstOrDefault();
|
||||||
|
|
||||||
|
if (localIp != null)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
CreateListener(localIp, ipV4.Index);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Failed to Initilize Socket", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void _ssdpHandler_MessageReceived(object sender, SsdpMessageEventArgs e)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
private IEnumerable<NetworkInterface> GetNetworkInterfaces()
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return NetworkInterface.GetAllNetworkInterfaces();
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error in GetAllNetworkInterfaces", ex);
|
||||||
|
return new List<NetworkInterface>();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
private void CreateListener(IPAddress localIp, int networkInterfaceIndex)
|
||||||
|
{
|
||||||
|
Task.Factory.StartNew(async (o) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var socket = GetMulticastSocket(networkInterfaceIndex);
|
||||||
|
|
||||||
|
var endPoint = new IPEndPoint(localIp, 1900);
|
||||||
|
|
||||||
|
socket.Bind(endPoint);
|
||||||
|
|
||||||
|
_logger.Info("Creating SSDP listener on {0}, network interface index {1}", localIp, networkInterfaceIndex);
|
||||||
|
|
||||||
|
var receiveBuffer = new byte[64000];
|
||||||
|
|
||||||
|
CreateNotifier(localIp);
|
||||||
|
|
||||||
|
while (!_tokenSource.IsCancellationRequested)
|
||||||
|
{
|
||||||
|
var receivedBytes = await socket.ReceiveAsync(receiveBuffer, 0, 64000);
|
||||||
|
|
||||||
|
if (receivedBytes > 0)
|
||||||
|
{
|
||||||
|
var args = SsdpHelper.ParseSsdpResponse(receiveBuffer, endPoint);
|
||||||
|
|
||||||
|
TryCreateDevice(args, localIp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
_logger.Info("SSDP listener - Task completed");
|
||||||
|
}
|
||||||
|
catch (OperationCanceledException)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error in listener", e);
|
||||||
|
}
|
||||||
|
|
||||||
|
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CreateNotifier(IPAddress localIp)
|
||||||
|
{
|
||||||
|
Task.Factory.StartNew(async (o) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
while (true)
|
||||||
|
{
|
||||||
|
_ssdpHandler.SendSearchMessage(new IPEndPoint(localIp, 1900));
|
||||||
|
|
||||||
|
var delay = _config.GetDlnaConfiguration().ClientDiscoveryIntervalSeconds * 1000;
|
||||||
|
|
||||||
|
await Task.Delay(delay, _tokenSource.Token).ConfigureAwait(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (OperationCanceledException)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error in notifier", ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CreateNotifier(Socket socket)
|
||||||
|
{
|
||||||
|
Task.Factory.StartNew(async (o) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var msg = new SsdpMessageBuilder().BuildRendererDiscoveryMessage();
|
||||||
|
var request = Encoding.UTF8.GetBytes(msg);
|
||||||
|
|
||||||
|
while (true)
|
||||||
|
{
|
||||||
|
socket.SendTo(request, new IPEndPoint(IPAddress.Parse("239.255.255.250"), 1900));
|
||||||
|
|
||||||
|
var delay = _config.GetDlnaConfiguration().ClientDiscoveryIntervalSeconds * 1000;
|
||||||
|
|
||||||
|
await Task.Delay(delay).ConfigureAwait(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (OperationCanceledException)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error in notifier", ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
}, _tokenSource.Token, TaskCreationOptions.LongRunning);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private Socket GetMulticastSocket(int networkInterfaceIndex)
|
||||||
|
{
|
||||||
|
var socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
|
||||||
|
socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, true);
|
||||||
|
socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(IPAddress.Parse("239.255.255.250"), networkInterfaceIndex));
|
||||||
|
socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastTimeToLive, 4);
|
||||||
|
return socket;
|
||||||
|
}
|
||||||
|
|
||||||
|
private async void TryCreateDevice(SsdpMessageEventArgs args, IPAddress localIp)
|
||||||
|
{
|
||||||
|
string nts;
|
||||||
|
args.Headers.TryGetValue("NTS", out nts);
|
||||||
|
|
||||||
|
string usn;
|
||||||
|
if (!args.Headers.TryGetValue("USN", out usn)) usn = string.Empty;
|
||||||
|
|
||||||
|
string nt;
|
||||||
|
if (!args.Headers.TryGetValue("NT", out nt)) nt = string.Empty;
|
||||||
|
|
||||||
|
// Ignore when a device is indicating it's shutting down
|
||||||
|
if (string.Equals(nts, "ssdp:byebye", StringComparison.OrdinalIgnoreCase))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Need to be able to download device description
|
||||||
|
string location;
|
||||||
|
if (!args.Headers.TryGetValue("Location", out location) ||
|
||||||
|
string.IsNullOrEmpty(location))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_config.GetDlnaConfiguration().EnableDebugLogging)
|
||||||
|
{
|
||||||
|
var headerTexts = args.Headers.Select(i => string.Format("{0}={1}", i.Key, i.Value));
|
||||||
|
var headerText = string.Join(",", headerTexts.ToArray());
|
||||||
|
|
||||||
|
_logger.Debug("{0} Device message received from {1}. Headers: {2}", args.Method, args.EndPoint, headerText);
|
||||||
|
}
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
await TryCreateDevice(new Uri(location), localIp, usn, nt).ConfigureAwait(false);
|
||||||
|
}
|
||||||
|
catch (OperationCanceledException)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.ErrorException("Error creating play to controller", ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private async Task TryCreateDevice(Uri uri, IPAddress localIp, string usn, string nt)
|
||||||
|
{
|
||||||
|
var device = await Device.CreateuPnpDeviceAsync(uri, _httpClient, _config, _logger).ConfigureAwait(false);
|
||||||
|
|
||||||
|
if (device != null)
|
||||||
|
{
|
||||||
|
EventHelper.FireEventIfNotNull(DeviceDiscovered, this, new GenericEventArgs<DeviceDiscoveryInfo>
|
||||||
|
{
|
||||||
|
Argument = new DeviceDiscoveryInfo
|
||||||
|
{
|
||||||
|
Device = device,
|
||||||
|
LocalIpAddress = localIp,
|
||||||
|
Uri = uri,
|
||||||
|
Usn = usn,
|
||||||
|
Nt = nt
|
||||||
|
}
|
||||||
|
|
||||||
|
}, _logger);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
_ssdpHandler.MessageReceived -= _ssdpHandler_MessageReceived;
|
||||||
|
|
||||||
|
if (!_disposed)
|
||||||
|
{
|
||||||
|
_disposed = true;
|
||||||
|
_tokenSource.Cancel();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
21
MediaBrowser.Dlna/Ssdp/DeviceDiscoveryInfo.cs
Normal file
21
MediaBrowser.Dlna/Ssdp/DeviceDiscoveryInfo.cs
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
using MediaBrowser.Dlna.PlayTo;
|
||||||
|
using System;
|
||||||
|
using System.Net;
|
||||||
|
|
||||||
|
namespace MediaBrowser.Dlna.Ssdp
|
||||||
|
{
|
||||||
|
public class DeviceDiscoveryInfo
|
||||||
|
{
|
||||||
|
public Device Device { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The server's ip address that the device responded to
|
||||||
|
/// </summary>
|
||||||
|
public IPAddress LocalIpAddress { get; set; }
|
||||||
|
|
||||||
|
public Uri Uri { get; set; }
|
||||||
|
|
||||||
|
public string Usn { get; set; }
|
||||||
|
public string Nt { get; set; }
|
||||||
|
}
|
||||||
|
}
|
|
@ -5,7 +5,7 @@ using System.Net.Sockets;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using System.Xml.Linq;
|
using System.Xml.Linq;
|
||||||
|
|
||||||
namespace MediaBrowser.Dlna.PlayTo
|
namespace MediaBrowser.Dlna.Ssdp
|
||||||
{
|
{
|
||||||
public static class Extensions
|
public static class Extensions
|
||||||
{
|
{
|
|
@ -84,20 +84,15 @@ namespace MediaBrowser.Dlna.Ssdp
|
||||||
ReloadAliveNotifier();
|
ReloadAliveNotifier();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void SendRendererSearchMessage(IPEndPoint localIp)
|
public void SendSearchMessage(IPEndPoint localIp)
|
||||||
{
|
|
||||||
SendSearchMessage("urn:schemas-upnp-org:device:MediaRenderer:1", "3", localIp);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SendSearchMessage(string deviceSearchType, string mx, IPEndPoint localIp)
|
|
||||||
{
|
{
|
||||||
var values = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
|
var values = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
|
||||||
|
|
||||||
values["HOST"] = "239.255.255.250:1900";
|
values["HOST"] = "239.255.255.250:1900";
|
||||||
values["USER-AGENT"] = "UPnP/1.0 DLNADOC/1.50 Platinum/1.0.4.2";
|
values["USER-AGENT"] = "UPnP/1.0 DLNADOC/1.50 Platinum/1.0.4.2";
|
||||||
values["ST"] = deviceSearchType;
|
values["ST"] = "ssdp:all";
|
||||||
values["MAN"] = "\"ssdp:discover\"";
|
values["MAN"] = "\"ssdp:discover\"";
|
||||||
values["MX"] = mx;
|
values["MX"] = "10";
|
||||||
|
|
||||||
SendDatagram("M-SEARCH * HTTP/1.1", values, localIp);
|
SendDatagram("M-SEARCH * HTTP/1.1", values, localIp);
|
||||||
}
|
}
|
||||||
|
@ -271,7 +266,7 @@ namespace MediaBrowser.Dlna.Ssdp
|
||||||
var headerTexts = args.Headers.Select(i => string.Format("{0}={1}", i.Key, i.Value));
|
var headerTexts = args.Headers.Select(i => string.Format("{0}={1}", i.Key, i.Value));
|
||||||
var headerText = string.Join(",", headerTexts.ToArray());
|
var headerText = string.Join(",", headerTexts.ToArray());
|
||||||
|
|
||||||
_logger.Debug("{0} message received from {1}. Headers: {2}", args.Method, args.EndPoint, headerText);
|
_logger.Debug("{0} message received from {1} on {3}. Headers: {2}", args.Method, args.EndPoint, headerText, _socket.LocalEndPoint);
|
||||||
}
|
}
|
||||||
|
|
||||||
OnMessageReceived(args);
|
OnMessageReceived(args);
|
||||||
|
|
|
@ -32,9 +32,9 @@ namespace MediaBrowser.Dlna.Ssdp
|
||||||
|
|
||||||
values["HOST"] = "239.255.255.250:1900";
|
values["HOST"] = "239.255.255.250:1900";
|
||||||
values["USER-AGENT"] = "UPnP/1.0 DLNADOC/1.50 Platinum/1.0.4.2";
|
values["USER-AGENT"] = "UPnP/1.0 DLNADOC/1.50 Platinum/1.0.4.2";
|
||||||
values["ST"] = deviceSearchType;
|
values["ST"] = "ssdp:all";
|
||||||
values["MAN"] = "\"ssdp:discover\"";
|
values["MAN"] = "ssdp:discover";
|
||||||
values["MX"] = mx;
|
values["MX"] = "10";
|
||||||
|
|
||||||
return BuildMessage(header, values);
|
return BuildMessage(header, values);
|
||||||
}
|
}
|
||||||
|
@ -43,5 +43,10 @@ namespace MediaBrowser.Dlna.Ssdp
|
||||||
{
|
{
|
||||||
return BuildDiscoveryMessage("urn:schemas-upnp-org:device:MediaRenderer:1", "3");
|
return BuildDiscoveryMessage("urn:schemas-upnp-org:device:MediaRenderer:1", "3");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public string BuildMediaServerDiscoveryMessage()
|
||||||
|
{
|
||||||
|
return BuildDiscoveryMessage("urn:schemas-upnp-org:device:MediaRenderer:1", "3");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,6 +9,8 @@ namespace MediaBrowser.Model.Dlna
|
||||||
{
|
{
|
||||||
public class StreamBuilder
|
public class StreamBuilder
|
||||||
{
|
{
|
||||||
|
private string[] _serverTextSubtitleOutputs = new string[] { "srt", "vtt" };
|
||||||
|
|
||||||
public StreamInfo BuildAudioItem(AudioOptions options)
|
public StreamInfo BuildAudioItem(AudioOptions options)
|
||||||
{
|
{
|
||||||
ValidateAudioInput(options);
|
ValidateAudioInput(options);
|
||||||
|
@ -48,16 +50,13 @@ namespace MediaBrowser.Model.Dlna
|
||||||
|
|
||||||
List<MediaSourceInfo> mediaSources = options.MediaSources;
|
List<MediaSourceInfo> mediaSources = options.MediaSources;
|
||||||
|
|
||||||
// If the client wants a specific media soure, filter now
|
// If the client wants a specific media source, filter now
|
||||||
if (!string.IsNullOrEmpty(options.MediaSourceId))
|
if (!string.IsNullOrEmpty(options.MediaSourceId))
|
||||||
{
|
{
|
||||||
// Avoid implicitly captured closure
|
|
||||||
string mediaSourceId = options.MediaSourceId;
|
|
||||||
|
|
||||||
var newMediaSources = new List<MediaSourceInfo>();
|
var newMediaSources = new List<MediaSourceInfo>();
|
||||||
foreach (MediaSourceInfo i in mediaSources)
|
foreach (MediaSourceInfo i in mediaSources)
|
||||||
{
|
{
|
||||||
if (StringHelper.EqualsIgnoreCase(i.Id, mediaSourceId))
|
if (StringHelper.EqualsIgnoreCase(i.Id, options.MediaSourceId))
|
||||||
newMediaSources.Add(i);
|
newMediaSources.Add(i);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -217,12 +216,9 @@ namespace MediaBrowser.Model.Dlna
|
||||||
playlistItem.MaxAudioChannels = Math.Min(options.MaxAudioChannels.Value, currentValue);
|
playlistItem.MaxAudioChannels = Math.Min(options.MaxAudioChannels.Value, currentValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Honor requested max bitrate
|
if (!playlistItem.AudioBitrate.HasValue)
|
||||||
if (maxBitrateSetting.HasValue)
|
|
||||||
{
|
{
|
||||||
int currentValue = playlistItem.AudioBitrate ?? maxBitrateSetting.Value;
|
playlistItem.AudioBitrate = 128000;
|
||||||
|
|
||||||
playlistItem.AudioBitrate = Math.Min(maxBitrateSetting.Value, currentValue);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -239,12 +235,17 @@ namespace MediaBrowser.Model.Dlna
|
||||||
RunTimeTicks = item.RunTimeTicks
|
RunTimeTicks = item.RunTimeTicks
|
||||||
};
|
};
|
||||||
|
|
||||||
MediaStream audioStream = item.DefaultAudioStream;
|
int? audioStreamIndex = options.AudioStreamIndex ?? item.DefaultAudioStreamIndex;
|
||||||
|
playlistItem.SubtitleStreamIndex = options.SubtitleStreamIndex ?? item.DefaultSubtitleStreamIndex;
|
||||||
|
|
||||||
|
MediaStream audioStream = audioStreamIndex.HasValue ? item.GetMediaStream(MediaStreamType.Audio, audioStreamIndex.Value) : null;
|
||||||
|
MediaStream subtitleStream = playlistItem.SubtitleStreamIndex.HasValue ? item.GetMediaStream(MediaStreamType.Subtitle, playlistItem.SubtitleStreamIndex.Value) : null;
|
||||||
|
|
||||||
MediaStream videoStream = item.VideoStream;
|
MediaStream videoStream = item.VideoStream;
|
||||||
|
|
||||||
int? maxBitrateSetting = options.MaxBitrate ?? options.Profile.MaxBitrate;
|
int? maxBitrateSetting = options.MaxBitrate ?? options.Profile.MaxBitrate;
|
||||||
|
|
||||||
if (IsEligibleForDirectPlay(item, options, maxBitrateSetting))
|
if (IsEligibleForDirectPlay(item, maxBitrateSetting, subtitleStream, options))
|
||||||
{
|
{
|
||||||
// See if it can be direct played
|
// See if it can be direct played
|
||||||
DirectPlayProfile directPlay = GetVideoDirectPlayProfile(options.Profile, item, videoStream, audioStream);
|
DirectPlayProfile directPlay = GetVideoDirectPlayProfile(options.Profile, item, videoStream, audioStream);
|
||||||
|
@ -254,6 +255,11 @@ namespace MediaBrowser.Model.Dlna
|
||||||
playlistItem.IsDirectStream = true;
|
playlistItem.IsDirectStream = true;
|
||||||
playlistItem.Container = item.Container;
|
playlistItem.Container = item.Container;
|
||||||
|
|
||||||
|
if (subtitleStream != null)
|
||||||
|
{
|
||||||
|
playlistItem.SubtitleDeliveryMethod = GetDirectStreamSubtitleDeliveryMethod(subtitleStream, options);
|
||||||
|
}
|
||||||
|
|
||||||
return playlistItem;
|
return playlistItem;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -271,6 +277,11 @@ namespace MediaBrowser.Model.Dlna
|
||||||
|
|
||||||
if (transcodingProfile != null)
|
if (transcodingProfile != null)
|
||||||
{
|
{
|
||||||
|
if (subtitleStream != null)
|
||||||
|
{
|
||||||
|
playlistItem.SubtitleDeliveryMethod = GetTranscodedSubtitleDeliveryMethod(subtitleStream, options);
|
||||||
|
}
|
||||||
|
|
||||||
playlistItem.IsDirectStream = false;
|
playlistItem.IsDirectStream = false;
|
||||||
playlistItem.Container = transcodingProfile.Container;
|
playlistItem.Container = transcodingProfile.Container;
|
||||||
playlistItem.EstimateContentLength = transcodingProfile.EstimateContentLength;
|
playlistItem.EstimateContentLength = transcodingProfile.EstimateContentLength;
|
||||||
|
@ -278,8 +289,7 @@ namespace MediaBrowser.Model.Dlna
|
||||||
playlistItem.AudioCodec = transcodingProfile.AudioCodec.Split(',')[0];
|
playlistItem.AudioCodec = transcodingProfile.AudioCodec.Split(',')[0];
|
||||||
playlistItem.VideoCodec = transcodingProfile.VideoCodec;
|
playlistItem.VideoCodec = transcodingProfile.VideoCodec;
|
||||||
playlistItem.Protocol = transcodingProfile.Protocol;
|
playlistItem.Protocol = transcodingProfile.Protocol;
|
||||||
playlistItem.AudioStreamIndex = options.AudioStreamIndex ?? item.DefaultAudioStreamIndex;
|
playlistItem.AudioStreamIndex = audioStreamIndex;
|
||||||
playlistItem.SubtitleStreamIndex = options.SubtitleStreamIndex ?? item.DefaultSubtitleStreamIndex;
|
|
||||||
|
|
||||||
List<ProfileCondition> videoTranscodingConditions = new List<ProfileCondition>();
|
List<ProfileCondition> videoTranscodingConditions = new List<ProfileCondition>();
|
||||||
foreach (CodecProfile i in options.Profile.CodecProfiles)
|
foreach (CodecProfile i in options.Profile.CodecProfiles)
|
||||||
|
@ -317,12 +327,9 @@ namespace MediaBrowser.Model.Dlna
|
||||||
playlistItem.MaxAudioChannels = Math.Min(options.MaxAudioChannels.Value, currentValue);
|
playlistItem.MaxAudioChannels = Math.Min(options.MaxAudioChannels.Value, currentValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Honor requested max bitrate
|
if (!playlistItem.AudioBitrate.HasValue)
|
||||||
if (options.MaxAudioTranscodingBitrate.HasValue)
|
|
||||||
{
|
{
|
||||||
int currentValue = playlistItem.AudioBitrate ?? options.MaxAudioTranscodingBitrate.Value;
|
playlistItem.AudioBitrate = GetAudioBitrate(playlistItem.TargetAudioChannels, playlistItem.TargetAudioCodec);
|
||||||
|
|
||||||
playlistItem.AudioBitrate = Math.Min(options.MaxAudioTranscodingBitrate.Value, currentValue);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Honor max rate
|
// Honor max rate
|
||||||
|
@ -339,17 +346,24 @@ namespace MediaBrowser.Model.Dlna
|
||||||
|
|
||||||
playlistItem.VideoBitrate = Math.Min(videoBitrate, currentValue);
|
playlistItem.VideoBitrate = Math.Min(videoBitrate, currentValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Hate to hard-code this, but it's still probably better than being subjected to encoder defaults
|
|
||||||
if (!playlistItem.VideoBitrate.HasValue)
|
|
||||||
{
|
|
||||||
playlistItem.VideoBitrate = 5000000;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return playlistItem;
|
return playlistItem;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private int GetAudioBitrate(int? channels, string codec)
|
||||||
|
{
|
||||||
|
if (channels.HasValue)
|
||||||
|
{
|
||||||
|
if (channels.Value >= 5)
|
||||||
|
{
|
||||||
|
return 320000;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 128000;
|
||||||
|
}
|
||||||
|
|
||||||
private DirectPlayProfile GetVideoDirectPlayProfile(DeviceProfile profile,
|
private DirectPlayProfile GetVideoDirectPlayProfile(DeviceProfile profile,
|
||||||
MediaSourceInfo mediaSource,
|
MediaSourceInfo mediaSource,
|
||||||
MediaStream videoStream,
|
MediaStream videoStream,
|
||||||
|
@ -473,16 +487,105 @@ namespace MediaBrowser.Model.Dlna
|
||||||
return directPlay;
|
return directPlay;
|
||||||
}
|
}
|
||||||
|
|
||||||
private bool IsEligibleForDirectPlay(MediaSourceInfo item, VideoOptions options, int? maxBitrate)
|
private bool IsEligibleForDirectPlay(MediaSourceInfo item,
|
||||||
|
int? maxBitrate,
|
||||||
|
MediaStream subtitleStream,
|
||||||
|
VideoOptions options)
|
||||||
{
|
{
|
||||||
if (options.SubtitleStreamIndex.HasValue)
|
if (subtitleStream != null)
|
||||||
{
|
{
|
||||||
return false;
|
if (!subtitleStream.IsTextSubtitleStream)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
SubtitleDeliveryMethod subtitleMethod = GetDirectStreamSubtitleDeliveryMethod(subtitleStream, options);
|
||||||
|
|
||||||
|
if (subtitleMethod != SubtitleDeliveryMethod.External && subtitleMethod != SubtitleDeliveryMethod.Direct)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return IsAudioEligibleForDirectPlay(item, maxBitrate);
|
return IsAudioEligibleForDirectPlay(item, maxBitrate);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private SubtitleDeliveryMethod GetDirectStreamSubtitleDeliveryMethod(MediaStream subtitleStream,
|
||||||
|
VideoOptions options)
|
||||||
|
{
|
||||||
|
if (subtitleStream.IsTextSubtitleStream)
|
||||||
|
{
|
||||||
|
string subtitleFormat = NormalizeSubtitleFormat(subtitleStream.Codec);
|
||||||
|
|
||||||
|
bool supportsDirect = ContainsSubtitleFormat(options.Profile.SoftSubtitleProfiles, new[] { subtitleFormat });
|
||||||
|
|
||||||
|
if (supportsDirect)
|
||||||
|
{
|
||||||
|
return SubtitleDeliveryMethod.Direct;
|
||||||
|
}
|
||||||
|
|
||||||
|
// See if the device can retrieve the subtitles externally
|
||||||
|
bool supportsSubsExternally = options.Context == EncodingContext.Streaming &&
|
||||||
|
ContainsSubtitleFormat(options.Profile.ExternalSubtitleProfiles, _serverTextSubtitleOutputs);
|
||||||
|
|
||||||
|
if (supportsSubsExternally)
|
||||||
|
{
|
||||||
|
return SubtitleDeliveryMethod.External;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return SubtitleDeliveryMethod.Encode;
|
||||||
|
}
|
||||||
|
|
||||||
|
private SubtitleDeliveryMethod GetTranscodedSubtitleDeliveryMethod(MediaStream subtitleStream,
|
||||||
|
VideoOptions options)
|
||||||
|
{
|
||||||
|
if (subtitleStream.IsTextSubtitleStream)
|
||||||
|
{
|
||||||
|
// See if the device can retrieve the subtitles externally
|
||||||
|
bool supportsSubsExternally = options.Context == EncodingContext.Streaming &&
|
||||||
|
ContainsSubtitleFormat(options.Profile.ExternalSubtitleProfiles, _serverTextSubtitleOutputs);
|
||||||
|
|
||||||
|
if (supportsSubsExternally)
|
||||||
|
{
|
||||||
|
return SubtitleDeliveryMethod.External;
|
||||||
|
}
|
||||||
|
|
||||||
|
// See if the device can retrieve the subtitles externally
|
||||||
|
bool supportsEmbedded = ContainsSubtitleFormat(options.Profile.SoftSubtitleProfiles, _serverTextSubtitleOutputs);
|
||||||
|
|
||||||
|
if (supportsEmbedded)
|
||||||
|
{
|
||||||
|
return SubtitleDeliveryMethod.Embed;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return SubtitleDeliveryMethod.Encode;
|
||||||
|
}
|
||||||
|
|
||||||
|
private string NormalizeSubtitleFormat(string codec)
|
||||||
|
{
|
||||||
|
if (StringHelper.EqualsIgnoreCase(codec, "subrip"))
|
||||||
|
{
|
||||||
|
return SubtitleFormat.SRT;
|
||||||
|
}
|
||||||
|
|
||||||
|
return codec;
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool ContainsSubtitleFormat(SubtitleProfile[] profiles, string[] formats)
|
||||||
|
{
|
||||||
|
foreach (SubtitleProfile profile in profiles)
|
||||||
|
{
|
||||||
|
if (ListHelper.ContainsIgnoreCase(formats, profile.Format))
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
private bool IsAudioEligibleForDirectPlay(MediaSourceInfo item, int? maxBitrate)
|
private bool IsAudioEligibleForDirectPlay(MediaSourceInfo item, int? maxBitrate)
|
||||||
{
|
{
|
||||||
// Honor the max bitrate setting
|
// Honor the max bitrate setting
|
||||||
|
|
|
@ -58,6 +58,8 @@ namespace MediaBrowser.Model.Dlna
|
||||||
|
|
||||||
public MediaSourceInfo MediaSource { get; set; }
|
public MediaSourceInfo MediaSource { get; set; }
|
||||||
|
|
||||||
|
public SubtitleDeliveryMethod SubtitleDeliveryMethod { get; set; }
|
||||||
|
|
||||||
public string MediaSourceId
|
public string MediaSourceId
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
|
@ -108,7 +110,7 @@ namespace MediaBrowser.Model.Dlna
|
||||||
item.VideoCodec ?? string.Empty,
|
item.VideoCodec ?? string.Empty,
|
||||||
item.AudioCodec ?? string.Empty,
|
item.AudioCodec ?? string.Empty,
|
||||||
item.AudioStreamIndex.HasValue ? StringHelper.ToStringCultureInvariant(item.AudioStreamIndex.Value) : string.Empty,
|
item.AudioStreamIndex.HasValue ? StringHelper.ToStringCultureInvariant(item.AudioStreamIndex.Value) : string.Empty,
|
||||||
item.SubtitleStreamIndex.HasValue ? StringHelper.ToStringCultureInvariant(item.SubtitleStreamIndex.Value) : string.Empty,
|
item.SubtitleStreamIndex.HasValue && item.SubtitleDeliveryMethod != SubtitleDeliveryMethod.External ? StringHelper.ToStringCultureInvariant(item.SubtitleStreamIndex.Value) : string.Empty,
|
||||||
item.VideoBitrate.HasValue ? StringHelper.ToStringCultureInvariant(item.VideoBitrate.Value) : string.Empty,
|
item.VideoBitrate.HasValue ? StringHelper.ToStringCultureInvariant(item.VideoBitrate.Value) : string.Empty,
|
||||||
item.AudioBitrate.HasValue ? StringHelper.ToStringCultureInvariant(item.AudioBitrate.Value) : string.Empty,
|
item.AudioBitrate.HasValue ? StringHelper.ToStringCultureInvariant(item.AudioBitrate.Value) : string.Empty,
|
||||||
item.MaxAudioChannels.HasValue ? StringHelper.ToStringCultureInvariant(item.MaxAudioChannels.Value) : string.Empty,
|
item.MaxAudioChannels.HasValue ? StringHelper.ToStringCultureInvariant(item.MaxAudioChannels.Value) : string.Empty,
|
||||||
|
@ -427,4 +429,24 @@ namespace MediaBrowser.Model.Dlna
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public enum SubtitleDeliveryMethod
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The encode
|
||||||
|
/// </summary>
|
||||||
|
Encode = 0,
|
||||||
|
/// <summary>
|
||||||
|
/// Internal format is supported natively
|
||||||
|
/// </summary>
|
||||||
|
Direct = 1,
|
||||||
|
/// <summary>
|
||||||
|
/// The embed
|
||||||
|
/// </summary>
|
||||||
|
Embed = 2,
|
||||||
|
/// <summary>
|
||||||
|
/// The external
|
||||||
|
/// </summary>
|
||||||
|
External = 3
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,11 +7,5 @@
|
||||||
{
|
{
|
||||||
public int? AudioStreamIndex { get; set; }
|
public int? AudioStreamIndex { get; set; }
|
||||||
public int? SubtitleStreamIndex { get; set; }
|
public int? SubtitleStreamIndex { get; set; }
|
||||||
public int? MaxAudioTranscodingBitrate { get; set; }
|
|
||||||
|
|
||||||
public VideoOptions()
|
|
||||||
{
|
|
||||||
MaxAudioTranscodingBitrate = 128000;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -103,6 +103,19 @@ namespace MediaBrowser.Model.Dto
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public MediaStream GetMediaStream(MediaStreamType type, int index)
|
||||||
|
{
|
||||||
|
foreach (MediaStream i in MediaStreams)
|
||||||
|
{
|
||||||
|
if (i.Type == type && i.Index == index)
|
||||||
|
{
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public enum MediaSourceType
|
public enum MediaSourceType
|
||||||
|
|
|
@ -24,5 +24,22 @@ namespace MediaBrowser.Model.Extensions
|
||||||
|
|
||||||
return list.Contains(value, StringComparer.OrdinalIgnoreCase);
|
return list.Contains(value, StringComparer.OrdinalIgnoreCase);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static bool ContainsAnyIgnoreCase(string[] list, string[] values)
|
||||||
|
{
|
||||||
|
if (values == null)
|
||||||
|
{
|
||||||
|
throw new ArgumentNullException("values");
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach (string val in values)
|
||||||
|
{
|
||||||
|
if (ContainsIgnoreCase(list, val))
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -223,7 +223,7 @@ namespace MediaBrowser.Providers.TV
|
||||||
var download = false;
|
var download = false;
|
||||||
var automaticUpdatesEnabled = _config.Configuration.EnableTvDbUpdates;
|
var automaticUpdatesEnabled = _config.Configuration.EnableTvDbUpdates;
|
||||||
|
|
||||||
const int cacheDays = 3;
|
const int cacheDays = 2;
|
||||||
|
|
||||||
var seriesFile = files.FirstOrDefault(i => string.Equals(seriesXmlFilename, i.Name, StringComparison.OrdinalIgnoreCase));
|
var seriesFile = files.FirstOrDefault(i => string.Equals(seriesXmlFilename, i.Name, StringComparison.OrdinalIgnoreCase));
|
||||||
// No need to check age if automatic updates are enabled
|
// No need to check age if automatic updates are enabled
|
||||||
|
|
|
@ -28,7 +28,6 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
{
|
{
|
||||||
private IChannel[] _channels;
|
private IChannel[] _channels;
|
||||||
private IChannelFactory[] _factories;
|
private IChannelFactory[] _factories;
|
||||||
private List<Channel> _channelEntities = new List<Channel>();
|
|
||||||
|
|
||||||
private readonly IUserManager _userManager;
|
private readonly IUserManager _userManager;
|
||||||
private readonly IUserDataManager _userDataManager;
|
private readonly IUserDataManager _userDataManager;
|
||||||
|
@ -69,7 +68,7 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
|
|
||||||
public void AddParts(IEnumerable<IChannel> channels, IEnumerable<IChannelFactory> factories)
|
public void AddParts(IEnumerable<IChannel> channels, IEnumerable<IChannelFactory> factories)
|
||||||
{
|
{
|
||||||
_channels = channels.ToArray();
|
_channels = channels.Where(i => !(i is IFactoryChannel)).ToArray();
|
||||||
_factories = factories.ToArray();
|
_factories = factories.ToArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -113,7 +112,10 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
? null
|
? null
|
||||||
: _userManager.GetUserById(new Guid(query.UserId));
|
: _userManager.GetUserById(new Guid(query.UserId));
|
||||||
|
|
||||||
var channels = _channelEntities.OrderBy(i => i.SortName).ToList();
|
var channels = GetAllChannels()
|
||||||
|
.Select(GetChannelEntity)
|
||||||
|
.OrderBy(i => i.SortName)
|
||||||
|
.ToList();
|
||||||
|
|
||||||
if (query.SupportsLatestItems.HasValue)
|
if (query.SupportsLatestItems.HasValue)
|
||||||
{
|
{
|
||||||
|
@ -167,8 +169,6 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
{
|
{
|
||||||
var allChannelsList = GetAllChannels().ToList();
|
var allChannelsList = GetAllChannels().ToList();
|
||||||
|
|
||||||
var list = new List<Channel>();
|
|
||||||
|
|
||||||
var numComplete = 0;
|
var numComplete = 0;
|
||||||
|
|
||||||
foreach (var channelInfo in allChannelsList)
|
foreach (var channelInfo in allChannelsList)
|
||||||
|
@ -179,8 +179,6 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
{
|
{
|
||||||
var item = await GetChannel(channelInfo, cancellationToken).ConfigureAwait(false);
|
var item = await GetChannel(channelInfo, cancellationToken).ConfigureAwait(false);
|
||||||
|
|
||||||
list.Add(item);
|
|
||||||
|
|
||||||
_libraryManager.RegisterItem(item);
|
_libraryManager.RegisterItem(item);
|
||||||
}
|
}
|
||||||
catch (OperationCanceledException)
|
catch (OperationCanceledException)
|
||||||
|
@ -199,16 +197,28 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
progress.Report(100 * percent);
|
progress.Report(100 * percent);
|
||||||
}
|
}
|
||||||
|
|
||||||
_channelEntities = list.ToList();
|
|
||||||
progress.Report(100);
|
progress.Report(100);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Channel GetChannelEntity(IChannel channel)
|
||||||
|
{
|
||||||
|
var item = GetChannel(GetInternalChannelId(channel.Name).ToString("N"));
|
||||||
|
|
||||||
|
if (item == null)
|
||||||
|
{
|
||||||
|
item = GetChannel(channel, CancellationToken.None).Result;
|
||||||
|
|
||||||
|
_libraryManager.RegisterItem(item);
|
||||||
|
}
|
||||||
|
|
||||||
|
return item;
|
||||||
|
}
|
||||||
|
|
||||||
public async Task<IEnumerable<MediaSourceInfo>> GetChannelItemMediaSources(string id, CancellationToken cancellationToken)
|
public async Task<IEnumerable<MediaSourceInfo>> GetChannelItemMediaSources(string id, CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
var item = (IChannelMediaItem)_libraryManager.GetItemById(id);
|
var item = (IChannelMediaItem)_libraryManager.GetItemById(id);
|
||||||
|
|
||||||
var channelGuid = new Guid(item.ChannelId);
|
var channel = GetChannel(item.ChannelId);
|
||||||
var channel = _channelEntities.First(i => i.Id == channelGuid);
|
|
||||||
var channelPlugin = GetChannelProvider(channel);
|
var channelPlugin = GetChannelProvider(channel);
|
||||||
|
|
||||||
var requiresCallback = channelPlugin as IRequiresMediaInfoCallback;
|
var requiresCallback = channelPlugin as IRequiresMediaInfoCallback;
|
||||||
|
@ -484,7 +494,8 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
|
|
||||||
public IEnumerable<ChannelFeatures> GetAllChannelFeatures()
|
public IEnumerable<ChannelFeatures> GetAllChannelFeatures()
|
||||||
{
|
{
|
||||||
return _channelEntities
|
return GetAllChannels()
|
||||||
|
.Select(GetChannelEntity)
|
||||||
.OrderBy(i => i.SortName)
|
.OrderBy(i => i.SortName)
|
||||||
.Select(i => GetChannelFeatures(i.Id.ToString("N")));
|
.Select(i => GetChannelFeatures(i.Id.ToString("N")));
|
||||||
}
|
}
|
||||||
|
@ -603,8 +614,8 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
var itemTasks = items.Select(i =>
|
var itemTasks = items.Select(i =>
|
||||||
{
|
{
|
||||||
var channelProvider = i.Item1;
|
var channelProvider = i.Item1;
|
||||||
var channel = GetChannel(GetInternalChannelId(channelProvider.Name).ToString("N"));
|
var internalChannelId = GetInternalChannelId(channelProvider.Name);
|
||||||
return GetChannelItemEntity(i.Item2, channelProvider, channel, token);
|
return GetChannelItemEntity(i.Item2, channelProvider, internalChannelId, token);
|
||||||
});
|
});
|
||||||
|
|
||||||
var internalItems = await Task.WhenAll(itemTasks).ConfigureAwait(false);
|
var internalItems = await Task.WhenAll(itemTasks).ConfigureAwait(false);
|
||||||
|
@ -761,8 +772,8 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
var itemTasks = items.Select(i =>
|
var itemTasks = items.Select(i =>
|
||||||
{
|
{
|
||||||
var channelProvider = i.Item1;
|
var channelProvider = i.Item1;
|
||||||
var channel = GetChannel(GetInternalChannelId(channelProvider.Name).ToString("N"));
|
var internalChannelId = GetInternalChannelId(channelProvider.Name);
|
||||||
return GetChannelItemEntity(i.Item2, channelProvider, channel, token);
|
return GetChannelItemEntity(i.Item2, channelProvider, internalChannelId, token);
|
||||||
});
|
});
|
||||||
|
|
||||||
var internalItems = await Task.WhenAll(itemTasks).ConfigureAwait(false);
|
var internalItems = await Task.WhenAll(itemTasks).ConfigureAwait(false);
|
||||||
|
@ -837,9 +848,8 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
|
|
||||||
public async Task<QueryResult<BaseItemDto>> GetChannelItems(ChannelItemQuery query, CancellationToken cancellationToken)
|
public async Task<QueryResult<BaseItemDto>> GetChannelItems(ChannelItemQuery query, CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
var queryChannelId = query.ChannelId;
|
|
||||||
// Get the internal channel entity
|
// Get the internal channel entity
|
||||||
var channel = _channelEntities.First(i => i.Id == new Guid(queryChannelId));
|
var channel = GetChannel(query.ChannelId);
|
||||||
|
|
||||||
// Find the corresponding channel provider plugin
|
// Find the corresponding channel provider plugin
|
||||||
var channelProvider = GetChannelProvider(channel);
|
var channelProvider = GetChannelProvider(channel);
|
||||||
|
@ -886,7 +896,7 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
|
|
||||||
var providerTotalRecordCount = providerLimit.HasValue ? itemsResult.TotalRecordCount : null;
|
var providerTotalRecordCount = providerLimit.HasValue ? itemsResult.TotalRecordCount : null;
|
||||||
|
|
||||||
var tasks = itemsResult.Items.Select(i => GetChannelItemEntity(i, channelProvider, channel, cancellationToken));
|
var tasks = itemsResult.Items.Select(i => GetChannelItemEntity(i, channelProvider, channel.Id, cancellationToken));
|
||||||
|
|
||||||
var internalItems = await Task.WhenAll(tasks).ConfigureAwait(false);
|
var internalItems = await Task.WhenAll(tasks).ConfigureAwait(false);
|
||||||
|
|
||||||
|
@ -1086,7 +1096,7 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
(channelProvider.Name ?? string.Empty) + "16";
|
(channelProvider.Name ?? string.Empty) + "16";
|
||||||
}
|
}
|
||||||
|
|
||||||
private async Task<BaseItem> GetChannelItemEntity(ChannelItemInfo info, IChannel channelProvider, Channel internalChannel, CancellationToken cancellationToken)
|
private async Task<BaseItem> GetChannelItemEntity(ChannelItemInfo info, IChannel channelProvider, Guid internalChannelId, CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
BaseItem item;
|
BaseItem item;
|
||||||
Guid id;
|
Guid id;
|
||||||
|
@ -1158,7 +1168,7 @@ namespace MediaBrowser.Server.Implementations.Channels
|
||||||
|
|
||||||
channelItem.OriginalImageUrl = info.ImageUrl;
|
channelItem.OriginalImageUrl = info.ImageUrl;
|
||||||
channelItem.ExternalId = info.Id;
|
channelItem.ExternalId = info.Id;
|
||||||
channelItem.ChannelId = internalChannel.Id.ToString("N");
|
channelItem.ChannelId = internalChannelId.ToString("N");
|
||||||
channelItem.ChannelItemType = info.Type;
|
channelItem.ChannelItemType = info.Type;
|
||||||
|
|
||||||
if (isNew)
|
if (isNew)
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,7 +58,7 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "P\u0159ehr\u00e1t",
|
"ButtonPlay": "P\u0159ehr\u00e1t",
|
||||||
"ButtonEdit": "Upravit",
|
"ButtonEdit": "Upravit",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Afspil",
|
"ButtonPlay": "Afspil",
|
||||||
"ButtonEdit": "Rediger",
|
"ButtonEdit": "Rediger",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "\u05e0\u05d2\u05df",
|
"ButtonPlay": "\u05e0\u05d2\u05df",
|
||||||
"ButtonEdit": "\u05e2\u05e8\u05d5\u05da",
|
"ButtonEdit": "\u05e2\u05e8\u05d5\u05da",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -249,7 +249,7 @@
|
||||||
"ButtonBrowseOnlineImages": "\u0416\u0435\u043b\u0456\u0434\u0435\u0433\u0456 \u0441\u0443\u0440\u0435\u0442\u0442\u0435\u0440\u0434\u0456 \u0448\u043e\u043b\u0443",
|
"ButtonBrowseOnlineImages": "\u0416\u0435\u043b\u0456\u0434\u0435\u0433\u0456 \u0441\u0443\u0440\u0435\u0442\u0442\u0435\u0440\u0434\u0456 \u0448\u043e\u043b\u0443",
|
||||||
"HeaderDeleteItem": "\u042d\u043b\u0435\u043c\u0435\u043d\u0442\u0442\u0456 \u0436\u043e\u044e",
|
"HeaderDeleteItem": "\u042d\u043b\u0435\u043c\u0435\u043d\u0442\u0442\u0456 \u0436\u043e\u044e",
|
||||||
"ConfirmDeleteItem": "\u0428\u044b\u043d\u044b\u043c\u0435\u043d \u043e\u0441\u044b \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u0442\u0456 \u0442\u0430\u0441\u0443\u0448\u044b\u0445\u0430\u043d\u0430\u0434\u0430\u043d \u0436\u043e\u044e \u049b\u0430\u0436\u0435\u0442 \u043f\u0435?",
|
"ConfirmDeleteItem": "\u0428\u044b\u043d\u044b\u043c\u0435\u043d \u043e\u0441\u044b \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u0442\u0456 \u0442\u0430\u0441\u0443\u0448\u044b\u0445\u0430\u043d\u0430\u0434\u0430\u043d \u0436\u043e\u044e \u049b\u0430\u0436\u0435\u0442 \u043f\u0435?",
|
||||||
"MessagePleaseEnterNameOrId": "Please enter a name or an external Id.",
|
"MessagePleaseEnterNameOrId": "\u0410\u0442\u044b\u043d \u043d\u0435\u043c\u0435\u0441\u0435 \u0441\u044b\u0440\u0442\u049b\u044b ID \u0435\u043d\u0433\u0456\u0437\u0456\u04a3\u0456\u0437.",
|
||||||
"MessageValueNotCorrect": "\u0415\u043d\u0433\u0456\u0437\u0456\u043b\u0433\u0435\u043d \u043c\u04d9\u043d \u0434\u04b1\u0440\u044b\u0441 \u0435\u043c\u0435\u0441. \u04d8\u0440\u0435\u043a\u0435\u0442\u0442\u0456 \u049b\u0430\u0439\u0442\u0430\u043b\u0430\u04a3\u044b\u0437.",
|
"MessageValueNotCorrect": "\u0415\u043d\u0433\u0456\u0437\u0456\u043b\u0433\u0435\u043d \u043c\u04d9\u043d \u0434\u04b1\u0440\u044b\u0441 \u0435\u043c\u0435\u0441. \u04d8\u0440\u0435\u043a\u0435\u0442\u0442\u0456 \u049b\u0430\u0439\u0442\u0430\u043b\u0430\u04a3\u044b\u0437.",
|
||||||
"MessageItemSaved": "\u042d\u043b\u0435\u043c\u0435\u043d\u0442 \u0441\u0430\u049b\u0442\u0430\u043b\u0434\u044b.",
|
"MessageItemSaved": "\u042d\u043b\u0435\u043c\u0435\u043d\u0442 \u0441\u0430\u049b\u0442\u0430\u043b\u0434\u044b.",
|
||||||
"OptionEnded": "\u0410\u044f\u049b\u0442\u0430\u043b\u0434\u044b",
|
"OptionEnded": "\u0410\u044f\u049b\u0442\u0430\u043b\u0434\u044b",
|
||||||
|
@ -257,7 +257,7 @@
|
||||||
"OptionOff": "\u04e8\u0448\u0456\u0440",
|
"OptionOff": "\u04e8\u0448\u0456\u0440",
|
||||||
"OptionOn": "\u049a\u043e\u0441",
|
"OptionOn": "\u049a\u043e\u0441",
|
||||||
"HeaderFields": "\u04e8\u0440\u0456\u0441\u0442\u0435\u0440",
|
"HeaderFields": "\u04e8\u0440\u0456\u0441\u0442\u0435\u0440",
|
||||||
"HeaderFieldsHelp": "Slide a field to 'off' to lock it and prevent it's data from being changed.",
|
"HeaderFieldsHelp": "\u049a\u04b1\u0440\u0441\u0430\u0443\u043b\u0430\u0443 \u04af\u0448\u0456\u043d \u0436\u04d9\u043d\u0435 \u0434\u0435\u0440\u0435\u043a\u0442\u0435\u0440 \u04e9\u0437\u0433\u0435\u0440\u0442\u0443\u0456\u043d\u0435 \u0442\u044b\u0439\u044b\u043c \u0441\u0430\u043b\u0443 \u04af\u0448\u0456\u043d, \u04e9\u0440\u0456\u0441\u0442\u0456 \"\u04e8\u0428\u0406\u0420\" \u0442\u0430\u0440\u0430\u043f\u044b\u043d\u0430 \u0441\u044b\u0440\u0493\u0430\u0442\u044b\u04a3\u044b\u0437.",
|
||||||
"HeaderLiveTV": "\u042d\u0444\u0438\u0440\u043b\u0456\u043a \u0422\u0414",
|
"HeaderLiveTV": "\u042d\u0444\u0438\u0440\u043b\u0456\u043a \u0422\u0414",
|
||||||
"MissingLocalTrailer": "\u0416\u0435\u0440\u0433\u0456\u043b\u0456\u043a\u0442\u0456 \u0442\u0440\u0435\u0439\u043b\u0435\u0440 \u0436\u043e\u049b.",
|
"MissingLocalTrailer": "\u0416\u0435\u0440\u0433\u0456\u043b\u0456\u043a\u0442\u0456 \u0442\u0440\u0435\u0439\u043b\u0435\u0440 \u0436\u043e\u049b.",
|
||||||
"MissingPrimaryImage": "\u0411\u0430\u0441\u0442\u0430\u043f\u049b\u044b \u0441\u0443\u0440\u0435\u0442 \u0436\u043e\u049b.",
|
"MissingPrimaryImage": "\u0411\u0430\u0441\u0442\u0430\u043f\u049b\u044b \u0441\u0443\u0440\u0435\u0442 \u0436\u043e\u049b.",
|
||||||
|
@ -283,17 +283,17 @@
|
||||||
"LabelNewProgram": "\u0416\u0410\u04a2\u0410",
|
"LabelNewProgram": "\u0416\u0410\u04a2\u0410",
|
||||||
"LabelPremiereProgram": "\u0422\u04b0\u0421\u0410\u0423\u041a\u0415\u0421\u0415\u0420\u0406",
|
"LabelPremiereProgram": "\u0422\u04b0\u0421\u0410\u0423\u041a\u0415\u0421\u0415\u0420\u0406",
|
||||||
"HeaderChangeFolderType": "\u049a\u0430\u043b\u0442\u0430 \u0442\u04af\u0440\u0456\u043d \u04e9\u0437\u0433\u0435\u0440\u0442\u0443",
|
"HeaderChangeFolderType": "\u049a\u0430\u043b\u0442\u0430 \u0442\u04af\u0440\u0456\u043d \u04e9\u0437\u0433\u0435\u0440\u0442\u0443",
|
||||||
"HeaderChangeFolderTypeHelp": "To change the folder type, please remove and rebuild the collection with the new type.",
|
"HeaderChangeFolderTypeHelp": "\u049a\u0430\u043b\u0442\u0430 \u0442\u04af\u0440\u0456\u043d \u04e9\u0437\u0433\u0435\u0440\u0442\u0443 \u04af\u0448\u0456\u043d, \u0430\u043b\u0430\u0441\u0442\u0430\u04a3\u044b\u0437 \u0436\u04d9\u043d\u0435 \u0436\u0438\u043d\u0430\u049b\u0442\u044b \u0436\u0430\u04a3\u0430 \u0442\u04af\u0440\u0456\u043c\u0435\u043d \u049b\u0430\u0439\u0442\u0430 \u049b\u04b1\u0440\u044b\u04a3\u044b\u0437.",
|
||||||
"HeaderAlert": "\u0415\u0441\u043a\u0435\u0440\u0442\u0443",
|
"HeaderAlert": "\u0415\u0441\u043a\u0435\u0440\u0442\u0443",
|
||||||
"MessagePleaseRestart": "\u0416\u0430\u04a3\u0430\u0440\u0442\u0443\u0434\u044b \u0430\u044f\u049b\u0442\u0430\u0443 \u04af\u0448\u0456\u043d \u049b\u0430\u0439\u0442\u0430 \u0456\u0441\u043a\u0435 \u049b\u043e\u0441\u044b\u04a3\u044b\u0437.",
|
"MessagePleaseRestart": "\u0416\u0430\u04a3\u0430\u0440\u0442\u0443\u0434\u044b \u0430\u044f\u049b\u0442\u0430\u0443 \u04af\u0448\u0456\u043d \u049b\u0430\u0439\u0442\u0430 \u0456\u0441\u043a\u0435 \u049b\u043e\u0441\u044b\u04a3\u044b\u0437.",
|
||||||
"ButtonRestart": "\u049a\u0430\u0439\u0442\u0430 \u0456\u0441\u043a\u0435 \u049b\u043e\u0441\u0443",
|
"ButtonRestart": "\u049a\u0430\u0439\u0442\u0430 \u0456\u0441\u043a\u0435 \u049b\u043e\u0441\u0443",
|
||||||
"MessagePleaseRefreshPage": "Please refresh this page to receive new updates from the server.",
|
"MessagePleaseRefreshPage": "\u0416\u0430\u04a3\u0430 \u0436\u0430\u04a3\u0430\u0440\u0442\u0443\u043b\u0430\u0440\u0434\u044b \u0430\u043b\u0443 \u04af\u0448\u0456\u043d \u043e\u0441\u044b \u0431\u0435\u0442\u0442\u0456 \u049b\u0430\u0439\u0442\u0430 \u0436\u04af\u043a\u0442\u0435\u04a3\u0456\u0437.",
|
||||||
"ButtonHide": "\u0416\u0430\u0441\u044b\u0440\u0443",
|
"ButtonHide": "\u0416\u0430\u0441\u044b\u0440\u0443",
|
||||||
"MessageSettingsSaved": "\u0422\u0435\u04a3\u0448\u0435\u043b\u0456\u043c \u0441\u0430\u049b\u0442\u0430\u043b\u0434\u044b.",
|
"MessageSettingsSaved": "\u0422\u0435\u04a3\u0448\u0435\u043b\u0456\u043c \u0441\u0430\u049b\u0442\u0430\u043b\u0434\u044b.",
|
||||||
"ButtonSignOut": "\u0428\u044b\u0493\u0443",
|
"ButtonSignOut": "\u0428\u044b\u0493\u0443",
|
||||||
"ButtonMyProfile": "\u041c\u0435\u043d\u0456\u04a3 \u043f\u0440\u043e\u0444\u0430\u0439\u043b\u044b\u043c",
|
"ButtonMyProfile": "\u041c\u0435\u043d\u0456\u04a3 \u043f\u0440\u043e\u0444\u0430\u0439\u043b\u044b\u043c",
|
||||||
"ButtonMyPreferences": "\u041c\u0435\u043d\u0456\u04a3 \u0442\u0435\u04a3\u0448\u0435\u043b\u0456\u043c\u0434\u0435\u0440\u0456\u043c",
|
"ButtonMyPreferences": "\u041c\u0435\u043d\u0456\u04a3 \u0442\u0435\u04a3\u0448\u0435\u043b\u0456\u043c\u0434\u0435\u0440\u0456\u043c",
|
||||||
"MessageBrowserDoesNotSupportWebSockets": "This browser does not support web sockets. For a better experience, try a newer browser such as Chrome, Firefox, IE10+, Safari (iOS) or Opera.",
|
"MessageBrowserDoesNotSupportWebSockets": "\u041e\u0441\u044b \u0448\u043e\u043b\u0493\u044b\u0448 \u0432\u0435\u0431-\u0441\u043e\u043a\u0435\u0442\u0442\u0435\u0440\u0434\u0456 \u049b\u043e\u043b\u0434\u0430\u043c\u0430\u0439\u0434\u044b. \u0410\u043d\u0430\u0493\u04b1\u0440\u043b\u044b\u043c \u0442\u0438\u0456\u043c\u0434\u0456 \u0436\u04b1\u043c\u044b\u0441 \u04af\u0448\u0456\u043d, \u0436\u0430\u04a3\u0430 \u0448\u043e\u043b\u0493\u044b\u0448 \u0430\u0440\u049b\u044b\u043b\u044b, \u043c\u044b\u0441\u0430\u043b\u044b, Chrome, Firefox, IE10+, Safari (iOS) \u043d\u0435 Opera, \u04d9\u0440\u0435\u043a\u0435\u0442 \u0436\u0430\u0441\u0430\u04a3\u044b\u0437",
|
||||||
"LabelInstallingPackage": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u0434\u0430",
|
"LabelInstallingPackage": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u0434\u0430",
|
||||||
"LabelPackageInstallCompleted": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u044b \u0430\u044f\u049b\u0442\u0430\u043b\u0434\u044b.",
|
"LabelPackageInstallCompleted": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u044b \u0430\u044f\u049b\u0442\u0430\u043b\u0434\u044b.",
|
||||||
"LabelPackageInstallFailed": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u044b \u0441\u04d9\u0442\u0441\u0456\u0437.",
|
"LabelPackageInstallFailed": "{0} \u043e\u0440\u043d\u0430\u0442\u044b\u043b\u0443\u044b \u0441\u04d9\u0442\u0441\u0456\u0437.",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -234,84 +234,84 @@
|
||||||
"MessageConfirmRevokeApiKey": "Deseja realmente revogar esta chave da api? A conex\u00e3o da aplica\u00e7\u00e3o com o Media Browser ser\u00e1 abruptamente encerrada.",
|
"MessageConfirmRevokeApiKey": "Deseja realmente revogar esta chave da api? A conex\u00e3o da aplica\u00e7\u00e3o com o Media Browser ser\u00e1 abruptamente encerrada.",
|
||||||
"HeaderConfirmRevokeApiKey": "Revogar Chave da Api",
|
"HeaderConfirmRevokeApiKey": "Revogar Chave da Api",
|
||||||
"ValueContainer": "Container: {0}",
|
"ValueContainer": "Container: {0}",
|
||||||
"ValueAudioCodec": "Audio Codec: {0}",
|
"ValueAudioCodec": "Codec de \u00c1udio: {0}",
|
||||||
"ValueVideoCodec": "Video Codec: {0}",
|
"ValueVideoCodec": "Codec de V\u00eddeo: {0}",
|
||||||
"ValueCodec": "Codec: {0}",
|
"ValueCodec": "Codec: {0}",
|
||||||
"ValueConditions": "Conditions: {0}",
|
"ValueConditions": "Condi\u00e7\u00f5es: {0}",
|
||||||
"LabelAll": "All",
|
"LabelAll": "Todos",
|
||||||
"HeaderDeleteImage": "Delete Image",
|
"HeaderDeleteImage": "Apagar Imagem",
|
||||||
"MessageFileNotFound": "File not found.",
|
"MessageFileNotFound": "Arquivo n\u00e3o encontrado.",
|
||||||
"MessageFileReadError": "An error occurred reading this file.",
|
"MessageFileReadError": "Ocorreu um erro ao ler este arquivo.",
|
||||||
"ButtonNextPage": "Next Page",
|
"ButtonNextPage": "Pr\u00f3xima P\u00e1gina",
|
||||||
"ButtonPreviousPage": "Previous Page",
|
"ButtonPreviousPage": "P\u00e1gina Anterior",
|
||||||
"ButtonMoveLeft": "Move left",
|
"ButtonMoveLeft": "Mover \u00e0 esquerda",
|
||||||
"ButtonMoveRight": "Move right",
|
"ButtonMoveRight": "Mover \u00e0 direita",
|
||||||
"ButtonBrowseOnlineImages": "Browse online images",
|
"ButtonBrowseOnlineImages": "Procurar imagens online",
|
||||||
"HeaderDeleteItem": "Delete Item",
|
"HeaderDeleteItem": "Apagar item",
|
||||||
"ConfirmDeleteItem": "Are you sure you wish to delete this item from your library?",
|
"ConfirmDeleteItem": "Deseja realmente apagar este item de sua biblioteca?",
|
||||||
"MessagePleaseEnterNameOrId": "Please enter a name or an external Id.",
|
"MessagePleaseEnterNameOrId": "Por favor, digite um nome ou Id externo.",
|
||||||
"MessageValueNotCorrect": "The value entered is not correct. Please try again.",
|
"MessageValueNotCorrect": "O valor digitado n\u00e3o est\u00e1 correto. Por favor, tente novamente.",
|
||||||
"MessageItemSaved": "Item saved.",
|
"MessageItemSaved": "Item salvo.",
|
||||||
"OptionEnded": "Finalizada",
|
"OptionEnded": "Finalizada",
|
||||||
"OptionContinuing": "Em Exibi\u00e7\u00e3o",
|
"OptionContinuing": "Em Exibi\u00e7\u00e3o",
|
||||||
"OptionOff": "Off",
|
"OptionOff": "Off",
|
||||||
"OptionOn": "On",
|
"OptionOn": "On",
|
||||||
"HeaderFields": "Fields",
|
"HeaderFields": "Campos",
|
||||||
"HeaderFieldsHelp": "Slide a field to 'off' to lock it and prevent it's data from being changed.",
|
"HeaderFieldsHelp": "Deslize um campo para 'off' para bloquear e evitar que seus dados sejam alterados.",
|
||||||
"HeaderLiveTV": "Live TV",
|
"HeaderLiveTV": "TV ao Vivo",
|
||||||
"MissingLocalTrailer": "Missing local trailer.",
|
"MissingLocalTrailer": "Faltando trailer local.",
|
||||||
"MissingPrimaryImage": "Missing primary image.",
|
"MissingPrimaryImage": "Faltando imagem principal.",
|
||||||
"MissingBackdropImage": "Missing backdrop image.",
|
"MissingBackdropImage": "Faltando imagem de fundo.",
|
||||||
"MissingLogoImage": "Missing logo image.",
|
"MissingLogoImage": "Faltando imagem do logo.",
|
||||||
"MissingEpisode": "Missing episode.",
|
"MissingEpisode": "Faltando epis\u00f3dio.",
|
||||||
"OptionScreenshots": "Screenshots",
|
"OptionScreenshots": "Screenshots",
|
||||||
"OptionBackdrops": "Backdrops",
|
"OptionBackdrops": "Imagens de Fundo",
|
||||||
"OptionImages": "Images",
|
"OptionImages": "Imagens",
|
||||||
"OptionKeywords": "Keywords",
|
"OptionKeywords": "Palavras-chave",
|
||||||
"OptionTags": "Tags",
|
"OptionTags": "Tags",
|
||||||
"OptionStudios": "Studios",
|
"OptionStudios": "Est\u00fadios",
|
||||||
"OptionName": "Name",
|
"OptionName": "Nome",
|
||||||
"OptionOverview": "Overview",
|
"OptionOverview": "Descri\u00e7\u00e3o",
|
||||||
"OptionGenres": "Genres",
|
"OptionGenres": "G\u00eaneros",
|
||||||
"OptionParentalRating": "Classifica\u00e7\u00e3o Parental",
|
"OptionParentalRating": "Classifica\u00e7\u00e3o Parental",
|
||||||
"OptionPeople": "People",
|
"OptionPeople": "Pessoas",
|
||||||
"OptionRuntime": "Dura\u00e7\u00e3o",
|
"OptionRuntime": "Dura\u00e7\u00e3o",
|
||||||
"OptionProductionLocations": "Production Locations",
|
"OptionProductionLocations": "Locais de Produ\u00e7\u00e3o",
|
||||||
"OptionBirthLocation": "Birth Location",
|
"OptionBirthLocation": "Local de Nascimento",
|
||||||
"LabelAllChannels": "Todos os canais",
|
"LabelAllChannels": "Todos os canais",
|
||||||
"LabelLiveProgram": "LIVE",
|
"LabelLiveProgram": "AO VIVO",
|
||||||
"LabelNewProgram": "NEW",
|
"LabelNewProgram": "NOVO",
|
||||||
"LabelPremiereProgram": "PREMIERE",
|
"LabelPremiereProgram": "ESTR\u00c9IA",
|
||||||
"HeaderChangeFolderType": "Change Folder Type",
|
"HeaderChangeFolderType": "Alterar Tipo de Pasta",
|
||||||
"HeaderChangeFolderTypeHelp": "To change the folder type, please remove and rebuild the collection with the new type.",
|
"HeaderChangeFolderTypeHelp": "Para alterar o tipo de pasta, por favor remova e reconstrua a cole\u00e7\u00e3o com o novo tipo.",
|
||||||
"HeaderAlert": "Alert",
|
"HeaderAlert": "Alerta",
|
||||||
"MessagePleaseRestart": "Please restart to finish updating.",
|
"MessagePleaseRestart": "Por favor, reinicie para finalizar a atualiza\u00e7\u00e3o.",
|
||||||
"ButtonRestart": "Reiniciar",
|
"ButtonRestart": "Reiniciar",
|
||||||
"MessagePleaseRefreshPage": "Please refresh this page to receive new updates from the server.",
|
"MessagePleaseRefreshPage": "Por favor, atualize esta p\u00e1gina para receber novas atualiza\u00e7\u00f5es do servidor.",
|
||||||
"ButtonHide": "Hide",
|
"ButtonHide": "Ocultar",
|
||||||
"MessageSettingsSaved": "Settings saved.",
|
"MessageSettingsSaved": "Ajustes salvos.",
|
||||||
"ButtonSignOut": "Sign Out",
|
"ButtonSignOut": "Sair",
|
||||||
"ButtonMyProfile": "My Profile",
|
"ButtonMyProfile": "Meu Perfil",
|
||||||
"ButtonMyPreferences": "My Preferences",
|
"ButtonMyPreferences": "Minhas Prefer\u00eancias",
|
||||||
"MessageBrowserDoesNotSupportWebSockets": "This browser does not support web sockets. For a better experience, try a newer browser such as Chrome, Firefox, IE10+, Safari (iOS) or Opera.",
|
"MessageBrowserDoesNotSupportWebSockets": "Este navegador n\u00e3o suporta web sockets. Para uma melhor experi\u00eancia, tente um navegador mais atual como o Chrome, Firefox, IE10+, Safari (iOS) ou Opera.",
|
||||||
"LabelInstallingPackage": "Installing {0}",
|
"LabelInstallingPackage": "Instalando {0}",
|
||||||
"LabelPackageInstallCompleted": "{0} installation completed.",
|
"LabelPackageInstallCompleted": "Instala\u00e7\u00e3o de {0} completa.",
|
||||||
"LabelPackageInstallFailed": "{0} installation failed.",
|
"LabelPackageInstallFailed": "Instala\u00e7\u00e3o de {0} falhou.",
|
||||||
"LabelPackageInstallCancelled": "{0} installation cancelled.",
|
"LabelPackageInstallCancelled": "Instala\u00e7\u00e3o de {0} cancelada.",
|
||||||
"TabServer": "Servidor",
|
"TabServer": "Servidor",
|
||||||
"TabUsers": "Users",
|
"TabUsers": "Usu\u00e1rios",
|
||||||
"TabLibrary": "Library",
|
"TabLibrary": "Biblioteca",
|
||||||
"TabMetadata": "Metadados",
|
"TabMetadata": "Metadados",
|
||||||
"TabDLNA": "DLNA",
|
"TabDLNA": "DLNA",
|
||||||
"TabLiveTV": "Live TV",
|
"TabLiveTV": "TV ao Vivo",
|
||||||
"TabAutoOrganize": "Auto-Organize",
|
"TabAutoOrganize": "Auto-Organizar",
|
||||||
"TabPlugins": "Plugins",
|
"TabPlugins": "Plugins",
|
||||||
"TabAdvanced": "Avan\u00e7ado",
|
"TabAdvanced": "Avan\u00e7ado",
|
||||||
"TabHelp": "Help",
|
"TabHelp": "Ajuda",
|
||||||
"TabScheduledTasks": "Scheduled Tasks",
|
"TabScheduledTasks": "Tarefas Agendadas",
|
||||||
"ButtonFullscreen": "Fullscreen",
|
"ButtonFullscreen": "Tela Cheia",
|
||||||
"ButtonAudioTracks": "Audio Tracks",
|
"ButtonAudioTracks": "Faixas de \u00c1udio",
|
||||||
"ButtonSubtitles": "Legendas",
|
"ButtonSubtitles": "Legendas",
|
||||||
"ButtonScenes": "Cenas",
|
"ButtonScenes": "Cenas",
|
||||||
"ButtonQuality": "Quality"
|
"ButtonQuality": "Qualidade"
|
||||||
}
|
}
|
|
@ -167,7 +167,7 @@
|
||||||
"HeaderShutdown": "\u0417\u0430\u0432\u0435\u0440\u0448\u0435\u043d\u0438\u0435 \u0440\u0430\u0431\u043e\u0442\u044b",
|
"HeaderShutdown": "\u0417\u0430\u0432\u0435\u0440\u0448\u0435\u043d\u0438\u0435 \u0440\u0430\u0431\u043e\u0442\u044b",
|
||||||
"MessageConfirmRestart": "\u0412\u044b \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0445\u043e\u0442\u0438\u0442\u0435 \u043f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c Media Browser Server?",
|
"MessageConfirmRestart": "\u0412\u044b \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0445\u043e\u0442\u0438\u0442\u0435 \u043f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c Media Browser Server?",
|
||||||
"MessageConfirmShutdown": "\u0412\u044b \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0445\u043e\u0442\u0438\u0442\u0435 \u0437\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u0443 Media Browser Server?",
|
"MessageConfirmShutdown": "\u0412\u044b \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0445\u043e\u0442\u0438\u0442\u0435 \u0437\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u0443 Media Browser Server?",
|
||||||
"ButtonUpdateNow": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c \u0441\u0435\u0439\u0447\u0430\u0441",
|
"ButtonUpdateNow": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c \u043d\u0435\u043c\u0435\u0434\u043b\u0435\u043d\u043d\u043e",
|
||||||
"NewVersionOfSomethingAvailable": "\u0414\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u0435\u0440\u0441\u0438\u044f {0}!",
|
"NewVersionOfSomethingAvailable": "\u0414\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u0435\u0440\u0441\u0438\u044f {0}!",
|
||||||
"VersionXIsAvailableForDownload": "\u0412\u0435\u0440\u0441\u0438\u044f {0} \u0441\u0435\u0439\u0447\u0430\u0441 \u0434\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u0434\u043b\u044f \u0437\u0430\u0433\u0440\u0443\u0437\u043a\u0438.",
|
"VersionXIsAvailableForDownload": "\u0412\u0435\u0440\u0441\u0438\u044f {0} \u0441\u0435\u0439\u0447\u0430\u0441 \u0434\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u0434\u043b\u044f \u0437\u0430\u0433\u0440\u0443\u0437\u043a\u0438.",
|
||||||
"LabelVersionNumber": "\u0412\u0435\u0440\u0441\u0438\u044f {0}",
|
"LabelVersionNumber": "\u0412\u0435\u0440\u0441\u0438\u044f {0}",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "Play",
|
"ButtonPlay": "Play",
|
||||||
"ButtonEdit": "Edit",
|
"ButtonEdit": "Edit",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -58,14 +58,14 @@
|
||||||
"ButtonMute": "Mute",
|
"ButtonMute": "Mute",
|
||||||
"ButtonUnmute": "Unmute",
|
"ButtonUnmute": "Unmute",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"ButtonPlay": "\u64ad\u653e",
|
"ButtonPlay": "\u64ad\u653e",
|
||||||
"ButtonEdit": "\u7de8\u8f2f",
|
"ButtonEdit": "\u7de8\u8f2f",
|
||||||
"ButtonQueue": "Queue",
|
"ButtonQueue": "Queue",
|
||||||
"ButtonPlayTrailer": "Play trailer",
|
"ButtonPlayTrailer": "Play trailer",
|
||||||
"ButtonPlaylist": "Playlist",
|
"ButtonPlaylist": "Playlist",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"LabelEnabled": "Enabled",
|
"LabelEnabled": "Enabled",
|
||||||
"LabelDisabled": "Disabled",
|
"LabelDisabled": "Disabled",
|
||||||
"ButtonMoreInformation": "More Information",
|
"ButtonMoreInformation": "More Information",
|
||||||
|
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -631,7 +631,7 @@
|
||||||
"ButtonSubtitles": "Titulky",
|
"ButtonSubtitles": "Titulky",
|
||||||
"ButtonAudioTracks": "Audio stopy",
|
"ButtonAudioTracks": "Audio stopy",
|
||||||
"ButtonPreviousTrack": "P\u0159edchod\u00ed stopa",
|
"ButtonPreviousTrack": "P\u0159edchod\u00ed stopa",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scener",
|
"ButtonScenes": "Scener",
|
||||||
"ButtonSubtitles": "Undertekster",
|
"ButtonSubtitles": "Undertekster",
|
||||||
"ButtonAudioTracks": "Lyd filer",
|
"ButtonAudioTracks": "Lyd filer",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "Nueva llave de API",
|
"HeaderNewApiKey": "Nueva llave de API",
|
||||||
"LabelAppName": "Nombre del App",
|
"LabelAppName": "Nombre del App",
|
||||||
"LabelAppNameExample": "Ejemplo: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Ejemplo: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Otorgar a la aplicaci\u00f3n persmiso para comunicarse con Media Browser."
|
"HeaderNewApiKeyHelp": "Otorgar a la aplicaci\u00f3n persmiso para comunicarse con Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "\u0416\u0430\u04a3\u0430 API \u043a\u0456\u043b\u0442\u0456",
|
"HeaderNewApiKey": "\u0416\u0430\u04a3\u0430 API \u043a\u0456\u043b\u0442\u0456",
|
||||||
"LabelAppName": "\u049a\u043e\u043b\u0434\u0430\u043d\u0431\u0430 \u0430\u0442\u044b",
|
"LabelAppName": "\u049a\u043e\u043b\u0434\u0430\u043d\u0431\u0430 \u0430\u0442\u044b",
|
||||||
"LabelAppNameExample": "\u041c\u044b\u0441\u0430\u043b\u044b: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "\u041c\u044b\u0441\u0430\u043b\u044b: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Media Browser \u0431\u0430\u0493\u0434\u0430\u0440\u043b\u0430\u043c\u0430\u0441\u044b\u043c\u0435\u043d \u049b\u0430\u0442\u044b\u043d\u0430\u0441\u0443 \u049b\u04b1\u049b\u044b\u049b\u044b\u0493\u044b \u04af\u0448\u0456\u043d \u049b\u043e\u043b\u0434\u0430\u043d\u0431\u0430\u0493\u0430 \u0440\u04b1\u049b\u0441\u0430\u0442 \u0435\u0442\u0443."
|
"HeaderNewApiKeyHelp": "Media Browser \u0431\u0430\u0493\u0434\u0430\u0440\u043b\u0430\u043c\u0430\u0441\u044b\u043c\u0435\u043d \u049b\u0430\u0442\u044b\u043d\u0430\u0441\u0443 \u049b\u04b1\u049b\u044b\u049b\u044b\u0493\u044b \u04af\u0448\u0456\u043d \u049b\u043e\u043b\u0434\u0430\u043d\u0431\u0430\u0493\u0430 \u0440\u04b1\u049b\u0441\u0430\u0442 \u0435\u0442\u0443.",
|
||||||
|
"HeaderHttpHeaders": "HTTP \u04af\u0441\u0442\u0456\u04a3\u0433\u0456 \u0434\u0435\u0440\u0435\u043a\u0442\u0435\u043c\u0435\u043b\u0435\u0440\u0456",
|
||||||
|
"HeaderIdentificationHeader": "\u0410\u043d\u044b\u049b\u0442\u0430\u0443\u0434\u044b\u04a3 \u04af\u0441\u0442\u0456\u04a3\u0433\u0456 \u0434\u0435\u0440\u0435\u043a\u0442\u0435\u043c\u0435\u0441\u0456",
|
||||||
|
"LabelValue": "\u041c\u04d9\u043d\u0456:",
|
||||||
|
"LabelMatchType": "\u0421\u04d9\u0439\u043a\u0435\u0441 \u0442\u04af\u0440\u0456:",
|
||||||
|
"OptionEquals": "\u0422\u0435\u04a3",
|
||||||
|
"OptionRegex": "\u04b0\u0434\u0430\u0439\u044b \u04e9\u0440\u043d\u0435\u043a",
|
||||||
|
"OptionSubstring": "\u0406\u0448\u043a\u0456 \u0436\u043e\u043b"
|
||||||
}
|
}
|
878
MediaBrowser.Server.Implementations/Localization/Server/ko.json
Normal file
878
MediaBrowser.Server.Implementations/Localization/Server/ko.json
Normal file
|
@ -0,0 +1,878 @@
|
||||||
|
{
|
||||||
|
"LabelExit": "Schweinsteiger",
|
||||||
|
"LabelVisitCommunity": "Visit Community",
|
||||||
|
"LabelGithubWiki": "Github Wiki",
|
||||||
|
"LabelSwagger": "Swagger",
|
||||||
|
"LabelStandard": "Standard",
|
||||||
|
"LabelViewApiDocumentation": "View Api Documentation",
|
||||||
|
"LabelBrowseLibrary": "Browse Library",
|
||||||
|
"LabelConfigureMediaBrowser": "Configure Media Browser",
|
||||||
|
"LabelOpenLibraryViewer": "Open Library Viewer",
|
||||||
|
"LabelRestartServer": "Restart Server",
|
||||||
|
"LabelShowLogWindow": "Show Log Window",
|
||||||
|
"LabelPrevious": "Previous",
|
||||||
|
"LabelFinish": "Finish",
|
||||||
|
"LabelNext": "Next",
|
||||||
|
"LabelYoureDone": "You're Done!",
|
||||||
|
"WelcomeToMediaBrowser": "Welcome to Media Browser!",
|
||||||
|
"TitleMediaBrowser": "Media Browser",
|
||||||
|
"ThisWizardWillGuideYou": "This wizard will help guide you through the setup process. To begin, please select your preferred language.",
|
||||||
|
"TellUsAboutYourself": "Tell us about yourself",
|
||||||
|
"LabelYourFirstName": "Your first name:",
|
||||||
|
"MoreUsersCanBeAddedLater": "More users can be added later within the Dashboard.",
|
||||||
|
"UserProfilesIntro": "Media Browser includes built-in support for user profiles, enabling each user to have their own display settings, playstate and parental controls.",
|
||||||
|
"LabelWindowsService": "Windows Service",
|
||||||
|
"AWindowsServiceHasBeenInstalled": "A Windows Service has been installed.",
|
||||||
|
"WindowsServiceIntro1": "Media Browser Server normally runs as a desktop application with a tray icon, but if you prefer to run it as a background service, it can be started from the windows services control panel instead.",
|
||||||
|
"WindowsServiceIntro2": "If using the windows service, please note that it cannot be run at the same time as the tray icon, so you'll need to exit the tray in order to run the service. The service will also need to be configured with administrative privileges via the control panel. Please note that at this time the service is unable to self-update, so new versions will require manual interaction.",
|
||||||
|
"WizardCompleted": "That's all we need for now. Media Browser has begun collecting information about your media library. Check out some of our apps, and then click <b>Finish<\/b> to view the <b>Dashboard<\/b>.",
|
||||||
|
"LabelConfigureSettings": "Configure settings",
|
||||||
|
"LabelEnableVideoImageExtraction": "Enable video image extraction",
|
||||||
|
"VideoImageExtractionHelp": "For videos that don't already have images, and that we're unable to find internet images for. This will add some additional time to the initial library scan but will result in a more pleasing presentation.",
|
||||||
|
"LabelEnableChapterImageExtractionForMovies": "Extract chapter image extraction for Movies",
|
||||||
|
"LabelChapterImageExtractionForMoviesHelp": "Extracting chapter images will allow clients to display graphical scene selection menus. The process can be slow, cpu-intensive and may require several gigabytes of space. It runs as a nightly scheduled task at 4am, although this is configurable in the scheduled tasks area. It is not recommended to run this task during peak usage hours.",
|
||||||
|
"LabelEnableAutomaticPortMapping": "Enable automatic port mapping",
|
||||||
|
"LabelEnableAutomaticPortMappingHelp": "UPnP allows automated router configuration for easy remote access. This may not work with some router models.",
|
||||||
|
"ButtonOk": "Ok",
|
||||||
|
"ButtonCancel": "Cancel",
|
||||||
|
"ButtonNew": "New",
|
||||||
|
"HeaderSetupLibrary": "Setup your media library",
|
||||||
|
"ButtonAddMediaFolder": "Add media folder",
|
||||||
|
"LabelFolderType": "Folder type:",
|
||||||
|
"MediaFolderHelpPluginRequired": "* Requires the use of a plugin, e.g. GameBrowser or MB Bookshelf.",
|
||||||
|
"ReferToMediaLibraryWiki": "Refer to the media library wiki.",
|
||||||
|
"LabelCountry": "Country:",
|
||||||
|
"LabelLanguage": "Language:",
|
||||||
|
"HeaderPreferredMetadataLanguage": "Preferred metadata language:",
|
||||||
|
"LabelSaveLocalMetadata": "Save artwork and metadata into media folders",
|
||||||
|
"LabelSaveLocalMetadataHelp": "Saving artwork and metadata directly into media folders will put them in a place where they can be easily edited.",
|
||||||
|
"LabelDownloadInternetMetadata": "Download artwork and metadata from the internet",
|
||||||
|
"LabelDownloadInternetMetadataHelp": "Media Browser can download information about your media to enable rich presentations.",
|
||||||
|
"TabPreferences": "Preferences",
|
||||||
|
"TabPassword": "Password",
|
||||||
|
"TabLibraryAccess": "Library Access",
|
||||||
|
"TabImage": "Image",
|
||||||
|
"TabProfile": "Profile",
|
||||||
|
"TabMetadata": "Metadata",
|
||||||
|
"TabImages": "Images",
|
||||||
|
"TabNotifications": "Notifications",
|
||||||
|
"TabCollectionTitles": "Titles",
|
||||||
|
"LabelDisplayMissingEpisodesWithinSeasons": "Display missing episodes within seasons",
|
||||||
|
"LabelUnairedMissingEpisodesWithinSeasons": "Display unaired episodes within seasons",
|
||||||
|
"HeaderVideoPlaybackSettings": "Video Playback Settings",
|
||||||
|
"HeaderPlaybackSettings": "Playback Settings",
|
||||||
|
"LabelAudioLanguagePreference": "Audio language preference:",
|
||||||
|
"LabelSubtitleLanguagePreference": "Subtitle language preference:",
|
||||||
|
"OptionDefaultSubtitles": "Default",
|
||||||
|
"OptionOnlyForcedSubtitles": "Only forced subtitles",
|
||||||
|
"OptionAlwaysPlaySubtitles": "Always play subtitles",
|
||||||
|
"OptionNoSubtitles": "No Subtitles",
|
||||||
|
"OptionDefaultSubtitlesHelp": "Subtitles matching the language preference will be loaded when the audio is in a foreign language.",
|
||||||
|
"OptionOnlyForcedSubtitlesHelp": "Only subtitles marked as forced will be loaded.",
|
||||||
|
"OptionAlwaysPlaySubtitlesHelp": "Subtitles matching the language preference will be loaded regardless of the audio language.",
|
||||||
|
"OptionNoSubtitlesHelp": "Subtitles will not be loaded by default.",
|
||||||
|
"TabProfiles": "Profiles",
|
||||||
|
"TabSecurity": "Security",
|
||||||
|
"ButtonAddUser": "Add User",
|
||||||
|
"ButtonSave": "Save",
|
||||||
|
"ButtonResetPassword": "Reset Password",
|
||||||
|
"LabelNewPassword": "New password:",
|
||||||
|
"LabelNewPasswordConfirm": "New password confirm:",
|
||||||
|
"HeaderCreatePassword": "Create Password",
|
||||||
|
"LabelCurrentPassword": "Current password:",
|
||||||
|
"LabelMaxParentalRating": "Maximum allowed parental rating:",
|
||||||
|
"MaxParentalRatingHelp": "Content with a higher rating will be hidden from this user.",
|
||||||
|
"LibraryAccessHelp": "Select the media folders to share with this user. Administrators will be able to edit all folders using the metadata manager.",
|
||||||
|
"ChannelAccessHelp": "Select the channels to share with this user. Administrators will be able to edit all channels using the metadata manager.",
|
||||||
|
"ButtonDeleteImage": "Delete Image",
|
||||||
|
"LabelSelectUsers": "Select users:",
|
||||||
|
"ButtonUpload": "Upload",
|
||||||
|
"HeaderUploadNewImage": "Upload New Image",
|
||||||
|
"LabelDropImageHere": "Drop Image Here",
|
||||||
|
"ImageUploadAspectRatioHelp": "1:1 Aspect Ratio Recommended. JPG\/PNG only.",
|
||||||
|
"MessageNothingHere": "Nothing here.",
|
||||||
|
"MessagePleaseEnsureInternetMetadata": "Please ensure downloading of internet metadata is enabled.",
|
||||||
|
"TabSuggested": "Suggested",
|
||||||
|
"TabLatest": "Latest",
|
||||||
|
"TabUpcoming": "Upcoming",
|
||||||
|
"TabShows": "Shows",
|
||||||
|
"TabEpisodes": "Episodes",
|
||||||
|
"TabGenres": "Genres",
|
||||||
|
"TabPeople": "People",
|
||||||
|
"TabNetworks": "Networks",
|
||||||
|
"HeaderUsers": "Users",
|
||||||
|
"HeaderFilters": "Filters:",
|
||||||
|
"ButtonFilter": "Filter",
|
||||||
|
"OptionFavorite": "Favorites",
|
||||||
|
"OptionLikes": "Likes",
|
||||||
|
"OptionDislikes": "Dislikes",
|
||||||
|
"OptionActors": "Actors",
|
||||||
|
"OptionGuestStars": "Guest Stars",
|
||||||
|
"OptionDirectors": "Directors",
|
||||||
|
"OptionWriters": "Writers",
|
||||||
|
"OptionProducers": "Producers",
|
||||||
|
"HeaderResume": "Resume",
|
||||||
|
"HeaderNextUp": "Next Up",
|
||||||
|
"NoNextUpItemsMessage": "None found. Start watching your shows!",
|
||||||
|
"HeaderLatestEpisodes": "Latest Episodes",
|
||||||
|
"HeaderPersonTypes": "Person Types:",
|
||||||
|
"TabSongs": "Songs",
|
||||||
|
"TabAlbums": "Albums",
|
||||||
|
"TabArtists": "Artists",
|
||||||
|
"TabAlbumArtists": "Album Artists",
|
||||||
|
"TabMusicVideos": "Music Videos",
|
||||||
|
"ButtonSort": "Sort",
|
||||||
|
"HeaderSortBy": "Sort By:",
|
||||||
|
"HeaderSortOrder": "Sort Order:",
|
||||||
|
"OptionPlayed": "Played",
|
||||||
|
"OptionUnplayed": "Unplayed",
|
||||||
|
"OptionAscending": "Ascending",
|
||||||
|
"OptionDescending": "Descending",
|
||||||
|
"OptionRuntime": "Runtime",
|
||||||
|
"OptionReleaseDate": "Release Date",
|
||||||
|
"OptionPlayCount": "Play Count",
|
||||||
|
"OptionDatePlayed": "Date Played",
|
||||||
|
"OptionDateAdded": "Date Added",
|
||||||
|
"OptionAlbumArtist": "Album Artist",
|
||||||
|
"OptionArtist": "Artist",
|
||||||
|
"OptionAlbum": "Album",
|
||||||
|
"OptionTrackName": "Track Name",
|
||||||
|
"OptionCommunityRating": "Community Rating",
|
||||||
|
"OptionNameSort": "Name",
|
||||||
|
"OptionFolderSort": "Folders",
|
||||||
|
"OptionBudget": "Budget",
|
||||||
|
"OptionRevenue": "Revenue",
|
||||||
|
"OptionPoster": "Poster",
|
||||||
|
"OptionBackdrop": "Backdrop",
|
||||||
|
"OptionTimeline": "Timeline",
|
||||||
|
"OptionThumb": "Thumb",
|
||||||
|
"OptionBanner": "Banner",
|
||||||
|
"OptionCriticRating": "Critic Rating",
|
||||||
|
"OptionVideoBitrate": "Video Bitrate",
|
||||||
|
"OptionResumable": "Resumable",
|
||||||
|
"ScheduledTasksHelp": "Click a task to adjust its schedule.",
|
||||||
|
"ScheduledTasksTitle": "Scheduled Tasks",
|
||||||
|
"TabMyPlugins": "My Plugins",
|
||||||
|
"TabCatalog": "Catalog",
|
||||||
|
"PluginsTitle": "Plugins",
|
||||||
|
"HeaderAutomaticUpdates": "Automatic Updates",
|
||||||
|
"HeaderNowPlaying": "Now Playing",
|
||||||
|
"HeaderLatestAlbums": "Latest Albums",
|
||||||
|
"HeaderLatestSongs": "Latest Songs",
|
||||||
|
"HeaderRecentlyPlayed": "Recently Played",
|
||||||
|
"HeaderFrequentlyPlayed": "Frequently Played",
|
||||||
|
"DevBuildWarning": "Dev builds are the bleeding edge. Released often, these build have not been tested. The application may crash and entire features may not work at all.",
|
||||||
|
"LabelVideoType": "Video Type:",
|
||||||
|
"OptionBluray": "Bluray",
|
||||||
|
"OptionDvd": "Dvd",
|
||||||
|
"OptionIso": "Iso",
|
||||||
|
"Option3D": "3D",
|
||||||
|
"LabelFeatures": "Features:",
|
||||||
|
"LabelService": "Service:",
|
||||||
|
"LabelStatus": "Status:",
|
||||||
|
"LabelVersion": "Version:",
|
||||||
|
"LabelLastResult": "Last result:",
|
||||||
|
"OptionHasSubtitles": "Subtitles",
|
||||||
|
"OptionHasTrailer": "Trailer",
|
||||||
|
"OptionHasThemeSong": "Theme Song",
|
||||||
|
"OptionHasThemeVideo": "Theme Video",
|
||||||
|
"TabMovies": "Movies",
|
||||||
|
"TabStudios": "Studios",
|
||||||
|
"TabTrailers": "Trailers",
|
||||||
|
"HeaderLatestMovies": "Latest Movies",
|
||||||
|
"HeaderLatestTrailers": "Latest Trailers",
|
||||||
|
"OptionHasSpecialFeatures": "Special Features",
|
||||||
|
"OptionImdbRating": "IMDb Rating",
|
||||||
|
"OptionParentalRating": "Parental Rating",
|
||||||
|
"OptionPremiereDate": "Premiere Date",
|
||||||
|
"TabBasic": "Basic",
|
||||||
|
"TabAdvanced": "Advanced",
|
||||||
|
"HeaderStatus": "Status",
|
||||||
|
"OptionContinuing": "Continuing",
|
||||||
|
"OptionEnded": "Ended",
|
||||||
|
"HeaderAirDays": "Air Days:",
|
||||||
|
"OptionSunday": "Sunday",
|
||||||
|
"OptionMonday": "Monday",
|
||||||
|
"OptionTuesday": "Tuesday",
|
||||||
|
"OptionWednesday": "Wednesday",
|
||||||
|
"OptionThursday": "Thursday",
|
||||||
|
"OptionFriday": "Friday",
|
||||||
|
"OptionSaturday": "Saturday",
|
||||||
|
"HeaderManagement": "Management:",
|
||||||
|
"OptionMissingImdbId": "Missing IMDb Id",
|
||||||
|
"OptionMissingTvdbId": "Missing TheTVDB Id",
|
||||||
|
"OptionMissingOverview": "Missing Overview",
|
||||||
|
"OptionFileMetadataYearMismatch": "File\/Metadata Years Mismatched",
|
||||||
|
"TabGeneral": "General",
|
||||||
|
"TitleSupport": "Support",
|
||||||
|
"TabLog": "Log",
|
||||||
|
"TabAbout": "About",
|
||||||
|
"TabSupporterKey": "Supporter Key",
|
||||||
|
"TabBecomeSupporter": "Become a Supporter",
|
||||||
|
"MediaBrowserHasCommunity": "Media Browser has a thriving community of users and contributors.",
|
||||||
|
"CheckoutKnowledgeBase": "Check out our knowledge base to help you get the most out of Media Browser.",
|
||||||
|
"SearchKnowledgeBase": "Search the Knowledge Base",
|
||||||
|
"VisitTheCommunity": "Visit the Community",
|
||||||
|
"VisitMediaBrowserWebsite": "Visit the Media Browser Web Site",
|
||||||
|
"VisitMediaBrowserWebsiteLong": "Visit the Media Browser Web site to catch the latest news and keep up with the developer blog.",
|
||||||
|
"OptionHideUser": "Hide this user from login screens",
|
||||||
|
"OptionDisableUser": "Disable this user",
|
||||||
|
"OptionDisableUserHelp": "If disabled the server will not allow any connections from this user. Existing connections will be abruptly terminated.",
|
||||||
|
"HeaderAdvancedControl": "Advanced Control",
|
||||||
|
"LabelName": "Name:",
|
||||||
|
"OptionAllowUserToManageServer": "Allow this user to manage the server",
|
||||||
|
"HeaderFeatureAccess": "Feature Access",
|
||||||
|
"OptionAllowMediaPlayback": "Allow media playback",
|
||||||
|
"OptionAllowBrowsingLiveTv": "Allow browsing of live tv",
|
||||||
|
"OptionAllowDeleteLibraryContent": "Allow this user to delete library content",
|
||||||
|
"OptionAllowManageLiveTv": "Allow management of live tv recordings",
|
||||||
|
"OptionAllowRemoteControlOthers": "Allow this user to remote control other users",
|
||||||
|
"OptionMissingTmdbId": "Missing Tmdb Id",
|
||||||
|
"OptionIsHD": "HD",
|
||||||
|
"OptionIsSD": "SD",
|
||||||
|
"OptionMetascore": "Metascore",
|
||||||
|
"ButtonSelect": "Select",
|
||||||
|
"ButtonSearch": "Search",
|
||||||
|
"ButtonGroupVersions": "Group Versions",
|
||||||
|
"ButtonAddToCollection": "Add to Collection",
|
||||||
|
"PismoMessage": "Utilizing Pismo File Mount through a donated license.",
|
||||||
|
"TangibleSoftwareMessage": "Utilizing Tangible Solutions Java\/C# converters through a donated license.",
|
||||||
|
"HeaderCredits": "Credits",
|
||||||
|
"PleaseSupportOtherProduces": "Please support other free products we utilize:",
|
||||||
|
"VersionNumber": "Version {0}",
|
||||||
|
"TabPaths": "Paths",
|
||||||
|
"TabServer": "Server",
|
||||||
|
"TabTranscoding": "Transcoding",
|
||||||
|
"TitleAdvanced": "Advanced",
|
||||||
|
"LabelAutomaticUpdateLevel": "Automatic update level",
|
||||||
|
"OptionRelease": "Official Release",
|
||||||
|
"OptionBeta": "Beta",
|
||||||
|
"OptionDev": "Dev (Unstable)",
|
||||||
|
"LabelAllowServerAutoRestart": "Allow the server to restart automatically to apply updates",
|
||||||
|
"LabelAllowServerAutoRestartHelp": "The server will only restart during idle periods, when no users are active.",
|
||||||
|
"LabelEnableDebugLogging": "Enable debug logging",
|
||||||
|
"LabelRunServerAtStartup": "Run server at startup",
|
||||||
|
"LabelRunServerAtStartupHelp": "This will start the tray icon on windows startup. To start the windows service, uncheck this and run the service from the windows control panel. Please note that you cannot run both at the same time, so you will need to exit the tray icon before starting the service.",
|
||||||
|
"ButtonSelectDirectory": "Select Directory",
|
||||||
|
"LabelCustomPaths": "Specify custom paths where desired. Leave fields empty to use the defaults.",
|
||||||
|
"LabelCachePath": "Cache path:",
|
||||||
|
"LabelCachePathHelp": "This folder contains server cache files, such as images.",
|
||||||
|
"LabelImagesByNamePath": "Images by name path:",
|
||||||
|
"LabelImagesByNamePathHelp": "This folder contains downloaded actor, artist, genre and studio images.",
|
||||||
|
"LabelMetadataPath": "Metadata path:",
|
||||||
|
"LabelMetadataPathHelp": "This location contains downloaded artwork and metadata that is not configured to be stored in media folders.",
|
||||||
|
"LabelTranscodingTempPath": "Transcoding temporary path:",
|
||||||
|
"LabelTranscodingTempPathHelp": "This folder contains working files used by the transcoder. Specify a custom path, or leave empty to use the default within the server's data folder.",
|
||||||
|
"TabBasics": "Basics",
|
||||||
|
"TabTV": "TV",
|
||||||
|
"TabGames": "Games",
|
||||||
|
"TabMusic": "Music",
|
||||||
|
"TabOthers": "Others",
|
||||||
|
"HeaderExtractChapterImagesFor": "Extract chapter images for:",
|
||||||
|
"OptionMovies": "Movies",
|
||||||
|
"OptionEpisodes": "Episodes",
|
||||||
|
"OptionOtherVideos": "Other Videos",
|
||||||
|
"TitleMetadata": "Metadata",
|
||||||
|
"LabelAutomaticUpdatesFanart": "Enable automatic updates from FanArt.tv",
|
||||||
|
"LabelAutomaticUpdatesTmdb": "Enable automatic updates from TheMovieDB.org",
|
||||||
|
"LabelAutomaticUpdatesTvdb": "Enable automatic updates from TheTVDB.com",
|
||||||
|
"LabelAutomaticUpdatesFanartHelp": "If enabled, new images will be downloaded automatically as they're added to fanart.tv. Existing images will not be replaced.",
|
||||||
|
"LabelAutomaticUpdatesTmdbHelp": "If enabled, new images will be downloaded automatically as they're added to TheMovieDB.org. Existing images will not be replaced.",
|
||||||
|
"LabelAutomaticUpdatesTvdbHelp": "If enabled, new images will be downloaded automatically as they're added to TheTVDB.com. Existing images will not be replaced.",
|
||||||
|
"ExtractChapterImagesHelp": "Extracting chapter images will allow clients to display graphical scene selection menus. The process can be slow, cpu-intensive and may require several gigabytes of space. It runs when videos are discovered, and also as a nightly scheduled task at 4am. The schedule is configurable in the scheduled tasks area. It is not recommended to run this task during peak usage hours.",
|
||||||
|
"LabelMetadataDownloadLanguage": "Preferred download language:",
|
||||||
|
"ButtonAutoScroll": "Auto-scroll",
|
||||||
|
"LabelImageSavingConvention": "Image saving convention:",
|
||||||
|
"LabelImageSavingConventionHelp": "Media Browser recognizes images from most major media applications. Choosing your downloading convention is useful if you also use other products.",
|
||||||
|
"OptionImageSavingCompatible": "Compatible - Media Browser\/Xbmc\/Plex",
|
||||||
|
"OptionImageSavingStandard": "Standard - MB2",
|
||||||
|
"ButtonSignIn": "Sign In",
|
||||||
|
"TitleSignIn": "Sign In",
|
||||||
|
"HeaderPleaseSignIn": "Please sign in",
|
||||||
|
"LabelUser": "User:",
|
||||||
|
"LabelPassword": "Password:",
|
||||||
|
"ButtonManualLogin": "Manual Login",
|
||||||
|
"PasswordLocalhostMessage": "Passwords are not required when logging in from localhost.",
|
||||||
|
"TabGuide": "Guide",
|
||||||
|
"TabChannels": "Channels",
|
||||||
|
"TabCollections": "Collections",
|
||||||
|
"HeaderChannels": "Channels",
|
||||||
|
"TabRecordings": "Recordings",
|
||||||
|
"TabScheduled": "Scheduled",
|
||||||
|
"TabSeries": "Series",
|
||||||
|
"TabFavorites": "Favorites",
|
||||||
|
"TabMyLibrary": "My Library",
|
||||||
|
"ButtonCancelRecording": "Cancel Recording",
|
||||||
|
"HeaderPrePostPadding": "Pre\/Post Padding",
|
||||||
|
"LabelPrePaddingMinutes": "Pre-padding minutes:",
|
||||||
|
"OptionPrePaddingRequired": "Pre-padding is required in order to record.",
|
||||||
|
"LabelPostPaddingMinutes": "Post-padding minutes:",
|
||||||
|
"OptionPostPaddingRequired": "Post-padding is required in order to record.",
|
||||||
|
"HeaderWhatsOnTV": "What's On",
|
||||||
|
"HeaderUpcomingTV": "Upcoming TV",
|
||||||
|
"TabStatus": "Status",
|
||||||
|
"TabSettings": "Settings",
|
||||||
|
"ButtonRefreshGuideData": "Refresh Guide Data",
|
||||||
|
"OptionPriority": "Priority",
|
||||||
|
"OptionRecordOnAllChannels": "Record program on all channels",
|
||||||
|
"OptionRecordAnytime": "Record program at any time",
|
||||||
|
"OptionRecordOnlyNewEpisodes": "Record only new episodes",
|
||||||
|
"HeaderDays": "Days",
|
||||||
|
"HeaderActiveRecordings": "Active Recordings",
|
||||||
|
"HeaderLatestRecordings": "Latest Recordings",
|
||||||
|
"HeaderAllRecordings": "All Recordings",
|
||||||
|
"ButtonPlay": "Play",
|
||||||
|
"ButtonEdit": "Edit",
|
||||||
|
"ButtonRecord": "Record",
|
||||||
|
"ButtonDelete": "Delete",
|
||||||
|
"ButtonRemove": "Remove",
|
||||||
|
"OptionRecordSeries": "Record Series",
|
||||||
|
"HeaderDetails": "Details",
|
||||||
|
"TitleLiveTV": "Live TV",
|
||||||
|
"LabelNumberOfGuideDays": "Number of days of guide data to download:",
|
||||||
|
"LabelNumberOfGuideDaysHelp": "Downloading more days worth of guide data provides the ability to schedule out further in advance and view more listings, but it will also take longer to download. Auto will choose based on the number of channels.",
|
||||||
|
"LabelActiveService": "Active Service:",
|
||||||
|
"LabelActiveServiceHelp": "Multiple tv plugins can be installed but only one can be active at a time.",
|
||||||
|
"OptionAutomatic": "Auto",
|
||||||
|
"LiveTvPluginRequired": "A Live TV service provider plugin is required in order to continue.",
|
||||||
|
"LiveTvPluginRequiredHelp": "Please install one of our available plugins, such as Next Pvr or ServerWmc.",
|
||||||
|
"LabelCustomizeOptionsPerMediaType": "Customize for media type:",
|
||||||
|
"OptionDownloadThumbImage": "Thumb",
|
||||||
|
"OptionDownloadMenuImage": "Menu",
|
||||||
|
"OptionDownloadLogoImage": "Logo",
|
||||||
|
"OptionDownloadBoxImage": "Box",
|
||||||
|
"OptionDownloadDiscImage": "Disc",
|
||||||
|
"OptionDownloadBannerImage": "Banner",
|
||||||
|
"OptionDownloadBackImage": "Back",
|
||||||
|
"OptionDownloadArtImage": "Art",
|
||||||
|
"OptionDownloadPrimaryImage": "Primary",
|
||||||
|
"HeaderFetchImages": "Fetch Images:",
|
||||||
|
"HeaderImageSettings": "Image Settings",
|
||||||
|
"TabOther": "Other",
|
||||||
|
"LabelMaxBackdropsPerItem": "Maximum number of backdrops per item:",
|
||||||
|
"LabelMaxScreenshotsPerItem": "Maximum number of screenshots per item:",
|
||||||
|
"LabelMinBackdropDownloadWidth": "Minimum backdrop download width:",
|
||||||
|
"LabelMinScreenshotDownloadWidth": "Minimum screenshot download width:",
|
||||||
|
"ButtonAddScheduledTaskTrigger": "Add Task Trigger",
|
||||||
|
"HeaderAddScheduledTaskTrigger": "Add Task Trigger",
|
||||||
|
"ButtonAdd": "Add",
|
||||||
|
"LabelTriggerType": "Trigger Type:",
|
||||||
|
"OptionDaily": "Daily",
|
||||||
|
"OptionWeekly": "Weekly",
|
||||||
|
"OptionOnInterval": "On an interval",
|
||||||
|
"OptionOnAppStartup": "On application startup",
|
||||||
|
"OptionAfterSystemEvent": "After a system event",
|
||||||
|
"LabelDay": "Day:",
|
||||||
|
"LabelTime": "Time:",
|
||||||
|
"LabelEvent": "Event:",
|
||||||
|
"OptionWakeFromSleep": "Wake from sleep",
|
||||||
|
"LabelEveryXMinutes": "Every:",
|
||||||
|
"HeaderTvTuners": "Tuners",
|
||||||
|
"HeaderGallery": "Gallery",
|
||||||
|
"HeaderLatestGames": "Latest Games",
|
||||||
|
"HeaderRecentlyPlayedGames": "Recently Played Games",
|
||||||
|
"TabGameSystems": "Game Systems",
|
||||||
|
"TitleMediaLibrary": "Media Library",
|
||||||
|
"TabFolders": "Folders",
|
||||||
|
"TabPathSubstitution": "Path Substitution",
|
||||||
|
"LabelSeasonZeroDisplayName": "Season 0 display name:",
|
||||||
|
"LabelEnableRealtimeMonitor": "Enable real time monitoring",
|
||||||
|
"LabelEnableRealtimeMonitorHelp": "Changes will be processed immediately, on supported file systems.",
|
||||||
|
"ButtonScanLibrary": "Scan Library",
|
||||||
|
"HeaderNumberOfPlayers": "Players:",
|
||||||
|
"OptionAnyNumberOfPlayers": "Any",
|
||||||
|
"Option1Player": "1+",
|
||||||
|
"Option2Player": "2+",
|
||||||
|
"Option3Player": "3+",
|
||||||
|
"Option4Player": "4+",
|
||||||
|
"HeaderMediaFolders": "Media Folders",
|
||||||
|
"HeaderThemeVideos": "Theme Videos",
|
||||||
|
"HeaderThemeSongs": "Theme Songs",
|
||||||
|
"HeaderScenes": "Scenes",
|
||||||
|
"HeaderAwardsAndReviews": "Awards and Reviews",
|
||||||
|
"HeaderSoundtracks": "Soundtracks",
|
||||||
|
"HeaderMusicVideos": "Music Videos",
|
||||||
|
"HeaderSpecialFeatures": "Special Features",
|
||||||
|
"HeaderCastCrew": "Cast & Crew",
|
||||||
|
"HeaderAdditionalParts": "Additional Parts",
|
||||||
|
"ButtonSplitVersionsApart": "Split Versions Apart",
|
||||||
|
"ButtonPlayTrailer": "Trailer",
|
||||||
|
"LabelMissing": "Missing",
|
||||||
|
"LabelOffline": "Offline",
|
||||||
|
"PathSubstitutionHelp": "Path substitutions are used for mapping a path on the server to a path that clients are able to access. By allowing clients direct access to media on the server they may be able to play them directly over the network and avoid using server resources to stream and transcode them.",
|
||||||
|
"HeaderFrom": "From",
|
||||||
|
"HeaderTo": "To",
|
||||||
|
"LabelFrom": "From:",
|
||||||
|
"LabelFromHelp": "Example: D:\\Movies (on the server)",
|
||||||
|
"LabelTo": "To:",
|
||||||
|
"LabelToHelp": "Example: \\\\MyServer\\Movies (a path clients can access)",
|
||||||
|
"ButtonAddPathSubstitution": "Add Substitution",
|
||||||
|
"OptionSpecialEpisode": "Specials",
|
||||||
|
"OptionMissingEpisode": "Missing Episodes",
|
||||||
|
"OptionUnairedEpisode": "Unaired Episodes",
|
||||||
|
"OptionEpisodeSortName": "Episode Sort Name",
|
||||||
|
"OptionSeriesSortName": "Series Name",
|
||||||
|
"OptionTvdbRating": "Tvdb Rating",
|
||||||
|
"HeaderTranscodingQualityPreference": "Transcoding Quality Preference:",
|
||||||
|
"OptionAutomaticTranscodingHelp": "The server will decide quality and speed",
|
||||||
|
"OptionHighSpeedTranscodingHelp": "Lower quality, but faster encoding",
|
||||||
|
"OptionHighQualityTranscodingHelp": "Higher quality, but slower encoding",
|
||||||
|
"OptionMaxQualityTranscodingHelp": "Best quality with slower encoding and high CPU usage",
|
||||||
|
"OptionHighSpeedTranscoding": "Higher speed",
|
||||||
|
"OptionHighQualityTranscoding": "Higher quality",
|
||||||
|
"OptionMaxQualityTranscoding": "Max quality",
|
||||||
|
"OptionEnableDebugTranscodingLogging": "Enable debug transcoding logging",
|
||||||
|
"OptionEnableDebugTranscodingLoggingHelp": "This will create very large log files and is only recommended as needed for troubleshooting purposes.",
|
||||||
|
"OptionUpscaling": "Allow clients to request upscaled video",
|
||||||
|
"OptionUpscalingHelp": "In some cases this will result in improved video quality but will increase CPU usage.",
|
||||||
|
"EditCollectionItemsHelp": "Add or remove any movies, series, albums, books or games you wish to group within this collection.",
|
||||||
|
"HeaderAddTitles": "Add Titles",
|
||||||
|
"LabelEnableDlnaPlayTo": "Enable DLNA Play To",
|
||||||
|
"LabelEnableDlnaPlayToHelp": "Media Browser can detect devices within your network and offer the ability to remote control them.",
|
||||||
|
"LabelEnableDlnaDebugLogging": "Enable DLNA debug logging",
|
||||||
|
"LabelEnableDlnaDebugLoggingHelp": "This will create large log files and should only be used as needed for troubleshooting purposes.",
|
||||||
|
"LabelEnableDlnaClientDiscoveryInterval": "Client discovery interval (seconds)",
|
||||||
|
"LabelEnableDlnaClientDiscoveryIntervalHelp": "Determines the duration in seconds between SSDP searches performed by Media Browser.",
|
||||||
|
"HeaderCustomDlnaProfiles": "Custom Profiles",
|
||||||
|
"HeaderSystemDlnaProfiles": "System Profiles",
|
||||||
|
"CustomDlnaProfilesHelp": "Create a custom profile to target a new device or override a system profile.",
|
||||||
|
"SystemDlnaProfilesHelp": "System profiles are read-only. Changes to a system profile will be saved to a new custom profile.",
|
||||||
|
"TitleDashboard": "Dashboard",
|
||||||
|
"TabHome": "Home",
|
||||||
|
"TabInfo": "Info",
|
||||||
|
"HeaderLinks": "Links",
|
||||||
|
"HeaderSystemPaths": "System Paths",
|
||||||
|
"LinkCommunity": "Community",
|
||||||
|
"LinkGithub": "Github",
|
||||||
|
"LinkApiDocumentation": "Api Documentation",
|
||||||
|
"LabelFriendlyServerName": "Friendly server name:",
|
||||||
|
"LabelFriendlyServerNameHelp": "This name will be used to identify this server. If left blank, the computer name will be used.",
|
||||||
|
"LabelPreferredDisplayLanguage": "Preferred display language",
|
||||||
|
"LabelPreferredDisplayLanguageHelp": "Translating Media Browser is an ongoing project and is not yet complete.",
|
||||||
|
"LabelReadHowYouCanContribute": "Read about how you can contribute.",
|
||||||
|
"HeaderNewCollection": "New Collection",
|
||||||
|
"HeaderAddToCollection": "Add to Collection",
|
||||||
|
"ButtonSubmit": "Submit",
|
||||||
|
"NewCollectionNameExample": "Example: Star Wars Collection",
|
||||||
|
"OptionSearchForInternetMetadata": "Search the internet for artwork and metadata",
|
||||||
|
"ButtonCreate": "Create",
|
||||||
|
"LabelHttpServerPortNumber": "Http server port number:",
|
||||||
|
"LabelWebSocketPortNumber": "Web socket port number:",
|
||||||
|
"LabelEnableAutomaticPortHelp": "UPnP allows automated router configuration for remote access. This may not work with some router models.",
|
||||||
|
"LabelExternalDDNS": "External DDNS:",
|
||||||
|
"LabelExternalDDNSHelp": "If you have a dynamic DNS enter it here. Media Browser apps will use it when connecting remotely.",
|
||||||
|
"TabResume": "Resume",
|
||||||
|
"TabWeather": "Weather",
|
||||||
|
"TitleAppSettings": "App Settings",
|
||||||
|
"LabelMinResumePercentage": "Min resume percentage:",
|
||||||
|
"LabelMaxResumePercentage": "Max resume percentage:",
|
||||||
|
"LabelMinResumeDuration": "Min resume duration (seconds):",
|
||||||
|
"LabelMinResumePercentageHelp": "Titles are assumed unplayed if stopped before this time",
|
||||||
|
"LabelMaxResumePercentageHelp": "Titles are assumed fully played if stopped after this time",
|
||||||
|
"LabelMinResumeDurationHelp": "Titles shorter than this will not be resumable",
|
||||||
|
"TitleAutoOrganize": "Auto-Organize",
|
||||||
|
"TabActivityLog": "Activity Log",
|
||||||
|
"HeaderName": "Name",
|
||||||
|
"HeaderDate": "Date",
|
||||||
|
"HeaderSource": "Source",
|
||||||
|
"HeaderDestination": "Destination",
|
||||||
|
"HeaderProgram": "Program",
|
||||||
|
"HeaderClients": "Clients",
|
||||||
|
"LabelCompleted": "Completed",
|
||||||
|
"LabelFailed": "Failed",
|
||||||
|
"LabelSkipped": "Skipped",
|
||||||
|
"HeaderEpisodeOrganization": "Episode Organization",
|
||||||
|
"LabelSeries": "Series:",
|
||||||
|
"LabelSeasonNumber": "Season number",
|
||||||
|
"LabelEpisodeNumber": "Episode number",
|
||||||
|
"LabelEndingEpisodeNumber": "Ending episode number",
|
||||||
|
"LabelEndingEpisodeNumberHelp": "Only required for multi-episode files",
|
||||||
|
"HeaderSupportTheTeam": "Support the Media Browser Team",
|
||||||
|
"LabelSupportAmount": "Amount (USD)",
|
||||||
|
"HeaderSupportTheTeamHelp": "Help ensure the continued development of this project by donating. A portion of all donations will be contributed to other free tools we depend on.",
|
||||||
|
"ButtonEnterSupporterKey": "Enter supporter key",
|
||||||
|
"DonationNextStep": "Once complete, please return and enter your supporter key, which you will receive by email.",
|
||||||
|
"AutoOrganizeHelp": "Auto-organize monitors your download folders for new files and moves them to your media directories.",
|
||||||
|
"AutoOrganizeTvHelp": "TV file organizing will only add episodes to existing series. It will not create new series folders.",
|
||||||
|
"OptionEnableEpisodeOrganization": "Enable new episode organization",
|
||||||
|
"LabelWatchFolder": "Watch folder:",
|
||||||
|
"LabelWatchFolderHelp": "The server will poll this folder during the 'Organize new media files' scheduled task.",
|
||||||
|
"ButtonViewScheduledTasks": "View scheduled tasks",
|
||||||
|
"LabelMinFileSizeForOrganize": "Minimum file size (MB):",
|
||||||
|
"LabelMinFileSizeForOrganizeHelp": "Files under this size will be ignored.",
|
||||||
|
"LabelSeasonFolderPattern": "Season folder pattern:",
|
||||||
|
"LabelSeasonZeroFolderName": "Season zero folder name:",
|
||||||
|
"HeaderEpisodeFilePattern": "Episode file pattern",
|
||||||
|
"LabelEpisodePattern": "Episode pattern:",
|
||||||
|
"LabelMultiEpisodePattern": "Multi-Episode pattern:",
|
||||||
|
"HeaderSupportedPatterns": "Supported Patterns",
|
||||||
|
"HeaderTerm": "Term",
|
||||||
|
"HeaderPattern": "Pattern",
|
||||||
|
"HeaderResult": "Result",
|
||||||
|
"LabelDeleteEmptyFolders": "Delete empty folders after organizing",
|
||||||
|
"LabelDeleteEmptyFoldersHelp": "Enable this to keep the download directory clean.",
|
||||||
|
"LabelDeleteLeftOverFiles": "Delete left over files with the following extensions:",
|
||||||
|
"LabelDeleteLeftOverFilesHelp": "Separate with ;. For example: .nfo;.txt",
|
||||||
|
"OptionOverwriteExistingEpisodes": "Overwrite existing episodes",
|
||||||
|
"LabelTransferMethod": "Transfer method",
|
||||||
|
"OptionCopy": "Copy",
|
||||||
|
"OptionMove": "Move",
|
||||||
|
"LabelTransferMethodHelp": "Copy or move files from the watch folder",
|
||||||
|
"HeaderLatestNews": "Latest News",
|
||||||
|
"HeaderHelpImproveMediaBrowser": "Help Improve Media Browser",
|
||||||
|
"HeaderRunningTasks": "Running Tasks",
|
||||||
|
"HeaderActiveDevices": "Active Devices",
|
||||||
|
"HeaderPendingInstallations": "Pending Installations",
|
||||||
|
"HeaerServerInformation": "Server Information",
|
||||||
|
"ButtonRestartNow": "Restart Now",
|
||||||
|
"ButtonRestart": "Restart",
|
||||||
|
"ButtonShutdown": "Shutdown",
|
||||||
|
"ButtonUpdateNow": "Update Now",
|
||||||
|
"PleaseUpdateManually": "Please shutdown the server and update manually.",
|
||||||
|
"NewServerVersionAvailable": "A new version of Media Browser Server is available!",
|
||||||
|
"ServerUpToDate": "Media Browser Server is up to date",
|
||||||
|
"ErrorConnectingToMediaBrowserRepository": "There was an error connecting to the remote Media Browser repository.",
|
||||||
|
"LabelComponentsUpdated": "The following components have been installed or updated:",
|
||||||
|
"MessagePleaseRestartServerToFinishUpdating": "Please restart the server to finish applying updates.",
|
||||||
|
"LabelDownMixAudioScale": "Audio boost when downmixing:",
|
||||||
|
"LabelDownMixAudioScaleHelp": "Boost audio when downmixing. Set to 1 to preserve original volume value.",
|
||||||
|
"ButtonLinkKeys": "Link Keys",
|
||||||
|
"LabelOldSupporterKey": "Old supporter key",
|
||||||
|
"LabelNewSupporterKey": "New supporter key",
|
||||||
|
"HeaderMultipleKeyLinking": "Multiple Key Linking",
|
||||||
|
"MultipleKeyLinkingHelp": "If you have more than one supporter key, use this form to link the old key's registrations with your new one.",
|
||||||
|
"LabelCurrentEmailAddress": "Current email address",
|
||||||
|
"LabelCurrentEmailAddressHelp": "The current email address to which your new key was sent.",
|
||||||
|
"HeaderForgotKey": "Forgot Key",
|
||||||
|
"LabelEmailAddress": "Email address",
|
||||||
|
"LabelSupporterEmailAddress": "The email address that was used to purchase the key.",
|
||||||
|
"ButtonRetrieveKey": "Retrieve Key",
|
||||||
|
"LabelSupporterKey": "Supporter Key (paste from email)",
|
||||||
|
"LabelSupporterKeyHelp": "Enter your supporter key to start enjoying additional benefits the community has developed for Media Browser.",
|
||||||
|
"MessageInvalidKey": "Supporter key is missing or invalid.",
|
||||||
|
"ErrorMessageInvalidKey": "In order for any premium content to be registered, you must also be a Media Browser Supporter. Please donate and support the continued development of the core product. Thank you.",
|
||||||
|
"HeaderDisplaySettings": "Display Settings",
|
||||||
|
"TabPlayTo": "Play To",
|
||||||
|
"LabelEnableDlnaServer": "Enable Dlna server",
|
||||||
|
"LabelEnableDlnaServerHelp": "Allows UPnP devices on your network to browse and play Media Browser content.",
|
||||||
|
"LabelEnableBlastAliveMessages": "Blast alive messages",
|
||||||
|
"LabelEnableBlastAliveMessagesHelp": "Enable this if the server is not detected reliably by other UPnP devices on your network.",
|
||||||
|
"LabelBlastMessageInterval": "Alive message interval (seconds)",
|
||||||
|
"LabelBlastMessageIntervalHelp": "Determines the duration in seconds between server alive messages.",
|
||||||
|
"LabelDefaultUser": "Default user:",
|
||||||
|
"LabelDefaultUserHelp": "Determines which user library should be displayed on connected devices. This can be overridden for each device using profiles.",
|
||||||
|
"TitleDlna": "DLNA",
|
||||||
|
"TitleChannels": "Channels",
|
||||||
|
"HeaderServerSettings": "Server Settings",
|
||||||
|
"LabelWeatherDisplayLocation": "Weather display location:",
|
||||||
|
"LabelWeatherDisplayLocationHelp": "US zip code \/ City, State, Country \/ City, Country",
|
||||||
|
"LabelWeatherDisplayUnit": "Weather display unit:",
|
||||||
|
"OptionCelsius": "Celsius",
|
||||||
|
"OptionFahrenheit": "Fahrenheit",
|
||||||
|
"HeaderRequireManualLogin": "Require manual username entry for:",
|
||||||
|
"HeaderRequireManualLoginHelp": "When disabled clients may present a login screen with a visual selection of users.",
|
||||||
|
"OptionOtherApps": "Other apps",
|
||||||
|
"OptionMobileApps": "Mobile apps",
|
||||||
|
"HeaderNotificationList": "Click on a notification to configure it's sending options.",
|
||||||
|
"NotificationOptionApplicationUpdateAvailable": "Application update available",
|
||||||
|
"NotificationOptionApplicationUpdateInstalled": "Application update installed",
|
||||||
|
"NotificationOptionPluginUpdateInstalled": "Plugin update installed",
|
||||||
|
"NotificationOptionPluginInstalled": "Plugin installed",
|
||||||
|
"NotificationOptionPluginUninstalled": "Plugin uninstalled",
|
||||||
|
"NotificationOptionVideoPlayback": "Video playback started",
|
||||||
|
"NotificationOptionAudioPlayback": "Audio playback started",
|
||||||
|
"NotificationOptionGamePlayback": "Game playback started",
|
||||||
|
"NotificationOptionVideoPlaybackStopped": "Video playback stopped",
|
||||||
|
"NotificationOptionAudioPlaybackStopped": "Audio playback stopped",
|
||||||
|
"NotificationOptionGamePlaybackStopped": "Game playback stopped",
|
||||||
|
"NotificationOptionTaskFailed": "Scheduled task failure",
|
||||||
|
"NotificationOptionInstallationFailed": "Installation failure",
|
||||||
|
"NotificationOptionNewLibraryContent": "New content added",
|
||||||
|
"NotificationOptionNewLibraryContentMultiple": "New content added (multiple)",
|
||||||
|
"SendNotificationHelp": "By default, notifications are delivered to the dashboard inbox. Browse the plugin catalog to install additional notification options.",
|
||||||
|
"NotificationOptionServerRestartRequired": "Server restart required",
|
||||||
|
"LabelNotificationEnabled": "Enable this notification",
|
||||||
|
"LabelMonitorUsers": "Monitor activity from:",
|
||||||
|
"LabelSendNotificationToUsers": "Send the notification to:",
|
||||||
|
"UsersNotNotifiedAboutSelfActivity": "Users will not be notified about their own activities.",
|
||||||
|
"LabelUseNotificationServices": "Use the following services:",
|
||||||
|
"CategoryUser": "User",
|
||||||
|
"CategorySystem": "System",
|
||||||
|
"CategoryApplication": "Application",
|
||||||
|
"CategoryPlugin": "Plugin",
|
||||||
|
"LabelMessageTitle": "Message title:",
|
||||||
|
"LabelAvailableTokens": "Available tokens:",
|
||||||
|
"AdditionalNotificationServices": "Browse the plugin catalog to install additional notification services.",
|
||||||
|
"OptionAllUsers": "All users",
|
||||||
|
"OptionAdminUsers": "Administrators",
|
||||||
|
"OptionCustomUsers": "Custom",
|
||||||
|
"ButtonArrowUp": "Up",
|
||||||
|
"ButtonArrowDown": "Down",
|
||||||
|
"ButtonArrowLeft": "Left",
|
||||||
|
"ButtonArrowRight": "Right",
|
||||||
|
"ButtonBack": "Back",
|
||||||
|
"ButtonInfo": "Info",
|
||||||
|
"ButtonOsd": "On screen display",
|
||||||
|
"ButtonPageUp": "Page Up",
|
||||||
|
"ButtonPageDown": "Page Down",
|
||||||
|
"PageAbbreviation": "PG",
|
||||||
|
"ButtonHome": "Home",
|
||||||
|
"ButtonSettings": "Settings",
|
||||||
|
"ButtonTakeScreenshot": "Capture Screenshot",
|
||||||
|
"ButtonLetterUp": "Letter Up",
|
||||||
|
"ButtonLetterDown": "Letter Down",
|
||||||
|
"PageButtonAbbreviation": "PG",
|
||||||
|
"LetterButtonAbbreviation": "A",
|
||||||
|
"TabNowPlaying": "Now Playing",
|
||||||
|
"TabNavigation": "Navigation",
|
||||||
|
"TabControls": "Controls",
|
||||||
|
"ButtonFullscreen": "Toggle fullscreen",
|
||||||
|
"ButtonScenes": "Scenes",
|
||||||
|
"ButtonSubtitles": "Subtitles",
|
||||||
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
|
"ButtonPreviousTrack": "Previous track",
|
||||||
|
"ButtonNextTrack": "Next track",
|
||||||
|
"ButtonStop": "Stop",
|
||||||
|
"ButtonPause": "Pause",
|
||||||
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
"LabelGroupMoviesIntoCollectionsHelp": "When displaying movie lists, movies belonging to a collection will be displayed as one grouped item.",
|
||||||
|
"NotificationOptionPluginError": "Plugin failure",
|
||||||
|
"ButtonVolumeUp": "Volume up",
|
||||||
|
"ButtonVolumeDown": "Volume down",
|
||||||
|
"ButtonMute": "Mute",
|
||||||
|
"HeaderLatestMedia": "Latest Media",
|
||||||
|
"OptionSpecialFeatures": "Special Features",
|
||||||
|
"HeaderCollections": "Collections",
|
||||||
|
"LabelProfileCodecsHelp": "Separated by comma. This can be left empty to apply to all codecs.",
|
||||||
|
"LabelProfileContainersHelp": "Separated by comma. This can be left empty to apply to all containers.",
|
||||||
|
"HeaderResponseProfile": "Response Profile",
|
||||||
|
"LabelType": "Type:",
|
||||||
|
"LabelProfileContainer": "Container:",
|
||||||
|
"LabelProfileVideoCodecs": "Video codecs:",
|
||||||
|
"LabelProfileAudioCodecs": "Audio codecs:",
|
||||||
|
"LabelProfileCodecs": "Codecs:",
|
||||||
|
"HeaderDirectPlayProfile": "Direct Play Profile",
|
||||||
|
"HeaderTranscodingProfile": "Transcoding Profile",
|
||||||
|
"HeaderCodecProfile": "Codec Profile",
|
||||||
|
"HeaderCodecProfileHelp": "Codec profiles indicate the limitations of a device when playing specific codecs. If a limitation applies then the media will be transcoded, even if the codec is configured for direct play.",
|
||||||
|
"HeaderContainerProfile": "Container Profile",
|
||||||
|
"HeaderContainerProfileHelp": "Container profiles indicate the limitations of a device when playing specific formats. If a limitation applies then the media will be transcoded, even if the format is configured for direct play.",
|
||||||
|
"OptionProfileVideo": "Video",
|
||||||
|
"OptionProfileAudio": "Audio",
|
||||||
|
"OptionProfileVideoAudio": "Video Audio",
|
||||||
|
"OptionProfilePhoto": "Photo",
|
||||||
|
"LabelUserLibrary": "User library:",
|
||||||
|
"LabelUserLibraryHelp": "Select which user library to display to the device. Leave empty to inherit the default setting.",
|
||||||
|
"OptionPlainStorageFolders": "Display all folders as plain storage folders",
|
||||||
|
"OptionPlainStorageFoldersHelp": "If enabled, all folders are represented in DIDL as \"object.container.storageFolder\" instead of a more specific type, such as \"object.container.person.musicArtist\".",
|
||||||
|
"OptionPlainVideoItems": "Display all videos as plain video items",
|
||||||
|
"OptionPlainVideoItemsHelp": "If enabled, all videos are represented in DIDL as \"object.item.videoItem\" instead of a more specific type, such as \"object.item.videoItem.movie\".",
|
||||||
|
"LabelSupportedMediaTypes": "Supported Media Types:",
|
||||||
|
"TabIdentification": "Identification",
|
||||||
|
"TabDirectPlay": "Direct Play",
|
||||||
|
"TabContainers": "Containers",
|
||||||
|
"TabCodecs": "Codecs",
|
||||||
|
"TabResponses": "Responses",
|
||||||
|
"HeaderProfileInformation": "Profile Information",
|
||||||
|
"LabelEmbedAlbumArtDidl": "Embed album art in Didl",
|
||||||
|
"LabelEmbedAlbumArtDidlHelp": "Some devices prefer this method for obtaining album art. Others may fail to play with this option enabled.",
|
||||||
|
"LabelAlbumArtPN": "Album art PN:",
|
||||||
|
"LabelAlbumArtHelp": "PN used for album art, within the dlna:profileID attribute on upnp:albumArtURI. Some clients require a specific value, regardless of the size of the image.",
|
||||||
|
"LabelAlbumArtMaxWidth": "Album art max width:",
|
||||||
|
"LabelAlbumArtMaxWidthHelp": "Max resolution of album art exposed via upnp:albumArtURI.",
|
||||||
|
"LabelAlbumArtMaxHeight": "Album art max height:",
|
||||||
|
"LabelAlbumArtMaxHeightHelp": "Max resolution of album art exposed via upnp:albumArtURI.",
|
||||||
|
"LabelIconMaxWidth": "Icon max width:",
|
||||||
|
"LabelIconMaxWidthHelp": "Max resolution of icons exposed via upnp:icon.",
|
||||||
|
"LabelIconMaxHeight": "Icon max height:",
|
||||||
|
"LabelIconMaxHeightHelp": "Max resolution of icons exposed via upnp:icon.",
|
||||||
|
"LabelIdentificationFieldHelp": "A case-insensitive substring or regex expression.",
|
||||||
|
"HeaderProfileServerSettingsHelp": "These values control how Media Browser will present itself to the device.",
|
||||||
|
"LabelMaxBitrate": "Max bitrate:",
|
||||||
|
"LabelMaxBitrateHelp": "Specify a max bitrate in bandwidth constrained environments, or if the device imposes it's own limit.",
|
||||||
|
"OptionIgnoreTranscodeByteRangeRequests": "Ignore transcode byte range requests",
|
||||||
|
"OptionIgnoreTranscodeByteRangeRequestsHelp": "If enabled, these requests will be honored but will ignore the byte range header.",
|
||||||
|
"LabelFriendlyName": "Friendly name",
|
||||||
|
"LabelManufacturer": "Manufacturer",
|
||||||
|
"LabelManufacturerUrl": "Manufacturer url",
|
||||||
|
"LabelModelName": "Model name",
|
||||||
|
"LabelModelNumber": "Model number",
|
||||||
|
"LabelModelDescription": "Model description",
|
||||||
|
"LabelModelUrl": "Model url",
|
||||||
|
"LabelSerialNumber": "Serial number",
|
||||||
|
"LabelDeviceDescription": "Device description",
|
||||||
|
"HeaderIdentificationCriteriaHelp": "Enter at least one identification criteria.",
|
||||||
|
"HeaderDirectPlayProfileHelp": "Add direct play profiles to indicate which formats the device can handle natively.",
|
||||||
|
"HeaderTranscodingProfileHelp": "Add transcoding profiles to indicate which formats should be used when transcoding is required.",
|
||||||
|
"HeaderResponseProfileHelp": "Response profiles provide a way to customize information sent to the device when playing certain kinds of media.",
|
||||||
|
"LabelXDlnaCap": "X-Dlna cap:",
|
||||||
|
"LabelXDlnaCapHelp": "Determines the content of the X_DLNACAP element in the urn:schemas-dlna-org:device-1-0 namespace.",
|
||||||
|
"LabelXDlnaDoc": "X-Dlna doc:",
|
||||||
|
"LabelXDlnaDocHelp": "Determines the content of the X_DLNADOC element in the urn:schemas-dlna-org:device-1-0 namespace.",
|
||||||
|
"LabelSonyAggregationFlags": "Sony aggregation flags:",
|
||||||
|
"LabelSonyAggregationFlagsHelp": "Determines the content of the aggregationFlags element in the urn:schemas-sonycom:av namespace.",
|
||||||
|
"LabelTranscodingContainer": "Container:",
|
||||||
|
"LabelTranscodingVideoCodec": "Video codec:",
|
||||||
|
"LabelTranscodingVideoProfile": "Video profile:",
|
||||||
|
"LabelTranscodingAudioCodec": "Audio codec:",
|
||||||
|
"OptionEnableM2tsMode": "Enable M2ts mode",
|
||||||
|
"OptionEnableM2tsModeHelp": "Enable m2ts mode when encoding to mpegts.",
|
||||||
|
"OptionEstimateContentLength": "Estimate content length when transcoding",
|
||||||
|
"OptionReportByteRangeSeekingWhenTranscoding": "Report that the server supports byte seeking when transcoding",
|
||||||
|
"OptionReportByteRangeSeekingWhenTranscodingHelp": "This is required for some devices that don't time seek very well.",
|
||||||
|
"HeaderSubtitleDownloadingHelp": "When Media Browser scans your video files it can search for missing subtitles, and download them using a subtitle provider such as OpenSubtitles.org.",
|
||||||
|
"HeaderDownloadSubtitlesFor": "Download subtitles for:",
|
||||||
|
"MessageNoChapterProviders": "Install a chapter provider plugin such as ChapterDb to enable additional chapter options.",
|
||||||
|
"LabelSkipIfGraphicalSubsPresent": "Skip if the video already contains graphical subtitles",
|
||||||
|
"LabelSkipIfGraphicalSubsPresentHelp": "Keeping text versions of subtitles will result in more efficient delivery to mobile clients.",
|
||||||
|
"TabSubtitles": "Subtitles",
|
||||||
|
"TabChapters": "Chapters",
|
||||||
|
"HeaderDownloadChaptersFor": "Download chapter names for:",
|
||||||
|
"LabelOpenSubtitlesUsername": "Open Subtitles username:",
|
||||||
|
"LabelOpenSubtitlesPassword": "Open Subtitles password:",
|
||||||
|
"HeaderChapterDownloadingHelp": "When Media Browser scans your video files it can download friendly chapter names from the internet using chapter plugins such as ChapterDb.",
|
||||||
|
"LabelPlayDefaultAudioTrack": "Play default audio track regardless of language",
|
||||||
|
"LabelSubtitlePlaybackMode": "Subtitle mode:",
|
||||||
|
"LabelDownloadLanguages": "Download languages:",
|
||||||
|
"ButtonRegister": "Register",
|
||||||
|
"LabelSkipIfAudioTrackPresent": "Skip if the default audio track matches the download language",
|
||||||
|
"LabelSkipIfAudioTrackPresentHelp": "Uncheck this to ensure all videos have subtitles, regardless of audio language.",
|
||||||
|
"HeaderSendMessage": "Send Message",
|
||||||
|
"ButtonSend": "Send",
|
||||||
|
"LabelMessageText": "Message text:",
|
||||||
|
"MessageNoAvailablePlugins": "No available plugins.",
|
||||||
|
"LabelDisplayPluginsFor": "Display plugins for:",
|
||||||
|
"PluginTabMediaBrowserClassic": "MB Classic",
|
||||||
|
"PluginTabMediaBrowserTheater": "MB Theater",
|
||||||
|
"LabelEpisodeName": "Episode name",
|
||||||
|
"LabelSeriesName": "Series name",
|
||||||
|
"ValueSeriesNamePeriod": "Series.name",
|
||||||
|
"ValueSeriesNameUnderscore": "Series_name",
|
||||||
|
"ValueEpisodeNamePeriod": "Episode.name",
|
||||||
|
"ValueEpisodeNameUnderscore": "Episode_name",
|
||||||
|
"HeaderTypeText": "Enter Text",
|
||||||
|
"LabelTypeText": "Text",
|
||||||
|
"HeaderSearchForSubtitles": "Search for Subtitles",
|
||||||
|
"MessageNoSubtitleSearchResultsFound": "No search results founds.",
|
||||||
|
"TabDisplay": "Display",
|
||||||
|
"TabLanguages": "Languages",
|
||||||
|
"TabWebClient": "Web Client",
|
||||||
|
"LabelEnableThemeSongs": "Enable theme songs",
|
||||||
|
"LabelEnableBackdrops": "Enable backdrops",
|
||||||
|
"LabelEnableThemeSongsHelp": "If enabled, theme songs will be played in the background while browsing the library.",
|
||||||
|
"LabelEnableBackdropsHelp": "If enabled, backdrops will be displayed in the background of some pages while browsing the library.",
|
||||||
|
"HeaderHomePage": "Home Page",
|
||||||
|
"HeaderSettingsForThisDevice": "Settings for This Device",
|
||||||
|
"OptionAuto": "Auto",
|
||||||
|
"OptionYes": "Yes",
|
||||||
|
"OptionNo": "No",
|
||||||
|
"LabelHomePageSection1": "Home page section one:",
|
||||||
|
"LabelHomePageSection2": "Home page section two:",
|
||||||
|
"LabelHomePageSection3": "Home page section three:",
|
||||||
|
"LabelHomePageSection4": "Home page section four:",
|
||||||
|
"OptionMyViewsButtons": "My views (buttons)",
|
||||||
|
"OptionMyViews": "My views",
|
||||||
|
"OptionMyViewsSmall": "My views (small)",
|
||||||
|
"OptionResumablemedia": "Resume",
|
||||||
|
"OptionLatestMedia": "Latest media",
|
||||||
|
"OptionLatestChannelMedia": "Latest channel items",
|
||||||
|
"HeaderLatestChannelItems": "Latest Channel Items",
|
||||||
|
"OptionNone": "None",
|
||||||
|
"HeaderLiveTv": "Live TV",
|
||||||
|
"HeaderReports": "Reports",
|
||||||
|
"HeaderMetadataManager": "Metadata Manager",
|
||||||
|
"HeaderPreferences": "Preferences",
|
||||||
|
"MessageLoadingChannels": "Loading channel content...",
|
||||||
|
"ButtonMarkRead": "Mark Read",
|
||||||
|
"OptionDefaultSort": "Default",
|
||||||
|
"OptionCommunityMostWatchedSort": "Most Watched",
|
||||||
|
"TabNextUp": "Next Up",
|
||||||
|
"MessageNoMovieSuggestionsAvailable": "No movie suggestions are currently available. Start watching and rating your movies, and then come back to view your recommendations.",
|
||||||
|
"MessageNoCollectionsAvailable": "Collections allow you to enjoy personalized groupings of Movies, Series, Albums, Books and Games. Click the New button to start creating Collections.",
|
||||||
|
"HeaderWelcomeToMediaBrowserWebClient": "Welcome to the Media Browser Web Client",
|
||||||
|
"ButtonDismiss": "Dismiss",
|
||||||
|
"MessageLearnHowToCustomize": "Learn how to customize this page to your own personal tastes. Click your user icon in the top right corner of the screen to view and update your preferences.",
|
||||||
|
"ButtonEditOtherUserPreferences": "Edit this user's personal preferences.",
|
||||||
|
"LabelChannelStreamQuality": "Preferred internet stream quality:",
|
||||||
|
"LabelChannelStreamQualityHelp": "In a low bandwidth environment, limiting quality can help ensure a smooth streaming experience.",
|
||||||
|
"OptionBestAvailableStreamQuality": "Best available",
|
||||||
|
"LabelEnableChannelContentDownloadingFor": "Enable channel content downloading for:",
|
||||||
|
"LabelEnableChannelContentDownloadingForHelp": "Some channels support downloading content prior to viewing. Enable this in low bandwidth enviornments to download channel content during off hours. Content is downloaded as part of the channel download scheduled task.",
|
||||||
|
"LabelChannelDownloadPath": "Channel content download path:",
|
||||||
|
"LabelChannelDownloadPathHelp": "Specify a custom download path if desired. Leave empty to download to an internal program data folder.",
|
||||||
|
"LabelChannelDownloadAge": "Delete content after: (days)",
|
||||||
|
"LabelChannelDownloadAgeHelp": "Downloaded content older than this will be deleted. It will remain playable via internet streaming.",
|
||||||
|
"ChannelSettingsFormHelp": "Install channels such as Trailers and Vimeo in the plugin catalog.",
|
||||||
|
"LabelSelectCollection": "Select collection:",
|
||||||
|
"ViewTypeMovies": "Movies",
|
||||||
|
"ViewTypeTvShows": "TV",
|
||||||
|
"ViewTypeGames": "Games",
|
||||||
|
"ViewTypeMusic": "Music",
|
||||||
|
"ViewTypeBoxSets": "Collections",
|
||||||
|
"ViewTypeChannels": "Channels",
|
||||||
|
"ViewTypeLiveTV": "Live TV",
|
||||||
|
"HeaderOtherDisplaySettings": "Display Settings",
|
||||||
|
"HeaderMyViews": "My Views",
|
||||||
|
"LabelSelectFolderGroups": "Automatically group content from the following folders into views such as Movies, Music and TV:",
|
||||||
|
"LabelSelectFolderGroupsHelp": "Folders that are unchecked will be displayed by themselves in their own view.",
|
||||||
|
"OptionDisplayAdultContent": "Display adult content",
|
||||||
|
"OptionLibraryFolders": "Media folders",
|
||||||
|
"TitleRemoteControl": "Remote Control",
|
||||||
|
"OptionLatestTvRecordings": "Latest recordings",
|
||||||
|
"LabelProtocolInfo": "Protocol info:",
|
||||||
|
"LabelProtocolInfoHelp": "The value that will be used when responding to GetProtocolInfo requests from the device.",
|
||||||
|
"TabXbmcMetadata": "Xbmc",
|
||||||
|
"HeaderXbmcMetadataHelp": "Media Browser includes native support for Xbmc Nfo metadata and images. To enable or disable Xbmc metadata, use the Advanced tab to configure options for your media types.",
|
||||||
|
"LabelXbmcMetadataUser": "Add user watch data to nfo's for:",
|
||||||
|
"LabelXbmcMetadataUserHelp": "Enable this to keep watch data in sync between Media Browser and Xbmc.",
|
||||||
|
"LabelXbmcMetadataDateFormat": "Release date format:",
|
||||||
|
"LabelXbmcMetadataDateFormatHelp": "All dates within nfo's will be read and written to using this format.",
|
||||||
|
"LabelXbmcMetadataSaveImagePaths": "Save image paths within nfo files",
|
||||||
|
"LabelXbmcMetadataSaveImagePathsHelp": "This is recommended if you have image file names that don't conform to Xbmc guidelines.",
|
||||||
|
"LabelXbmcMetadataEnablePathSubstitution": "Enable path substitution",
|
||||||
|
"LabelXbmcMetadataEnablePathSubstitutionHelp": "Enables path substitution of image paths using the server's path substitution settings.",
|
||||||
|
"LabelXbmcMetadataEnablePathSubstitutionHelp2": "See path substitution.",
|
||||||
|
"LabelGroupChannelsIntoViews": "Display the following channels directly within my views:",
|
||||||
|
"LabelGroupChannelsIntoViewsHelp": "If enabled, these channels will be displayed directly alongside other views. If disabled, they'll be displayed within a separate Channels view.",
|
||||||
|
"LabelDisplayCollectionsView": "Display a collections view to show movie collections",
|
||||||
|
"LabelXbmcMetadataEnableExtraThumbs": "Copy extrafanart into extrathumbs",
|
||||||
|
"LabelXbmcMetadataEnableExtraThumbsHelp": "When downloading images they can be saved into both extrafanart and extrathumbs for maximum Xbmc skin compatibility.",
|
||||||
|
"TabServices": "Services",
|
||||||
|
"TabLogs": "Logs",
|
||||||
|
"HeaderServerLogFiles": "Server log files:",
|
||||||
|
"TabBranding": "Branding",
|
||||||
|
"HeaderBrandingHelp": "Customize the appearance of Media Browser to fit the needs of your group or organization.",
|
||||||
|
"LabelLoginDisclaimer": "Login disclaimer:",
|
||||||
|
"LabelLoginDisclaimerHelp": "This will be displayed at the bottom of the login page.",
|
||||||
|
"LabelAutomaticallyDonate": "Automatically donate this amount every six months",
|
||||||
|
"LabelAutomaticallyDonateHelp": "You can cancel at any time via your PayPal account.",
|
||||||
|
"OptionList": "List",
|
||||||
|
"TabDashboard": "Dashboard",
|
||||||
|
"TitleServer": "Server",
|
||||||
|
"LabelCache": "Cache:",
|
||||||
|
"LabelLogs": "Logs:",
|
||||||
|
"LabelMetadata": "Metadata:",
|
||||||
|
"LabelImagesByName": "Images by name:",
|
||||||
|
"LabelTranscodingTemporaryFiles": "Transcoding temporary files:",
|
||||||
|
"HeaderLatestMusic": "Latest Music",
|
||||||
|
"HeaderBranding": "Branding",
|
||||||
|
"HeaderApiKeys": "Api Keys",
|
||||||
|
"HeaderApiKeysHelp": "External applications are required to have an Api key in order to communicate with Media Browser. Keys are issued by logging in with a Media Browser account, or by manually granting the application a key.",
|
||||||
|
"HeaderApiKey": "Api Key",
|
||||||
|
"HeaderApp": "App",
|
||||||
|
"HeaderDevice": "Device",
|
||||||
|
"HeaderUser": "User",
|
||||||
|
"HeaderDateIssued": "Date Issued",
|
||||||
|
"LabelChapterName": "Chapter {0}",
|
||||||
|
"HeaderNewApiKey": "New Api Key",
|
||||||
|
"LabelAppName": "App name",
|
||||||
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "Nieuwe API-sleutel",
|
"HeaderNewApiKey": "Nieuwe API-sleutel",
|
||||||
"LabelAppName": "Applicatie Naam",
|
"LabelAppName": "Applicatie Naam",
|
||||||
"LabelAppNameExample": "Voorbeeld: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Voorbeeld: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Verleen een applicatie toestemming om te communiceren met Media Browser."
|
"HeaderNewApiKeyHelp": "Verleen een applicatie toestemming om te communiceren met Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identificatie Header",
|
||||||
|
"LabelValue": "Waarde:",
|
||||||
|
"LabelMatchType": "Type overeenkomst:",
|
||||||
|
"OptionEquals": "Is gelijk aan",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Subtekenreeks"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "Nova Chave da Api",
|
"HeaderNewApiKey": "Nova Chave da Api",
|
||||||
"LabelAppName": "Nome da app",
|
"LabelAppName": "Nome da app",
|
||||||
"LabelAppNameExample": "Exemplo: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Exemplo: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Conceder permiss\u00e3o a uma aplica\u00e7\u00e3o para se comunicar com o Media Browser."
|
"HeaderNewApiKeyHelp": "Conceder permiss\u00e3o a uma aplica\u00e7\u00e3o para se comunicar com o Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Cabe\u00e7alhos de Http",
|
||||||
|
"HeaderIdentificationHeader": "Cabe\u00e7alho de Identifica\u00e7\u00e3o",
|
||||||
|
"LabelValue": "Valor:",
|
||||||
|
"LabelMatchType": "Tipo de correspond\u00eancia",
|
||||||
|
"OptionEquals": "Igual",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -524,10 +524,10 @@
|
||||||
"HeaderActiveDevices": "\u0410\u043a\u0442\u0438\u0432\u043d\u044b\u0435 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430",
|
"HeaderActiveDevices": "\u0410\u043a\u0442\u0438\u0432\u043d\u044b\u0435 \u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430",
|
||||||
"HeaderPendingInstallations": "\u041e\u0442\u043b\u043e\u0436\u0435\u043d\u043d\u044b\u0435 \u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043a\u0438",
|
"HeaderPendingInstallations": "\u041e\u0442\u043b\u043e\u0436\u0435\u043d\u043d\u044b\u0435 \u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043a\u0438",
|
||||||
"HeaerServerInformation": "\u0421\u0432\u0435\u0434\u0435\u043d\u0438\u044f \u043e \u0441\u0435\u0440\u0432\u0435\u0440\u0435",
|
"HeaerServerInformation": "\u0421\u0432\u0435\u0434\u0435\u043d\u0438\u044f \u043e \u0441\u0435\u0440\u0432\u0435\u0440\u0435",
|
||||||
"ButtonRestartNow": "\u041f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c \u0441\u0435\u0439\u0447\u0430\u0441",
|
"ButtonRestartNow": "\u041f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c \u043d\u0435\u043c\u0435\u0434\u043b\u0435\u043d\u043d\u043e",
|
||||||
"ButtonRestart": "\u041f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c",
|
"ButtonRestart": "\u041f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442\u044c",
|
||||||
"ButtonShutdown": "\u0417\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u0443",
|
"ButtonShutdown": "\u0417\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u0443",
|
||||||
"ButtonUpdateNow": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c \u0441\u0435\u0439\u0447\u0430\u0441",
|
"ButtonUpdateNow": "\u041e\u0431\u043d\u043e\u0432\u0438\u0442\u044c \u043d\u0435\u043c\u0435\u0434\u043b\u0435\u043d\u043d\u043e",
|
||||||
"PleaseUpdateManually": "\u0417\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u0435 \u0440\u0430\u0431\u043e\u0442\u0443 \u0441\u0435\u0440\u0432\u0435\u0440\u0430 \u0438 \u043e\u0431\u043d\u043e\u0432\u0438\u0442\u0435 \u0432\u0440\u0443\u0447\u043d\u0443\u044e.",
|
"PleaseUpdateManually": "\u0417\u0430\u0432\u0435\u0440\u0448\u0438\u0442\u0435 \u0440\u0430\u0431\u043e\u0442\u0443 \u0441\u0435\u0440\u0432\u0435\u0440\u0430 \u0438 \u043e\u0431\u043d\u043e\u0432\u0438\u0442\u0435 \u0432\u0440\u0443\u0447\u043d\u0443\u044e.",
|
||||||
"NewServerVersionAvailable": "\u0414\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u0435\u0440\u0441\u0438\u044f Media Browser Server!",
|
"NewServerVersionAvailable": "\u0414\u043e\u0441\u0442\u0443\u043f\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u0435\u0440\u0441\u0438\u044f Media Browser Server!",
|
||||||
"ServerUpToDate": "Media Browser Server - \u043e\u0431\u043d\u043e\u0432\u043b\u0451\u043d",
|
"ServerUpToDate": "Media Browser Server - \u043e\u0431\u043d\u043e\u0432\u043b\u0451\u043d",
|
||||||
|
@ -857,7 +857,7 @@
|
||||||
"HeaderLatestMusic": "\u041d\u043e\u0432\u0438\u043d\u043a\u0438 \u043c\u0443\u0437\u044b\u043a\u0438",
|
"HeaderLatestMusic": "\u041d\u043e\u0432\u0438\u043d\u043a\u0438 \u043c\u0443\u0437\u044b\u043a\u0438",
|
||||||
"HeaderBranding": "\u0411\u0440\u0435\u043d\u0434\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435",
|
"HeaderBranding": "\u0411\u0440\u0435\u043d\u0434\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435",
|
||||||
"HeaderApiKeys": "\u041a\u043b\u044e\u0447\u0438 API",
|
"HeaderApiKeys": "\u041a\u043b\u044e\u0447\u0438 API",
|
||||||
"HeaderApiKeysHelp": "\u0412\u043d\u0435\u0448\u043d\u0438\u043c \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f\u043c \u0442\u0440\u0435\u0431\u0443\u0435\u0442\u0441\u044f \u043a\u043b\u044e\u0447 API, \u0434\u043b\u044f \u043f\u043e\u0434\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u044f \u043a Media Browser. \u041a\u043b\u044e\u0447\u0438 \u0432\u044b\u0434\u0430\u044e\u0442\u0441\u044f \u043f\u0440\u0438 \u0432\u0445\u043e\u0434\u0435 \u0441 \u0443\u0447\u0451\u0442\u043d\u043e\u0439 \u0437\u0430\u043f\u0438\u0441\u044c\u044e Media Browser, \u0438\u043b\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044e \u0432\u0440\u0443\u0447\u043d\u0443\u044e \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442\u0441\u044f \u043a\u043b\u044e\u0447.",
|
"HeaderApiKeysHelp": "\u0412\u043d\u0435\u0448\u043d\u0438\u043c \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f\u043c \u0442\u0440\u0435\u0431\u0443\u0435\u0442\u0441\u044f \u043a\u043b\u044e\u0447 API, \u0434\u043b\u044f \u043f\u043e\u0434\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u044f \u043a Media Browser. \u041a\u043b\u044e\u0447\u0438 \u0432\u044b\u0434\u0430\u044e\u0442\u0441\u044f \u043f\u0440\u0438 \u0432\u0445\u043e\u0434\u0435 \u0441 \u0443\u0447\u0451\u0442\u043d\u043e\u0439 \u0437\u0430\u043f\u0438\u0441\u044c\u044e Media Browser, \u0438\u043b\u0438 \u043a\u043b\u044e\u0447 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044e \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442\u0441\u044f \u0432\u0440\u0443\u0447\u043d\u0443\u044e.",
|
||||||
"HeaderApiKey": "\u041a\u043b\u044e\u0447 API",
|
"HeaderApiKey": "\u041a\u043b\u044e\u0447 API",
|
||||||
"HeaderApp": "\u041f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0435",
|
"HeaderApp": "\u041f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0435",
|
||||||
"HeaderDevice": "\u0423\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e",
|
"HeaderDevice": "\u0423\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u043e",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "\u041d\u043e\u0432\u044b\u0439 \u043a\u043b\u044e\u0447 API",
|
"HeaderNewApiKey": "\u041d\u043e\u0432\u044b\u0439 \u043a\u043b\u044e\u0447 API",
|
||||||
"LabelAppName": "\u041d\u0430\u0437\u0432\u0430\u043d\u0438\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f",
|
"LabelAppName": "\u041d\u0430\u0437\u0432\u0430\u043d\u0438\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f",
|
||||||
"LabelAppNameExample": "\u041f\u0440\u0438\u043c\u0435\u0440: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "\u041f\u0440\u0438\u043c\u0435\u0440: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "\u041f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044e \u0440\u0430\u0437\u0440\u0435\u0448\u0435\u043d\u0438\u044f \u043d\u0430 \u043f\u043e\u0434\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435 \u043a Media Browser."
|
"HeaderNewApiKeyHelp": "\u041f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044e \u0440\u0430\u0437\u0440\u0435\u0448\u0435\u043d\u0438\u044f \u043d\u0430 \u043f\u043e\u0434\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435 \u043a Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "HTTP-\u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u0438",
|
||||||
|
"HeaderIdentificationHeader": "\u0418\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0446\u0438\u043e\u043d\u043d\u044b\u0439 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043e\u043a",
|
||||||
|
"LabelValue": "\u0417\u043d\u0430\u0447\u0435\u043d\u0438\u0435:",
|
||||||
|
"LabelMatchType": "\u0421\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u0439 \u0442\u0438\u043f:",
|
||||||
|
"OptionEquals": "\u0420\u0430\u0432\u043d\u044f\u0435\u0442\u0441\u044f",
|
||||||
|
"OptionRegex": "\u0420\u0435\u0433\u0443\u043b\u044f\u0440\u043d\u043e\u0435 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435",
|
||||||
|
"OptionSubstring": "\u041f\u043e\u0434\u0441\u0442\u0440\u043e\u043a\u0430"
|
||||||
}
|
}
|
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "Ny API-nyckel",
|
"HeaderNewApiKey": "Ny API-nyckel",
|
||||||
"LabelAppName": "Appens namn",
|
"LabelAppName": "Appens namn",
|
||||||
"LabelAppNameExample": "Exempel: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Exempel: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Till\u00e5t en app att kommunicera med Media Browser"
|
"HeaderNewApiKeyHelp": "Till\u00e5t en app att kommunicera med Media Browser",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -630,8 +630,8 @@
|
||||||
"ButtonScenes": "Scenes",
|
"ButtonScenes": "Scenes",
|
||||||
"ButtonSubtitles": "Subtitles",
|
"ButtonSubtitles": "Subtitles",
|
||||||
"ButtonAudioTracks": "Audio tracks",
|
"ButtonAudioTracks": "Audio tracks",
|
||||||
"ButtonPreviousTrack": "Previous Track",
|
"ButtonPreviousTrack": "Previous track",
|
||||||
"ButtonNextTrack": "Next Track",
|
"ButtonNextTrack": "Next track",
|
||||||
"ButtonStop": "Stop",
|
"ButtonStop": "Stop",
|
||||||
"ButtonPause": "Pause",
|
"ButtonPause": "Pause",
|
||||||
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
"LabelGroupMoviesIntoCollections": "Group movies into collections",
|
||||||
|
@ -867,5 +867,12 @@
|
||||||
"HeaderNewApiKey": "New Api Key",
|
"HeaderNewApiKey": "New Api Key",
|
||||||
"LabelAppName": "App name",
|
"LabelAppName": "App name",
|
||||||
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
"LabelAppNameExample": "Example: Sickbeard, NzbDrone",
|
||||||
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser."
|
"HeaderNewApiKeyHelp": "Grant an application permission to communicate with Media Browser.",
|
||||||
|
"HeaderHttpHeaders": "Http Headers",
|
||||||
|
"HeaderIdentificationHeader": "Identification Header",
|
||||||
|
"LabelValue": "Value:",
|
||||||
|
"LabelMatchType": "Match type:",
|
||||||
|
"OptionEquals": "Equals",
|
||||||
|
"OptionRegex": "Regex",
|
||||||
|
"OptionSubstring": "Substring"
|
||||||
}
|
}
|
|
@ -357,6 +357,7 @@
|
||||||
<EmbeddedResource Include="Localization\Server\pl.json" />
|
<EmbeddedResource Include="Localization\Server\pl.json" />
|
||||||
<EmbeddedResource Include="Localization\JavaScript\es_ES.json" />
|
<EmbeddedResource Include="Localization\JavaScript\es_ES.json" />
|
||||||
<EmbeddedResource Include="Localization\Server\es_ES.json" />
|
<EmbeddedResource Include="Localization\Server\es_ES.json" />
|
||||||
|
<EmbeddedResource Include="Localization\Server\ko.json" />
|
||||||
<None Include="packages.config" />
|
<None Include="packages.config" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|
|
@ -522,6 +522,7 @@ namespace MediaBrowser.WebDashboard.Api
|
||||||
"mediacontroller.js",
|
"mediacontroller.js",
|
||||||
"chromecast.js",
|
"chromecast.js",
|
||||||
"backdrops.js",
|
"backdrops.js",
|
||||||
|
"sync.js",
|
||||||
|
|
||||||
"mediaplayer.js",
|
"mediaplayer.js",
|
||||||
"mediaplayer-video.js",
|
"mediaplayer-video.js",
|
||||||
|
|
|
@ -770,6 +770,9 @@
|
||||||
<Content Include="dashboard-ui\scripts\serversecurity.js">
|
<Content Include="dashboard-ui\scripts\serversecurity.js">
|
||||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||||
</Content>
|
</Content>
|
||||||
|
<Content Include="dashboard-ui\scripts\sync.js">
|
||||||
|
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||||
|
</Content>
|
||||||
<Content Include="dashboard-ui\scripts\thememediaplayer.js">
|
<Content Include="dashboard-ui\scripts\thememediaplayer.js">
|
||||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||||
</Content>
|
</Content>
|
||||||
|
|
Loading…
Reference in a new issue