fix some subtitles not displaying on transcoded streams

This commit is contained in:
Aiden Vigue 2021-05-25 18:46:10 -04:00
parent 3dd0f370c7
commit 5cf959336d
No known key found for this signature in database
GPG Key ID: E7570472648F4544
12 changed files with 89 additions and 51 deletions

View File

@ -478,7 +478,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 19;
CURRENT_PROJECT_VERSION = 20;
DEVELOPMENT_ASSET_PATHS = "\"JellyfinPlayer/Preview Content\"";
DEVELOPMENT_TEAM = 9R8RREG67J;
ENABLE_BITCODE = NO;
@ -508,7 +508,7 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 19;
CURRENT_PROJECT_VERSION = 20;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
DEVELOPMENT_ASSET_PATHS = "\"JellyfinPlayer/Preview Content\"";
DEVELOPMENT_TEAM = 9R8RREG67J;

View File

@ -118,7 +118,7 @@ struct ContinueWatchingView: View {
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=550&quality=80&tag=\(item.Image)")!)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 6, height: 6))!)
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 48, height: 32))!)
.resizable()
.frame(width: 320, height: 180)
.cornerRadius(10)
@ -148,7 +148,7 @@ struct ContinueWatchingView: View {
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=550&quality=80&tag=\(item.Image)")!)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 6, height: 6))!)
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 48, height: 32))!)
.resizable()
.frame(width: 320, height: 180)
.cornerRadius(10)

View File

@ -196,6 +196,9 @@ struct EpisodeItemView: View {
.supportedOrientations(.landscape)
.overrideViewPreference(.dark)
.prefersHomeIndicatorAutoHidden(true)
.introspectTabBarController { (UITabBarController) in
UITabBarController.tabBar.isHidden = true
}
} else {
LoadingView(isShowing: $isLoading) {
VStack(alignment:.leading) {
@ -570,11 +573,12 @@ struct EpisodeItemView: View {
.navigationBarTitleDisplayMode(.inline)
.navigationTitle("\(fullItem.Name) - S\(String(fullItem.ParentIndexNumber ?? 0)):E\(String(fullItem.IndexNumber ?? 0)) - \(fullItem.SeriesName ?? "")")
.introspectTabBarController { (UITabBarController) in
UITabBarController.tabBar.isHidden = true
UITabBarController.tabBar.isHidden = false
}
}.onAppear(perform: loadData)
.supportedOrientations(.allButUpsideDown)
.overrideViewPreference(.unspecified)
.preferredColorScheme(.none)
.prefersHomeIndicatorAutoHidden(false)
}
}

View File

@ -19,7 +19,7 @@
<key>CFBundleShortVersionString</key>
<string>$(MARKETING_VERSION)</string>
<key>CFBundleVersion</key>
<string>19</string>
<string>20</string>
<key>ITSAppUsesNonExemptEncryption</key>
<false/>
<key>LSRequiresIPhoneOS</key>

View File

@ -91,10 +91,10 @@ struct LatestMediaView: View {
VStack(alignment: .leading) {
if(item.Type == "Series") {
Spacer().frame(height:10)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=150&quality=80&tag=\(item.Image)")!)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=250&quality=80&tag=\(item.Image)")!)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 6, height: 6))!)
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 16, height: 16))!)
.resizable()
.frame(width: 100, height: 150)
.cornerRadius(10)
@ -122,10 +122,10 @@ struct LatestMediaView: View {
).shadow(radius: 6)
} else {
Spacer().frame(height:10)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=150&quality=80&tag=\(item.Image)")!)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=250&quality=80&tag=\(item.Image)")!)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 6, height: 6))!)
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 16, height: 16))!)
.resizable()
.frame(width: 100, height: 150)
.cornerRadius(10)

View File

