Add inline video support to Tweets
This commit is contained in:
parent
8f71b09440
commit
dd94212c9f
@ -69,6 +69,7 @@
|
|||||||
51B3630D244B6428000DEF2A /* TwitterSymbol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B3630C244B6428000DEF2A /* TwitterSymbol.swift */; };
|
51B3630D244B6428000DEF2A /* TwitterSymbol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B3630C244B6428000DEF2A /* TwitterSymbol.swift */; };
|
||||||
51B3630F244B6CB9000DEF2A /* TwitterExtendedEntities.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B3630E244B6CB9000DEF2A /* TwitterExtendedEntities.swift */; };
|
51B3630F244B6CB9000DEF2A /* TwitterExtendedEntities.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B3630E244B6CB9000DEF2A /* TwitterExtendedEntities.swift */; };
|
||||||
51B36311244B6CFB000DEF2A /* TwitterMedia.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B36310244B6CFA000DEF2A /* TwitterMedia.swift */; };
|
51B36311244B6CFB000DEF2A /* TwitterMedia.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B36310244B6CFA000DEF2A /* TwitterMedia.swift */; };
|
||||||
|
51B36313244B8B5E000DEF2A /* TwitterVideo.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51B36312244B8B5E000DEF2A /* TwitterVideo.swift */; };
|
||||||
51BB7B84233531BC008E8144 /* AccountBehaviors.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BB7B83233531BC008E8144 /* AccountBehaviors.swift */; };
|
51BB7B84233531BC008E8144 /* AccountBehaviors.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BB7B83233531BC008E8144 /* AccountBehaviors.swift */; };
|
||||||
51BC8FCC237EC055004F8B56 /* Feed.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BC8FCB237EC055004F8B56 /* Feed.swift */; };
|
51BC8FCC237EC055004F8B56 /* Feed.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BC8FCB237EC055004F8B56 /* Feed.swift */; };
|
||||||
51BFDECE238B508D00216323 /* ContainerIdentifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BFDECD238B508D00216323 /* ContainerIdentifier.swift */; };
|
51BFDECE238B508D00216323 /* ContainerIdentifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 51BFDECD238B508D00216323 /* ContainerIdentifier.swift */; };
|
||||||
@ -317,6 +318,7 @@
|
|||||||
51B3630C244B6428000DEF2A /* TwitterSymbol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterSymbol.swift; sourceTree = "<group>"; };
|
51B3630C244B6428000DEF2A /* TwitterSymbol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterSymbol.swift; sourceTree = "<group>"; };
|
||||||
51B3630E244B6CB9000DEF2A /* TwitterExtendedEntities.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterExtendedEntities.swift; sourceTree = "<group>"; };
|
51B3630E244B6CB9000DEF2A /* TwitterExtendedEntities.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterExtendedEntities.swift; sourceTree = "<group>"; };
|
||||||
51B36310244B6CFA000DEF2A /* TwitterMedia.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterMedia.swift; sourceTree = "<group>"; };
|
51B36310244B6CFA000DEF2A /* TwitterMedia.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterMedia.swift; sourceTree = "<group>"; };
|
||||||
|
51B36312244B8B5E000DEF2A /* TwitterVideo.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TwitterVideo.swift; sourceTree = "<group>"; };
|
||||||
51BB7B83233531BC008E8144 /* AccountBehaviors.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AccountBehaviors.swift; sourceTree = "<group>"; };
|
51BB7B83233531BC008E8144 /* AccountBehaviors.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AccountBehaviors.swift; sourceTree = "<group>"; };
|
||||||
51BC8FCB237EC055004F8B56 /* Feed.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Feed.swift; sourceTree = "<group>"; };
|
51BC8FCB237EC055004F8B56 /* Feed.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Feed.swift; sourceTree = "<group>"; };
|
||||||
51BFDECD238B508D00216323 /* ContainerIdentifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ContainerIdentifier.swift; sourceTree = "<group>"; };
|
51BFDECD238B508D00216323 /* ContainerIdentifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ContainerIdentifier.swift; sourceTree = "<group>"; };
|
||||||
@ -590,6 +592,7 @@
|
|||||||
51B3630C244B6428000DEF2A /* TwitterSymbol.swift */,
|
51B3630C244B6428000DEF2A /* TwitterSymbol.swift */,
|
||||||
51B36308244B62A5000DEF2A /* TwitterURL.swift */,
|
51B36308244B62A5000DEF2A /* TwitterURL.swift */,
|
||||||
5132DE802449159100806ADE /* TwitterUser.swift */,
|
5132DE802449159100806ADE /* TwitterUser.swift */,
|
||||||
|
51B36312244B8B5E000DEF2A /* TwitterVideo.swift */,
|
||||||
);
|
);
|
||||||
path = Twitter;
|
path = Twitter;
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
@ -1215,6 +1218,7 @@
|
|||||||
51E59599228C77BC00FCC42B /* FeedbinUnreadEntry.swift in Sources */,
|
51E59599228C77BC00FCC42B /* FeedbinUnreadEntry.swift in Sources */,
|
||||||
552032F8229D5D5A009559E0 /* ReaderAPIEntry.swift in Sources */,
|
552032F8229D5D5A009559E0 /* ReaderAPIEntry.swift in Sources */,
|
||||||
552032FB229D5D5A009559E0 /* ReaderAPITag.swift in Sources */,
|
552032FB229D5D5A009559E0 /* ReaderAPITag.swift in Sources */,
|
||||||
|
51B36313244B8B5E000DEF2A /* TwitterVideo.swift in Sources */,
|
||||||
5165D72822835F7800D9D53D /* FeedFinder.swift in Sources */,
|
5165D72822835F7800D9D53D /* FeedFinder.swift in Sources */,
|
||||||
9EBD49C023C67602005AD5CD /* FeedlyDownloadArticlesOperation.swift in Sources */,
|
9EBD49C023C67602005AD5CD /* FeedlyDownloadArticlesOperation.swift in Sources */,
|
||||||
51D58755227F53BE00900287 /* FeedbinTag.swift in Sources */,
|
51D58755227F53BE00900287 /* FeedbinTag.swift in Sources */,
|
||||||
|
@ -17,6 +17,7 @@ struct TwitterMedia: Codable {
|
|||||||
let url: String?
|
let url: String?
|
||||||
let displayURL: String?
|
let displayURL: String?
|
||||||
let type: String?
|
let type: String?
|
||||||
|
let video: TwitterVideo?
|
||||||
|
|
||||||
enum CodingKeys: String, CodingKey {
|
enum CodingKeys: String, CodingKey {
|
||||||
case idStr = "idStr"
|
case idStr = "idStr"
|
||||||
@ -26,6 +27,7 @@ struct TwitterMedia: Codable {
|
|||||||
case url = "url"
|
case url = "url"
|
||||||
case displayURL = "display_url"
|
case displayURL = "display_url"
|
||||||
case type = "type"
|
case type = "type"
|
||||||
|
case video = "video_info"
|
||||||
}
|
}
|
||||||
|
|
||||||
func renderAsHTML() -> String {
|
func renderAsHTML() -> String {
|
||||||
@ -37,9 +39,13 @@ struct TwitterMedia: Codable {
|
|||||||
html += "<a href=\"\(url)\">"
|
html += "<a href=\"\(url)\">"
|
||||||
html += renderPhotoAsHTML()
|
html += renderPhotoAsHTML()
|
||||||
html += "</a>"
|
html += "</a>"
|
||||||
|
} else {
|
||||||
|
html += renderPhotoAsHTML()
|
||||||
}
|
}
|
||||||
|
case "video":
|
||||||
|
html += renderVideoAsHTML()
|
||||||
default:
|
default:
|
||||||
return ""
|
break
|
||||||
}
|
}
|
||||||
|
|
||||||
return html
|
return html
|
||||||
@ -58,5 +64,37 @@ private extension TwitterMedia {
|
|||||||
}
|
}
|
||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func renderVideoAsHTML() -> String {
|
||||||
|
guard let bestVariantURL = findBestVariant()?.url else { return "" }
|
||||||
|
|
||||||
|
var html = "<video "
|
||||||
|
|
||||||
|
if let httpsMediaURL = httpsMediaURL {
|
||||||
|
html += "poster=\"\(httpsMediaURL)\" "
|
||||||
|
} else if let mediaURL = mediaURL {
|
||||||
|
html += "poster=\"\(mediaURL)\" "
|
||||||
|
}
|
||||||
|
|
||||||
|
html += "src=\"\(bestVariantURL)\"></video>"
|
||||||
|
return html
|
||||||
|
}
|
||||||
|
|
||||||
|
func findBestVariant() -> TwitterVideo.Variant? {
|
||||||
|
var best: TwitterVideo.Variant? = nil
|
||||||
|
if let variants = video?.variants {
|
||||||
|
for variant in variants {
|
||||||
|
if let currentBest = best {
|
||||||
|
if variant.bitrate ?? 0 > currentBest.bitrate ?? 0 {
|
||||||
|
best = variant
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
best = variant
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return best
|
||||||
|
}
|
||||||
|
|
||||||
|
// <video poster="https://pbs.twimg.com/ext_tw_video_thumb/1251578276709109764/pu/img/fHFdxWFL3nQE9L0I.jpg:large" width="10" height="7" src="https://video.twimg.com/ext_tw_video/1251578276709109764/pu/vid/1028x720/lHpEeJekcIZAod2B.mp4?tag=10" playsinline="true" controls="true"></video>
|
||||||
}
|
}
|
||||||
|
34
Frameworks/Account/FeedProvider/Twitter/TwitterVideo.swift
Normal file
34
Frameworks/Account/FeedProvider/Twitter/TwitterVideo.swift
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
//
|
||||||
|
// TwitterVideoInfo.swift
|
||||||
|
// Account
|
||||||
|
//
|
||||||
|
// Created by Maurice Parker on 4/18/20.
|
||||||
|
// Copyright © 2020 Ranchero Software, LLC. All rights reserved.
|
||||||
|
//
|
||||||
|
|
||||||
|
import Foundation
|
||||||
|
|
||||||
|
|
||||||
|
struct TwitterVideo: Codable {
|
||||||
|
|
||||||
|
let variants: [Variant]?
|
||||||
|
|
||||||
|
enum CodingKeys: String, CodingKey {
|
||||||
|
case variants = "variants"
|
||||||
|
}
|
||||||
|
|
||||||
|
struct Variant: Codable {
|
||||||
|
|
||||||
|
let bitrate: Int?
|
||||||
|
let contentType: String?
|
||||||
|
let url: String?
|
||||||
|
|
||||||
|
enum CodingKeys: String, CodingKey {
|
||||||
|
case bitrate = "bitrate"
|
||||||
|
case contentType = "content_type"
|
||||||
|
case url = "url"
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user