You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

format.go 7.5KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164
  1. package data
  2. import "encoding/json"
  3. type FormatType uint8
  4. const (
  5. FormatVideoOnly = 1 << iota
  6. FormatAudioOnly
  7. Format3D
  8. FormatHLS
  9. FormatDASH
  10. FormatHighFps
  11. FormatStd = 0
  12. )
  13. type Format struct {
  14. ID string `json:"id"`
  15. Extension string `json:"ext"`
  16. Width uint32 `json:"width"`
  17. Height uint32 `json:"height"`
  18. VideoCodec string `json:"vcodec"`
  19. AudioCodec string `json:"acodec"`
  20. AudioBitrate uint32 `json:"abr"`
  21. Flags FormatType `json:"flags"`
  22. }
  23. var FormatsById map[string]*Format
  24. func init() {
  25. ids := []string {
  26. "5", "6", "13", "17", "18", "22", "34", "35",
  27. "36", "37", "38", "43", "44", "45", "46", "59",
  28. "78", "82", "83", "84", "85", "100", "101", "102",
  29. "91", "92", "93", "94", "95", "96", "132", "151",
  30. "133", "134", "135", "136", "137", "138", "160", "212",
  31. "264", "298", "299", "266", "139", "140", "141", "256",
  32. "258", "325", "328", "167", "168", "169", "170", "218",
  33. "219", "278", "242", "243", "244", "245", "246", "247",
  34. "248", "271", "272", "302", "303", "308", "313", "315",
  35. "171", "172", "249", "250", "251",
  36. }
  37. FormatsById = make(map[string]*Format)
  38. for i, id := range ids {
  39. format := &Formats[i]
  40. if format.ID != id { panic("misaligned IDs: " + id + "/" + format.ID) }
  41. FormatsById[id] = format
  42. }
  43. }
  44. // Taken from github.com/rg3/youtube-dl
  45. // As in youtube_dl/extractor/youtube.py
  46. var Formats = []Format{
  47. // Standard formats
  48. { "5", "flv", 400, 240, "h263", "mp3", 64, FormatStd },
  49. { "6", "flv", 450, 270, "h263", "mp3", 64, FormatStd },
  50. { "13", "3gp", 0, 0, "mp4v", "aac", 0, FormatStd },
  51. { "17", "3gp", 176, 144, "mp4v", "aac", 24, FormatStd },
  52. { "18", "mp4", 640, 360, "h264", "aac", 96, FormatStd },
  53. { "22", "mp4", 1280, 720, "h264", "aac", 192, FormatStd },
  54. { "34", "flv", 640, 360, "h264", "aac", 128, FormatStd },
  55. { "35", "flv", 854, 480, "h264", "aac", 128, FormatStd },
  56. // * ID 36 videos are either 320x180 (BaW_jenozKc) or 320x240 (__2ABJjxzNo), abr varies as well
  57. { "36", "3gp", 320, 0, "mp4v", "aac", 0, FormatStd },
  58. { "37", "mp4", 1920, 1080, "h264", "aac", 192, FormatStd },
  59. { "38", "mp4", 4096, 3072, "h264", "aac", 192, FormatStd },
  60. { "43", "webm", 640, 360, "vp8", "vorbis", 128, FormatStd },
  61. { "44", "webm", 854, 480, "vp8", "vorbis", 128, FormatStd },
  62. { "45", "webm", 1280, 720, "vp8", "vorbis", 192, FormatStd },
  63. { "46", "webm", 1920, 1080, "vp8", "vorbis", 192, FormatStd },
  64. { "59", "mp4", 854, 480, "h264", "aac", 128, FormatStd },
  65. { "78", "mp4", 854, 480, "h264", "aac", 128, FormatStd },
  66. // 3D videos
  67. { "82", "mp4", 0, 360, "h264", "aac", 128, Format3D },
  68. { "83", "mp4", 0, 480, "h264", "aac", 128, Format3D },
  69. { "84", "mp4", 0, 720, "h264", "aac", 192, Format3D },
  70. { "85", "mp4", 0, 1080, "h264", "aac", 192, Format3D },
  71. { "100", "webm", 0, 360, "vp8", "vorbis", 128, Format3D },
  72. { "101", "webm", 0, 480, "vp8", "vorbis", 192, Format3D },
  73. { "102", "webm", 0, 720, "vp8", "vorbis", 192, Format3D },
  74. // Apple HTTP Live Streaming
  75. { "91", "mp4", 0, 144, "h264", "aac", 48, FormatHLS },
  76. { "92", "mp4", 0, 240, "h264", "aac", 48, FormatHLS },
  77. { "93", "mp4", 0, 360, "h264", "aac", 128, FormatHLS },
  78. { "94", "mp4", 0, 480, "h264", "aac", 128, FormatHLS },
  79. { "95", "mp4", 0, 720, "h264", "aac", 256, FormatHLS },
  80. { "96", "mp4", 0, 1080, "h264", "aac", 256, FormatHLS },
  81. { "132", "mp4", 0, 240, "h264", "aac", 48, FormatHLS },
  82. { "151", "mp4", 0, 72, "h264", "aac", 24, FormatHLS },
  83. // DASH mp4 video
  84. { "133", "mp4", 0, 240, "h264", "", 0, FormatDASH | FormatVideoOnly },
  85. { "134", "mp4", 0, 360, "h264", "", 0, FormatDASH | FormatVideoOnly },
  86. { "135", "mp4", 0, 480, "h264", "", 0, FormatDASH | FormatVideoOnly },
  87. { "136", "mp4", 0, 720, "h264", "", 0, FormatDASH | FormatVideoOnly },
  88. { "137", "mp4", 0, 1080, "h264", "", 0, FormatDASH | FormatVideoOnly },
  89. { "138", "mp4", 0, 0, "h264", "", 0, FormatDASH | FormatVideoOnly }, // Height can vary (https://github.com/rg3/youtube-dl/issues/4559)
  90. { "160", "mp4", 0, 144, "h264", "", 0, FormatDASH | FormatVideoOnly },
  91. { "212", "mp4", 0, 480, "h264", "", 0, FormatDASH | FormatVideoOnly },
  92. { "264", "mp4", 0, 1440, "h264", "", 0, FormatDASH | FormatVideoOnly },
  93. { "298", "mp4", 0, 720, "h264", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  94. { "299", "mp4", 0, 1080, "h264", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  95. { "266", "mp4", 0, 2160, "h264", "", 0, FormatDASH | FormatVideoOnly },
  96. // DASH mp4 audio
  97. { "139", "m4a", 0, 0, "", "aac", 48, FormatDASH | FormatAudioOnly },
  98. { "140", "m4a", 0, 0, "", "aac", 128, FormatDASH | FormatAudioOnly },
  99. { "141", "m4a", 0, 0, "", "aac", 256, FormatDASH | FormatAudioOnly },
  100. { "256", "m4a", 0, 0, "", "aac", 0, FormatDASH | FormatAudioOnly },
  101. { "258", "m4a", 0, 0, "", "aac", 0, FormatDASH | FormatAudioOnly },
  102. { "325", "m4a", 0, 0, "", "dtse", 0, FormatDASH | FormatAudioOnly },
  103. { "328", "m4a", 0, 0, "", "ec-3", 0, FormatDASH | FormatAudioOnly },
  104. // DASH webm
  105. { "167", "webm", 640, 360, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  106. { "168", "webm", 854, 480, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  107. { "169", "webm", 1280, 720, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  108. { "170", "webm", 1920, 1080, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  109. { "218", "webm", 854, 480, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  110. { "219", "webm", 854, 480, "vp8", "", 0, FormatDASH | FormatVideoOnly },
  111. { "278", "webm", 0, 144, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  112. { "242", "webm", 0, 240, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  113. { "243", "webm", 0, 360, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  114. { "244", "webm", 0, 480, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  115. { "245", "webm", 0, 480, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  116. { "246", "webm", 0, 480, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  117. { "247", "webm", 0, 720, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  118. { "248", "webm", 0, 1080, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  119. { "271", "webm", 0, 1440, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  120. // * ID 272 videos are either 3840x2160 (e.g. RtoitU2A-3E) or 7680x4320 (sLprVF6d7Ug)
  121. { "272", "webm", 0, 2160, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  122. { "302", "webm", 0, 720, "vp9", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  123. { "303", "webm", 0, 1080, "vp9", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  124. { "308", "webm", 0, 1440, "vp9", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  125. { "313", "webm", 0, 2160, "vp9", "", 0, FormatDASH | FormatVideoOnly },
  126. { "315", "webm", 0, 2160, "vp9", "", 0, FormatDASH | FormatVideoOnly | FormatHighFps },
  127. // DASH webm audio
  128. { "171", "webm", 0, 0, "", "vorbis", 128, FormatDASH | FormatAudioOnly },
  129. { "172", "webm", 0, 0, "", "vorbis", 256, FormatDASH | FormatAudioOnly },
  130. // DASH webm opus audio
  131. { "249", "webm", 0, 0, "", "opus", 50, FormatDASH | FormatAudioOnly },
  132. { "250", "webm", 0, 0, "", "opus", 70, FormatDASH | FormatAudioOnly },
  133. { "251", "webm", 0, 0, "", "opus", 160, FormatDASH | FormatAudioOnly },
  134. }
  135. func (f FormatType) MarshalJSON() ([]byte, error) {
  136. flags := make([]string, 0)
  137. setFlag := func(mask FormatType, name string) {
  138. if f&mask != 0 {
  139. flags = append(flags, name)
  140. }
  141. }
  142. setFlag(FormatVideoOnly, "videoOnly")
  143. setFlag(FormatAudioOnly, "audioOnly")
  144. setFlag(Format3D, "3d")
  145. setFlag(FormatHLS, "hls")
  146. setFlag(FormatDASH, "dash")
  147. setFlag(FormatHighFps, "hiFps")
  148. return json.Marshal(flags)
  149. }