[vlc-devel] [PATCH 2/8] Add coreanim.m for Core Animation code that must use Objective C.

David Menestrina dmenest-vlc at ofb.net
Fri Sep 10 00:12:29 CEST 2010


---
 projects/mozilla/Makefile.am |   15 ++-
 projects/mozilla/coreanim.h  |   44 +++++++++
 projects/mozilla/coreanim.m  |  216 ++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 271 insertions(+), 4 deletions(-)
 create mode 100644 projects/mozilla/coreanim.h
 create mode 100644 projects/mozilla/coreanim.m

diff --git a/projects/mozilla/Makefile.am b/projects/mozilla/Makefile.am
index 230b720..b7b2874 100644
--- a/projects/mozilla/Makefile.am
+++ b/projects/mozilla/Makefile.am
@@ -2,6 +2,11 @@
 # Building the Mozilla plugin
 ###############################################################################
 
+# Automake forgets to add a proper tag to libtool with Objective-C files.
+# Moreover Libtool should default tag to CC when none is specified but
+# obviously does not. Here is a fix for that.
+LIBTOOL=@LIBTOOL@ --tag=CC
+
 MOSTLYCLEANFILES = 
 CLEANFILES = $(BUILT_SOURCES)
 EXTRA_DIST = $(DIST_sources) npvlc_rc.rc.in COPYING npvlc.dll.manifest
@@ -19,7 +24,7 @@ SOURCES_mozilla_common = \
 	support/classinfo.h
 
 DIST_sources = $(SOURCES_mozilla_common) \
-	support/npwin.cpp support/npmac.cpp support/npunix.c
+	support/npwin.cpp support/npmac.cpp support/npunix.c coreanim.m coreanim.h
 
 if BUILD_MOZILLA
 
@@ -62,18 +67,20 @@ if HAVE_DARWIN
 
 lib_LTLIBRARIES = npvlc.la
 
-SOURCES_support = support/npmac.cpp
+SOURCES_support = support/npmac.cpp coreanim.m
 CPPFLAGS_mozilla_EXTRA = -I. -I$(top_builddir) -I$(srcdir)/../include -c \
 	-F/System/Library/Frameworks/CoreFoundation.framework $(moz_CFLAGS) \
 	-I/Developer/Headers/FlatCarbon -fno-common -fpascal-strings \
 	-Wmost -Wno-four-char-constants -Wno-unknown-pragmas -DXP_MACOSX=1 \
-	-DNO_X11=1 -DUSE_SYSTEM_CONSOLE=1 -pipe -fmessage-length=0 
+	-DNO_X11=1 -DUSE_SYSTEM_CONSOLE=1 -pipe -fmessage-length=0
+OBJCFLAGS_mozilla_EXTRA = $(CPPFLAGS_mozilla_EXTRA)
 LDFLAGS_mozilla_EXTRA = -no-undefined -bundle -Wl,-read_only_relocs -Wl,suppress \
-	-Wl,-headerpad_max_install_names -shrext $(LIBEXT) -Wl,-framework,Carbon -Wl,-framework,System
+	-Wl,-headerpad_max_install_names -shrext $(LIBEXT) -Wl,-framework,Carbon -Wl,-framework,System -Wl,-framework,Cocoa -Wl,-framework,QuartzCore
 
 npvlc_la_SOURCES = $(SOURCES_mozilla_common) $(SOURCES_support)
 npvlc_la_CFLAGS = `$(VLC_CONFIG) --cflags mozilla` $(CPPFLAGS_mozilla_EXTRA)
 npvlc_la_CXXFLAGS = `$(VLC_CONFIG) --cxxflags mozilla` $(CPPFLAGS_mozilla_EXTRA) 
+npvlc_la_OBJCFLAGS = `$(VLC_CONFIG) --objcflags mozilla` $(OBJCFLAGS_mozilla_extra)
 npvlc_la_DEPENDENCIES = $(LIBRARIES_libvlc)
 npvlc_la_LDFLAGS = `$(VLC_CONFIG) --ldflags mozilla` -module -avoid-version \
 				   $(LDFLAGS_mozilla_EXTRA)
