1use serde::{Deserialize, Serialize};
2use viser_ffmpeg::{
3 Codec, RES_360P, RES_480P, RES_720P, RES_1080P, RES_1440P, RES_2160P, Resolution,
4};
5use viser_ladder::Opts as LadderOpts;
6
7#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
8#[serde(rename_all = "snake_case")]
9pub enum DeviceClass {
10 Mobile,
11 Desktop,
12 Tv,
13 Tv4k,
14}
15
16#[derive(Debug, Clone, Serialize, Deserialize)]
18pub struct Profile {
19 pub name: String,
20 pub device: DeviceClass,
21 pub description: String,
22 pub vmaf_model: String,
23 pub max_res: Resolution,
24 pub resolutions: Vec<Resolution>,
25 pub codecs: Vec<Codec>,
26 pub ladder_opts: LadderOpts,
27}
28
29pub fn mobile_profile() -> Profile {
30 Profile {
31 name: "Mobile".into(),
32 device: DeviceClass::Mobile,
33 description: "Smartphones and small tablets. Screen <7 inches.".into(),
34 vmaf_model: "vmaf_v0.6.1".into(),
35 max_res: RES_720P,
36 resolutions: vec![RES_360P, RES_480P, RES_720P],
37 codecs: vec![Codec::SvtAv1, Codec::X264],
38 ladder_opts: LadderOpts {
39 num_rungs: 4,
40 min_bitrate: 150.0,
41 max_bitrate: 3000.0,
42 min_vmaf: 50.0,
43 max_vmaf: 95.0,
44 },
45 }
46}
47
48pub fn desktop_profile() -> Profile {
49 Profile {
50 name: "Desktop".into(),
51 device: DeviceClass::Desktop,
52 description: "Laptops and desktop monitors. 13-27 inch screens.".into(),
53 vmaf_model: "vmaf_v0.6.1".into(),
54 max_res: RES_1080P,
55 resolutions: vec![RES_480P, RES_720P, RES_1080P],
56 codecs: vec![Codec::SvtAv1, Codec::X265, Codec::X264],
57 ladder_opts: LadderOpts::default(),
58 }
59}
60
61pub fn tv_profile() -> Profile {
62 Profile {
63 name: "TV (1080p)".into(),
64 device: DeviceClass::Tv,
65 description: "TVs and large displays. 40-65 inch screens.".into(),
66 vmaf_model: "vmaf_v0.6.1".into(),
67 max_res: RES_1080P,
68 resolutions: vec![RES_480P, RES_720P, RES_1080P],
69 codecs: vec![Codec::SvtAv1, Codec::X265, Codec::X264],
70 ladder_opts: LadderOpts {
71 num_rungs: 8,
72 min_bitrate: 200.0,
73 max_bitrate: 12000.0,
74 min_vmaf: 40.0,
75 max_vmaf: 97.0,
76 },
77 }
78}
79
80pub fn tv_4k_profile() -> Profile {
81 Profile {
82 name: "TV (4K)".into(),
83 device: DeviceClass::Tv4k,
84 description: "4K TVs. 55-85 inch screens.".into(),
85 vmaf_model: "vmaf_4k_v0.6.1".into(),
86 max_res: RES_2160P,
87 resolutions: vec![RES_720P, RES_1080P, RES_1440P, RES_2160P],
88 codecs: vec![Codec::SvtAv1, Codec::X265],
89 ladder_opts: LadderOpts {
90 num_rungs: 8,
91 min_bitrate: 1000.0,
92 max_bitrate: 25000.0,
93 min_vmaf: 40.0,
94 max_vmaf: 97.0,
95 },
96 }
97}
98
99pub fn all_profiles() -> Vec<Profile> {
100 vec![mobile_profile(), desktop_profile(), tv_profile(), tv_4k_profile()]
101}