diff options
author | wm4 <wm4@nowhere> | 2012-11-05 17:02:04 +0100 |
---|---|---|
committer | wm4 <wm4@nowhere> | 2012-11-12 20:06:14 +0100 |
commit | d4bdd0473d6f43132257c9fb3848d829755167a3 (patch) | |
tree | 8021c2f7da1841393c8c832105e20cd527826d6c /video/out | |
parent | bd48deba77bd5582c5829d6fe73a7d2571088aba (diff) | |
download | mpv-d4bdd0473d6f43132257c9fb3848d829755167a3.tar.bz2 mpv-d4bdd0473d6f43132257c9fb3848d829755167a3.tar.xz |
Rename directories, move files (step 1 of 2) (does not compile)
Tis drops the silly lib prefixes, and attempts to organize the tree in
a more logical way. Make the top-level directory less cluttered as
well.
Renames the following directories:
libaf -> audio/filter
libao2 -> audio/out
libvo -> video/out
libmpdemux -> demux
Split libmpcodecs:
vf* -> video/filter
vd*, dec_video.* -> video/decode
mp_image*, img_format*, ... -> video/
ad*, dec_audio.* -> audio/decode
libaf/format.* is moved to audio/ - this is similar to how mp_image.*
is located in video/.
Move most top-level .c/.h files to core. (talloc.c/.h is left on top-
level, because it's external.) Park some of the more annoying files
in compat/. Some of these are relicts from the time mplayer used
ffmpeg internals.
sub/ is not split, because it's too much of a mess (subtitle code is
mixed with OSD display and rendering).
Maybe the organization of core is not ideal: it mixes playback core
(like mplayer.c) and utility helpers (like bstr.c/h). Should the need
arise, the playback core will be moved somewhere else, while core
contains all helper and common code.
Diffstat (limited to 'video/out')
41 files changed, 21338 insertions, 0 deletions
diff --git a/video/out/aspect.c b/video/out/aspect.c new file mode 100644 index 0000000000..f3cd00a5e5 --- /dev/null +++ b/video/out/aspect.c @@ -0,0 +1,148 @@ +/* + * This file is part of MPlayer. + * + * MPlayer is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * MPlayer is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with MPlayer; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +/* Stuff for correct aspect scaling. */ +#include "aspect.h" +#include "geometry.h" +#include "video_out.h" +#include "mp_msg.h" +#include "options.h" + +#include "video_out.h" + +void aspect_save_videores(struct vo *vo, int w, int h, int d_w, int d_h) +{ + vo->aspdat.orgw = w; + vo->aspdat.orgh = h; + vo->aspdat.prew = d_w; + vo->aspdat.preh = d_h; + vo->aspdat.par = (double)d_w / d_h * h / w; +} + +void aspect_save_screenres(struct vo *vo, int scrw, int scrh) +{ + mp_msg(MSGT_VO, MSGL_DBG2, "aspect_save_screenres %dx%d\n", scrw, scrh); + struct MPOpts *opts = vo->opts; + if (scrw <= 0 && scrh <= 0) + scrw = 1024; + if (scrh <= 0) + scrh = (scrw * 3 + 3) / 4; + if (scrw <= 0) + scrw = (scrh * 4 + 2) / 3; + vo->aspdat.scrw = scrw; + vo->aspdat.scrh = scrh; + if (opts->force_monitor_aspect) + vo->monitor_par = opts->force_monitor_aspect * scrh / scrw; + else + vo->monitor_par = 1.0 / opts->monitor_pixel_aspect; +} + +/* aspect is called with the source resolution and the + * resolution, that the scaled image should fit into + */ + +void aspect_fit(struct vo *vo, int *srcw, int *srch, int fitw, int fith) +{ + struct aspect_data *aspdat = &vo->aspdat; + float pixelaspect = vo->monitor_par; + + mp_msg(MSGT_VO, MSGL_DBG2, "aspect(0) fitin: %dx%d monitor_par: %.2f\n", + fitw, fith, vo->monitor_par); + *srcw = fitw; + *srch = (float)fitw / aspdat->prew * aspdat->preh / pixelaspect; + *srch += *srch % 2; // round + mp_msg(MSGT_VO, MSGL_DBG2, "aspect(1) wh: %dx%d (org: %dx%d)\n", + *srcw, *srch, aspdat->prew, aspdat->preh); + if (*srch > fith || *srch < aspdat->orgh) { + int tmpw = (float)fith / aspdat->preh * aspdat->prew * pixelaspect; + tmpw += tmpw % 2; // round + if (tmpw <= fitw) { + *srch = fith; + *srcw = tmpw; + } else if (*srch > fith) { + mp_tmsg(MSGT_VO, MSGL_WARN, + "[ASPECT] Warning: No suitable new res found!\n"); + } + } + aspdat->asp = *srcw / (float)*srch; + mp_msg(MSGT_VO, MSGL_DBG2, "aspect(2) wh: %dx%d (org: %dx%d)\n", + *srcw, *srch, aspdat->prew, aspdat->preh); +} + +static void get_max_dims(struct vo *vo, int *w, int *h, int zoom) +{ + struct aspect_data *aspdat = &vo->aspdat; + *w = zoom ? aspdat->scrw : aspdat->prew; + *h = zoom ? aspdat->scrh : aspdat->preh; + if (zoom && WinID >= 0) + zoom = A_WINZOOM; + if (zoom == A_WINZOOM) { + *w = vo->dwidth; + *h = vo->dheight; + } +} + +void aspect(struct vo *vo, int *srcw, int *srch, int zoom) +{ + int fitw; + int fith; + get_max_dims(vo, &fitw, &fith, zoom); + if (!zoom && geometry_wh_changed) { + mp_msg(MSGT_VO, MSGL_DBG2, "aspect(0) no aspect forced!\n"); + return; // the user doesn't want to fix aspect + } + aspect_fit(vo, srcw, srch, fitw, fith); +} + +void panscan_init(struct vo *vo) +{ + vo->panscan_x = 0; + vo->panscan_y = 0; + vo->panscan_amount = 0.0f; +} + +static void panscan_calc_internal(struct vo *vo, int zoom) +{ + int fwidth, fheight; + int vo_panscan_area; + int max_w, max_h; + get_max_dims(vo, &max_w, &max_h, zoom); + struct MPOpts *opts = vo->opts; + + if (opts->vo_panscanrange > 0) { + aspect(vo, &fwidth, &fheight, zoom); + vo_panscan_area = max_h - fheight; + if (!vo_panscan_area) + vo_panscan_area = max_w - fwidth; + vo_panscan_area *= opts->vo_panscanrange; + } else + vo_panscan_area = -opts->vo_panscanrange * max_h; + + vo->panscan_amount = vo_fs || zoom == A_WINZOOM ? vo_panscan : 0; + vo->panscan_x = vo_panscan_area * vo->panscan_amount * vo->aspdat.asp; + vo->panscan_y = vo_panscan_area * vo->panscan_amount; +} + +/** + * vos that set vo_dwidth and v_dheight correctly should call this to update + * vo_panscan_x and vo_panscan_y + */ +void panscan_calc_windowed(struct vo *vo) +{ + panscan_calc_internal(vo, A_WINZOOM); +} diff --git a/video/out/aspect.h b/video/out/aspect.h new file mode 100644 index 0000000000..c5247421d2 --- /dev/null +++ b/video/out/aspect.h @@ -0,0 +1,37 @@ +/* + * This file is part of MPlayer. + * + * MPlayer is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * MPlayer is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with MPlayer; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#ifndef MPLAYER_ASPECT_H +#define MPLAYER_ASPECT_H +/* Stuff for correct aspect scaling. */ + +struct vo; +void panscan_init(struct vo *vo); +void panscan_calc_windowed(struct vo *vo); + +void aspect_save_videores(struct vo *vo, int w, int h, int d_w, int d_h); +void aspect_save_screenres(struct vo *vo, int scrw, int scrh); + +#define A_WINZOOM 2 ///< zoom to fill window size +#define A_ZOOM 1 +#define A_NOZOOM 0 + +void aspect(struct vo *vo, int *srcw, int *srch, int zoom); +void aspect_fit(struct vo *vo, int *srcw, int *srch, int fitw, int fith); + +#endif /* MPLAYER_ASPECT_H */ diff --git a/video/out/bitmap_packer.c b/video/out/bitmap_packer.c new file mode 100644 index 0000000000..603a6ce410 --- /dev/null +++ b/video/out/bitmap_packer.c @@ -0,0 +1,227 @@ +/* + * Calculate how to pack bitmap rectangles into a larger surface + * + * Copyright 2009, 2012 Uoti Urpala + * + * This file is part of mplayer2. + * + * mplayer2 is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * mplayer2 is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with mplayer2. If not, see <http://www.gnu.org/licenses/>. + */ + +#include <stdlib.h> +#include <assert.h> + +#include <libavutil/common.h> + +#include "talloc.h" +#include "bitmap_packer.h" +#include "mp_msg.h" +#include "mpcommon.h" +#include "sub/dec_sub.h" +#include "fastmemcpy.h" + +#define IS_POWER_OF_2(x) (((x) > 0) && !(((x) - 1) & (x))) + +void packer_reset(struct bitmap_packer *packer) +{ + struct bitmap_packer old = *packer; + *packer = (struct bitmap_packer) { + .w_max = old.w_max, + .h_max = old.h_max, + }; + talloc_free_children(packer); +} + +void packer_get_bb(struct bitmap_packer *packer, struct pos out_bb[2]) +{ + out_bb[0] = (struct pos) {0}; + out_bb[1] = (struct pos) { + FFMIN(packer->used_width + packer->padding, packer->w), + FFMIN(packer->used_height + packer->padding, packer->h), + }; +} + +#define HEIGHT_SORT_BITS 4 +static int size_index(int s) +{ + int n = av_log2_16bit(s); + return (n << HEIGHT_SORT_BITS) + + (- 1 - (s << HEIGHT_SORT_BITS >> n) & (1 << HEIGHT_SORT_BITS) - 1); +} + +/* Pack the given rectangles into an area of size w * h. + * The size of each rectangle is read from in[i].x / in[i].y. + * The height of each rectangle must be less than 65536. + * 'scratch' must point to work memory for num_rects+16 ints. + * The packed position for rectangle number i is set in out[i]. + * Return 0 on success, -1 if the rectangles did not fit in w*h. + * + * The rectangles are placed in rows in order approximately sorted by + * height (the approximate sorting is simpler than a full one would be, + * and allows the algorithm to work in linear time). Additionally, to + * reduce wasted space when there are a few tall rectangles, empty + * lower-right parts of rows are filled recursively when the size of + * rectangles in the row drops past a power-of-two threshold. So if a + * row starts with rectangles of size 3x50, 10x40 and 5x20 then the + * free rectangle with corners (13, 20)-(w, 50) is filled recursively. + */ +static int pack_rectangles(struct pos *in, struct pos *out, int num_rects, + int w, int h, int *scratch, int *used_width) +{ + int bins[16 << HEIGHT_SORT_BITS]; + int sizes[16 << HEIGHT_SORT_BITS] = { 0 }; + for (int i = 0; i < num_rects; i++) + sizes[size_index(in[i].y)]++; + int idx = 0; + for (int i = 0; i < 16 << HEIGHT_SORT_BITS; i += 1 << HEIGHT_SORT_BITS) { + for (int j = 0; j < 1 << HEIGHT_SORT_BITS; j++) { + bins[i + j] = idx; + idx += sizes[i + j]; + } + scratch[idx++] = -1; + } + for (int i = 0; i < num_rects; i++) + scratch[bins[size_index(in[i].y)]++] = i; + for (int i = 0; i < 16; i++) + bins[i] = bins[i << HEIGHT_SORT_BITS] - sizes[i << HEIGHT_SORT_BITS]; + struct { + int size, x, bottom; + } stack[16] = {{15, 0, h}}, s = {}; + int stackpos = 1; + int y; + while (stackpos) { + y = s.bottom; + s = stack[--stackpos]; + s.size++; + while (s.size--) { + int maxy = -1; + int obj; + while ((obj = scratch[bins[s.size]]) >= 0) { + int bottom = y + in[obj].y; + if (bottom > s.bottom) + break; + int right = s.x + in[obj].x; + if (right > w) + break; + bins[s.size]++; + out[obj] = (struct pos){s.x, y}; + num_rects--; + if (maxy < 0) + stack[stackpos++] = s; + s.x = right; + maxy = FFMAX(maxy, bottom); + } + *used_width = FFMAX(*used_width, s.x); + if (maxy > 0) + s.bottom = maxy; + } + } + return num_rects ? -1 : y; +} + +int packer_pack(struct bitmap_packer *packer) +{ + if (packer->count == 0) + return 0; + int w_orig = packer->w, h_orig = packer->h; + struct pos *in = packer->in; + int xmax = 0, ymax = 0; + for (int i = 0; i < packer->count; i++) { + if (in[i].x <= packer->padding || in[i].y <= packer->padding) + in[i] = (struct pos){0, 0}; + if (in[i].x < 0 || in [i].x > 65535 || in[i].y < 0 || in[i].y > 65535) { + mp_msg(MSGT_VO, MSGL_FATAL, "Invalid OSD / subtitle bitmap size\n"); + abort(); + } + xmax = FFMAX(xmax, in[i].x); + ymax = FFMAX(ymax, in[i].y); + } + xmax = FFMAX(0, xmax - packer->padding); + ymax = FFMAX(0, ymax - packer->padding); + if (xmax > packer->w) + packer->w = 1 << av_log2(xmax - 1) + 1; + if (ymax > packer->h) + packer->h = 1 << av_log2(ymax - 1) + 1; + while (1) { + int used_width = 0; + int y = pack_rectangles(in, packer->result, packer->count, + packer->w + packer->padding, + packer->h + packer->padding, + packer->scratch, &used_width); + if (y >= 0) { + // No padding at edges + packer->used_width = FFMIN(used_width, packer->w); + packer->used_height = FFMIN(y, packer->h); + assert(packer->w == 0 || IS_POWER_OF_2(packer->w)); + assert(packer->h == 0 || IS_POWER_OF_2(packer->h)); + return packer->w != w_orig || packer->h != h_orig; + } + if (packer->w <= packer->h && packer->w != packer->w_max) + packer->w = FFMIN(packer->w * 2, packer->w_max); + else if (packer->h != packer->h_max) + packer->h = FFMIN(packer->h * 2, packer->h_max); + else { + packer->w = w_orig; + packer->h = h_orig; + return -1; + } + } +} + +void packer_set_size(struct bitmap_packer *packer, int size) +{ + packer->count = size; + if (size <= packer->asize) + return; + packer->asize = FFMAX(packer->asize * 2, size); + talloc_free(packer->result); + talloc_free(packer->scratch); + packer->in = talloc_realloc(packer, packer->in, struct pos, packer->asize); + packer->result = talloc_array_ptrtype(packer, packer->result, + packer->asize); + packer->scratch = talloc_array_ptrtype(packer, packer->scratch, + packer->asize + 16); +} + +int packer_pack_from_subbitmaps(struct bitmap_packer *packer, + struct sub_bitmaps *b) +{ + packer->count = 0; + if (b->format == SUBBITMAP_EMPTY) + return 0; + packer_set_size(packer, b->num_parts); + int a = packer->padding; + for (int i = 0; i < b->num_parts; i++) + packer->in[i] = (struct pos){b->parts[i].w + a, b->parts[i].h + a}; + return packer_pack(packer); +} + +void packer_copy_subbitmaps(struct bitmap_packer *packer, struct sub_bitmaps *b, + void *data, int pixel_stride, int stride) +{ + assert(packer->count == b->num_parts); + if (packer->padding) { + struct pos bb[2]; + packer_get_bb(packer, bb); + memset_pic(data, 0, bb[1].x * pixel_stride, bb[1].y, stride); + } + for (int n = 0; n < packer->count; n++) { + struct sub_bitmap *s = &b->parts[n]; + struct pos p = packer->result[n]; + + void *pdata = (uint8_t *)data + p.y * stride + p.x * pixel_stride; + memcpy_pic(pdata, s->bitmap, s->w * pixel_stride, s->h, + stride, s->stride); + } +} diff --git a/video/out/bitmap_packer.h b/video/out/bitmap_packer.h new file mode 100644 index 0000000000..b86c3ec4f9 --- /dev/null +++ b/video/out/bitmap_packer.h @@ -0,0 +1,68 @@ +#ifndef MPLAYER_PACK_RECTANGLES_H +#define MPLAYER_PACK_RECTANGLES_H + +struct pos { + int x; + int y; +}; + +struct bitmap_packer { + int w; + int h; + int w_max; + int h_max; + int padding; + int count; + struct pos *in; + struct pos *result; + int used_width; + int used_height; + + // internal + int *scratch; + int asize; +}; + +struct ass_image; +struct sub_bitmaps; + +// Clear all internal state. Leave the following fields: w_max, h_max +void packer_reset(struct bitmap_packer *packer); + +// Get the bounding box used for bitmap data (including padding). +// The bounding box doesn't exceed (0,0)-(packer->w,packer->h). +void packer_get_bb(struct bitmap_packer *packer, struct pos out_bb[2]); + +/* Reallocate packer->in for at least to desired number of items. + * Also sets packer->count to the same value. + */ +void packer_set_size(struct bitmap_packer *packer, int size); + +/* To use this, set packer->count to number of rectangles, w_max and h_max + * to maximum output rectangle size, and w and h to start size (may be 0). + * Write input sizes in packer->in. + * Resulting packing will be written in packer->result. + * w and h will be increased if necessary for successful packing. + * There is a strong guarantee that w and h will be powers of 2 (or set to 0). + * Return value is -1 if packing failed because w and h were set to max + * values but that wasn't enough, 1 if w or h was increased, and 0 otherwise. + */ +int packer_pack(struct bitmap_packer *packer); + +/* Like above, but packer->count will be automatically set and + * packer->in will be reallocated if needed and filled from the + * given image list. + */ +int packer_pack_from_subbitmaps(struct bitmap_packer *packer, + struct sub_bitmaps *b); + +// Copy the (already packed) sub-bitmaps from b to the image in data. +// data must point to an image that is at least (packer->w, packer->h) big. +// The image has the given stride (bytes between (x, y) to (x, y + 1)), and the +// pixel format used by both the sub-bitmaps and the image uses pixel_stride +// bytes per pixel (bytes between (x, y) to (x + 1, y)). +// If packer->padding is set, the padding borders are cleared with 0. +void packer_copy_subbitmaps(struct bitmap_packer *packer, struct sub_bitmaps *b, + void *data, int pixel_stride, int stride); + +#endif diff --git a/video/out/cocoa_common.h b/video/out/cocoa_common.h new file mode 100644 index 0000000000..079e497441 --- /dev/null +++ b/video/out/cocoa_common.h @@ -0,0 +1,55 @@ +/* + * Cocoa OpenGL Backend + * + * This file is part of mplayer2. + * + * mplayer2 is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * mplayer2 is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with mplayer2. If not, see <http://www.gnu.org/licenses/>. + */ + +#ifndef MPLAYER_COCOA_COMMON_H +#define MPLAYER_COCOA_COMMON_H + +#include "video_out.h" + +struct vo_cocoa_state; + +bool vo_cocoa_gui_running(void); +void *vo_cocoa_glgetaddr(const char *s); + +int vo_cocoa_init(struct vo *vo); +void vo_cocoa_uninit(struct vo *vo); + +void vo_cocoa_update_xinerama_info(struct vo *vo); + +int vo_cocoa_change_attributes(struct vo *vo); +int vo_cocoa_create_window(struct vo *vo, uint32_t d_width, + uint32_t d_height, uint32_t flags, + int gl3profile); + +void vo_cocoa_swap_buffers(struct vo *vo); +int vo_cocoa_check_events(struct vo *vo); +void vo_cocoa_fullscreen(struct vo *vo); +void vo_cocoa_ontop(struct vo *vo); +void vo_cocoa_pause(struct vo *vo); +void vo_cocoa_resume(struct vo *vo); + +// returns an int to conform to the gl extensions from other platforms +int vo_cocoa_swap_interval(int enabled); + +void *vo_cocoa_cgl_context(struct vo *vo); +void *vo_cocoa_cgl_pixel_format(struct vo *vo); + +int vo_cocoa_cgl_color_size(struct vo *vo); + +#endif /* MPLAYER_COCOA_COMMON_H */ diff --git a/video/out/cocoa_common.m b/video/out/cocoa_common.m new file mode 100644 index 0000000000..337e0a32be --- /dev/null +++ b/video/out/cocoa_common.m @@ -0,0 +1,865 @@ +/* + * Cocoa OpenGL Backend + * + * This file is part of mplayer2. + * + * mplayer2 is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * mplayer2 is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with mplayer2. If not, see <http://www.gnu.org/licenses/>. + */ + +#import <Cocoa/Cocoa.h> +#import <CoreServices/CoreServices.h> // for CGDisplayHideCursor +#import <IOKit/pwr_mgt/IOPMLib.h> +#include <dlfcn.h> + +#include "cocoa_common.h" + +#include "config.h" + +#include "options.h" +#include "video_out.h" +#include "aspect.h" + +#include "mp_fifo.h" +#include "talloc.h" + +#include "input/input.h" +#include "input/keycodes.h" +#include "osx_common.h" +#include "mp_msg.h" + +#ifndef NSOpenGLPFAOpenGLProfile +#define NSOpenGLPFAOpenGLProfile 99 +#endif + +#ifndef NSOpenGLProfileVersionLegacy +#define NSOpenGLProfileVersionLegacy 0x1000 +#endif + +#ifndef NSOpenGLProfileVersion3_2Core +#define NSOpenGLProfileVersion3_2Core 0x3200 +#endif + +#define NSLeftAlternateKeyMask (0x000020 | NSAlternateKeyMask) +#define NSRightAlternateKeyMask (0x000040 | NSAlternateKeyMask) + +// add methods not available on OSX versions prior to 10.7 +#ifndef MAC_OS_X_VERSION_10_7 +@interface NSView (IntroducedInLion) +- (NSRect)convertRectToBacking:(NSRect)aRect; +- (void)setWantsBestResolutionOpenGLSurface:(BOOL)aBool; +@end +#endif + +// add power management assertion not available on OSX versions prior to 10.7 +#ifndef kIOPMAssertionTypePreventUserIdleDisplaySleep +#define kIOPMAssertionTypePreventUserIdleDisplaySleep \ + CFSTR("PreventUserIdleDisplaySleep") +#endif + +@interface GLMPlayerWindow : NSWindow <NSWindowDelegate> { + struct vo *_vo; +} +- (void)setVideoOutput:(struct vo *)vo; +- (BOOL)canBecomeKeyWindow; +- (BOOL)canBecomeMainWindow; +- (void)fullscreen; +- (void)mouseEvent:(NSEvent *)theEvent; +- (void)mulSize:(float)multiplier; +- (void)setContentSize:(NSSize)newSize keepCentered:(BOOL)keepCentered; +@end + +@interface GLMPlayerOpenGLView : NSView +@end + +struct vo_cocoa_state { + NSAutoreleasePool *pool; + GLMPlayerWindow *window; + NSOpenGLContext *glContext; + NSOpenGLPixelFormat *pixelFormat; + + NSSize current_video_size; + NSSize previous_video_size; + + NSRect screen_frame; + NSScreen *screen_handle; + NSArray *screen_array; + + NSInteger windowed_mask; + NSInteger fullscreen_mask; + + NSRect windowed_frame; + + NSString *window_title; + + NSInteger window_level; + NSInteger fullscreen_window_level; + + int display_cursor; + int cursor_timer; + int cursor_autohide_delay; + |