@ -208,7 +208,7 @@ struct LibraryView: View {
NavigationLink(destination: ItemView(item: item )) {
VStack(alignment: .leading) {
if(item.Type == "Movie") {
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=150&quality=80&tag=\(item.Image)"))
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=250&quality=80&tag=\(item.Image)"))
.resizable()
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 16, height: 16))!)
@ -218,8 +218,9 @@ struct LibraryView: View {
}
.frame(width:100, height: 150)
.cornerRadius(10)
.shadow(radius: 5)
} else {
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=150&quality=80&tag=\(item.Image)"))
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.Id)/Images/\(item.ImageType)?maxWidth=250&quality=80&tag=\(item.Image)"))
.resizable()
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 16, height: 16))!)
@ -245,7 +246,7 @@ struct LibraryView: View {
.opacity(0.8)
.cornerRadius(10.0)
.padding(3), alignment: .topTrailing
)
).shadow(radius: 5)
}
Text(item.Name)
.font(.caption)

View File

@ -12,6 +12,8 @@ struct UserSettings: Decodable {
var RemoteMaxBitrate: Int;
var AutoSelectSubtitles: Bool;
var AutoSelectSubtitlesLangcode: String;
var SubtitlePositionOffset: Int;
var SubtitleFontName: String;
}
struct Bitrates: Codable, Hashable {

View File

@ -224,6 +224,7 @@ struct MovieItemView: View {
_progressString.wrappedValue = "\(String(progminutes).leftPad(toWidth: 2, withString: "0"))m"
}
}
_isLoading.wrappedValue = false;
} catch {
}
@ -232,7 +233,6 @@ struct MovieItemView: View {
debugPrint(error)
break
}
_isLoading.wrappedValue = false;
}
}
@ -243,6 +243,9 @@ struct MovieItemView: View {
.preferredColorScheme(.dark)
.overrideViewPreference(.dark)
.prefersHomeIndicatorAutoHidden(true)
.introspectTabBarController { (UITabBarController) in
UITabBarController.tabBar.isHidden = true
}
} else {
LoadingView(isShowing: $isLoading) {
VStack(alignment:.leading) {
@ -382,14 +385,14 @@ struct MovieItemView: View {
WebImage(url: cast.Image)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (cast.ImageBlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : cast.ImageBlurHash), size: CGSize(width: 4, height: 4))!)
Image(uiImage: UIImage(blurHash: (cast.ImageBlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : cast.ImageBlurHash), size: CGSize(width: 16, height: 16))!)
.resizable()
.aspectRatio(contentMode: .fill)
.frame(width: 70, height: 70)
.frame(width: 100, height: 100)
.cornerRadius(10)
}
.aspectRatio(contentMode: .fill)
.frame(width: 70, height: 70)
.frame(width: 100, height: 100)
.cornerRadius(10).shadow(radius: 6)
Text(cast.Name).font(.footnote).fontWeight(.regular).lineLimit(1).frame(width: 100).foregroundColor(Color.primary)
if(cast.Role != "") {
@ -564,7 +567,7 @@ struct MovieItemView: View {
WebImage(url: cast.Image)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (cast.ImageBlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : cast.ImageBlurHash), size: CGSize(width: 8, height: 8))!)
Image(uiImage: UIImage(blurHash: (cast.ImageBlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : cast.ImageBlurHash), size: CGSize(width: 16, height: 16))!)
.resizable()
.aspectRatio(contentMode: .fill)
.frame(width: 100, height: 100)
@ -621,6 +624,7 @@ struct MovieItemView: View {
}.onAppear(perform: loadData)
.supportedOrientations(.allButUpsideDown)
.overrideViewPreference(.unspecified)
.preferredColorScheme(.none)
.prefersHomeIndicatorAutoHidden(false)
}
}

View File

