summaryrefslogtreecommitdiffstats
path: root/src/plugins/platforms/cocoa
diff options
context:
space:
mode:
Diffstat (limited to 'src/plugins/platforms/cocoa')
-rw-r--r--src/plugins/platforms/cocoa/cocoa.pro18
-rw-r--r--src/plugins/platforms/cocoa/qcocoaeventloopintegration.mm112
-rw-r--r--src/plugins/platforms/cocoa/qcocoaglcontext.h54
-rw-r--r--src/plugins/platforms/cocoa/qcocoaglcontext.mm105
-rw-r--r--src/plugins/platforms/cocoa/qcocoaintegration.h8
-rw-r--r--src/plugins/platforms/cocoa/qcocoaintegration.mm28
-rw-r--r--src/plugins/platforms/cocoa/qcocoanativeinterface.h (renamed from src/plugins/platforms/cocoa/qcocoaeventloopintegration.h)24
-rw-r--r--src/plugins/platforms/cocoa/qcocoanativeinterface.mm60
-rw-r--r--src/plugins/platforms/cocoa/qcocoawindow.h22
-rw-r--r--src/plugins/platforms/cocoa/qcocoawindow.mm87
-rw-r--r--src/plugins/platforms/cocoa/qcocoawindowsurface.h6
-rw-r--r--src/plugins/platforms/cocoa/qcocoawindowsurface.mm17
-rw-r--r--src/plugins/platforms/cocoa/qnsview.h11
-rw-r--r--src/plugins/platforms/cocoa/qnsview.mm135
-rw-r--r--src/plugins/platforms/cocoa/qnswindowdelegate.h21
-rw-r--r--src/plugins/platforms/cocoa/qnswindowdelegate.mm10
16 files changed, 510 insertions, 208 deletions
diff --git a/src/plugins/platforms/cocoa/cocoa.pro b/src/plugins/platforms/cocoa/cocoa.pro
index bfa147f948..5573b19fcd 100644
--- a/src/plugins/platforms/cocoa/cocoa.pro
+++ b/src/plugins/platforms/cocoa/cocoa.pro
@@ -7,23 +7,29 @@ OBJECTIVE_SOURCES = main.mm \
qcocoawindowsurface.mm \
qcocoawindow.mm \
qnsview.mm \
- qcocoaeventloopintegration.mm \
qcocoaautoreleasepool.mm \
- qnswindowdelegate.mm
+ qnswindowdelegate.mm \
+ qcocoaglcontext.mm \
+ qcocoanativeinterface.mm
+
OBJECTIVE_HEADERS = qcocoaintegration.h \
qcocoawindowsurface.h \
qcocoawindow.h \
qnsview.h \
- qcocoaeventloopintegration.h \
qcocoaautoreleasepool.h \
- qnswindowdelegate.h
+ qnswindowdelegate.h \
+ qcocoaglcontext.h \
+ qcocoanativeinterface.h
+
+DEFINES += QT_BUILD_COCOA_LIB
#add libz for freetype.
LIBS += -lz
LIBS += -framework cocoa
-include(../fontdatabases/coretext/coretext.pri)
+QT += core-private gui-private platformsupport-private
+
+CONFIG += qpa/basicunixfontdatabase
target.path += $$[QT_INSTALL_PLUGINS]/platforms
INSTALLS += target
-
diff --git a/src/plugins/platforms/cocoa/qcocoaeventloopintegration.mm b/src/plugins/platforms/cocoa/qcocoaeventloopintegration.mm
deleted file mode 100644
index ac0b75e9ea..0000000000
--- a/src/plugins/platforms/cocoa/qcocoaeventloopintegration.mm
+++ /dev/null
@@ -1,112 +0,0 @@
-/****************************************************************************
-**
-** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
-** All rights reserved.
-** Contact: Nokia Corporation (qt-info@nokia.com)
-**
-** This file is part of the plugins of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:LGPL$
-** GNU Lesser General Public License Usage
-** This file may be used under the terms of the GNU Lesser General Public
-** License version 2.1 as published by the Free Software Foundation and
-** appearing in the file LICENSE.LGPL included in the packaging of this
-** file. Please review the following information to ensure the GNU Lesser
-** General Public License version 2.1 requirements will be met:
-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
-**
-** In addition, as a special exception, Nokia gives you certain additional
-** rights. These rights are described in the Nokia Qt LGPL Exception
-** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
-**
-** GNU General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU General
-** Public License version 3.0 as published by the Free Software Foundation
-** and appearing in the file LICENSE.GPL included in the packaging of this
-** file. Please review the following information to ensure the GNU General
-** Public License version 3.0 requirements will be met:
-** http://www.gnu.org/copyleft/gpl.html.
-**
-** Other Usage
-** Alternatively, this file may be used in accordance with the terms and
-** conditions contained in a signed written agreement between you and Nokia.
-**
-**
-**
-**
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
-
-#include "qcocoaeventloopintegration.h"
-
-#import <Cocoa/Cocoa.h>
-
-#include "qcocoaautoreleasepool.h"
-
-#include <QtCore/QElapsedTimer>
-
-#include <QDebug>
-#include <QApplication>
-
-void wakeupCallback ( void * ) {
- QPlatformEventLoopIntegration::processEvents();
-}
-
-void timerCallback( CFRunLoopTimerRef timer, void *info)
-{
- QPlatformEventLoopIntegration::processEvents();
- QCocoaEventLoopIntegration *eventLoopIntegration =
- static_cast<QCocoaEventLoopIntegration *>(info);
- qint64 nextTime = eventLoopIntegration->nextTimerEvent();
- CFAbsoluteTime nexttime = CFAbsoluteTimeGetCurrent();
- nexttime = nexttime + (double(nextTime)/1000);
- CFRunLoopTimerSetNextFireDate(timer,nexttime);
-}
-
-QCocoaEventLoopIntegration::QCocoaEventLoopIntegration() :
- QPlatformEventLoopIntegration()
-{
- [NSApplication sharedApplication];
- m_sourceContext.version = 0;
- m_sourceContext.info = this;
- m_sourceContext.retain = 0;
- m_sourceContext.release = 0;
- m_sourceContext.copyDescription = 0;
- m_sourceContext.equal = 0;
- m_sourceContext.hash = 0;
- m_sourceContext.schedule = 0;
- m_sourceContext.cancel = 0;
- m_sourceContext.perform = wakeupCallback;
-
- m_source = CFRunLoopSourceCreate(0,0,&m_sourceContext);
- CFRunLoopAddSource(CFRunLoopGetMain(),m_source,kCFRunLoopCommonModes);
-
- m_timerContext.version = 0;
- m_timerContext.info = this;
- m_timerContext.retain = 0;
- m_timerContext.release = 0;
- m_timerContext.copyDescription = 0;
- CFAbsoluteTime fireDate = CFAbsoluteTimeGetCurrent ();
- CFTimeInterval interval = 30;
-
- CFRunLoopTimerRef m_timerSource = CFRunLoopTimerCreate(0,fireDate,interval,0,0,timerCallback,&m_timerContext);
- CFRunLoopAddTimer(CFRunLoopGetMain(),m_timerSource,kCFRunLoopCommonModes);
-}
-
-void QCocoaEventLoopIntegration::startEventLoop()
-{
- [[NSApplication sharedApplication] run];
-}
-
-void QCocoaEventLoopIntegration::quitEventLoop()
-{
- [[NSApplication sharedApplication] terminate:nil];
-}
-
-void QCocoaEventLoopIntegration::qtNeedsToProcessEvents()
-{
- CFRunLoopSourceSignal(m_source);
-}
-
diff --git a/src/plugins/platforms/cocoa/qcocoaglcontext.h b/src/plugins/platforms/cocoa/qcocoaglcontext.h
new file mode 100644
index 0000000000..01d931b662
--- /dev/null
+++ b/src/plugins/platforms/cocoa/qcocoaglcontext.h
@@ -0,0 +1,54 @@
+#ifndef QCOCOAGLCONTEXT_H
+#define QCOCOAGLCONTEXT_H
+
+#include <QtCore/QWeakPointer>
+#include <QtGui/QPlatformGLContext>
+#include <QtGui/QGuiGLContext>
+#include <QtGui/QWindow>
+
+#include <Cocoa/Cocoa.h>
+
+QT_BEGIN_NAMESPACE
+
+class QCocoaGLSurface : public QPlatformGLSurface
+{
+public:
+ QCocoaGLSurface(const QGuiGLFormat &format, QWindow *window)
+ : QPlatformGLSurface(format)
+ , window(window)
+ {
+ }
+
+ QWindow *window;
+};
+
+class QCocoaGLContext : public QPlatformGLContext
+{
+public:
+ QCocoaGLContext(const QGuiGLFormat &format, QPlatformGLContext *share);
+
+ QGuiGLFormat format() const;
+
+ void swapBuffers(const QPlatformGLSurface &surface);
+
+ bool makeCurrent(const QPlatformGLSurface &surface);
+ void doneCurrent();
+
+ void (*getProcAddress(const QByteArray &procName)) ();
+
+ void update();
+
+ static NSOpenGLPixelFormat *createNSOpenGLPixelFormat();
+ NSOpenGLContext *nsOpenGLContext() const;
+
+private:
+ void setActiveWindow(QWindow *window);
+
+ NSOpenGLContext *m_context;
+ QGuiGLFormat m_format;
+ QWeakPointer<QWindow> m_currentWindow;
+};
+
+QT_END_NAMESPACE
+
+#endif // QCOCOAGLCONTEXT_H
diff --git a/src/plugins/platforms/cocoa/qcocoaglcontext.mm b/src/plugins/platforms/cocoa/qcocoaglcontext.mm
new file mode 100644
index 0000000000..f9cda1bb37
--- /dev/null
+++ b/src/plugins/platforms/cocoa/qcocoaglcontext.mm
@@ -0,0 +1,105 @@
+#include "qcocoaglcontext.h"
+#include "qcocoawindow.h"
+#include <qdebug.h>
+#include <QtCore/private/qcore_mac_p.h>
+
+#import <Cocoa/Cocoa.h>
+
+QCocoaGLContext::QCocoaGLContext(const QGuiGLFormat &format, QPlatformGLContext *share)
+ : m_format(format)
+{
+ NSOpenGLPixelFormat *pixelFormat = createNSOpenGLPixelFormat();
+ NSOpenGLContext *actualShare = share ? static_cast<QCocoaGLContext *>(share)->m_context : 0;
+
+ m_context = [NSOpenGLContext alloc];
+ [m_context initWithFormat:pixelFormat shareContext:actualShare];
+}
+
+// Match up with createNSOpenGLPixelFormat!
+QGuiGLFormat QCocoaGLContext::format() const
+{
+ return m_format;
+}
+
+void QCocoaGLContext::swapBuffers(const QPlatformGLSurface &surface)
+{
+ QWindow *window = static_cast<const QCocoaGLSurface &>(surface).window;
+ setActiveWindow(window);
+
+ [m_context flushBuffer];
+}
+
+bool QCocoaGLContext::makeCurrent(const QPlatformGLSurface &surface)
+{
+ QWindow *window = static_cast<const QCocoaGLSurface &>(surface).window;
+ setActiveWindow(window);
+
+ [m_context makeCurrentContext];
+ return true;
+}
+
+void QCocoaGLContext::setActiveWindow(QWindow *window)
+{
+ if (window == m_currentWindow.data())
+ return;
+
+ if (m_currentWindow)
+ static_cast<QCocoaWindow *>(m_currentWindow.data()->handle())->setCurrentContext(0);
+
+ Q_ASSERT(window->handle());
+
+ m_currentWindow = window;
+
+ QCocoaWindow *cocoaWindow = static_cast<QCocoaWindow *>(window->handle());
+ cocoaWindow->setCurrentContext(this);
+
+ NSView *view = cocoaWindow->windowSurfaceView();
+ [m_context setView:view];
+}
+
+void QCocoaGLContext::doneCurrent()
+{
+ if (m_currentWindow)
+ static_cast<QCocoaWindow *>(m_currentWindow.data()->handle())->setCurrentContext(0);
+
+ m_currentWindow.clear();
+
+ [NSOpenGLContext clearCurrentContext];
+}
+
+void (*QCocoaGLContext::getProcAddress(const QByteArray &procName)) ()
+{
+ CFURLRef url = CFURLCreateWithFileSystemPath(kCFAllocatorDefault,
+ CFSTR("/System/Library/Frameworks/OpenGL.framework"), kCFURLPOSIXPathStyle, false);
+ CFBundleRef bundle = CFBundleCreate(kCFAllocatorDefault, url);
+ CFStringRef procNameCF = QCFString::toCFStringRef(QString::fromAscii(procName.constData()));
+ void *proc = CFBundleGetFunctionPointerForName(bundle, procNameCF);
+ CFRelease(url);
+ CFRelease(bundle);
+ CFRelease(procNameCF);
+ return (void (*) ())proc;
+}
+
+void QCocoaGLContext::update()
+{
+ [m_context update];
+}
+
+NSOpenGLPixelFormat *QCocoaGLContext::createNSOpenGLPixelFormat()
+{
+ NSOpenGLPixelFormatAttribute attrs[] =
+ {
+ NSOpenGLPFADoubleBuffer,
+ NSOpenGLPFADepthSize, 32,
+ 0
+ };
+
+ NSOpenGLPixelFormat* pixelFormat = [[NSOpenGLPixelFormat alloc] initWithAttributes:attrs];
+ return pixelFormat;
+}
+
+NSOpenGLContext *QCocoaGLContext::nsOpenGLContext() const
+{
+ return m_context;
+}
+
diff --git a/src/plugins/platforms/cocoa/qcocoaintegration.h b/src/plugins/platforms/cocoa/qcocoaintegration.h
index 120bee46b7..59008b4e3f 100644
--- a/src/plugins/platforms/cocoa/qcocoaintegration.h
+++ b/src/plugins/platforms/cocoa/qcocoaintegration.h
@@ -77,15 +77,15 @@ public:
bool hasCapability(QPlatformIntegration::Capability cap) const;
QPixmapData *createPixmapData(QPixmapData::PixelType type) const;
- QPlatformWindow *createPlatformWindow(QWidget *widget, WId winId = 0) const;
- QWindowSurface *createWindowSurface(QWidget *widget, WId winId) const;
+ QPlatformWindow *createPlatformWindow(QWindow *window) const;
+ QPlatformGLContext *createPlatformGLContext(const QGuiGLFormat &glFormat, QPlatformGLContext *share) const;
+ QWindowSurface *createWindowSurface(QWindow *widget, WId winId) const;
QList<QPlatformScreen *> screens() const { return mScreens; }
QPlatformFontDatabase *fontDatabase() const;
- QPlatformEventLoopIntegration *createEventLoopIntegration() const;
-
+ QPlatformNativeInterface *nativeInterface() const;
private:
QList<QPlatformScreen *> mScreens;
QPlatformFontDatabase *mFontDb;
diff --git a/src/plugins/platforms/cocoa/qcocoaintegration.mm b/src/plugins/platforms/cocoa/qcocoaintegration.mm
index 086f7b62e9..dfe225ff2e 100644
--- a/src/plugins/platforms/cocoa/qcocoaintegration.mm
+++ b/src/plugins/platforms/cocoa/qcocoaintegration.mm
@@ -43,11 +43,9 @@
#include "qcocoawindow.h"
#include "qcocoawindowsurface.h"
-#include "qcocoaeventloopintegration.h"
+#include "qcocoanativeinterface.h"
-#include "qcoretextfontdatabase.h"
-
-#include <QtGui/QApplication>
+#include "qbasicunixfontdatabase.h"
#include <private/qpixmap_raster_p.h>
@@ -74,7 +72,7 @@ QCocoaScreen::~QCocoaScreen()
}
QCocoaIntegration::QCocoaIntegration()
- : mFontDb(new QCoreTextFontDatabase())
+ : mFontDb(new QBasicUnixFontDatabase())
{
mPool = new QCocoaAutoReleasePool;
@@ -98,6 +96,7 @@ bool QCocoaIntegration::hasCapability(QPlatformIntegration::Capability cap) cons
{
switch (cap) {
case ThreadedPixmaps: return true;
+ case OpenGL : return true;
default: return QPlatformIntegration::hasCapability(cap);
}
}
@@ -109,15 +108,19 @@ QPixmapData *QCocoaIntegration::createPixmapData(QPixmapData::PixelType type) co
return new QRasterPixmapData(type);
}
-QPlatformWindow *QCocoaIntegration::createPlatformWindow(QWidget *widget, WId winId) const
+QPlatformWindow *QCocoaIntegration::createPlatformWindow(QWindow *window) const
{
- Q_UNUSED(winId);
- return new QCocoaWindow(widget);
+ return new QCocoaWindow(window);
}
-QWindowSurface *QCocoaIntegration::createWindowSurface(QWidget *widget, WId winId) const
+QPlatformGLContext *QCocoaIntegration::createPlatformGLContext(const QGuiGLFormat &glFormat, QPlatformGLContext *share) const
{
- return new QCocoaWindowSurface(widget,winId);
+ return new QCocoaGLContext(glFormat, share);
+}
+
+QWindowSurface *QCocoaIntegration::createWindowSurface(QWindow *window, WId winId) const
+{
+ return new QCocoaWindowSurface(window, winId);
}
QPlatformFontDatabase *QCocoaIntegration::fontDatabase() const
@@ -125,8 +128,9 @@ QPlatformFontDatabase *QCocoaIntegration::fontDatabase() const
return mFontDb;
}
-QPlatformEventLoopIntegration *QCocoaIntegration::createEventLoopIntegration() const
+QPlatformNativeInterface *QCocoaIntegration::nativeInterface() const
{
- return new QCocoaEventLoopIntegration();
+ return new QCocoaNativeInterface();
}
+
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/qcocoaeventloopintegration.h b/src/plugins/platforms/cocoa/qcocoanativeinterface.h
index 5765483fc7..f8216d8e61 100644
--- a/src/plugins/platforms/cocoa/qcocoaeventloopintegration.h
+++ b/src/plugins/platforms/cocoa/qcocoanativeinterface.h
@@ -39,27 +39,17 @@
**
****************************************************************************/
-#ifndef QCOCAEVENTLOOPINTEGRATION_H
-#define QCOCAEVENTLOOPINTEGRATION_H
+#ifndef QCOCOANATIVEINTERFACE_H
+#define QCOCOANATIVEINTERFACE_H
-#include <Cocoa/Cocoa.h>
+#include <QtGui/QPlatformNativeInterface>
-#include <QPlatformEventLoopIntegration>
+class QWidget;
-
-class QCocoaEventLoopIntegration : public QPlatformEventLoopIntegration
+class QCocoaNativeInterface : public QPlatformNativeInterface
{
public:
- QCocoaEventLoopIntegration();
- void startEventLoop();
- void quitEventLoop();
- void qtNeedsToProcessEvents();
-
-private:
- CFRunLoopSourceContext m_sourceContext;
- CFRunLoopTimerContext m_timerContext;
- CFRunLoopSourceRef m_source;
+ void *nativeResourceForWindow(const QByteArray &resourceString, QWindow *window);
};
-#endif // QCOCAEVENTLOOPINTEGRATION_H
-
+#endif // QCOCOANATIVEINTERFACE_H
diff --git a/src/plugins/platforms/cocoa/qcocoanativeinterface.mm b/src/plugins/platforms/cocoa/qcocoanativeinterface.mm
new file mode 100644
index 0000000000..87d0ec4a0c
--- /dev/null
+++ b/src/plugins/platforms/cocoa/qcocoanativeinterface.mm
@@ -0,0 +1,60 @@
+/****************************************************************************
+**
+** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** GNU Lesser General Public License Usage
+** This file may be used under the terms of the GNU Lesser General Public
+** License version 2.1 as published by the Free Software Foundation and
+** appearing in the file LICENSE.LGPL included in the packaging of this
+** file. Please review the following information to ensure the GNU Lesser
+** General Public License version 2.1 requirements will be met:
+** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU General
+** Public License version 3.0 as published by the Free Software Foundation
+** and appearing in the file LICENSE.GPL included in the packaging of this
+** file. Please review the following information to ensure the GNU General
+** Public License version 3.0 requirements will be met:
+** http://www.gnu.org/copyleft/gpl.html.
+**
+** Other Usage
+** Alternatively, this file may be used in accordance with the terms and
+** conditions contained in a signed written agreement between you and Nokia.
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qcocoanativeinterface.h"
+#include "qcocoaglcontext.h"
+#include "qcocoawindow.h"
+#include <qbytearray.h>
+#include <qwindow.h>
+#include "qplatformwindow_qpa.h"
+#include "qguiglformat_qpa.h"
+#include "qplatformglcontext_qpa.h"
+#include "qguiglcontext_qpa.h"
+#include <qdebug.h>
+
+void *QCocoaNativeInterface::nativeResourceForWindow(const QByteArray &resourceString, QWindow *window)
+{
+ if (resourceString == "nsopenglcontext") {
+
+ static_cast<QCocoaWindow *>(window->handle())->currentContext()->nsOpenGLContext();
+ }
+ return 0;
+}
diff --git a/src/plugins/platforms/cocoa/qcocoawindow.h b/src/plugins/platforms/cocoa/qcocoawindow.h
index 9e7e68b7d2..9d7d37c2ee 100644
--- a/src/plugins/platforms/cocoa/qcocoawindow.h
+++ b/src/plugins/platforms/cocoa/qcocoawindow.h
@@ -46,27 +46,41 @@
#include <QPlatformWindow>
+#include "qcocoaglcontext.h"
+#include "qnsview.h"
+
QT_BEGIN_NAMESPACE
class QCocoaWindow : public QPlatformWindow
{
public:
- QCocoaWindow(QWidget *tlw);
+ QCocoaWindow(QWindow *tlw);
~QCocoaWindow();
void setGeometry(const QRect &rect);
-
void setVisible(bool visible);
+ void setWindowTitle(const QString &title);
+ void raise();
+ void lower();
WId winId() const;
-
NSView *contentView() const;
- void setContentView(NSView *contentView);
+ NSView *windowSurfaceView() const;
+ void windowDidMove();
void windowDidResize();
+ QPlatformGLSurface *createGLSurface() const;
+
+ void setCurrentContext(QCocoaGLContext *context);
+ QCocoaGLContext *currentContext() const;
+
private:
+ friend class QCocoaWindowSurface;
NSWindow *m_nsWindow;
+ QNSView *m_contentView;
+ NSView *m_windowSurfaceView;
+ QCocoaGLContext *m_glContext;
};
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/qcocoawindow.mm b/src/plugins/platforms/cocoa/qcocoawindow.mm
index a2fdce3520..874790a128 100644
--- a/src/plugins/platforms/cocoa/qcocoawindow.mm
+++ b/src/plugins/platforms/cocoa/qcocoawindow.mm
@@ -41,17 +41,17 @@
#include "qcocoawindow.h"
#include "qnswindowdelegate.h"
#include "qcocoaautoreleasepool.h"
-
-#include <QWidget>
-
-#include <QtGui/QApplication>
+#include "qcocoaglcontext.h"
+#include "qnsview.h"
+#include <QtCore/private/qcore_mac_p.h>
#include <QWindowSystemInterface>
#include <QDebug>
-QCocoaWindow::QCocoaWindow(QWidget *tlw)
+QCocoaWindow::QCocoaWindow(QWindow *tlw)
: QPlatformWindow(tlw)
+ , m_glContext(0)
{
QCocoaAutoReleasePool pool;
const QRect geo = tlw->geometry();
@@ -65,12 +65,26 @@ QCocoaWindow::QCocoaWindow(QWidget *tlw)
QNSWindowDelegate *delegate = [[QNSWindowDelegate alloc] initWithQCocoaWindow:this];
[m_nsWindow setDelegate:delegate];
- [m_nsWindow makeKeyAndOrderFront:nil];
[m_nsWindow setAcceptsMouseMovedEvents:YES];
+
+ m_contentView = [[QNSView alloc] initWithQWindow:tlw];
+
+ if (tlw->surfaceType() == QWindow::OpenGLSurface) {
+ NSRect glFrame = NSMakeRect(0, 0, geo.width(), geo.height());
+ m_windowSurfaceView = [[NSOpenGLView alloc] initWithFrame : glFrame pixelFormat : QCocoaGLContext::createNSOpenGLPixelFormat() ];
+ [m_contentView setAutoresizesSubviews : YES];
+ [m_windowSurfaceView setAutoresizingMask : (NSViewWidthSizable | NSViewHeightSizable)];
+ [m_contentView addSubview : m_windowSurfaceView];
+ } else {
+ m_windowSurfaceView = m_contentView;
+ }
+
+ [m_nsWindow setContentView:m_contentView];
}
QCocoaWindow::~QCocoaWindow()
{
+
}
void QCocoaWindow::setGeometry(const QRect &rect)
@@ -79,16 +93,41 @@ void QCocoaWindow::setGeometry(const QRect &rect)
NSRect bounds = NSMakeRect(rect.x(), rect.y(), rect.width(), rect.height());
[[m_nsWindow contentView]setFrameSize:bounds.size];
+
+ if (m_glContext)
+ m_glContext->update();
}
void QCocoaWindow::setVisible(bool visible)
{
- Q_UNUSED(visible);
+ if (visible) {
+ [m_nsWindow makeKeyAndOrderFront:nil];
+ } else {
+ [m_nsWindow orderOut:nil];
+ }
+}
+
+void QCocoaWindow::setWindowTitle(const QString &title)
+{
+ CFStringRef windowTitle = QCFString::toCFStringRef(title);
+ [m_nsWindow setTitle: reinterpret_cast<const NSString *>(windowTitle)];
+ CFRelease(windowTitle);
+}
+
+void QCocoaWindow::raise()
+{
+ // ### handle spaces (see Qt 4 raise_sys in qwidget_mac.mm)
+ [m_nsWindow orderFront];
+}
+
+void QCocoaWindow::lower()
+{
+ [m_nsWindow orderBack];
}
WId QCocoaWindow::winId() const
{
- return WId([m_nsWindow windowNumber]);
+ return WId(m_nsWindow);
}
NSView *QCocoaWindow::contentView() const
@@ -96,9 +135,15 @@ NSView *QCocoaWindow::contentView() const
return [m_nsWindow contentView];
}
-void QCocoaWindow::setContentView(NSView *contentView)
+NSView *QCocoaWindow::windowSurfaceView() const
+{
+ return m_windowSurfaceView;
+}
+
+void QCocoaWindow::windowDidMove()
{
- [m_nsWindow setContentView:contentView];
+ if (m_glContext)
+ m_glContext->update();
}
void QCocoaWindow::windowDidResize()
@@ -106,5 +151,25 @@ void QCocoaWindow::windowDidResize()
//jlind: XXX This isn't ideal. Eventdispatcher does not run when resizing...
NSRect rect = [[m_nsWindow contentView]frame];
QRect geo(rect.origin.x,rect.origin.y,rect.size.width,rect.size.height);
- QWindowSystemInterface::handleGeometryChange(widget(),geo);
+ QWindowSystemInterface::handleGeometryChange(window(),geo);
+
+ if (m_glContext)
+ m_glContext->update();
+}
+
+QPlatformGLSurface *QCocoaWindow::createGLSurface() const
+{
+ Q_ASSERT(window()->surfaceType() == QWindow::OpenGLSurface);
+ return new QCocoaGLSurface(window()->glFormat(), window());
}
+
+void QCocoaWindow::setCurrentContext(QCocoaGLContext *context)
+{
+ m_glContext = context;
+}
+
+QCocoaGLContext *QCocoaWindow::currentContext() const
+{
+ return m_glContext;
+}
+
diff --git a/src/plugins/platforms/cocoa/qcocoawindowsurface.h b/src/plugins/platforms/cocoa/qcocoawindowsurface.h
index 95eea2b7ea..01c6ccde3e 100644
--- a/src/plugins/platforms/cocoa/qcocoawindowsurface.h
+++ b/src/plugins/platforms/cocoa/qcocoawindowsurface.h
@@ -54,18 +54,16 @@ QT_BEGIN_NAMESPACE
class QCocoaWindowSurface : public QWindowSurface
{
public:
- QCocoaWindowSurface(QWidget *window, WId wid);
+ QCocoaWindowSurface(QWindow *window, WId wid);
~QCocoaWindowSurface();
QPaintDevice *paintDevice();
- void flush(QWidget *widget, const QRegion &region, const QPoint &offset);
+ void flush(QWindow *widget, const QRegion &region, const QPoint &offset);
void resize (const QSize &size);
private:
-
QCocoaWindow *m_cocoaWindow;
QImage *m_image;
- QNSView *m_contentView;
};
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/qcocoawindowsurface.mm b/src/plugins/platforms/cocoa/qcocoawindowsurface.mm
index 16bb327196..9a4b42b31e 100644
--- a/src/plugins/platforms/cocoa/qcocoawindowsurface.mm
+++ b/src/plugins/platforms/cocoa/qcocoawindowsurface.mm
@@ -42,7 +42,6 @@
#include "qcocoawindowsurface.h"
#include <QtCore/qdebug.h>
-
#include <QtGui/QPainter>
QT_BEGIN_NAMESPACE
@@ -56,17 +55,16 @@ QRect flipedRect(const QRect &sourceRect,int height)
return flippedRect;
}
-QCocoaWindowSurface::QCocoaWindowSurface(QWidget *window, WId wId)
+QCocoaWindowSurface::QCocoaWindowSurface(QWindow *window, WId wId)
: QWindowSurface(window)
{
- m_cocoaWindow = static_cast<QCocoaWindow *>(window->platformWindow());
+ Q_UNUSED(wId);
+ m_cocoaWindow = static_cast<QCocoaWindow *>(window->handle());
const QRect geo = window->geometry();
NSRect rect = NSMakeRect(geo.x(),geo.y(),geo.width(),geo.height());
- m_contentView = [[QNSView alloc] initWithWidget:window];
- m_cocoaWindow->setContentView(m_contentView);
- m_image = new QImage(window->size(),QImage::Format_ARGB32);
+ m_image = new QImage(window->geometry().size(),QImage::Format_ARGB32);
}
QCocoaWindowSurface::~QCocoaWindowSurface()
@@ -79,7 +77,7 @@ QPaintDevice *QCocoaWindowSurface::paintDevice()
return m_image;
}
-void QCocoaWindowSurface::flush(QWidget *widget, const QRegion &region, const QPoint &offset)
+void QCocoaWindowSurface::flush(QWindow *widget, const QRegion &region, const QPoint &offset)
{
Q_UNUSED(widget);
Q_UNUSED(offset);
@@ -87,7 +85,7 @@ void QCocoaWindowSurface::flush(QWidget *widget, const QRegion &region, const QP
QRect geo = region.boundingRect();
NSRect rect = NSMakeRect(geo.x(), geo.y(), geo.width(), geo.height());
- [m_contentView displayRect:rect];
+ [m_cocoaWindow->m_windowSurfaceView displayRect:rect];
}
void QCocoaWindowSurface::resize(const QSize &size)
@@ -96,8 +94,7 @@ void QCocoaWindowSurface::resize(const QSize &size)
delete m_image;
m_image = new QImage(size,QImage::Format_ARGB32_Premultiplied);
NSSize newSize = NSMakeSize(size.width(),size.height());
- [m_contentView setImage:m_image];
-
+ [m_cocoaWindow->m_windowSurfaceView setImage:m_image];
}
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/qnsview.h b/src/plugins/platforms/cocoa/qnsview.h
index 69a11134bd..0b96928d5b 100644
--- a/src/plugins/platforms/cocoa/qnsview.h
+++ b/src/plugins/platforms/cocoa/qnsview.h
@@ -48,17 +48,18 @@
@interface QNSView : NSView {
CGImageRef m_cgImage;
- QWidget *m_widget;
+ QWindow *m_window;
Qt::MouseButtons m_buttons;
}
- (id)init;
-- (id)initWithWidget:(QWidget *)widget;
+- (id)initWithQWindow:(QWindow *)window;
- (void)setImage:(QImage *)image;
- (void)drawRect:(NSRect)dirtyRect;
- (BOOL)isFlipped;
+- (BOOL)acceptsFirstResponder;
- (void)handleMouseEvent:(NSEvent *)theEvent;
- (void)mouseDown:(NSEvent *)theEvent;
@@ -74,6 +75,12 @@
- (void)otherMouseDragged:(NSEvent *)theEvent;
- (void)otherMouseUp:(NSEvent *)theEvent;
+- (int) convertKeyCode : (QChar)keyCode;
+- (Qt::KeyboardModifiers) convertKeyModifiers : (ulong)modifierFlags;
+- (void)handleKeyEvent:(NSEvent *)theEvent eventType:(int)eventType;
+- (void)keyDown:(NSEvent *)theEvent;
+- (void)keyUp:(NSEvent *)theEvent;
+
@end
#endif //QNSVIEW_H
diff --git a/src/plugins/platforms/cocoa/qnsview.mm b/src/plugins/platforms/cocoa/qnsview.mm
index 037cbdb5d6..5d7fd05b1f 100644
--- a/src/plugins/platforms/cocoa/qnsview.mm
+++ b/src/plugins/platforms/cocoa/qnsview.mm
@@ -52,16 +52,16 @@
self = [super init];
if (self) {
m_cgImage = 0;
- m_widget = 0;
+ m_window = 0;
m_buttons = Qt::NoButton;
}
return self;
}
-- (id)initWithWidget:(QWidget *)widget {
+- (id)initWithQWindow:(QWindow *)widget {
self = [self init];
if (self) {
- m_widget = widget;
+ m_window = widget;
}
return self;
}
@@ -130,48 +130,55 @@
return YES;
}
+- (BOOL)acceptsFirstResponder
+{
+ return YES;
+}
+
- (void)handleMouseEvent:(NSEvent *)theEvent;
{
- NSPoint point = [self convertPoint: [theEvent locationInWindow] fromView: nil];
- QPoint qt_localPoint(point.x,point.y);
+ NSPoint windowPoint = [self convertPoint: [theEvent locationInWindow] fromView: nil];
+ QPoint qt_windowPoint(windowPoint.x, windowPoint.y);
NSTimeInterval timestamp = [theEvent timestamp];
ulong qt_timestamp = timestamp * 1000;
- QWindowSystemInterface::handleMouseEvent(m_widget,qt_timestamp,qt_localPoint,QPoint(),m_buttons);
+ // ### Should the points be windowPoint and screenPoint?
+ QWindowSystemInterface::handleMouseEvent(m_window, qt_timestamp, qt_windowPoint, qt_windowPoint, m_buttons);
+}
+- (void)mouseDown:(NSEvent *)theEvent
+{
+ m_buttons |= Qt::LeftButton;
+ [self handleMouseEvent:theEvent];
+}
+
+- (void)mouseDragged:(NSEvent *)theEvent
+{
+ if (!(m_buttons & Qt::LeftButton))
+ qWarning("Internal Mousebutton tracking invalid(missing Qt::LeftButton");
+ [self handleMouseEvent:theEvent];
+}
+
+- (void)mouseUp:(NSEvent *)theEvent
+{
+ m_buttons &= QFlag(~int(Qt::LeftButton));
+ [self handleMouseEvent:theEvent];
}
- - (void)mouseDown:(NSEvent *)theEvent
- {
- m_buttons |= Qt::LeftButton;
- [self handleMouseEvent:theEvent];
- }
- - (void)mouseDragged:(NSEvent *)theEvent
- {
- if (!(m_buttons & Qt::LeftButton))
- qWarning("Internal Mousebutton tracking invalid(missing Qt::LeftButton");
- [self handleMouseEvent:theEvent];
- }
- - (void)mouseUp:(NSEvent *)theEvent
- {
- m_buttons &= QFlag(~int(Qt::LeftButton));
- [self handleMouseEvent:theEvent];
- }
- (void)mouseMoved:(NSEvent *)theEvent
{
- qDebug() << "mouseMove";
[self handleMouseEvent:theEvent];
}
- (void)mouseEntered:(NSEvent *)theEvent
{
Q_UNUSED(theEvent);
- QWindowSystemInterface::handleEnterEvent(m_widget);
+ QWindowSystemInterface::handleEnterEvent(m_window);
}
- (void)mouseExited:(NSEvent *)theEvent
{
Q_UNUSED(theEvent);
- QWindowSystemInterface::handleLeaveEvent(m_widget);
+ QWindowSystemInterface::handleLeaveEvent(m_window);
}
- (void)rightMouseDown:(NSEvent *)theEvent
{
@@ -206,6 +213,84 @@
[self handleMouseEvent:theEvent];
}
+- (int) convertKeyCode : (QChar)keyChar
+{
+ if (keyChar.isLower())
+ keyChar = keyChar.toUpper();
+ int keyCode = keyChar.unicode();
+
+ int qtKeyCode = Qt::Key(keyCode); // default case, overrides below
+ switch (keyCode) {
+ case NSEnterCharacter: qtKeyCode = Qt::Key_Enter; break;
+ case NSBackspaceCharacter: qtKeyCode = Qt::Key_Backspace; break;
+ case NSTabCharacter: qtKeyCode = Qt::Key_Tab; break;
+ case NSNewlineCharacter: qtKeyCode = Qt::Key_Return; break;
+ case NSCarriageReturnCharacter: qtKeyCode = Qt::Key_Return; break;
+ case NSBackTabCharacter: qtKeyCode = Qt::Key_Backtab; break;
+ case 27 : qtKeyCode = Qt::Key_Escape; break;
+ case NSDeleteCharacter : qtKeyCode = Qt::Key_Backspace; break; // Cocoa sends us delete when pressing backspace.
+ case NSUpArrowFunctionKey: qtKeyCode = Qt::Key_Up; break;
+ case NSDownArrowFunctionKey: qtKeyCode = Qt::Key_Down; break;
+ case NSLeftArrowFunctionKey: qtKeyCode = Qt::Key_Left; break;
+ case NSRightArrowFunctionKey: qtKeyCode = Qt::Key_Right; break;
+ case NSInsertFunctionKey: qtKeyCode = Qt::Key_Insert; break;
+ case NSDeleteFunctionKey: qtKeyCode = Qt::Key_Delete; break;
+ case NSHomeFunctionKey: qtKeyCode = Qt::Key_Home; break;
+ case NSEndFunctionKey: qtKeyCode = Qt::Key_End; break;
+ case NSPageUpFunctionKey: qtKeyCode = Qt::Key_PageUp; break;
+ case NSPageDownFunctionKey: qtKeyCode = Qt::Key_PageDown; break;
+ case NSPrintScreenFunctionKey: qtKeyCode = Qt::Key_Print; break;
+ case NSScrollLockFunctionKey: qtKeyCode = Qt::Key_ScrollLock; break;
+ case NSPauseFunctionKey: qtKeyCode = Qt::Key_Pause; break;
+ case NSSysReqFunctionKey: qtKeyCode = Qt::Key_SysReq; break;
+ case NSMenuFunctionKey: qtKeyCode = Qt::Key_Menu; break;
+ case NSHelpFunctionKey: qtKeyCode = Qt::Key_Help; break;
+ default : break;
+ }
+
+ // handle all function keys (F1-F35)
+ if (keyCode >= NSF1FunctionKey && keyCode <= NSF35FunctionKey)
+ qtKeyCode = Qt::Key_F1 + (keyCode - NSF1FunctionKey);
+ return qtKeyCode;
+}
+
+- (Qt::KeyboardModifiers) convertKeyModifiers : (ulong)modifierFlags
+{
+ Qt::KeyboardModifiers qtMods =Qt::NoModifier;
+ if (modifierFlags & NSShiftKeyMask)
+ qtMods |= Qt::ShiftModifier;
+ if (modifierFlags & NSControlKeyMask)
+ qtMods |= Qt::MetaModifier;
+ if (modifierFlags & NSAlternateKeyMask)
+ qtMods |= Qt::AltModifier;
+ if (modifierFlags & NSCommandKeyMask)
+ qtMods |= Qt::ControlModifier;
+ if (modifierFlags & NSNumericPadKeyMask)
+ qtMods |= Qt::KeypadModifier;
+ return qtMods;
+}
+
+- (void)handleKeyEvent:(NSEvent *)theEvent eventType:(int)eventType
+{
+ NSTimeInterval timestamp = [theEvent timestamp];
+ ulong qt_timestamp = timestamp * 1000;
+ QString characters = QString::fromUtf8([[theEvent characters] UTF8String]);
+ Qt::KeyboardModifiers modifiers = [self convertKeyModifiers : [theEvent modifierFlags]];
+ QChar ch([[theEvent charactersIgnoringModifiers] characterAtIndex:0]);
+ int keyCode = [self convertKeyCode : ch];
+
+ QWindowSystemInterface::handleKeyEvent(m_window, qt_timestamp, QEvent::Type(eventType), keyCode, modifiers, characters);
+}
+
+- (void)keyDown:(NSEvent *)theEvent
+{
+ [self handleKeyEvent : theEvent eventType :int(QEvent::KeyPress)];
+}
+
+- (void)keyUp:(NSEvent *)theEvent
+{
+ [self handleKeyEvent : theEvent eventType :int(QEvent::KeyRelease)];
+}
@end
diff --git a/src/plugins/platforms/cocoa/qnswindowdelegate.h b/src/plugins/platforms/cocoa/qnswindowdelegate.h
index cf296c4a8b..5cd226a71d 100644
--- a/src/plugins/platforms/cocoa/qnswindowdelegate.h
+++ b/src/plugins/platforms/cocoa/qnswindowdelegate.h
@@ -46,6 +46,26 @@
#include "qcocoawindow.h"
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_5
+@protocol NSWindowDelegate <NSObject>
+//- (NSSize)windowWillResize:(NSWindow *)window toSize:(NSSize)proposedFrameSize;
+//- (void)windowDidMiniaturize:(NSNotification*)notification;
+- (void)windowDidResize:(NSNotification *)notification;
+- (void)windowWillClose:(NSNotification *)notification;
+//- (NSRect)windowWillUseStandardFrame:(NSWindow *)window defaultFrame:(NSRect)defaultFrame;
+- (void)windowDidMove:(NSNotification *)notification;
+//- (BOOL)windowShouldClose:(id)window;
+//- (void)windowDidDeminiaturize:(NSNotification *)notification;
+//- (void)windowDidBecomeMain:(NSNotification*)notification;
+//- (void)windowDidResignMain:(NSNotification*)notification;
+//- (void)windowDidBecomeKey:(NSNotification*)notification;
+//- (void)windowDidResignKey:(NSNotification*)notification;
+//- (BOOL)window:(NSWindow *)window shouldPopUpDocumentPathMenu:(NSMenu *)menu;
+//- (BOOL)window:(NSWindow *)window shouldDragDocumentWithEvent:(NSEvent *)event from:(NSPoint)dragImageLocation withPasteboard:(NSPasteboard *)pasteboard;
+//- (BOOL)windowShouldZoom:(NSWindow *)window toFrame:(NSRect)newFrame;
+@end
+#endif
+
@interface QNSWindowDelegate : NSObject <NSWindowDelegate>
{
QCocoaWindow *m_cocoaWindow;
@@ -54,6 +74,7 @@
- (id)initWithQCocoaWindow: (QCocoaWindow *) cocoaWindow;
- (void)windowDidResize:(NSNotification *)notification;
+- (void)windowDidMove:(NSNotification *)notification;
- (void)windowWillClose:(NSNotification *)notification;
@end
diff --git a/src/plugins/platforms/cocoa/qnswindowdelegate.mm b/src/plugins/platforms/cocoa/qnswindowdelegate.mm
index 887b08f6d2..6521db5cf7 100644
--- a/src/plugins/platforms/cocoa/qnswindowdelegate.mm
+++ b/src/plugins/platforms/cocoa/qnswindowdelegate.mm
@@ -64,10 +64,18 @@
}
}
+- (void)windowDidMove:(NSNotification *)notification
+{
+ Q_UNUSED(notification);
+ if (m_cocoaWindow) {
+ m_cocoaWindow->windowDidMove();
+ }
+}
+
- (void)windowWillClose:(NSNotification *)notification
{
Q_UNUSED(notification);
- QWindowSystemInterface::handleCloseEvent(m_cocoaWindow->widget());
+ QWindowSystemInterface::handleCloseEvent(m_cocoaWindow->window());
}
@end