diff --git a/projects/mozilla/coreanim.h b/projects/mozilla/coreanim.h
new file mode 100644
index 0000000..853f42e
--- /dev/null
+++ b/projects/mozilla/coreanim.h
@@ -0,0 +1,44 @@
+/*****************************************************************************
+ * coreanim.h:
+ *****************************************************************************
+ * Copyright (C) 2010 Veetle, Inc.
+ * $Id$
+ *
+ * Authors: David Menestrina <dmenest-vlc at ofb.net>
+ *
+ * This program 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.
+ *
+ * This program 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#ifndef __VLCPLUGIN_COREANIM_H__
+#define __VLCPLUGIN_COREANIM_H__
+
+typedef struct coreanim_instance_t coreanim_instance_t;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+coreanim_instance_t *coreanim_init();
+void *coreanim_get_browser_layer(coreanim_instance_t *inst);
+void *coreanim_get_video_layer(coreanim_instance_t *inst);
+void coreanim_toggle_fullscreen(coreanim_instance_t *inst);
+void coreanim_set_fullscreen(coreanim_instance_t *inst, int fs);
+int  coreanim_get_fullscreen(coreanim_instance_t *inst);
+void coreanim_destroy(coreanim_instance_t *inst);
+#ifdef __cplusplus
+}
+#endif
+
+#endif // __VLCPLUGIN_COREANIM_H__
diff --git a/projects/mozilla/coreanim.m b/projects/mozilla/coreanim.m
new file mode 100644
index 0000000..280b264
--- /dev/null
+++ b/projects/mozilla/coreanim.m
@@ -0,0 +1,216 @@
+/*****************************************************************************
+ * coreanim.m:
+ *****************************************************************************
+ * Copyright (C) 2010 Veetle, Inc.
+ * $Id$
+ *
+ * Authors: David Menestrina <dmenest-vlc at ofb.net>
+ *
+ * This program 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.
+ *
+ * This program 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 this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
+ *****************************************************************************/
+
+#import <Cocoa/Cocoa.h>
+#import <QuartzCore/QuartzCore.h>
+#include "coreanim.h"
+
+void bla(const char *fmt, ...);
+
+struct coreanim_instance_t {
+    BOOL b_fullscreen;
+    CALayer *browserLayer;
+    CALayer *vlcLayer;
+    CALayer *fullscreenLayer;
+    NSView *fullscreenView;
+};
+
+/**
+ *  VLCFullscreenView is a simple subclass of NSView.  Its main purpose is
+ *  to handle events in fullscreen mode.
+ */
+ at interface VLCFullscreenView : NSView
+{
+    coreanim_instance_t *inst;
+}
+- (id) initWithInstance: (coreanim_instance_t *) p_inst;
+ at end
+
+ at implementation VLCFullscreenView : NSView
+- (id) initWithInstance: (coreanim_instance_t *) p_inst
+{
+    if( self = [super initWithFrame: [[NSScreen mainScreen] frame]] )
+        inst = p_inst;
+
+    return self;
+}
+- (void) dealloc
+{
+    inst = NULL;
+    [super dealloc];
+}
+- (BOOL) acceptsFirstResponder
+{
+    // We must return YES here if we wish to receive keyboard events.
+    return YES;
+}
+- (void) cancelOperation: (id) sender
+{
+    // Command-period is handled here.
+    // Also, the Escape key is handled here as long as the
+    // Escape keyDown event is passed up to the superclass.
+    coreanim_set_fullscreen(inst, FALSE);
+}
+- (void) mouseDown: (NSEvent *) event
+{
+    // Exit fullscreen on double click.
+    if( event.clickCount > 1 )
+        coreanim_set_fullscreen(inst, FALSE);
+    else
+        [super mouseDown: event];
+}
+ at end
+
+/**
+ *  Create and store the fullscreen layer and view for fullscreen mode,
+ *  storing them in the inst structure.
+ */
+static void createFullscreenView(coreanim_instance_t *inst)
+{
+    inst->fullscreenLayer = [[CALayer layer] retain];
+    inst->fullscreenLayer.layoutManager = [CAConstraintLayoutManager layoutManager];
+    inst->fullscreenLayer.backgroundColor = CGColorGetConstantColor(kCGColorBlack);
+
+    inst->fullscreenView = [[VLCFullscreenView alloc] initWithInstance: inst];
+    [inst->fullscreenView setLayer:inst->fullscreenLayer];
+    [inst->fullscreenView setWantsLayer:YES];
+}
+
+/**
+ *  Destroy the fullscreen layer and view.
+ */
+static void destroyFullscreenView(coreanim_instance_t *inst)
+{
+    [inst->fullscreenLayer release];
+    inst->fullscreenLayer = Nil;
+    [inst->fullscreenView release];
+    inst->fullscreenView = Nil;
+}
+
+coreanim_instance_t *coreanim_init()
+{
+    coreanim_instance_t *inst = calloc(1, sizeof(coreanim_instance_t));
+
+    inst->b_fullscreen = FALSE;
+
+    inst->browserLayer = [[CALayer layer] retain];
+
+    // According to Simon Fraser (Apple), WebKit will release the layer, so
+    // we must retain twice when we start, and then release once when we exit.
+    // http://lists.apple.com/archives/Webkitsdk-dev/2010/Sep/msg00001.html
+    [inst->browserLayer retain];
+    inst->browserLayer.layoutManager=[CAConstraintLayoutManager layoutManager];
+    inst->browserLayer.backgroundColor = CGColorGetConstantColor(kCGColorBlack);
+
+    inst->vlcLayer = [[CALayer layer] retain];
+    inst->vlcLayer.layoutManager = [CAConstraintLayoutManager layoutManager];
+    inst->vlcLayer.needsDisplayOnBoundsChange = YES;
+    [inst->vlcLayer addConstraint:[CAConstraint constraintWithAttribute:kCAConstraintWidth
+                                                             relativeTo:@"superlayer"
+                                                              attribute:kCAConstraintWidth]];
+    [inst->vlcLayer addConstraint:[CAConstraint constraintWithAttribute:kCAConstraintHeight
+                                                             relativeTo:@"superlayer"
+                                                              attribute:kCAConstraintHeight]];
+    [inst->vlcLayer addConstraint:[CAConstraint constraintWithAttribute:kCAConstraintMidY
+                                                             relativeTo:@"superlayer"
+                                                              attribute:kCAConstraintMidY]];
+    [inst->vlcLayer addConstraint:[CAConstraint constraintWithAttribute:kCAConstraintMidX
+                                                             relativeTo:@"superlayer"
+                                                              attribute:kCAConstraintMidX]];
+    [inst->browserLayer addSublayer: inst->vlcLayer];
+    NSMutableDictionary *newActions = [[NSMutableDictionary alloc] initWithObjectsAndKeys:[NSNull null], @"onOrderIn",
+                                       [NSNull null], @"onOrderOut",
+                                       [NSNull null], @"sublayers",
+                                       [NSNull null], @"contents",
+                                       [NSNull null], @"bounds",
+                                       [NSNull null], @"position",
+                                       nil];
+    inst->vlcLayer.actions = newActions;
+    [newActions release];
+
+    createFullscreenView(inst);
+
+    return inst;
+}
+
+void coreanim_destroy(coreanim_instance_t *inst)
+{
+    if( inst )
+    {
+        [inst->browserLayer release];
+        [inst->vlcLayer release];
+        destroyFullscreenView(inst);
+        free(inst);
+    }
+}
+
+static void coreanim_enter_fullscreen(coreanim_instance_t *inst)
+{
+    [inst->fullscreenView enterFullScreenMode:[NSScreen mainScreen]
+                                  withOptions:Nil];
+    [inst->vlcLayer removeFromSuperlayer];
+    [inst->fullscreenLayer addSublayer: inst->vlcLayer];
+    inst->b_fullscreen = TRUE;
+}
+
+static void coreanim_exit_fullscreen(coreanim_instance_t *inst)
+{
+    [inst->fullscreenView exitFullScreenModeWithOptions:Nil];
+
+    [inst->vlcLayer removeFromSuperlayer];
+    [inst->browserLayer addSublayer: inst->vlcLayer];
+    inst->b_fullscreen = FALSE;
+}
+
+void coreanim_toggle_fullscreen(coreanim_instance_t *inst)
+{
+   coreanim_set_fullscreen(inst, !inst->b_fullscreen);
+}
+
+void coreanim_set_fullscreen(coreanim_instance_t *inst, int fs)
+{
+    if (inst->b_fullscreen == fs)
+        return;
+
+    inst->b_fullscreen = fs;
+
+    if (fs)
+        coreanim_enter_fullscreen(inst);
+    else
+        coreanim_exit_fullscreen(inst);
+}
+
+int coreanim_get_fullscreen(coreanim_instance_t *inst)
+{
+    return inst->b_fullscreen;
+}
+
+void *coreanim_get_browser_layer(coreanim_instance_t *inst)
+{
+    return inst->browserLayer;
+}
+
+void *coreanim_get_video_layer(coreanim_instance_t *inst)
+{
+    return inst->vlcLayer;
+}
-- 
1.7.0.3




More information about the vlc-devel mailing list