@ -79,7 +79,7 @@ struct NextUpView: View {
NavigationLink(destination: ItemView(item: item)) {
VStack(alignment: .leading) {
Spacer().frame(height:10)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.SeriesId ?? "")/Images/\(item.ImageType)?maxWidth=150&quality=80&tag=\(item.Image)")!)
WebImage(url: URL(string: "\(globalData.server?.baseURI ?? "")/Items/\(item.SeriesId ?? "")/Images/\(item.ImageType)?maxWidth=250&quality=80&tag=\(item.Image)")!)
.resizable() // Resizable like SwiftUI.Image, you must use this modifier or the view will use the image bitmap size
.placeholder {
Image(uiImage: UIImage(blurHash: (item.BlurHash == "" ? "W$H.4}D%bdo#a#xbtpxVW?W?jXWsXVt7Rjf5axWqxbWXnhada{s-" : item.BlurHash), size: CGSize(width: 16, height: 16))!)

View File

@ -7,6 +7,10 @@
"name": "4K - 100 Mbps",
"value": 100000000
},
{
"name": "4K - 80 Mbps",
"value": 80000000
},
{
"name": "1080p - 60 Mbps",
"value": 60000000

View File

@ -44,7 +44,7 @@ struct VideoPlayerView: View {
var item: DetailItem;
@State private var pbitem: PlaybackItem = PlaybackItem(videoType: VideoType.direct, videoUrl: URL(string: "https://example.com")!, subtitles: []);
@State private var streamLoading = false;
@State private var vlcplayer: VLCMediaPlayer = VLCMediaPlayer(options: ["--sub-margin=-50"]);
@State private var vlcplayer: VLCMediaPlayer = VLCMediaPlayer();
@State private var isPlaying = false;
@State private var subtitles: [Subtitle] = [];
@State private var audioTracks: [Subtitle] = [];
@ -272,7 +272,7 @@ struct VideoPlayerView: View {
let disableSubtitleTrack = Subtitle(name: "Disabled", id: -1, url: URL(string: "https://example.com")!, delivery: "Embed", codec: "")
_subtitles.wrappedValue.append(disableSubtitleTrack);
for (_,stream):(String, JSON) in json["MediaSources"][0]["MediaStreams"] {
if(stream["Type"].string == "Subtitle" && stream["Codec"] != "subrip") { //ignore ripped subtitles - we don't want to extract subtitles
if(stream["Type"].string == "Subtitle") { //ignore ripped subtitles - we don't want to extract subtitles
let deliveryUrl = URL(string: "\(globalData.server?.baseURI ?? "")\(stream["DeliveryUrl"].string ?? "")")!
let subtitle = Subtitle(name: stream["DisplayTitle"].string ?? "", id: Int32(stream["Index"].int ?? 0), url: deliveryUrl, delivery: stream["DeliveryMethod"].string ?? "", codec: stream["Codec"].string ?? "")
_subtitles.wrappedValue.append(subtitle);
@ -315,7 +315,7 @@ struct VideoPlayerView: View {
let disableSubtitleTrack = Subtitle(name: "Disabled", id: -1, url: URL(string: "https://example.com")!, delivery: "Embed", codec: "")
_subtitles.wrappedValue.append(disableSubtitleTrack);
for (_,stream):(String, JSON) in json["MediaSources"][0]["MediaStreams"] {
if(stream["Type"].string == "Subtitle" && stream["Codec"] != "subrip") {
if(stream["Type"].string == "Subtitle") {
let deliveryUrl = URL(string: "\(globalData.server?.baseURI ?? "")\(stream["DeliveryUrl"].string ?? "")")!
let subtitle = Subtitle(name: stream["DisplayTitle"].string ?? "", id: Int32(stream["Index"].int ?? 0), url: deliveryUrl, delivery: stream["DeliveryMethod"].string ?? "", codec: stream["Codec"].string ?? "")
_subtitles.wrappedValue.append(subtitle);
@ -490,10 +490,14 @@ struct VideoPlayerView: View {
.onAppear(perform: startStream)
.navigationBarHidden(true)
.overrideViewPreference(.dark)
.preferredColorScheme(.dark)
.navigationBarBackButtonHidden(true)
.edgesIgnoringSafeArea(.all)
.introspectTabBarController { (UITabBarController) in
UITabBarController.tabBar.isHidden = true
.withHostingWindow { window in
if let vc = window?.rootViewController {
let preferenceHost = vc as! PreferenceUIHostingController
preferenceHost._viewPreference = .dark
}
}
.statusBar(hidden: true)
.onTapGesture(perform: resetTimer)

View File

@ -18,19 +18,23 @@ struct SettingsView: View {
@State private var username: String = "";
@State private var inNetworkStreamBitrate: Int = 40000000;
@State private var outOfNetworkStreamBitrate: Int = 40000000;
@State private var autoSelectSubtitles: Bool = false;
@State private var autoSelectSubtitlesLangcode: String = "none";
func onAppear() {
_username.wrappedValue = globalData.user?.username ?? "";
let defaults = UserDefaults.standard
_inNetworkStreamBitrate.wrappedValue = defaults.integer(forKey: "InNetworkBandwidth");
_outOfNetworkStreamBitrate.wrappedValue = defaults.integer(forKey: "OutOfNetworkBandwidth");
_autoSelectSubtitles.wrappedValue = defaults.bool(forKey: "AutoSelectSubtitles");
_autoSelectSubtitlesLangcode.wrappedValue = defaults.string(forKey: "AutoSelectSubtitlesLangcode") ?? "";
}
var body: some View {
NavigationView() {
Form() {
Section(header: Text("Playback settings")) {
Picker("Default local playback bitrate", selection: $inNetworkStreamBitrate) {
Picker("Default local quality", selection: $inNetworkStreamBitrate) {
ForEach(self.viewModel.bitrates, id: \.self) { bitrate in
Text(bitrate.name).tag(bitrate.value)
}
@ -39,7 +43,7 @@ struct SettingsView: View {
defaults.setValue(_inNetworkStreamBitrate.wrappedValue, forKey: "InNetworkBandwidth")
}
Picker("Default remote playback bitrate", selection: $outOfNetworkStreamBitrate) {
Picker("Default remote quality", selection: $outOfNetworkStreamBitrate) {
ForEach(self.viewModel.bitrates, id: \.self) { bitrate in
Text(bitrate.name).tag(bitrate.value)
}
@ -49,38 +53,53 @@ struct SettingsView: View {
}
}
Section(header: Text("Accessibility")) {
Toggle("Automatically show subtitles", isOn: $autoSelectSubtitles).onChange(of: autoSelectSubtitles, perform: { _ in
let defaults = UserDefaults.standard
defaults.setValue(autoSelectSubtitles, forKey: "AutoSelectSubtitles")
})
Picker("Language preferences", selection: $autoSelectSubtitlesLangcode) {
}
}
Section() {
Button {
let fetchRequest: NSFetchRequest<NSFetchRequestResult> = NSFetchRequest(entityName: "Server")
let deleteRequest = NSBatchDeleteRequest(fetchRequest: fetchRequest)
HStack() {
Text("Signed in as \(username)").foregroundColor(.primary)
Spacer()
Button {
let fetchRequest: NSFetchRequest<NSFetchRequestResult> = NSFetchRequest(entityName: "Server")
let deleteRequest = NSBatchDeleteRequest(fetchRequest: fetchRequest)
do {
try viewContext.execute(deleteRequest)
} catch _ as NSError {
// TODO: handle the error
}
let fetchRequest2: NSFetchRequest<NSFetchRequestResult> = NSFetchRequest(entityName: "SignedInUser")
let deleteRequest2 = NSBatchDeleteRequest(fetchRequest: fetchRequest2)
do {
try viewContext.execute(deleteRequest)
} catch _ as NSError {
// TODO: handle the error
}
let fetchRequest2: NSFetchRequest<NSFetchRequestResult> = NSFetchRequest(entityName: "SignedInUser")
let deleteRequest2 = NSBatchDeleteRequest(fetchRequest: fetchRequest2)
do {
try viewContext.execute(deleteRequest2)
} catch _ as NSError {
// TODO: handle the error
do {
try viewContext.execute(deleteRequest2)
} catch _ as NSError {
// TODO: handle the error
}
globalData.server = nil
globalData.user = nil
globalData.authToken = ""
globalData.authHeader = ""
jsi.did = true
// TODO: This should redirect to the server selection screen
exit(-1)
} label: {
Text("Log out").font(.callout)
}
globalData.server = nil
globalData.user = nil
globalData.authToken = ""
globalData.authHeader = ""
jsi.did = true
// TODO: This should redirect to the server selection screen
exit(-1)
} label: {
Text("Log out")
}
}
}
.navigationBarTitle("Settings", displayMode: .inline)
.toolbar {
ToolbarItemGroup(placement: .navigationBarLeading) {