aboutsummaryrefslogtreecommitdiffhomepage
path: root/DOCS/client_api_examples
diff options
context:
space:
mode:
Diffstat (limited to 'DOCS/client_api_examples')
-rw-r--r--DOCS/client_api_examples/Copyright14
-rw-r--r--DOCS/client_api_examples/README.md114
-rw-r--r--DOCS/client_api_examples/cocoa-openglcb/cocoa-openglcb.m304
-rw-r--r--DOCS/client_api_examples/cocoa/cocoabasic.m209
-rw-r--r--DOCS/client_api_examples/qml/main.cpp136
-rw-r--r--DOCS/client_api_examples/qml/main.h36
-rw-r--r--DOCS/client_api_examples/qml/main.qml71
-rw-r--r--DOCS/client_api_examples/qml/mpvtest.pro12
-rw-r--r--DOCS/client_api_examples/qml/mpvtest.qrc5
-rw-r--r--DOCS/client_api_examples/qml_direct/main.cpp159
-rw-r--r--DOCS/client_api_examples/qml_direct/main.h51
-rw-r--r--DOCS/client_api_examples/qml_direct/main.qml49
-rw-r--r--DOCS/client_api_examples/qml_direct/mpvtest.pro12
-rw-r--r--DOCS/client_api_examples/qml_direct/mpvtest.qrc5
-rw-r--r--DOCS/client_api_examples/qt/qtexample.cpp225
-rw-r--r--DOCS/client_api_examples/qt/qtexample.h37
-rw-r--r--DOCS/client_api_examples/qt/qtexample.pro13
-rw-r--r--DOCS/client_api_examples/qt_opengl/main.cpp13
-rw-r--r--DOCS/client_api_examples/qt_opengl/mainwindow.cpp52
-rw-r--r--DOCS/client_api_examples/qt_opengl/mainwindow.h27
-rw-r--r--DOCS/client_api_examples/qt_opengl/mpvwidget.cpp129
-rw-r--r--DOCS/client_api_examples/qt_opengl/mpvwidget.h38
-rw-r--r--DOCS/client_api_examples/qt_opengl/qt_opengl.pro13
-rw-r--r--DOCS/client_api_examples/sdl/main.c158
-rw-r--r--DOCS/client_api_examples/simple/simple.c54
25 files changed, 0 insertions, 1936 deletions
diff --git a/DOCS/client_api_examples/Copyright b/DOCS/client_api_examples/Copyright
deleted file mode 100644
index 38d1891eb7..0000000000
--- a/DOCS/client_api_examples/Copyright
+++ /dev/null
@@ -1,14 +0,0 @@
-All examples in this directory and its sub-directories are licensed
-under one of the following licenses:
-
- WTFPL, ISC, Ms-PL, AGPLv3, BSD (any)
-
-Pick any license of your liking, and disregard the others.
-
-(The full text of each license is available on this website:
- http://opensource.org/licenses/alphabetical )
-
-Additionally, you may consider the example code to be public domain.
-You are free to use any of the example code without further
-requirements or need for attribution.
-
diff --git a/DOCS/client_api_examples/README.md b/DOCS/client_api_examples/README.md
deleted file mode 100644
index c21deb5579..0000000000
--- a/DOCS/client_api_examples/README.md
+++ /dev/null
@@ -1,114 +0,0 @@
-# Client API examples
-
-All these examples use the mpv client API through libmpv.
-
-## Where are the docs?
-
-The libmpv C API is documented directly in the header files (on normal Unix
-systems, this is in `/usr/include/mpv/client.h`.
-
-libmpv merely gives you access to mpv's command interface, which is documented
-here:
-* Options (`mpv_set_option()` and friends): http://mpv.io/manual/master/#options
-* Commands (`mpv_command()` and friends): http://mpv.io/manual/master/#list-of-input-commands
-* Properties (`mpv_set_property()` and friends): http://mpv.io/manual/master/#properties
-
-Essentially everything is done with them, including loading a file, retrieving
-playback progress, and so on.
-
-## Methods of embedding the video window
-
-All of these examples concentrate on how to integrate mpv's video renderers
-with your own GUI. This is generally the hardest part. libmpv enforces a
-somewhat efficient video output method, rather than e.g. returning a RGBA
-surface in memory for each frame. The latter would be prohibitively inefficient,
-because it would require conversion on the CPU. The goal is also not requiring
-the API users to reinvent their own video rendering/scaling/presentation
-mechanisms.
-
-There are currently 2 methods of embedding video.
-
-### Native window embedding
-
-This uses the platform's native method of nesting multiple windows. For example,
-Linux/X11 can nest a window from a completely different process. The nested
-window can redraw contents on its own, and receive user input if the user
-interacts with this window.
-
-libmpv lets you specify a parent window for its own video window via the `wid`
-option. Then libmpv will create its window with your window as parent, and
-render its video inside of it.
-
-This method is highly OS-dependent. Some behavior is OS-specific. There are
-problems with focusing on X11 (the ancient X11 focus policy mismatches with
-that of modern UI toolkits - it's normally worked around, but this is not
-easily possible with raw window embedding). It seems to have stability problems
-on OSX when using the Qt toolkit.
-
-### OpenGL embedding
-
-This method lets you use libmpv's OpenGL renderer directly. You create an
-OpenGL context, and then use `mpv_opengl_cb_draw()` to render the video on
-each frame.
-
-This is more complicated, because libmpv will work directly on your own OpenGL
-state. It's also not possible to have mpv automatically receive user input.
-You will have to simulate this with the `mouse`/`keypress`/`keydown`/`keyup`
-commands.
-
-You also get much more flexibility. For example, you can actually render your
-own OSD on top of the video, something that is not possible with raw window
-embedding.
-
-### Which one to use?
-
-Due to the various platform-specific behavior and problems (in particular on
-OSX), OpenGL embedding is recommended. If you're not comfortable with requiring
-OpenGL, or want to support "direct" video output such as vdpau (which might
-win when it comes to performance and energy-saving), you should probably
-support both methods if possible.
-
-## List of examples
-
-### simple
-
-Very primitive terminal-only example. Shows some most basic API usage.
-
-### cocoa
-
-Shows how to embed the mpv video window in Objective-C/Cocoa.
-
-### cocoa-openglcb
-
-Similar to the cocoa sample, but shows how to integrate mpv's OpenGL renderer
-using libmpv's opengl-cb API. Since it does not require complicated interaction
-with Cocoa elements from different libraries, it's more robust.
-
-### qt
-
-Shows how to embed the mpv video window in Qt (using normal desktop widgets).
-
-### qt_opengl
-
-Shows how to use mpv's OpenGL video renderer in Qt. This uses the opengl-cb API
-for video. Since it does not rely on embedding "foreign" native Windows, it's
-usually more robust, potentially faster, and it's easier to control how your
-GUI interacts with the video. You can do your own OpenGL rendering on top of
-the video as well.
-
-### qml
-
-Shows how to use mpv's OpenGL video renderer in QtQuick2 with QML. Uses the
-opengl-cb API for video. Since the video is a normal QML element, it's trivial
-to create OSD overlays with QML-native graphical elements as well.
-
-### qml_direct
-
-Alternative example, which typically avoids a FBO indirection. Might be
-slightly faster, but is less flexible and harder to use. In particular, the
-video is not a normal QML element. Uses the opengl-cb API for video.
-
-### sdl
-
-Show how to embed the mpv OpenGL renderer in SDL. Uses the opengl-cb API for
-video.
diff --git a/DOCS/client_api_examples/cocoa-openglcb/cocoa-openglcb.m b/DOCS/client_api_examples/cocoa-openglcb/cocoa-openglcb.m
deleted file mode 100644
index 4a4e8aa533..0000000000
--- a/DOCS/client_api_examples/cocoa-openglcb/cocoa-openglcb.m
+++ /dev/null
@@ -1,304 +0,0 @@
-// Plays a video from the command line in an opengl view in its own window.
-
-// Build with: clang -o cocoa-openglcb cocoa-openglcb.m `pkg-config --libs --cflags mpv` -framework Cocoa -framework OpenGL
-
-#import <mpv/client.h>
-#import <mpv/opengl_cb.h>
-
-#import <stdio.h>
-#import <stdlib.h>
-#import <OpenGL/gl.h>
-
-#import <Cocoa/Cocoa.h>
-
-
-static inline void check_error(int status)
-{
- if (status < 0) {
- printf("mpv API error: %s\n", mpv_error_string(status));
- exit(1);
- }
-}
-
-static void *get_proc_address(void *ctx, const char *name)
-{
- CFStringRef symbolName = CFStringCreateWithCString(kCFAllocatorDefault, name, kCFStringEncodingASCII);
- void *addr = CFBundleGetFunctionPointerForName(CFBundleGetBundleWithIdentifier(CFSTR("com.apple.opengl")), symbolName);
- CFRelease(symbolName);
- return addr;
-}
-
-static void glupdate(void *ctx);
-
-@interface MpvClientOGLView : NSOpenGLView
-@property mpv_opengl_cb_context *mpvGL;
-- (instancetype)initWithFrame:(NSRect)frame;
-- (void)drawRect;
-- (void)fillBlack;
-@end
-
-@implementation MpvClientOGLView
-- (instancetype)initWithFrame:(NSRect)frame
-{
- // make sure the pixel format is double buffered so we can use
- // [[self openGLContext] flushBuffer].
- NSOpenGLPixelFormatAttribute attributes[] = {
- NSOpenGLPFADoubleBuffer,
- 0
- };
- self = [super initWithFrame:frame
- pixelFormat:[[NSOpenGLPixelFormat alloc] initWithAttributes:attributes]];
-
- if (self) {
- [self setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable];
- // swap on vsyncs
- GLint swapInt = 1;
- [[self openGLContext] setValues:&swapInt forParameter:NSOpenGLCPSwapInterval];
- [[self openGLContext] makeCurrentContext];
- self.mpvGL = nil;
- }
- return self;
-}
-
-- (void)fillBlack
-{
- glClearColor(0, 0, 0, 0);
- glClear(GL_COLOR_BUFFER_BIT);
-}
-
-- (void)drawRect
-{
- if (self.mpvGL)
- mpv_opengl_cb_draw(self.mpvGL, 0, self.bounds.size.width, -self.bounds.size.height);
- else
- [self fillBlack];
- [[self openGLContext] flushBuffer];
-}
-
-- (void)drawRect:(NSRect)dirtyRect
-{
- [self drawRect];
-}
-@end
-
-@interface CocoaWindow : NSWindow
-@property(retain, readonly) MpvClientOGLView *glView;
-@property(retain, readonly) NSButton *pauseButton;
-@end
-
-@implementation CocoaWindow
-- (BOOL)canBecomeMainWindow { return YES; }
-- (BOOL)canBecomeKeyWindow { return YES; }
-- (void)initOGLView {
- NSRect bounds = [[self contentView] bounds];
- // window coordinate origin is bottom left
- NSRect glFrame = NSMakeRect(bounds.origin.x, bounds.origin.y + 30, bounds.size.width, bounds.size.height - 30);
- _glView = [[MpvClientOGLView alloc] initWithFrame:glFrame];
- [self.contentView addSubview:_glView];
-
- NSRect buttonFrame = NSMakeRect(bounds.origin.x, bounds.origin.y, 60, 30);
- _pauseButton = [[NSButton alloc] initWithFrame:buttonFrame];
- _pauseButton.buttonType = NSToggleButton;
- // button target has to be the delegate (it holds the mpv context
- // pointer), so that's set later.
- _pauseButton.action = @selector(togglePause:);
- _pauseButton.title = @"Pause";
- _pauseButton.alternateTitle = @"Play";
- [self.contentView addSubview:_pauseButton];
-}
-@end
-
-@interface AppDelegate : NSObject <NSApplicationDelegate>
-{
- mpv_handle *mpv;
- dispatch_queue_t queue;
- CocoaWindow *window;
-}
-@end
-
-static void wakeup(void *);
-
-@implementation AppDelegate
-
-- (void)createWindow {
-
- int mask = NSTitledWindowMask|NSClosableWindowMask|
- NSMiniaturizableWindowMask|NSResizableWindowMask;
-
- window = [[CocoaWindow alloc]
- initWithContentRect:NSMakeRect(0, 0, 1280, 720)
- styleMask:mask
- backing:NSBackingStoreBuffered
- defer:NO];
-
- // force a minimum size to stop opengl from exploding.
- [window setMinSize:NSMakeSize(200, 200)];
- [window initOGLView];
- [window setTitle:@"cocoa-openglcb example"];
- [window makeMainWindow];
- [window makeKeyAndOrderFront:nil];
-
- NSMenu *m = [[NSMenu alloc] initWithTitle:@"AMainMenu"];
- NSMenuItem *item = [m addItemWithTitle:@"Apple" action:nil keyEquivalent:@""];
- NSMenu *sm = [[NSMenu alloc] initWithTitle:@"Apple"];
- [m setSubmenu:sm forItem:item];
- [sm addItemWithTitle: @"quit" action:@selector(terminate:) keyEquivalent:@"q"];
- [NSApp setMenu:m];
- [NSApp activateIgnoringOtherApps:YES];
-}
-
-- (void) applicationDidFinishLaunching:(NSNotification *)notification {
- [NSApp setActivationPolicy:NSApplicationActivationPolicyRegular];
- atexit_b(^{
- // Because activation policy has just been set to behave like a real
- // application, that policy must be reset on exit to prevent, among
- // other things, the menubar created here from remaining on screen.
- [NSApp setActivationPolicy:NSApplicationActivationPolicyProhibited];
- });
-
- // Read filename
- NSArray *args = [NSProcessInfo processInfo].arguments;
- if (args.count < 2) {
- NSLog(@"Expected filename on command line");
- exit(1);
- }
- NSString *filename = args[1];
-
- [self createWindow];
- window.pauseButton.target = self;
-
- mpv = mpv_create();
- if (!mpv) {
- printf("failed creating context\n");
- exit(1);
- }
-
- check_error(mpv_set_option_string(mpv, "input-media-keys", "yes"));
- // request important errors
- check_error(mpv_request_log_messages(mpv, "warn"));
-
- check_error(mpv_initialize(mpv));
- check_error(mpv_set_option_string(mpv, "vo", "opengl-cb"));
- mpv_opengl_cb_context *mpvGL = mpv_get_sub_api(mpv, MPV_SUB_API_OPENGL_CB);
- if (!mpvGL) {
- puts("libmpv does not have the opengl-cb sub-API.");
- exit(1);
- }
- // pass the mpvGL context to our view
- window.glView.mpvGL = mpvGL;
- int r = mpv_opengl_cb_init_gl(mpvGL, NULL, get_proc_address, NULL);
- if (r < 0) {
- puts("gl init has failed.");
- exit(1);
- }
- mpv_opengl_cb_set_update_callback(mpvGL, glupdate, (__bridge void *)window.glView);
-
- // Deal with MPV in the background.
- queue = dispatch_queue_create("mpv", DISPATCH_QUEUE_SERIAL);
- dispatch_async(queue, ^{
- // Register to be woken up whenever mpv generates new events.
- mpv_set_wakeup_callback(mpv, wakeup, (__bridge void *)self);
- // Load the indicated file
- const char *cmd[] = {"loadfile", filename.UTF8String, NULL};
- check_error(mpv_command(mpv, cmd));
- });
-}
-
-static void glupdate(void *ctx)
-{
- MpvClientOGLView *glView = (__bridge MpvClientOGLView *)ctx;
- // I'm still not sure what the best way to handle this is, but this
- // works.
- dispatch_async(dispatch_get_main_queue(), ^{
- [glView drawRect];
- });
-}
-
-- (void) handleEvent:(mpv_event *)event
-{
- switch (event->event_id) {
- case MPV_EVENT_SHUTDOWN: {
- mpv_detach_destroy(mpv);
- mpv_opengl_cb_uninit_gl(window.glView.mpvGL);
- mpv = NULL;
- printf("event: shutdown\n");
- break;
- }
-
- case MPV_EVENT_LOG_MESSAGE: {
- struct mpv_event_log_message *msg = (struct mpv_event_log_message *)event->data;
- printf("[%s] %s: %s", msg->prefix, msg->level, msg->text);
- }
-
- default:
- printf("event: %s\n", mpv_event_name(event->event_id));
- }
-}
-
-- (void)togglePause:(NSButton *)button
-{
- if (mpv) {
- switch (button.state) {
- case NSOffState:
- {
- int pause = 0;
- mpv_set_property(mpv, "pause", MPV_FORMAT_FLAG, &pause);
- }
- break;
- case NSOnState:
- {
- int pause = 1;
- mpv_set_property(mpv, "pause", MPV_FORMAT_FLAG, &pause);
- }
- break;
- default:
- NSLog(@"This should never happen.");
- }
- }
-}
-
-- (void) readEvents
-{
- dispatch_async(queue, ^{
- while (mpv) {
- mpv_event *event = mpv_wait_event(mpv, 0);
- if (event->event_id == MPV_EVENT_NONE)
- break;
- [self handleEvent:event];
- }
- });
-}
-
-static void wakeup(void *context)
-{
- AppDelegate *a = (__bridge AppDelegate *) context;
- [a readEvents];
-}
-
-// quit when the window is closed.
-- (BOOL)applicationShouldTerminateAfterLastWindowClosed:(NSApplication *)app
-{
- return YES;
-}
-
-- (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender
-{
- NSLog(@"Terminating.");
- const char *args[] = {"quit", NULL};
- mpv_command(mpv, args);
- [window.glView clearGLContext];
- return NSTerminateNow;
-}
-
-@end
-
-// Delete this if you already have a main.m.
-int main(int argc, const char * argv[]) {
- @autoreleasepool {
- NSApplication *app = [NSApplication sharedApplication];
- AppDelegate *delegate = [AppDelegate new];
- app.delegate = delegate;
- [app run];
- }
- return 0;
-}
diff --git a/DOCS/client_api_examples/cocoa/cocoabasic.m b/DOCS/client_api_examples/cocoa/cocoabasic.m
deleted file mode 100644
index 5a78250c3a..0000000000
--- a/DOCS/client_api_examples/cocoa/cocoabasic.m
+++ /dev/null
@@ -1,209 +0,0 @@
-// Plays a video from the command line in a view provided by the client
-// application.
-
-// Build with: clang -o cocoabasic cocoabasic.m `pkg-config --libs --cflags mpv` -framework cocoa
-
-#include <mpv/client.h>
-
-#include <stdio.h>
-#include <stdlib.h>
-
-static inline void check_error(int status)
-{
- if (status < 0) {
- printf("mpv API error: %s\n", mpv_error_string(status));
- exit(1);
- }
-}
-
-#import <Cocoa/Cocoa.h>
-
-@interface CocoaWindow : NSWindow
-@end
-
-@implementation CocoaWindow
-- (BOOL)canBecomeMainWindow { return YES; }
-- (BOOL)canBecomeKeyWindow { return YES; }
-@end
-
-@interface AppDelegate : NSObject <NSApplicationDelegate>
-{
- mpv_handle *mpv;
- dispatch_queue_t queue;
- NSWindow *w;
- NSView *wrapper;
-}
-@end
-
-static void wakeup(void *);
-
-@implementation AppDelegate
-
-- (void)createWindow {
-
- int mask = NSTitledWindowMask|NSClosableWindowMask|
- NSMiniaturizableWindowMask|NSResizableWindowMask;
-
- self->w = [[CocoaWindow alloc]
- initWithContentRect:NSMakeRect(0,0, 1280, 720)
- styleMask:mask
- backing:NSBackingStoreBuffered
- defer:NO];
-
- [self->w setTitle:@"cocoabasic example"];
- [self->w makeMainWindow];
- [self->w makeKeyAndOrderFront:nil];
-
- NSRect frame = [[self->w contentView] bounds];
- self->wrapper = [[NSView alloc] initWithFrame:frame];
- [self->wrapper setAutoresizingMask:NSViewWidthSizable|NSViewHeightSizable];
- [[self->w contentView] addSubview:self->wrapper];
- [self->wrapper release];
-
- NSMenu *m = [[NSMenu alloc] initWithTitle:@"AMainMenu"];
- NSMenuItem *item = [m addItemWithTitle:@"Apple" action:nil keyEquivalent:@""];
- NSMenu *sm = [[NSMenu alloc] initWithTitle:@"Apple"];
- [m setSubmenu:sm forItem:item];
- [sm addItemWithTitle: @"mpv_command('stop')" action:@selector(mpv_stop) keyEquivalent:@""];
- [sm addItemWithTitle: @"mpv_command('quit')" action:@selector(mpv_quit) keyEquivalent:@""];
- [sm addItemWithTitle: @"quit" action:@selector(terminate:) keyEquivalent:@"q"];
- [NSApp setMenu:m];
- [NSApp activateIgnoringOtherApps:YES];
-}
-
-- (void) applicationDidFinishLaunching:(NSNotification *)notification {
- [NSApp setActivationPolicy:NSApplicationActivationPolicyRegular];
- atexit_b(^{
- // Because activation policy has just been set to behave like a real
- // application, that policy must be reset on exit to prevent, among
- // other things, the menubar created here from remaining on screen.
- [NSApp setActivationPolicy:NSApplicationActivationPolicyProhibited];
- });
-
- // Read filename
- NSArray *args = [NSProcessInfo processInfo].arguments;
- if (args.count < 2) {
- NSLog(@"Expected filename on command line");
- exit(1);
- }
- NSString *filename = args[1];
-
- [self createWindow];
-
- // Deal with MPV in the background.
- queue = dispatch_queue_create("mpv", DISPATCH_QUEUE_SERIAL);
- dispatch_async(queue, ^{
-
- mpv = mpv_create();
- if (!mpv) {
- printf("failed creating context\n");
- exit(1);
- }
-
- int64_t wid = (intptr_t) self->wrapper;
- check_error(mpv_set_option(mpv, "wid", MPV_FORMAT_INT64, &wid));
-
- // Maybe set some options here, like default key bindings.
- // NOTE: Interaction with the window seems to be broken for now.
- check_error(mpv_set_option_string(mpv, "input-default-bindings", "yes"));
-
- // for testing!
- check_error(mpv_set_option_string(mpv, "input-media-keys", "yes"));
- check_error(mpv_set_option_string(mpv, "input-cursor", "no"));
- check_error(mpv_set_option_string(mpv, "input-vo-keyboard", "yes"));
-
- // request important errors
- check_error(mpv_request_log_messages(mpv, "warn"));
-
- check_error(mpv_initialize(mpv));
-
- // Register to be woken up whenever mpv generates new events.
- mpv_set_wakeup_callback(mpv, wakeup, (__bridge void *) self);
-
- // Load the indicated file
- const char *cmd[] = {"loadfile", filename.UTF8String, NULL};
- check_error(mpv_command(mpv, cmd));
- });
-}
-
-- (void) handleEvent:(mpv_event *)event
-{
- switch (event->event_id) {
- case MPV_EVENT_SHUTDOWN: {
- mpv_detach_destroy(mpv);
- mpv = NULL;
- printf("event: shutdown\n");
- break;
- }
-
- case MPV_EVENT_LOG_MESSAGE: {
- struct mpv_event_log_message *msg = (struct mpv_event_log_message *)event->data;
- printf("[%s] %s: %s", msg->prefix, msg->level, msg->text);
- }
-
- case MPV_EVENT_VIDEO_RECONFIG: {
- dispatch_async(dispatch_get_main_queue(), ^{
- NSArray *subviews = [self->wrapper subviews];
- if ([subviews count] > 0) {
- // mpv's events view
- NSView *eview = [self->wrapper subviews][0];
- [self->w makeFirstResponder:eview];
- }
- });
- }
-
- default:
- printf("event: %s\n", mpv_event_name(event->event_id));
- }
-}
-
-- (void) readEvents
-{
- dispatch_async(queue, ^{
- while (mpv) {
- mpv_event *event = mpv_wait_event(mpv, 0);
- if (event->event_id == MPV_EVENT_NONE)
- break;
- [self handleEvent:event];
- }
- });
-}
-
-static void wakeup(void *context) {
- AppDelegate *a = (__bridge AppDelegate *) context;
- [a readEvents];
-}
-
-// Ostensibly, mpv's window would be hooked up to this.
-- (BOOL) windowShouldClose:(id)sender
-{
- return NO;
-}
-
-- (void) mpv_stop
-{
- if (mpv) {
- const char *args[] = {"stop", NULL};
- mpv_command(mpv, args);
- }
-}
-
-- (void) mpv_quit
-{
- if (mpv) {
- const char *args[] = {"quit", NULL};
- mpv_command(mpv, args);
- }
-}
-@end
-
-// Delete this if you already have a main.m.
-int main(int argc, const char * argv[]) {
- @autoreleasepool {
- NSApplication *app = [NSApplication sharedApplication];
- AppDelegate *delegate = [AppDelegate new];
- app.delegate = delegate;
- [app run];
- }
- return 0;
-}
diff --git a/DOCS/client_api_examples/qml/main.cpp b/DOCS/client_api_examples/qml/main.cpp
deleted file mode 100644
index 2122cd8c5c..0000000000
--- a/DOCS/client_api_examples/qml/main.cpp
+++ /dev/null
@@ -1,136 +0,0 @@
-#include "main.h"
-
-#include <stdexcept>
-#include <clocale>
-
-#include <QObject>
-#include <QtGlobal>
-#include <QOpenGLContext>
-#include <QGuiApplication>
-
-#include <QtGui/QOpenGLFramebufferObject>
-
-#include <QtQuick/QQuickWindow>
-#include <QtQuick/QQuickView>
-
-class MpvRenderer : public QQuickFramebufferObject::Renderer
-{
- static void *get_proc_address(void *ctx, const char *name) {
- (void)ctx;
- QOpenGLContext *glctx = QOpenGLContext::currentContext();
- if (!glctx)
- return NULL;
- return (void *)glctx->getProcAddress(QByteArray(name));
- }
-
- mpv::qt::Handle mpv;
- QQuickWindow *window;
- mpv_opengl_cb_context *mpv_gl;
-public:
- MpvRenderer(const MpvObject *obj)
- : mpv(obj->mpv), window(obj->window()), mpv_gl(obj->mpv_gl)
- {
- int r = mpv_opengl_cb_init_gl(mpv_gl, NULL, get_proc_address, NULL);
- if (r < 0)
- throw std::runtime_error("could not initialize OpenGL");
- }
-
- virtual ~MpvRenderer()
- {
- // Until this call is done, we need to make sure the player remains
- // alive. This is done implicitly with the mpv::qt::Handle instance
- // in this class.
- mpv_opengl_cb_uninit_gl(mpv_gl);
- }
-
- void render()
- {
- QOpenGLFramebufferObject *fbo = framebufferObject();
- window->resetOpenGLState();
- mpv_opengl_cb_draw(mpv_gl, fbo->handle(), fbo->width(), fbo->height());
- window->resetOpenGLState();
- }
-};
-
-MpvObject::MpvObject(QQuickItem * parent)
- : QQuickFramebufferObject(parent), mpv_gl(0)
-{
- mpv = mpv::qt::Handle::FromRawHandle(mpv_create());
- if (!mpv)
- throw std::runtime_error("could not create mpv context");
-
- mpv_set_option_string(mpv, "terminal", "yes");
- mpv_set_option_string(mpv, "msg-level", "all=v");
-
- if (mpv_initialize(mpv) < 0)
- throw std::runtime_error("could not initialize mpv context");
-
- // Make use of the MPV_SUB_API_OPENGL_CB API.
- mpv::qt::set_option_variant(mpv, "vo", "opengl-cb");
-
- // Request hw decoding, just for testing.
- mpv::qt::set_option_variant(mpv, "hwdec", "auto");
-
- // Setup the callback that will make QtQuick update and redraw if there
- // is a new video frame. Use a queued connection: this makes sure the
- // doUpdate() function is run on the GUI thread.
- mpv_gl = (mpv_opengl_cb_context *)mpv_get_sub_api(mpv, MPV_SUB_API_OPENGL_CB);
- if (!mpv_gl)
- throw std::runtime_error("OpenGL not compiled in");
- mpv_opengl_cb_set_update_callback(mpv_gl, MpvObject::on_update, (void *)this);
- connect(this, &MpvObject::onUpdate, this, &MpvObject::doUpdate,
- Qt::QueuedConnection);
-}
-
-MpvObject::~MpvObject()
-{
- if (mpv_gl)
- mpv_opengl_cb_set_update_callback(mpv_gl, NULL, NULL);
-}
-
-void MpvObject::on_update(void *ctx)
-{
- MpvObject *self = (MpvObject *)ctx;
- emit self->onUpdate();
-}
-
-// connected to onUpdate(); signal makes sure it runs on the GUI thread
-void MpvObject::doUpdate()
-{
- update();
-}
-
-void MpvObject::command(const QVariant& params)
-{
- mpv::qt::command_variant(mpv, params);
-}
-
-void MpvObject::setProperty(const QString& name, const QVariant& value)
-{
- mpv::qt::set_property_variant(mpv, name, value);
-}
-
-QQuickFramebufferObject::Renderer *MpvObject::createRenderer() const
-{
- window()->setPersistentOpenGLContext(true);
- window()->setPersistentSceneGraph(true);
- return new MpvRenderer(this);
-}
-
-int main(int argc, char **argv)
-{
- QGuiApplication app(argc, argv);
-
- // Qt sets the locale in the QGuiApplication constructor, but libmpv
- // requires the LC_NUMERIC category to be set to "C", so change it back.
- std::setlocale(LC_NUMERIC, "C");
-
- qmlRegisterType<MpvObject>("mpvtest", 1, 0, "MpvObject");
-
- QQuickView view;
- view.setResizeMode(QQuickView::SizeRootObjectToView);
- view.setSource(QUrl("qrc:///mpvtest/main.qml"));
- view.show();
-
- return app.exec();
-}
diff --git a/DOCS/client_api_examples/qml/main.h b/DOCS/client_api_examples/qml/main.h
deleted file mode 100644
index 9a65ae5350..0000000000
--- a/DOCS/client_api_examples/qml/main.h
+++ /dev/null
@@ -1,36 +0,0 @@
-#ifndef MPVRENDERER_H_
-#define MPVRENDERER_H_
-
-#include <QtQuick/QQuickFramebufferObject>
-
-#include <mpv/client.h>
-#include <mpv/opengl_cb.h>
-#include <mpv/qthelper.hpp>
-
-class MpvRenderer;
-
-class MpvObject : public QQuickFramebufferObject
-{
- Q_OBJECT
-
- mpv::qt::Handle mpv;
- mpv_opengl_cb_context *mpv_gl;
-
- friend class MpvRenderer;
-
-public:
- MpvObject(QQuickItem * parent = 0);
- virtual ~MpvObject();
- virtual Renderer *createRenderer() const;
-public slots:
- void command(const QVariant& params);
- void setProperty(const QString& name, const QVariant& value);
-signals:
- void onUpdate();
-private slots:
- void doUpdate();
-private:
- static void on_update(void *ctx);
-};
-
-#endif
diff --git a/DOCS/client_api_examples/qml/main.qml b/DOCS/client_api_examples/qml/main.qml
deleted file mode 100644
index ec06790e86..0000000000
--- a/DOCS/client_api_examples/qml/main.qml
+++ /dev/null
@@ -1,71 +0,0 @@
-import QtQuick 2.0
-import QtQuick.Controls 1.0
-
-import mpvtest 1.0
-
-Item {
- width: 1280
- height: 720
-
- MpvObject {
- id: renderer
- anchors.fill: parent
-
- MouseArea {
- anchors.fill: parent
- onClicked: renderer.command(["loadfile", "../../../test.mkv"])
- }
- }
-
- Rectangle {
- id: labelFrame
- anchors.margins: -50
- radius: 5
- color: "white"
- border.color: "black"
- opacity: 0.8
- anchors.fill: box
- }
-
- Row {
- id: box
- anchors.bottom: renderer.bottom
- anchors.left: renderer.left
- anchors.right: renderer.right
- anchors.margins: 100
-
- Text {
- anchors.margins: 10
- wrapMode: Text.WordWrap
- text: "QtQuick and mpv are both rendering stuff.\n
- Click to load ../../../test.mkv"
- }
-
- // Don't take these controls too seriously. They're for testing.
- Column {
- CheckBox {
- id: checkbox
- anchors.margins: 10
- // Heavily filtered means good, right?
- text: "Make video look like on a Smart TV"
- onClicked: {
- if (checkbox.checked) {
- renderer.command(["vo_cmdline", "sharpen=5.0"])
- } else {
- renderer.command(["vo_cmdline", ""])
- }
- }
- }
- Slider {
- id: slider
- anchors.margins: 10
- anchors.left: checkbox.left
- anchors.right: checkbox.right
- minimumValue: -100
- maximumValue: 100
- value: 0
- onValueChanged: renderer.setProperty("gamma", slider.value | 0)
- }
- }
- }
-}
diff --git a/DOCS/client_api_examples/qml/mpvtest.pro b/DOCS/client_api_examples/qml/mpvtest.pro
deleted file mode 100644
index 0b2e96fe99..0000000000
--- a/DOCS/client_api_examples/qml/mpvtest.pro
+++ /dev/null
@@ -1,12 +0,0 @@
-QT += qml quick
-
-HEADERS += main.h
-SOURCES += main.cpp
-
-QT_CONFIG -= no-pkg-config
-CONFIG += link_pkgconfig debug
-PKGCONFIG += mpv
-
-RESOURCES += mpvtest.qrc
-
-OTHER_FILES += main.qml
diff --git a/DOCS/client_api_examples/qml/mpvtest.qrc b/DOCS/client_api_examples/qml/mpvtest.qrc
deleted file mode 100644
index bb672657e5..0000000000
--- a/DOCS/client_api_examples/qml/mpvtest.qrc
+++ /dev/null
@@ -1,5 +0,0 @@
-<RCC>
- <qresource prefix="/mpvtest">
- <file>main.qml</file>
- </qresource>
-</RCC>
diff --git a/DOCS/client_api_examples/qml_direct/main.cpp b/DOCS/client_api_examples/qml_direct/main.cpp
deleted file mode 100644
index 37c6119707..0000000000
--- a/DOCS/client_api_examples/qml_direct/main.cpp
+++ /dev/null
@@ -1,159 +0,0 @@
-#include "main.h"
-
-#include <stdexcept>
-#include <clocale>
-
-#include <QObject>
-#include <QtGlobal>
-#include <QOpenGLContext>
-
-#include <QGuiApplication>
-#include <QtQuick/QQuickWindow>
-#include <QtQuick/QQuickView>
-
-static void *get_proc_address(void *ctx, const char *name) {
- (void)ctx;
- QOpenGLContext *glctx = QOpenGLContext::currentContext();
- if (!glctx)
- return NULL;
- return (void *)glctx->getProcAddress(QByteArray(name));
-}
-
-MpvRenderer::MpvRenderer(mpv::qt::Handle a_mpv, mpv_opengl_cb_context *a_mpv_gl)
- : mpv(a_mpv), mpv_gl(a_mpv_gl), window(0), size()
-{
- int r = mpv_opengl_cb_init_gl(mpv_gl, NULL, get_proc_address, NULL);
- if (r < 0)
- throw std::runtime_error("could not initialize OpenGL");
-}
-
-MpvRenderer::~MpvRenderer()
-{
- // Until this call is done, we need to make sure the player remains
- // alive. This is done implicitly with the mpv::qt::Handle instance
- // in this class.
- mpv_opengl_cb_uninit_gl(mpv_gl);
-}
-
-void MpvRenderer::paint()
-{
- window->resetOpenGLState();
-
- // This uses 0 as framebuffer, which indicates that mpv will render directly
- // to the frontbuffer. Note that mpv will always switch framebuffers
- // explicitly. Some QWindow setups (such as using QQuickWidget) actually
- // want you to render into a FBO in the beforeRendering() signal, and this
- // code won't work there.
- // The negation is used for rendering with OpenGL's flipped coordinates.
- mpv_opengl_cb_draw(mpv_gl, 0, size.width(), -size.height());
-
- window->resetOpenGLState();
-}
-
-MpvObject::MpvObject(QQuickItem * parent)
- : QQuickItem(parent), mpv_gl(0), renderer(0)
-{
- mpv = mpv::qt::Handle::FromRawHandle(mpv_create());
- if (!mpv)
- throw std::runtime_error("could not create mpv context");
-
- mpv_set_option_string(mpv, "terminal", "yes");
- mpv_set_option_string(mpv, "msg-level", "all=v");
-
- if (mpv_initialize(mpv) < 0)
- throw std::runtime_error("could not initialize mpv context");
-
- // Make use of the MPV_SUB_API_OPENGL_CB API.
- mpv::qt::set_option_variant(mpv, "vo", "opengl-cb");
-
- // Setup the callback that will make QtQuick update and redraw if there
- // is a new video frame. Use a queued connection: this makes sure the
- // doUpdate() function is run on the GUI thread.
- mpv_gl = (mpv_opengl_cb_context *)mpv_get_sub_api(mpv, MPV_SUB_API_OPENGL_CB);
- if (!mpv_gl)
- throw std::runtime_error("OpenGL not compiled in");
- mpv_opengl_cb_set_update_callback(mpv_gl, MpvObject::on_update, (void *)this);
- connect(this, &MpvObject::onUpdate, this, &MpvObject::doUpdate,
- Qt::QueuedConnection);
-
- connect(this, &QQuickItem::windowChanged,
- this, &MpvObject::handleWindowChanged);
-}
-
-MpvObject::~MpvObject()
-{
- if (mpv_gl)
- mpv_opengl_cb_set_update_callback(mpv_gl, NULL, NULL);
-}
-
-void MpvObject::handleWindowChanged(QQuickWindow *win)
-{
- if (!win)
- return;
- connect(win, &QQuickWindow::beforeSynchronizing,
- this, &MpvObject::sync, Qt::DirectConnection);
- connect(win, &QQuickWindow::sceneGraphInvalidated,
- this, &MpvObject::cleanup, Qt::DirectConnection);
- connect(win, &QQuickWindow::frameSwapped,
- this, &MpvObject::swapped, Qt::DirectConnection);
- win->setClearBeforeRendering(false);
-}
-
-void MpvObject::sync()
-{
- if (!renderer) {
- renderer = new MpvRenderer(mpv, mpv_gl);
- connect(window(), &QQuickWindow::beforeRendering,
- renderer, &MpvRenderer::paint, Qt::DirectConnection);
- }
- renderer->window = window();
- renderer->size = window()->size() * window()->devicePixelRatio();
-}
-
-void MpvObject::swapped()
-{
- mpv_opengl_cb_report_flip(mpv_gl, 0);
-}
-
-void MpvObject::cleanup()
-{
- if (renderer) {
- delete renderer;
- renderer = 0;
- }
-}
-
-void MpvObject::on_update(void *ctx)
-{
- MpvObject *self = (MpvObject *)ctx;
- emit self->onUpdate();
-}
-
-// connected to onUpdate(); signal makes sure it runs on the GUI thread
-void MpvObject::doUpdate()
-{
- window()->update();
-}
-
-void MpvObject::command(const QVariant& params)
-{
- mpv::qt::command_variant(mpv, params);
-}
-
-int main(int argc, char **argv)
-{
- QGuiApplication app(argc, argv);
-
- // Qt sets the locale in the QGuiApplication constructor, but libmpv
- // requires the LC_NUMERIC category to be set to "C", so change it back.
- std::setlocale(LC_NUMERIC, "C");
-
- qmlRegisterType<MpvObject>("mpvtest", 1, 0, "MpvObject");
-
- QQuickView view;
- view.setResizeMode(QQuickView::SizeRootObjectToView);
- view.setSource(QUrl("qrc:///mpvtest/main.qml"));
- view.show();
-
- return app.exec();
-}
diff --git a/DOCS/client_api_examples/qml_direct/main.h b/DOCS/client_api_examples/qml_direct/main.h
deleted file mode 100644
index b0310ff0be..0000000000
--- a/DOCS/client_api_examples/qml_direct/main.h
+++ /dev/null
@@ -1,51 +0,0 @@
-#ifndef MPVRENDERER_H_
-#define MPVRENDERER_H_
-
-#include <QtQuick/QQuickItem>
-
-#include <mpv/client.h>
-#include <mpv/opengl_cb.h>
-#include <mpv/qthelper.hpp>
-
-class MpvRenderer : public QObject
-{
- Q_OBJECT
- mpv::qt::Handle mpv;
- mpv_opengl_cb_context *mpv_gl;
- QQuickWindow *window;
- QSize size;
-
- friend class MpvObject;
-public:
- MpvRenderer(mpv::qt::Handle a_mpv, mpv_opengl_cb_context *a_mpv_gl);
- virtual ~MpvRenderer();
-public slots:
- void paint();
-};
-
-class MpvObject : public QQuickItem
-{
- Q_OBJECT
-
- mpv::qt::Handle mpv;
- mpv_opengl_cb_context *mpv_gl;
- MpvRenderer *renderer;
-
-public:
- MpvObject(QQuickItem * parent = 0);
- virtual ~MpvObject();
-public slots:
- void command(const QVariant& params);
- void sync();
- void swapped();
- void cleanup();
-signals:
- void onUpdate();
-private slots:
- void doUpdate();
- void handleWindowChanged(QQuickWindow *win);
-private:
- static void on_update(void *ctx);
-};
-
-#endif
diff --git a/DOCS/client_api_examples/qml_direct/main.qml b/DOCS/client_api_examples/qml_direct/main.qml
deleted file mode 100644
index 92be9bc405..0000000000
--- a/DOCS/client_api_examples/qml_direct/main.qml
+++ /dev/null
@@ -1,49 +0,0 @@
-import QtQuick 2.0
-import QtQuick.Controls 1.0
-
-import mpvtest 1.0
-
-Item {
- width: 1280
- height: 720
-
- MpvObject {
- id: renderer
-
- // This object isn't real and not visible; it just renders into the
- // background of the containing Window.
- width: 0
- height: 0
- }
-
- MouseArea {
- anchors.fill: parent
- onClicked: renderer.command(["loadfile", "../../../test.mkv"])
- }
-
- Rectangle {
- id: labelFrame
- anchors.margins: -50
- radius: 5
- color: "white"
- border.color: "black"
- opacity: 0.8
- anchors.fill: box
- }
-
- Row {
- id: box
- anchors.bottom: parent.bottom
- anchors.left: parent.left
- anchors.right: parent.right
- anchors.margins: 100
-
- Text {
- anchors.margins: 10
- wrapMode: Text.WordWrap
- text: "QtQuick and mpv are both rendering stuff.\n
- In this example, mpv is always in the background.\n
- Click to load ../../../test.mkv"
- }
- }
-}
diff --git a/DOCS/client_api_examples/qml_direct/mpvtest.pro b/DOCS/client_api_examples/qml_direct/mpvtest.pro
deleted file mode 100644
index 0b2e96fe99..0000000000
--- a/DOCS/client_api_examples/qml_direct/mpvtest.pro
+++ /dev/null
@@ -1,12 +0,0 @@
-QT += qml quick
-
-HEADERS += main.h
-SOURCES += main.cpp
-
-QT_CONFIG -= no-pkg-config
-CONFIG += link_pkgconfig debug
-PKGCONFIG += mpv
-
-RESOURCES += mpvtest.qrc
-
-OTHER_FILES += main.qml
diff --git a/DOCS/client_api_examples/qml_direct/mpvtest.qrc b/DOCS/client_api_examples/qml_direct/mpvtest.qrc
deleted file mode 100644
index bb672657e5..0000000000
--- a/DOCS/client_api_examples/qml_direct/mpvtest.qrc
+++ /dev/null
@@ -1,5 +0,0 @@
-<RCC>
- <qresource prefix="/mpvtest">
- <file>main.qml</file>
- </qresource>
-</RCC>
diff --git a/DOCS/client_api_examples/qt/qtexample.cpp b/DOCS/client_api_examples/qt/qtexample.cpp
deleted file mode 100644
index 5f4e86e891..0000000000
--- a/DOCS/client_api_examples/qt/qtexample.cpp
+++ /dev/null
@@ -1,225 +0,0 @@
-// This example can be built with: qmake && make
-
-#include <clocale>
-#include <sstream>
-#include <stdexcept>
-
-#include <QtGlobal>
-#include <QFileDialog>
-#include <QStatusBar>
-#include <QMenuBar>
-#include <QMenu>
-#include <QGridLayout>
-#include <QApplication>
-#include <QTextEdit>
-
-#if QT_VERSION >= 0x050000
-#include <QJsonDocument>
-#endif
-
-#include <mpv/qthelper.hpp>
-
-#include "qtexample.h"
-
-static void wakeup(void *ctx)
-{
- // This callback is invoked from any mpv thread (but possibly also
- // recursively from a thread that is calling the mpv API). Just notify
- // the Qt GUI thread to wake up (so that it can process events with
- // mpv_wait_event()), and return as quickly as possible.
- MainWindow *mainwindow = (MainWindow *)ctx;
- emit mainwindow->mpv_events();
-}
-
-MainWindow::MainWindow(QWidget *parent) :
- QMainWindow(parent)
-{
- setWindowTitle("Qt embedding demo");
- setMinimumSize(640, 480);
-
- QMenu *menu = menuBar()->addMenu(tr("&File"));
- QAction *on_open = new QAction(tr("&Open"), this);
- on_open->setShortcuts(QKeySequence::Open);
- on_open->setStatusTip(tr("Open a file"));
- connect(on_open, &QAction::triggered, this, &MainWindow::on_file_open);
- menu->addAction(on_open);
-
- QAction *on_new = new QAction(tr("&New window"), this);
- connect(on_new, &QAction::triggered, this, &MainWindow::on_new_window);
- menu->addAction(on_new);
-
- statusBar();
-
- QMainWindow *log_window = new QMainWindow(this);
- log = new QTextEdit(log_window);
- log->setReadOnly(true);
- log_window->setCentralWidget(log);
- log_window->setWindowTitle("mpv log window");
- log_window->setMinimumSize(500, 50);
- log_window->show();
-
- mpv = mpv_create();
- if (!mpv)
- throw std::runtime_error("can't create mpv instance");
-
- // Create a video child window. Force Qt to create a native window, and
- // pass the window ID to the mpv wid option. Works on: X11, win32, Cocoa
- mpv_container = new QWidget(this);
- setCentralWidget(mpv_container);
- mpv_container->setAttribute(Qt::WA_DontCreateNativeAncestors);
- mpv_container->setAttribute(Qt::WA_NativeWindow);
- // If you have a HWND, use: int64_t wid = (intptr_t)hwnd;
- int64_t wid = mpv_container->winId();
- mpv_set_option(mpv, "wid", MPV_FORMAT_INT64, &wid);
-
- // Enable default bindings, because we're lazy. Normally, a player using
- // mpv as backend would implement its own key bindings.
- mpv_set_option_string(mpv, "input-default-bindings", "yes");
-
- // Enable keyboard input on the X11 window. For the messy details, see
- // --input-vo-keyboard on the manpage.
- mpv_set_option_string(mpv, "input-vo-keyboard", "yes");
-
- // Let us receive property change events with MPV_EVENT_PROPERTY_CHANGE if
- // this property changes.
- mpv_observe_property(mpv, 0, "time-pos", MPV_FORMAT_DOUBLE);
-
- mpv_observe_property(mpv, 0, "track-list", MPV_FORMAT_NODE);
- mpv_observe_property(mpv, 0, "chapter-list", MPV_FORMAT_NODE);
-
- // Request log messages with level "info" or higher.
- // They are received as MPV_EVENT_LOG_MESSAGE.
- mpv_request_log_messages(mpv, "info");
-
- // From this point on, the wakeup function will be called. The callback
- // can come from any thread, so we use the QueuedConnection mechanism to
- // relay the wakeup in a thread-safe way.
- connect(this, &MainWindow::mpv_events, this, &MainWindow::on_mpv_events,
- Qt::QueuedConnection);
- mpv_set_wakeup_callback(mpv, wakeup, this);
-
- if (mpv_initialize(mpv) < 0)
- throw std::runtime_error("mpv failed to initialize");
-}
-
-void MainWindow::handle_mpv_event(mpv_event *event)
-{
- switch (event->event_id) {
- case MPV_EVENT_PROPERTY_CHANGE: {
- mpv_event_property *prop = (mpv_event_property *)event->data;
- if (strcmp(prop->name, "time-pos") == 0) {
- if (prop->format == MPV_FORMAT_DOUBLE) {
- double time = *(double *)prop->data;
- std::stringstream ss;
- ss << "At: " << time;
- statusBar()->showMessage(QString::fromStdString(ss.str()));
- } else if (prop->format == MPV_FORMAT_NONE) {
- // The property is unavailable, which probably means playback
- // was stopped.
- statusBar()->showMessage("");
- }
- } else if (strcmp(prop->name, "chapter-list") == 0 ||
- strcmp(prop->name, "track-list") == 0)
- {
- // Dump the properties as JSON for demo purposes.
-#if QT_VERSION >= 0x050000
- if (prop->format == MPV_FORMAT_NODE) {
- QVariant v = mpv::qt::node_to_variant((mpv_node *)prop->data);
- // Abuse JSON support for easily printing the mpv_node contents.
- QJsonDocument d = QJsonDocument::fromVariant(v);
- append_log("Change property " + QString(prop->name) + ":\n");
- append_log(d.toJson().data());
- }
-#endif
- }
- break;
- }
- case MPV_EVENT_VIDEO_RECONFIG: {
- // Retrieve the new video size.
- int64_t w, h;
- if (mpv_get_property(mpv, "dwidth", MPV_FORMAT_INT64, &w) >= 0 &&
- mpv_get_property(mpv, "dheight", MPV_FORMAT_INT64, &h) >= 0 &&
- w > 0 && h > 0)
- {
- // Note that the MPV_EVENT_VIDEO_RECONFIG event doesn't necessarily
- // imply a resize, and you should check yourself if the video
- // dimensions really changed.
- // mpv itself will scale/letter box the video to the container size
- // if the video doesn't fit.
- std::stringstream ss;
- ss << "Reconfig: " << w << " " << h;
- statusBar()->showMessage(QString::fromStdString(ss.str()));
- }
- break;
- }
- case MPV_EVENT_LOG_MESSAGE: {
- struct mpv_event_log_message *msg = (struct mpv_event_log_message *)event->data;
- std::stringstream ss;
- ss << "[" << msg->prefix << "] " << msg->level << ": " << msg->text;
- append_log(QString::fromStdString(ss.str()));
- break;
- }
- case MPV_EVENT_SHUTDOWN: {
- mpv_terminate_destroy(mpv);
- mpv = NULL;
- break;
- }
- default: ;
- // Ignore uninteresting or unknown events.
- }
-}
-
-// This slot is invoked by wakeup() (through the mpv_events signal).
-void MainWindow::on_mpv_events()
-{
- // Process all events, until the event queue is empty.
- while (mpv) {
- mpv_event *event = mpv_wait_event(mpv, 0);
- if (event->event_id == MPV_EVENT_NONE)
- break;
- handle_mpv_event(event);
- }
-}
-
-void MainWindow::on_file_open()
-{
- QString filename = QFileDialog::getOpenFileName(this, "Open file");
- if (mpv) {
- const QByteArray c_filename = filename.toUtf8();
- const char *args[] = {"loadfile", c_filename.data(), NULL};
- mpv_command_async(mpv, 0, args);
- }
-}
-
-void MainWindow::on_new_window()
-{
- (new MainWindow())->show();
-}
-
-void MainWindow::append_log(const QString &text)
-{
- QTextCursor cursor = log->textCursor();
- cursor.movePosition(QTextCursor::End);
- cursor.insertText(text);
- log->setTextCursor(cursor);
-}
-
-MainWindow::~MainWindow()
-{
- if (mpv)
- mpv_terminate_destroy(mpv);
-}
-
-int main(int argc, char *argv[])
-{
- QApplication a(argc, argv);
-
- // Qt sets the locale in the QApplication constructor, but libmpv requires
- // the LC_NUMERIC category to be set to "C", so change it back.
- std::setlocale(LC_NUMERIC, "C");
-
- MainWindow w;
- w.show();
-
- return a.exec();
-}
diff --git a/DOCS/client_api_examples/qt/qtexample.h b/DOCS/client_api_examples/qt/qtexample.h
deleted file mode 100644
index c3891cf4a7..0000000000
--- a/DOCS/client_api_examples/qt/qtexample.h
+++ /dev/null
@@ -1,37 +0,0 @@
-#ifndef QTEXAMPLE_H
-#define QTEXAMPLE_H
-
-#include <QMainWindow>
-
-#include <mpv/client.h>
-
-class QTextEdit;
-
-class MainWindow : public QMainWindow
-{
- Q_OBJECT
-
-public:
- explicit MainWindow(QWidget *parent = 0);
- ~MainWindow();
-
-private slots:
- void on_file_open();
- void on_new_window();
- void on_mpv_events();
-
-signals:
- void mpv_events();
-
-private:
- QWidget *mpv_container;
- mpv_handle *mpv;
- QTextEdit *log;
-
- void append_log(const QString &text);
-
- void create_player();
- void handle_mpv_event(mpv_event *event);
-};
-
-#endif // QTEXAMPLE_H
diff --git a/DOCS/client_api_examples/qt/qtexample.pro b/DOCS/client_api_examples/qt/qtexample.pro
deleted file mode 100644
index 7c0a6ade02..0000000000
--- a/DOCS/client_api_examples/qt/qtexample.pro
+++ /dev/null
@@ -1,13 +0,0 @@
-QT += core gui
-
-greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
-
-TARGET = qtexample
-TEMPLATE = app
-
-QT_CONFIG -= no-pkg-config
-CONFIG += link_pkgconfig debug
-PKGCONFIG += mpv
-
-SOURCES += qtexample.cpp
-HEADERS += qtexample.h
diff --git a/DOCS/client_api_examples/qt_opengl/main.cpp b/DOCS/client_api_examples/qt_opengl/main.cpp
deleted file mode 100644
index 086a4b4617..0000000000
--- a/DOCS/client_api_examples/qt_opengl/main.cpp
+++ /dev/null
@@ -1,13 +0,0 @@
-#include <QApplication>
-#include "mainwindow.h"
-
-int main(int argc, char *argv[])
-{
- QApplication a(argc, argv);
- // Qt sets the locale in the QApplication constructor, but libmpv requires
- // the LC_NUMERIC category to be set to "C", so change it back.
- setlocale(LC_NUMERIC, "C");
- MainWindow w;
- w.show();
- return a.exec();
-}
diff --git a/DOCS/client_api_examples/qt_opengl/mainwindow.cpp b/DOCS/client_api_examples/qt_opengl/mainwindow.cpp
deleted file mode 100644
index 3ecd0a196d..0000000000
--- a/DOCS/client_api_examples/qt_opengl/mainwindow.cpp
+++ /dev/null
@@ -1,52 +0,0 @@
-#include "mainwindow.h"
-#include "mpvwidget.h"
-#include <QPushButton>
-#include <QSlider>
-#include <QLayout>
-#include <QFileDialog>
-
-MainWindow::MainWindow(QWidget *parent) : QWidget(parent)
-{
- m_mpv = new MpvWidget(this);
- m_slider = new QSlider();
- m_slider->setOrientation(Qt::Horizontal);
- m_openBtn = new QPushButton("Open");
- m_playBtn = new QPushButton("Pause");
- QHBoxLayout *hb = new QHBoxLayout();
- hb->addWidget(m_openBtn);
- hb->addWidget(m_playBtn);
- QVBoxLayout *vl = new QVBoxLayout();
- vl->addWidget(m_mpv);
- vl->addWidget(m_slider);
- vl->addLayout(hb);
- setLayout(vl);
- connect(m_slider, SIGNAL(sliderMoved(int)), SLOT(seek(int)));
- connect(m_openBtn, SIGNAL(clicked()), SLOT(openMedia()));
- connect(m_playBtn, SIGNAL(clicked()), SLOT(pauseResume()));
- connect(m_mpv, SIGNAL(positionChanged(int)), m_slider, SLOT(setValue(int)));
- connect(m_mpv, SIGNAL(durationChanged(int)), this, SLOT(setSliderRange(int)));
-}
-
-void MainWindow::openMedia()
-{
- QString file = QFileDialog::getOpenFileName(0, "Open a video");
- if (file.isEmpty())
- return;
- m_mpv->command(QStringList() << "loadfile" << file);
-}
-
-void MainWindow::seek(int pos)
-{
- m_mpv->command(QVariantList() << "seek" << pos << "absolute");
-}
-
-void MainWindow::pauseResume()
-{
- const bool paused = m_mpv->getProperty("pause").toBool();
- m_mpv->setProperty("pause", !paused);
-}
-
-void MainWindow::setSliderRange(int duration)
-{
- m_slider->setRange(0, duration);
-}
diff --git a/DOCS/client_api_examples/qt_opengl/mainwindow.h b/DOCS/client_api_examples/qt_opengl/mainwindow.h
deleted file mode 100644
index 523b385bb4..0000000000
--- a/DOCS/client_api_examples/qt_opengl/mainwindow.h
+++ /dev/null
@@ -1,27 +0,0 @@
-#ifndef MainWindow_H
-#define MainWindow_H
-
-#include <QtWidgets/QWidget>
-
-class MpvWidget;
-class QSlider;
-class QPushButton;
-class MainWindow : public QWidget
-{
- Q_OBJECT
-public:
- explicit MainWindow(QWidget *parent = 0);
-public Q_SLOTS:
- void openMedia();
- void seek(int pos);
- void pauseResume();
-private Q_SLOTS:
- void setSliderRange(int duration);
-private:
- MpvWidget *m_mpv;
- QSlider *m_slider;
- QPushButton *m_openBtn;
- QPushButton *m_playBtn;
-};
-
-#endif // MainWindow_H
diff --git a/DOCS/client_api_examples/qt_opengl/mpvwidget.cpp b/DOCS/client_api_examples/qt_opengl/mpvwidget.cpp
deleted file mode 100644
index 4d2cad6241..0000000000
--- a/DOCS/client_api_examples/qt_opengl/mpvwidget.cpp
+++ /dev/null
@@ -1,129 +0,0 @@
-#include "mpvwidget.h"
-#include <stdexcept>
-#include <QtGui/QOpenGLContext>
-#include <QtCore/QMetaObject>
-
-static void wakeup(void *ctx)
-{
- QMetaObject::invokeMethod((MpvWidget*)ctx, "on_mpv_events", Qt::QueuedConnection);
-}
-
-static void *get_proc_address(void *ctx, const char *name) {
- Q_UNUSED(ctx);
- QOpenGLContext *glctx = QOpenGLContext::currentContext();
- if (!glctx)
- return NULL;
- return (void *)glctx->getProcAddress(QByteArray(name));
-}
-
-MpvWidget::MpvWidget(QWidget *parent, Qt::WindowFlags f)
- : QOpenGLWidget(parent, f)
-{
- mpv = mpv::qt::Handle::FromRawHandle(mpv_create());
- if (!mpv)
- throw std::runtime_error("could not create mpv context");
-
- mpv_set_option_string(mpv, "terminal", "yes");
- mpv_set_option_string(mpv, "msg-level", "all=v");
- if (mpv_initialize(mpv) < 0)
- throw std::runtime_error("could not initialize mpv context");
-
- // Make use of the MPV_SUB_API_OPENGL_CB API.
- mpv::qt::set_option_variant(mpv, "vo", "opengl-cb");
-
- // Request hw decoding, just for testing.
- mpv::qt::set_option_variant(mpv, "hwdec", "auto");
-
- mpv_gl = (mpv_opengl_cb_context *)mpv_get_sub_api(mpv, MPV_SUB_API_OPENGL_CB);
- if (!mpv_gl)
- throw std::runtime_error("OpenGL not compiled in");
- mpv_opengl_cb_set_update_callback(mpv_gl, MpvWidget::on_update, (void *)this);
- connect(this, SIGNAL(frameSwapped()), SLOT(swapped()));
-
- mpv_observe_property(mpv, 0, "duration", MPV_FORMAT_DOUBLE);
- mpv_observe_property(mpv, 0, "time-pos", MPV_FORMAT_DOUBLE);
- mpv_set_wakeup_callback(mpv, wakeup, this);
-}
-
-MpvWidget::~MpvWidget()
-{
- makeCurrent();
- if (mpv_gl)
- mpv_opengl_cb_set_update_callback(mpv_gl, NULL, NULL);
- // Until this call is done, we need to make sure the player remains
- // alive. This is done implicitly with the mpv::qt::Handle instance
- // in this class.
- mpv_opengl_cb_uninit_gl(mpv_gl);
-}
-
-void MpvWidget::command(const QVariant& params)
-{
- mpv::qt::command_variant(mpv, params);
-}
-
-void MpvWidget::setProperty(const QString& name, const QVariant& value)
-{
- mpv::qt::set_property_variant(mpv, name, value);
-}
-
-QVariant MpvWidget::getProperty(const QString &name) const
-{
- return mpv::qt::get_property_variant(mpv, name);
-}
-
-void MpvWidget::initializeGL()
-{
- int r = mpv_opengl_cb_init_gl(mpv_gl, NULL, get_proc_address, NULL);
- if (r < 0)
- throw std::runtime_error("could not initialize OpenGL");
-}
-
-void MpvWidget::paintGL()
-{
- mpv_opengl_cb_draw(mpv_gl, defaultFramebufferObject(), width(), -height());
-}
-
-void MpvWidget::swapped()
-{
- mpv_opengl_cb_report_flip(mpv_gl, 0);
-}
-
-void MpvWidget::on_mpv_events()
-{
- // Process all events, until the event queue is empty.
- while (mpv) {
- mpv_event *event = mpv_wait_event(mpv, 0);
- if (event->event_id == MPV_EVENT_NONE) {
- break;
- }
- handle_mpv_event(event);
- }
-}
-
-void MpvWidget::handle_mpv_event(mpv_event *event)
-{
- switch (event->event_id) {
- case MPV_EVENT_PROPERTY_CHANGE: {
- mpv_event_property *prop = (mpv_event_property *)event->data;
- if (strcmp(prop->name, "time-pos") == 0) {
- if (prop->format == MPV_FORMAT_DOUBLE) {
- double time = *(double *)prop->data;
- Q_EMIT positionChanged(time);
- }
- } else if (strcmp(prop->name, "duration") == 0) {
- if (prop->format == MPV_FORMAT_DOUBLE) {
- double time = *(double *)prop->data;
- Q_EMIT durationChanged(time);
- }
- }
- break;
- }
- default: ;
- // Ignore uninteresting or unknown events.
- }
-}
-
-void MpvWidget::on_update(void *ctx)
-{
- QMetaObject::invokeMethod((MpvWidget*)ctx, "update");
-}
diff --git a/DOCS/client_api_examples/qt_opengl/mpvwidget.h b/DOCS/client_api_examples/qt_opengl/mpvwidget.h
deleted file mode 100644
index a219681393..0000000000
--- a/DOCS/client_api_examples/qt_opengl/mpvwidget.h
+++ /dev/null
@@ -1,38 +0,0 @@
-#ifndef PLAYERWINDOW_H
-#define PLAYERWINDOW_H
-
-#include <QtWidgets/QOpenGLWidget>
-#include <mpv/client.h>
-#include <mpv/opengl_cb.h>
-#include <mpv/qthelper.hpp>
-
-class MpvWidget Q_DECL_FINAL: public QOpenGLWidget
-{
- Q_OBJECT
-public:
- MpvWidget(QWidget *parent = 0, Qt::WindowFlags f = 0);
- ~MpvWidget();
- void command(const QVariant& params);
- void setProperty(const QString& name, const QVariant& value);
- QVariant getProperty(const QString& name) const;
- QSize sizeHint() const { return QSize(480, 270);}
-Q_SIGNALS:
- void durationChanged(int value);
- void positionChanged(int value);
-protected:
- void initializeGL() Q_DECL_OVERRIDE;
- void paintGL() Q_DECL_OVERRIDE;
-private Q_SLOTS:
- void swapped();
- void on_mpv_events();
-private:
- void handle_mpv_event(mpv_event *event);
- static void on_update(void *ctx);
-
- mpv::qt::Handle mpv;
- mpv_opengl_cb_context *mpv_gl;
-};
-
-
-
-#endif // PLAYERWINDOW_H
diff --git a/DOCS/client_api_examples/qt_opengl/qt_opengl.pro b/DOCS/client_api_examples/qt_opengl/qt_opengl.pro
deleted file mode 100644
index 8a2bcc665d..0000000000
--- a/DOCS/client_api_examples/qt_opengl/qt_opengl.pro
+++ /dev/null
@@ -1,13 +0,0 @@
-CONFIG -= app_bundle
-QT += widgets
-
-QT_CONFIG -= no-pkg-config
-CONFIG += link_pkgconfig debug
-PKGCONFIG += mpv
-
-HEADERS = \
- mpvwidget.h \
- mainwindow.h
-SOURCES = main.cpp \
- mpvwidget.cpp \
- mainwindow.cpp
diff --git a/DOCS/client_api_examples/sdl/main.c b/DOCS/client_api_examples/sdl/main.c
deleted file mode 100644
index b3b5952668..0000000000
--- a/DOCS/client_api_examples/sdl/main.c
+++ /dev/null
@@ -1,158 +0,0 @@
-// Build with: gcc -o main main.c `pkg-config --libs --cflags mpv sdl2`
-
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <SDL.h>
-
-#include <mpv/client.h>
-#include <mpv/opengl_cb.h>
-
-static Uint32 wakeup_on_mpv_redraw, wakeup_on_mpv_events;
-
-static void die(const char *msg)
-{
- fprintf(stderr, "%s\n", msg);
- exit(1);
-}
-
-static void *get_proc_address_mpv(void *fn_ctx, const char *name)
-{
- return SDL_GL_GetProcAddress(name);
-}
-
-static void on_mpv_events(void *ctx)
-{
- SDL_Event event = {.type = wakeup_on_mpv_events};
- SDL_PushEvent(&event);
-}
-
-static void on_mpv_redraw(void *ctx)
-{
- SDL_Event event = {.type = wakeup_on_mpv_redraw};
- SDL_PushEvent(&event);
-}
-
-int main(int argc, char *argv[])
-{
- if (argc != 2)
- die("pass a single media file as argument");
-
- mpv_handle *mpv = mpv_create();
- if (!mpv)
- die("context init failed");
-
- // Some minor options can only be set before mpv_initialize().
- if (mpv_initialize(mpv) < 0)
- die("mpv init failed");
-
- if (SDL_Init(SDL_INIT_VIDEO) < 0)
- die("SDL init failed");
-
- SDL_Window *window =
- SDL_CreateWindow("hi", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
- 1000, 500, SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN |
- SDL_WINDOW_RESIZABLE);
- if (!window)
- die("failed to create SDL window");
-
- // The OpenGL API is somewhat separate from the normal mpv API. This only
- // returns NULL if no OpenGL support is compiled.
- mpv_opengl_cb_context *mpv_gl = mpv_get_sub_api(mpv, MPV_SUB_API_OPENGL_CB);
- if (!mpv_gl)
- die("failed to create mpv GL API handle");
-
- SDL_GLContext glcontext = SDL_GL_CreateContext(window);
- if (!glcontext)
- die("failed to create SDL GL context");
-
- // This makes mpv use the currently set GL context. It will use the callback
- // to resolve GL builtin functions, as well as extensions.
- if (mpv_opengl_cb_init_gl(mpv_gl, NULL, get_proc_address_mpv, NULL) < 0)
- die("failed to initialize mpv GL context");
-
- // Actually using the opengl_cb state has to be explicitly requested.
- // Otherwise, mpv will create a separate platform window.
- if (mpv_set_option_string(mpv, "vo", "opengl-cb") < 0)
- die("failed to set VO");
-
- // We use events for thread-safe notification of the SDL main loop.
- // Generally, the wakeup callbacks (set further below) should do as least
- // work as possible, and merely wake up another thread to do actual work.
- // On SDL, waking up the mainloop is the ideal course of action. SDL's
- // SDL_PushEvent() is thread-safe, so we use that.
- wakeup_on_mpv_redraw = SDL_RegisterEvents(1);
- wakeup_on_mpv_events = SDL_RegisterEvents(1);
- if (wakeup_on_mpv_redraw == (Uint32)-1 || wakeup_on_mpv_events == (Uint32)-1)
- die("could not register events");
-
- // When normal mpv events are available.
- mpv_set_wakeup_callback(mpv, on_mpv_events, NULL);
-
- // When a new frame should be drawn with mpv_opengl_cb_draw().
- // (Separate from the normal event handling mechanism for the sake of
- // users which run OpenGL on a different thread.)
- mpv_opengl_cb_set_update_callback(mpv_gl, on_mpv_redraw, NULL);
-
- // Play this file. Note that this starts playback asynchronously.
- const char *cmd[] = {"loadfile", argv[1], NULL};
- mpv_command(mpv, cmd);
-
- while (1) {
- SDL_Event event;
- if (SDL_WaitEvent(&event) != 1)
- die("event loop error");
- int redraw = 0;
- switch (event.type) {
- case SDL_QUIT:
- goto done;
- case SDL_WINDOWEVENT:
- if (event.window.event == SDL_WINDOWEVENT_EXPOSED)
- redraw = 1;
- break;
- case SDL_KEYDOWN:
- if (event.key.keysym.sym == SDLK_SPACE)
- mpv_command_string(mpv, "cycle pause");
- break;
- default:
- // Happens when a new video frame should be rendered, or if the
- // current frame has to be redrawn e.g. due to OSD changes.
- if (event.type == wakeup_on_mpv_redraw)
- redraw = 1;
- // Happens when at least 1 new event is in the mpv event queue.
- if (event.type == wakeup_on_mpv_events) {
- // Handle all remaining mpv events.
- while (1) {
- mpv_event *mp_event = mpv_wait_event(mpv, 0);
- if (mp_event->event_id == MPV_EVENT_NONE)
- break;
- printf("event: %s\n", mpv_event_name(mp_event->event_id));
- }
- }
- }
- if (redraw) {
- int w, h;
- SDL_GetWindowSize(window, &w, &h);
- // Note:
- // - The 0 is the FBO to use; 0 is the default framebuffer (i.e.
- // render to the window directly.
- // - The negative height tells mpv to flip the coordinate system.
- // - If you do not want the video to cover the whole screen, or want
- // to apply any form of fancy transformation, you will have to
- // render to a FBO.
- // - See opengl_cb.h on what OpenGL environment mpv expects, and
- // other API details.
- mpv_opengl_cb_draw(mpv_gl, 0, w, -h);
- SDL_GL_SwapWindow(window);
- }
- }
-done:
-
- // Destroy the GL renderer and all of the GL objects it allocated. If video
- // is still running, the video track will be deselected.
- mpv_opengl_cb_uninit_gl(mpv_gl);
-
- mpv_terminate_destroy(mpv);
- return 0;
-}
diff --git a/DOCS/client_api_examples/simple/simple.c b/DOCS/client_api_examples/simple/simple.c
deleted file mode 100644
index 3ba1c35686..0000000000
--- a/DOCS/client_api_examples/simple/simple.c
+++ /dev/null
@@ -1,54 +0,0 @@
-// Build with: gcc -o simple simple.c `pkg-config --libs --cflags mpv`
-
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <mpv/client.h>
-
-static inline void check_error(int status)
-{
- if (status < 0) {
- printf("mpv API error: %s\n", mpv_error_string(status));
- exit(1);
- }
-}
-
-int main(int argc, char *argv[])
-{
- if (argc != 2) {
- printf("pass a single media file as argument\n");
- return 1;
- }
-
- mpv_handle *ctx = mpv_create();
- if (!ctx) {
- printf("failed creating context\n");
- return 1;
- }
-
- // Enable default key bindings, so the user can actually interact with
- // the player (and e.g. close the window).
- check_error(mpv_set_option_string(ctx, "input-default-bindings", "yes"));
- mpv_set_option_string(ctx, "input-vo-keyboard", "yes");
- int val = 1;
- check_error(mpv_set_option(ctx, "osc", MPV_FORMAT_FLAG, &val));
-
- // Done setting up options.
- check_error(mpv_initialize(ctx));
-
- // Play this file.
- const char *cmd[] = {"loadfile", argv[1], NULL};
- check_error(mpv_command(ctx, cmd));
-
- // Let it play, and wait until the user quits.
- while (1) {
- 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;
-}