Commit 07f63871 authored by Pierre d'Herbemont's avatar Pierre d'Herbemont

MacOSX/Framework/VLCVideoView.m: Supports the opengllayer video_output.

parent 38c86a7b
...@@ -23,6 +23,8 @@ ...@@ -23,6 +23,8 @@
*****************************************************************************/ *****************************************************************************/
#import <Cocoa/Cocoa.h> #import <Cocoa/Cocoa.h>
#import <QuartzCore/QuartzCore.h>
@class CALayer;
/* Notifications */ /* Notifications */
extern NSString * VLCVideoViewEnteredFullScreen; extern NSString * VLCVideoViewEnteredFullScreen;
...@@ -34,40 +36,26 @@ extern NSString * VLCVideoViewLeftFullScreen; ...@@ -34,40 +36,26 @@ extern NSString * VLCVideoViewLeftFullScreen;
- (void)videoLeftFullscreen:(NSNotification *)aNotification; - (void)videoLeftFullscreen:(NSNotification *)aNotification;
@end @end
@protocol VLCOpenGLVoutEmbedding @interface VLCVideoView : NSView
- (void)addVoutSubview:(NSView *)view;
- (void)removeVoutSubview:(NSView *)view;
- (void)enterFullscreen;
- (void)leaveFullscreen;
- (BOOL)stretchesVideo;
//- (void)setOnTop: (BOOL)ontop; /* Do we really want that in protocol? */
@end
@interface VLCVideoView : NSView <VLCOpenGLVoutEmbedding>
{ {
id delegate; id delegate;
NSColor * backColor; NSColor * backColor;
BOOL stretchesVideo; BOOL stretchesVideo;
BOOL fullscreen;
id layoutManager;
// TODO: Allow for view to report transparency to do some cool effects // TODO: Allow for view to report transparency to do some cool effects
// with the video? // with the video?
} }
@property (readonly, assign) BOOL fullscreen;
@property BOOL fillScreen;
- (void)setDelegate:(id)value; - (void)setDelegate:(id)value;
- (id)delegate; - (id)delegate;
- (void)setBackColor:(NSColor *)value; - (void)setBackColor:(NSColor *)value;
- (NSColor *)backColor; - (NSColor *)backColor;
- (void)setStretchesVideo:(BOOL)value;
- (BOOL)stretchesVideo;
- (void)addVoutSubview:(NSView *)aView;
- (void)removeVoutSubview:(NSView *)aView;
- (void)enterFullscreen; - (void)enterFullscreen;
- (void)leaveFullscreen; - (void)leaveFullscreen;
......
...@@ -30,18 +30,130 @@ ...@@ -30,18 +30,130 @@
#include <vlc/vlc.h> #include <vlc/vlc.h>
#include <vlc/libvlc.h> #include <vlc/libvlc.h>
#import <QuartzCore/QuartzCore.h>
/* Notifications */ /* Notifications */
NSString *VLCVideoViewEnteredFullScreen = @"VLCVideoViewEnteredFullScreen"; NSString *VLCVideoViewEnteredFullScreen = @"VLCVideoViewEnteredFullScreen";
NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
/******************************************************************************
* Soon deprecated stuff
*/
/* This is a forward reference to VLCOpenGLVoutView specified in minimal_macosx /* This is a forward reference to VLCOpenGLVoutView specified in minimal_macosx
library. We could get rid of this, but it prevents warnings from the library. We could get rid of this, but it prevents warnings from the
compiler. */ compiler. (Scheduled to deletion) */
@interface VLCOpenGLVoutView : NSView @interface VLCOpenGLVoutView : NSView
- (void)detachFromVout; - (void)detachFromVout;
@end @end
/* Depreacted methods */
@interface VLCVideoView (Deprecated)
- (void)setStretchesVideo:(BOOL)value;
- (BOOL)stretchesVideo;
- (void)addVoutSubview:(NSView *)aView; /* (Scheduled to deletion) */
- (void)removeVoutSubview:(NSView *)aView; /* (Scheduled to deletion) */
@end
/******************************************************************************
* VLCVideoView (Private)
*/
@interface VLCVideoView ()
/* Property */
@property (readwrite, assign) BOOL fullscreen;
@end
@interface VLCVideoView (Private)
/* Method */
- (void)addVoutLayer:(CALayer *)aLayer;
@end
/******************************************************************************
* Interface & Implementation VLCConstraintLayoutManager
*
* Manage the size of the video layer
*/
@interface VLCConstraintLayoutManager : CAConstraintLayoutManager
{
CGSize originalVideoSize;
BOOL fillScreenEntirely;
}
@property BOOL fillScreenEntirely;
@property CGSize originalVideoSize;
@end
@implementation VLCConstraintLayoutManager
@synthesize fillScreenEntirely;
@synthesize originalVideoSize;
- (id)init
{
if( self = [super init] )
{
self.originalVideoSize = CGSizeMake(0., 0.);
self.fillScreenEntirely = NO;
}
return self;
}
+ (id)layoutManager
{
return [[[VLCConstraintLayoutManager alloc] init] autorelease];
}
- (void)layoutSublayersOfLayer:(CALayer *)layer
{
/* Called by CA, when our rootLayer needs layout */
[super layoutSublayersOfLayer:layer];
/* After having done everything normally resize the vlcopengllayer */
if( [[layer sublayers] count] > 0 && [[[[layer sublayers] objectAtIndex:0] name] isEqualToString:@"vlcopengllayer"])
{
CALayer * videolayer = [[layer sublayers] objectAtIndex:0];
CGRect bounds = layer.bounds;
float new_height = (bounds.size.width * originalVideoSize.height) / originalVideoSize.width;
if( fillScreenEntirely )
{
if( bounds.size.height > new_height )
bounds.size.height = new_height;
else
bounds.size.width = (bounds.size.height * originalVideoSize.width) / originalVideoSize.height;
}
else
{
if( bounds.size.height > new_height )
bounds.size.width = (bounds.size.height * originalVideoSize.width) / originalVideoSize.height;
else
bounds.size.height = new_height;
}
bounds.origin = CGPointMake( 0.0, 0.0 );
videolayer.bounds = bounds;
videolayer.position = CGPointMake((layer.bounds.size.width - layer.bounds.origin.x)/2, (layer.bounds.size.height - layer.bounds.origin.y)/2);
}
}
@end
/******************************************************************************
* Implementation VLCVideoView
*/
@implementation VLCVideoView @implementation VLCVideoView
@synthesize fullscreen;
- (BOOL)fillScreen
{
return [layoutManager fillScreenEntirely];
}
- (void)setFillScreen:(BOOL)fillScreen
{
[layoutManager setFillScreenEntirely:fillScreen];
[[self layer] setNeedsLayout];
}
- (id)initWithFrame:(NSRect)rect - (id)initWithFrame:(NSRect)rect
{ {
if (self = [super initWithFrame:rect]) if (self = [super initWithFrame:rect])
...@@ -50,12 +162,15 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; ...@@ -50,12 +162,15 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
[self setBackColor:[NSColor blackColor]]; [self setBackColor:[NSColor blackColor]];
[self setStretchesVideo:NO]; [self setStretchesVideo:NO];
[self setAutoresizesSubviews:YES]; [self setAutoresizesSubviews:YES];
[self setFillScreen: NO];
layoutManager = [VLCConstraintLayoutManager layoutManager];
} }
return self; return self;
} }
- (void)dealloc - (void)dealloc
{ {
[layoutManager release];
delegate = nil; delegate = nil;
[backColor release]; [backColor release];
[super dealloc]; [super dealloc];
...@@ -85,45 +200,6 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; ...@@ -85,45 +200,6 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
return backColor; return backColor;
} }
- (void)setStretchesVideo:(BOOL)value
{
stretchesVideo = value;
}
- (BOOL)stretchesVideo
{
return stretchesVideo;
}
/* This is called by the libvlc module 'minimal_macosx' as soon as there is one
* vout available
*/
- (void)addVoutSubview:(NSView *)aView
{
if( [[self subviews] count] )
{
/* XXX: This is a hack until core gets fixed */
int i;
for( i = 0; i < [[self subviews] count]; i++ )
{
[[[self subviews] objectAtIndex:i] detachFromVout];
[[[self subviews] objectAtIndex:i] retain];
[[[self subviews] objectAtIndex:i] removeFromSuperview];
}
}
[self addSubview:aView];
[aView setFrame:[self bounds]];
// TODO: Should we let the media player specify these values?
[aView setAutoresizingMask:NSViewHeightSizable | NSViewWidthSizable];
}
- (void)removeVoutSubview:(NSView *)view
{
// Should we do something? I don't know, however the protocol requires
// this to be implemented
}
/* This is a LibVLC notification that we're about to enter into full screen, /* This is a LibVLC notification that we're about to enter into full screen,
there is no other place where I can see where we can trap this event */ there is no other place where I can see where we can trap this event */
- (void)enterFullscreen - (void)enterFullscreen
...@@ -133,7 +209,8 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; ...@@ -133,7 +209,8 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
withDelegateMethod:nil withDelegateMethod:nil
withNotificationName:VLCVideoViewEnteredFullScreen]; withNotificationName:VLCVideoViewEnteredFullScreen];
// There is nothing else to do, as this object strictly displays the video feed [super enterFullScreenMode:[[self window] screen] withOptions:nil];
self.fullscreen = YES;
} }
/* This is a LibVLC notification that we're about to enter leaving full screen, /* This is a LibVLC notification that we're about to enter leaving full screen,
...@@ -146,6 +223,8 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; ...@@ -146,6 +223,8 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
withNotificationName:VLCVideoViewLeftFullScreen]; withNotificationName:VLCVideoViewLeftFullScreen];
// There is nothing else to do, as this object strictly displays the video feed // There is nothing else to do, as this object strictly displays the video feed
[super exitFullScreenModeWithOptions:nil];
self.fullscreen = NO;
} }
- (void)drawRect:(NSRect)aRect - (void)drawRect:(NSRect)aRect
...@@ -160,4 +239,93 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen"; ...@@ -160,4 +239,93 @@ NSString *VLCVideoViewLeftFullScreen = @"VLCVideoViewLeftFullScreen";
{ {
return YES; return YES;
} }
- (void)mouseDown:(NSEvent *)theEvent
{
if([theEvent clickCount] != 2)
return;
if(self.fullscreen)
[self leaveFullscreen];
else
[self enterFullscreen];
}
@end
/******************************************************************************
* Implementation VLCVideoView (Private)
*/
@implementation VLCVideoView (Private)
/* This is called by the libvlc module 'opengllayer' as soon as there is one
* vout available
*/
- (void)addVoutLayer:(CALayer *)aLayer
{
[CATransaction begin];
[self setWantsLayer: YES];
CALayer * rootLayer = [self layer];
aLayer.name = @"vlcopengllayer";
[layoutManager setOriginalVideoSize:aLayer.bounds.size];
[rootLayer setLayoutManager:layoutManager];
[rootLayer insertSublayer:aLayer atIndex:0];
[aLayer setNeedsLayout];
[aLayer setNeedsDisplay];
[rootLayer setNeedsDisplay];
[rootLayer layoutIfNeeded];
[CATransaction commit];
}
@end
/******************************************************************************
* Implementation VLCVideoView (Deprecated)
*/
@implementation VLCVideoView (Deprecated)
- (void)setStretchesVideo:(BOOL)value
{
stretchesVideo = value;
}
- (BOOL)stretchesVideo
{
return stretchesVideo;
}
/* This is called by the libvlc module 'minimal_macosx' as soon as there is one
* vout available
*/
- (void)addVoutSubview:(NSView *)aView /* (Scheduled to deletion) */
{
/* This is where the real video comes from */
if( [[self subviews] count] )
{
/* XXX: This is a hack until core gets fixed */
int i;
for( i = 0; i < [[self subviews] count]; i++ )
{
[[[self subviews] objectAtIndex:i] detachFromVout];
[[[self subviews] objectAtIndex:i] retain];
[[[self subviews] objectAtIndex:i] removeFromSuperview];
}
}
[aView setFrame:[self bounds]];
[self addSubview:aView];
// TODO: Should we let the media player specify these values?
[aView setAutoresizingMask:NSViewHeightSizable | NSViewWidthSizable];
}
- (void)removeVoutSubview:(NSView *)view /* (Scheduled to deletion) */
{
// Should we do something? I don't know, however the protocol requires
// this to be implemented
}
@end @end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment