aboutsummaryrefslogtreecommitdiff
path: root/video_player/src/main.cpp
blob: 3a06f920e2f137d3ce144955cbdcf425580955c2 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>

#include <mpv/client.h>

static void usage() {
    fprintf(stderr, "usage: quickmedia-video-player [--wid <window_id>] <file>\n");
    fprintf(stderr, "  --wid <window_id>    The window to embed the video player into. Optional\n");
    fprintf(stderr, "examples:\n");
    fprintf(stderr, "  quickmedia-video-player video.mp4\n");
    fprintf(stderr, "  quickmedia-video-player --wid 30481231 video.mp4\n");
    exit(1);
}

static bool string_to_long(const char *str, long &result) {
    errno = 0;
    char *endptr = NULL;
    result = strtol(str, &endptr, 0);
    return endptr != str && errno == 0;
}

static inline void check_error(int status) {
    if (status < 0) {
        fprintf(stderr, "mpv API error: %s\n", mpv_error_string(status));
        exit(2);
    }
}

int main(int argc, char **argv) {
    long wid_num = 0;
    const char *wid = nullptr;
    const char *file_to_play = nullptr;

    for(int i = 1; i < argc; ++i) {
        const char *arg = argv[i];
        if(strcmp(arg, "--wid") == 0) {
            if(wid) {
                fprintf(stderr, "Error: option --wid was specified multiple times\n");
                usage();
            }

            if(i + 1 == argc) {
                fprintf(stderr, "Error: missing window id after option --wid\n");
                usage();
            }

            wid = argv[i + 1];
            ++i;
        } else if(strcmp(arg, "--") == 0) {
            if(i + 1 == argc) {
                fprintf(stderr, "Error: missing file option after --\n");
                usage();
            } else if(i + 1 != argc - 1) {
                fprintf(stderr, "Error: more than one option was specified after --\n");
                usage();
            }

            file_to_play = argv[i + 1];
            ++i;
        } else if(strncmp(arg, "--", 2) == 0) {
            fprintf(stderr, "Error: invalid option %s\n", arg);
            usage();
        } else {
            if(file_to_play) {
                fprintf(stderr, "Error: file option was specified multiple times\n");
                usage();
            }

            file_to_play = arg;
        }
    }

    if(!file_to_play) {
        fprintf(stderr, "Error: missing file option\n");
        usage();
    }

    if(wid) {
        if(!string_to_long(wid, wid_num)) {
            fprintf(stderr, "Error: invalid number %s was specified for option --wid\n", wid);
            usage();
        }
    }

    mpv_handle *ctx = mpv_create();
    if (!ctx) {
        printf("failed creating context\n");
        return 1;
    }

    check_error(mpv_set_option_string(ctx, "input-default-bindings", "yes"));
    check_error(mpv_set_option_string(ctx, "input-vo-keyboard", "yes"));
    check_error(mpv_set_option_string(ctx, "osc", "yes"));
    
    check_error(mpv_set_option_string(ctx, "profile", "gpu-hq"));
    check_error(mpv_set_option_string(ctx, "vo", "gpu"));
    check_error(mpv_set_option_string(ctx, "hwdec", "auto"));
    check_error(mpv_set_option_string(ctx, "config", "yes"));

    if(wid)
        check_error(mpv_set_option_string(ctx, "wid", wid));

    check_error(mpv_initialize(ctx));

    const char *cmd[] = { "loadfile", file_to_play, NULL };
    check_error(mpv_command(ctx, cmd));

    while (true) {
        mpv_event *event = mpv_wait_event(ctx, 10000);
        printf("event: %s\n", mpv_event_name(event->event_id));
        if (event->event_id == MPV_EVENT_SHUTDOWN)
            break;
    }

    mpv_terminate_destroy(ctx);
    return 0;
}