From: Morten Johan Sorvig Date: Thu, 12 Jan 2012 07:14:38 +0000 (+0100) Subject: Delete src/widgets/platforms/mac X-Git-Tag: qt-v5.0.0-alpha1~1767 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=bc02ef882ba013e996380b625a15e95a2e0168a2;hp=82340ea5cd148253eb07877468bf3c8873f90e56;p=profile%2Fivi%2Fqtbase.git Delete src/widgets/platforms/mac This looks like the mac port but isn't any more, remove it to prevent confusion. Change-Id: I498f536d77d1a3c53e687f696ca6992539a1a90b Reviewed-by: Morten Johan Sørvig --- diff --git a/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm b/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm index a513237..0cf4666 100644 --- a/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm +++ b/src/plugins/platforms/cocoa/qcocoafiledialoghelper.mm @@ -51,8 +51,8 @@ #include #include #include -#include -#include +#include "qt_mac_p.h" +#include "qcocoahelpers.h" #include #include #include diff --git a/src/plugins/platforms/cocoa/qcocoahelpers.h b/src/plugins/platforms/cocoa/qcocoahelpers.h index 61076aa..1cfa846 100644 --- a/src/plugins/platforms/cocoa/qcocoahelpers.h +++ b/src/plugins/platforms/cocoa/qcocoahelpers.h @@ -52,8 +52,7 @@ // // We mean it. // - -#include +#include "qt_mac_p.h" #include #include diff --git a/src/widgets/platforms/mac/qmacdefines_mac.h b/src/plugins/platforms/cocoa/qmacdefines_mac.h similarity index 100% rename from src/widgets/platforms/mac/qmacdefines_mac.h rename to src/plugins/platforms/cocoa/qmacdefines_mac.h diff --git a/src/plugins/platforms/cocoa/qmenu_mac.h b/src/plugins/platforms/cocoa/qmenu_mac.h index 1e72b2f..0500d6c 100644 --- a/src/plugins/platforms/cocoa/qmenu_mac.h +++ b/src/plugins/platforms/cocoa/qmenu_mac.h @@ -39,7 +39,7 @@ ** ****************************************************************************/ -#include +#include "qt_mac_p.h" #include #include #include diff --git a/src/widgets/platforms/mac/qt_mac_p.h b/src/plugins/platforms/cocoa/qt_mac_p.h similarity index 100% rename from src/widgets/platforms/mac/qt_mac_p.h rename to src/plugins/platforms/cocoa/qt_mac_p.h diff --git a/src/widgets/platforms/mac/qapplication_mac.mm b/src/widgets/platforms/mac/qapplication_mac.mm deleted file mode 100644 index 13fb6fd..0000000 --- a/src/widgets/platforms/mac/qapplication_mac.mm +++ /dev/null @@ -1,1878 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include - -#include "qapplication.h" -#include "qbitarray.h" -#include "qclipboard.h" -#include "qcursor.h" -#include "qdatastream.h" -#include "qdatetime.h" -#include "qdesktopwidget.h" -#include "qdockwidget.h" -#include "qevent.h" -#include "qhash.h" -#include "qlayout.h" -#include "qmenubar.h" -#include "qmessagebox.h" -#include "qmime.h" -#include "qpixmapcache.h" -#include "qpointer.h" -#include "qsessionmanager.h" -#include "qsettings.h" -#include "qsocketnotifier.h" -#include "qstyle.h" -#include "qstylefactory.h" -#include "qtextcodec.h" -#include "qtoolbar.h" -#include "qvariant.h" -#include "qwidget.h" -#include "qcolormap.h" -#include "qdir.h" -#include "qdebug.h" -#include "qtimer.h" -#include "qurl.h" -#include "private/qmacinputcontext_p.h" -#include "private/qpaintengine_mac_p.h" -#include "private/qcursor_p.h" -#include "private/qapplication_p.h" -#include "private/qcolor_p.h" -#include "private/qwidget_p.h" -#include "private/qkeymapper_p.h" -#include "private/qeventdispatcher_mac_p.h" -#include "private/qeventdispatcher_unix_p.h" -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#ifndef QT_NO_ACCESSIBILITY -# include "qaccessible.h" -#endif - -#ifndef QT_NO_THREAD -# include "qmutex.h" -#endif - -#include -#include -#include -#include - -/***************************************************************************** - QApplication debug facilities - *****************************************************************************/ -//#define DEBUG_EVENTS //like EventDebug but more specific to Qt -//#define DEBUG_DROPPED_EVENTS -//#define DEBUG_MOUSE_MAPS -//#define DEBUG_MODAL_EVENTS -//#define DEBUG_PLATFORM_SETTINGS - -#define QMAC_SPEAK_TO_ME -#ifdef QMAC_SPEAK_TO_ME -#include "qregexp.h" -#endif - -#ifndef kThemeBrushAlternatePrimaryHighlightColor -#define kThemeBrushAlternatePrimaryHighlightColor -5 -#endif - -#define kCMDeviceUnregisteredNotification CFSTR("CMDeviceUnregisteredNotification") -#define kCMDefaultDeviceNotification CFSTR("CMDefaultDeviceNotification") -#define kCMDeviceProfilesNotification CFSTR("CMDeviceProfilesNotification") -#define kCMDefaultDeviceProfileNotification CFSTR("CMDefaultDeviceProfileNotification") - -QT_BEGIN_NAMESPACE - -//for qt_mac.h -QPaintDevice *qt_mac_safe_pdev = 0; -QList *QMacWindowChangeEvent::change_events = 0; -QPointer topLevelAt_cache = 0; - -/***************************************************************************** - Internal variables and functions - *****************************************************************************/ -static struct { - bool use_qt_time_limit; - QPointer last_widget; - int last_x, last_y; - int last_modifiers, last_button; - EventTime last_time; -} qt_mac_dblclick = { false, 0, -1, -1, 0, 0, -2 }; - -static bool app_do_modal = false; // modal mode -extern QWidgetList *qt_modal_stack; // stack of modal widgets -extern bool qt_tab_all_widgets; // from qapplication.cpp -bool qt_scrollbar_jump_to_pos = false; -static bool qt_mac_collapse_on_dblclick = true; -extern int qt_antialiasing_threshold; // from qapplication.cpp -QWidget * qt_button_down; // widget got last button-down -QPointer qt_last_mouse_receiver; -#if defined(QT_DEBUG) -static bool appNoGrab = false; // mouse/keyboard grabbing -#endif -static AEEventHandlerUPP app_proc_ae_handlerUPP = NULL; -static EventHandlerRef tablet_proximity_handler = 0; -static EventHandlerUPP tablet_proximity_UPP = 0; -bool QApplicationPrivate::native_modal_dialog_active; - -Q_GUI_EXPORT bool qt_applefontsmoothing_enabled; - -/***************************************************************************** - External functions - *****************************************************************************/ -extern void qt_mac_beep(); //qsound_mac.mm -extern Qt::KeyboardModifiers qt_mac_get_modifiers(int keys); //qkeymapper_mac.cpp -extern bool qt_mac_can_clickThrough(const QWidget *); //qwidget_mac.cpp -extern bool qt_mac_is_macdrawer(const QWidget *); //qwidget_mac.cpp -extern OSWindowRef qt_mac_window_for(const QWidget*); //qwidget_mac.cpp -extern QWidget *qt_mac_find_window(OSWindowRef); //qwidget_mac.cpp -extern void qt_mac_set_cursor(const QCursor *); //qcursor_mac.cpp -extern bool qt_mac_is_macsheet(const QWidget *); //qwidget_mac.cpp -extern QString qt_mac_from_pascal_string(const Str255); //qglobal.cpp -extern void qt_mac_command_set_enabled(MenuRef, UInt32, bool); //qmenu_mac.cpp -extern bool qt_sendSpontaneousEvent(QObject *obj, QEvent *event); // qapplication.cpp -extern void qt_mac_update_cursor(); // qcursor_mac.mm - -// Forward Decls -void onApplicationWindowChangedActivation( QWidget*widget, bool activated ); -void onApplicationChangedActivation( bool activated ); - -static void qt_mac_read_fontsmoothing_settings() -{ - qt_applefontsmoothing_enabled = true; - int w = 10, h = 10; - QImage image(w, h, QImage::Format_RGB32); - image.fill(0xffffffff); - QPainter p(&image); - p.drawText(0, h, "X\\"); - p.end(); - - const int *bits = (const int *) ((const QImage &) image).bits(); - int bpl = image.bytesPerLine() / 4; - for (int y=0; y= MAC_OS_X_VERSION_10_5) - const bool resized = flags & kCGDisplayDesktopShapeChangedFlag; -#else - Q_UNUSED(flags); - const bool resized = true; -#endif - if (resized && qApp) { - if (QDesktopWidget *dw = qApp->desktop()) { - QResizeEvent *re = new QResizeEvent(dw->size(), dw->size()); - QApplication::postEvent(dw, re); - QCoreGraphicsPaintEngine::cleanUpMacColorSpaces(); - } - } -} - -#ifdef DEBUG_PLATFORM_SETTINGS -static void qt_mac_debug_palette(const QPalette &pal, const QPalette &pal2, const QString &where) -{ - const char *const groups[] = {"Active", "Disabled", "Inactive" }; - const char *const roles[] = { "WindowText", "Button", "Light", "Midlight", "Dark", "Mid", - "Text", "BrightText", "ButtonText", "Base", "Window", "Shadow", - "Highlight", "HighlightedText", "Link", "LinkVisited" }; - if (!where.isNull()) - qDebug("qt-internal: %s", where.toLatin1().constData()); - for(int grp = 0; grp < QPalette::NColorGroups; grp++) { - for(int role = 0; role < QPalette::NColorRoles; role++) { - QBrush b = pal.brush((QPalette::ColorGroup)grp, (QPalette::ColorRole)role); - QPixmap pm = b.texture(); - qDebug(" %s::%s %d::%d::%d [%p]%s", groups[grp], roles[role], b.color().red(), - b.color().green(), b.color().blue(), pm.isNull() ? 0 : &pm, - pal2.brush((QPalette::ColorGroup)grp, (QPalette::ColorRole)role) != b ? " (*)" : ""); - } - } - -} -#else -#define qt_mac_debug_palette(x, y, z) -#endif - -//raise a notification -void qt_mac_send_notification() -{ - QMacCocoaAutoReleasePool pool; - [[NSApplication sharedApplication] requestUserAttention:NSInformationalRequest]; -} - -void qt_mac_cancel_notification() -{ - QMacCocoaAutoReleasePool pool; - [[NSApplication sharedApplication] cancelUserAttentionRequest:NSInformationalRequest]; -} - -void qt_mac_set_app_icon(const QPixmap &pixmap) -{ - QMacCocoaAutoReleasePool pool; - NSImage *image = NULL; - if (pixmap.isNull()) { - // Get Application icon from bundle - image = [[NSImage imageNamed:@"NSApplicationIcon"] retain]; // released below - } else { - image = static_cast(qt_mac_create_nsimage(pixmap)); - } - - [NSApp setApplicationIconImage:image]; - [image release]; -} - -Q_GUI_EXPORT void qt_mac_set_press_and_hold_context(bool b) -{ - Q_UNUSED(b); - qWarning("qt_mac_set_press_and_hold_context: This functionality is no longer available"); -} - -bool qt_nograb() // application no-grab option -{ -#if defined(QT_DEBUG) - return appNoGrab; -#else - return false; -#endif -} - -void qt_mac_update_os_settings() -{ - if (!qApp) - return; - if (!QApplication::startingUp()) { - static bool needToPolish = true; - if (needToPolish) { - QApplication::style()->polish(qApp); - needToPolish = false; - } - } - //focus mode - /* First worked as of 10.2.3 */ - QSettings appleSettings(QLatin1String("apple.com")); - QVariant appleValue = appleSettings.value(QLatin1String("AppleKeyboardUIMode"), 0); - qt_tab_all_widgets = (appleValue.toInt() & 0x2); - //paging mode - /* First worked as of 10.2.3 */ - appleValue = appleSettings.value(QLatin1String("AppleScrollerPagingBehavior"), false); - qt_scrollbar_jump_to_pos = appleValue.toBool(); - //collapse - /* First worked as of 10.3.3 */ - appleValue = appleSettings.value(QLatin1String("AppleMiniaturizeOnDoubleClick"), true); - qt_mac_collapse_on_dblclick = appleValue.toBool(); - - // Anti-aliasing threshold - appleValue = appleSettings.value(QLatin1String("AppleAntiAliasingThreshold")); - if (appleValue.isValid()) - qt_antialiasing_threshold = appleValue.toInt(); - -#ifdef DEBUG_PLATFORM_SETTINGS - qDebug("qt_mac_update_os_settings *********************************************************************"); -#endif - { // setup the global palette - QColor qc; - (void) QApplication::style(); // trigger creation of application style and system palettes - QPalette pal = *QApplicationPrivate::sys_pal; - - pal.setBrush( QPalette::Active, QPalette::Highlight, qcolorForTheme(kThemeBrushPrimaryHighlightColor) ); - pal.setBrush( QPalette::Inactive, QPalette::Highlight, qcolorForTheme(kThemeBrushSecondaryHighlightColor) ); - - pal.setBrush( QPalette::Disabled, QPalette::Highlight, qcolorForTheme(kThemeBrushSecondaryHighlightColor) ); - pal.setBrush( QPalette::Active, QPalette::Shadow, qcolorForTheme(kThemeBrushButtonActiveDarkShadow) ); - - pal.setBrush( QPalette::Inactive, QPalette::Shadow, qcolorForTheme(kThemeBrushButtonInactiveDarkShadow) ); - pal.setBrush( QPalette::Disabled, QPalette::Shadow, qcolorForTheme(kThemeBrushButtonInactiveDarkShadow) ); - - qc = qcolorForThemeTextColor(kThemeTextColorDialogActive); - pal.setColor(QPalette::Active, QPalette::Text, qc); - pal.setColor(QPalette::Active, QPalette::WindowText, qc); - pal.setColor(QPalette::Active, QPalette::HighlightedText, qc); - - qc = qcolorForThemeTextColor(kThemeTextColorDialogInactive); - pal.setColor(QPalette::Inactive, QPalette::Text, qc); - pal.setColor(QPalette::Inactive, QPalette::WindowText, qc); - pal.setColor(QPalette::Inactive, QPalette::HighlightedText, qc); - pal.setColor(QPalette::Disabled, QPalette::Text, qc); - pal.setColor(QPalette::Disabled, QPalette::WindowText, qc); - pal.setColor(QPalette::Disabled, QPalette::HighlightedText, qc); - pal.setBrush(QPalette::ToolTipBase, QColor(255, 255, 199)); - - if (!QApplicationPrivate::sys_pal || *QApplicationPrivate::sys_pal != pal) { - QApplicationPrivate::setSystemPalette(pal); - QApplication::setPalette(pal); - } -#ifdef DEBUG_PLATFORM_SETTINGS - qt_mac_debug_palette(pal, QApplication::palette(), "Global Palette"); -#endif - } - - QFont fnt = qfontForThemeFont(kThemeApplicationFont); -#ifdef DEBUG_PLATFORM_SETTINGS - qDebug("qt-internal: Font for Application [%s::%d::%d::%d]", - fnt.family().toLatin1().constData(), fnt.pointSize(), fnt.bold(), fnt.italic()); -#endif - if (!QApplicationPrivate::sys_font || *QApplicationPrivate::sys_font != fnt) - QApplicationPrivate::setSystemFont(fnt); - - { //setup the fonts - struct FontMap { - FontMap(const char *qc, short fk) : qt_class(qc), font_key(fk) { } - const char *const qt_class; - short font_key; - } mac_widget_fonts[] = { - FontMap("QPushButton", kThemePushButtonFont), - FontMap("QListView", kThemeViewsFont), - FontMap("QListBox", kThemeViewsFont), - FontMap("QTitleBar", kThemeWindowTitleFont), - FontMap("QMenuBar", kThemeMenuTitleFont), - FontMap("QMenu", kThemeMenuItemFont), - FontMap("QComboMenuItem", kThemeSystemFont), - FontMap("QHeaderView", kThemeSmallSystemFont), - FontMap("Q3Header", kThemeSmallSystemFont), - FontMap("QTipLabel", kThemeSmallSystemFont), - FontMap("QLabel", kThemeSystemFont), - FontMap("QToolButton", kThemeSmallSystemFont), - FontMap("QMenuItem", kThemeMenuItemFont), // It doesn't exist, but its unique. - FontMap("QComboLineEdit", kThemeViewsFont), // It doesn't exist, but its unique. - FontMap("QSmallFont", kThemeSmallSystemFont), // It doesn't exist, but its unique. - FontMap("QMiniFont", kThemeMiniSystemFont), // It doesn't exist, but its unique. - FontMap(0, 0) }; - for(int i = 0; mac_widget_fonts[i].qt_class; i++) { - QFont fnt = qfontForThemeFont(mac_widget_fonts[i].font_key); - bool set_font = true; - FontHash *hash = qt_app_fonts_hash(); - if (!hash->isEmpty()) { - FontHash::const_iterator it - = hash->constFind(mac_widget_fonts[i].qt_class); - if (it != hash->constEnd()) - set_font = (fnt != *it); - } - if (set_font) { - QApplication::setFont(fnt, mac_widget_fonts[i].qt_class); -#ifdef DEBUG_PLATFORM_SETTINGS - qDebug("qt-internal: Font for %s [%s::%d::%d::%d]", mac_widget_fonts[i].qt_class, - fnt.family().toLatin1().constData(), fnt.pointSize(), fnt.bold(), fnt.italic()); -#endif - } - } - } - QApplicationPrivate::initializeWidgetPaletteHash(); -#ifdef DEBUG_PLATFORM_SETTINGS - qDebug("qt_mac_update_os_settings END !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"); -#endif -} - -void QApplicationPrivate::initializeWidgetPaletteHash() -{ - { //setup the palette - struct PaletteMap { - inline PaletteMap(const char *qc, ThemeBrush a, ThemeBrush i) : - qt_class(qc), active(a), inactive(i) { } - const char *const qt_class; - ThemeBrush active, inactive; - } mac_widget_colors[] = { - PaletteMap("QToolButton", kThemeTextColorBevelButtonActive, kThemeTextColorBevelButtonInactive), - PaletteMap("QAbstractButton", kThemeTextColorPushButtonActive, kThemeTextColorPushButtonInactive), - PaletteMap("QHeaderView", kThemeTextColorPushButtonActive, kThemeTextColorPushButtonInactive), - PaletteMap("Q3Header", kThemeTextColorPushButtonActive, kThemeTextColorPushButtonInactive), - PaletteMap("QComboBox", kThemeTextColorPopupButtonActive, kThemeTextColorPopupButtonInactive), - PaletteMap("QAbstractItemView", kThemeTextColorListView, kThemeTextColorDialogInactive), - PaletteMap("QMessageBoxLabel", kThemeTextColorAlertActive, kThemeTextColorAlertInactive), - PaletteMap("QTabBar", kThemeTextColorTabFrontActive, kThemeTextColorTabFrontInactive), - PaletteMap("QLabel", kThemeTextColorPlacardActive, kThemeTextColorPlacardInactive), - PaletteMap("QGroupBox", kThemeTextColorPlacardActive, kThemeTextColorPlacardInactive), - PaletteMap("QMenu", kThemeTextColorPopupLabelActive, kThemeTextColorPopupLabelInactive), - PaletteMap("QTextEdit", 0, 0), - PaletteMap("QTextControl", 0, 0), - PaletteMap("QLineEdit", 0, 0), - PaletteMap(0, 0, 0) }; - QColor qc; - for(int i = 0; mac_widget_colors[i].qt_class; i++) { - QPalette pal; - if (mac_widget_colors[i].active != 0) { - qc = qcolorForThemeTextColor(mac_widget_colors[i].active); - pal.setColor(QPalette::Active, QPalette::Text, qc); - pal.setColor(QPalette::Active, QPalette::WindowText, qc); - pal.setColor(QPalette::Active, QPalette::HighlightedText, qc); - qc = qcolorForThemeTextColor(mac_widget_colors[i].inactive); - pal.setColor(QPalette::Inactive, QPalette::Text, qc); - pal.setColor(QPalette::Disabled, QPalette::Text, qc); - pal.setColor(QPalette::Inactive, QPalette::WindowText, qc); - pal.setColor(QPalette::Disabled, QPalette::WindowText, qc); - pal.setColor(QPalette::Inactive, QPalette::HighlightedText, qc); - pal.setColor(QPalette::Disabled, QPalette::HighlightedText, qc); - } - if (!strcmp(mac_widget_colors[i].qt_class, "QMenu")) { - qc = qcolorForThemeTextColor(kThemeTextColorMenuItemActive); - pal.setBrush(QPalette::ButtonText, qc); - qc = qcolorForThemeTextColor(kThemeTextColorMenuItemSelected); - pal.setBrush(QPalette::HighlightedText, qc); - qc = qcolorForThemeTextColor(kThemeTextColorMenuItemDisabled); - pal.setBrush(QPalette::Disabled, QPalette::Text, qc); - } else if (!strcmp(mac_widget_colors[i].qt_class, "QAbstractButton") - || !strcmp(mac_widget_colors[i].qt_class, "QHeaderView") - || !strcmp(mac_widget_colors[i].qt_class, "Q3Header")) { //special - pal.setColor(QPalette::Disabled, QPalette::ButtonText, - pal.color(QPalette::Disabled, QPalette::Text)); - pal.setColor(QPalette::Inactive, QPalette::ButtonText, - pal.color(QPalette::Inactive, QPalette::Text)); - pal.setColor(QPalette::Active, QPalette::ButtonText, - pal.color(QPalette::Active, QPalette::Text)); - } else if (!strcmp(mac_widget_colors[i].qt_class, "QAbstractItemView")) { - pal.setBrush(QPalette::Active, QPalette::Highlight, - qcolorForTheme(kThemeBrushAlternatePrimaryHighlightColor)); - qc = qcolorForThemeTextColor(kThemeTextColorMenuItemSelected); - pal.setBrush(QPalette::Active, QPalette::HighlightedText, qc); -#if 1 - pal.setBrush(QPalette::Inactive, QPalette::Text, - pal.brush(QPalette::Active, QPalette::Text)); - pal.setBrush(QPalette::Inactive, QPalette::HighlightedText, - pal.brush(QPalette::Active, QPalette::Text)); -#endif - } else if (!strcmp(mac_widget_colors[i].qt_class, "QTextEdit") - || !strcmp(mac_widget_colors[i].qt_class, "QTextControl")) { - pal.setBrush(QPalette::Inactive, QPalette::Text, - pal.brush(QPalette::Active, QPalette::Text)); - pal.setBrush(QPalette::Inactive, QPalette::HighlightedText, - pal.brush(QPalette::Active, QPalette::Text)); - } else if (!strcmp(mac_widget_colors[i].qt_class, "QLineEdit")) { - pal.setBrush(QPalette::Disabled, QPalette::Base, - pal.brush(QPalette::Active, QPalette::Base)); - } - - bool set_palette = true; - PaletteHash *phash = qt_app_palettes_hash(); - if (!phash->isEmpty()) { - PaletteHash::const_iterator it - = phash->constFind(mac_widget_colors[i].qt_class); - if (it != phash->constEnd()) - set_palette = (pal != *it); - } - if (set_palette) { - QApplication::setPalette(pal, mac_widget_colors[i].qt_class); -#ifdef DEBUG_PLATFORM_SETTINGS - qt_mac_debug_palette(pal, QApplication::palette(), QLatin1String("Palette for ") + QString::fromLatin1(mac_widget_colors[i].qt_class)); -#endif - } - } - } -} - -static void qt_mac_event_release(EventRef &event) -{ - ReleaseEvent(event); - event = 0; -} - -/* sheets */ -void qt_event_request_showsheet(QWidget *w) -{ - Q_ASSERT(qt_mac_is_macsheet(w)); - [NSApp beginSheet:qt_mac_window_for(w) modalForWindow:qt_mac_window_for(w->parentWidget()) - modalDelegate:nil didEndSelector:nil contextInfo:0]; -} - -static void qt_post_window_change_event(QWidget *widget) -{ - qt_widget_private(widget)->needWindowChange = true; - QEvent *glWindowChangeEvent = new QEvent(QEvent::MacGLWindowChange); - QApplication::postEvent(widget, glWindowChangeEvent); -} - -/* - Posts updates to all child and grandchild OpenGL widgets for the given widget. -*/ -static void qt_mac_update_child_gl_widgets(QWidget *widget) -{ - // Update all OpenGL child widgets for the given widget. - QList &glWidgets = qt_widget_private(widget)->glWidgets; - QList::iterator end = glWidgets.end(); - QList::iterator it = glWidgets.begin(); - - for (;it != end; ++it) { - qt_post_window_change_event(it->widget); - } -} - -/* - Sends updates to all child and grandchild gl widgets that have updates pending. -*/ -void qt_mac_send_posted_gl_updates(QWidget *widget) -{ - QList &glWidgets = qt_widget_private(widget)->glWidgets; - QList::iterator end = glWidgets.end(); - QList::iterator it = glWidgets.begin(); - - for (;it != end; ++it) { - QWidget *glWidget = it->widget; - if (qt_widget_private(glWidget)->needWindowChange) { - QEvent glChangeEvent(QEvent::MacGLWindowChange); - QApplication::sendEvent(glWidget, &glChangeEvent); - } - } -} - -/* - Posts updates to all OpenGL widgets within the window that the given widget intersects. -*/ -static void qt_mac_update_intersected_gl_widgets(QWidget *widget) -{ - Q_UNUSED(widget); -} - -/* - Posts a kEventQtRequestWindowChange event to the main Carbon event queue. -*/ -static EventRef request_window_change_pending = 0; -Q_GUI_EXPORT void qt_event_request_window_change() -{ - if(request_window_change_pending) - return; - - CreateEvent(0, kEventClassQt, kEventQtRequestWindowChange, GetCurrentEventTime(), - kEventAttributeUserEvent, &request_window_change_pending); - PostEventToQueue(GetMainEventQueue(), request_window_change_pending, kEventPriorityHigh); -} - -/* window changing. This is a hack around Apple's missing functionality, pending the toolbox - team fix. --Sam */ -Q_GUI_EXPORT void qt_event_request_window_change(QWidget *widget) -{ - if (!widget) - return; - - // Post a kEventQtRequestWindowChange event. This event is semi-public, - // don't remove this line! - qt_event_request_window_change(); - - // Post update request on gl widgets unconditionally. - if (qt_widget_private(widget)->isGLWidget == true) { - qt_post_window_change_event(widget); - return; - } - - qt_mac_update_child_gl_widgets(widget); - qt_mac_update_intersected_gl_widgets(widget); -} - -/* activation */ -static struct { - QPointer widget; - EventRef event; - EventLoopTimerRef timer; - EventLoopTimerUPP timerUPP; -} request_activate_pending = { 0, 0, 0, 0 }; -bool qt_event_remove_activate() -{ - if (request_activate_pending.timer) { - RemoveEventLoopTimer(request_activate_pending.timer); - request_activate_pending.timer = 0; - } - if (request_activate_pending.event) - qt_mac_event_release(request_activate_pending.event); - return true; -} - -void qt_event_activate_timer_callbk(EventLoopTimerRef r, void *) -{ - EventLoopTimerRef otc = request_activate_pending.timer; - qt_event_remove_activate(); - if (r == otc && !request_activate_pending.widget.isNull()) { - const QWidget *tlw = request_activate_pending.widget->window(); - Qt::WindowType wt = tlw->windowType(); - if (tlw->isVisible() - && ((wt != Qt::Desktop && wt != Qt::Popup && wt != Qt::Tool) || tlw->isModal())) { - CreateEvent(0, kEventClassQt, kEventQtRequestActivate, GetCurrentEventTime(), - kEventAttributeUserEvent, &request_activate_pending.event); - PostEventToQueue(GetMainEventQueue(), request_activate_pending.event, kEventPriorityHigh); - } - } -} - -void qt_event_request_activate(QWidget *w) -{ - if (w == request_activate_pending.widget) - return; - - /* We put these into a timer because due to order of events being sent we need to be sure this - comes from inside of the event loop */ - qt_event_remove_activate(); - if (!request_activate_pending.timerUPP) - request_activate_pending.timerUPP = NewEventLoopTimerUPP(qt_event_activate_timer_callbk); - request_activate_pending.widget = w; - InstallEventLoopTimer(GetMainEventLoop(), 0, 0, request_activate_pending.timerUPP, 0, &request_activate_pending.timer); -} - - -/* menubars */ -void qt_event_request_menubarupdate() -{ - // Just call this. The request has the benefit that we don't call this multiple times, but - // we can optimize this. - QMenuBar::macUpdateMenuBar(); -} - - -void QApplicationPrivate::createEventDispatcher() -{ - Q_Q(QApplication); - if (q->type() != QApplication::Tty) - eventDispatcher = new QEventDispatcherMac(q); - else - eventDispatcher = new QEventDispatcherUNIX(q); -} - -/* clipboard */ -void qt_event_send_clipboard_changed() -{ -} - -/* app menu */ -static QMenu *qt_mac_dock_menu = 0; -Q_GUI_EXPORT void qt_mac_set_dock_menu(QMenu *menu) -{ - qt_mac_dock_menu = menu; - [NSApp setDockMenu:menu->macMenu()]; -} - -/* events that hold pointers to widgets, must be cleaned up like this */ -void qt_mac_event_release(QWidget *w) -{ - if (w) { - if (w == qt_mac_dock_menu) { - qt_mac_dock_menu = 0; - [NSApp setDockMenu:0]; - } - } -} - -struct QMacAppleEventTypeSpec { - AEEventClass mac_class; - AEEventID mac_id; -} app_apple_events[] = { - { kCoreEventClass, kAEQuitApplication }, - { kCoreEventClass, kAEOpenDocuments }, - { kInternetEventClass, kAEGetURL }, -}; - -static void qt_init_tablet_proximity_handler() -{ - EventTypeSpec tabletProximityEvent = { kEventClassTablet, kEventTabletProximity }; - InstallEventHandler(GetEventMonitorTarget(), tablet_proximity_UPP, - 1, &tabletProximityEvent, qApp, &tablet_proximity_handler); -} - -static void qt_release_tablet_proximity_handler() -{ - RemoveEventHandler(tablet_proximity_handler); -} - -QString QApplicationPrivate::appName() const -{ - static QString applName; - if (applName.isEmpty()) { - applName = QCoreApplicationPrivate::macMenuBarName(); - ProcessSerialNumber psn; - if (applName.isEmpty() && qt_is_gui_used && GetCurrentProcess(&psn) == noErr) { - QCFString cfstr; - CopyProcessName(&psn, &cfstr); - applName = cfstr; - } - } - return applName; -} - -void qt_release_app_proc_handler() -{ -} - -void qt_color_profile_changed(CFNotificationCenterRef, void *, CFStringRef, const void *, - CFDictionaryRef) -{ - QCoreGraphicsPaintEngine::cleanUpMacColorSpaces(); -} -/* platform specific implementations */ -void qt_init(QApplicationPrivate *priv, int) -{ - if (qt_is_gui_used) { - CGDisplayRegisterReconfigurationCallback(qt_mac_display_change_callbk, 0); - CFNotificationCenterRef center = CFNotificationCenterGetDistributedCenter(); - CFNotificationCenterAddObserver(center, qApp, qt_color_profile_changed, - kCMDeviceUnregisteredNotification, 0, - CFNotificationSuspensionBehaviorDeliverImmediately); - CFNotificationCenterAddObserver(center, qApp, qt_color_profile_changed, - kCMDefaultDeviceNotification, 0, - CFNotificationSuspensionBehaviorDeliverImmediately); - CFNotificationCenterAddObserver(center, qApp, qt_color_profile_changed, - kCMDeviceProfilesNotification, 0, - CFNotificationSuspensionBehaviorDeliverImmediately); - CFNotificationCenterAddObserver(center, qApp, qt_color_profile_changed, - kCMDefaultDeviceProfileNotification, 0, - CFNotificationSuspensionBehaviorDeliverImmediately); - ProcessSerialNumber psn; - if (GetCurrentProcess(&psn) == noErr) { - // Jambi needs to transform itself since most people aren't "used" - // to putting things in bundles, but other people may actually not - // want to tranform the process (running as a helper or something) - // so don't do that for them. This means checking both LSUIElement - // and LSBackgroundOnly. If you set them both... well, you - // shouldn't do that. - - bool forceTransform = true; - CFTypeRef value = CFBundleGetValueForInfoDictionaryKey(CFBundleGetMainBundle(), - CFSTR("LSUIElement")); - if (value) { - CFTypeID valueType = CFGetTypeID(value); - // Officially it's supposed to be a string, a boolean makes sense, so we'll check. - // A number less so, but OK. - if (valueType == CFStringGetTypeID()) - forceTransform = !(QCFString::toQString(static_cast(value)).toInt()); - else if (valueType == CFBooleanGetTypeID()) - forceTransform = !CFBooleanGetValue(static_cast(value)); - else if (valueType == CFNumberGetTypeID()) { - int valueAsInt; - CFNumberGetValue(static_cast(value), kCFNumberIntType, &valueAsInt); - forceTransform = !valueAsInt; - } - } - - if (forceTransform) { - value = CFBundleGetValueForInfoDictionaryKey(CFBundleGetMainBundle(), - CFSTR("LSBackgroundOnly")); - if (value) { - CFTypeID valueType = CFGetTypeID(value); - if (valueType == CFBooleanGetTypeID()) - forceTransform = !CFBooleanGetValue(static_cast(value)); - else if (valueType == CFStringGetTypeID()) - forceTransform = !(QCFString::toQString(static_cast(value)).toInt()); - else if (valueType == CFNumberGetTypeID()) { - int valueAsInt; - CFNumberGetValue(static_cast(value), kCFNumberIntType, &valueAsInt); - forceTransform = !valueAsInt; - } - } - } - - - if (forceTransform) { - TransformProcessType(&psn, kProcessTransformToForegroundApplication); - } - } - } - - char **argv = priv->argv; - - // Get command line params - if (int argc = priv->argc) { - int i, j = 1; - QString passed_psn; - for(i=1; i < argc; i++) { - if (argv[i] && *argv[i] != '-') { - argv[j++] = argv[i]; - continue; - } - QByteArray arg(argv[i]); -#if defined(QT_DEBUG) - if (arg == "-nograb") - appNoGrab = !appNoGrab; - else -#endif // QT_DEBUG - if (arg.left(5) == "-psn_") { - passed_psn = QString::fromLatin1(arg.mid(6)); - } else { - argv[j++] = argv[i]; - } - } - if (j < priv->argc) { - priv->argv[j] = 0; - priv->argc = j; - } - - //special hack to change working directory (for an app bundle) when running from finder - if (!passed_psn.isNull() && QDir::currentPath() == QLatin1String("/")) { - QCFType bundleURL(CFBundleCopyBundleURL(CFBundleGetMainBundle())); - QString qbundlePath = QCFString(CFURLCopyFileSystemPath(bundleURL, - kCFURLPOSIXPathStyle)); - if (qbundlePath.endsWith(QLatin1String(".app"))) - QDir::setCurrent(qbundlePath.section(QLatin1Char('/'), 0, -2)); - } - } - - QMacPasteboardMime::initialize(); - - qApp->setObjectName(priv->appName()); - if (qt_is_gui_used) { - QColormap::initialize(); - QFont::initialize(); - QCursorData::initialize(); - QCoreGraphicsPaintEngine::initialize(); -#ifndef QT_NO_ACCESSIBILITY - QAccessible::initialize(); -#endif - QMacInputContext::initialize(); - QApplicationPrivate::inputContext = new QMacInputContext; - - if (QApplication::desktopSettingsAware()) - qt_mac_update_os_settings(); - if (!app_proc_ae_handlerUPP && !QApplication::testAttribute(Qt::AA_MacPluginApplication)) { - app_proc_ae_handlerUPP = AEEventHandlerUPP(QApplicationPrivate::globalAppleEventProcessor); - for(uint i = 0; i < sizeof(app_apple_events) / sizeof(QMacAppleEventTypeSpec); ++i) { - // Install apple event handler, but avoid overwriting an already - // existing handler (it means a 3rd party application has installed one): - SRefCon refCon = 0; - AEEventHandlerUPP current_handler = NULL; - AEGetEventHandler(app_apple_events[i].mac_class, app_apple_events[i].mac_id, ¤t_handler, &refCon, false); - if (!current_handler) - AEInstallEventHandler(app_apple_events[i].mac_class, app_apple_events[i].mac_id, - app_proc_ae_handlerUPP, SRefCon(qApp), false); - } - } - - if (QApplicationPrivate::app_style) { - QEvent ev(QEvent::Style); - qt_sendSpontaneousEvent(QApplicationPrivate::app_style, &ev); - } - } - if (QApplication::desktopSettingsAware()) - QApplicationPrivate::qt_mac_apply_settings(); - - // Cocoa application delegate - NSApplication *cocoaApp = [QNSApplication sharedApplication]; - qt_redirectNSApplicationSendEvent(); - - QMacCocoaAutoReleasePool pool; - id oldDelegate = [cocoaApp delegate]; - QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) *newDelegate = [QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) sharedDelegate]; - Q_ASSERT(newDelegate); - [newDelegate setQtPrivate:priv]; - // Only do things that make sense to do once, otherwise we crash. - if (oldDelegate != newDelegate && !QApplication::testAttribute(Qt::AA_MacPluginApplication)) { - [newDelegate setReflectionDelegate:oldDelegate]; - [cocoaApp setDelegate:newDelegate]; - - QT_MANGLE_NAMESPACE(QCocoaMenuLoader) *qtMenuLoader = [[QT_MANGLE_NAMESPACE(QCocoaMenuLoader) alloc] init]; - if ([NSBundle loadNibNamed:@"qt_menu" owner:qtMenuLoader] == false) { - qFatal("Qt internal error: qt_menu.nib could not be loaded. The .nib file" - " should be placed in QtGui.framework/Versions/Current/Resources/ " - " or in the resources directory of your application bundle."); - } - - [cocoaApp setMenu:[qtMenuLoader menu]]; - [newDelegate setMenuLoader:qtMenuLoader]; - [qtMenuLoader release]; - } - // Register for Carbon tablet proximity events on the event monitor target. - // This means that we should receive proximity events even when we aren't the active application. - if (!tablet_proximity_handler) { - tablet_proximity_UPP = NewEventHandlerUPP(QApplicationPrivate::tabletProximityCallback); - qt_init_tablet_proximity_handler(); - } - priv->native_modal_dialog_active = false; - - qt_mac_read_fontsmoothing_settings(); -} - -void qt_release_apple_event_handler() -{ - if(app_proc_ae_handlerUPP) { - for(uint i = 0; i < sizeof(app_apple_events) / sizeof(QMacAppleEventTypeSpec); ++i) - AERemoveEventHandler(app_apple_events[i].mac_class, app_apple_events[i].mac_id, - app_proc_ae_handlerUPP, true); - DisposeAEEventHandlerUPP(app_proc_ae_handlerUPP); - app_proc_ae_handlerUPP = 0; - } -} - -/***************************************************************************** - qt_cleanup() - cleans up when the application is finished - *****************************************************************************/ - -void qt_cleanup() -{ - CGDisplayRemoveReconfigurationCallback(qt_mac_display_change_callbk, 0); - CFNotificationCenterRef center = CFNotificationCenterGetDistributedCenter(); - CFNotificationCenterRemoveObserver(center, qApp, kCMDeviceUnregisteredNotification, 0); - CFNotificationCenterRemoveObserver(center, qApp, kCMDefaultDeviceNotification, 0); - CFNotificationCenterRemoveObserver(center, qApp, kCMDeviceProfilesNotification, 0); - CFNotificationCenterRemoveObserver(center, qApp, kCMDefaultDeviceProfileNotification, 0); - - qt_release_apple_event_handler(); - qt_release_tablet_proximity_handler(); - if (tablet_proximity_UPP) - DisposeEventHandlerUPP(tablet_proximity_UPP); - - QPixmapCache::clear(); - if (qt_is_gui_used) { -#ifndef QT_NO_ACCESSIBILITY - QAccessible::cleanup(); -#endif - QMacInputContext::cleanup(); - QCursorData::cleanup(); - QFont::cleanup(); - QColormap::cleanup(); - if (qt_mac_safe_pdev) { - delete qt_mac_safe_pdev; - qt_mac_safe_pdev = 0; - } - extern void qt_mac_unregister_widget(); // qapplication_mac.cpp - qt_mac_unregister_widget(); - } -} - -/***************************************************************************** - Platform specific global and internal functions - *****************************************************************************/ -void qt_updated_rootinfo() -{ -} - -bool qt_wstate_iconified(WId) -{ - return false; -} - -/***************************************************************************** - Platform specific QApplication members - *****************************************************************************/ -extern QWidget * mac_mouse_grabber; -extern QWidget * mac_keyboard_grabber; - -#ifndef QT_NO_CURSOR - -/***************************************************************************** - QApplication cursor stack - *****************************************************************************/ - -void QApplication::setOverrideCursor(const QCursor &cursor) -{ - qApp->d_func()->cursor_list.prepend(cursor); - - qt_mac_update_cursor(); -} - -void QApplication::restoreOverrideCursor() -{ - if (qApp->d_func()->cursor_list.isEmpty()) - return; - qApp->d_func()->cursor_list.removeFirst(); - - qt_mac_update_cursor(); -} -#endif // QT_NO_CURSOR - -QWidget *QApplication::topLevelAt(const QPoint &p) -{ - // Use a cache to avoid iterate through the whole list of windows for all - // calls to to topLevelAt. We e.g. do this for each and every mouse - // move since we need to find the widget under mouse: - if (topLevelAt_cache && topLevelAt_cache->frameGeometry().contains(p)) - return topLevelAt_cache; - - // INVARIANT: Cache miss. Go through the list if windows instead: - QMacCocoaAutoReleasePool pool; - NSPoint cocoaPoint = flipPoint(p); - NSInteger windowCount; - NSCountWindows(&windowCount); - if (windowCount <= 0) - return 0; // There's no window to find! - - QVarLengthArray windowList(windowCount); - NSWindowList(windowCount, windowList.data()); - int firstQtWindowFound = -1; - for (int i = 0; i < windowCount; ++i) { - NSWindow *window = [NSApp windowWithWindowNumber:windowList[i]]; - if (window) { - QWidget *candidateWindow = [window QT_MANGLE_NAMESPACE(qt_qwidget)]; - if (candidateWindow && firstQtWindowFound == -1) - firstQtWindowFound = i; - - if (NSPointInRect(cocoaPoint, [window frame])) { - // Check to see if there's a hole in the window where the mask is. - // If there is, we should just continue to see if there is a window below. - if (candidateWindow && !candidateWindow->mask().isEmpty()) { - QPoint localPoint = candidateWindow->mapFromGlobal(p); - if (!candidateWindow->mask().contains(localPoint)) - continue; - else - return candidateWindow; - } else { - if (i == firstQtWindowFound) { - // The cache will only work when the window under mouse is - // top most (that is, not partially obscured by other windows. - // And we only set it if no mask is present to optimize for the common case: - topLevelAt_cache = candidateWindow; - } - return candidateWindow; - } - } - } - } - - topLevelAt_cache = 0; - return 0; -} - -/***************************************************************************** - Main event loop - *****************************************************************************/ - -bool QApplicationPrivate::modalState() -{ - return app_do_modal; -} - - -void QApplicationPrivate::enterModal_sys(QWidget *widget) -{ -#ifdef DEBUG_MODAL_EVENTS - Q_ASSERT(widget); - qDebug("Entering modal state with %s::%s::%p (%d)", widget->metaObject()->className(), widget->objectName().toLocal8Bit().constData(), - widget, qt_modal_stack ? (int)qt_modal_stack->count() : -1); -#endif - if (!qt_modal_stack) - qt_modal_stack = new QWidgetList; - - dispatchEnterLeave(0, qt_last_mouse_receiver); - qt_last_mouse_receiver = 0; - - qt_modal_stack->insert(0, widget); - if (!app_do_modal) - qt_event_request_menubarupdate(); - app_do_modal = true; - qt_button_down = 0; - - if (!qt_mac_is_macsheet(widget)) - QEventDispatcherMacPrivate::beginModalSession(widget); -} - -void QApplicationPrivate::leaveModal_sys(QWidget *widget) -{ - if (qt_modal_stack && qt_modal_stack->removeAll(widget)) { -#ifdef DEBUG_MODAL_EVENTS - qDebug("Leaving modal state with %s::%s::%p (%d)", widget->metaObject()->className(), widget->objectName().toLocal8Bit().constData(), - widget, qt_modal_stack->count()); -#endif - if (qt_modal_stack->isEmpty()) { - delete qt_modal_stack; - qt_modal_stack = 0; - QPoint p(QCursor::pos()); - app_do_modal = false; - QWidget* w = 0; - if (QWidget *grabber = QWidget::mouseGrabber()) - w = grabber; - else - w = QApplication::widgetAt(p.x(), p.y()); - dispatchEnterLeave(w, qt_last_mouse_receiver); // send synthetic enter event - qt_last_mouse_receiver = w; - } - if (!qt_mac_is_macsheet(widget)) - QEventDispatcherMacPrivate::endModalSession(widget); - } -#ifdef DEBUG_MODAL_EVENTS - else qDebug("Failure to remove %s::%s::%p -- %p", widget->metaObject()->className(), widget->objectName().toLocal8Bit().constData(), widget, qt_modal_stack); -#endif - app_do_modal = (qt_modal_stack != 0); - if (!app_do_modal) - qt_event_request_menubarupdate(); -} - -QWidget *QApplicationPrivate::tryModalHelper_sys(QWidget *top) -{ - return top; -} - - -OSStatus QApplicationPrivate::tabletProximityCallback(EventHandlerCallRef, EventRef carbonEvent, - void *) -{ - OSType eventClass = GetEventClass(carbonEvent); - UInt32 eventKind = GetEventKind(carbonEvent); - if (eventClass != kEventClassTablet || eventKind != kEventTabletProximity) - return eventNotHandledErr; - - // Get the current point of the device and its unique ID. - ::TabletProximityRec proxRec; - GetEventParameter(carbonEvent, kEventParamTabletProximityRec, typeTabletProximityRec, 0, - sizeof(proxRec), 0, &proxRec); - qt_dispatchTabletProximityEvent(proxRec); - return noErr; -} - -OSStatus -QApplicationPrivate::globalEventProcessor(EventHandlerCallRef er, EventRef event, void *data) -{ - Q_UNUSED(er); - Q_UNUSED(event); - Q_UNUSED(data); - return eventNotHandledErr; -} - -void QApplicationPrivate::qt_initAfterNSAppStarted() -{ - setupAppleEvents(); - qt_mac_update_cursor(); -} - -void QApplicationPrivate::setupAppleEvents() -{ - // This function is called from the event dispatcher when NSApplication has - // finished initialization, which appears to be just after [NSApplication run] has - // started to execute. By setting up our apple events handlers this late, we override - // the ones set up by NSApplication. - - // If Qt is used as a plugin, we let the 3rd party application handle events - // like quit and open file events. Otherwise, if we install our own handlers, we - // easily end up breaking functionallity the 3rd party application depend on: - if (QApplication::testAttribute(Qt::AA_MacPluginApplication)) - return; - - QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) *newDelegate = [QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) sharedDelegate]; - NSAppleEventManager *eventManager = [NSAppleEventManager sharedAppleEventManager]; - [eventManager setEventHandler:newDelegate andSelector:@selector(appleEventQuit:withReplyEvent:) - forEventClass:kCoreEventClass andEventID:kAEQuitApplication]; - [eventManager setEventHandler:newDelegate andSelector:@selector(getUrl:withReplyEvent:) - forEventClass:kInternetEventClass andEventID:kAEGetURL]; -} - -// In Carbon this is your one stop for apple events. -// In Cocoa, it ISN'T. This is the catch-all Apple Event handler that exists -// for the time between instantiating the NSApplication, but before the -// NSApplication has installed it's OWN Apple Event handler. When Cocoa has -// that set up, we remove this. So, if you are debugging problems, you likely -// want to check out QCocoaApplicationDelegate instead. -OSStatus QApplicationPrivate::globalAppleEventProcessor(const AppleEvent *ae, AppleEvent *, long handlerRefcon) -{ - QApplication *app = (QApplication *)handlerRefcon; - bool handled_event=false; - OSType aeID=typeWildCard, aeClass=typeWildCard; - AEGetAttributePtr(ae, keyEventClassAttr, typeType, 0, &aeClass, sizeof(aeClass), 0); - AEGetAttributePtr(ae, keyEventIDAttr, typeType, 0, &aeID, sizeof(aeID), 0); - if(aeClass == kCoreEventClass) { - switch(aeID) { - case kAEQuitApplication: { - extern bool qt_mac_quit_menu_item_enabled; // qmenu_mac.cpp - if (qt_mac_quit_menu_item_enabled) { - QCloseEvent ev; - QApplication::sendSpontaneousEvent(app, &ev); - if(ev.isAccepted()) { - handled_event = true; - app->quit(); - } - } else { - QApplication::beep(); // Sorry, you can't quit right now. - } - break; } - case kAEOpenDocuments: { - AEDescList docs; - if(AEGetParamDesc(ae, keyDirectObject, typeAEList, &docs) == noErr) { - long cnt = 0; - AECountItems(&docs, &cnt); - UInt8 *str_buffer = NULL; - for(int i = 0; i < cnt; i++) { - FSRef ref; - if(AEGetNthPtr(&docs, i+1, typeFSRef, 0, 0, &ref, sizeof(ref), 0) != noErr) - continue; - if(!str_buffer) - str_buffer = (UInt8 *)malloc(1024); - FSRefMakePath(&ref, str_buffer, 1024); - QFileOpenEvent ev(QString::fromUtf8((const char *)str_buffer)); - QApplication::sendSpontaneousEvent(app, &ev); - } - if(str_buffer) - free(str_buffer); - } - break; } - default: - break; - } - } else if (aeClass == kInternetEventClass) { - switch (aeID) { - case kAEGetURL: { - char urlData[1024]; - Size actualSize; - if (AEGetParamPtr(ae, keyDirectObject, typeChar, 0, urlData, - sizeof(urlData) - 1, &actualSize) == noErr) { - urlData[actualSize] = 0; - QFileOpenEvent ev(QUrl(QString::fromUtf8(urlData))); - QApplication::sendSpontaneousEvent(app, &ev); - } - break; - } - default: - break; - } - } -#ifdef DEBUG_EVENTS - qDebug("Qt: internal: %shandled Apple event! %c%c%c%c %c%c%c%c", handled_event ? "(*)" : "", - char(aeID >> 24), char((aeID >> 16) & 255), char((aeID >> 8) & 255),char(aeID & 255), - char(aeClass >> 24), char((aeClass >> 16) & 255), char((aeClass >> 8) & 255),char(aeClass & 255)); -#else - if(!handled_event) //let the event go through - return eventNotHandledErr; - return noErr; //we eat the event -#endif -} - -/*! - \fn bool QApplication::macEventFilter(EventHandlerCallRef caller, EventRef event) - - \warning This virtual function is only used under Mac OS X, and behaves different - depending on if Qt is based on Carbon or Cocoa. - - For the Carbon port, If you create an application that inherits QApplication and reimplement - this function, you get direct access to all Carbon Events that Qt registers - for from Mac OS X with this function being called with the \a caller and - the \a event. - - For the Cocoa port, If you create an application that inherits QApplication and reimplement - this function, you get direct access to all Cocoa Events that Qt receives - from Mac OS X with this function being called with the \a caller being 0 and - the \a event being an NSEvent pointer: - - NSEvent *e = reinterpret_cast(event); - - Return true if you want to stop the event from being processed. - Return false for normal event dispatching. The default - implementation returns false. -*/ -bool QApplication::macEventFilter(EventHandlerCallRef, EventRef) -{ - return false; -} - -/*! - \internal -*/ -void QApplicationPrivate::openPopup(QWidget *popup) -{ - if (!QApplicationPrivate::popupWidgets) // create list - QApplicationPrivate::popupWidgets = new QWidgetList; - QApplicationPrivate::popupWidgets->append(popup); // add to end of list - - // popups are not focus-handled by the window system (the first - // popup grabbed the keyboard), so we have to do that manually: A - // new popup gets the focus - if (popup->focusWidget()) { - popup->focusWidget()->setFocus(Qt::PopupFocusReason); - } else if (QApplicationPrivate::popupWidgets->count() == 1) { // this was the first popup - popup->setFocus(Qt::PopupFocusReason); - } -} - -/*! - \internal -*/ -void QApplicationPrivate::closePopup(QWidget *popup) -{ - Q_Q(QApplication); - if (!QApplicationPrivate::popupWidgets) - return; - - QApplicationPrivate::popupWidgets->removeAll(popup); - if (popup == qt_button_down) - qt_button_down = 0; - if (QApplicationPrivate::popupWidgets->isEmpty()) { // this was the last popup - delete QApplicationPrivate::popupWidgets; - QApplicationPrivate::popupWidgets = 0; - - // Special case for Tool windows: since they are activated and deactived together - // with a normal window they never become the QApplicationPrivate::active_window. - QWidget *appFocusWidget = QApplication::focusWidget(); - if (appFocusWidget && appFocusWidget->window()->windowType() == Qt::Tool) { - appFocusWidget->setFocus(Qt::PopupFocusReason); - } else if (QApplicationPrivate::active_window) { - if (QWidget *fw = QApplicationPrivate::active_window->focusWidget()) { - if (fw != QApplication::focusWidget()) { - fw->setFocus(Qt::PopupFocusReason); - } else { - QFocusEvent e(QEvent::FocusIn, Qt::PopupFocusReason); - q->sendEvent(fw, &e); - } - } - } - } else { - // popups are not focus-handled by the window system (the - // first popup grabbed the keyboard), so we have to do that - // manually: A popup was closed, so the previous popup gets - // the focus. - QWidget* aw = QApplicationPrivate::popupWidgets->last(); - if (QWidget *fw = aw->focusWidget()) - fw->setFocus(Qt::PopupFocusReason); - } -} - -void QApplication::beep() -{ - qt_mac_beep(); -} - -void QApplication::alert(QWidget *widget, int duration) -{ - if (!QApplicationPrivate::checkInstance("alert")) - return; - - QWidgetList windowsToMark; - if (!widget) - windowsToMark += topLevelWidgets(); - else - windowsToMark.append(widget->window()); - - bool needNotification = false; - for (int i = 0; i < windowsToMark.size(); ++i) { - QWidget *window = windowsToMark.at(i); - if (!window->isActiveWindow() && window->isVisible()) { - needNotification = true; // yeah, we may set it multiple times, but that's OK. - if (duration != 0) { - QTimer *timer = new QTimer(qApp); - timer->setSingleShot(true); - connect(timer, SIGNAL(timeout()), qApp, SLOT(_q_alertTimeOut())); - if (QTimer *oldTimer = qApp->d_func()->alertTimerHash.value(widget)) { - qApp->d_func()->alertTimerHash.remove(widget); - delete oldTimer; - } - qApp->d_func()->alertTimerHash.insert(widget, timer); - timer->start(duration); - } - } - } - if (needNotification) - qt_mac_send_notification(); -} - -void QApplicationPrivate::_q_alertTimeOut() -{ - if (QTimer *timer = qobject_cast(q_func()->sender())) { - QHash::iterator it = alertTimerHash.begin(); - while (it != alertTimerHash.end()) { - if (it.value() == timer) { - alertTimerHash.erase(it); - timer->deleteLater(); - break; - } - ++it; - } - if (alertTimerHash.isEmpty()) { - qt_mac_cancel_notification(); - } - } -} - -void QApplication::setCursorFlashTime(int msecs) -{ - QApplicationPrivate::cursor_flash_time = msecs; -} - -int QApplication::cursorFlashTime() -{ - return QApplicationPrivate::cursor_flash_time; -} - -void QApplication::setDoubleClickInterval(int ms) -{ - qt_mac_dblclick.use_qt_time_limit = true; - QApplicationPrivate::mouse_double_click_time = ms; -} - -int QApplication::doubleClickInterval() -{ - if (!qt_mac_dblclick.use_qt_time_limit) { //get it from the system - QSettings appleSettings(QLatin1String("apple.com")); - /* First worked as of 10.3.3 */ - double dci = appleSettings.value(QLatin1String("com/apple/mouse/doubleClickThreshold"), 0.5).toDouble(); - return int(dci * 1000); - } - return QApplicationPrivate::mouse_double_click_time; -} - -void QApplication::setKeyboardInputInterval(int ms) -{ - QApplicationPrivate::keyboard_input_time = ms; -} - -int QApplication::keyboardInputInterval() -{ - // FIXME: get from the system - return QApplicationPrivate::keyboard_input_time; -} - -#ifndef QT_NO_WHEELEVENT -void QApplication::setWheelScrollLines(int n) -{ - QApplicationPrivate::wheel_scroll_lines = n; -} - -int QApplication::wheelScrollLines() -{ - return QApplicationPrivate::wheel_scroll_lines; -} -#endif - -void QApplication::setEffectEnabled(Qt::UIEffect effect, bool enable) -{ - switch (effect) { - case Qt::UI_FadeMenu: - QApplicationPrivate::fade_menu = enable; - break; - case Qt::UI_AnimateMenu: - QApplicationPrivate::animate_menu = enable; - break; - case Qt::UI_FadeTooltip: - QApplicationPrivate::fade_tooltip = enable; - break; - case Qt::UI_AnimateTooltip: - QApplicationPrivate::animate_tooltip = enable; - break; - case Qt::UI_AnimateCombo: - QApplicationPrivate::animate_combo = enable; - break; - case Qt::UI_AnimateToolBox: - QApplicationPrivate::animate_toolbox = enable; - break; - case Qt::UI_General: - QApplicationPrivate::fade_tooltip = true; - break; - default: - QApplicationPrivate::animate_ui = enable; - break; - } - - if (enable) - QApplicationPrivate::animate_ui = true; -} - -bool QApplication::isEffectEnabled(Qt::UIEffect effect) -{ - if (QColormap::instance().depth() < 16 || !QApplicationPrivate::animate_ui) - return false; - - switch(effect) { - case Qt::UI_AnimateMenu: - return QApplicationPrivate::animate_menu; - case Qt::UI_FadeMenu: - return QApplicationPrivate::fade_menu; - case Qt::UI_AnimateCombo: - return QApplicationPrivate::animate_combo; - case Qt::UI_AnimateTooltip: - return QApplicationPrivate::animate_tooltip; - case Qt::UI_FadeTooltip: - return QApplicationPrivate::fade_tooltip; - case Qt::UI_AnimateToolBox: - return QApplicationPrivate::animate_toolbox; - default: - break; - } - return QApplicationPrivate::animate_ui; -} - -/*! - \internal -*/ -bool QApplicationPrivate::qt_mac_apply_settings() -{ - QSettings settings(QSettings::UserScope, QLatin1String("Trolltech")); - settings.beginGroup(QLatin1String("Qt")); - - /* - Qt settings. This is how they are written into the datastream. - Palette/ * - QPalette - font - QFont - libraryPath - QStringList - style - QString - doubleClickInterval - int - cursorFlashTime - int - wheelScrollLines - int - colorSpec - QString - defaultCodec - QString - globalStrut/width - int - globalStrut/height - int - GUIEffects - QStringList - Font Substitutions/ * - QStringList - Font Substitutions/... - QStringList - */ - - // read library (ie. plugin) path list - QString libpathkey = - QString::fromLatin1("%1.%2/libraryPath") - .arg(QT_VERSION >> 16) - .arg((QT_VERSION & 0xff00) >> 8); - QStringList pathlist = settings.value(libpathkey).toString().split(QLatin1Char(':')); - if (!pathlist.isEmpty()) { - QStringList::ConstIterator it = pathlist.begin(); - while(it != pathlist.end()) - QApplication::addLibraryPath(*it++); - } - - QString defaultcodec = settings.value(QLatin1String("defaultCodec"), QVariant(QLatin1String("none"))).toString(); - if (defaultcodec != QLatin1String("none")) { - QTextCodec *codec = QTextCodec::codecForName(defaultcodec.toLatin1().constData()); - if (codec) - QTextCodec::setCodecForTr(codec); - } - - if (qt_is_gui_used) { - QString str; - QStringList strlist; - int num; - - // read new palette - int i; - QPalette pal(QApplication::palette()); - strlist = settings.value(QLatin1String("Palette/active")).toStringList(); - if (strlist.count() == QPalette::NColorRoles) { - for (i = 0; i < QPalette::NColorRoles; i++) - pal.setColor(QPalette::Active, (QPalette::ColorRole) i, - QColor(strlist[i])); - } - strlist = settings.value(QLatin1String("Palette/inactive")).toStringList(); - if (strlist.count() == QPalette::NColorRoles) { - for (i = 0; i < QPalette::NColorRoles; i++) - pal.setColor(QPalette::Inactive, (QPalette::ColorRole) i, - QColor(strlist[i])); - } - strlist = settings.value(QLatin1String("Palette/disabled")).toStringList(); - if (strlist.count() == QPalette::NColorRoles) { - for (i = 0; i < QPalette::NColorRoles; i++) - pal.setColor(QPalette::Disabled, (QPalette::ColorRole) i, - QColor(strlist[i])); - } - - if (pal != QApplication::palette()) - QApplication::setPalette(pal); - - // read new font - QFont font(QApplication::font()); - str = settings.value(QLatin1String("font")).toString(); - if (!str.isEmpty()) { - font.fromString(str); - if (font != QApplication::font()) - QApplication::setFont(font); - } - - // read new QStyle - QString stylename = settings.value(QLatin1String("style")).toString(); - if (! stylename.isNull() && ! stylename.isEmpty()) { - QStyle *style = QStyleFactory::create(stylename); - if (style) - QApplication::setStyle(style); - else - stylename = QLatin1String("default"); - } else { - stylename = QLatin1String("default"); - } - - num = settings.value(QLatin1String("doubleClickInterval"), - QApplication::doubleClickInterval()).toInt(); - QApplication::setDoubleClickInterval(num); - - num = settings.value(QLatin1String("cursorFlashTime"), - QApplication::cursorFlashTime()).toInt(); - QApplication::setCursorFlashTime(num); - -#ifndef QT_NO_WHEELEVENT - num = settings.value(QLatin1String("wheelScrollLines"), - QApplication::wheelScrollLines()).toInt(); - QApplication::setWheelScrollLines(num); -#endif - - QString colorspec = settings.value(QLatin1String("colorSpec"), - QVariant(QLatin1String("default"))).toString(); - if (colorspec == QLatin1String("normal")) - QApplication::setColorSpec(QApplication::NormalColor); - else if (colorspec == QLatin1String("custom")) - QApplication::setColorSpec(QApplication::CustomColor); - else if (colorspec == QLatin1String("many")) - QApplication::setColorSpec(QApplication::ManyColor); - else if (colorspec != QLatin1String("default")) - colorspec = QLatin1String("default"); - - int w = settings.value(QLatin1String("globalStrut/width")).toInt(); - int h = settings.value(QLatin1String("globalStrut/height")).toInt(); - QSize strut(w, h); - if (strut.isValid()) - QApplication::setGlobalStrut(strut); - - QStringList effects = settings.value(QLatin1String("GUIEffects")).toStringList(); - if (!effects.isEmpty()) { - if (effects.contains(QLatin1String("none"))) - QApplication::setEffectEnabled(Qt::UI_General, false); - if (effects.contains(QLatin1String("general"))) - QApplication::setEffectEnabled(Qt::UI_General, true); - if (effects.contains(QLatin1String("animatemenu"))) - QApplication::setEffectEnabled(Qt::UI_AnimateMenu, true); - if (effects.contains(QLatin1String("fademenu"))) - QApplication::setEffectEnabled(Qt::UI_FadeMenu, true); - if (effects.contains(QLatin1String("animatecombo"))) - QApplication::setEffectEnabled(Qt::UI_AnimateCombo, true); - if (effects.contains(QLatin1String("animatetooltip"))) - QApplication::setEffectEnabled(Qt::UI_AnimateTooltip, true); - if (effects.contains(QLatin1String("fadetooltip"))) - QApplication::setEffectEnabled(Qt::UI_FadeTooltip, true); - if (effects.contains(QLatin1String("animatetoolbox"))) - QApplication::setEffectEnabled(Qt::UI_AnimateToolBox, true); - } else { - QApplication::setEffectEnabled(Qt::UI_General, true); - } - - settings.beginGroup(QLatin1String("Font Substitutions")); - QStringList fontsubs = settings.childKeys(); - if (!fontsubs.isEmpty()) { - QStringList::Iterator it = fontsubs.begin(); - for (; it != fontsubs.end(); ++it) { - QString fam = QString::fromLatin1((*it).toLatin1().constData()); - QStringList subs = settings.value(fam).toStringList(); - QFont::insertSubstitutions(fam, subs); - } - } - settings.endGroup(); - } - - settings.endGroup(); - return true; -} - -// DRSWAT - -bool QApplicationPrivate::canQuit() -{ - Q_Q(QApplication); - [[NSApp mainMenu] cancelTracking]; - - bool handle_quit = true; - if (QApplicationPrivate::modalState() && [[[[QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) sharedDelegate] - menuLoader] quitMenuItem] isEnabled]) { - int visible = 0; - const QWidgetList tlws = QApplication::topLevelWidgets(); - for(int i = 0; i < tlws.size(); ++i) { - if (tlws.at(i)->isVisible()) - ++visible; - } - handle_quit = (visible <= 1); - } - if (handle_quit) { - QCloseEvent ev; - QApplication::sendSpontaneousEvent(q, &ev); - if (ev.isAccepted()) { - return true; - } - } - return false; -} - -void onApplicationWindowChangedActivation(QWidget *widget, bool activated) -{ - if (!widget) - return; - - if (activated) { - if (QApplicationPrivate::app_style) { - QEvent ev(QEvent::Style); - qt_sendSpontaneousEvent(QApplicationPrivate::app_style, &ev); - } - qApp->setActiveWindow(widget); - } else { // deactivated - if (QApplicationPrivate::active_window == widget) - qApp->setActiveWindow(0); - } - - QMenuBar::macUpdateMenuBar(); - qt_mac_update_cursor(); -} - - -void onApplicationChangedActivation( bool activated ) -{ - QApplication *app = qApp; - -//NSLog(@"App Changed Activation\n"); - - if ( activated ) { - if (QApplication::desktopSettingsAware()) - qt_mac_update_os_settings(); - - if (qt_clipboard) { //manufacture an event so the clipboard can see if it has changed - QEvent ev(QEvent::Clipboard); - qt_sendSpontaneousEvent(qt_clipboard, &ev); - } - - if (app) { - QEvent ev(QEvent::ApplicationActivate); - qt_sendSpontaneousEvent(app, &ev); - } - - if (!app->activeWindow()) { - OSWindowRef wp = [NSApp keyWindow]; - if (QWidget *tmp_w = qt_mac_find_window(wp)) - app->setActiveWindow(tmp_w); - } - QMenuBar::macUpdateMenuBar(); - qt_mac_update_cursor(); - } else { // de-activated - QApplicationPrivate *priv = [[QT_MANGLE_NAMESPACE(QCocoaApplicationDelegate) sharedDelegate] qAppPrivate]; - while (priv->inPopupMode()) - app->activePopupWidget()->close(); - if (app) { - QEvent ev(QEvent::ApplicationDeactivate); - qt_sendSpontaneousEvent(app, &ev); - } - app->setActiveWindow(0); - } -} - -void QApplicationPrivate::initializeMultitouch_sys() -{ } -void QApplicationPrivate::cleanupMultitouch_sys() -{ } - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qclipboard_mac.cpp b/src/widgets/platforms/mac/qclipboard_mac.cpp deleted file mode 100644 index 3ec4bfb..0000000 --- a/src/widgets/platforms/mac/qclipboard_mac.cpp +++ /dev/null @@ -1,632 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qclipboard.h" -#include "qapplication.h" -#include "qbitmap.h" -#include "qdatetime.h" -#include "qdebug.h" -#include "qapplication_p.h" -#include -#include "qevent.h" -#include "qurl.h" -#include -#include -#include "qt_cocoa_helpers_mac_p.h" - -QT_BEGIN_NAMESPACE - -QT_USE_NAMESPACE - -/***************************************************************************** - QClipboard debug facilities - *****************************************************************************/ -//#define DEBUG_PASTEBOARD - -#ifndef QT_NO_CLIPBOARD - -/***************************************************************************** - QClipboard member functions for mac. - *****************************************************************************/ - -static QMacPasteboard *qt_mac_pasteboards[2] = {0, 0}; - -static inline QMacPasteboard *qt_mac_pasteboard(QClipboard::Mode mode) -{ - Q_ASSERT(mode == QClipboard::Clipboard || mode == QClipboard::FindBuffer); - if (mode == QClipboard::Clipboard) - return qt_mac_pasteboards[0]; - else - return qt_mac_pasteboards[1]; -} - -static void qt_mac_cleanupPasteboard() { - delete qt_mac_pasteboards[0]; - delete qt_mac_pasteboards[1]; - qt_mac_pasteboards[0] = 0; - qt_mac_pasteboards[1] = 0; -} - -static bool qt_mac_updateScrap(QClipboard::Mode mode) -{ - if(!qt_mac_pasteboards[0]) { - qt_mac_pasteboards[0] = new QMacPasteboard(kPasteboardClipboard, QMacPasteboardMime::MIME_CLIP); - qt_mac_pasteboards[1] = new QMacPasteboard(kPasteboardFind, QMacPasteboardMime::MIME_CLIP); - qAddPostRoutine(qt_mac_cleanupPasteboard); - return true; - } - return qt_mac_pasteboard(mode)->sync(); -} - -void QClipboard::clear(Mode mode) -{ - if (!supportsMode(mode)) - return; - qt_mac_updateScrap(mode); - qt_mac_pasteboard(mode)->clear(); - setMimeData(0, mode); -} - -void QClipboard::ownerDestroyed() -{ -} - - -void QClipboard::connectNotify(const char *signal) -{ - Q_UNUSED(signal); -} - -bool QClipboard::event(QEvent *e) -{ - if(e->type() != QEvent::Clipboard) - return QObject::event(e); - - if (qt_mac_updateScrap(QClipboard::Clipboard)) { - emitChanged(QClipboard::Clipboard); - } - - if (qt_mac_updateScrap(QClipboard::FindBuffer)) { - emitChanged(QClipboard::FindBuffer); - } - - return QObject::event(e); -} - -const QMimeData *QClipboard::mimeData(Mode mode) const -{ - if (!supportsMode(mode)) - return 0; - qt_mac_updateScrap(mode); - return qt_mac_pasteboard(mode)->mimeData(); -} - -void QClipboard::setMimeData(QMimeData *src, Mode mode) -{ - if (!supportsMode(mode)) - return; - qt_mac_updateScrap(mode); - qt_mac_pasteboard(mode)->setMimeData(src); - emitChanged(mode); -} - -bool QClipboard::supportsMode(Mode mode) const -{ - return (mode == Clipboard || mode == FindBuffer); -} - -bool QClipboard::ownsMode(Mode mode) const -{ - Q_UNUSED(mode); - return false; -} - -#endif // QT_NO_CLIPBOARD - -/***************************************************************************** - QMacPasteboard code -*****************************************************************************/ - -QMacPasteboard::QMacPasteboard(PasteboardRef p, uchar mt) -{ - mac_mime_source = false; - mime_type = mt ? mt : uchar(QMacPasteboardMime::MIME_ALL); - paste = p; - CFRetain(paste); -} - -QMacPasteboard::QMacPasteboard(uchar mt) -{ - mac_mime_source = false; - mime_type = mt ? mt : uchar(QMacPasteboardMime::MIME_ALL); - paste = 0; - OSStatus err = PasteboardCreate(0, &paste); - if(err == noErr) { - PasteboardSetPromiseKeeper(paste, promiseKeeper, this); - } else { - qDebug("PasteBoard: Error creating pasteboard: [%d]", (int)err); - } -} - -QMacPasteboard::QMacPasteboard(CFStringRef name, uchar mt) -{ - mac_mime_source = false; - mime_type = mt ? mt : uchar(QMacPasteboardMime::MIME_ALL); - paste = 0; - OSStatus err = PasteboardCreate(name, &paste); - if(err == noErr) { - PasteboardSetPromiseKeeper(paste, promiseKeeper, this); - } else { - qDebug("PasteBoard: Error creating pasteboard: %s [%d]", QCFString::toQString(name).toLatin1().constData(), (int)err); - } -} - -QMacPasteboard::~QMacPasteboard() -{ - // commit all promises for paste after exit close - for (int i = 0; i < promises.count(); ++i) { - const Promise &promise = promises.at(i); - QCFString flavor = QCFString(promise.convertor->flavorFor(promise.mime)); - promiseKeeper(paste, (PasteboardItemID)promise.itemId, flavor, this); - } - - if(paste) - CFRelease(paste); -} - -PasteboardRef -QMacPasteboard::pasteBoard() const -{ - return paste; -} - -OSStatus QMacPasteboard::promiseKeeper(PasteboardRef paste, PasteboardItemID id, CFStringRef flavor, void *_qpaste) -{ - QMacPasteboard *qpaste = (QMacPasteboard*)_qpaste; - const long promise_id = (long)id; - - // Find the kept promise - const QString flavorAsQString = QCFString::toQString(flavor); - QMacPasteboard::Promise promise; - for (int i = 0; i < qpaste->promises.size(); i++){ - QMacPasteboard::Promise tmp = qpaste->promises[i]; - if (tmp.itemId == promise_id && tmp.convertor->canConvert(tmp.mime, flavorAsQString)){ - promise = tmp; - break; - } - } - - if (!promise.itemId && flavorAsQString == QLatin1String("com.trolltech.qt.MimeTypeName")) { - // we have promised this data, but wont be able to convert, so return null data. - // This helps in making the application/x-qt-mime-type-name hidden from normal use. - QByteArray ba; - QCFType data = CFDataCreate(0, (UInt8*)ba.constData(), ba.size()); - PasteboardPutItemFlavor(paste, id, flavor, data, kPasteboardFlavorNoFlags); - return noErr; - } - - if (!promise.itemId) { - // There was no promise that could deliver data for the - // given id and flavor. This should not happend. - qDebug("Pasteboard: %d: Request for %ld, %s, but no promise found!", __LINE__, promise_id, qPrintable(flavorAsQString)); - return cantGetFlavorErr; - } - -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: Calling in promise for %s[%ld] [%s] (%s) [%d]", qPrintable(promise.mime), promise_id, - qPrintable(flavorAsQString), qPrintable(promise.convertor->convertorName()), promise.offset); -#endif - - QList md = promise.convertor->convertFromMime(promise.mime, promise.data, flavorAsQString); - if (md.size() <= promise.offset) - return cantGetFlavorErr; - const QByteArray &ba = md[promise.offset]; - QCFType data = CFDataCreate(0, (UInt8*)ba.constData(), ba.size()); - PasteboardPutItemFlavor(paste, id, flavor, data, kPasteboardFlavorNoFlags); - return noErr; -} - -bool -QMacPasteboard::hasOSType(int c_flavor) const -{ - if (!paste) - return false; - - sync(); - - ItemCount cnt = 0; - if(PasteboardGetItemCount(paste, &cnt) || !cnt) - return false; - -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: hasOSType [%c%c%c%c]", (c_flavor>>24)&0xFF, (c_flavor>>16)&0xFF, - (c_flavor>>8)&0xFF, (c_flavor>>0)&0xFF); -#endif - for(uint index = 1; index <= cnt; ++index) { - - PasteboardItemID id; - if(PasteboardGetItemIdentifier(paste, index, &id) != noErr) - return false; - - QCFType types; - if(PasteboardCopyItemFlavors(paste, id, &types ) != noErr) - return false; - - const int type_count = CFArrayGetCount(types); - for(int i = 0; i < type_count; ++i) { - CFStringRef flavor = (CFStringRef)CFArrayGetValueAtIndex(types, i); - const int os_flavor = UTGetOSTypeFromString(UTTypeCopyPreferredTagWithClass(flavor, kUTTagClassOSType)); - if(os_flavor == c_flavor) { -#ifdef DEBUG_PASTEBOARD - qDebug(" - Found!"); -#endif - return true; - } - } - } -#ifdef DEBUG_PASTEBOARD - qDebug(" - NotFound!"); -#endif - return false; -} - -bool -QMacPasteboard::hasFlavor(QString c_flavor) const -{ - if (!paste) - return false; - - sync(); - - ItemCount cnt = 0; - if(PasteboardGetItemCount(paste, &cnt) || !cnt) - return false; - -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: hasFlavor [%s]", qPrintable(c_flavor)); -#endif - for(uint index = 1; index <= cnt; ++index) { - - PasteboardItemID id; - if(PasteboardGetItemIdentifier(paste, index, &id) != noErr) - return false; - - PasteboardFlavorFlags flags; - if(PasteboardGetItemFlavorFlags(paste, id, QCFString(c_flavor), &flags) == noErr) { -#ifdef DEBUG_PASTEBOARD - qDebug(" - Found!"); -#endif - return true; - } - } -#ifdef DEBUG_PASTEBOARD - qDebug(" - NotFound!"); -#endif - return false; -} - -class QMacPasteboardMimeSource : public QMimeData { - const QMacPasteboard *paste; -public: - QMacPasteboardMimeSource(const QMacPasteboard *p) : QMimeData(), paste(p) { } - ~QMacPasteboardMimeSource() { } - virtual QStringList formats() const { return paste->formats(); } - virtual QVariant retrieveData(const QString &format, QVariant::Type type) const { return paste->retrieveData(format, type); } -}; - -QMimeData -*QMacPasteboard::mimeData() const -{ - if(!mime) { - mac_mime_source = true; - mime = new QMacPasteboardMimeSource(this); - - } - return mime; -} - -class QMacMimeData : public QMimeData -{ -public: - QVariant variantData(const QString &mime) { return retrieveData(mime, QVariant::Invalid); } -private: - QMacMimeData(); -}; - -void -QMacPasteboard::setMimeData(QMimeData *mime_src) -{ - if (!paste) - return; - - if (mime == mime_src || (!mime_src && mime && mac_mime_source)) - return; - mac_mime_source = false; - delete mime; - mime = mime_src; - - QList availableConverters = QMacPasteboardMime::all(mime_type); - if (mime != 0) { - clear_helper(); - QStringList formats = mime_src->formats(); - - // QMimeData sub classes reimplementing the formats() might not expose the - // temporary "application/x-qt-mime-type-name" mimetype. So check the existence - // of this mime type while doing drag and drop. - QString dummyMimeType(QLatin1String("application/x-qt-mime-type-name")); - if (!formats.contains(dummyMimeType)) { - QByteArray dummyType = mime_src->data(dummyMimeType); - if (!dummyType.isEmpty()) { - formats.append(dummyMimeType); - } - } - for(int f = 0; f < formats.size(); ++f) { - QString mimeType = formats.at(f); - for (QList::Iterator it = availableConverters.begin(); it != availableConverters.end(); ++it) { - QMacPasteboardMime *c = (*it); - QString flavor(c->flavorFor(mimeType)); - if(!flavor.isEmpty()) { - QVariant mimeData = static_cast(mime_src)->variantData(mimeType); -#if 0 - //### Grrr, why didn't I put in a virtual int QMacPasteboardMime::count()? --Sam - const int numItems = c->convertFromMime(mimeType, mimeData, flavor).size(); -#else - int numItems = 1; //this is a hack but it is much faster than allowing conversion above - if(c->convertorName() == QLatin1String("FileURL")) - numItems = mime_src->urls().count(); -#endif - for(int item = 0; item < numItems; ++item) { - const int itemID = item+1; //id starts at 1 - promises.append(QMacPasteboard::Promise(itemID, c, mimeType, mimeData, item)); - PasteboardPutItemFlavor(paste, (PasteboardItemID)itemID, QCFString(flavor), 0, kPasteboardFlavorNoFlags); -#ifdef DEBUG_PASTEBOARD - qDebug(" - adding %d %s [%s] <%s> [%d]", - itemID, qPrintable(mimeType), qPrintable(flavor), qPrintable(c->convertorName()), item); -#endif - } - } - } - } - } -} - -QStringList -QMacPasteboard::formats() const -{ - if (!paste) - return QStringList(); - - sync(); - - QStringList ret; - ItemCount cnt = 0; - if(PasteboardGetItemCount(paste, &cnt) || !cnt) - return ret; - -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: Formats [%d]", (int)cnt); -#endif - for(uint index = 1; index <= cnt; ++index) { - - PasteboardItemID id; - if(PasteboardGetItemIdentifier(paste, index, &id) != noErr) - continue; - - QCFType types; - if(PasteboardCopyItemFlavors(paste, id, &types ) != noErr) - continue; - - const int type_count = CFArrayGetCount(types); - for(int i = 0; i < type_count; ++i) { - const QString flavor = QCFString::toQString((CFStringRef)CFArrayGetValueAtIndex(types, i)); -#ifdef DEBUG_PASTEBOARD - qDebug(" -%s", qPrintable(QString(flavor))); -#endif - QString mimeType = QMacPasteboardMime::flavorToMime(mime_type, flavor); - if(!mimeType.isEmpty() && !ret.contains(mimeType)) { -#ifdef DEBUG_PASTEBOARD - qDebug(" -<%d> %s [%s]", ret.size(), qPrintable(mimeType), qPrintable(QString(flavor))); -#endif - ret << mimeType; - } - } - } - return ret; -} - -bool -QMacPasteboard::hasFormat(const QString &format) const -{ - if (!paste) - return false; - - sync(); - - ItemCount cnt = 0; - if(PasteboardGetItemCount(paste, &cnt) || !cnt) - return false; - -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: hasFormat [%s]", qPrintable(format)); -#endif - for(uint index = 1; index <= cnt; ++index) { - - PasteboardItemID id; - if(PasteboardGetItemIdentifier(paste, index, &id) != noErr) - continue; - - QCFType types; - if(PasteboardCopyItemFlavors(paste, id, &types ) != noErr) - continue; - - const int type_count = CFArrayGetCount(types); - for(int i = 0; i < type_count; ++i) { - const QString flavor = QCFString::toQString((CFStringRef)CFArrayGetValueAtIndex(types, i)); -#ifdef DEBUG_PASTEBOARD - qDebug(" -%s [0x%x]", qPrintable(QString(flavor)), mime_type); -#endif - QString mimeType = QMacPasteboardMime::flavorToMime(mime_type, flavor); -#ifdef DEBUG_PASTEBOARD - if(!mimeType.isEmpty()) - qDebug(" - %s", qPrintable(mimeType)); -#endif - if(mimeType == format) - return true; - } - } - return false; -} - -QVariant -QMacPasteboard::retrieveData(const QString &format, QVariant::Type) const -{ - if (!paste) - return QVariant(); - - sync(); - - ItemCount cnt = 0; - if(PasteboardGetItemCount(paste, &cnt) || !cnt) - return QByteArray(); - -#ifdef DEBUG_PASTEBOARD - qDebug("Pasteboard: retrieveData [%s]", qPrintable(format)); -#endif - const QList mimes = QMacPasteboardMime::all(mime_type); - for(int mime = 0; mime < mimes.size(); ++mime) { - QMacPasteboardMime *c = mimes.at(mime); - QString c_flavor = c->flavorFor(format); - if(!c_flavor.isEmpty()) { - // Handle text/plain a little differently. Try handling Unicode first. - bool checkForUtf16 = (c_flavor == QLatin1String("com.apple.traditional-mac-plain-text") - || c_flavor == QLatin1String("public.utf8-plain-text")); - if (checkForUtf16 || c_flavor == QLatin1String("public.utf16-plain-text")) { - // Try to get the NSStringPboardType from NSPasteboard, newlines are mapped - // correctly (as '\n') in this data. The 'public.utf16-plain-text' type - // usually maps newlines to '\r' instead. - QString str = qt_mac_get_pasteboardString(paste); - if (!str.isEmpty()) - return str; - } - if (checkForUtf16 && hasFlavor(QLatin1String("public.utf16-plain-text"))) - c_flavor = QLatin1String("public.utf16-plain-text"); - - QVariant ret; - QList retList; - for(uint index = 1; index <= cnt; ++index) { - PasteboardItemID id; - if(PasteboardGetItemIdentifier(paste, index, &id) != noErr) - continue; - - QCFType types; - if(PasteboardCopyItemFlavors(paste, id, &types ) != noErr) - continue; - - const int type_count = CFArrayGetCount(types); - for(int i = 0; i < type_count; ++i) { - CFStringRef flavor = static_cast(CFArrayGetValueAtIndex(types, i)); - if(c_flavor == QCFString::toQString(flavor)) { - QCFType macBuffer; - if(PasteboardCopyItemFlavorData(paste, id, flavor, &macBuffer) == noErr) { - QByteArray buffer((const char *)CFDataGetBytePtr(macBuffer), CFDataGetLength(macBuffer)); - if(!buffer.isEmpty()) { -#ifdef DEBUG_PASTEBOARD - qDebug(" - %s [%s] (%s)", qPrintable(format), qPrintable(QCFString::toQString(flavor)), qPrintable(c->convertorName())); -#endif - buffer.detach(); //detach since we release the macBuffer - retList.append(buffer); - break; //skip to next element - } - } - } else { -#ifdef DEBUG_PASTEBOARD - qDebug(" - NoMatch %s [%s] (%s)", qPrintable(c_flavor), qPrintable(QCFString::toQString(flavor)), qPrintable(c->convertorName())); -#endif - } - } - } - - if (!retList.isEmpty()) { - ret = c->convertToMime(format, retList, c_flavor); - return ret; - } - } - } - return QVariant(); -} - -void QMacPasteboard::clear_helper() -{ - if (paste) - PasteboardClear(paste); - promises.clear(); -} - -void -QMacPasteboard::clear() -{ -#ifdef DEBUG_PASTEBOARD - qDebug("PasteBoard: clear!"); -#endif - clear_helper(); -} - -bool -QMacPasteboard::sync() const -{ - if (!paste) - return false; - const bool fromGlobal = PasteboardSynchronize(paste) & kPasteboardModified; - - if (fromGlobal) - const_cast(this)->setMimeData(0); - -#ifdef DEBUG_PASTEBOARD - if(fromGlobal) - qDebug("Pasteboard: Synchronize!"); -#endif - return fromGlobal; -} - - - - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qcocoaintrospection_mac.mm b/src/widgets/platforms/mac/qcocoaintrospection_mac.mm deleted file mode 100644 index e68aacb..0000000 --- a/src/widgets/platforms/mac/qcocoaintrospection_mac.mm +++ /dev/null @@ -1,119 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include - -QT_BEGIN_NAMESPACE - -void qt_cocoa_change_implementation(Class baseClass, SEL originalSel, Class proxyClass, SEL replacementSel, SEL backupSel) -{ - { -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_5 - // The following code replaces the _implementation_ for the selector we want to hack - // (originalSel) with the implementation found in proxyClass. Then it creates - // a new 'backup' method inside baseClass containing the old, original, - // implementation (fakeSel). You can let the proxy implementation of originalSel - // call fakeSel if needed (similar approach to calling a super class implementation). - // fakeSel must also be implemented in proxyClass, as the signature is used - // as template for the method one we add into baseClass. - // NB: You will typically never create any instances of proxyClass; we use it - // only for stealing its contents and put it into baseClass. - if (!replacementSel) - replacementSel = originalSel; - - Method originalMethod = class_getInstanceMethod(baseClass, originalSel); - Method replacementMethod = class_getInstanceMethod(proxyClass, replacementSel); - IMP originalImp = method_setImplementation(originalMethod, method_getImplementation(replacementMethod)); - - if (backupSel) { - Method backupMethod = class_getInstanceMethod(proxyClass, backupSel); - class_addMethod(baseClass, backupSel, originalImp, method_getTypeEncoding(backupMethod)); - } -#endif - } -} - -void qt_cocoa_change_back_implementation(Class baseClass, SEL originalSel, SEL backupSel) -{ - { -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_5 - Method originalMethod = class_getInstanceMethod(baseClass, originalSel); - Method backupMethodInBaseClass = class_getInstanceMethod(baseClass, backupSel); - method_setImplementation(originalMethod, method_getImplementation(backupMethodInBaseClass)); -#endif - } -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qcocoaintrospection_p.h b/src/widgets/platforms/mac/qcocoaintrospection_p.h deleted file mode 100644 index 9521957..0000000 --- a/src/widgets/platforms/mac/qcocoaintrospection_p.h +++ /dev/null @@ -1,84 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include -#import - -QT_BEGIN_NAMESPACE - -void qt_cocoa_change_implementation(Class baseClass, SEL originalSel, Class proxyClass, SEL replacementSel = 0, SEL backupSel = 0); -void qt_cocoa_change_back_implementation(Class baseClass, SEL originalSel, SEL backupSel); - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qcocoapanel_mac.mm b/src/widgets/platforms/mac/qcocoapanel_mac.mm deleted file mode 100644 index 115f78b..0000000 --- a/src/widgets/platforms/mac/qcocoapanel_mac.mm +++ /dev/null @@ -1,68 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#import -#import -#import -#import -#import -#import -#import -#import -#import -#import -#import - -#include - -QT_FORWARD_DECLARE_CLASS(QWidget); -QT_USE_NAMESPACE - -@implementation QT_MANGLE_NAMESPACE(QCocoaPanel) - -/*********************************************************************** - Copy and Paste between QCocoaWindow and QCocoaPanel - This is a bit unfortunate, but thanks to the dynamic dispatch we - have to duplicate this code or resort to really silly forwarding methods -**************************************************************************/ -#include "qcocoasharedwindowmethods_mac_p.h" - -@end diff --git a/src/widgets/platforms/mac/qcocoapanel_mac_p.h b/src/widgets/platforms/mac/qcocoapanel_mac_p.h deleted file mode 100644 index 19eab92..0000000 --- a/src/widgets/platforms/mac/qcocoapanel_mac_p.h +++ /dev/null @@ -1,81 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#ifndef QCOCOAPANEL_MAC_P -#define QCOCOAPANEL_MAC_P - -#include "qmacdefines_mac.h" -#import - -QT_FORWARD_DECLARE_CLASS(QStringList); -QT_FORWARD_DECLARE_CLASS(QCocoaDropData); - -@interface NSPanel (QtIntegration) -- (NSDragOperation)draggingEntered:(id )sender; -- (NSDragOperation)draggingUpdated:(id )sender; -- (void)draggingExited:(id )sender; -- (BOOL)performDragOperation:(id )sender; -@end - -@interface QT_MANGLE_NAMESPACE(QCocoaPanel) : NSPanel { - QStringList *currentCustomDragTypes; - QCocoaDropData *dropData; - NSInteger dragEnterSequence; -} - -+ (Class)frameViewClassForStyleMask:(NSUInteger)styleMask; -- (void)registerDragTypes; -- (void)drawRectOriginal:(NSRect)rect; - -@end - -#endif diff --git a/src/widgets/platforms/mac/qcocoasharedwindowmethods_mac_p.h b/src/widgets/platforms/mac/qcocoasharedwindowmethods_mac_p.h deleted file mode 100644 index edafcfc..0000000 --- a/src/widgets/platforms/mac/qcocoasharedwindowmethods_mac_p.h +++ /dev/null @@ -1,610 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** - NB: This is not a header file, dispite the file name suffix. This file is - included directly into the source code of qcocoawindow_mac.mm and - qcocoapanel_mac.mm to avoid manually doing copy and paste of the exact - same code needed at both places. This solution makes it more difficult - to e.g fix a bug in qcocoawindow_mac.mm, but forget to do the same in - qcocoapanel_mac.mm. - The reason we need to do copy and paste in the first place, rather than - resolve to method overriding, is that QCocoaPanel needs to inherit from - NSPanel, while QCocoaWindow needs to inherit NSWindow rather than NSPanel). -****************************************************************************/ - -// WARNING: Don't include any header files from within this file. Put them -// directly into qcocoawindow_mac_p.h and qcocoapanel_mac_p.h - -QT_BEGIN_NAMESPACE -extern Qt::MouseButton cocoaButton2QtButton(NSInteger buttonNum); // qcocoaview.mm -extern QPointer qt_button_down; //qapplication_mac.cpp -extern const QStringList& qEnabledDraggedTypes(); // qmime_mac.cpp -extern void qt_event_request_window_change(QWidget *); // qapplication_mac.mm -extern void qt_mac_send_posted_gl_updates(QWidget *widget); // qapplication_mac.mm - -Q_GLOBAL_STATIC(QPointer, currentDragTarget); -QT_END_NAMESPACE - -- (id)initWithContentRect:(NSRect)contentRect - styleMask:(NSUInteger)windowStyle - backing:(NSBackingStoreType)bufferingType - defer:(BOOL)deferCreation -{ - self = [super initWithContentRect:contentRect styleMask:windowStyle - backing:bufferingType defer:deferCreation]; - if (self) { - currentCustomDragTypes = 0; - } - return self; -} - -- (void)dealloc -{ - delete currentCustomDragTypes; - [super dealloc]; -} - -- (BOOL)canBecomeKeyWindow -{ - QWidget *widget = [self QT_MANGLE_NAMESPACE(qt_qwidget)]; - if (!widget) - return NO; // This should happen only for qt_root_win - if (QApplicationPrivate::isBlockedByModal(widget)) - return NO; - - bool isToolTip = (widget->windowType() == Qt::ToolTip); - bool isPopup = (widget->windowType() == Qt::Popup); - return !(isPopup || isToolTip); -} - -- (BOOL)canBecomeMainWindow -{ - QWidget *widget = [self QT_MANGLE_NAMESPACE(qt_qwidget)]; - if (!widget) - return NO; // This should happen only for qt_root_win - if ([self isSheet]) - return NO; - - bool isToolTip = (widget->windowType() == Qt::ToolTip); - bool isPopup = (widget->windowType() == Qt::Popup); - bool isTool = (widget->windowType() == Qt::Tool); - return !(isPopup || isToolTip || isTool); -} - -- (void)becomeMainWindow -{ - [super becomeMainWindow]; - // Cocoa sometimes tell a hidden window to become the - // main window (and as such, show it). This can e.g - // happend when the application gets activated. If - // this is the case, we tell it to hide again: - if (![self isVisible]) - [self orderOut:self]; -} - -- (void)toggleToolbarShown:(id)sender -{ - macSendToolbarChangeEvent([self QT_MANGLE_NAMESPACE(qt_qwidget)]); - [super toggleToolbarShown:sender]; -} - -- (void)flagsChanged:(NSEvent *)theEvent -{ - qt_dispatchModifiersChanged(theEvent, [self QT_MANGLE_NAMESPACE(qt_qwidget)]); - [super flagsChanged:theEvent]; -} - - -- (void)tabletProximity:(NSEvent *)tabletEvent -{ - qt_dispatchTabletProximityEvent(tabletEvent); -} - -- (void)terminate:(id)sender -{ - // This function is called from the quit item in the menubar when this window - // is in the first responder chain (see also qtDispatcherToQAction above) - [NSApp terminate:sender]; -} - -- (void)setLevel:(NSInteger)windowLevel -{ - // Cocoa will upon activating/deactivating applications level modal - // windows up and down, regardsless of any explicit set window level. - // To ensure that modal stays-on-top dialogs actually stays on top after - // the application is activated (and therefore stacks in front of - // other stays-on-top windows), we need to add this little special-case override: - QWidget *widget = [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] qt_qwidgetForWindow:self]; - if (widget && widget->isModal() && (widget->windowFlags() & Qt::WindowStaysOnTopHint)) - [super setLevel:NSPopUpMenuWindowLevel]; - else - [super setLevel:windowLevel]; -} - -- (void)sendEvent:(NSEvent *)event -{ - [self retain]; - - bool handled = false; - switch([event type]) { - case NSMouseMoved: - // Cocoa sends move events to a parent and all its children under the mouse, much - // like Qt handles hover events. But we only want to handle the move event once, so - // to optimize a bit (since we subscribe for move event for all views), we handle it - // here before this logic happends. Note: it might be tempting to do this shortcut for - // all mouse events. The problem is that Cocoa does more than just find the correct view - // when sending the event, like raising windows etc. So avoid it as much as possible: - handled = qt_mac_handleMouseEvent(event, QEvent::MouseMove, Qt::NoButton, 0); - break; - default: - break; - } - - if (!handled) { - [super sendEvent:event]; - qt_mac_handleNonClientAreaMouseEvent(self, event); - } - [self release]; -} - -- (void)setInitialFirstResponder:(NSView *)view -{ - // This method is called the first time the window is placed on screen and - // is the earliest point in time we can connect OpenGL contexts to NSViews. - QWidget *qwidget = [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] qt_qwidgetForWindow:self]; - if (qwidget) { - qt_event_request_window_change(qwidget); - qt_mac_send_posted_gl_updates(qwidget); - } - - [super setInitialFirstResponder:view]; -} - -- (BOOL)makeFirstResponder:(NSResponder *)responder -{ - // For some reason Cocoa wants to flip the first responder - // when Qt doesn't want to, sorry, but "No" :-) - if (responder == nil && qApp->focusWidget()) - return NO; - return [super makeFirstResponder:responder]; -} - -+ (Class)frameViewClassForStyleMask:(NSUInteger)styleMask -{ - if (styleMask & QtMacCustomizeWindow) - return [QT_MANGLE_NAMESPACE(QCocoaWindowCustomThemeFrame) class]; - return [super frameViewClassForStyleMask:styleMask]; -} - -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_6 -- (void)touchesBeganWithEvent:(NSEvent *)event; -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetTouch = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, 0, &widgetToGetTouch); - if (!widgetToGetTouch) - return; - - bool all = widgetToGetTouch->testAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents); - qt_translateRawTouchEvent(widgetToGetTouch, QTouchEvent::TouchPad, QCocoaTouch::getCurrentTouchPointList(event, all)); -} - -- (void)touchesMovedWithEvent:(NSEvent *)event; -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetTouch = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, 0, &widgetToGetTouch); - if (!widgetToGetTouch) - return; - - bool all = widgetToGetTouch->testAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents); - qt_translateRawTouchEvent(widgetToGetTouch, QTouchEvent::TouchPad, QCocoaTouch::getCurrentTouchPointList(event, all)); -} - -- (void)touchesEndedWithEvent:(NSEvent *)event; -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetTouch = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, 0, &widgetToGetTouch); - if (!widgetToGetTouch) - return; - - bool all = widgetToGetTouch->testAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents); - qt_translateRawTouchEvent(widgetToGetTouch, QTouchEvent::TouchPad, QCocoaTouch::getCurrentTouchPointList(event, all)); -} - -- (void)touchesCancelledWithEvent:(NSEvent *)event; -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetTouch = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, 0, &widgetToGetTouch); - if (!widgetToGetTouch) - return; - - bool all = widgetToGetTouch->testAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents); - qt_translateRawTouchEvent(widgetToGetTouch, QTouchEvent::TouchPad, QCocoaTouch::getCurrentTouchPointList(event, all)); -} -#endif // MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_6 - --(void)registerDragTypes -{ - // Calling registerForDraggedTypes below is slow, so only do - // it once for each window, or when the custom types change. - QMacCocoaAutoReleasePool pool; - const QStringList& customTypes = qEnabledDraggedTypes(); - if (currentCustomDragTypes == 0 || *currentCustomDragTypes != customTypes) { - if (currentCustomDragTypes == 0) - currentCustomDragTypes = new QStringList(); - *currentCustomDragTypes = customTypes; - const NSString* mimeTypeGeneric = @"com.trolltech.qt.MimeTypeName"; - NSMutableArray *supportedTypes = [NSMutableArray arrayWithObjects:NSColorPboardType, - NSFilenamesPboardType, NSStringPboardType, - NSFilenamesPboardType, NSPostScriptPboardType, NSTIFFPboardType, - NSRTFPboardType, NSTabularTextPboardType, NSFontPboardType, - NSRulerPboardType, NSFileContentsPboardType, NSColorPboardType, - NSRTFDPboardType, NSHTMLPboardType, NSPICTPboardType, - NSURLPboardType, NSPDFPboardType, NSVCardPboardType, - NSFilesPromisePboardType, NSInkTextPboardType, - NSMultipleTextSelectionPboardType, mimeTypeGeneric, nil]; - // Add custom types supported by the application. - for (int i = 0; i < customTypes.size(); i++) { - [supportedTypes addObject:qt_mac_QStringToNSString(customTypes[i])]; - } - [self registerForDraggedTypes:supportedTypes]; - } -} - -- (void)removeDropData -{ - if (dropData) { - delete dropData; - dropData = 0; - } -} - -- (void)addDropData:(id )sender -{ - [self removeDropData]; - CFStringRef dropPasteboard = (CFStringRef) [[sender draggingPasteboard] name]; - dropData = new QCocoaDropData(dropPasteboard); -} - -- (void)changeDraggingCursor:(NSDragOperation)newOperation -{ - static SEL action = nil; - static bool operationSupported = false; - if (action == nil) { - action = NSSelectorFromString(@"operationNotAllowedCursor"); - if ([NSCursor respondsToSelector:action]) { - operationSupported = true; - } - } - if (operationSupported) { - NSCursor *notAllowedCursor = [NSCursor performSelector:action]; - bool isNotAllowedCursor = ([NSCursor currentCursor] == notAllowedCursor); - if (newOperation == NSDragOperationNone && !isNotAllowedCursor) { - [notAllowedCursor push]; - } else if (newOperation != NSDragOperationNone && isNotAllowedCursor) { - [notAllowedCursor pop]; - } - - } -} - -- (NSDragOperation)draggingEntered:(id )sender -{ - // The user dragged something into the window. Send a draggingEntered message - // to the QWidget under the mouse. As the drag moves over the window, and over - // different widgets, we will handle enter and leave events from within - // draggingUpdated below. The reason why we handle this ourselves rather than - // subscribing for drag events directly in QCocoaView is that calling - // registerForDraggedTypes on the views will severly degrade initialization time - // for an application that uses a lot of drag subscribing widgets. - - NSPoint nswindowPoint = [sender draggingLocation]; - NSPoint nsglobalPoint = [[sender draggingDestinationWindow] convertBaseToScreen:nswindowPoint]; - QPoint globalPoint = flipPoint(nsglobalPoint).toPoint(); - - QWidget *qwidget = QApplication::widgetAt(globalPoint); - *currentDragTarget() = qwidget; - if (!qwidget) - return [super draggingEntered:sender]; - if (qwidget->testAttribute(Qt::WA_DropSiteRegistered) == false) - return NSDragOperationNone; - - [self addDropData:sender]; - - QMimeData *mimeData = dropData; - if (QDragManager::self()->source()) - mimeData = QDragManager::self()->dragPrivate()->data; - - NSDragOperation nsActions = [sender draggingSourceOperationMask]; - Qt::DropActions qtAllowed = qt_mac_mapNSDragOperations(nsActions); - QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec.lastOperation) = nsActions; - Qt::KeyboardModifiers modifiers = Qt::NoModifier; - - if ([sender draggingSource] != nil) { - // modifier flags might have changed, update it here since we don't send any input events. - QApplicationPrivate::modifier_buttons = qt_cocoaModifiers2QtModifiers([[NSApp currentEvent] modifierFlags]); - modifiers = QApplication::keyboardModifiers(); - } else { - // when the source is from another application the above technique will not work. - modifiers = qt_cocoaDragOperation2QtModifiers(nsActions); - } - - // send the drag enter event to the widget. - QPoint localPoint(qwidget->mapFromGlobal(globalPoint)); - QDragEnterEvent qDEEvent(localPoint, qtAllowed, mimeData, QApplication::mouseButtons(), modifiers); - QApplication::sendEvent(qwidget, &qDEEvent); - - if (!qDEEvent.isAccepted()) { - // The enter event was not accepted. We mark this by removing - // the drop data so we don't send subsequent drag move events: - [self removeDropData]; - [self changeDraggingCursor:NSDragOperationNone]; - return NSDragOperationNone; - } else { - // Send a drag move event immediately after a drag enter event (as per documentation). - QDragMoveEvent qDMEvent(localPoint, qtAllowed, mimeData, QApplication::mouseButtons(), modifiers); - qDMEvent.setDropAction(qDEEvent.dropAction()); - qDMEvent.accept(); // accept by default, since enter event was accepted. - QApplication::sendEvent(qwidget, &qDMEvent); - - if (!qDMEvent.isAccepted() || qDMEvent.dropAction() == Qt::IgnoreAction) { - // Since we accepted the drag enter event, the widget expects - // future drage move events. - nsActions = NSDragOperationNone; - // Save as ignored in the answer rect. - qDMEvent.setDropAction(Qt::IgnoreAction); - } else { - nsActions = QT_PREPEND_NAMESPACE(qt_mac_mapDropAction)(qDMEvent.dropAction()); - } - - QT_PREPEND_NAMESPACE(qt_mac_copy_answer_rect)(qDMEvent); - [self changeDraggingCursor:nsActions]; - return nsActions; - } - } - -- (NSDragOperation)draggingUpdated:(id )sender -{ - NSPoint nswindowPoint = [sender draggingLocation]; - NSPoint nsglobalPoint = [[sender draggingDestinationWindow] convertBaseToScreen:nswindowPoint]; - QPoint globalPoint = flipPoint(nsglobalPoint).toPoint(); - - QWidget *qwidget = QApplication::widgetAt(globalPoint); - if (!qwidget) - return [super draggingEntered:sender]; - - // First, check if the widget under the mouse has changed since the - // last drag move events. If so, we need to change target, and dispatch - // syntetic drag enter/leave events: - if (qwidget != *currentDragTarget()) { - if (*currentDragTarget() && dropData) { - QDragLeaveEvent de; - QApplication::sendEvent(*currentDragTarget(), &de); - [self removeDropData]; - } - return [self draggingEntered:sender]; - } - - if (qwidget->testAttribute(Qt::WA_DropSiteRegistered) == false) - return NSDragOperationNone; - - // If we have no drop data (which will be assigned inside draggingEntered), it means - // that the current drag target did not accept the enter event. If so, we ignore - // subsequent move events as well: - if (dropData == 0) { - [self changeDraggingCursor:NSDragOperationNone]; - return NSDragOperationNone; - } - - // If the mouse is still within the accepted rect (provided by - // the application on a previous event), we follow the optimization - // and just return the answer given at that point: - NSDragOperation nsActions = [sender draggingSourceOperationMask]; - QPoint localPoint(qwidget->mapFromGlobal(globalPoint)); - if (qt_mac_mouse_inside_answer_rect(localPoint) - && QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec.lastOperation) == nsActions) { - NSDragOperation operation = QT_PREPEND_NAMESPACE(qt_mac_mapDropActions)(QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec.lastAction)); - [self changeDraggingCursor:operation]; - return operation; - } - - QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec.lastOperation) = nsActions; - Qt::DropActions qtAllowed = QT_PREPEND_NAMESPACE(qt_mac_mapNSDragOperations)(nsActions); - Qt::KeyboardModifiers modifiers = Qt::NoModifier; - - // Update modifiers: - if ([sender draggingSource] != nil) { - QApplicationPrivate::modifier_buttons = qt_cocoaModifiers2QtModifiers([[NSApp currentEvent] modifierFlags]); - modifiers = QApplication::keyboardModifiers(); - } else { - modifiers = qt_cocoaDragOperation2QtModifiers(nsActions); - } - - QMimeData *mimeData = dropData; - if (QDragManager::self()->source()) - mimeData = QDragManager::self()->dragPrivate()->data; - - // Insert the same drop action on the event according to - // what the application told us it should be on the previous event: - QDragMoveEvent qDMEvent(localPoint, qtAllowed, mimeData, QApplication::mouseButtons(), modifiers); - if (QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec).lastAction != Qt::IgnoreAction - && QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec).buttons == qDMEvent.mouseButtons() - && QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec).modifiers == qDMEvent.keyboardModifiers()) - qDMEvent.setDropAction(QT_PREPEND_NAMESPACE(qt_mac_dnd_answer_rec).lastAction); - - // Now, end the drag move event to the widget: - qDMEvent.accept(); - QApplication::sendEvent(qwidget, &qDMEvent); - - NSDragOperation operation = qt_mac_mapDropAction(qDMEvent.dropAction()); - if (!qDMEvent.isAccepted() || qDMEvent.dropAction() == Qt::IgnoreAction) { - // Ignore this event (we will still receive further - // notifications), save as ignored in the answer rect: - operation = NSDragOperationNone; - qDMEvent.setDropAction(Qt::IgnoreAction); - } - - qt_mac_copy_answer_rect(qDMEvent); - [self changeDraggingCursor:operation]; - - return operation; -} - -- (void)draggingExited:(id )sender -{ - NSPoint nswindowPoint = [sender draggingLocation]; - NSPoint nsglobalPoint = [[sender draggingDestinationWindow] convertBaseToScreen:nswindowPoint]; - QPoint globalPoint = flipPoint(nsglobalPoint).toPoint(); - - QWidget *qwidget = *currentDragTarget(); - if (!qwidget) - return [super draggingExited:sender]; - - if (dropData) { - QDragLeaveEvent de; - QApplication::sendEvent(qwidget, &de); - [self removeDropData]; - } - - // Clean-up: - [self removeDropData]; - *currentDragTarget() = 0; - [self changeDraggingCursor:NSDragOperationEvery]; -} - -- (BOOL)performDragOperation:(id )sender -{ - QWidget *qwidget = *currentDragTarget(); - if (!qwidget) - return NO; - - *currentDragTarget() = 0; - NSPoint nswindowPoint = [sender draggingLocation]; - NSPoint nsglobalPoint = [[sender draggingDestinationWindow] convertBaseToScreen:nswindowPoint]; - QPoint globalPoint = flipPoint(nsglobalPoint).toPoint(); - - [self addDropData:sender]; - - NSDragOperation nsActions = [sender draggingSourceOperationMask]; - Qt::DropActions qtAllowed = qt_mac_mapNSDragOperations(nsActions); - QMimeData *mimeData = dropData; - - if (QDragManager::self()->source()) - mimeData = QDragManager::self()->dragPrivate()->data; - if (QDragManager::self()->object) - QDragManager::self()->dragPrivate()->target = qwidget; - - QPoint localPoint(qwidget->mapFromGlobal(globalPoint)); - QDropEvent de(localPoint, qtAllowed, mimeData, - QApplication::mouseButtons(), QApplication::keyboardModifiers()); - QApplication::sendEvent(qwidget, &de); - - if (QDragManager::self()->object) - QDragManager::self()->dragPrivate()->executed_action = de.dropAction(); - - return de.isAccepted(); -} - -// This is a hack and it should be removed once we find the real cause for -// the painting problems. -// We have a static variable that signals if we have been called before or not. -static bool firstDrawingInvocation = true; - -// The method below exists only as a workaround to draw/not draw the baseline -// in the title bar. This is to support unifiedToolbar look. - -// This method is very special. To begin with, it is a -// method that will get called only if we enable documentMode. -// Furthermore, it won't get called as a normal method, we swap -// this method with the normal implementation of drawRect in -// _NSThemeFrame. When this method is active, its mission is to -// first call the original drawRect implementation so the widget -// gets proper painting. After that, it needs to detect if there -// is a toolbar or not, in order to decide how to handle the unified -// look. The distinction is important since the presence and -// visibility of a toolbar change the way we enter into unified mode. -// When there is a toolbar and that toolbar is visible, the problem -// is as simple as to tell the toolbar not to draw its baseline. -// However when there is not toolbar or the toolbar is not visible, -// we need to draw a line on top of the baseline, because the baseline -// in that case will belong to the title. For this case we need to draw -// a line on top of the baseline. -// As usual, there is a special case. When we first are called, we might -// need to repaint ourselves one more time. We only need that if we -// didn't get the activation, i.e. when we are launched via the command -// line. And this only if the toolbar is visible from the beginning, -// so we have a special flag that signals if we need to repaint or not. -- (void)drawRectSpecial:(NSRect)rect -{ - // Call the original drawing method. - [id(self) drawRectOriginal:rect]; - NSWindow *window = [id(self) window]; - NSToolbar *toolbar = [window toolbar]; - if(!toolbar) { - // There is no toolbar, we have to draw a line on top of the line drawn by Cocoa. - macDrawRectOnTop((void *)window); - } else { - if([toolbar isVisible]) { - // We tell Cocoa to avoid drawing the line at the end. - if(firstDrawingInvocation) { - firstDrawingInvocation = false; - macSyncDrawingOnFirstInvocation((void *)window); - } else - [toolbar setShowsBaselineSeparator:NO]; - } else { - // There is a toolbar but it is not visible so - // we have to draw a line on top of the line drawn by Cocoa. - macDrawRectOnTop((void *)window); - } - } -} - -- (void)drawRectOriginal:(NSRect)rect -{ - Q_UNUSED(rect) - // This method implementation is here to silenct the compiler. - // See drawRectSpecial for information. -} - diff --git a/src/widgets/platforms/mac/qcocoaview_mac.mm b/src/widgets/platforms/mac/qcocoaview_mac.mm deleted file mode 100644 index f4b2b8d..0000000 --- a/src/widgets/platforms/mac/qcocoaview_mac.mm +++ /dev/null @@ -1,1386 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#import - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -@interface NSEvent (Qt_Compile_Leopard_DeviceDelta) - - (CGFloat)deviceDeltaX; - - (CGFloat)deviceDeltaY; - - (CGFloat)deviceDeltaZ; -@end - -@interface NSEvent (Qt_Compile_Leopard_Gestures) - - (CGFloat)magnification; -@end - -QT_BEGIN_NAMESPACE - -extern void qt_mac_update_cursor(); // qcursor_mac.mm -extern bool qt_sendSpontaneousEvent(QObject *, QEvent *); // qapplication.cpp -extern QPointer qt_last_mouse_receiver; // qapplication_mac.cpp -extern QPointer qt_last_native_mouse_receiver; // qt_cocoa_helpers_mac.mm -extern OSViewRef qt_mac_nativeview_for(const QWidget *w); // qwidget_mac.mm -extern OSViewRef qt_mac_effectiveview_for(const QWidget *w); // qwidget_mac.mm -extern QPointer qt_button_down; //qapplication_mac.cpp -extern Qt::MouseButton cocoaButton2QtButton(NSInteger buttonNum); -extern QWidget *mac_mouse_grabber; -extern bool qt_mac_clearDirtyOnWidgetInsideDrawWidget; // qwidget.cpp - -static QColor colorFrom(NSColor *color) -{ - QColor qtColor; - NSString *colorSpace = [color colorSpaceName]; - if (colorSpace == NSDeviceCMYKColorSpace) { - CGFloat cyan, magenta, yellow, black, alpha; - [color getCyan:&cyan magenta:&magenta yellow:&yellow black:&black alpha:&alpha]; - qtColor.setCmykF(cyan, magenta, yellow, black, alpha); - } else { - NSColor *tmpColor; - tmpColor = [color colorUsingColorSpaceName:NSDeviceRGBColorSpace]; - CGFloat red, green, blue, alpha; - [tmpColor getRed:&red green:&green blue:&blue alpha:&alpha]; - qtColor.setRgbF(red, green, blue, alpha); - } - return qtColor; -} - -QT_END_NAMESPACE - -QT_FORWARD_DECLARE_CLASS(QMacCocoaAutoReleasePool) -QT_FORWARD_DECLARE_CLASS(QCFString) -QT_FORWARD_DECLARE_CLASS(QDragManager) -QT_FORWARD_DECLARE_CLASS(QMimeData) -QT_FORWARD_DECLARE_CLASS(QPoint) -QT_FORWARD_DECLARE_CLASS(QApplication) -QT_FORWARD_DECLARE_CLASS(QApplicationPrivate) -QT_FORWARD_DECLARE_CLASS(QDragEnterEvent) -QT_FORWARD_DECLARE_CLASS(QDragMoveEvent) -QT_FORWARD_DECLARE_CLASS(QStringList) -QT_FORWARD_DECLARE_CLASS(QString) -QT_FORWARD_DECLARE_CLASS(QRect) -QT_FORWARD_DECLARE_CLASS(QRegion) -QT_FORWARD_DECLARE_CLASS(QAbstractScrollArea) -QT_FORWARD_DECLARE_CLASS(QAbstractScrollAreaPrivate) -QT_FORWARD_DECLARE_CLASS(QPaintEvent) -QT_FORWARD_DECLARE_CLASS(QPainter) -QT_FORWARD_DECLARE_CLASS(QHoverEvent) -QT_FORWARD_DECLARE_CLASS(QCursor) -QT_USE_NAMESPACE -extern "C" { - extern NSString *NSTextInputReplacementRangeAttributeName; -} - -//#define ALIEN_DEBUG 1 -#ifdef ALIEN_DEBUG -static int qCocoaViewCount = 0; -#endif - -@implementation QT_MANGLE_NAMESPACE(QCocoaView) - -- (id)initWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate -{ - self = [super init]; - if (self) { - [self finishInitWithQWidget:widget widgetPrivate:widgetprivate]; - } - [self setFocusRingType:NSFocusRingTypeNone]; - composingText = new QString(); - -#ifdef ALIEN_DEBUG - ++qCocoaViewCount; - qDebug() << "Alien: create native view for" << widget << ". qCocoaViewCount is:" << qCocoaViewCount; -#endif - - composing = false; - sendKeyEvents = true; - fromKeyDownEvent = false; - alienTouchCount = 0; - - [self setHidden:YES]; - return self; -} - -- (void) finishInitWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate -{ - qwidget = widget; - qwidgetprivate = widgetprivate; - [[NSNotificationCenter defaultCenter] addObserver:self - selector:@selector(frameDidChange:) - name:@"NSViewFrameDidChangeNotification" - object:self]; -} - -- (void)dealloc -{ - QMacCocoaAutoReleasePool pool; - delete composingText; - [[NSNotificationCenter defaultCenter] removeObserver:self]; - -#ifdef ALIEN_DEBUG - --qCocoaViewCount; - qDebug() << "Alien: widget deallocated. qCocoaViewCount is:" << qCocoaViewCount; -#endif - - [super dealloc]; -} - -- (BOOL)isOpaque -{ - if (!qwidgetprivate) - return [super isOpaque]; - return qwidgetprivate->isOpaque; -} - -- (BOOL)isFlipped -{ - return YES; -} - -// We preserve the content of the view if WA_StaticContents is defined. -// -// More info in the Cocoa documentation: -// http://developer.apple.com/mac/library/documentation/cocoa/conceptual/CocoaViewsGuide/Optimizing/Optimizing.html -- (BOOL) preservesContentDuringLiveResize -{ - return qwidget->testAttribute(Qt::WA_StaticContents); -} - -- (void) setFrameSize:(NSSize)newSize -{ - [super setFrameSize:newSize]; - - // A change in size has required the view to be invalidated. - if ([self inLiveResize]) { - NSRect rects[4]; - NSInteger count; - [self getRectsExposedDuringLiveResize:rects count:&count]; - while (count-- > 0) - { - [self setNeedsDisplayInRect:rects[count]]; - } - } else { - [self setNeedsDisplay:YES]; - } - - // Make sure the opengl context is updated on resize. - if (qwidgetprivate && qwidgetprivate->isGLWidget && [self window]) { - qwidgetprivate->needWindowChange = true; - QEvent event(QEvent::MacGLWindowChange); - qApp->sendEvent(qwidget, &event); - } -} - -// We catch the 'setNeedsDisplay:' message in order to avoid a useless full repaint. -// During the resize, the top of the widget is repainted, probably because of the -// change of coordinate space (Quartz vs Qt). This is then followed by this message: -// -[NSView _setNeedsDisplayIfTopLeftChanged] -// which force a full repaint by sending the message 'setNeedsDisplay:'. -// That is what we are preventing here. -- (void)setNeedsDisplay:(BOOL)flag { - if (![self inLiveResize] || !(qwidget->testAttribute(Qt::WA_StaticContents))) { - [super setNeedsDisplay:flag]; - } -} - -- (void)drawRect:(NSRect)aRect -{ - if (!qwidget) - return; - - // Getting context. - CGContextRef context = (CGContextRef)[[NSGraphicsContext currentContext] graphicsPort]; - qt_mac_retain_graphics_context(context); - - // We use a different graphics system. - // - // Widgets that are set to paint on screen, specifically QGLWidget, - // requires the native engine to execute in order to be drawn. - if (QApplicationPrivate::graphicsSystem() != 0 && !qwidget->testAttribute(Qt::WA_PaintOnScreen)) { - - // Raster engine. - if (QApplicationPrivate::graphics_system_name == QLatin1String("raster")) { - - if (!qwidgetprivate->isInUnifiedToolbar) { - - // Qt handles the painting occuring inside the window. - // Cocoa also keeps track of all widgets as NSView and therefore might - // ask for a repainting of a widget even if Qt is already taking care of it. - // - // The only valid reason for Cocoa to call drawRect: is for window manipulation - // (ie. resize, ...). - // - // Qt will then forward the update to the children. - if (!qwidget->isWindow()) { - qt_mac_release_graphics_context(context); - return; - } - - QRasterWindowSurface *winSurface = dynamic_cast(qwidget->windowSurface()); - if (!winSurface || !winSurface->needsFlush) { - qt_mac_release_graphics_context(context); - return; - } - - // Clip to region. - const QVector &rects = winSurface->regionToFlush.rects(); - for (int i = 0; i < rects.size(); ++i) { - const QRect &rect = rects.at(i); - CGContextAddRect(context, CGRectMake(rect.x(), rect.y(), rect.width(), rect.height())); - } - CGContextClip(context); - - QRect r = winSurface->regionToFlush.boundingRect(); - const CGRect area = CGRectMake(r.x(), r.y(), r.width(), r.height()); - - qt_mac_draw_image(context, winSurface->imageContext(), area, area); - - winSurface->needsFlush = false; - winSurface->regionToFlush = QRegion(); - - } else { - - QUnifiedToolbarSurface *unifiedSurface = qwidgetprivate->unifiedSurface; - if (!unifiedSurface) { - qt_mac_release_graphics_context(context); - return; - } - - int areaX = qwidgetprivate->toolbar_offset.x(); - int areaY = qwidgetprivate->toolbar_offset.y(); - int areaWidth = qwidget->geometry().width(); - int areaHeight = qwidget->geometry().height(); - const CGRect area = CGRectMake(areaX, areaY, areaWidth, areaHeight); - const CGRect drawingArea = CGRectMake(0, 0, areaWidth, areaHeight); - - qt_mac_draw_image(context, unifiedSurface->imageContext(), area, drawingArea); - - qwidgetprivate->flushRequested = false; - - } - - CGContextFlush(context); - qt_mac_release_graphics_context(context); - return; - } - - // Qt handles the painting occuring inside the window. - // Cocoa also keeps track of all widgets as NSView and therefore might - // ask for a repainting of a widget even if Qt is already taking care of it. - // - // The only valid reason for Cocoa to call drawRect: is for window manipulation - // (ie. resize, ...). - // - // Qt will then forward the update to the children. - if (qwidget->isWindow()) { - qwidgetprivate->syncBackingStore(qwidget->rect()); - } - } - - // Native engine. - qwidgetprivate->hd = context; - - if (qwidget->isVisible() && qwidget->updatesEnabled()) { //process the actual paint event. - if (qwidget->testAttribute(Qt::WA_WState_InPaintEvent)) - qWarning("QWidget::repaint: Recursive repaint detected"); - - const QRect qrect = QRect(aRect.origin.x, aRect.origin.y, aRect.size.width, aRect.size.height); - QRegion qrgn; - - const NSRect *rects; - NSInteger count; - [self getRectsBeingDrawn:&rects count:&count]; - for (int i = 0; i < count; ++i) { - QRect tmpRect = QRect(rects[i].origin.x, rects[i].origin.y, rects[i].size.width, rects[i].size.height); - qrgn += tmpRect; - } - - if (!qwidget->isWindow() && !qobject_cast(qwidget->parent())) { - const QRegion &parentMask = qwidget->window()->mask(); - if (!parentMask.isEmpty()) { - const QPoint mappedPoint = qwidget->mapTo(qwidget->window(), qrect.topLeft()); - qrgn.translate(mappedPoint); - qrgn &= parentMask; - qrgn.translate(-mappedPoint.x(), -mappedPoint.y()); - } - } - - QPoint redirectionOffset(0, 0); - //setup the context - qwidget->setAttribute(Qt::WA_WState_InPaintEvent); - QPaintEngine *engine = qwidget->paintEngine(); - if (engine) - engine->setSystemClip(qrgn); - if (qwidgetprivate->extra && qwidgetprivate->extra->hasMask) { - CGRect widgetRect = CGRectMake(0, 0, qwidget->width(), qwidget->height()); - CGContextTranslateCTM (context, 0, widgetRect.size.height); - CGContextScaleCTM(context, 1, -1); - if (qwidget->isWindow()) - CGContextClearRect(context, widgetRect); - CGContextClipToMask(context, widgetRect, qwidgetprivate->extra->imageMask); - CGContextScaleCTM(context, 1, -1); - CGContextTranslateCTM (context, 0, -widgetRect.size.height); - } - - if (qwidget->isWindow() && !qwidgetprivate->isOpaque - && !qwidget->testAttribute(Qt::WA_MacBrushedMetal)) { - CGContextClearRect(context, NSRectToCGRect(aRect)); - } - - qwidget->setAttribute(Qt::WA_WState_InPaintEvent, false); - QWidgetPrivate *qwidgetPrivate = qt_widget_private(qwidget); - - // We specify that we want to draw the widget itself, and - // all its children recursive. But we skip native children, because - // they will receive drawRect calls by themselves as needed: - int flags = QWidgetPrivate::DrawPaintOnScreen - | QWidgetPrivate::DrawRecursive - | QWidgetPrivate::DontDrawNativeChildren; - - if (qwidget->isWindow()) - flags |= QWidgetPrivate::DrawAsRoot; - - // Start to draw: - qt_mac_clearDirtyOnWidgetInsideDrawWidget = true; - qwidgetPrivate->drawWidget(qwidget, qrgn, QPoint(), flags, 0); - qt_mac_clearDirtyOnWidgetInsideDrawWidget = false; - - if (!redirectionOffset.isNull()) - QPainter::restoreRedirected(qwidget); - if (engine) - engine->setSystemClip(QRegion()); - qwidget->setAttribute(Qt::WA_WState_InPaintEvent, false); - if(!qwidget->testAttribute(Qt::WA_PaintOutsidePaintEvent) && qwidget->paintingActive()) - qWarning("QWidget: It is dangerous to leave painters active on a" - " widget outside of the PaintEvent"); - } - qwidgetprivate->hd = 0; - qt_mac_release_graphics_context(context); -} - -- (BOOL)acceptsFirstMouse:(NSEvent *)theEvent -{ - // Find the widget that should receive the event: - QPoint qlocal, qglobal; - QWidget *widgetToGetMouse = qt_mac_getTargetForMouseEvent(theEvent, QEvent::MouseButtonPress, qlocal, qglobal, qwidget, 0); - if (!widgetToGetMouse) - return NO; - - return !widgetToGetMouse->testAttribute(Qt::WA_MacNoClickThrough); -} - -- (NSView *)hitTest:(NSPoint)aPoint -{ - if (!qwidget) - return [super hitTest:aPoint]; - - if (qwidget->testAttribute(Qt::WA_TransparentForMouseEvents)) - return nil; // You cannot hit a transparent for mouse event widget. - return [super hitTest:aPoint]; -} - -- (void)updateTrackingAreas -{ - if (!qwidget) - return; - - // [NSView addTrackingArea] is slow, so bail out early if we can: - if (NSIsEmptyRect([self visibleRect])) - return; - - QMacCocoaAutoReleasePool pool; - if (NSArray *trackingArray = [self trackingAreas]) { - NSUInteger size = [trackingArray count]; - for (NSUInteger i = 0; i < size; ++i) { - NSTrackingArea *t = [trackingArray objectAtIndex:i]; - [self removeTrackingArea:t]; - } - } - - // Ideally, we shouldn't have NSTrackingMouseMoved events included below, it should - // only be turned on if mouseTracking, hover is on or a tool tip is set. - // Unfortunately, Qt will send "tooltip" events on mouse moves, so we need to - // turn it on in ALL case. That means EVERY QCocoaView gets to pay the cost of - // mouse moves delivered to it (Apple recommends keeping it OFF because there - // is a performance hit). So it goes. - NSUInteger trackingOptions = NSTrackingMouseEnteredAndExited | NSTrackingActiveInActiveApp - | NSTrackingInVisibleRect | NSTrackingMouseMoved; - NSTrackingArea *ta = [[NSTrackingArea alloc] initWithRect:NSMakeRect(0, 0, - qwidget->width(), - qwidget->height()) - options:trackingOptions - owner:self - userInfo:nil]; - [self addTrackingArea:ta]; - [ta release]; -} - -- (void)mouseEntered:(NSEvent *)event -{ - // Cocoa will not send a move event on mouseEnter. But since - // Qt expect this, we fake one now. See also mouseExited below - // for info about enter/leave event handling - NSEvent *nsmoveEvent = [NSEvent - mouseEventWithType:NSMouseMoved - location:[[self window] mouseLocationOutsideOfEventStream] - modifierFlags: [event modifierFlags] - timestamp: [event timestamp] - windowNumber: [event windowNumber] - context: [event context] - eventNumber: [event eventNumber] - clickCount: 0 - pressure: 0]; - - // Important: Cocoa sends us mouseEnter on all views under the mouse - // and not just the one on top. Therefore, to we cannot use qwidget - // as native widget for this case. Instead, we let qt_mac_handleMouseEvent - // resolve it (last argument set to 0): - qt_mac_handleMouseEvent(nsmoveEvent, QEvent::MouseMove, Qt::NoButton, 0); -} - -- (void)mouseExited:(NSEvent *)event -{ - // Note: normal enter/leave handling is done from within mouseMove. This handler - // catches the case when the mouse moves out of the window (which mouseMove do not). - // Updating the mouse cursor follows the same logic as enter/leave. And we update - // neither if a grab exists (even if the grab points to this widget, it seems, ref X11) - Q_UNUSED(event); - if (self == [[self window] contentView] && !qt_button_down && !QWidget::mouseGrabber()) { - qt_mac_update_cursor(); - // If the mouse exits the content view, but qt_mac_getTargetForMouseEvent still - // reports a target, it means that either there is a grab involved, or the mouse - // hovered over another window in the application. In both cases, move events will - // cause qt_mac_handleMouseEvent to be called, which will handle enter/leave. - QPoint qlocal, qglobal; - QWidget *widgetUnderMouse = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Leave, qlocal, qglobal, qwidget, &widgetUnderMouse); - - if (widgetUnderMouse == 0) { - QApplicationPrivate::dispatchEnterLeave(0, qt_last_mouse_receiver); - qt_last_mouse_receiver = 0; - qt_last_native_mouse_receiver = 0; - } - } -} - -- (void)flagsChanged:(NSEvent *)theEvent -{ - QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget); - if (!widgetToGetKey) - return; - - qt_dispatchModifiersChanged(theEvent, widgetToGetKey); - [super flagsChanged:theEvent]; -} - -- (void)mouseMoved:(NSEvent *)theEvent -{ - // Important: this method will only be called when the view's window is _not_ inside - // QCocoaWindow/QCocoaPanel. Otherwise, [QCocoaWindow sendEvent] will handle the event - // before it ends up here. So, this method is added for supporting QMacNativeWidget. - // TODO: Cocoa send move events to all views under the mouse. So make sure we only - // handle the event for the widget on top when using QMacNativeWidget. - qt_mac_handleMouseEvent(theEvent, QEvent::MouseMove, Qt::NoButton, qwidget); -} - -- (void)mouseDown:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonPress, Qt::LeftButton, qwidget); - // Don't call super here. This prevents us from getting the mouseUp event, - // which we need to send even if the mouseDown event was not accepted. - // (this is standard Qt behavior.) -} - -- (void)mouseUp:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonRelease, Qt::LeftButton, qwidget); -} - -- (void)rightMouseDown:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonPress, Qt::RightButton, qwidget); -} - -- (void)rightMouseUp:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonRelease, Qt::RightButton, qwidget); -} - -- (void)otherMouseDown:(NSEvent *)theEvent -{ - Qt::MouseButton mouseButton = cocoaButton2QtButton([theEvent buttonNumber]); - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonPress, mouseButton, qwidget); -} - -- (void)otherMouseUp:(NSEvent *)theEvent -{ - Qt::MouseButton mouseButton = cocoaButton2QtButton([theEvent buttonNumber]); - qt_mac_handleMouseEvent(theEvent, QEvent::MouseButtonRelease, mouseButton, qwidget); -} - -- (void)mouseDragged:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseMove, Qt::NoButton, qwidget); -} - -- (void)rightMouseDragged:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseMove, Qt::NoButton, qwidget); -} - -- (void)otherMouseDragged:(NSEvent *)theEvent -{ - qt_mac_handleMouseEvent(theEvent, QEvent::MouseMove, Qt::NoButton, qwidget); -} - -- (void)scrollWheel:(NSEvent *)theEvent -{ - // Give the Input Manager a chance to process the wheel event. - NSInputManager *currentIManager = [NSInputManager currentInputManager]; - if (currentIManager && [currentIManager wantsToHandleMouseEvents]) { - [currentIManager handleMouseEvent:theEvent]; - } - - Qt::MouseButtons buttons = QApplication::mouseButtons(); - Qt::KeyboardModifiers keyMods = qt_cocoaModifiers2QtModifiers([theEvent modifierFlags]); - - // Find the widget that should receive the event: - QPoint qlocal, qglobal; - QWidget *widgetToGetMouse = qt_mac_getTargetForMouseEvent(theEvent, QEvent::Wheel, qlocal, qglobal, qwidget, 0); - if (!widgetToGetMouse) - return; - - int deltaX = 0; - int deltaY = 0; - int deltaZ = 0; - - const EventRef carbonEvent = (EventRef)[theEvent eventRef]; - const UInt32 carbonEventKind = carbonEvent ? ::GetEventKind(carbonEvent) : 0; - const bool scrollEvent = carbonEventKind == kEventMouseScroll; - - if (scrollEvent) { - // The mouse device containts pixel scroll wheel support (Mighty Mouse, Trackpad). - // Since deviceDelta is delivered as pixels rather than degrees, we need to - // convert from pixels to degrees in a sensible manner. - // It looks like 1/4 degrees per pixel behaves most native. - // (NB: Qt expects the unit for delta to be 8 per degree): - const int pixelsToDegrees = 2; // 8 * 1/4 - deltaX = [theEvent deviceDeltaX] * pixelsToDegrees; - deltaY = [theEvent deviceDeltaY] * pixelsToDegrees; - deltaZ = [theEvent deviceDeltaZ] * pixelsToDegrees; - } else { - // carbonEventKind == kEventMouseWheelMoved - // Remove acceleration, and use either -120 or 120 as delta: - deltaX = qBound(-120, int([theEvent deltaX] * 10000), 120); - deltaY = qBound(-120, int([theEvent deltaY] * 10000), 120); - deltaZ = qBound(-120, int([theEvent deltaZ] * 10000), 120); - } - -#ifndef QT_NO_WHEELEVENT - // ### Qt 5: Send one QWheelEvent with dx, dy and dz - - if (deltaX != 0 && deltaY != 0) - QMacScrollOptimization::initDelayedScroll(); - - if (deltaX != 0) { - QWheelEvent qwe(qlocal, qglobal, deltaX, buttons, keyMods, Qt::Horizontal); - qt_sendSpontaneousEvent(widgetToGetMouse, &qwe); - } - - if (deltaY != 0) { - QWheelEvent qwe(qlocal, qglobal, deltaY, buttons, keyMods, Qt::Vertical); - qt_sendSpontaneousEvent(widgetToGetMouse, &qwe); - } - - if (deltaZ != 0) { - // Qt doesn't explicitly support wheels with a Z component. In a misguided attempt to - // try to be ahead of the pack, I'm adding this extra value. - QWheelEvent qwe(qlocal, qglobal, deltaZ, buttons, keyMods, (Qt::Orientation)3); - qt_sendSpontaneousEvent(widgetToGetMouse, &qwe); - } - - if (deltaX != 0 && deltaY != 0) - QMacScrollOptimization::performDelayedScroll(); -#endif //QT_NO_WHEELEVENT -} - -- (void)tabletProximity:(NSEvent *)tabletEvent -{ - qt_dispatchTabletProximityEvent(tabletEvent); -} - -- (void)tabletPoint:(NSEvent *)tabletEvent -{ - if (!qt_mac_handleTabletEvent(self, tabletEvent)) - [super tabletPoint:tabletEvent]; -} - -- (void)magnifyWithEvent:(NSEvent *)event -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetGesture = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, qwidget, &widgetToGetGesture); - if (!widgetToGetGesture) - return; - if (!QApplicationPrivate::tryModalHelper(widgetToGetGesture, 0)) - return; - -#ifndef QT_NO_GESTURES - QNativeGestureEvent qNGEvent; - qNGEvent.gestureType = QNativeGestureEvent::Zoom; - NSPoint p = [[event window] convertBaseToScreen:[event locationInWindow]]; - qNGEvent.position = flipPoint(p).toPoint(); - qNGEvent.percentage = [event magnification]; - qt_sendSpontaneousEvent(widgetToGetGesture, &qNGEvent); -#endif // QT_NO_GESTURES -} - -- (void)rotateWithEvent:(NSEvent *)event -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetGesture = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, qwidget, &widgetToGetGesture); - if (!widgetToGetGesture) - return; - if (!QApplicationPrivate::tryModalHelper(widgetToGetGesture, 0)) - return; - -#ifndef QT_NO_GESTURES - QNativeGestureEvent qNGEvent; - qNGEvent.gestureType = QNativeGestureEvent::Rotate; - NSPoint p = [[event window] convertBaseToScreen:[event locationInWindow]]; - qNGEvent.position = flipPoint(p).toPoint(); - qNGEvent.percentage = -[event rotation]; - qt_sendSpontaneousEvent(widgetToGetGesture, &qNGEvent); -#endif // QT_NO_GESTURES -} - -- (void)swipeWithEvent:(NSEvent *)event -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetGesture = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, qwidget, &widgetToGetGesture); - if (!widgetToGetGesture) - return; - if (!QApplicationPrivate::tryModalHelper(widgetToGetGesture, 0)) - return; - -#ifndef QT_NO_GESTURES - QNativeGestureEvent qNGEvent; - qNGEvent.gestureType = QNativeGestureEvent::Swipe; - NSPoint p = [[event window] convertBaseToScreen:[event locationInWindow]]; - qNGEvent.position = flipPoint(p).toPoint(); - if ([event deltaX] == 1) - qNGEvent.angle = 180.0f; - else if ([event deltaX] == -1) - qNGEvent.angle = 0.0f; - else if ([event deltaY] == 1) - qNGEvent.angle = 90.0f; - else if ([event deltaY] == -1) - qNGEvent.angle = 270.0f; - qt_sendSpontaneousEvent(widgetToGetGesture, &qNGEvent); -#endif // QT_NO_GESTURES -} - -- (void)beginGestureWithEvent:(NSEvent *)event -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetGesture = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, qwidget, &widgetToGetGesture); - if (!widgetToGetGesture) - return; - if (!QApplicationPrivate::tryModalHelper(widgetToGetGesture, 0)) - return; - -#ifndef QT_NO_GESTURES - QNativeGestureEvent qNGEvent; - qNGEvent.gestureType = QNativeGestureEvent::GestureBegin; - NSPoint p = [[event window] convertBaseToScreen:[event locationInWindow]]; - qNGEvent.position = flipPoint(p).toPoint(); - qt_sendSpontaneousEvent(widgetToGetGesture, &qNGEvent); -#endif // QT_NO_GESTURES -} - -- (void)endGestureWithEvent:(NSEvent *)event -{ - QPoint qlocal, qglobal; - QWidget *widgetToGetGesture = 0; - qt_mac_getTargetForMouseEvent(event, QEvent::Gesture, qlocal, qglobal, qwidget, &widgetToGetGesture); - if (!widgetToGetGesture) - return; - if (!QApplicationPrivate::tryModalHelper(widgetToGetGesture, 0)) - return; - -#ifndef QT_NO_GESTURES - QNativeGestureEvent qNGEvent; - qNGEvent.gestureType = QNativeGestureEvent::GestureEnd; - NSPoint p = [[event window] convertBaseToScreen:[event locationInWindow]]; - qNGEvent.position = flipPoint(p).toPoint(); - qt_sendSpontaneousEvent(widgetToGetGesture, &qNGEvent); -} -#endif // QT_NO_GESTURES - -- (void)frameDidChange:(NSNotification *)note -{ - Q_UNUSED(note); - if (!qwidget) - return; - if (qwidget->isWindow()) - return; - NSRect newFrame = [self frame]; - QRect newGeo(newFrame.origin.x, newFrame.origin.y, newFrame.size.width, newFrame.size.height); - bool moved = qwidget->testAttribute(Qt::WA_Moved); - bool resized = qwidget->testAttribute(Qt::WA_Resized); - qwidget->setGeometry(newGeo); - qwidget->setAttribute(Qt::WA_Moved, moved); - qwidget->setAttribute(Qt::WA_Resized, resized); - qwidgetprivate->syncCocoaMask(); -} - -- (BOOL)isEnabled -{ - if (!qwidget) - return [super isEnabled]; - return [super isEnabled] && qwidget->isEnabled(); -} - -- (void)setEnabled:(BOOL)flag -{ - QMacCocoaAutoReleasePool pool; - [super setEnabled:flag]; - if (qwidget && qwidget->isEnabled() != flag) - qwidget->setEnabled(flag); -} - -+ (Class)cellClass -{ - return [NSActionCell class]; -} - -- (BOOL)acceptsFirstResponder -{ - if (!qwidget) - return NO; - - // Disabled widget shouldn't get focus even if it's a window. - // hence disabled windows will not get any key or mouse events. - if (!qwidget->isEnabled()) - return NO; - - if (qwidget->isWindow() && !qt_widget_private(qwidget)->topData()->embedded) { - QWidget *focusWidget = qApp->focusWidget(); - if (!focusWidget) { - // There is no focus widget, but we still want to receive key events - // for shortcut handling etc. So we accept first responer for the - // content view as a last resort: - return YES; - } - if (!focusWidget->internalWinId() && focusWidget->nativeParentWidget() == qwidget) { - // The current focus widget is alien, and hence, cannot get acceptsFirstResponder - // calls. Since the focus widget is a child of qwidget, we let this view say YES: - return YES; - } - if (focusWidget->window() != qwidget) { - // The current focus widget is in another window. Since cocoa - // suggest that this window should be key now, we accept: - return YES; - } - } - - return qwidget->focusPolicy() != Qt::NoFocus; -} - -- (BOOL)resignFirstResponder -{ - if (!qwidget) - return YES; - - // Seems like the following test only triggers if this - // view is inside a QMacNativeWidget: -// if (QWidget *fw = QApplication::focusWidget()) { -// if (qwidget == fw || qwidget == fw->nativeParentWidget()) -// fw->clearFocus(); -// } - return YES; -} - -- (BOOL)becomeFirstResponder -{ - // see the comment in the acceptsFirstResponder - if the window "stole" focus - // let it become the responder, but don't tell Qt - if (qwidget && qt_widget_private(qwidget->window())->topData()->embedded - && !QApplication::focusWidget() && qwidget->focusPolicy() != Qt::NoFocus) - qwidget->setFocus(Qt::OtherFocusReason); - return YES; -} - -- (NSDragOperation)draggingSourceOperationMaskForLocal:(BOOL)isLocal -{ - Q_UNUSED(isLocal); - return supportedActions; -} - -- (void)setSupportedActions:(NSDragOperation)actions -{ - supportedActions = actions; -} - -- (void)draggedImage:(NSImage *)anImage endedAt:(NSPoint)aPoint operation:(NSDragOperation)operation -{ - Q_UNUSED(anImage); - Q_UNUSED(aPoint); - macCurrentDnDParameters()->performedAction = operation; - if (QDragManager::self()->object - && QDragManager::self()->dragPrivate()->executed_action != Qt::ActionMask) { - macCurrentDnDParameters()->performedAction = - qt_mac_mapDropAction(QDragManager::self()->dragPrivate()->executed_action); - } -} - -- (QWidget *)qt_qwidget -{ - return qwidget; -} - -- (void) qt_clearQWidget -{ - qwidget = 0; - qwidgetprivate = 0; -} - -- (void)keyDown:(NSEvent *)theEvent -{ - if (!qwidget) - return; - QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget); - if (!widgetToGetKey) - return; - - sendKeyEvents = true; - - if (widgetToGetKey->testAttribute(Qt::WA_InputMethodEnabled) - && !(widgetToGetKey->inputMethodHints() & Qt::ImhDigitsOnly - || widgetToGetKey->inputMethodHints() & Qt::ImhFormattedNumbersOnly - || widgetToGetKey->inputMethodHints() & Qt::ImhHiddenText)) { - fromKeyDownEvent = true; - [qt_mac_nativeview_for(qwidget) interpretKeyEvents:[NSArray arrayWithObject: theEvent]]; - fromKeyDownEvent = false; - } - - if (sendKeyEvents && !composing) { - bool keyEventEaten = qt_dispatchKeyEvent(theEvent, widgetToGetKey); - if (!keyEventEaten && qwidget) { - // The event is not yet eaten, and if Qt is embedded inside a native - // cocoa application, send it to first responder not owned by Qt. - // The exception is if widgetToGetKey was redirected to a popup. - QWidget *toplevel = qwidget->window(); - if (toplevel == widgetToGetKey->window()) { - if (qt_widget_private(toplevel)->topData()->embedded) { - if (NSResponder *w = [qt_mac_nativeview_for(toplevel) superview]) - [w keyDown:theEvent]; - } - } - } - } -} - - -- (void)keyUp:(NSEvent *)theEvent -{ - if (sendKeyEvents) { - QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget); - if (!widgetToGetKey) - return; - - bool keyEventEaten = qt_dispatchKeyEvent(theEvent, widgetToGetKey); - if (!keyEventEaten && qwidget) { - // The event is not yet eaten, and if Qt is embedded inside a native - // cocoa application, send it to first responder not owned by Qt. - // The exception is if widgetToGetKey was redirected to a popup. - QWidget *toplevel = qwidget->window(); - if (toplevel == widgetToGetKey->window()) { - if (qt_widget_private(toplevel)->topData()->embedded) { - if (NSResponder *w = [qt_mac_nativeview_for(toplevel) superview]) - [w keyUp:theEvent]; - } - } - } - } -} - -- (void)viewWillMoveToWindow:(NSWindow *)window -{ - if (qwidget == 0) - return; - - if (qwidget->windowFlags() & Qt::MSWindowsOwnDC - && (window != [self window])) { // OpenGL Widget - QEvent event(QEvent::MacGLClearDrawable); - qApp->sendEvent(qwidget, &event); - } -} - -- (void)viewDidMoveToWindow -{ - if (qwidget == 0) - return; - - if (qwidget->windowFlags() & Qt::MSWindowsOwnDC && [self window]) { - // call update paint event - qwidgetprivate->needWindowChange = true; - QEvent event(QEvent::MacGLWindowChange); - qApp->sendEvent(qwidget, &event); - } -} - - -// NSTextInput Protocol implementation - -- (void) insertText:(id)aString -{ - QString commitText; - if ([aString length]) { - if ([aString isKindOfClass:[NSAttributedString class]]) { - commitText = QCFString::toQString(reinterpret_cast([aString string])); - } else { - commitText = QCFString::toQString(reinterpret_cast(aString)); - }; - } - - // When entering characters through Character Viewer or Keyboard Viewer, the text is passed - // through this insertText method. Since we dont receive a keyDown Event in such cases, the - // composing flag will be false. - if (([aString length] && composing) || !fromKeyDownEvent) { - // Send the commit string to the widget. - composing = false; - sendKeyEvents = false; - QInputMethodEvent e; - e.setCommitString(commitText); - if (QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget)) - qt_sendSpontaneousEvent(widgetToGetKey, &e); - } else { - // The key sequence "`q" on a French Keyboard will generate two calls to insertText before - // it returns from interpretKeyEvents. The first call will turn off 'composing' and accept - // the "`" key. The last keyDown event needs to be processed by the widget to get the - // character "q". The string parameter is ignored for the second call. - sendKeyEvents = true; - } - - composingText->clear(); -} - -- (void) setMarkedText:(id)aString selectedRange:(NSRange)selRange -{ - // Generate the QInputMethodEvent with preedit string and the attributes - // for rendering it. The attributes handled here are 'underline', - // 'underline color' and 'cursor position'. - sendKeyEvents = false; - composing = true; - QString qtText; - // Cursor position is retrived from the range. - QList attrs; - attrs<([aString string])); - composingLength = qtText.length(); - int index = 0; - // Create attributes for individual sections of preedit text - while (index < composingLength) { - NSRange effectiveRange; - NSRange range = NSMakeRange(index, composingLength-index); - NSDictionary *attributes = [aString attributesAtIndex:index - longestEffectiveRange:&effectiveRange - inRange:range]; - NSNumber *underlineStyle = [attributes objectForKey:NSUnderlineStyleAttributeName]; - if (underlineStyle) { - QColor clr (Qt::black); - NSColor *color = [attributes objectForKey:NSUnderlineColorAttributeName]; - if (color) { - clr = colorFrom(color); - } - QTextCharFormat format; - format.setFontUnderline(true); - format.setUnderlineColor(clr); - attrs<(aString)); - composingLength = qtText.length(); - } - // Make sure that we have at least one text format. - if (attrs.size() <= 1) { - QTextCharFormat format; - format.setFontUnderline(true); - attrs<clear(); - composing = false; -} - -- (BOOL) hasMarkedText -{ - return (composing ? YES: NO); -} - -- (void) doCommandBySelector:(SEL)aSelector -{ - Q_UNUSED(aSelector); -} - -- (BOOL)isComposing -{ - return composing; -} - -- (NSInteger) conversationIdentifier -{ - // Return a unique identifier fot this ime conversation - return (NSInteger)self; -} - -- (NSAttributedString *) attributedSubstringFromRange:(NSRange)theRange -{ - QString selectedText(qwidget->inputMethodQuery(Qt::ImCurrentSelection).toString()); - if (!selectedText.isEmpty()) { - QCFString string(selectedText.mid(theRange.location, theRange.length)); - const NSString *tmpString = reinterpret_cast((CFStringRef)string); - return [[[NSAttributedString alloc] initWithString:const_cast(tmpString)] autorelease]; - } else { - return nil; - } -} - -- (NSRange) markedRange -{ - NSRange range; - if (composing) { - range.location = 0; - range.length = composingLength; - } else { - range.location = NSNotFound; - range.length = 0; - } - return range; -} - -- (NSRange) selectedRange -{ - NSRange selRange; - QString selectedText(qwidget->inputMethodQuery(Qt::ImCurrentSelection).toString()); - if (!selectedText.isEmpty()) { - // Consider only the selected text. - selRange.location = 0; - selRange.length = selectedText.length(); - } else { - // No selected text. - selRange.location = NSNotFound; - selRange.length = 0; - } - return selRange; - -} - -- (NSRect) firstRectForCharacterRange:(NSRange)theRange -{ - Q_UNUSED(theRange); - // The returned rect is always based on the internal cursor. - QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget); - if (!widgetToGetKey) - return NSZeroRect; - - QRect mr(widgetToGetKey->inputMethodQuery(Qt::ImMicroFocus).toRect()); - QPoint mp(widgetToGetKey->mapToGlobal(QPoint(mr.bottomLeft()))); - NSRect rect ; - rect.origin.x = mp.x(); - rect.origin.y = flipYCoordinate(mp.y()); - rect.size.width = mr.width(); - rect.size.height = mr.height(); - return rect; -} - -- (NSUInteger)characterIndexForPoint:(NSPoint)thePoint -{ - // We dont support cursor movements using mouse while composing. - Q_UNUSED(thePoint); - return NSNotFound; -} - -- (NSArray*) validAttributesForMarkedText -{ - QWidget *widgetToGetKey = qt_mac_getTargetForKeyEvent(qwidget); - if (!widgetToGetKey) - return nil; - - if (!widgetToGetKey->testAttribute(Qt::WA_InputMethodEnabled)) - return nil; // Not sure if that's correct, but it's saves a malloc. - - // Support only underline color/style. - return [NSArray arrayWithObjects:NSUnderlineColorAttributeName, - NSUnderlineStyleAttributeName, nil]; -} -@end - -QT_BEGIN_NAMESPACE -void QMacInputContext::reset() -{ - QWidget *w = QInputContext::focusWidget(); - if (w) { - NSView *view = qt_mac_effectiveview_for(w); - if ([view isKindOfClass:[QT_MANGLE_NAMESPACE(QCocoaView) class]]) { - QMacCocoaAutoReleasePool pool; - QT_MANGLE_NAMESPACE(QCocoaView) *qc = static_cast(view); - NSInputManager *currentIManager = [NSInputManager currentInputManager]; - if (currentIManager) { - [currentIManager markedTextAbandoned:view]; - [qc unmarkText]; - } - } - } -} - -bool QMacInputContext::isComposing() const -{ - QWidget *w = QInputContext::focusWidget(); - if (w) { - NSView *view = qt_mac_effectiveview_for(w); - if ([view isKindOfClass:[QT_MANGLE_NAMESPACE(QCocoaView) class]]) { - return [static_cast(view) isComposing]; - } - } - return false; -} - -extern bool qt_mac_in_drag; -void * /*NSImage */qt_mac_create_nsimage(const QPixmap &pm); -static const int default_pm_hotx = -2; -static const int default_pm_hoty = -16; -static const char* default_pm[] = { - "13 9 3 1", - ". c None", - " c #000000", - "X c #FFFFFF", - "X X X X X X X", - " X X X X X X ", - "X ......... X", - " X.........X ", - "X ......... X", - " X.........X ", - "X ......... X", - " X X X X X X ", - "X X X X X X X", -}; - -Qt::DropAction QDragManager::drag(QDrag *o) -{ - if(qt_mac_in_drag) { //just make sure.. - qWarning("Qt: Internal error: WH0A, unexpected condition reached"); - return Qt::IgnoreAction; - } - if(object == o) - return Qt::IgnoreAction; - /* At the moment it seems clear that Mac OS X does not want to drag with a non-left button - so we just bail early to prevent it */ - if(!(GetCurrentEventButtonState() & kEventMouseButtonPrimary)) - return Qt::IgnoreAction; - - if(object) { - dragPrivate()->source->removeEventFilter(this); - cancel(); - beingCancelled = false; - } - - object = o; - dragPrivate()->target = 0; - -#ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(this, 0, QAccessible::DragDropStart); -#endif - - // setup the data - QMacPasteboard dragBoard((CFStringRef) NSDragPboard, QMacPasteboardMime::MIME_DND); - dragPrivate()->data->setData(QLatin1String("application/x-qt-mime-type-name"), QByteArray("dummy")); - dragBoard.setMimeData(dragPrivate()->data); - - // create the image - QPoint hotspot; - QPixmap pix = dragPrivate()->pixmap; - if(pix.isNull()) { - if(dragPrivate()->data->hasText() || dragPrivate()->data->hasUrls()) { - // get the string - QString s = dragPrivate()->data->hasText() ? dragPrivate()->data->text() - : dragPrivate()->data->urls().first().toString(); - if(s.length() > 26) - s = s.left(23) + QChar(0x2026); - if(!s.isEmpty()) { - // draw it - QFont f(qApp->font()); - f.setPointSize(12); - QFontMetrics fm(f); - QPixmap tmp(fm.width(s), fm.height()); - if(!tmp.isNull()) { - QPainter p(&tmp); - p.fillRect(0, 0, tmp.width(), tmp.height(), Qt::color0); - p.setPen(Qt::color1); - p.setFont(f); - p.drawText(0, fm.ascent(), s); - // save it - pix = tmp; - hotspot = QPoint(tmp.width() / 2, tmp.height() / 2); - } - } - } else { - pix = QPixmap(default_pm); - hotspot = QPoint(default_pm_hotx, default_pm_hoty); - } - } else { - hotspot = dragPrivate()->hotspot; - } - - // Convert the image to NSImage: - NSImage *image = (NSImage *)qt_mac_create_nsimage(pix); - [image retain]; - - DnDParams *dndParams = macCurrentDnDParameters(); - QT_MANGLE_NAMESPACE(QCocoaView) *theView = static_cast(dndParams->view); - - // Save supported actions: - [theView setSupportedActions: qt_mac_mapDropActions(dragPrivate()->possible_actions)]; - QPoint pointInView = [theView qt_qwidget]->mapFromGlobal(dndParams->globalPoint); - NSPoint imageLoc = {pointInView.x() - hotspot.x(), pointInView.y() + pix.height() - hotspot.y()}; - NSSize mouseOffset = {0.0, 0.0}; - NSPasteboard *pboard = [NSPasteboard pasteboardWithName:NSDragPboard]; - dragPrivate()->executed_action = Qt::ActionMask; - - // Execute the drag: - [theView retain]; - [theView dragImage:image - at:imageLoc - offset:mouseOffset - event:dndParams->theEvent - pasteboard:pboard - source:theView - slideBack:YES]; - - // Reset the implicit grab widget when drag ends because we will not - // receive the mouse release event when DND is active: - qt_button_down = 0; - [theView release]; - [image release]; - if (dragPrivate()) - dragPrivate()->executed_action = Qt::IgnoreAction; - object = 0; - Qt::DropAction performedAction(qt_mac_mapNSDragOperation(dndParams->performedAction)); - - // Do post drag processing, if required. - if (performedAction != Qt::IgnoreAction) { - // Check if the receiver points us to a file location. - // if so, we need to do the file copy/move ourselves. - QCFType pasteLocation = 0; - PasteboardCopyPasteLocation(dragBoard.pasteBoard(), &pasteLocation); - if (pasteLocation) { - QList urls = o->mimeData()->urls(); - for (int i = 0; i < urls.size(); ++i) { - QUrl fromUrl = urls.at(i); - QString filename = QFileInfo(fromUrl.path()).fileName(); - QUrl toUrl(QCFString::toQString(CFURLGetString(pasteLocation)) + filename); - if (performedAction == Qt::MoveAction) - QFile::rename(fromUrl.path(), toUrl.path()); - else if (performedAction == Qt::CopyAction) - QFile::copy(fromUrl.path(), toUrl.path()); - } - } - } - - // Clean-up: - o->setMimeData(0); - o->deleteLater(); - return performedAction; -} - -QT_END_NAMESPACE - diff --git a/src/widgets/platforms/mac/qcocoaview_mac_p.h b/src/widgets/platforms/mac/qcocoaview_mac_p.h deleted file mode 100644 index e534e7a..0000000 --- a/src/widgets/platforms/mac/qcocoaview_mac_p.h +++ /dev/null @@ -1,85 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include -#import - -@class QT_MANGLE_NAMESPACE(QCocoaView); -QT_FORWARD_DECLARE_CLASS(QWidgetPrivate); -QT_FORWARD_DECLARE_CLASS(QWidget); -QT_FORWARD_DECLARE_CLASS(QEvent); -QT_FORWARD_DECLARE_CLASS(QString); -QT_FORWARD_DECLARE_CLASS(QStringList); - -Q_WIDGETS_EXPORT -@interface QT_MANGLE_NAMESPACE(QCocoaView) : NSControl { - QWidget *qwidget; - QWidgetPrivate *qwidgetprivate; - NSDragOperation supportedActions; - bool composing; - int composingLength; - bool sendKeyEvents; - bool fromKeyDownEvent; - QString *composingText; - @public int alienTouchCount; -} -- (id)initWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate; -- (void) finishInitWithQWidget:(QWidget *)widget widgetPrivate:(QWidgetPrivate *)widgetprivate; -- (void)frameDidChange:(NSNotification *)note; -- (void)setSupportedActions:(NSDragOperation)actions; -- (NSDragOperation)draggingSourceOperationMaskForLocal:(BOOL)isLocal; -- (void)draggedImage:(NSImage *)anImage endedAt:(NSPoint)aPoint operation:(NSDragOperation)operation; -- (BOOL)isComposing; -- (QWidget *)qt_qwidget; -- (void) qt_clearQWidget; - -@end diff --git a/src/widgets/platforms/mac/qcocoawindow_mac.mm b/src/widgets/platforms/mac/qcocoawindow_mac.mm deleted file mode 100644 index 918e5a0..0000000 --- a/src/widgets/platforms/mac/qcocoawindow_mac.mm +++ /dev/null @@ -1,88 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qmacdefines_mac.h" -#import -#import -#import -#import -#import -#import -#import -#import - -#include - -QT_FORWARD_DECLARE_CLASS(QWidget); -QT_USE_NAMESPACE - -@implementation NSWindow (QT_MANGLE_NAMESPACE(QWidgetIntegration)) - -- (id)QT_MANGLE_NAMESPACE(qt_initWithQWidget):(QWidget*)widget contentRect:(NSRect)rect styleMask:(NSUInteger)mask -{ - self = [self initWithContentRect:rect styleMask:mask backing:NSBackingStoreBuffered defer:YES]; - if (self) { - [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] becomeDelegteForWindow:self widget:widget]; - [self setReleasedWhenClosed:NO]; - } - return self; -} - -- (QWidget *)QT_MANGLE_NAMESPACE(qt_qwidget) -{ - QWidget *widget = 0; - if ([self delegate] == [QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate]) - widget = [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] qt_qwidgetForWindow:self]; - return widget; -} - -@end - -@implementation QT_MANGLE_NAMESPACE(QCocoaWindow) - -/*********************************************************************** - Copy and Paste between QCocoaWindow and QCocoaPanel - This is a bit unfortunate, but thanks to the dynamic dispatch we - have to duplicate this code or resort to really silly forwarding methods -**************************************************************************/ -#include "qcocoasharedwindowmethods_mac_p.h" - -@end diff --git a/src/widgets/platforms/mac/qcocoawindow_mac_p.h b/src/widgets/platforms/mac/qcocoawindow_mac_p.h deleted file mode 100644 index 83ecb7c..0000000 --- a/src/widgets/platforms/mac/qcocoawindow_mac_p.h +++ /dev/null @@ -1,95 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#ifndef QCOCOAWINDOW_MAC_P -#define QCOCOAWINDOW_MAC_P - -#include "qmacdefines_mac.h" -#import -#include -#include - -enum { QtMacCustomizeWindow = 1 << 21 }; // This will one day be run over by - -QT_FORWARD_DECLARE_CLASS(QWidget); -QT_FORWARD_DECLARE_CLASS(QStringList); -QT_FORWARD_DECLARE_CLASS(QCocoaDropData); - -@interface NSWindow (QtCoverForHackWithCategory) -+ (Class)frameViewClassForStyleMask:(NSUInteger)styleMask; -@end - -@interface NSWindow (QT_MANGLE_NAMESPACE(QWidgetIntegration)) -- (id)QT_MANGLE_NAMESPACE(qt_initWithQWidget):(QWidget *)widget contentRect:(NSRect)rect styleMask:(NSUInteger)mask; -- (QWidget *)QT_MANGLE_NAMESPACE(qt_qwidget); -@end - -@interface NSWindow (QtIntegration) -- (NSDragOperation)draggingEntered:(id )sender; -- (NSDragOperation)draggingUpdated:(id )sender; -- (void)draggingExited:(id )sender; -- (BOOL)performDragOperation:(id )sender; -@end - -@interface QT_MANGLE_NAMESPACE(QCocoaWindow) : NSWindow { - QStringList *currentCustomDragTypes; - QCocoaDropData *dropData; - NSInteger dragEnterSequence; -} - -+ (Class)frameViewClassForStyleMask:(NSUInteger)styleMask; -- (void)registerDragTypes; -- (void)drawRectOriginal:(NSRect)rect; - -@end - -#endif diff --git a/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac.mm b/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac.mm deleted file mode 100644 index f1b3814..0000000 --- a/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac.mm +++ /dev/null @@ -1,60 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qmacdefines_mac.h" - - -#import "private/qcocoawindowcustomthemeframe_mac_p.h" -#import "private/qcocoawindow_mac_p.h" -#include "private/qt_cocoa_helpers_mac_p.h" -#include "qwidget.h" - -@implementation QT_MANGLE_NAMESPACE(QCocoaWindowCustomThemeFrame) - -- (void)_updateButtons -{ - [super _updateButtons]; - NSWindow *window = [self window]; - qt_syncCocoaTitleBarButtons(window, [window QT_MANGLE_NAMESPACE(qt_qwidget)]); -} - -@end - diff --git a/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac_p.h b/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac_p.h deleted file mode 100644 index cd49784..0000000 --- a/src/widgets/platforms/mac/qcocoawindowcustomthemeframe_mac_p.h +++ /dev/null @@ -1,61 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of qapplication_*.cpp, qwidget*.cpp, qcolor_x11.cpp, qfiledialog.cpp -// and many other. This header file may change from version to version -// without notice, or even be removed. -// -// We mean it. -// -#import -#include "qmacdefines_mac.h" -#import "qnsthemeframe_mac_p.h" - -@interface QT_MANGLE_NAMESPACE(QCocoaWindowCustomThemeFrame) : NSThemeFrame -{ -} - -@end diff --git a/src/widgets/platforms/mac/qcocoawindowdelegate_mac.mm b/src/widgets/platforms/mac/qcocoawindowdelegate_mac.mm deleted file mode 100644 index fc89821..0000000 --- a/src/widgets/platforms/mac/qcocoawindowdelegate_mac.mm +++ /dev/null @@ -1,437 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#import "private/qcocoawindowdelegate_mac_p.h" -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -QT_BEGIN_NAMESPACE -extern QWidgetData *qt_qwidget_data(QWidget *); // qwidget.cpp -extern void onApplicationWindowChangedActivation(QWidget *, bool); //qapplication_mac.mm -extern bool qt_sendSpontaneousEvent(QObject *, QEvent *); // qapplication.cpp -QT_END_NAMESPACE - -QT_USE_NAMESPACE - -static QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) *sharedCocoaWindowDelegate = nil; - -// This is a singleton, but unlike most Cocoa singletons, it lives in a library and could be -// pontentially loaded and unloaded. This means we should at least attempt to do the -// memory management correctly. - -static void cleanupCocoaWindowDelegate() -{ - [sharedCocoaWindowDelegate release]; -} - -@implementation QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) - -- (id)init -{ - self = [super init]; - if (self != nil) { - m_windowHash = new QHash(); - m_drawerHash = new QHash(); - } - return self; -} - -- (void)dealloc -{ - sharedCocoaWindowDelegate = nil; - QHash::const_iterator windowIt = m_windowHash->constBegin(); - while (windowIt != m_windowHash->constEnd()) { - [windowIt.key() setDelegate:nil]; - ++windowIt; - } - delete m_windowHash; - QHash::const_iterator drawerIt = m_drawerHash->constBegin(); - while (drawerIt != m_drawerHash->constEnd()) { - [drawerIt.key() setDelegate:nil]; - ++drawerIt; - } - delete m_drawerHash; - [super dealloc]; -} - -+ (id)allocWithZone:(NSZone *)zone -{ - @synchronized(self) { - if (sharedCocoaWindowDelegate == nil) { - sharedCocoaWindowDelegate = [super allocWithZone:zone]; - return sharedCocoaWindowDelegate; - qAddPostRoutine(cleanupCocoaWindowDelegate); - } - } - return nil; -} - -+ (QT_MANGLE_NAMESPACE(QCocoaWindowDelegate)*)sharedDelegate -{ - @synchronized(self) { - if (sharedCocoaWindowDelegate == nil) - [[self alloc] init]; - } - return [[sharedCocoaWindowDelegate retain] autorelease]; -} - --(void)syncSizeForWidget:(QWidget *)qwidget toSize:(const QSize &)newSize fromSize:(const QSize &)oldSize -{ - qt_qwidget_data(qwidget)->crect.setSize(newSize); - // ### static contents optimization needs to go here - const OSViewRef view = qt_mac_nativeview_for(qwidget); - [view setFrameSize:NSMakeSize(newSize.width(), newSize.height())]; - if (!qwidget->isVisible()) { - qwidget->setAttribute(Qt::WA_PendingResizeEvent, true); - } else { - QResizeEvent qre(newSize, oldSize); - if (qwidget->testAttribute(Qt::WA_PendingResizeEvent)) { - qwidget->setAttribute(Qt::WA_PendingResizeEvent, false); - QApplication::sendEvent(qwidget, &qre); - } else { - qt_sendSpontaneousEvent(qwidget, &qre); - } - } -} - -- (void)dumpMaximizedStateforWidget:(QWidget*)qwidget window:(NSWindow *)window -{ - if (!window) - return; // Nothing to do. - QWidgetData *widgetData = qt_qwidget_data(qwidget); - if ((widgetData->window_state & Qt::WindowMaximized) && ![window isZoomed]) { - widgetData->window_state &= ~Qt::WindowMaximized; - QWindowStateChangeEvent e(Qt::WindowState(widgetData->window_state | Qt::WindowMaximized)); - qt_sendSpontaneousEvent(qwidget, &e); - } -} - -- (NSSize)closestAcceptableSizeForWidget:(QWidget *)qwidget window:(NSWindow *)window - withNewSize:(NSSize)proposedSize -{ - [self dumpMaximizedStateforWidget:qwidget window:window]; - QSize newSize = QLayout::closestAcceptableSize(qwidget, - QSize(proposedSize.width, proposedSize.height)); - return [NSWindow frameRectForContentRect: - NSMakeRect(0., 0., newSize.width(), newSize.height()) - styleMask:[window styleMask]].size; -} - -- (NSSize)windowWillResize:(NSWindow *)windowToResize toSize:(NSSize)proposedFrameSize -{ - QWidget *qwidget = m_windowHash->value(windowToResize); - return [self closestAcceptableSizeForWidget:qwidget window:windowToResize - withNewSize:[NSWindow contentRectForFrameRect: - NSMakeRect(0, 0, - proposedFrameSize.width, - proposedFrameSize.height) - styleMask:[windowToResize styleMask]].size]; -} - -- (NSSize)drawerWillResizeContents:(NSDrawer *)sender toSize:(NSSize)contentSize -{ - QWidget *qwidget = m_drawerHash->value(sender); - return [self closestAcceptableSizeForWidget:qwidget window:nil withNewSize:contentSize]; -} - --(void)windowDidMiniaturize:(NSNotification*)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - if (!qwidget->isMinimized()) { - QWidgetData *widgetData = qt_qwidget_data(qwidget); - widgetData->window_state = widgetData->window_state | Qt::WindowMinimized; - QWindowStateChangeEvent e(Qt::WindowStates(widgetData->window_state & ~Qt::WindowMinimized)); - qt_sendSpontaneousEvent(qwidget, &e); - } - // Send hide to match Qt on X11 and Windows - QEvent e(QEvent::Hide); - qt_sendSpontaneousEvent(qwidget, &e); -} - -- (void)windowDidResize:(NSNotification *)notification -{ - NSWindow *window = [notification object]; - QWidget *qwidget = m_windowHash->value(window); - QWidgetData *widgetData = qt_qwidget_data(qwidget); - if (!(qwidget->windowState() & (Qt::WindowMaximized | Qt::WindowFullScreen)) && [window isZoomed]) { - widgetData->window_state = widgetData->window_state | Qt::WindowMaximized; - QWindowStateChangeEvent e(Qt::WindowStates(widgetData->window_state - & ~Qt::WindowMaximized)); - qt_sendSpontaneousEvent(qwidget, &e); - } else { - widgetData->window_state = widgetData->window_state & ~Qt::WindowMaximized; - QWindowStateChangeEvent e(Qt::WindowStates(widgetData->window_state - | Qt::WindowMaximized)); - qt_sendSpontaneousEvent(qwidget, &e); - } - NSRect rect = [[window contentView] frame]; - const QSize newSize(rect.size.width, rect.size.height); - const QSize &oldSize = widgetData->crect.size(); - if (newSize != oldSize) { - QWidgetPrivate::qt_mac_update_sizer(qwidget); - [self syncSizeForWidget:qwidget toSize:newSize fromSize:oldSize]; - } - - // We force the repaint to be synchronized with the resize of the window. - // Otherwise, the resize looks sluggish because we paint one event loop later. - if ([[window contentView] inLiveResize]) { - qwidget->repaint(); - - // We need to repaint the toolbar as well. - QMainWindow* mWindow = qobject_cast(qwidget->window()); - if (mWindow) { - QMainWindowLayout *mLayout = qobject_cast(mWindow->layout()); - QList toolbarList = mLayout->qtoolbarsInUnifiedToolbarList; - - for (int i = 0; i < toolbarList.size(); ++i) { - QToolBar* toolbar = toolbarList.at(i); - toolbar->repaint(); - } - } - } -} - -- (void)windowDidMove:(NSNotification *)notification -{ - // The code underneath needs to translate the window location - // from bottom left (which is the origin used by Cocoa) to - // upper left (which is the origin used by Qt): - NSWindow *window = [notification object]; - NSRect newRect = [window frame]; - QWidget *qwidget = m_windowHash->value(window); - QPoint qtPoint = flipPoint(NSMakePoint(newRect.origin.x, - newRect.origin.y + newRect.size.height)).toPoint(); - const QRect &oldRect = qwidget->frameGeometry(); - - if (qtPoint.x() != oldRect.x() || qtPoint.y() != oldRect.y()) { - QWidgetData *widgetData = qt_qwidget_data(qwidget); - QRect oldCRect = widgetData->crect; - QWidgetPrivate *widgetPrivate = qt_widget_private(qwidget); - const QRect &fStrut = widgetPrivate->frameStrut(); - widgetData->crect.moveTo(qtPoint.x() + fStrut.left(), qtPoint.y() + fStrut.top()); - if (!qwidget->isVisible()) { - qwidget->setAttribute(Qt::WA_PendingMoveEvent, true); - } else { - QMoveEvent qme(qtPoint, oldRect.topLeft()); - qt_sendSpontaneousEvent(qwidget, &qme); - } - } -} - --(BOOL)windowShouldClose:(id)windowThatWantsToClose -{ - QWidget *qwidget = m_windowHash->value(windowThatWantsToClose); - QScopedLoopLevelCounter counter(qt_widget_private(qwidget)->threadData); - return qt_widget_private(qwidget)->close_helper(QWidgetPrivate::CloseWithSpontaneousEvent); -} - --(void)windowDidDeminiaturize:(NSNotification *)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - QWidgetData *widgetData = qt_qwidget_data(qwidget); - Qt::WindowStates currState = Qt::WindowStates(widgetData->window_state); - Qt::WindowStates newState = currState; - if (currState & Qt::WindowMinimized) - newState &= ~Qt::WindowMinimized; - if (!(currState & Qt::WindowActive)) - newState |= Qt::WindowActive; - if (newState != currState) { - widgetData->window_state = newState; - QWindowStateChangeEvent e(currState); - qt_sendSpontaneousEvent(qwidget, &e); - } - QShowEvent qse; - qt_sendSpontaneousEvent(qwidget, &qse); -} - --(void)windowDidBecomeMain:(NSNotification*)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - Q_ASSERT(qwidget); - onApplicationWindowChangedActivation(qwidget, true); -} - --(void)windowDidResignMain:(NSNotification*)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - Q_ASSERT(qwidget); - onApplicationWindowChangedActivation(qwidget, false); -} - -// These are the same as main, but they are probably better to keep separate since there is a -// tiny difference between main and key windows. --(void)windowDidBecomeKey:(NSNotification*)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - Q_ASSERT(qwidget); - onApplicationWindowChangedActivation(qwidget, true); -} - --(void)windowDidResignKey:(NSNotification*)notification -{ - QWidget *qwidget = m_windowHash->value([notification object]); - Q_ASSERT(qwidget); - onApplicationWindowChangedActivation(qwidget, false); -} - --(QWidget *)qt_qwidgetForWindow:(NSWindow *)window -{ - return m_windowHash->value(window); -} - -- (BOOL)windowShouldZoom:(NSWindow *)window toFrame:(NSRect)newFrame -{ - Q_UNUSED(newFrame); - // saving the current window geometry before the window is maximized - QWidget *qwidget = m_windowHash->value(window); - QWidgetPrivate *widgetPrivate = qt_widget_private(qwidget); - if (qwidget->isWindow()) { - if(qwidget->windowState() & Qt::WindowMaximized) { - // Restoring - widgetPrivate->topData()->wasMaximized = false; - } else { - // Maximizing - widgetPrivate->topData()->normalGeometry = qwidget->geometry(); - // If the window was maximized we need to update the coordinates since now it will start at 0,0. - // We do this in a special field that is only used when not restoring but manually resizing the window. - // Since the coordinates are fixed we just set a boolean flag. - widgetPrivate->topData()->wasMaximized = true; - } - } - return YES; -} - -- (NSRect)windowWillUseStandardFrame:(NSWindow *)window defaultFrame:(NSRect)defaultFrame -{ - NSRect frameToReturn = defaultFrame; - QWidget *qwidget = m_windowHash->value(window); - QSizeF size = qwidget->maximumSize(); - NSRect windowFrameRect = [window frame]; - NSRect viewFrameRect = [[window contentView] frame]; - // consider additional size required for titlebar & frame - frameToReturn.size.width = qMin(frameToReturn.size.width, - size.width()+(windowFrameRect.size.width - viewFrameRect.size.width)); - frameToReturn.size.height = qMin(frameToReturn.size.height, - size.height()+(windowFrameRect.size.height - viewFrameRect.size.height)); - return frameToReturn; -} - -- (void)becomeDelegteForWindow:(NSWindow *)window widget:(QWidget *)widget -{ - m_windowHash->insert(window, widget); - [window setDelegate:self]; -} - -- (void)resignDelegateForWindow:(NSWindow *)window -{ - [window setDelegate:nil]; - m_windowHash->remove(window); -} - -- (void)becomeDelegateForDrawer:(NSDrawer *)drawer widget:(QWidget *)widget -{ - m_drawerHash->insert(drawer, widget); - [drawer setDelegate:self]; - NSWindow *window = [[drawer contentView] window]; - [self becomeDelegteForWindow:window widget:widget]; -} - -- (void)resignDelegateForDrawer:(NSDrawer *)drawer -{ - QWidget *widget = m_drawerHash->value(drawer); - [drawer setDelegate:nil]; - if (widget) - [self resignDelegateForWindow:[[drawer contentView] window]]; - m_drawerHash->remove(drawer); -} - -- (BOOL)window:(NSWindow *)window shouldPopUpDocumentPathMenu:(NSMenu *)menu -{ - Q_UNUSED(menu); - QWidget *qwidget = m_windowHash->value(window); - if (qwidget && !qwidget->windowFilePath().isEmpty()) { - return YES; - } - return NO; -} - -- (BOOL)window:(NSWindow *)window shouldDragDocumentWithEvent:(NSEvent *)event - from:(NSPoint)dragImageLocation - withPasteboard:(NSPasteboard *)pasteboard -{ - Q_UNUSED(event); - Q_UNUSED(dragImageLocation); - Q_UNUSED(pasteboard); - QWidget *qwidget = m_windowHash->value(window); - if (qwidget && !qwidget->windowFilePath().isEmpty()) { - return YES; - } - return NO; -} - -- (void)syncContentViewFrame: (NSNotification *)notification -{ - NSView *cView = [notification object]; - if (cView) { - NSWindow *window = [cView window]; - QWidget *qwidget = m_windowHash->value(window); - if (qwidget) { - QWidgetData *widgetData = qt_qwidget_data(qwidget); - NSRect rect = [cView frame]; - const QSize newSize(rect.size.width, rect.size.height); - const QSize &oldSize = widgetData->crect.size(); - if (newSize != oldSize) { - [self syncSizeForWidget:qwidget toSize:newSize fromSize:oldSize]; - } - } - - } -} - -@end diff --git a/src/widgets/platforms/mac/qcocoawindowdelegate_mac_p.h b/src/widgets/platforms/mac/qcocoawindowdelegate_mac_p.h deleted file mode 100644 index 27906e1..0000000 --- a/src/widgets/platforms/mac/qcocoawindowdelegate_mac_p.h +++ /dev/null @@ -1,108 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include "qmacdefines_mac.h" - -#import - -QT_BEGIN_NAMESPACE -template class QHash; -QT_END_NAMESPACE -using QT_PREPEND_NAMESPACE(QHash); -QT_FORWARD_DECLARE_CLASS(QWidget) -QT_FORWARD_DECLARE_CLASS(QSize) -QT_FORWARD_DECLARE_CLASS(QWidgetData) - -#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_5 -@protocol NSWindowDelegate -- (NSSize)windowWillResize:(NSWindow *)window toSize:(NSSize)proposedFrameSize; -- (void)windowDidMiniaturize:(NSNotification*)notification; -- (void)windowDidResize:(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 - -@protocol NSDrawerDelegate -- (NSSize)drawerWillResizeContents:(NSDrawer *)sender toSize:(NSSize)contentSize; -@end - -#endif - - - -@interface QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) : NSObject { - QHash *m_windowHash; - QHash *m_drawerHash; -} -+ (QT_MANGLE_NAMESPACE(QCocoaWindowDelegate)*)sharedDelegate; -- (void)becomeDelegteForWindow:(NSWindow *)window widget:(QWidget *)widget; -- (void)resignDelegateForWindow:(NSWindow *)window; -- (void)becomeDelegateForDrawer:(NSDrawer *)drawer widget:(QWidget *)widget; -- (void)resignDelegateForDrawer:(NSDrawer *)drawer; -- (void)dumpMaximizedStateforWidget:(QWidget*)qwidget window:(NSWindow *)window; -- (void)syncSizeForWidget:(QWidget *)qwidget - toSize:(const QSize &)newSize - fromSize:(const QSize &)oldSize; -- (NSSize)closestAcceptableSizeForWidget:(QWidget *)qwidget - window:(NSWindow *)window withNewSize:(NSSize)proposedSize; -- (QWidget *)qt_qwidgetForWindow:(NSWindow *)window; -- (void)syncContentViewFrame: (NSNotification *)notification; -@end diff --git a/src/widgets/platforms/mac/qcolormap_mac.cpp b/src/widgets/platforms/mac/qcolormap_mac.cpp deleted file mode 100644 index de920d7..0000000 --- a/src/widgets/platforms/mac/qcolormap_mac.cpp +++ /dev/null @@ -1,111 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qcolormap.h" -#include "qcolor.h" - -QT_BEGIN_NAMESPACE - -class QColormapPrivate -{ -public: - inline QColormapPrivate() - : ref(1) - { } - - QAtomicInt ref; -}; -static QColormap *qt_mac_global_map = 0; - -void QColormap::initialize() -{ - qt_mac_global_map = new QColormap; -} - -void QColormap::cleanup() -{ - delete qt_mac_global_map; - qt_mac_global_map = 0; -} - -QColormap QColormap::instance(int) -{ - return *qt_mac_global_map; -} - -QColormap::QColormap() : d(new QColormapPrivate) -{} - -QColormap::QColormap(const QColormap &colormap) :d (colormap.d) -{ d->ref.ref(); } - -QColormap::~QColormap() -{ - if (!d->ref.deref()) - delete d; -} - -QColormap::Mode QColormap::mode() const -{ return QColormap::Direct; } - -int QColormap::depth() const -{ - return 32; -} - -int QColormap::size() const -{ - return -1; -} - -uint QColormap::pixel(const QColor &color) const -{ return color.rgba(); } - -const QColor QColormap::colorAt(uint pixel) const -{ return QColor(pixel); } - -const QVector QColormap::colormap() const -{ return QVector(); } - -QColormap &QColormap::operator=(const QColormap &colormap) -{ qAtomicAssign(d, colormap.d); return *this; } - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qdesktopwidget_mac.mm b/src/widgets/platforms/mac/qdesktopwidget_mac.mm deleted file mode 100644 index 9869eee..0000000 --- a/src/widgets/platforms/mac/qdesktopwidget_mac.mm +++ /dev/null @@ -1,257 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#import - -#include "qapplication.h" -#include "qdesktopwidget.h" -#include -#include "qwidget_p.h" -#include -#include - -QT_BEGIN_NAMESPACE - -QT_USE_NAMESPACE - -/***************************************************************************** - Externals - *****************************************************************************/ - -/***************************************************************************** - QDesktopWidget member functions - *****************************************************************************/ - -Q_GLOBAL_STATIC(QDesktopWidgetImplementation, qdesktopWidgetImplementation) - -QDesktopWidgetImplementation::QDesktopWidgetImplementation() - : appScreen(0) -{ - onResize(); -} - -QDesktopWidgetImplementation::~QDesktopWidgetImplementation() -{ -} - -QDesktopWidgetImplementation *QDesktopWidgetImplementation::instance() -{ - return qdesktopWidgetImplementation(); -} - -QRect QDesktopWidgetImplementation::availableRect(int screenIndex) const -{ - if (screenIndex < 0 || screenIndex >= screenCount) - screenIndex = appScreen; - - return availableRects[screenIndex].toRect(); -} - -QRect QDesktopWidgetImplementation::screenRect(int screenIndex) const -{ - if (screenIndex < 0 || screenIndex >= screenCount) - screenIndex = appScreen; - - return screenRects[screenIndex].toRect(); -} - -void QDesktopWidgetImplementation::onResize() -{ - QMacCocoaAutoReleasePool pool; - NSArray *displays = [NSScreen screens]; - screenCount = [displays count]; - - screenRects.clear(); - availableRects.clear(); - NSRect primaryRect = [[displays objectAtIndex:0] frame]; - for (int i = 0; iappScreen; -} - -int QDesktopWidget::numScreens() const -{ - return qdesktopWidgetImplementation()->screenCount; -} - -QWidget *QDesktopWidget::screen(int) -{ - return this; -} - -const QRect QDesktopWidget::availableGeometry(int screen) const -{ - return qdesktopWidgetImplementation()->availableRect(screen); -} - -const QRect QDesktopWidget::screenGeometry(int screen) const -{ - return qdesktopWidgetImplementation()->screenRect(screen); -} - -int QDesktopWidget::screenNumber(const QWidget *widget) const -{ - QDesktopWidgetImplementation *d = qdesktopWidgetImplementation(); - if (!widget) - return d->appScreen; - QRect frame = widget->frameGeometry(); - if (!widget->isWindow()) - frame.moveTopLeft(widget->mapToGlobal(QPoint(0,0))); - int maxSize = -1, maxScreen = -1; - for (int i = 0; i < d->screenCount; ++i) { - QRect rr = d->screenRect(i); - QRect sect = rr.intersected(frame); - int size = sect.width() * sect.height(); - if (size > maxSize && sect.width() > 0 && sect.height() > 0) { - maxSize = size; - maxScreen = i; - } - } - return maxScreen; -} - -int QDesktopWidget::screenNumber(const QPoint &point) const -{ - QDesktopWidgetImplementation *d = qdesktopWidgetImplementation(); - int closestScreen = -1; - int shortestDistance = INT_MAX; - for (int i = 0; i < d->screenCount; ++i) { - QRect rr = d->screenRect(i); - int thisDistance = QWidgetPrivate::pointToRect(point, rr); - if (thisDistance < shortestDistance) { - shortestDistance = thisDistance; - closestScreen = i; - } - } - return closestScreen; -} - -void QDesktopWidget::resizeEvent(QResizeEvent *) -{ - QDesktopWidgetImplementation *d = qdesktopWidgetImplementation(); - - const int oldScreenCount = d->screenCount; - const QVector oldRects(d->screenRects); - const QVector oldWorks(d->availableRects); - - d->onResize(); - - for (int i = 0; i < qMin(oldScreenCount, d->screenCount); ++i) { - if (oldRects.at(i) != d->screenRects.at(i)) - emit resized(i); - } - for (int i = 0; i < qMin(oldScreenCount, d->screenCount); ++i) { - if (oldWorks.at(i) != d->availableRects.at(i)) - emit workAreaResized(i); - } - - if (oldScreenCount != d->screenCount) - emit screenCountChanged(d->screenCount); -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qdesktopwidget_mac_p.h b/src/widgets/platforms/mac/qdesktopwidget_mac_p.h deleted file mode 100644 index a2d7552..0000000 --- a/src/widgets/platforms/mac/qdesktopwidget_mac_p.h +++ /dev/null @@ -1,75 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include - -QT_BEGIN_NAMESPACE - -class QDesktopWidgetImplementation -{ -public: - QDesktopWidgetImplementation(); - ~QDesktopWidgetImplementation(); - static QDesktopWidgetImplementation *instance(); - - int appScreen; - int screenCount; - - QVector availableRects; - QVector screenRects; - - QRect availableRect(int screenIndex) const; - QRect screenRect(int screenIndex) const; - void onResize(); -}; - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qdnd_mac.mm b/src/widgets/platforms/mac/qdnd_mac.mm deleted file mode 100644 index b554302..0000000 --- a/src/widgets/platforms/mac/qdnd_mac.mm +++ /dev/null @@ -1,261 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qapplication.h" -#ifndef QT_NO_DRAGANDDROP -#include "qbitmap.h" -#include "qcursor.h" -#include "qevent.h" -#include "qpainter.h" -#include "qurl.h" -#include "qwidget.h" -#include "qfile.h" -#include "qfileinfo.h" -#include -#include -#ifndef QT_NO_ACCESSIBILITY -# include "qaccessible.h" -#endif - -#include -#include -#include -#include - -QT_BEGIN_NAMESPACE - -QT_USE_NAMESPACE - -QMacDndAnswerRecord qt_mac_dnd_answer_rec; - -/***************************************************************************** - QDnD debug facilities - *****************************************************************************/ -//#define DEBUG_DRAG_EVENTS -//#define DEBUG_DRAG_PROMISES - -/***************************************************************************** - QDnD globals - *****************************************************************************/ -bool qt_mac_in_drag = false; - -/***************************************************************************** - Externals - *****************************************************************************/ -extern void qt_mac_send_modifiers_changed(quint32, QObject *); //qapplication_mac.cpp -extern uint qGlobalPostedEventsCount(); //qapplication.cpp -extern RgnHandle qt_mac_get_rgn(); // qregion_mac.cpp -extern void qt_mac_dispose_rgn(RgnHandle); // qregion_mac.cpp -/***************************************************************************** - QDnD utility functions - *****************************************************************************/ - -//action management -#ifdef DEBUG_DRAG_EVENTS -# define MAP_MAC_ENUM(x) x, #x -#else -# define MAP_MAC_ENUM(x) x -#endif -struct mac_enum_mapper -{ - int mac_code; - int qt_code; -#ifdef DEBUG_DRAG_EVENTS - char *qt_desc; -#endif -}; - -/***************************************************************************** - DnD functions - *****************************************************************************/ -bool QDropData::hasFormat_sys(const QString &mime) const -{ - Q_UNUSED(mime); - return false; -} - -QVariant QDropData::retrieveData_sys(const QString &mime, QVariant::Type type) const -{ - Q_UNUSED(mime); - Q_UNUSED(type); - return QVariant(); -} - -QStringList QDropData::formats_sys() const -{ - return QStringList(); -} - -void QDragManager::timerEvent(QTimerEvent*) -{ -} - -bool QDragManager::eventFilter(QObject *, QEvent *) -{ - return false; -} - -void QDragManager::updateCursor() -{ -} - -void QDragManager::cancel(bool) -{ - if(object) { - beingCancelled = true; - object = 0; - } -#ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(this, 0, QAccessible::DragDropEnd); -#endif -} - -void QDragManager::move(const QPoint &) -{ -} - -void QDragManager::drop() -{ -} - -/** - If a drop action is already set on the carbon event - (from e.g. an earlier enter event), we insert the same - action on the new Qt event that has yet to be sendt. -*/ -static inline bool qt_mac_set_existing_drop_action(const DragRef &dragRef, QDropEvent &event) -{ - Q_UNUSED(dragRef); - Q_UNUSED(event); - return false; -} - -/** - If an answer rect has been set on the event (after being sent - to the global event processor), we store that rect so we can - check if the mouse is in the same area upon next drag move event. -*/ -void qt_mac_copy_answer_rect(const QDragMoveEvent &event) -{ - if (!event.answerRect().isEmpty()) { - qt_mac_dnd_answer_rec.rect = event.answerRect(); - qt_mac_dnd_answer_rec.buttons = event.mouseButtons(); - qt_mac_dnd_answer_rec.modifiers = event.keyboardModifiers(); - qt_mac_dnd_answer_rec.lastAction = event.dropAction(); - } -} - -bool qt_mac_mouse_inside_answer_rect(QPoint mouse) -{ - if (!qt_mac_dnd_answer_rec.rect.isEmpty() - && qt_mac_dnd_answer_rec.rect.contains(mouse) - && QApplication::mouseButtons() == qt_mac_dnd_answer_rec.buttons - && QApplication::keyboardModifiers() == qt_mac_dnd_answer_rec.modifiers) - return true; - else - return false; -} - -bool QWidgetPrivate::qt_mac_dnd_event(uint kind, DragRef dragRef) -{ - Q_UNUSED(kind); - Q_UNUSED(dragRef); - return false; -} - -void QDragManager::updatePixmap() -{ -} - -QCocoaDropData::QCocoaDropData(CFStringRef pasteboard) - : QInternalMimeData() -{ - NSString* pasteboardName = (NSString*)pasteboard; - [pasteboardName retain]; - dropPasteboard = pasteboard; -} - -QCocoaDropData::~QCocoaDropData() -{ - NSString* pasteboardName = (NSString*)dropPasteboard; - [pasteboardName release]; -} - -QStringList QCocoaDropData::formats_sys() const -{ - QStringList formats; - OSPasteboardRef board; - if (PasteboardCreate(dropPasteboard, &board) != noErr) { - qDebug("DnD: Cannot get PasteBoard!"); - return formats; - } - formats = QMacPasteboard(board, QMacPasteboardMime::MIME_DND).formats(); - return formats; -} - -QVariant QCocoaDropData::retrieveData_sys(const QString &mimeType, QVariant::Type type) const -{ - QVariant data; - OSPasteboardRef board; - if (PasteboardCreate(dropPasteboard, &board) != noErr) { - qDebug("DnD: Cannot get PasteBoard!"); - return data; - } - data = QMacPasteboard(board, QMacPasteboardMime::MIME_DND).retrieveData(mimeType, type); - CFRelease(board); - return data; -} - -bool QCocoaDropData::hasFormat_sys(const QString &mimeType) const -{ - bool has = false; - OSPasteboardRef board; - if (PasteboardCreate(dropPasteboard, &board) != noErr) { - qDebug("DnD: Cannot get PasteBoard!"); - return has; - } - has = QMacPasteboard(board, QMacPasteboardMime::MIME_DND).hasFormat(mimeType); - CFRelease(board); - return has; -} - -#endif // QT_NO_DRAGANDDROP -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qeventdispatcher_mac.mm b/src/widgets/platforms/mac/qeventdispatcher_mac.mm deleted file mode 100644 index 0056ebe..0000000 --- a/src/widgets/platforms/mac/qeventdispatcher_mac.mm +++ /dev/null @@ -1,1127 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include "qplatformdefs.h" -#include "private/qt_mac_p.h" -#include "qeventdispatcher_mac_p.h" -#include "qapplication.h" -#include "qevent.h" -#include "qdialog.h" -#include "qhash.h" -#include "qsocketnotifier.h" -#include "private/qwidget_p.h" -#include "private/qthread_p.h" -#include "private/qapplication_p.h" - -#include -#include "private/qt_cocoa_helpers_mac_p.h" - -#ifndef QT_NO_THREAD -# include "qmutex.h" -#endif - -QT_BEGIN_NAMESPACE - -QT_USE_NAMESPACE - -/***************************************************************************** - Externals - *****************************************************************************/ -extern void qt_event_request_timer(MacTimerInfo *); //qapplication_mac.cpp -extern MacTimerInfo *qt_event_get_timer(EventRef); //qapplication_mac.cpp -extern void qt_event_request_select(QEventDispatcherMac *); //qapplication_mac.cpp -extern void qt_event_request_updates(); //qapplication_mac.cpp -extern OSWindowRef qt_mac_window_for(const QWidget *); //qwidget_mac.cpp -extern bool qt_is_gui_used; //qapplication.cpp -extern bool qt_sendSpontaneousEvent(QObject*, QEvent*); // qapplication.cpp -extern bool qt_mac_is_macsheet(const QWidget *); //qwidget_mac.cpp - -static inline CFRunLoopRef mainRunLoop() -{ - return CFRunLoopGetMain(); -} - -/***************************************************************************** - Timers stuff - *****************************************************************************/ - -/* timer call back */ -void QEventDispatcherMacPrivate::activateTimer(CFRunLoopTimerRef, void *info) -{ - int timerID = -#ifdef Q_OS_MAC64 - qint64(info); -#else - int(info); -#endif - - MacTimerInfo *tmr; - tmr = macTimerHash.value(timerID); - if (tmr == 0 || tmr->pending == true) - return; // Can't send another timer event if it's pending. - - - if (blockSendPostedEvents) { - QCoreApplication::postEvent(tmr->obj, new QTimerEvent(tmr->id)); - } else { - tmr->pending = true; - QTimerEvent e(tmr->id); - qt_sendSpontaneousEvent(tmr->obj, &e); - // Get the value again in case the timer gets unregistered during the sendEvent. - tmr = macTimerHash.value(timerID); - if (tmr != 0) - tmr->pending = false; - } - -} - -void QEventDispatcherMac::registerTimer(int timerId, int interval, QObject *obj) -{ -#ifndef QT_NO_DEBUG - if (timerId < 1 || interval < 0 || !obj) { - qWarning("QEventDispatcherMac::registerTimer: invalid arguments"); - return; - } else if (obj->thread() != thread() || thread() != QThread::currentThread()) { - qWarning("QObject::startTimer: timers cannot be started from another thread"); - return; - } -#endif - - MacTimerInfo *t = new MacTimerInfo(); - t->id = timerId; - t->interval = interval; - t->obj = obj; - t->runLoopTimer = 0; - t->pending = false; - - CFAbsoluteTime fireDate = CFAbsoluteTimeGetCurrent(); - CFTimeInterval cfinterval = qMax(CFTimeInterval(interval) / 1000, 0.0000001); - fireDate += cfinterval; - QEventDispatcherMacPrivate::macTimerHash.insert(timerId, t); - CFRunLoopTimerContext info = { 0, (void *)timerId, 0, 0, 0 }; - t->runLoopTimer = CFRunLoopTimerCreate(0, fireDate, cfinterval, 0, 0, - QEventDispatcherMacPrivate::activateTimer, &info); - if (t->runLoopTimer == 0) { - qFatal("QEventDispatcherMac::registerTimer: Cannot create timer"); - } - CFRunLoopAddTimer(mainRunLoop(), t->runLoopTimer, kCFRunLoopCommonModes); -} - -bool QEventDispatcherMac::unregisterTimer(int identifier) -{ -#ifndef QT_NO_DEBUG - if (identifier < 1) { - qWarning("QEventDispatcherMac::unregisterTimer: invalid argument"); - return false; - } else if (thread() != QThread::currentThread()) { - qWarning("QObject::killTimer: timers cannot be stopped from another thread"); - return false; - } -#endif - if (identifier <= 0) - return false; // not init'd or invalid timer - - MacTimerInfo *timerInfo = QEventDispatcherMacPrivate::macTimerHash.take(identifier); - if (timerInfo == 0) - return false; - - if (!QObjectPrivate::get(timerInfo->obj)->inThreadChangeEvent) - QAbstractEventDispatcherPrivate::releaseTimerId(identifier); - CFRunLoopTimerInvalidate(timerInfo->runLoopTimer); - CFRelease(timerInfo->runLoopTimer); - delete timerInfo; - - return true; -} - -bool QEventDispatcherMac::unregisterTimers(QObject *obj) -{ -#ifndef QT_NO_DEBUG - if (!obj) { - qWarning("QEventDispatcherMac::unregisterTimers: invalid argument"); - return false; - } else if (obj->thread() != thread() || thread() != QThread::currentThread()) { - qWarning("QObject::killTimers: timers cannot be stopped from another thread"); - return false; - } -#endif - - MacTimerHash::iterator it = QEventDispatcherMacPrivate::macTimerHash.begin(); - while (it != QEventDispatcherMacPrivate::macTimerHash.end()) { - MacTimerInfo *timerInfo = it.value(); - if (timerInfo->obj != obj) { - ++it; - } else { - if (!QObjectPrivate::get(timerInfo->obj)->inThreadChangeEvent) - QAbstractEventDispatcherPrivate::releaseTimerId(timerInfo->id); - CFRunLoopTimerInvalidate(timerInfo->runLoopTimer); - CFRelease(timerInfo->runLoopTimer); - delete timerInfo; - it = QEventDispatcherMacPrivate::macTimerHash.erase(it); - } - } - return true; -} - -QList -QEventDispatcherMac::registeredTimers(QObject *object) const -{ - if (!object) { - qWarning("QEventDispatcherMac:registeredTimers: invalid argument"); - return QList(); - } - - QList list; - - MacTimerHash::const_iterator it = QEventDispatcherMacPrivate::macTimerHash.constBegin(); - while (it != QEventDispatcherMacPrivate::macTimerHash.constEnd()) { - MacTimerInfo *t = it.value(); - if (t->obj == object) - list << TimerInfo(t->id, t->interval); - ++it; - } - return list; -} - -/************************************************************************** - Socket Notifiers - *************************************************************************/ -void qt_mac_socket_callback(CFSocketRef s, CFSocketCallBackType callbackType, CFDataRef, - const void *, void *info) { - QEventDispatcherMacPrivate *const eventDispatcher - = static_cast(info); - int nativeSocket = CFSocketGetNative(s); - MacSocketInfo *socketInfo = eventDispatcher->macSockets.value(nativeSocket); - QEvent notifierEvent(QEvent::SockAct); - - // There is a race condition that happen where we disable the notifier and - // the kernel still has a notification to pass on. We then get this - // notification after we've successfully disabled the CFSocket, but our Qt - // notifier is now gone. The upshot is we have to check the notifier - // everytime. - if (callbackType == kCFSocketReadCallBack) { - if (socketInfo->readNotifier) - QApplication::sendEvent(socketInfo->readNotifier, ¬ifierEvent); - } else if (callbackType == kCFSocketWriteCallBack) { - if (socketInfo->writeNotifier) - QApplication::sendEvent(socketInfo->writeNotifier, ¬ifierEvent); - } -} - -/* - Adds a loop source for the given socket to the current run loop. -*/ -CFRunLoopSourceRef qt_mac_add_socket_to_runloop(const CFSocketRef socket) -{ - CFRunLoopSourceRef loopSource = CFSocketCreateRunLoopSource(kCFAllocatorDefault, socket, 0); - if (!loopSource) - return 0; - - CFRunLoopAddSource(mainRunLoop(), loopSource, kCFRunLoopCommonModes); - return loopSource; -} - -/* - Removes the loop source for the given socket from the current run loop. -*/ -void qt_mac_remove_socket_from_runloop(const CFSocketRef socket, CFRunLoopSourceRef runloop) -{ - Q_ASSERT(runloop); - CFRunLoopRemoveSource(mainRunLoop(), runloop, kCFRunLoopCommonModes); - CFSocketDisableCallBacks(socket, kCFSocketReadCallBack); - CFSocketDisableCallBacks(socket, kCFSocketWriteCallBack); - CFRunLoopSourceInvalidate(runloop); -} - -/* - Register a QSocketNotifier with the mac event system by creating a CFSocket with - with a read/write callback. - - Qt has separate socket notifiers for reading and writing, but on the mac there is - a limitation of one CFSocket object for each native socket. -*/ -void QEventDispatcherMac::registerSocketNotifier(QSocketNotifier *notifier) -{ - Q_ASSERT(notifier); - int nativeSocket = notifier->socket(); - int type = notifier->type(); -#ifndef QT_NO_DEBUG - if (nativeSocket < 0 || nativeSocket > FD_SETSIZE) { - qWarning("QSocketNotifier: Internal error"); - return; - } else if (notifier->thread() != thread() - || thread() != QThread::currentThread()) { - qWarning("QSocketNotifier: socket notifiers cannot be enabled from another thread"); - return; - } -#endif - - Q_D(QEventDispatcherMac); - - if (type == QSocketNotifier::Exception) { - qWarning("QSocketNotifier::Exception is not supported on Mac OS X"); - return; - } - - // Check if we have a CFSocket for the native socket, create one if not. - MacSocketInfo *socketInfo = d->macSockets.value(nativeSocket); - if (!socketInfo) { - socketInfo = new MacSocketInfo(); - - // Create CFSocket, specify that we want both read and write callbacks (the callbacks - // are enabled/disabled later on). - const int callbackTypes = kCFSocketReadCallBack | kCFSocketWriteCallBack; - CFSocketContext context = {0, d, 0, 0, 0}; - socketInfo->socket = CFSocketCreateWithNative(kCFAllocatorDefault, nativeSocket, callbackTypes, qt_mac_socket_callback, &context); - if (CFSocketIsValid(socketInfo->socket) == false) { - qWarning("QEventDispatcherMac::registerSocketNotifier: Failed to create CFSocket"); - return; - } - - CFOptionFlags flags = CFSocketGetSocketFlags(socketInfo->socket); - flags |= kCFSocketAutomaticallyReenableWriteCallBack; //QSocketNotifier stays enabled after a write - flags &= ~kCFSocketCloseOnInvalidate; //QSocketNotifier doesn't close the socket upon destruction/invalidation - CFSocketSetSocketFlags(socketInfo->socket, flags); - - // Add CFSocket to runloop. - if(!(socketInfo->runloop = qt_mac_add_socket_to_runloop(socketInfo->socket))) { - qWarning("QEventDispatcherMac::registerSocketNotifier: Failed to add CFSocket to runloop"); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); - return; - } - - // Disable both callback types by default. This must be done after - // we add the CFSocket to the runloop, or else these calls will have - // no effect. - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketReadCallBack); - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); - - d->macSockets.insert(nativeSocket, socketInfo); - } - - // Increment read/write counters and select enable callbacks if necessary. - if (type == QSocketNotifier::Read) { - Q_ASSERT(socketInfo->readNotifier == 0); - socketInfo->readNotifier = notifier; - CFSocketEnableCallBacks(socketInfo->socket, kCFSocketReadCallBack); - } else if (type == QSocketNotifier::Write) { - Q_ASSERT(socketInfo->writeNotifier == 0); - socketInfo->writeNotifier = notifier; - CFSocketEnableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); - } -} - -/* - Unregister QSocketNotifer. The CFSocket correspoding to this notifier is - removed from the runloop of this is the last notifier that users - that CFSocket. -*/ -void QEventDispatcherMac::unregisterSocketNotifier(QSocketNotifier *notifier) -{ - Q_ASSERT(notifier); - int nativeSocket = notifier->socket(); - int type = notifier->type(); -#ifndef QT_NO_DEBUG - if (nativeSocket < 0 || nativeSocket > FD_SETSIZE) { - qWarning("QSocketNotifier: Internal error"); - return; - } else if (notifier->thread() != thread() || thread() != QThread::currentThread()) { - qWarning("QSocketNotifier: socket notifiers cannot be disabled from another thread"); - return; - } -#endif - - Q_D(QEventDispatcherMac); - - if (type == QSocketNotifier::Exception) { - qWarning("QSocketNotifier::Exception is not supported on Mac OS X"); - return; - } - MacSocketInfo *socketInfo = d->macSockets.value(nativeSocket); - if (!socketInfo) { - qWarning("QEventDispatcherMac::unregisterSocketNotifier: Tried to unregister a not registered notifier"); - return; - } - - // Decrement read/write counters and disable callbacks if necessary. - if (type == QSocketNotifier::Read) { - Q_ASSERT(notifier == socketInfo->readNotifier); - socketInfo->readNotifier = 0; - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketReadCallBack); - } else if (type == QSocketNotifier::Write) { - Q_ASSERT(notifier == socketInfo->writeNotifier); - socketInfo->writeNotifier = 0; - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); - } - - // Remove CFSocket from runloop if this was the last QSocketNotifier. - if (socketInfo->readNotifier == 0 && socketInfo->writeNotifier == 0) { - if (CFSocketIsValid(socketInfo->socket)) - qt_mac_remove_socket_from_runloop(socketInfo->socket, socketInfo->runloop); - CFRunLoopSourceInvalidate(socketInfo->runloop); - CFRelease(socketInfo->runloop); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); - delete socketInfo; - d->macSockets.remove(nativeSocket); - } -} - -bool QEventDispatcherMac::hasPendingEvents() -{ - extern uint qGlobalPostedEventsCount(); - return qGlobalPostedEventsCount() || (qt_is_gui_used && GetNumEventsInQueue(GetMainEventQueue())); -} - - -static bool qt_mac_send_event(QEventLoop::ProcessEventsFlags, OSEventRef event, OSWindowRef pt) -{ - if (pt) - [pt sendEvent:event]; - else - [NSApp sendEvent:event]; - return true; -} - -static bool IsMouseOrKeyEvent( NSEvent* event ) -{ - bool result = false; - - switch( [event type] ) - { - case NSLeftMouseDown: - case NSLeftMouseUp: - case NSRightMouseDown: - case NSRightMouseUp: - case NSMouseMoved: // ?? - case NSLeftMouseDragged: - case NSRightMouseDragged: - case NSMouseEntered: - case NSMouseExited: - case NSKeyDown: - case NSKeyUp: - case NSFlagsChanged: // key modifiers changed? - case NSCursorUpdate: // ?? - case NSScrollWheel: - case NSTabletPoint: - case NSTabletProximity: - case NSOtherMouseDown: - case NSOtherMouseUp: - case NSOtherMouseDragged: -#ifndef QT_NO_GESTURES -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_6 - case NSEventTypeGesture: // touch events - case NSEventTypeMagnify: - case NSEventTypeSwipe: - case NSEventTypeRotate: - case NSEventTypeBeginGesture: - case NSEventTypeEndGesture: -#endif -#endif // QT_NO_GESTURES - result = true; - break; - - default: - break; - } - return result; -} - -static inline void qt_mac_waitForMoreEvents() -{ - // If no event exist in the cocoa event que, wait - // (and free up cpu time) until at least one event occur. - // This implementation is a bit on the edge, but seems to - // work fine: - NSEvent* event = [NSApp nextEventMatchingMask:NSAnyEventMask - untilDate:[NSDate distantFuture] - inMode:NSDefaultRunLoopMode - dequeue:YES]; - if (event) - [NSApp postEvent:event atStart:YES]; -} - -static inline void qt_mac_waitForMoreModalSessionEvents() -{ - // If no event exist in the cocoa event que, wait - // (and free up cpu time) until at least one event occur. - // This implementation is a bit on the edge, but seems to - // work fine: - NSEvent* event = [NSApp nextEventMatchingMask:NSAnyEventMask - untilDate:[NSDate distantFuture] - inMode:NSModalPanelRunLoopMode - dequeue:YES]; - if (event) - [NSApp postEvent:event atStart:YES]; -} - -bool QEventDispatcherMac::processEvents(QEventLoop::ProcessEventsFlags flags) -{ - Q_D(QEventDispatcherMac); - d->interrupt = false; - - bool interruptLater = false; - QtMacInterruptDispatcherHelp::cancelInterruptLater(); - - // In case we end up recursing while we now process events, make sure - // that we send remaining posted Qt events before this call returns: - wakeUp(); - emit awake(); - - bool excludeUserEvents = flags & QEventLoop::ExcludeUserInputEvents; - bool retVal = false; - forever { - if (d->interrupt) - break; - - QMacCocoaAutoReleasePool pool; - NSEvent* event = 0; - - // First, send all previously excluded input events, if any: - if (!excludeUserEvents) { - while (!d->queuedUserInputEvents.isEmpty()) { - event = static_cast(d->queuedUserInputEvents.takeFirst()); - if (!filterEvent(event)) { - qt_mac_send_event(flags, event, 0); - retVal = true; - } - [event release]; - } - } - - // If Qt is used as a plugin, or as an extension in a native cocoa - // application, we should not run or stop NSApplication; This will be - // done from the application itself. And if processEvents is called - // manually (rather than from a QEventLoop), we cannot enter a tight - // loop and block this call, but instead we need to return after one flush. - // Finally, if we are to exclude user input events, we cannot call [NSApp run] - // as we then loose control over which events gets dispatched: - const bool canExec_3rdParty = d->nsAppRunCalledByQt || ![NSApp isRunning]; - const bool canExec_Qt = !excludeUserEvents && - (flags & QEventLoop::DialogExec || flags & QEventLoop::EventLoopExec) ; - - if (canExec_Qt && canExec_3rdParty) { - // We can use exec-mode, meaning that we can stay in a tight loop until - // interrupted. This is mostly an optimization, but it allow us to use - // [NSApp run], which is the normal code path for cocoa applications. - if (NSModalSession session = d->currentModalSession()) { - QBoolBlocker execGuard(d->currentExecIsNSAppRun, false); - while ([NSApp runModalSession:session] == NSRunContinuesResponse && !d->interrupt) - qt_mac_waitForMoreModalSessionEvents(); - - if (!d->interrupt && session == d->currentModalSessionCached) { - // Someone called [NSApp stopModal:] from outside the event - // dispatcher (e.g to stop a native dialog). But that call wrongly stopped - // 'session' as well. As a result, we need to restart all internal sessions: - d->temporarilyStopAllModalSessions(); - } - } else { - d->nsAppRunCalledByQt = true; - QBoolBlocker execGuard(d->currentExecIsNSAppRun, true); - [NSApp run]; - } - retVal = true; - } else { - // We cannot block the thread (and run in a tight loop). - // Instead we will process all current pending events and return. - d->ensureNSAppInitialized(); - if (NSModalSession session = d->currentModalSession()) { - // INVARIANT: a modal window is executing. - if (!excludeUserEvents) { - // Since we can dispatch all kinds of events, we choose - // to use cocoa's native way of running modal sessions: - if (flags & QEventLoop::WaitForMoreEvents) - qt_mac_waitForMoreModalSessionEvents(); - NSInteger status = [NSApp runModalSession:session]; - if (status != NSRunContinuesResponse && session == d->currentModalSessionCached) { - // INVARIANT: Someone called [NSApp stopModal:] from outside the event - // dispatcher (e.g to stop a native dialog). But that call wrongly stopped - // 'session' as well. As a result, we need to restart all internal sessions: - d->temporarilyStopAllModalSessions(); - } - retVal = true; - } else do { - // Dispatch all non-user events (but que non-user events up for later). In - // this case, we need more control over which events gets dispatched, and - // cannot use [NSApp runModalSession:session]: - event = [NSApp nextEventMatchingMask:NSAnyEventMask - untilDate:nil - inMode:NSModalPanelRunLoopMode - dequeue: YES]; - - if (event) { - if (IsMouseOrKeyEvent(event)) { - [event retain]; - d->queuedUserInputEvents.append(event); - continue; - } - if (!filterEvent(event) && qt_mac_send_event(flags, event, 0)) - retVal = true; - } - } while (!d->interrupt && event != nil); - } else do { - // INVARIANT: No modal window is executing. - event = [NSApp nextEventMatchingMask:NSAnyEventMask - untilDate:nil - inMode:NSDefaultRunLoopMode - dequeue: YES]; - - if (event) { - if (flags & QEventLoop::ExcludeUserInputEvents) { - if (IsMouseOrKeyEvent(event)) { - [event retain]; - d->queuedUserInputEvents.append(event); - continue; - } - } - if (!filterEvent(event) && qt_mac_send_event(flags, event, 0)) - retVal = true; - } - } while (!d->interrupt && event != nil); - - // Be sure to flush the Qt posted events when not using exec mode - // (exec mode will always do this call from the event loop source): - if (!d->interrupt) - QCoreApplicationPrivate::sendPostedEvents(0, 0, d->threadData); - - // Since the window that holds modality might have changed while processing - // events, we we need to interrupt when we return back the previous process - // event recursion to ensure that we spin the correct modal session. - // We do the interruptLater at the end of the function to ensure that we don't - // disturb the 'wait for more events' below (as deleteLater will post an event): - interruptLater = true; - } - - bool canWait = (d->threadData->canWait - && !retVal - && !d->interrupt - && (flags & QEventLoop::WaitForMoreEvents)); - if (canWait) { - // INVARIANT: We haven't processed any events yet. And we're told - // to stay inside this function until at least one event is processed. - qt_mac_waitForMoreEvents(); - flags &= ~QEventLoop::WaitForMoreEvents; - } else { - // Done with event processing for now. - // Leave the function: - break; - } - } - - // If we're interrupted, we need to interrupt the _current_ - // recursion as well to check if it is still supposed to be - // executing. This way we wind down the stack until we land - // on a recursion that again calls processEvents (typically - // from QEventLoop), and set interrupt to false: - if (d->interrupt) - interrupt(); - - if (interruptLater) - QtMacInterruptDispatcherHelp::interruptLater(); - - return retVal; -} - -void QEventDispatcherMac::wakeUp() -{ - Q_D(QEventDispatcherMac); - d->serialNumber.ref(); - CFRunLoopSourceSignal(d->postedEventsSource); - CFRunLoopWakeUp(mainRunLoop()); -} - -void QEventDispatcherMac::flush() -{ - if(qApp) { - QWidgetList tlws = QApplication::topLevelWidgets(); - for(int i = 0; i < tlws.size(); i++) { - QWidget *tlw = tlws.at(i); - if(tlw->isVisible()) - macWindowFlush(qt_mac_window_for(tlw)); - } - } -} - -/***************************************************************************** - QEventDispatcherMac Implementation - *****************************************************************************/ -MacTimerHash QEventDispatcherMacPrivate::macTimerHash; -bool QEventDispatcherMacPrivate::blockSendPostedEvents = false; -bool QEventDispatcherMacPrivate::interrupt = false; - -QStack QEventDispatcherMacPrivate::cocoaModalSessionStack; -bool QEventDispatcherMacPrivate::currentExecIsNSAppRun = false; -bool QEventDispatcherMacPrivate::nsAppRunCalledByQt = false; -bool QEventDispatcherMacPrivate::cleanupModalSessionsNeeded = false; -NSModalSession QEventDispatcherMacPrivate::currentModalSessionCached = 0; - -void QEventDispatcherMacPrivate::ensureNSAppInitialized() -{ - // Some elements in Cocoa require NSApplication to be running before - // they get fully initialized, in particular the menu bar. This - // function is intended for cases where a dialog is told to execute before - // QApplication::exec is called, or the application spins the events loop - // manually rather than calling QApplication:exec. - // The function makes sure that NSApplication starts running, but stops - // it again as soon as the send posted events callback is called. That way - // we let Cocoa finish the initialization it seems to need. We'll only - // apply this trick at most once for any application, and we avoid doing it - // for the common case where main just starts QApplication::exec. - if (nsAppRunCalledByQt || [NSApp isRunning]) - return; - nsAppRunCalledByQt = true; - QBoolBlocker block1(interrupt, true); - QBoolBlocker block2(currentExecIsNSAppRun, true); - [NSApp run]; -} - -void QEventDispatcherMacPrivate::temporarilyStopAllModalSessions() -{ - // Flush, and Stop, all created modal session, and as - // such, make them pending again. The next call to - // currentModalSession will recreate them again. The - // reason to stop all session like this is that otherwise - // a call [NSApp stop] would not stop NSApp, but rather - // the current modal session. So if we need to stop NSApp - // we need to stop all the modal session first. To avoid changing - // the stacking order of the windows while doing so, we put - // up a block that is used in QCocoaWindow and QCocoaPanel: - int stackSize = cocoaModalSessionStack.size(); - for (int i=0; itestAttribute(Qt::WA_DontShowOnScreen)) - continue; - if (!info.session) { - QMacCocoaAutoReleasePool pool; - NSWindow *window = qt_mac_window_for(info.widget); - if (!window) - continue; - - ensureNSAppInitialized(); - QBoolBlocker block1(blockSendPostedEvents, true); - info.nswindow = window; - [(NSWindow*) info.nswindow retain]; - int levelBeforeEnterModal = [window level]; - info.session = [NSApp beginModalSessionForWindow:window]; - // Make sure we don't stack the window lower that it was before - // entering modal, in case it e.g. had the stays-on-top flag set: - if (levelBeforeEnterModal > [window level]) - [window setLevel:levelBeforeEnterModal]; - } - currentModalSessionCached = info.session; - cleanupModalSessionsNeeded = false; - } - return currentModalSessionCached; -} - -static void setChildrenWorksWhenModal(QWidget *widget, bool worksWhenModal) -{ - // For NSPanels (but not NSWindows, sadly), we can set the flag - // worksWhenModal, so that they are active even when they are not modal. - QList dialogs = widget->findChildren(); - for (int i=0; i(window) setWorksWhenModal:worksWhenModal]; - if (worksWhenModal && [window isVisible]){ - [window orderFront:window]; - } - } - } -} - -void QEventDispatcherMacPrivate::updateChildrenWorksWhenModal() -{ - // Make the dialog children of the widget - // active. And make the dialog children of - // the previous modal dialog unactive again: - QMacCocoaAutoReleasePool pool; - int size = cocoaModalSessionStack.size(); - if (size > 0){ - if (QWidget *prevModal = cocoaModalSessionStack[size-1].widget) - setChildrenWorksWhenModal(prevModal, true); - if (size > 1){ - if (QWidget *prevModal = cocoaModalSessionStack[size-2].widget) - setChildrenWorksWhenModal(prevModal, false); - } - } -} - -void QEventDispatcherMacPrivate::cleanupModalSessions() -{ - // Go through the list of modal sessions, and end those - // that no longer has a widget assosiated; no widget means - // the the session has logically ended. The reason we wait like - // this to actually end the sessions for real (rather than at the - // point they were marked as stopped), is that ending a session - // when no other session runs below it on the stack will make cocoa - // drop some events on the floor. - QMacCocoaAutoReleasePool pool; - int stackSize = cocoaModalSessionStack.size(); - - for (int i=stackSize-1; i>=0; --i) { - QCocoaModalSessionInfo &info = cocoaModalSessionStack[i]; - if (info.widget) { - // This session has a widget, and is therefore not marked - // as stopped. So just make it current. There might still be other - // stopped sessions on the stack, but those will be stopped on - // a later "cleanup" call. - currentModalSessionCached = info.session; - break; - } - cocoaModalSessionStack.remove(i); - currentModalSessionCached = 0; - if (info.session) { - [NSApp endModalSession:info.session]; - [(NSWindow *)info.nswindow release]; - } - } - - updateChildrenWorksWhenModal(); - cleanupModalSessionsNeeded = false; -} - -void QEventDispatcherMacPrivate::beginModalSession(QWidget *widget) -{ - // Add a new, empty (null), NSModalSession to the stack. - // It will become active the next time QEventDispatcher::processEvents is called. - // A QCocoaModalSessionInfo is considered pending to become active if the widget pointer - // is non-zero, and the session pointer is zero (it will become active upon a call to - // currentModalSession). A QCocoaModalSessionInfo is considered pending to be stopped if - // the widget pointer is zero, and the session pointer is non-zero (it will be fully - // stopped in cleanupModalSessions()). - QCocoaModalSessionInfo info = {widget, 0, 0}; - cocoaModalSessionStack.push(info); - updateChildrenWorksWhenModal(); - currentModalSessionCached = 0; -} - -void QEventDispatcherMacPrivate::endModalSession(QWidget *widget) -{ - // Mark all sessions attached to widget as pending to be stopped. We do this - // by setting the widget pointer to zero, but leave the session pointer. - // We don't tell cocoa to stop any sessions just yet, because cocoa only understands - // when we stop the _current_ modal session (which is the session on top of - // the stack, and might not belong to 'widget'). - int stackSize = cocoaModalSessionStack.size(); - for (int i=stackSize-1; i>=0; --i) { - QCocoaModalSessionInfo &info = cocoaModalSessionStack[i]; - if (info.widget == widget) { - info.widget = 0; - if (i == stackSize-1) { - // The top sessions ended. Interrupt the event dispatcher - // to start spinning the correct session immidiatly: - currentModalSessionCached = 0; - cleanupModalSessionsNeeded = true; - QEventDispatcherMac::instance()->interrupt(); - } - } - } -} - - -QEventDispatcherMacPrivate::QEventDispatcherMacPrivate() -{ -} - -QEventDispatcherMac::QEventDispatcherMac(QObject *parent) - : QAbstractEventDispatcher(*new QEventDispatcherMacPrivate, parent) -{ - Q_D(QEventDispatcherMac); - CFRunLoopSourceContext context; - bzero(&context, sizeof(CFRunLoopSourceContext)); - context.info = d; - context.equal = QEventDispatcherMacPrivate::postedEventSourceEqualCallback; - context.perform = QEventDispatcherMacPrivate::postedEventsSourcePerformCallback; - d->postedEventsSource = CFRunLoopSourceCreate(0, 0, &context); - Q_ASSERT(d->postedEventsSource); - CFRunLoopAddSource(mainRunLoop(), d->postedEventsSource, kCFRunLoopCommonModes); - - CFRunLoopObserverContext observerContext; - bzero(&observerContext, sizeof(CFRunLoopObserverContext)); - observerContext.info = this; - d->waitingObserver = CFRunLoopObserverCreate(kCFAllocatorDefault, - kCFRunLoopBeforeWaiting | kCFRunLoopAfterWaiting, - true, 0, - QEventDispatcherMacPrivate::waitingObserverCallback, - &observerContext); - CFRunLoopAddObserver(mainRunLoop(), d->waitingObserver, kCFRunLoopCommonModes); - - /* The first cycle in the loop adds the source and the events of the source - are not processed. - We use an observer to process the posted events for the first - execution of the loop. */ - CFRunLoopObserverContext firstTimeObserverContext; - bzero(&firstTimeObserverContext, sizeof(CFRunLoopObserverContext)); - firstTimeObserverContext.info = d; - d->firstTimeObserver = CFRunLoopObserverCreate(kCFAllocatorDefault, - kCFRunLoopEntry, - /* repeats = */ false, - 0, - QEventDispatcherMacPrivate::firstLoopEntry, - &firstTimeObserverContext); - CFRunLoopAddObserver(mainRunLoop(), d->firstTimeObserver, kCFRunLoopCommonModes); -} - -void QEventDispatcherMacPrivate::waitingObserverCallback(CFRunLoopObserverRef, - CFRunLoopActivity activity, void *info) -{ - if (activity == kCFRunLoopBeforeWaiting) - emit static_cast(info)->aboutToBlock(); - else - emit static_cast(info)->awake(); -} - -Boolean QEventDispatcherMacPrivate::postedEventSourceEqualCallback(const void *info1, const void *info2) -{ - return info1 == info2; -} - -inline static void processPostedEvents(QEventDispatcherMacPrivate *const d, const bool blockSendPostedEvents) -{ - if (blockSendPostedEvents) { - // We're told to not send posted events (because the event dispatcher - // is currently working on setting up the correct session to run). But - // we still need to make sure that we don't fall asleep until pending events - // are sendt, so we just signal this need, and return: - CFRunLoopSourceSignal(d->postedEventsSource); - return; - } - - if (d->cleanupModalSessionsNeeded) - d->cleanupModalSessions(); - - if (d->interrupt) { - if (d->currentExecIsNSAppRun) { - // The event dispatcher has been interrupted. But since - // [NSApplication run] is running the event loop, we - // delayed stopping it until now (to let cocoa process - // pending cocoa events first). - if (d->currentModalSessionCached) - d->temporarilyStopAllModalSessions(); - [NSApp stop:NSApp]; - d->cancelWaitForMoreEvents(); - } - return; - } - - if (!d->threadData->canWait || (d->serialNumber != d->lastSerial)) { - d->lastSerial = d->serialNumber; - QApplicationPrivate::sendPostedEvents(0, 0, d->threadData); - } -} - -void QEventDispatcherMacPrivate::firstLoopEntry(CFRunLoopObserverRef ref, - CFRunLoopActivity activity, - void *info) -{ - Q_UNUSED(ref); - Q_UNUSED(activity); - QApplicationPrivate::qt_initAfterNSAppStarted(); - processPostedEvents(static_cast(info), blockSendPostedEvents); -} - -void QEventDispatcherMacPrivate::postedEventsSourcePerformCallback(void *info) -{ - processPostedEvents(static_cast(info), blockSendPostedEvents); -} - -void QEventDispatcherMacPrivate::cancelWaitForMoreEvents() -{ - // In case the event dispatcher is waiting for more - // events somewhere, we post a dummy event to wake it up: - QMacCocoaAutoReleasePool pool; - [NSApp postEvent:[NSEvent otherEventWithType:NSApplicationDefined location:NSZeroPoint - modifierFlags:0 timestamp:0. windowNumber:0 context:0 - subtype:QtCocoaEventSubTypeWakeup data1:0 data2:0] atStart:NO]; -} - -void QEventDispatcherMac::interrupt() -{ - Q_D(QEventDispatcherMac); - d->interrupt = true; - wakeUp(); - - // We do nothing more here than setting d->interrupt = true, and - // poke the event loop if it is sleeping. Actually stopping - // NSApp, or the current modal session, is done inside the send - // posted events callback. We do this to ensure that all current pending - // cocoa events gets delivered before we stop. Otherwise, if we now stop - // the last event loop recursion, cocoa will just drop pending posted - // events on the floor before we get a chance to reestablish a new session. - d->cancelWaitForMoreEvents(); -} - -QEventDispatcherMac::~QEventDispatcherMac() -{ - Q_D(QEventDispatcherMac); - //timer cleanup - MacTimerHash::iterator it = QEventDispatcherMacPrivate::macTimerHash.begin(); - while (it != QEventDispatcherMacPrivate::macTimerHash.end()) { - MacTimerInfo *t = it.value(); - if (t->runLoopTimer) { - CFRunLoopTimerInvalidate(t->runLoopTimer); - CFRelease(t->runLoopTimer); - } - delete t; - ++it; - } - QEventDispatcherMacPrivate::macTimerHash.clear(); - - // Remove CFSockets from the runloop. - for (MacSocketHash::ConstIterator it = d->macSockets.constBegin(); it != d->macSockets.constEnd(); ++it) { - MacSocketInfo *socketInfo = (*it); - if (CFSocketIsValid(socketInfo->socket)) { - qt_mac_remove_socket_from_runloop(socketInfo->socket, socketInfo->runloop); - CFRunLoopSourceInvalidate(socketInfo->runloop); - CFRelease(socketInfo->runloop); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); - } - } - CFRunLoopRemoveSource(mainRunLoop(), d->postedEventsSource, kCFRunLoopCommonModes); - CFRelease(d->postedEventsSource); - - CFRunLoopObserverInvalidate(d->waitingObserver); - CFRelease(d->waitingObserver); - - CFRunLoopObserverInvalidate(d->firstTimeObserver); - CFRelease(d->firstTimeObserver); -} - - -QtMacInterruptDispatcherHelp* QtMacInterruptDispatcherHelp::instance = 0; - -QtMacInterruptDispatcherHelp::QtMacInterruptDispatcherHelp() : cancelled(false) -{ - // The whole point of this class is that we enable a way to interrupt - // the event dispatcher when returning back to a lower recursion level - // than where interruptLater was called. This is needed to detect if - // [NSApp run] should still be running at the recursion level it is at. - // Since the interrupt is canceled if processEvents is called before - // this object gets deleted, we also avoid interrupting unnecessary. - deleteLater(); -} - -QtMacInterruptDispatcherHelp::~QtMacInterruptDispatcherHelp() -{ - if (cancelled) - return; - instance = 0; - QEventDispatcherMac::instance()->interrupt(); -} - -void QtMacInterruptDispatcherHelp::cancelInterruptLater() -{ - if (!instance) - return; - instance->cancelled = true; - delete instance; - instance = 0; -} - -void QtMacInterruptDispatcherHelp::interruptLater() -{ - cancelInterruptLater(); - instance = new QtMacInterruptDispatcherHelp; -} - - -QT_END_NAMESPACE - diff --git a/src/widgets/platforms/mac/qeventdispatcher_mac_p.h b/src/widgets/platforms/mac/qeventdispatcher_mac_p.h deleted file mode 100644 index 57797b0..0000000 --- a/src/widgets/platforms/mac/qeventdispatcher_mac_p.h +++ /dev/null @@ -1,218 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#ifndef QEVENTDISPATCHER_MAC_P_H -#define QEVENTDISPATCHER_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include -#include -#include -#include "private/qabstracteventdispatcher_p.h" -#include "private/qt_mac_p.h" - -QT_BEGIN_NAMESPACE - -typedef struct _NSModalSession *NSModalSession; -typedef struct _QCocoaModalSessionInfo { - QPointer widget; - NSModalSession session; - void *nswindow; -} QCocoaModalSessionInfo; - -class QEventDispatcherMacPrivate; - -class QEventDispatcherMac : public QAbstractEventDispatcher -{ - Q_OBJECT - Q_DECLARE_PRIVATE(QEventDispatcherMac) - -public: - explicit QEventDispatcherMac(QObject *parent = 0); - ~QEventDispatcherMac(); - - bool processEvents(QEventLoop::ProcessEventsFlags flags); - bool hasPendingEvents(); - - void registerSocketNotifier(QSocketNotifier *notifier); - void unregisterSocketNotifier(QSocketNotifier *notifier); - - void registerTimer(int timerId, int interval, QObject *object); - bool unregisterTimer(int timerId); - bool unregisterTimers(QObject *object); - QList registeredTimers(QObject *object) const; - - void wakeUp(); - void flush(); - void interrupt(); - -private: - friend void qt_mac_select_timer_callbk(__EventLoopTimer*, void*); - friend class QApplicationPrivate; -}; - -struct MacTimerInfo { - int id; - int interval; - QObject *obj; - bool pending; - CFRunLoopTimerRef runLoopTimer; - bool operator==(const MacTimerInfo &other) const - { - return (id == other.id); - } -}; -typedef QHash MacTimerHash; - -struct MacSocketInfo { - MacSocketInfo() : socket(0), runloop(0), readNotifier(0), writeNotifier(0) {} - CFSocketRef socket; - CFRunLoopSourceRef runloop; - QObject *readNotifier; - QObject *writeNotifier; -}; -typedef QHash MacSocketHash; - -class QEventDispatcherMacPrivate : public QAbstractEventDispatcherPrivate -{ - Q_DECLARE_PUBLIC(QEventDispatcherMac) - -public: - QEventDispatcherMacPrivate(); - - static MacTimerHash macTimerHash; - // Set 'blockSendPostedEvents' to true if you _really_ need - // to make sure that qt events are not posted while calling - // low-level cocoa functions (like beginModalForWindow). And - // use a QBoolBlocker to be safe: - static bool blockSendPostedEvents; - // The following variables help organizing modal sessions: - static QStack cocoaModalSessionStack; - static bool currentExecIsNSAppRun; - static bool nsAppRunCalledByQt; - static bool cleanupModalSessionsNeeded; - static NSModalSession currentModalSessionCached; - static NSModalSession currentModalSession(); - static void updateChildrenWorksWhenModal(); - static void temporarilyStopAllModalSessions(); - static void beginModalSession(QWidget *widget); - static void endModalSession(QWidget *widget); - static void cancelWaitForMoreEvents(); - static void cleanupModalSessions(); - static void ensureNSAppInitialized(); - - MacSocketHash macSockets; - QList queuedUserInputEvents; // List of EventRef in Carbon, and NSEvent * in Cocoa - CFRunLoopSourceRef postedEventsSource; - CFRunLoopObserverRef waitingObserver; - CFRunLoopObserverRef firstTimeObserver; - QAtomicInt serialNumber; - int lastSerial; - static bool interrupt; -private: - static Boolean postedEventSourceEqualCallback(const void *info1, const void *info2); - static void postedEventsSourcePerformCallback(void *info); - static void activateTimer(CFRunLoopTimerRef, void *info); - static void waitingObserverCallback(CFRunLoopObserverRef observer, - CFRunLoopActivity activity, void *info); - static void firstLoopEntry(CFRunLoopObserverRef ref, CFRunLoopActivity activity, void *info); -}; - -class QtMacInterruptDispatcherHelp : public QObject -{ - static QtMacInterruptDispatcherHelp *instance; - bool cancelled; - - QtMacInterruptDispatcherHelp(); - ~QtMacInterruptDispatcherHelp(); - - public: - static void interruptLater(); - static void cancelInterruptLater(); -}; - -QT_END_NAMESPACE - -#endif // QEVENTDISPATCHER_MAC_P_H diff --git a/src/widgets/platforms/mac/qkeymapper_mac.cpp b/src/widgets/platforms/mac/qkeymapper_mac.cpp deleted file mode 100644 index 3cacb09..0000000 --- a/src/widgets/platforms/mac/qkeymapper_mac.cpp +++ /dev/null @@ -1,963 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include -#include -#include -#include -#include -#include -#include -#include -#include - -QT_BEGIN_NAMESPACE - -QT_USE_NAMESPACE - -/***************************************************************************** - QKeyMapper debug facilities - *****************************************************************************/ -//#define DEBUG_KEY_BINDINGS -//#define DEBUG_KEY_BINDINGS_MODIFIERS -//#define DEBUG_KEY_MAPS - -/***************************************************************************** - Internal variables and functions - *****************************************************************************/ -bool qt_mac_eat_unicode_key = false; -extern bool qt_sendSpontaneousEvent(QObject *obj, QEvent *event); //qapplication_mac.cpp - -Q_WIDGETS_EXPORT void qt_mac_secure_keyboard(bool b) -{ - static bool secure = false; - if (b != secure){ - b ? EnableSecureEventInput() : DisableSecureEventInput(); - secure = b; - } -} - -/* - \internal - A Mac KeyboardLayoutItem has 8 possible states: - 1. Unmodified - 2. Shift - 3. Control - 4. Control + Shift - 5. Alt - 6. Alt + Shift - 7. Alt + Control - 8. Alt + Control + Shift - 9. Meta - 10. Meta + Shift - 11. Meta + Control - 12. Meta + Control + Shift - 13. Meta + Alt - 14. Meta + Alt + Shift - 15. Meta + Alt + Control - 16. Meta + Alt + Control + Shift -*/ -struct KeyboardLayoutItem { - bool dirty; - quint32 qtKey[16]; // Can by any Qt::Key_, or unicode character -}; - -// Possible modifier states. -// NOTE: The order of these states match the order in QKeyMapperPrivate::updatePossibleKeyCodes()! -static const Qt::KeyboardModifiers ModsTbl[] = { - Qt::NoModifier, // 0 - Qt::ShiftModifier, // 1 - Qt::ControlModifier, // 2 - Qt::ControlModifier | Qt::ShiftModifier, // 3 - Qt::AltModifier, // 4 - Qt::AltModifier | Qt::ShiftModifier, // 5 - Qt::AltModifier | Qt::ControlModifier, // 6 - Qt::AltModifier | Qt::ShiftModifier | Qt::ControlModifier, // 7 - Qt::MetaModifier, // 8 - Qt::MetaModifier | Qt::ShiftModifier, // 9 - Qt::MetaModifier | Qt::ControlModifier, // 10 - Qt::MetaModifier | Qt::ControlModifier | Qt::ShiftModifier,// 11 - Qt::MetaModifier | Qt::AltModifier, // 12 - Qt::MetaModifier | Qt::AltModifier | Qt::ShiftModifier, // 13 - Qt::MetaModifier | Qt::AltModifier | Qt::ControlModifier, // 14 - Qt::MetaModifier | Qt::AltModifier | Qt::ShiftModifier | Qt::ControlModifier, // 15 -}; - -/* key maps */ -struct qt_mac_enum_mapper -{ - int mac_code; - int qt_code; -#if defined(DEBUG_KEY_BINDINGS) -# define QT_MAC_MAP_ENUM(x) x, #x - const char *desc; -#else -# define QT_MAC_MAP_ENUM(x) x -#endif -}; - -//modifiers -static qt_mac_enum_mapper qt_mac_modifier_symbols[] = { - { shiftKey, QT_MAC_MAP_ENUM(Qt::ShiftModifier) }, - { rightShiftKey, QT_MAC_MAP_ENUM(Qt::ShiftModifier) }, - { controlKey, QT_MAC_MAP_ENUM(Qt::MetaModifier) }, - { rightControlKey, QT_MAC_MAP_ENUM(Qt::MetaModifier) }, - { cmdKey, QT_MAC_MAP_ENUM(Qt::ControlModifier) }, - { optionKey, QT_MAC_MAP_ENUM(Qt::AltModifier) }, - { rightOptionKey, QT_MAC_MAP_ENUM(Qt::AltModifier) }, - { kEventKeyModifierNumLockMask, QT_MAC_MAP_ENUM(Qt::KeypadModifier) }, - { 0, QT_MAC_MAP_ENUM(0) } -}; -Qt::KeyboardModifiers qt_mac_get_modifiers(int keys) -{ -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("Qt: internal: **Mapping modifiers: %d (0x%04x)", keys, keys); -#endif - Qt::KeyboardModifiers ret = Qt::NoModifier; - for (int i = 0; qt_mac_modifier_symbols[i].qt_code; i++) { - if (keys & qt_mac_modifier_symbols[i].mac_code) { -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("Qt: internal: got modifier: %s", qt_mac_modifier_symbols[i].desc); -#endif - ret |= Qt::KeyboardModifier(qt_mac_modifier_symbols[i].qt_code); - } - } - if (qApp->testAttribute(Qt::AA_MacDontSwapCtrlAndMeta)) { - Qt::KeyboardModifiers oldModifiers = ret; - ret &= ~(Qt::MetaModifier | Qt::ControlModifier); - if (oldModifiers & Qt::ControlModifier) - ret |= Qt::MetaModifier; - if (oldModifiers & Qt::MetaModifier) - ret |= Qt::ControlModifier; - } - return ret; -} -static int qt_mac_get_mac_modifiers(Qt::KeyboardModifiers keys) -{ -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("Qt: internal: **Mapping modifiers: %d (0x%04x)", (int)keys, (int)keys); -#endif - int ret = 0; - for (int i = 0; qt_mac_modifier_symbols[i].qt_code; i++) { - if (keys & qt_mac_modifier_symbols[i].qt_code) { -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("Qt: internal: got modifier: %s", qt_mac_modifier_symbols[i].desc); -#endif - ret |= qt_mac_modifier_symbols[i].mac_code; - } - } - - if (qApp->testAttribute(Qt::AA_MacDontSwapCtrlAndMeta)) { - int oldModifiers = ret; - ret &= ~(controlKeyBit | cmdKeyBit); - if (oldModifiers & controlKeyBit) - ret |= cmdKeyBit; - if (oldModifiers & cmdKeyBit) - ret |= controlKeyBit; - } - return ret; -} -void qt_mac_send_modifiers_changed(quint32 modifiers, QObject *object) -{ - static quint32 cachedModifiers = 0; - quint32 lastModifiers = cachedModifiers, - changedModifiers = lastModifiers ^ modifiers; - cachedModifiers = modifiers; - - //check the bits - static qt_mac_enum_mapper modifier_key_symbols[] = { - { shiftKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Shift) }, - { rightShiftKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Shift) }, //??? - { controlKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Meta) }, - { rightControlKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Meta) }, //??? - { cmdKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Control) }, - { optionKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Alt) }, - { rightOptionKeyBit, QT_MAC_MAP_ENUM(Qt::Key_Alt) }, //??? - { alphaLockBit, QT_MAC_MAP_ENUM(Qt::Key_CapsLock) }, - { kEventKeyModifierNumLockBit, QT_MAC_MAP_ENUM(Qt::Key_NumLock) }, - { 0, QT_MAC_MAP_ENUM(0) } }; - for (int i = 0; i <= 32; i++) { //just check each bit - if (!(changedModifiers & (1 << i))) - continue; - QEvent::Type etype = QEvent::KeyPress; - if (lastModifiers & (1 << i)) - etype = QEvent::KeyRelease; - int key = 0; - for (uint x = 0; modifier_key_symbols[x].mac_code; x++) { - if (modifier_key_symbols[x].mac_code == i) { -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("got modifier changed: %s", modifier_key_symbols[x].desc); -#endif - key = modifier_key_symbols[x].qt_code; - break; - } - } - if (!key) { -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("could not get modifier changed: %d", i); -#endif - continue; - } -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("KeyEvent (modif): Sending %s to %s::%s: %d - 0x%08x", - etype == QEvent::KeyRelease ? "KeyRelease" : "KeyPress", - object ? object->metaObject()->className() : "none", - object ? object->objectName().toLatin1().constData() : "", - key, (int)modifiers); -#endif - QKeyEvent ke(etype, key, qt_mac_get_modifiers(modifiers ^ (1 << i)), QLatin1String("")); - qt_sendSpontaneousEvent(object, &ke); - } -} - -//keyboard keys (non-modifiers) -static qt_mac_enum_mapper qt_mac_keyboard_symbols[] = { - { kHomeCharCode, QT_MAC_MAP_ENUM(Qt::Key_Home) }, - { kEnterCharCode, QT_MAC_MAP_ENUM(Qt::Key_Enter) }, - { kEndCharCode, QT_MAC_MAP_ENUM(Qt::Key_End) }, - { kBackspaceCharCode, QT_MAC_MAP_ENUM(Qt::Key_Backspace) }, - { kTabCharCode, QT_MAC_MAP_ENUM(Qt::Key_Tab) }, - { kPageUpCharCode, QT_MAC_MAP_ENUM(Qt::Key_PageUp) }, - { kPageDownCharCode, QT_MAC_MAP_ENUM(Qt::Key_PageDown) }, - { kReturnCharCode, QT_MAC_MAP_ENUM(Qt::Key_Return) }, - { kEscapeCharCode, QT_MAC_MAP_ENUM(Qt::Key_Escape) }, - { kLeftArrowCharCode, QT_MAC_MAP_ENUM(Qt::Key_Left) }, - { kRightArrowCharCode, QT_MAC_MAP_ENUM(Qt::Key_Right) }, - { kUpArrowCharCode, QT_MAC_MAP_ENUM(Qt::Key_Up) }, - { kDownArrowCharCode, QT_MAC_MAP_ENUM(Qt::Key_Down) }, - { kHelpCharCode, QT_MAC_MAP_ENUM(Qt::Key_Help) }, - { kDeleteCharCode, QT_MAC_MAP_ENUM(Qt::Key_Delete) }, -//ascii maps, for debug - { ':', QT_MAC_MAP_ENUM(Qt::Key_Colon) }, - { ';', QT_MAC_MAP_ENUM(Qt::Key_Semicolon) }, - { '<', QT_MAC_MAP_ENUM(Qt::Key_Less) }, - { '=', QT_MAC_MAP_ENUM(Qt::Key_Equal) }, - { '>', QT_MAC_MAP_ENUM(Qt::Key_Greater) }, - { '?', QT_MAC_MAP_ENUM(Qt::Key_Question) }, - { '@', QT_MAC_MAP_ENUM(Qt::Key_At) }, - { ' ', QT_MAC_MAP_ENUM(Qt::Key_Space) }, - { '!', QT_MAC_MAP_ENUM(Qt::Key_Exclam) }, - { '"', QT_MAC_MAP_ENUM(Qt::Key_QuoteDbl) }, - { '#', QT_MAC_MAP_ENUM(Qt::Key_NumberSign) }, - { '$', QT_MAC_MAP_ENUM(Qt::Key_Dollar) }, - { '%', QT_MAC_MAP_ENUM(Qt::Key_Percent) }, - { '&', QT_MAC_MAP_ENUM(Qt::Key_Ampersand) }, - { '\'', QT_MAC_MAP_ENUM(Qt::Key_Apostrophe) }, - { '(', QT_MAC_MAP_ENUM(Qt::Key_ParenLeft) }, - { ')', QT_MAC_MAP_ENUM(Qt::Key_ParenRight) }, - { '*', QT_MAC_MAP_ENUM(Qt::Key_Asterisk) }, - { '+', QT_MAC_MAP_ENUM(Qt::Key_Plus) }, - { ',', QT_MAC_MAP_ENUM(Qt::Key_Comma) }, - { '-', QT_MAC_MAP_ENUM(Qt::Key_Minus) }, - { '.', QT_MAC_MAP_ENUM(Qt::Key_Period) }, - { '/', QT_MAC_MAP_ENUM(Qt::Key_Slash) }, - { '[', QT_MAC_MAP_ENUM(Qt::Key_BracketLeft) }, - { ']', QT_MAC_MAP_ENUM(Qt::Key_BracketRight) }, - { '\\', QT_MAC_MAP_ENUM(Qt::Key_Backslash) }, - { '_', QT_MAC_MAP_ENUM(Qt::Key_Underscore) }, - { '`', QT_MAC_MAP_ENUM(Qt::Key_QuoteLeft) }, - { '{', QT_MAC_MAP_ENUM(Qt::Key_BraceLeft) }, - { '}', QT_MAC_MAP_ENUM(Qt::Key_BraceRight) }, - { '|', QT_MAC_MAP_ENUM(Qt::Key_Bar) }, - { '~', QT_MAC_MAP_ENUM(Qt::Key_AsciiTilde) }, - { '^', QT_MAC_MAP_ENUM(Qt::Key_AsciiCircum) }, - { 0, QT_MAC_MAP_ENUM(0) } -}; - -static qt_mac_enum_mapper qt_mac_keyvkey_symbols[] = { //real scan codes - { 122, QT_MAC_MAP_ENUM(Qt::Key_F1) }, - { 120, QT_MAC_MAP_ENUM(Qt::Key_F2) }, - { 99, QT_MAC_MAP_ENUM(Qt::Key_F3) }, - { 118, QT_MAC_MAP_ENUM(Qt::Key_F4) }, - { 96, QT_MAC_MAP_ENUM(Qt::Key_F5) }, - { 97, QT_MAC_MAP_ENUM(Qt::Key_F6) }, - { 98, QT_MAC_MAP_ENUM(Qt::Key_F7) }, - { 100, QT_MAC_MAP_ENUM(Qt::Key_F8) }, - { 101, QT_MAC_MAP_ENUM(Qt::Key_F9) }, - { 109, QT_MAC_MAP_ENUM(Qt::Key_F10) }, - { 103, QT_MAC_MAP_ENUM(Qt::Key_F11) }, - { 111, QT_MAC_MAP_ENUM(Qt::Key_F12) }, - { 105, QT_MAC_MAP_ENUM(Qt::Key_F13) }, - { 107, QT_MAC_MAP_ENUM(Qt::Key_F14) }, - { 113, QT_MAC_MAP_ENUM(Qt::Key_F15) }, - { 106, QT_MAC_MAP_ENUM(Qt::Key_F16) }, - { 0, QT_MAC_MAP_ENUM(0) } -}; - -static qt_mac_enum_mapper qt_mac_private_unicode[] = { - { 0xF700, QT_MAC_MAP_ENUM(Qt::Key_Up) }, //NSUpArrowFunctionKey - { 0xF701, QT_MAC_MAP_ENUM(Qt::Key_Down) }, //NSDownArrowFunctionKey - { 0xF702, QT_MAC_MAP_ENUM(Qt::Key_Left) }, //NSLeftArrowFunctionKey - { 0xF703, QT_MAC_MAP_ENUM(Qt::Key_Right) }, //NSRightArrowFunctionKey - { 0xF727, QT_MAC_MAP_ENUM(Qt::Key_Insert) }, //NSInsertFunctionKey - { 0xF728, QT_MAC_MAP_ENUM(Qt::Key_Delete) }, //NSDeleteFunctionKey - { 0xF729, QT_MAC_MAP_ENUM(Qt::Key_Home) }, //NSHomeFunctionKey - { 0xF72B, QT_MAC_MAP_ENUM(Qt::Key_End) }, //NSEndFunctionKey - { 0xF72C, QT_MAC_MAP_ENUM(Qt::Key_PageUp) }, //NSPageUpFunctionKey - { 0xF72D, QT_MAC_MAP_ENUM(Qt::Key_PageDown) }, //NSPageDownFunctionKey - { 0xF72F, QT_MAC_MAP_ENUM(Qt::Key_ScrollLock) }, //NSScrollLockFunctionKey - { 0xF730, QT_MAC_MAP_ENUM(Qt::Key_Pause) }, //NSPauseFunctionKey - { 0xF731, QT_MAC_MAP_ENUM(Qt::Key_SysReq) }, //NSSysReqFunctionKey - { 0xF735, QT_MAC_MAP_ENUM(Qt::Key_Menu) }, //NSMenuFunctionKey - { 0xF738, QT_MAC_MAP_ENUM(Qt::Key_Print) }, //NSPrintFunctionKey - { 0xF73A, QT_MAC_MAP_ENUM(Qt::Key_Clear) }, //NSClearDisplayFunctionKey - { 0xF73D, QT_MAC_MAP_ENUM(Qt::Key_Insert) }, //NSInsertCharFunctionKey - { 0xF73E, QT_MAC_MAP_ENUM(Qt::Key_Delete) }, //NSDeleteCharFunctionKey - { 0xF741, QT_MAC_MAP_ENUM(Qt::Key_Select) }, //NSSelectFunctionKey - { 0xF742, QT_MAC_MAP_ENUM(Qt::Key_Execute) }, //NSExecuteFunctionKey - { 0xF746, QT_MAC_MAP_ENUM(Qt::Key_Help) }, //NSHelpFunctionKey - { 0xF747, QT_MAC_MAP_ENUM(Qt::Key_Mode_switch) }, //NSModeSwitchFunctionKey - { 0, QT_MAC_MAP_ENUM(0) } -}; - -static int qt_mac_get_key(int modif, const QChar &key, int virtualKey) -{ -#ifdef DEBUG_KEY_BINDINGS - qDebug("**Mapping key: %d (0x%04x) - %d (0x%04x)", key.unicode(), key.unicode(), virtualKey, virtualKey); -#endif - - if (key == kClearCharCode && virtualKey == 0x47) - return Qt::Key_Clear; - - if (key.isDigit()) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: %d", __LINE__, key.digitValue()); -#endif - return key.digitValue() + Qt::Key_0; - } - - if (key.isLetter()) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: %d", __LINE__, (key.toUpper().unicode() - 'A')); -#endif - return (key.toUpper().unicode() - 'A') + Qt::Key_A; - } - if (key.isSymbol()) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: %d", __LINE__, (key.unicode())); -#endif - return key.unicode(); - } - - for (int i = 0; qt_mac_keyboard_symbols[i].qt_code; i++) { - if (qt_mac_keyboard_symbols[i].mac_code == key) { - /* To work like Qt for X11 we issue Backtab when Shift + Tab are pressed */ - if (qt_mac_keyboard_symbols[i].qt_code == Qt::Key_Tab && (modif & Qt::ShiftModifier)) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: Qt::Key_Backtab", __LINE__); -#endif - return Qt::Key_Backtab; - } - -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: %s", __LINE__, qt_mac_keyboard_symbols[i].desc); -#endif - return qt_mac_keyboard_symbols[i].qt_code; - } - } - - //last ditch try to match the scan code - for (int i = 0; qt_mac_keyvkey_symbols[i].qt_code; i++) { - if (qt_mac_keyvkey_symbols[i].mac_code == virtualKey) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("%d: got key: %s", __LINE__, qt_mac_keyvkey_symbols[i].desc); -#endif - return qt_mac_keyvkey_symbols[i].qt_code; - } - } - - // check if they belong to key codes in private unicode range - if (key >= 0xf700 && key <= 0xf747) { - if (key >= 0xf704 && key <= 0xf726) { - return Qt::Key_F1 + (key.unicode() - 0xf704) ; - } - for (int i = 0; qt_mac_private_unicode[i].qt_code; i++) { - if (qt_mac_private_unicode[i].mac_code == key) { - return qt_mac_private_unicode[i].qt_code; - } - } - - } - - //oh well -#ifdef DEBUG_KEY_BINDINGS - qDebug("Unknown case.. %s:%d %d[%d] %d", __FILE__, __LINE__, key.unicode(), key.toLatin1(), virtualKey); -#endif - return Qt::Key_unknown; -} - -static Boolean qt_KeyEventComparatorProc(EventRef inEvent, void *data) -{ - UInt32 ekind = GetEventKind(inEvent), - eclass = GetEventClass(inEvent); - return (eclass == kEventClassKeyboard && (void *)ekind == data); -} - -static bool translateKeyEventInternal(EventHandlerCallRef er, EventRef keyEvent, int *qtKey, - QChar *outChar, Qt::KeyboardModifiers *outModifiers, bool *outHandled) -{ - const UInt32 ekind = GetEventKind(keyEvent); - { - UInt32 mac_modifiers = 0; - GetEventParameter(keyEvent, kEventParamKeyModifiers, typeUInt32, 0, - sizeof(mac_modifiers), 0, &mac_modifiers); -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("************ Mapping modifiers and key ***********"); -#endif - *outModifiers = qt_mac_get_modifiers(mac_modifiers); -#ifdef DEBUG_KEY_BINDINGS_MODIFIERS - qDebug("------------ Mapping modifiers and key -----------"); -#endif - } - - //get keycode - UInt32 keyCode = 0; - GetEventParameter(keyEvent, kEventParamKeyCode, typeUInt32, 0, sizeof(keyCode), 0, &keyCode); - - //get mac mapping - static UInt32 tmp_unused_state = 0L; - const UCKeyboardLayout *uchrData = 0; -#if defined(Q_OS_MAC32) - KeyboardLayoutRef keyLayoutRef = 0; - KLGetCurrentKeyboardLayout(&keyLayoutRef); - OSStatus err; - if (keyLayoutRef != 0) { - err = KLGetKeyboardLayoutProperty(keyLayoutRef, kKLuchrData, - (reinterpret_cast(&uchrData))); - if (err != noErr) { - qWarning("Qt::internal::unable to get keyboardlayout %ld %s:%d", - long(err), __FILE__, __LINE__); - } - } -#else - QCFType inputSource = TISCopyCurrentKeyboardInputSource(); - Q_ASSERT(inputSource != 0); - CFDataRef data = static_cast(TISGetInputSourceProperty(inputSource, - kTISPropertyUnicodeKeyLayoutData)); - uchrData = data ? reinterpret_cast(CFDataGetBytePtr(data)) : 0; -#endif - *qtKey = Qt::Key_unknown; - if (uchrData) { - // The easy stuff; use the unicode stuff! - UniChar string[4]; - UniCharCount actualLength; - UInt32 currentModifiers = GetCurrentEventKeyModifiers(); - UInt32 currentModifiersWOAltOrControl = currentModifiers & ~(controlKey | optionKey); - int keyAction; - switch (ekind) { - default: - case kEventRawKeyDown: - keyAction = kUCKeyActionDown; - break; - case kEventRawKeyUp: - keyAction = kUCKeyActionUp; - break; - case kEventRawKeyRepeat: - keyAction = kUCKeyActionAutoKey; - break; - } - OSStatus err = UCKeyTranslate(uchrData, keyCode, keyAction, - ((currentModifiersWOAltOrControl >> 8) & 0xff), LMGetKbdType(), - kUCKeyTranslateNoDeadKeysMask, &tmp_unused_state, 4, &actualLength, - string); - if (err == noErr) { - *outChar = QChar(string[0]); - *qtKey = qt_mac_get_key(*outModifiers, *outChar, keyCode); - if (currentModifiersWOAltOrControl != currentModifiers) { - // Now get the real char. - err = UCKeyTranslate(uchrData, keyCode, keyAction, - ((currentModifiers >> 8) & 0xff), LMGetKbdType(), - kUCKeyTranslateNoDeadKeysMask, &tmp_unused_state, 4, &actualLength, - string); - if (err == noErr) - *outChar = QChar(string[0]); - } - } else { - qWarning("Qt::internal::UCKeyTranslate is returnining %ld %s:%d", - long(err), __FILE__, __LINE__); - } - } -#ifdef Q_OS_MAC32 - else { - // The road less travelled; use KeyTranslate - const void *keyboard_layout; - KeyboardLayoutRef keyLayoutRef = 0; - KLGetCurrentKeyboardLayout(&keyLayoutRef); - err = KLGetKeyboardLayoutProperty(keyLayoutRef, kKLKCHRData, - reinterpret_cast(&keyboard_layout)); - - int translatedChar = KeyTranslate(keyboard_layout, (GetCurrentEventKeyModifiers() & - (kEventKeyModifierNumLockMask|shiftKey|cmdKey| - rightShiftKey|alphaLock)) | keyCode, - &tmp_unused_state); - if (!translatedChar) { - if (outHandled) { - qt_mac_eat_unicode_key = false; - if (er) - CallNextEventHandler(er, keyEvent); - *outHandled = qt_mac_eat_unicode_key; - } - return false; - } - - //map it into qt keys - *qtKey = qt_mac_get_key(*outModifiers, QChar(translatedChar), keyCode); - if (*outModifiers & (Qt::AltModifier | Qt::ControlModifier)) { - if (translatedChar & (1 << 7)) //high ascii - translatedChar = 0; - } else { //now get the real ascii value - UInt32 tmp_mod = 0L; - static UInt32 tmp_state = 0L; - if (*outModifiers & Qt::ShiftModifier) - tmp_mod |= shiftKey; - if (*outModifiers & Qt::MetaModifier) - tmp_mod |= controlKey; - if (*outModifiers & Qt::ControlModifier) - tmp_mod |= cmdKey; - if (GetCurrentEventKeyModifiers() & alphaLock) //no Qt mapper - tmp_mod |= alphaLock; - if (*outModifiers & Qt::AltModifier) - tmp_mod |= optionKey; - if (*outModifiers & Qt::KeypadModifier) - tmp_mod |= kEventKeyModifierNumLockMask; - translatedChar = KeyTranslate(keyboard_layout, tmp_mod | keyCode, &tmp_state); - } - { - ByteCount unilen = 0; - if (GetEventParameter(keyEvent, kEventParamKeyUnicodes, typeUnicodeText, 0, 0, &unilen, 0) - == noErr && unilen == 2) { - GetEventParameter(keyEvent, kEventParamKeyUnicodes, typeUnicodeText, 0, unilen, 0, outChar); - } else if (translatedChar) { - static QTextCodec *c = 0; - if (!c) - c = QTextCodec::codecForName("Apple Roman"); - char tmpChar = (char)translatedChar; // **sigh** - *outChar = c->toUnicode(&tmpChar, 1).at(0); - } else { - *qtKey = qt_mac_get_key(*outModifiers, QChar(translatedChar), keyCode); - } - } - } -#endif - if (*qtKey == Qt::Key_unknown) - *qtKey = qt_mac_get_key(*outModifiers, *outChar, keyCode); - return true; -} - -QKeyMapperPrivate::QKeyMapperPrivate() -{ - memset(keyLayout, 0, sizeof(keyLayout)); - keyboard_layout_format.unicode = 0; -#ifdef Q_OS_MAC32 - keyboard_mode = NullMode; -#else - currentInputSource = 0; -#endif -} - -QKeyMapperPrivate::~QKeyMapperPrivate() -{ - deleteLayouts(); -} - -bool -QKeyMapperPrivate::updateKeyboard() -{ - const UCKeyboardLayout *uchrData = 0; -#ifdef Q_OS_MAC32 - KeyboardLayoutRef keyLayoutRef = 0; - KLGetCurrentKeyboardLayout(&keyLayoutRef); - - if (keyboard_mode != NullMode && currentKeyboardLayout == keyLayoutRef) - return false; - - OSStatus err; - if (keyLayoutRef != 0) { - err = KLGetKeyboardLayoutProperty(keyLayoutRef, kKLuchrData, - const_cast(reinterpret_cast(&uchrData))); - if (err != noErr) { - qWarning("Qt::internal::unable to get unicode keyboardlayout %ld %s:%d", - long(err), __FILE__, __LINE__); - } - } -#else - QCFType source = TISCopyCurrentKeyboardInputSource(); - if (keyboard_mode != NullMode && source == currentInputSource) { - return false; - } - Q_ASSERT(source != 0); - CFDataRef data = static_cast(TISGetInputSourceProperty(source, - kTISPropertyUnicodeKeyLayoutData)); - uchrData = data ? reinterpret_cast(CFDataGetBytePtr(data)) : 0; -#endif - - keyboard_kind = LMGetKbdType(); - if (uchrData) { - keyboard_layout_format.unicode = uchrData; - keyboard_mode = UnicodeMode; - } -#ifdef Q_OS_MAC32 - else { - void *happy; - err = KLGetKeyboardLayoutProperty(keyLayoutRef, kKLKCHRData, - const_cast(reinterpret_cast(&happy))); - if (err != noErr) { - qFatal("Qt::internal::unable to get non-unicode layout, cannot procede %ld %s:%d", - long(err), __FILE__, __LINE__); - } - keyboard_layout_format.other = happy; - keyboard_mode = OtherMode; - } - - currentKeyboardLayout = keyLayoutRef; -#else - currentInputSource = source; -#endif - keyboard_dead = 0; - CFStringRef iso639Code; -#ifdef Q_OS_MAC32 -# ifndef kKLLanguageCode -# define kKLLanguageCode 9 -# endif - KLGetKeyboardLayoutProperty(currentKeyboardLayout, kKLLanguageCode, - reinterpret_cast(&iso639Code)); -#else - CFArrayRef array = static_cast(TISGetInputSourceProperty(currentInputSource, kTISPropertyInputSourceLanguages)); - iso639Code = static_cast(CFArrayGetValueAtIndex(array, 0)); // Actually a RFC3066bis, but it's close enough -#endif - if (iso639Code) { - keyboardInputLocale = QLocale(QCFString::toQString(iso639Code)); - keyboardInputDirection = keyboardInputLocale.textDirection(); - } else { - keyboardInputLocale = QLocale::c(); - keyboardInputDirection = Qt::LeftToRight; - } - return true; -} - -void -QKeyMapperPrivate::deleteLayouts() -{ - keyboard_mode = NullMode; - for (int i = 0; i < 255; ++i) { - if (keyLayout[i]) { - delete keyLayout[i]; - keyLayout[i] = 0; - } - } -} - -void -QKeyMapperPrivate::clearMappings() -{ - deleteLayouts(); - updateKeyboard(); -} - -QList -QKeyMapperPrivate::possibleKeys(QKeyEvent *e) -{ - QList ret; - - KeyboardLayoutItem *kbItem = keyLayout[e->nativeVirtualKey()]; - if (!kbItem) // Key is not in any keyboard layout (e.g. eisu-key on Japanese keyboard) - return ret; - - int baseKey = kbItem->qtKey[0]; - Qt::KeyboardModifiers keyMods = e->modifiers(); - ret << int(baseKey + keyMods); // The base key is _always_ valid, of course - - for (int i = 1; i < 8; ++i) { - Qt::KeyboardModifiers neededMods = ModsTbl[i]; - int key = kbItem->qtKey[i]; - if (key && key != baseKey && ((keyMods & neededMods) == neededMods)) - ret << int(key + (keyMods & ~neededMods)); - } - - return ret; -} - -bool QKeyMapperPrivate::translateKeyEvent(QWidget *widget, EventHandlerCallRef er, EventRef event, - void *info, bool grab) -{ - Q_ASSERT(GetEventClass(event) == kEventClassKeyboard); - bool handled_event=true; - UInt32 ekind = GetEventKind(event); - - // unfortunately modifiers changed event looks quite different, so I have a separate - // code path - if (ekind == kEventRawKeyModifiersChanged) { - //figure out changed modifiers, wish Apple would just send a delta - UInt32 modifiers = 0; - GetEventParameter(event, kEventParamKeyModifiers, typeUInt32, 0, - sizeof(modifiers), 0, &modifiers); - qt_mac_send_modifiers_changed(modifiers, widget); - return true; - } - - QInputContext *currentContext = qApp->inputContext(); - if (currentContext && currentContext->isComposing()) { - if (ekind == kEventRawKeyDown) { - QMacInputContext *context = qobject_cast(currentContext); - if (context) - context->setLastKeydownEvent(event); - } - return false; - } - // Once we process the key down , we don't need to send the saved event again from - // kEventTextInputUnicodeForKeyEvent, so clear it. - if (currentContext && ekind == kEventRawKeyDown) { - QMacInputContext *context = qobject_cast(currentContext); - if (context) - context->setLastKeydownEvent(0); - } - - //get modifiers - Qt::KeyboardModifiers modifiers; - int qtKey; - QChar ourChar; - if (translateKeyEventInternal(er, event, &qtKey, &ourChar, &modifiers, - &handled_event) == false) - return handled_event; - QString text(ourChar); - /* This is actually wrong - but unfortunately it is the best that can be - done for now because of the Control/Meta mapping problems */ - if (modifiers & (Qt::ControlModifier | Qt::MetaModifier) - && !qApp->testAttribute(Qt::AA_MacDontSwapCtrlAndMeta)) { - text = QString(); - } - - - if (widget) { - // Try to compress key events. - if (!text.isEmpty() && widget->testAttribute(Qt::WA_KeyCompression)) { - EventTime lastTime = GetEventTime(event); - for (;;) { - EventRef releaseEvent = FindSpecificEventInQueue(GetMainEventQueue(), - qt_KeyEventComparatorProc, - (void*)kEventRawKeyUp); - if (!releaseEvent) - break; - const EventTime releaseTime = GetEventTime(releaseEvent); - if (releaseTime < lastTime) - break; - lastTime = releaseTime; - - EventRef pressEvent = FindSpecificEventInQueue(GetMainEventQueue(), - qt_KeyEventComparatorProc, - (void*)kEventRawKeyDown); - if (!pressEvent) - break; - const EventTime pressTime = GetEventTime(pressEvent); - if (pressTime < lastTime) - break; - lastTime = pressTime; - - Qt::KeyboardModifiers compressMod; - int compressQtKey = 0; - QChar compressChar; - if (translateKeyEventInternal(er, pressEvent, - &compressQtKey, &compressChar, &compressMod, 0) - == false) { - break; - } - // Copied from qapplication_x11.cpp (change both). - - bool stopCompression = - // 1) misc keys - (compressQtKey >= Qt::Key_Escape && compressQtKey <= Qt::Key_SysReq) - // 2) cursor movement - || (compressQtKey >= Qt::Key_Home && compressQtKey <= Qt::Key_PageDown) - // 3) extra keys - || (compressQtKey >= Qt::Key_Super_L && compressQtKey <= Qt::Key_Direction_R) - // 4) something that a) doesn't translate to text or b) translates - // to newline text - || (compressQtKey == 0) - || (compressChar == QLatin1Char('\n')) - || (compressQtKey == Qt::Key_unknown); - - if (compressMod == modifiers && !compressChar.isNull() && !stopCompression) { -#ifdef DEBUG_KEY_BINDINGS - qDebug("compressing away %c", compressChar.toLatin1()); -#endif - text += compressChar; - // Clean up - RemoveEventFromQueue(GetMainEventQueue(), releaseEvent); - RemoveEventFromQueue(GetMainEventQueue(), pressEvent); - } else { -#ifdef DEBUG_KEY_BINDINGS - qDebug("stoping compression.."); -#endif - break; - } - } - } - - // There is no way to get the scan code from carbon. But we cannot use the value 0, since - // it indicates that the event originates from somewhere else than the keyboard - UInt32 macScanCode = 1; - UInt32 macVirtualKey = 0; - GetEventParameter(event, kEventParamKeyCode, typeUInt32, 0, sizeof(macVirtualKey), 0, &macVirtualKey); - UInt32 macModifiers = 0; - GetEventParameter(event, kEventParamKeyModifiers, typeUInt32, 0, - sizeof(macModifiers), 0, &macModifiers); - // The unicode characters in the range 0xF700-0xF747 are reserved - // by Mac OS X for transient use as keyboard function keys. We - // wont send 'text' for such key events. This is done to match - // behavior on other platforms. - unsigned int *unicodeKey = (unsigned int*)info; - if (*unicodeKey >= 0xf700 && *unicodeKey <= 0xf747) - text = QString(); - bool isAccepted; - handled_event = QKeyMapper::sendKeyEvent(widget, grab, - (ekind == kEventRawKeyUp) ? QEvent::KeyRelease : QEvent::KeyPress, - qtKey, modifiers, text, ekind == kEventRawKeyRepeat, 0, - macScanCode, macVirtualKey, macModifiers - ,&isAccepted - ); - *unicodeKey = (unsigned int)isAccepted; - } - return handled_event; -} - -void -QKeyMapperPrivate::updateKeyMap(EventHandlerCallRef, EventRef event, void * - unicodeKey // unicode character from NSEvent (modifiers applied) - ) -{ - UInt32 macVirtualKey = 0; - GetEventParameter(event, kEventParamKeyCode, typeUInt32, 0, sizeof(macVirtualKey), 0, &macVirtualKey); - if (updateKeyboard()) - QKeyMapper::changeKeyboard(); - else if (keyLayout[macVirtualKey]) - return; - - UniCharCount buffer_size = 10; - UniChar buffer[buffer_size]; - keyLayout[macVirtualKey] = new KeyboardLayoutItem; - for (int i = 0; i < 16; ++i) { - UniCharCount out_buffer_size = 0; - keyLayout[macVirtualKey]->qtKey[i] = 0; -#ifdef Q_WS_MAC32 - if (keyboard_mode == UnicodeMode) { -#endif - const UInt32 keyModifier = ((qt_mac_get_mac_modifiers(ModsTbl[i]) >> 8) & 0xFF); - OSStatus err = UCKeyTranslate(keyboard_layout_format.unicode, macVirtualKey, kUCKeyActionDown, keyModifier, - keyboard_kind, 0, &keyboard_dead, buffer_size, &out_buffer_size, buffer); - if (err == noErr && out_buffer_size) { - const QChar unicode(buffer[0]); - int qtkey = qt_mac_get_key(keyModifier, unicode, macVirtualKey); - if (qtkey == Qt::Key_unknown) - qtkey = unicode.unicode(); - keyLayout[macVirtualKey]->qtKey[i] = qtkey; - } -#ifndef Q_WS_MAC32 - else { - const QChar unicode(*((UniChar *)unicodeKey)); - int qtkey = qt_mac_get_key(keyModifier, unicode, macVirtualKey); - if (qtkey == Qt::Key_unknown) - qtkey = unicode.unicode(); - keyLayout[macVirtualKey]->qtKey[i] = qtkey; - } -#endif -#ifdef Q_WS_MAC32 - } else { - const UInt32 keyModifier = (qt_mac_get_mac_modifiers(ModsTbl[i])); - - uchar translatedChar = KeyTranslate(keyboard_layout_format.other, keyModifier | macVirtualKey, &keyboard_dead); - if (translatedChar) { - static QTextCodec *c = 0; - if (!c) - c = QTextCodec::codecForName("Apple Roman"); - const QChar unicode(c->toUnicode((const char *)&translatedChar, 1).at(0)); - int qtkey = qt_mac_get_key(keyModifier, unicode, macVirtualKey); - if (qtkey == Qt::Key_unknown) - qtkey = unicode.unicode(); - keyLayout[macVirtualKey]->qtKey[i] = qtkey; - } - } -#endif - } -#ifdef DEBUG_KEY_MAPS - qDebug("updateKeyMap for virtual key = 0x%02x!", (uint)macVirtualKey); - for (int i = 0; i < 16; ++i) { - qDebug(" [%d] (%d,0x%02x,'%c')", i, - keyLayout[macVirtualKey]->qtKey[i], - keyLayout[macVirtualKey]->qtKey[i], - keyLayout[macVirtualKey]->qtKey[i]); - } -#endif -} - -bool -QKeyMapper::sendKeyEvent(QWidget *widget, bool grab, - QEvent::Type type, int code, Qt::KeyboardModifiers modifiers, - const QString &text, bool autorepeat, int count, - quint32 nativeScanCode, quint32 nativeVirtualKey, - quint32 nativeModifiers, bool *isAccepted) -{ - Q_UNUSED(count); - Q_UNUSED(grab); - - if (widget && widget->isEnabled()) { - bool key_event = true; - if (key_event) { -#if defined(DEBUG_KEY_BINDINGS) || defined(DEBUG_KEY_BINDINGS_MODIFIERS) - qDebug("KeyEvent: Sending %s to %s::%s: %s 0x%08x%s", - type == QEvent::KeyRelease ? "KeyRelease" : "KeyPress", - widget ? widget->metaObject()->className() : "none", - widget ? widget->objectName().toLatin1().constData() : "", - text.toLatin1().constData(), int(modifiers), - autorepeat ? " Repeat" : ""); -#endif - QKeyEventEx ke(type, code, modifiers, text, autorepeat, qMax(1, text.length()), - nativeScanCode, nativeVirtualKey, nativeModifiers); - bool retMe = qt_sendSpontaneousEvent(widget,&ke); - if (isAccepted) - *isAccepted = ke.isAccepted(); - return retMe; - } - } - return false; -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qmacgesturerecognizer_mac.mm b/src/widgets/platforms/mac/qmacgesturerecognizer_mac.mm deleted file mode 100644 index 54823aa..0000000 --- a/src/widgets/platforms/mac/qmacgesturerecognizer_mac.mm +++ /dev/null @@ -1,270 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qmacgesturerecognizer_mac_p.h" -#include "qgesture.h" -#include "qgesture_p.h" -#include "qevent.h" -#include "qevent_p.h" -#include "qwidget.h" -#include "qdebug.h" - -#ifndef QT_NO_GESTURES - -QT_BEGIN_NAMESPACE - -QMacSwipeGestureRecognizer::QMacSwipeGestureRecognizer() -{ -} - -QGesture *QMacSwipeGestureRecognizer::create(QObject * /*target*/) -{ - return new QSwipeGesture; -} - -QGestureRecognizer::Result -QMacSwipeGestureRecognizer::recognize(QGesture *gesture, QObject *obj, QEvent *event) -{ - if (event->type() == QEvent::NativeGesture && obj->isWidgetType()) { - QNativeGestureEvent *ev = static_cast(event); - switch (ev->gestureType) { - case QNativeGestureEvent::Swipe: { - QSwipeGesture *g = static_cast(gesture); - g->setSwipeAngle(ev->angle); - g->setHotSpot(ev->position); - return QGestureRecognizer::FinishGesture | QGestureRecognizer::ConsumeEventHint; - break; } - default: - break; - } - } - - return QGestureRecognizer::Ignore; -} - -void QMacSwipeGestureRecognizer::reset(QGesture *gesture) -{ - QSwipeGesture *g = static_cast(gesture); - g->setSwipeAngle(0); - QGestureRecognizer::reset(gesture); -} - -//////////////////////////////////////////////////////////////////////// - -QMacPinchGestureRecognizer::QMacPinchGestureRecognizer() -{ -} - -QGesture *QMacPinchGestureRecognizer::create(QObject * /*target*/) -{ - return new QPinchGesture; -} - -QGestureRecognizer::Result -QMacPinchGestureRecognizer::recognize(QGesture *gesture, QObject *obj, QEvent *event) -{ - if (event->type() == QEvent::NativeGesture && obj->isWidgetType()) { - QPinchGesture *g = static_cast(gesture); - QNativeGestureEvent *ev = static_cast(event); - switch(ev->gestureType) { - case QNativeGestureEvent::GestureBegin: - reset(gesture); - g->setStartCenterPoint(static_cast(obj)->mapFromGlobal(ev->position)); - g->setCenterPoint(g->startCenterPoint()); - g->setChangeFlags(QPinchGesture::CenterPointChanged); - g->setTotalChangeFlags(g->totalChangeFlags() | g->changeFlags()); - g->setHotSpot(ev->position); - return QGestureRecognizer::MayBeGesture | QGestureRecognizer::ConsumeEventHint; - case QNativeGestureEvent::Rotate: { - g->setLastScaleFactor(g->scaleFactor()); - g->setLastRotationAngle(g->rotationAngle()); - g->setRotationAngle(g->rotationAngle() + ev->percentage); - g->setChangeFlags(QPinchGesture::RotationAngleChanged); - g->setTotalChangeFlags(g->totalChangeFlags() | g->changeFlags()); - g->setHotSpot(ev->position); - return QGestureRecognizer::TriggerGesture | QGestureRecognizer::ConsumeEventHint; - } - case QNativeGestureEvent::Zoom: - g->setLastScaleFactor(g->scaleFactor()); - g->setLastRotationAngle(g->rotationAngle()); - g->setScaleFactor(g->scaleFactor() * (1 + ev->percentage)); - g->setChangeFlags(QPinchGesture::ScaleFactorChanged); - g->setTotalChangeFlags(g->totalChangeFlags() | g->changeFlags()); - g->setHotSpot(ev->position); - return QGestureRecognizer::TriggerGesture | QGestureRecognizer::ConsumeEventHint; - case QNativeGestureEvent::GestureEnd: - return QGestureRecognizer::FinishGesture | QGestureRecognizer::ConsumeEventHint; - default: - break; - } - } - - return QGestureRecognizer::Ignore; -} - -void QMacPinchGestureRecognizer::reset(QGesture *gesture) -{ - QPinchGesture *g = static_cast(gesture); - g->setChangeFlags(0); - g->setTotalChangeFlags(0); - g->setScaleFactor(1.0f); - g->setTotalScaleFactor(1.0f); - g->setLastScaleFactor(1.0f); - g->setRotationAngle(0.0f); - g->setTotalRotationAngle(0.0f); - g->setLastRotationAngle(0.0f); - g->setCenterPoint(QPointF()); - g->setStartCenterPoint(QPointF()); - g->setLastCenterPoint(QPointF()); - QGestureRecognizer::reset(gesture); -} - -//////////////////////////////////////////////////////////////////////// - - -QMacPanGestureRecognizer::QMacPanGestureRecognizer() : _panCanceled(true) -{ -} - -QGesture *QMacPanGestureRecognizer::create(QObject *target) -{ - if (!target) - return new QPanGesture; - - if (QWidget *w = qobject_cast(target)) { - w->setAttribute(Qt::WA_AcceptTouchEvents); - w->setAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents); - return new QPanGesture; - } - return 0; -} - -QGestureRecognizer::Result -QMacPanGestureRecognizer::recognize(QGesture *gesture, QObject *target, QEvent *event) -{ - const int panBeginDelay = 300; - const int panBeginRadius = 3; - - QPanGesture *g = static_cast(gesture); - - switch (event->type()) { - case QEvent::TouchBegin: { - const QTouchEvent *ev = static_cast(event); - if (ev->touchPoints().size() == 1) { - reset(gesture); - _startPos = QCursor::pos(); - _panTimer.start(panBeginDelay, target); - _panCanceled = false; - return QGestureRecognizer::MayBeGesture; - } - break;} - case QEvent::TouchEnd: { - if (_panCanceled) - break; - - const QTouchEvent *ev = static_cast(event); - if (ev->touchPoints().size() == 1) - return QGestureRecognizer::FinishGesture; - break;} - case QEvent::TouchUpdate: { - if (_panCanceled) - break; - - const QTouchEvent *ev = static_cast(event); - if (ev->touchPoints().size() == 1) { - if (_panTimer.isActive()) { - // INVARIANT: Still in maybeGesture. Check if the user - // moved his finger so much that it makes sense to cancel the pan: - const QPointF p = QCursor::pos(); - if ((p - _startPos).manhattanLength() > panBeginRadius) { - _panCanceled = true; - _panTimer.stop(); - return QGestureRecognizer::CancelGesture; - } - } else { - const QPointF p = QCursor::pos(); - const QPointF posOffset = p - _startPos; - g->setLastOffset(g->offset()); - g->setOffset(QPointF(posOffset.x(), posOffset.y())); - g->setHotSpot(_startPos); - return QGestureRecognizer::TriggerGesture; - } - } else if (_panTimer.isActive()) { - // I only want to cancel the pan if the user is pressing - // more than one finger, and the pan hasn't started yet: - _panCanceled = true; - _panTimer.stop(); - return QGestureRecognizer::CancelGesture; - } - break;} - case QEvent::Timer: { - QTimerEvent *ev = static_cast(event); - if (ev->timerId() == _panTimer.timerId()) { - _panTimer.stop(); - if (_panCanceled) - break; - // Begin new pan session! - _startPos = QCursor::pos(); - g->setHotSpot(_startPos); - return QGestureRecognizer::TriggerGesture | QGestureRecognizer::ConsumeEventHint; - } - break; } - default: - break; - } - - return QGestureRecognizer::Ignore; -} - -void QMacPanGestureRecognizer::reset(QGesture *gesture) -{ - QPanGesture *g = static_cast(gesture); - _startPos = QPointF(); - _panCanceled = true; - g->setOffset(QPointF(0, 0)); - g->setLastOffset(QPointF(0, 0)); - g->setAcceleration(qreal(1)); - QGestureRecognizer::reset(gesture); -} - -QT_END_NAMESPACE - -#endif // QT_NO_GESTURES diff --git a/src/widgets/platforms/mac/qmacgesturerecognizer_mac_p.h b/src/widgets/platforms/mac/qmacgesturerecognizer_mac_p.h deleted file mode 100644 index c77ead3..0000000 --- a/src/widgets/platforms/mac/qmacgesturerecognizer_mac_p.h +++ /dev/null @@ -1,104 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#ifndef QMACSWIPEGESTURERECOGNIZER_MAC_P_H -#define QMACSWIPEGESTURERECOGNIZER_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of other Qt classes. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include "qtimer.h" -#include "qpoint.h" -#include "qgesturerecognizer.h" - -#ifndef QT_NO_GESTURES - -QT_BEGIN_NAMESPACE - -class QMacSwipeGestureRecognizer : public QGestureRecognizer -{ -public: - QMacSwipeGestureRecognizer(); - - QGesture *create(QObject *target); - QGestureRecognizer::Result recognize(QGesture *gesture, QObject *watched, QEvent *event); - void reset(QGesture *gesture); -}; - -class QMacPinchGestureRecognizer : public QGestureRecognizer -{ -public: - QMacPinchGestureRecognizer(); - - QGesture *create(QObject *target); - QGestureRecognizer::Result recognize(QGesture *gesture, QObject *watched, QEvent *event); - void reset(QGesture *gesture); -}; - - -class QMacPanGestureRecognizer : public QObject, public QGestureRecognizer -{ -public: - QMacPanGestureRecognizer(); - - QGesture *create(QObject *target); - QGestureRecognizer::Result recognize(QGesture *gesture, QObject *watched, QEvent *event); - void reset(QGesture *gesture); -private: - QPointF _startPos; - QBasicTimer _panTimer; - bool _panCanceled; -}; - - -QT_END_NAMESPACE - -#endif // QT_NO_GESTURES - -#endif // QMACSWIPEGESTURERECOGNIZER_MAC_P_H diff --git a/src/widgets/platforms/mac/qmacinputcontext_mac.cpp b/src/widgets/platforms/mac/qmacinputcontext_mac.cpp deleted file mode 100644 index ee0bf70..0000000 --- a/src/widgets/platforms/mac/qmacinputcontext_mac.cpp +++ /dev/null @@ -1,124 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include -#include -#include "qtextformat.h" -#include -#include -#include - -QT_BEGIN_NAMESPACE - -extern bool qt_sendSpontaneousEvent(QObject*, QEvent*); - -#if (MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_5) -# define typeRefCon typeSInt32 -# define typeByteCount typeSInt32 -#endif - -QMacInputContext::QMacInputContext(QObject *parent) - : QInputContext(parent), composing(false), recursionGuard(false), textDocument(0), - keydownEvent(0) -{ -// createTextDocument(); -} - -QMacInputContext::~QMacInputContext() -{ -} - -void -QMacInputContext::createTextDocument() -{ -} - - -QString QMacInputContext::language() -{ - return QString(); -} - - -void QMacInputContext::mouseHandler(int pos, QMouseEvent *e) -{ - Q_UNUSED(pos); - Q_UNUSED(e); -} - - -void QMacInputContext::setFocusWidget(QWidget *w) -{ - createTextDocument(); - QInputContext::setFocusWidget(w); -} - - - -void -QMacInputContext::initialize() -{ -} - -void -QMacInputContext::cleanup() -{ -} - -void QMacInputContext::setLastKeydownEvent(EventRef event) -{ - EventRef tmpEvent = keydownEvent; - keydownEvent = event; - if (keydownEvent) - RetainEvent(keydownEvent); - if (tmpEvent) - ReleaseEvent(tmpEvent); -} - -OSStatus -QMacInputContext::globalEventProcessor(EventHandlerCallRef, EventRef event, void *) -{ - Q_UNUSED(event); - return noErr; //we eat the event -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qmacinputcontext_p.h b/src/widgets/platforms/mac/qmacinputcontext_p.h deleted file mode 100644 index 7a7ef96..0000000 --- a/src/widgets/platforms/mac/qmacinputcontext_p.h +++ /dev/null @@ -1,97 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#ifndef QMACINPUTCONTEXT_P_H -#define QMACINPUTCONTEXT_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include "QtWidgets/qinputcontext.h" -#include "private/qt_mac_p.h" - -QT_BEGIN_NAMESPACE - -class Q_WIDGETS_EXPORT QMacInputContext : public QInputContext -{ - Q_OBJECT - //Q_DECLARE_PRIVATE(QMacInputContext) - void createTextDocument(); -public: - explicit QMacInputContext(QObject* parent = 0); - virtual ~QMacInputContext(); - - virtual void setFocusWidget(QWidget *w); - virtual QString identifierName() { return QLatin1String("mac"); } - virtual QString language(); - - virtual void reset(); - - virtual bool isComposing() const; - - static OSStatus globalEventProcessor(EventHandlerCallRef, EventRef, void *); - static void initialize(); - static void cleanup(); - - EventRef lastKeydownEvent() { return keydownEvent; } - void setLastKeydownEvent(EventRef); - -protected: - void mouseHandler(int pos, QMouseEvent *); -private: - bool composing; - bool recursionGuard; - TSMDocumentID textDocument; - QString currentText; - EventRef keydownEvent; -}; - -QT_END_NAMESPACE - -#endif // QMACINPUTCONTEXT_P_H diff --git a/src/widgets/platforms/mac/qmime_mac.cpp b/src/widgets/platforms/mac/qmime_mac.cpp deleted file mode 100644 index 730f672..0000000 --- a/src/widgets/platforms/mac/qmime_mac.cpp +++ /dev/null @@ -1,1126 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qmime.h" - -//#define USE_INTERNET_CONFIG - -#ifndef USE_INTERNET_CONFIG -# include "qfile.h" -# include "qfileinfo.h" -# include "qtextstream.h" -# include "qdir.h" -# include -# include -# include -# include -#endif - -#include "qdebug.h" -#include "qpixmap.h" -#include "qimagewriter.h" -#include "qimagereader.h" -#include "qdatastream.h" -#include "qbuffer.h" -#include "qdatetime.h" -#include "qapplication_p.h" -#include "qtextcodec.h" -#include "qregexp.h" -#include "qurl.h" -#include "qmap.h" -#include - - -#ifdef Q_WS_MAC32 -#include -#include -#endif - -QT_BEGIN_NAMESPACE - -extern CGImageRef qt_mac_createCGImageFromQImage(const QImage &img, const QImage **imagePtr = 0); // qpaintengine_mac.cpp - -typedef QList MimeList; -Q_GLOBAL_STATIC(MimeList, globalMimeList) - -static void cleanup_mimes() -{ - MimeList *mimes = globalMimeList(); - while (!mimes->isEmpty()) - delete mimes->takeFirst(); -} - -Q_GLOBAL_STATIC(QStringList, globalDraggedTypesList) - -/*! - \fn void qRegisterDraggedTypes(const QStringList &types) - \relates QMacPasteboardMime - - Registers the given \a types as custom pasteboard types. - - This function should be called to enable the Drag and Drop events - for custom pasteboard types on Cocoa implementations. This is required - in addition to a QMacPasteboardMime subclass implementation. By default - drag and drop is enabled for all standard pasteboard types. - - \sa QMacPasteboardMime -*/ -Q_WIDGETS_EXPORT void qRegisterDraggedTypes(const QStringList &types) -{ - (*globalDraggedTypesList()) += types; -} - -const QStringList& qEnabledDraggedTypes() -{ - return (*globalDraggedTypesList()); -} - - -/***************************************************************************** - QDnD debug facilities - *****************************************************************************/ -//#define DEBUG_MIME_MAPS - -//functions -extern QString qt_mac_from_pascal_string(const Str255); //qglobal.cpp -extern void qt_mac_from_pascal_string(QString, Str255, TextEncoding encoding=0, int len=-1); //qglobal.cpp - -ScrapFlavorType qt_mac_mime_type = 'CUTE'; -CFStringRef qt_mac_mime_typeUTI = CFSTR("com.pasteboard.trolltech.marker"); - -/*! - \class QMacPasteboardMime - \brief The QMacPasteboardMime class converts between a MIME type and a - \l{http://developer.apple.com/macosx/uniformtypeidentifiers.html}{Uniform - Type Identifier (UTI)} format. - \since 4.2 - - \ingroup draganddrop - \inmodule QtWidgets - - Qt's drag and drop and clipboard facilities use the MIME - standard. On X11, this maps trivially to the Xdnd protocol. On - Mac, although some applications use MIME to describe clipboard - contents, it is more common to use Apple's UTI format. - - QMacPasteboardMime's role is to bridge the gap between MIME and UTI; - By subclasses this class, one can extend Qt's drag and drop - and clipboard handling to convert to and from unsupported, or proprietary, UTI formats. - - A subclass of QMacPasteboardMime will automatically be registered, and active, upon instantiation. - - Qt has predefined support for the following UTIs: - \list - \i public.utf8-plain-text - converts to "text/plain" - \i public.utf16-plain-text - converts to "text/plain" - \i public.html - converts to "text/html" - \i public.url - converts to "text/uri-list" - \i public.file-url - converts to "text/uri-list" - \i public.tiff - converts to "application/x-qt-image" - \i public.vcard - converts to "text/plain" - \i com.apple.traditional-mac-plain-text - converts to "text/plain" - \i com.apple.pict - converts to "application/x-qt-image" - \endlist - - When working with MIME data, Qt will interate through all instances of QMacPasteboardMime to - find an instance that can convert to, or from, a specific MIME type. It will do this by calling - canConvert() on each instance, starting with (and choosing) the last created instance first. - The actual conversions will be done by using convertToMime() and convertFromMime(). - - \note The API uses the term "flavor" in some cases. This is for backwards - compatibility reasons, and should now be understood as UTIs. -*/ - -/*! \enum QMacPasteboardMime::QMacPasteboardMimeType - \internal -*/ - -/*! - Constructs a new conversion object of type \a t, adding it to the - globally accessed list of available convertors. -*/ -QMacPasteboardMime::QMacPasteboardMime(char t) : type(t) -{ - globalMimeList()->append(this); -} - -/*! - Destroys a conversion object, removing it from the global - list of available convertors. -*/ -QMacPasteboardMime::~QMacPasteboardMime() -{ - if(!QApplication::closingDown()) - globalMimeList()->removeAll(this); -} - -class QMacPasteboardMimeAny : public QMacPasteboardMime { -private: - -public: - QMacPasteboardMimeAny() : QMacPasteboardMime(MIME_QT_CONVERTOR|MIME_ALL) { - } - ~QMacPasteboardMimeAny() { - } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeAny::convertorName() -{ - return QLatin1String("Any-Mime"); -} - -QString QMacPasteboardMimeAny::flavorFor(const QString &mime) -{ - // do not handle the mime type name in the drag pasteboard - if(mime == QLatin1String("application/x-qt-mime-type-name")) - return QString(); - QString ret = QLatin1String("com.trolltech.anymime.") + mime; - return ret.replace(QLatin1Char('/'), QLatin1String("--")); -} - -QString QMacPasteboardMimeAny::mimeFor(QString flav) -{ - const QString any_prefix = QLatin1String("com.trolltech.anymime."); - if(flav.size() > any_prefix.length() && flav.startsWith(any_prefix)) - return flav.mid(any_prefix.length()).replace(QLatin1String("--"), QLatin1String("/")); - return QString(); -} - -bool QMacPasteboardMimeAny::canConvert(const QString &mime, QString flav) -{ - return mimeFor(flav) == mime; -} - -QVariant QMacPasteboardMimeAny::convertToMime(const QString &mime, QList data, QString) -{ - if(data.count() > 1) - qWarning("QMacPasteboardMimeAny: Cannot handle multiple member data"); - QVariant ret; - if (mime == QLatin1String("text/plain")) - ret = QString::fromUtf8(data.first()); - else - ret = data.first(); - return ret; -} - -QList QMacPasteboardMimeAny::convertFromMime(const QString &mime, QVariant data, QString) -{ - QList ret; - if (mime == QLatin1String("text/plain")) - ret.append(data.toString().toUtf8()); - else - ret.append(data.toByteArray()); - return ret; -} - -class QMacPasteboardMimeTypeName : public QMacPasteboardMime { -private: - -public: - QMacPasteboardMimeTypeName() : QMacPasteboardMime(MIME_QT_CONVERTOR|MIME_ALL) { - } - ~QMacPasteboardMimeTypeName() { - } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeTypeName::convertorName() -{ - return QLatin1String("Qt-Mime-Type"); -} - -QString QMacPasteboardMimeTypeName::flavorFor(const QString &mime) -{ - if(mime == QLatin1String("application/x-qt-mime-type-name")) - return QLatin1String("com.trolltech.qt.MimeTypeName"); - return QString(); -} - -QString QMacPasteboardMimeTypeName::mimeFor(QString) -{ - return QString(); -} - -bool QMacPasteboardMimeTypeName::canConvert(const QString &, QString) -{ - return false; -} - -QVariant QMacPasteboardMimeTypeName::convertToMime(const QString &, QList, QString) -{ - QVariant ret; - return ret; -} - -QList QMacPasteboardMimeTypeName::convertFromMime(const QString &, QVariant, QString) -{ - QList ret; - ret.append(QString("x-qt-mime-type-name").toUtf8()); - return ret; -} - -class QMacPasteboardMimePlainText : public QMacPasteboardMime { -public: - QMacPasteboardMimePlainText() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimePlainText::convertorName() -{ - return QLatin1String("PlainText"); -} - -QString QMacPasteboardMimePlainText::flavorFor(const QString &mime) -{ - if (mime == QLatin1String("text/plain")) - return QLatin1String("com.apple.traditional-mac-plain-text"); - return QString(); -} - -QString QMacPasteboardMimePlainText::mimeFor(QString flav) -{ - if (flav == QLatin1String("com.apple.traditional-mac-plain-text")) - return QLatin1String("text/plain"); - return QString(); -} - -bool QMacPasteboardMimePlainText::canConvert(const QString &mime, QString flav) -{ - return flavorFor(mime) == flav; -} - -QVariant QMacPasteboardMimePlainText::convertToMime(const QString &mimetype, QList data, QString flavor) -{ - if(data.count() > 1) - qWarning("QMacPasteboardMimePlainText: Cannot handle multiple member data"); - const QByteArray &firstData = data.first(); - QVariant ret; - if(flavor == QCFString(QLatin1String("com.apple.traditional-mac-plain-text"))) { - QCFString str(CFStringCreateWithBytes(kCFAllocatorDefault, - reinterpret_cast(firstData.constData()), - firstData.size(), CFStringGetSystemEncoding(), false)); - ret = QString(str); - } else { - qWarning("QMime::convertToMime: unhandled mimetype: %s", qPrintable(mimetype)); - } - return ret; -} - -QList QMacPasteboardMimePlainText::convertFromMime(const QString &, QVariant data, QString flavor) -{ - QList ret; - QString string = data.toString(); - if(flavor == QCFString(QLatin1String("com.apple.traditional-mac-plain-text"))) - ret.append(string.toLatin1()); - return ret; -} - -class QMacPasteboardMimeUnicodeText : public QMacPasteboardMime { -public: - QMacPasteboardMimeUnicodeText() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeUnicodeText::convertorName() -{ - return QLatin1String("UnicodeText"); -} - -QString QMacPasteboardMimeUnicodeText::flavorFor(const QString &mime) -{ - if (mime == QLatin1String("text/plain")) - return QLatin1String("public.utf16-plain-text"); - int i = mime.indexOf(QLatin1String("charset=")); - if (i >= 0) { - QString cs(mime.mid(i+8).toLower()); - i = cs.indexOf(QLatin1Char(';')); - if (i>=0) - cs = cs.left(i); - if (cs == QLatin1String("system")) - return QLatin1String("public.utf8-plain-text"); - else if (cs == QLatin1String("iso-10646-ucs-2") - || cs == QLatin1String("utf16")) - return QLatin1String("public.utf16-plain-text"); - } - return QString(); -} - -QString QMacPasteboardMimeUnicodeText::mimeFor(QString flav) -{ - if (flav == QLatin1String("public.utf16-plain-text") || flav == QLatin1String("public.utf8-plain-text")) - return QLatin1String("text/plain"); - return QString(); -} - -bool QMacPasteboardMimeUnicodeText::canConvert(const QString &mime, QString flav) -{ - return flavorFor(mime) == flav; -} - -QVariant QMacPasteboardMimeUnicodeText::convertToMime(const QString &mimetype, QList data, QString flavor) -{ - if(data.count() > 1) - qWarning("QMacPasteboardMimeUnicodeText: Cannot handle multiple member data"); - const QByteArray &firstData = data.first(); - // I can only handle two types (system and unicode) so deal with them that way - QVariant ret; - if(flavor == QLatin1String("public.utf8-plain-text")) { - QCFString str(CFStringCreateWithBytes(kCFAllocatorDefault, - reinterpret_cast(firstData.constData()), - firstData.size(), CFStringGetSystemEncoding(), false)); - ret = QString(str); - } else if (flavor == QLatin1String("public.utf16-plain-text")) { - ret = QString(reinterpret_cast(firstData.constData()), - firstData.size() / sizeof(QChar)); - } else { - qWarning("QMime::convertToMime: unhandled mimetype: %s", qPrintable(mimetype)); - } - return ret; -} - -QList QMacPasteboardMimeUnicodeText::convertFromMime(const QString &, QVariant data, QString flavor) -{ - QList ret; - QString string = data.toString(); - if(flavor == QLatin1String("public.utf8-plain-text")) - ret.append(string.toUtf8()); - else if (flavor == QLatin1String("public.utf16-plain-text")) - ret.append(QByteArray((char*)string.utf16(), string.length()*2)); - return ret; -} - -class QMacPasteboardMimeHTMLText : public QMacPasteboardMime { -public: - QMacPasteboardMimeHTMLText() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeHTMLText::convertorName() -{ - return QLatin1String("HTML"); -} - -QString QMacPasteboardMimeHTMLText::flavorFor(const QString &mime) -{ - if (mime == QLatin1String("text/html")) - return QLatin1String("public.html"); - return QString(); -} - -QString QMacPasteboardMimeHTMLText::mimeFor(QString flav) -{ - if (flav == QLatin1String("public.html")) - return QLatin1String("text/html"); - return QString(); -} - -bool QMacPasteboardMimeHTMLText::canConvert(const QString &mime, QString flav) -{ - return flavorFor(mime) == flav; -} - -QVariant QMacPasteboardMimeHTMLText::convertToMime(const QString &mimeType, QList data, QString flavor) -{ - if (!canConvert(mimeType, flavor)) - return QVariant(); - if (data.count() > 1) - qWarning("QMacPasteboardMimeHTMLText: Cannot handle multiple member data"); - return data.first(); -} - -QList QMacPasteboardMimeHTMLText::convertFromMime(const QString &mime, QVariant data, QString flavor) -{ - QList ret; - if (!canConvert(mime, flavor)) - return ret; - ret.append(data.toByteArray()); - return ret; -} - - -#ifdef Q_WS_MAC32 - -// This can be removed once 10.6 is the minimum (or we have to require 64-bit) whichever comes first. - -typedef ComponentResult (*PtrGraphicsImportSetDataHandle)(GraphicsImportComponent, Handle); -typedef ComponentResult (*PtrGraphicsImportCreateCGImage)(GraphicsImportComponent, CGImageRef*, UInt32); -typedef ComponentResult (*PtrGraphicsExportSetInputCGImage)(GraphicsExportComponent, CGImageRef); -typedef ComponentResult (*PtrGraphicsExportSetOutputHandle)(GraphicsExportComponent, Handle); -typedef ComponentResult (*PtrGraphicsExportDoExport)(GraphicsExportComponent, unsigned long *); - -static PtrGraphicsImportSetDataHandle ptrGraphicsImportSetDataHandle = 0; -static PtrGraphicsImportCreateCGImage ptrGraphicsImportCreateCGImage = 0; -static PtrGraphicsExportSetInputCGImage ptrGraphicsExportSetInputCGImage = 0; -static PtrGraphicsExportSetOutputHandle ptrGraphicsExportSetOutputHandle = 0; -static PtrGraphicsExportDoExport ptrGraphicsExportDoExport = 0; - -static bool resolveMimeQuickTimeSymbols() -{ - if (ptrGraphicsImportSetDataHandle == 0) { - QLibrary library(QLatin1String("/System/Library/Frameworks/QuickTime.framework/QuickTime")); - ptrGraphicsImportSetDataHandle = reinterpret_cast(library.resolve("GraphicsImportSetDataHandle")); - ptrGraphicsImportCreateCGImage = reinterpret_cast(library.resolve("GraphicsImportCreateCGImage")); - ptrGraphicsExportSetInputCGImage = reinterpret_cast(library.resolve("GraphicsExportSetInputCGImage")); - ptrGraphicsExportSetOutputHandle = reinterpret_cast(library.resolve("GraphicsExportSetOutputHandle")); - ptrGraphicsExportDoExport = reinterpret_cast(library.resolve("GraphicsExportDoExport")); - } - - return ptrGraphicsImportSetDataHandle != 0 - && ptrGraphicsImportCreateCGImage != 0 && ptrGraphicsExportSetInputCGImage != 0 - && ptrGraphicsExportSetOutputHandle != 0 && ptrGraphicsExportDoExport != 0; -} - -class QMacPasteboardMimePict : public QMacPasteboardMime { -public: - QMacPasteboardMimePict() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimePict::convertorName() -{ - return QLatin1String("Pict"); -} - -QString QMacPasteboardMimePict::flavorFor(const QString &mime) -{ - if(mime.startsWith(QLatin1String("application/x-qt-image"))) - return QLatin1String("com.apple.pict"); - return QString(); -} - -QString QMacPasteboardMimePict::mimeFor(QString flav) -{ - if(flav == QLatin1String("com.apple.pict")) - return QLatin1String("application/x-qt-image"); - return QString(); -} - -bool QMacPasteboardMimePict::canConvert(const QString &mime, QString flav) -{ - return flav == QLatin1String("com.apple.pict") - && mime == QLatin1String("application/x-qt-image"); -} - - -QVariant QMacPasteboardMimePict::convertToMime(const QString &mime, QList data, QString flav) -{ - if(data.count() > 1) - qWarning("QMacPasteboardMimePict: Cannot handle multiple member data"); - QVariant ret; - if (!resolveMimeQuickTimeSymbols()) - return ret; - - if(!canConvert(mime, flav)) - return ret; - const QByteArray &a = data.first(); - - // This function expects the 512 header (just to skip it, so create the extra space for it). - Handle pic = NewHandle(a.size() + 512); - memcpy(*pic + 512, a.constData(), a.size()); - - GraphicsImportComponent graphicsImporter; - ComponentResult result = OpenADefaultComponent(GraphicsImporterComponentType, - kQTFileTypePicture, &graphicsImporter); - QCFType cgImage; - if (!result) - result = ptrGraphicsImportSetDataHandle(graphicsImporter, pic); - if (!result) - result = ptrGraphicsImportCreateCGImage(graphicsImporter, &cgImage, - kGraphicsImportCreateCGImageUsingCurrentSettings); - if (!result) - ret = QVariant(QPixmap::fromMacCGImageRef(cgImage).toImage()); - CloseComponent(graphicsImporter); - DisposeHandle(pic); - return ret; -} - -QList QMacPasteboardMimePict::convertFromMime(const QString &mime, QVariant variant, - QString flav) -{ - QList ret; - if (!resolveMimeQuickTimeSymbols()) - return ret; - - if (!canConvert(mime, flav)) - return ret; - QCFType cgimage = qt_mac_createCGImageFromQImage(qvariant_cast(variant)); - Handle pic = NewHandle(0); - GraphicsExportComponent graphicsExporter; - ComponentResult result = OpenADefaultComponent(GraphicsExporterComponentType, - kQTFileTypePicture, &graphicsExporter); - if (!result) { - unsigned long sizeWritten; - result = ptrGraphicsExportSetInputCGImage(graphicsExporter, cgimage); - if (!result) - result = ptrGraphicsExportSetOutputHandle(graphicsExporter, pic); - if (!result) - result = ptrGraphicsExportDoExport(graphicsExporter, &sizeWritten); - - CloseComponent(graphicsExporter); - } - - int size = GetHandleSize((Handle)pic); - // Skip the Picture File header (512 bytes) and feed the raw data - QByteArray ar(reinterpret_cast(*pic + 512), size - 512); - ret.append(ar); - DisposeHandle(pic); - return ret; -} - - -#endif //Q_WS_MAC32 - -class QMacPasteboardMimeTiff : public QMacPasteboardMime { -public: - QMacPasteboardMimeTiff() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeTiff::convertorName() -{ - return QLatin1String("Tiff"); -} - -QString QMacPasteboardMimeTiff::flavorFor(const QString &mime) -{ - if(mime.startsWith(QLatin1String("application/x-qt-image"))) - return QLatin1String("public.tiff"); - return QString(); -} - -QString QMacPasteboardMimeTiff::mimeFor(QString flav) -{ - if(flav == QLatin1String("public.tiff")) - return QLatin1String("application/x-qt-image"); - return QString(); -} - -bool QMacPasteboardMimeTiff::canConvert(const QString &mime, QString flav) -{ - return flav == QLatin1String("public.tiff") && mime == QLatin1String("application/x-qt-image"); -} - -QVariant QMacPasteboardMimeTiff::convertToMime(const QString &mime, QList data, QString flav) -{ - if(data.count() > 1) - qWarning("QMacPasteboardMimeTiff: Cannot handle multiple member data"); - QVariant ret; - if (!canConvert(mime, flav)) - return ret; - const QByteArray &a = data.first(); - QCFType image; - QCFType tiffData = CFDataCreateWithBytesNoCopy(0, - reinterpret_cast(a.constData()), - a.size(), kCFAllocatorNull); - QCFType imageSource = CGImageSourceCreateWithData(tiffData, 0); - image = CGImageSourceCreateImageAtIndex(imageSource, 0, 0); - - if (image != 0) - ret = QVariant(QPixmap::fromMacCGImageRef(image).toImage()); - return ret; -} - -QList QMacPasteboardMimeTiff::convertFromMime(const QString &mime, QVariant variant, QString flav) -{ - QList ret; - if (!canConvert(mime, flav)) - return ret; - - QImage img = qvariant_cast(variant); - QCFType cgimage = qt_mac_createCGImageFromQImage(img); -#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_4) - if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_4) { - QCFType data = CFDataCreateMutable(0, 0); - QCFType imageDestination = CGImageDestinationCreateWithData(data, kUTTypeTIFF, 1, 0); - if (imageDestination != 0) { - CFTypeRef keys[2]; - QCFType values[2]; - QCFType options; - keys[0] = kCGImagePropertyPixelWidth; - keys[1] = kCGImagePropertyPixelHeight; - int width = img.width(); - int height = img.height(); - values[0] = CFNumberCreate(0, kCFNumberIntType, &width); - values[1] = CFNumberCreate(0, kCFNumberIntType, &height); - options = CFDictionaryCreate(0, reinterpret_cast(keys), - reinterpret_cast(values), 2, - &kCFTypeDictionaryKeyCallBacks, - &kCFTypeDictionaryValueCallBacks); - CGImageDestinationAddImage(imageDestination, cgimage, options); - CGImageDestinationFinalize(imageDestination); - } - QByteArray ar(CFDataGetLength(data), 0); - CFDataGetBytes(data, - CFRangeMake(0, ar.size()), - reinterpret_cast(ar.data())); - ret.append(ar); - } else -#endif - { -#ifdef Q_WS_MAC32 - Handle tiff = NewHandle(0); - if (resolveMimeQuickTimeSymbols()) { - GraphicsExportComponent graphicsExporter; - ComponentResult result = OpenADefaultComponent(GraphicsExporterComponentType, - kQTFileTypeTIFF, &graphicsExporter); - if (!result) { - unsigned long sizeWritten; - result = ptrGraphicsExportSetInputCGImage(graphicsExporter, cgimage); - if (!result) - result = ptrGraphicsExportSetOutputHandle(graphicsExporter, tiff); - if (!result) - result = ptrGraphicsExportDoExport(graphicsExporter, &sizeWritten); - - CloseComponent(graphicsExporter); - } - } - int size = GetHandleSize((Handle)tiff); - QByteArray ar(reinterpret_cast(*tiff), size); - ret.append(ar); - DisposeHandle(tiff); -#endif - } - return ret; -} - - -class QMacPasteboardMimeFileUri : public QMacPasteboardMime { -public: - QMacPasteboardMimeFileUri() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeFileUri::convertorName() -{ - return QLatin1String("FileURL"); -} - -QString QMacPasteboardMimeFileUri::flavorFor(const QString &mime) -{ - if (mime == QLatin1String("text/uri-list")) - return QCFString(UTTypeCreatePreferredIdentifierForTag(kUTTagClassOSType, CFSTR("furl"), 0)); - return QString(); -} - -QString QMacPasteboardMimeFileUri::mimeFor(QString flav) -{ - if (flav == QCFString(UTTypeCreatePreferredIdentifierForTag(kUTTagClassOSType, CFSTR("furl"), 0))) - return QLatin1String("text/uri-list"); - return QString(); -} - -bool QMacPasteboardMimeFileUri::canConvert(const QString &mime, QString flav) -{ - return mime == QLatin1String("text/uri-list") - && flav == QCFString(UTTypeCreatePreferredIdentifierForTag(kUTTagClassOSType, CFSTR("furl"), 0)); -} - -QVariant QMacPasteboardMimeFileUri::convertToMime(const QString &mime, QList data, QString flav) -{ - if(!canConvert(mime, flav)) - return QVariant(); - QList ret; - for(int i = 0; i < data.size(); ++i) { - QUrl url = QUrl::fromEncoded(data.at(i)); - if (url.host().toLower() == QLatin1String("localhost")) - url.setHost(QString()); - url.setPath(url.path().normalized(QString::NormalizationForm_C)); - ret.append(url); - } - return QVariant(ret); -} - -QList QMacPasteboardMimeFileUri::convertFromMime(const QString &mime, QVariant data, QString flav) -{ - QList ret; - if (!canConvert(mime, flav)) - return ret; - QList urls = data.toList(); - for(int i = 0; i < urls.size(); ++i) { - QUrl url = urls.at(i).toUrl(); - if (url.scheme().isEmpty()) - url.setScheme(QLatin1String("file")); - if (url.scheme().toLower() == QLatin1String("file")) { - if (url.host().isEmpty()) - url.setHost(QLatin1String("localhost")); - url.setPath(url.path().normalized(QString::NormalizationForm_D)); - } - ret.append(url.toEncoded()); - } - return ret; -} - -class QMacPasteboardMimeUrl : public QMacPasteboardMime { -public: - QMacPasteboardMimeUrl() : QMacPasteboardMime(MIME_ALL) { } - QString convertorName(); - - QString flavorFor(const QString &mime); - QString mimeFor(QString flav); - bool canConvert(const QString &mime, QString flav); - QVariant convertToMime(const QString &mime, QList data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeUrl::convertorName() -{ - return QLatin1String("URL"); -} - -QString QMacPasteboardMimeUrl::flavorFor(const QString &mime) -{ - if(mime.startsWith(QLatin1String("text/uri-list"))) - return QLatin1String("public.url"); - return QString(); -} - -QString QMacPasteboardMimeUrl::mimeFor(QString flav) -{ - if(flav == QLatin1String("public.url")) - return QLatin1String("text/uri-list"); - return QString(); -} - -bool QMacPasteboardMimeUrl::canConvert(const QString &mime, QString flav) -{ - return flav == QLatin1String("public.url") - && mime == QLatin1String("text/uri-list"); -} - -QVariant QMacPasteboardMimeUrl::convertToMime(const QString &mime, QList data, QString flav) -{ - if(!canConvert(mime, flav)) - return QVariant(); - - QList ret; - for (int i=0; i QMacPasteboardMimeUrl::convertFromMime(const QString &mime, QVariant data, QString flav) -{ - QList ret; - if (!canConvert(mime, flav)) - return ret; - - QList urls = data.toList(); - for(int i=0; i data, QString flav); - QList convertFromMime(const QString &mime, QVariant data, QString flav); -}; - -QString QMacPasteboardMimeVCard::convertorName() -{ - return QString("VCard"); -} - -bool QMacPasteboardMimeVCard::canConvert(const QString &mime, QString flav) -{ - return mimeFor(flav) == mime; -} - -QString QMacPasteboardMimeVCard::flavorFor(const QString &mime) -{ - if(mime.startsWith(QLatin1String("text/plain"))) - return QLatin1String("public.vcard"); - return QString(); -} - -QString QMacPasteboardMimeVCard::mimeFor(QString flav) -{ - if (flav == QLatin1String("public.vcard")) - return QLatin1String("text/plain"); - return QString(); -} - -QVariant QMacPasteboardMimeVCard::convertToMime(const QString &mime, QList data, QString) -{ - QByteArray cards; - if (mime == QLatin1String("text/plain")) { - for (int i=0; i QMacPasteboardMimeVCard::convertFromMime(const QString &mime, QVariant data, QString) -{ - QList ret; - if (mime == QLatin1String("text/plain")) - ret.append(data.toString().toUtf8()); - return ret; -} - - -/*! - \internal - - This is an internal function. -*/ -void QMacPasteboardMime::initialize() -{ - if(globalMimeList()->isEmpty()) { - qAddPostRoutine(cleanup_mimes); - - //standard types that we wrap - new QMacPasteboardMimeTiff; -#ifdef Q_WS_MAC32 - // 10.6 does automatic synthesis to and from PICT to standard image types (like TIFF), - // so don't bother doing it ourselves, especially since it's not available in 64-bit. - if (QSysInfo::MacintoshVersion < QSysInfo::MV_10_6) - new QMacPasteboardMimePict; -#endif - new QMacPasteboardMimeUnicodeText; - new QMacPasteboardMimePlainText; - new QMacPasteboardMimeHTMLText; - new QMacPasteboardMimeFileUri; - new QMacPasteboardMimeUrl; - new QMacPasteboardMimeTypeName; - new QMacPasteboardMimeVCard; - //make sure our "non-standard" types are always last! --Sam - new QMacPasteboardMimeAny; - } -} - -/*! - Returns the most-recently created QMacPasteboardMime of type \a t that can convert - between the \a mime and \a flav formats. Returns 0 if no such convertor - exists. -*/ -QMacPasteboardMime* -QMacPasteboardMime::convertor(uchar t, const QString &mime, QString flav) -{ - MimeList *mimes = globalMimeList(); - for(MimeList::const_iterator it = mimes->constBegin(); it != mimes->constEnd(); ++it) { -#ifdef DEBUG_MIME_MAPS - qDebug("QMacPasteboardMime::convertor: seeing if %s (%d) can convert %s to %d[%c%c%c%c] [%d]", - (*it)->convertorName().toLatin1().constData(), - (*it)->type & t, mime.toLatin1().constData(), - flav, (flav >> 24) & 0xFF, (flav >> 16) & 0xFF, (flav >> 8) & 0xFF, (flav) & 0xFF, - (*it)->canConvert(mime,flav)); - for(int i = 0; i < (*it)->countFlavors(); ++i) { - int f = (*it)->flavor(i); - qDebug(" %d) %d[%c%c%c%c] [%s]", i, f, - (f >> 24) & 0xFF, (f >> 16) & 0xFF, (f >> 8) & 0xFF, (f) & 0xFF, - (*it)->convertorName().toLatin1().constData()); - } -#endif - if(((*it)->type & t) && (*it)->canConvert(mime, flav)) - return (*it); - } - return 0; -} -/*! - Returns a MIME type of type \a t for \a flav, or 0 if none exists. -*/ -QString QMacPasteboardMime::flavorToMime(uchar t, QString flav) -{ - MimeList *mimes = globalMimeList(); - for(MimeList::const_iterator it = mimes->constBegin(); it != mimes->constEnd(); ++it) { -#ifdef DEBUG_MIME_MAPS - qDebug("QMacMIme::flavorToMime: attempting %s (%d) for flavor %d[%c%c%c%c] [%s]", - (*it)->convertorName().toLatin1().constData(), - (*it)->type & t, flav, (flav >> 24) & 0xFF, (flav >> 16) & 0xFF, (flav >> 8) & 0xFF, (flav) & 0xFF, - (*it)->mimeFor(flav).toLatin1().constData()); - -#endif - if((*it)->type & t) { - QString mimeType = (*it)->mimeFor(flav); - if(!mimeType.isNull()) - return mimeType; - } - } - return QString(); -} - -/*! - Returns a list of all currently defined QMacPasteboardMime objects of type \a t. -*/ -QList QMacPasteboardMime::all(uchar t) -{ - MimeList ret; - MimeList *mimes = globalMimeList(); - for(MimeList::const_iterator it = mimes->constBegin(); it != mimes->constEnd(); ++it) { - if((*it)->type & t) - ret.append((*it)); - } - return ret; -} - - -/*! - \fn QString QMacPasteboardMime::convertorName() - - Returns a name for the convertor. - - All subclasses must reimplement this pure virtual function. -*/ - -/*! - \fn bool QMacPasteboardMime::canConvert(const QString &mime, QString flav) - - Returns true if the convertor can convert (both ways) between - \a mime and \a flav; otherwise returns false. - - All subclasses must reimplement this pure virtual function. -*/ - -/*! - \fn QString QMacPasteboardMime::mimeFor(QString flav) - - Returns the MIME UTI used for Mac flavor \a flav, or 0 if this - convertor does not support \a flav. - - All subclasses must reimplement this pure virtual function. -*/ - -/*! - \fn QString QMacPasteboardMime::flavorFor(const QString &mime) - - Returns the Mac UTI used for MIME type \a mime, or 0 if this - convertor does not support \a mime. - - All subclasses must reimplement this pure virtual function. -*/ - -/*! - \fn QVariant QMacPasteboardMime::convertToMime(const QString &mime, QList data, QString flav) - - Returns \a data converted from Mac UTI \a flav to MIME type \a - mime. - - Note that Mac flavors must all be self-terminating. The input \a - data may contain trailing data. - - All subclasses must reimplement this pure virtual function. -*/ - -/*! - \fn QList QMacPasteboardMime::convertFromMime(const QString &mime, QVariant data, QString flav) - - Returns \a data converted from MIME type \a mime - to Mac UTI \a flav. - - Note that Mac flavors must all be self-terminating. The return - value may contain trailing data. - - All subclasses must reimplement this pure virtual function. -*/ - - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qnsframeview_mac_p.h b/src/widgets/platforms/mac/qnsframeview_mac_p.h deleted file mode 100644 index 1534ad1..0000000 --- a/src/widgets/platforms/mac/qnsframeview_mac_p.h +++ /dev/null @@ -1,154 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of qapplication_*.cpp, qwidget*.cpp, qcolor_x11.cpp, qfiledialog.cpp -// and many other. This header file may change from version to version -// without notice, or even be removed. -// -// We mean it. -// - -// Private AppKit class (dumped from classdump). - -#import - -@interface NSFrameView : NSView -{ - unsigned int styleMask; - NSString *_title; - NSCell *titleCell; - NSButton *closeButton; - NSButton *zoomButton; - NSButton *minimizeButton; - char resizeByIncrement; - char frameNeedsDisplay; - unsigned char tabViewCount; - NSSize resizeParameter; - int shadowState; -} - -+ (void)initialize; -+ (void)initTitleCell:fp8 styleMask:(unsigned int)fp12; -+ (struct _NSRect)frameRectForContentRect:(struct _NSRect)fp8 styleMask:(unsigned int)fp24; -+ (struct _NSRect)contentRectForFrameRect:(struct _NSRect)fp8 styleMask:(unsigned int)fp24; -+ (struct _NSSize)minFrameSizeForMinContentSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -+ (struct _NSSize)minContentSizeForMinFrameSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -+ (float)minFrameWidthWithTitle:fp8 styleMask:(unsigned int)fp12; -+ (unsigned int)_validateStyleMask:(unsigned int)fp8; -- initWithFrame:(struct _NSRect)fp8 styleMask:(unsigned int)fp24 owner:fp28; -- initWithFrame:(struct _NSRect)fp8; -- (void)dealloc; -- (void)shapeWindow; -- (void)tileAndSetWindowShape:(char)fp8; -- (void)tile; -- (void)drawRect:(struct _NSRect)fp8; -- (void)_drawFrameRects:(struct _NSRect)fp8; -- (void)drawFrame:(struct _NSRect)fp8; -- (void)drawThemeContentFill:(struct _NSRect)fp8 inView:fp24; -- (void)drawWindowBackgroundRect:(struct _NSRect)fp8; -- (void)drawWindowBackgroundRegion:(void *)fp8; -- (float)contentAlpha; -- (void)_windowChangedKeyState; -- (void)_updateButtonState; -- (char)_isSheet; -- (char)_isUtility; -- (void)setShadowState:(int)fp8; -- (int)shadowState; -- (char)_canHaveToolbar; -- (char)_toolbarIsInTransition; -- (char)_toolbarIsShown; -- (char)_toolbarIsHidden; -- (void)_showToolbarWithAnimation:(char)fp8; -- (void)_hideToolbarWithAnimation:(char)fp8; -- (float)_distanceFromToolbarBaseToTitlebar; -- (int)_shadowType; -- (unsigned int)_shadowFlags; -- (void)_setShadowParameters; -- (void)_drawFrameShadowAndFlushContext:fp8; -- (void)setUpGState; -- (void)adjustHalftonePhase; -- (void)systemColorsDidChange:fp8; -- frameColor; -- contentFill; -- (void)tabViewAdded; -- (void)tabViewRemoved; -- title; -- (void)setTitle:fp8; -- titleCell; -- (void)initTitleCell:fp8; -- (void)setResizeIncrements:(struct _NSSize)fp8; -- (struct _NSSize)resizeIncrements; -- (void)setAspectRatio:(struct _NSSize)fp8; -- (struct _NSSize)aspectRatio; -- (unsigned int)styleMask; -- representedFilename; -- (void)setRepresentedFilename:fp8; -- (void)setDocumentEdited:(char)fp8; -- (void)_setFrameNeedsDisplay:(char)fp8; -- (char)frameNeedsDisplay; -- titleFont; -- (struct _NSRect)_maxTitlebarTitleRect; -- (struct _NSRect)titlebarRect; -- (void)_setUtilityWindow:(char)fp8; -- (void)_setNonactivatingPanel:(char)fp8; -- (void)setIsClosable:(char)fp8; -- (void)setIsResizable:(char)fp8; -- closeButton; -- minimizeButton; -- zoomButton; -- (struct _NSSize)miniaturizedSize; -- (void)_clearDragMargins; -- (void)_resetDragMargins; -- (void)setTitle:fp8 andDefeatWrap:(char)fp12; -- (struct _NSRect)frameRectForContentRect:(struct _NSRect)fp8 styleMask:(unsigned int)fp24; -- (struct _NSRect)contentRectForFrameRect:(struct _NSRect)fp8 styleMask:(unsigned int)fp24; -- (struct _NSSize)minFrameSizeForMinContentSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -- (struct _NSRect)dragRectForFrameRect:(struct _NSRect)fp8; -- (struct _NSRect)contentRect; -- (struct _NSSize)minFrameSize; -- (void)_recursiveDisplayRectIfNeededIgnoringOpacity:(struct _NSRect)fp8 isVisibleRect:(char)fp24 rectIsVisibleRectForView:fp28 topView:(char)fp32; - -@end diff --git a/src/widgets/platforms/mac/qnsthemeframe_mac_p.h b/src/widgets/platforms/mac/qnsthemeframe_mac_p.h deleted file mode 100644 index 1768ad8..0000000 --- a/src/widgets/platforms/mac/qnsthemeframe_mac_p.h +++ /dev/null @@ -1,246 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of qapplication_*.cpp, qwidget*.cpp, qcolor_x11.cpp, qfiledialog.cpp -// and many other. This header file may change from version to version -// without notice, or even be removed. -// -// We mean it. -// - -// Private AppKit class (dumped from classdump). - -#import -#import "qnstitledframe_mac_p.h" - -@interface NSThemeFrame : NSTitledFrame -{ - NSButton *toolbarButton; - int toolbarVisibleStatus; - NSImage *showToolbarTransitionImage; - NSSize showToolbarPreWindowSize; - NSButton *modeButton; - int leftGroupTrackingTagNum; - int rightGroupTrackingTagNum; - char mouseInsideLeftGroup; - char mouseInsideRightGroup; - int widgetState; - NSString *displayName; -} - -+ (void)initialize; -+ (float)_windowBorderThickness:(unsigned int)fp8; -+ (float)_minXWindowBorderWidth:(unsigned int)fp8; -+ (float)_maxXWindowBorderWidth:(unsigned int)fp8; -+ (float)_minYWindowBorderHeight:(unsigned int)fp8; -+ (float)_windowTitlebarButtonSpacingWidth:(unsigned int)fp8; -+ (float)_windowFileButtonSpacingWidth:(unsigned int)fp8; -+ (float)_minXTitlebarWidgetInset:(unsigned int)fp8; -+ (float)_maxXTitlebarWidgetInset:(unsigned int)fp8; -+ (float)minFrameWidthWithTitle:fp8 styleMask:(unsigned int)fp12; -+ (float)_windowSideTitlebarTitleMinWidth:(unsigned int)fp8; -+ (float)_windowTitlebarTitleMinHeight:(unsigned int)fp8; -+ (float)_sideTitlebarWidth:(unsigned int)fp8; -+ (float)_titlebarHeight:(unsigned int)fp8; -+ (float)_resizeHeight:(unsigned int)fp8; -+ (char)_resizeFromEdge; -+ (struct _NSSize)sizeOfTitlebarButtons:(unsigned int)fp8; -+ (float)_contentToFrameMinXWidth:(unsigned int)fp8; -+ (float)_contentToFrameMaxXWidth:(unsigned int)fp8; -+ (float)_contentToFrameMinYHeight:(unsigned int)fp8; -+ (float)_contentToFrameMaxYHeight:(unsigned int)fp8; -+ (unsigned int)_validateStyleMask:(unsigned int)fp8; -- (struct _NSSize)_topCornerSize; -- (struct _NSSize)_bottomCornerSize; -- (void *)_createWindowOpaqueShape; -- (void)shapeWindow; -- (void)_recursiveDisplayRectIfNeededIgnoringOpacity:(NSRect)fp8 isVisibleRect:(char)fp24 rectIsVisibleRectForView:fp28 topView:(char)fp32; -- (void *)_regionForOpaqueDescendants:(NSRect)fp8 forMove:(char)fp24; -- (void)_drawFrameInterior:(NSRect *)fp8 clip:(NSRect)fp12; -- (void)_setTextShadow:(char)fp8; -- (void)_drawTitleBar:(NSRect)fp8; -- (void)_drawResizeIndicators:(NSRect)fp8; -- (void)_drawFrameRects:(NSRect)fp8; -- (void)drawFrame:(NSRect)fp8; -- contentFill; -- (void)viewDidEndLiveResize; -- (float)contentAlpha; -- (void)setThemeFrameWidgetState:(int)fp8; -- (char)constrainResizeEdge:(int *)fp8 withDelta:(struct _NSSize)fp12 elapsedTime:(float)fp20; -- (void)addFileButton:fp8; -- (void)_updateButtons; -- (void)_updateButtonState; -- newCloseButton; -- newZoomButton; -- newMiniaturizeButton; -- newToolbarButton; -- newFileButton; -- (void)_resetTitleBarButtons; -- (void)setDocumentEdited:(char)fp8; -- toolbarButton; -- modeButton; -- initWithFrame:(NSRect)fp8 styleMask:(unsigned int)fp24 owner:fp28; -- (void)dealloc; -- (void)setFrameSize:(struct _NSSize)fp8; -- (char)_canHaveToolbar; -- (char)_toolbarIsInTransition; -- (char)_toolbarIsShown; -- (char)_toolbarIsHidden; -- _toolbarView; -- _toolbar; -- (float)_distanceFromToolbarBaseToTitlebar; -- (unsigned int)_shadowFlags; -- (NSRect)frameRectForContentRect:(NSRect)fp8 styleMask:(unsigned int)fp24; -- (NSRect)contentRectForFrameRect:(NSRect)fp8 styleMask:(unsigned int)fp24; -- (struct _NSSize)minFrameSizeForMinContentSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -- (NSRect)contentRect; -- (NSRect)_contentRectExcludingToolbar; -- (NSRect)_contentRectIncludingToolbarAtHome; -- (void)_setToolbarShowHideResizeWeightingOptimizationOn:(char)fp8; -- (char)_usingToolbarShowHideWeightingOptimization; -- (void)handleSetFrameCommonRedisplay; -- (void)_startLiveResizeAsTopLevel; -- (void)_endLiveResizeAsTopLevel; -- (void)_growContentReshapeContentAndToolbarView:(int)fp8 animate:(char)fp12; -- (char)_growWindowReshapeContentAndToolbarView:(int)fp8 animate:(char)fp12; -- (void)_reshapeContentAndToolbarView:(int)fp8 resizeWindow:(char)fp12 animate:(char)fp16; -- (void)_toolbarFrameSizeChanged:fp8 oldSize:(struct _NSSize)fp12; -- (void)_syncToolbarPosition; -- (void)_showHideToolbar:(int)fp8 resizeWindow:(char)fp12 animate:(char)fp16; -- (void)_showToolbarWithAnimation:(char)fp8; -- (void)_hideToolbarWithAnimation:(char)fp8; -- (void)_drawToolbarTransitionIfNecessary; -- (void)drawRect:(NSRect)fp8; -- (void)resetCursorRects; -- (char)shouldBeTreatedAsInkEvent:fp8; -- (char)_shouldBeTreatedAsInkEventInInactiveWindow:fp8; -//- hitTest:(struct _NSPoint)fp8; // collides with hittest in qcocoasharedwindowmethods_mac_p.h -- (NSRect)_leftGroupRect; -- (NSRect)_rightGroupRect; -- (void)_updateWidgets; -- (void)_updateMouseTracking; -- (void)mouseEntered:fp8; -- (void)mouseExited:fp8; -- (void)_setMouseEnteredGroup:(char)fp8 entered:(char)fp12; -- (char)_mouseInGroup:fp8; -- (struct _NSSize)miniaturizedSize; -- (float)_minXTitlebarDecorationMinWidth; -- (float)_maxXTitlebarDecorationMinWidth; -- (struct _NSSize)minFrameSize; -- (float)_windowBorderThickness; -- (float)_windowTitlebarXResizeBorderThickness; -- (float)_windowTitlebarYResizeBorderThickness; -- (float)_windowResizeBorderThickness; -- (float)_minXWindowBorderWidth; -- (float)_maxXWindowBorderWidth; -- (float)_minYWindowBorderHeight; -- (float)_maxYWindowBorderHeight; -- (float)_minYTitlebarButtonsOffset; -- (float)_minYTitlebarTitleOffset; -- (float)_sideTitlebarWidth; -- (float)_titlebarHeight; -- (NSRect)_titlebarTitleRect; -- (NSRect)titlebarRect; -- (float)_windowTitlebarTitleMinHeight; -- (struct _NSSize)_sizeOfTitlebarFileButton; -- (struct _NSSize)sizeOfTitlebarToolbarButton; -- (float)_windowTitlebarButtonSpacingWidth; -- (float)_windowFileButtonSpacingWidth; -- (float)_minXTitlebarWidgetInset; -- (float)_maxXTitlebarWidgetInset; -- (float)_minXTitlebarButtonsWidth; -- (float)_maxXTitlebarButtonsWidth; -- (struct _NSPoint)_closeButtonOrigin; -- (struct _NSPoint)_zoomButtonOrigin; -- (struct _NSPoint)_collapseButtonOrigin; -- (struct _NSPoint)_toolbarButtonOrigin; -- (struct _NSPoint)_fileButtonOrigin; -- (void)_tileTitlebar; -- (NSRect)_commandPopupRect; -- (void)_resetDragMargins; -- (float)_maxYTitlebarDragHeight; -- (float)_minXTitlebarDragWidth; -- (float)_maxXTitlebarDragWidth; -- (float)_contentToFrameMinXWidth; -- (float)_contentToFrameMaxXWidth; -- (float)_contentToFrameMinYHeight; -- (float)_contentToFrameMaxYHeight; -- (float)_windowResizeCornerThickness; -- (NSRect)_minYResizeRect; -- (NSRect)_minYminXResizeRect; -- (NSRect)_minYmaxXResizeRect; -- (NSRect)_minXResizeRect; -- (NSRect)_minXminYResizeRect; -- (NSRect)_minXmaxYResizeRect; -- (NSRect)_maxYResizeRect; -- (NSRect)_maxYminXResizeRect; -- (NSRect)_maxYmaxXResizeRect; -- (NSRect)_maxXResizeRect; -- (NSRect)_maxXminYResizeRect; -- (NSRect)_maxXmaxYResizeRect; -- (NSRect)_minXTitlebarResizeRect; -- (NSRect)_maxXTitlebarResizeRect; -- (NSRect)_minXBorderRect; -- (NSRect)_maxXBorderRect; -- (NSRect)_maxYBorderRect; -- (NSRect)_minYBorderRect; -- (void)_setUtilityWindow:(char)fp8; -- (char)_isUtility; -- (float)_sheetHeightAdjustment; -- (void)_setSheet:(char)fp8; -- (char)_isSheet; -- (char)_isResizable; -- (char)_isClosable; -- (char)_isMiniaturizable; -- (char)_hasToolbar; -- (NSRect)_growBoxRect; -- (void)_drawGrowBoxWithClip:(NSRect)fp8; -- (char)_inactiveButtonsNeedMask; -- (void)mouseDown:fp8; -- _displayName; -- (void)_setDisplayName:fp8; - -@end diff --git a/src/widgets/platforms/mac/qnstitledframe_mac_p.h b/src/widgets/platforms/mac/qnstitledframe_mac_p.h deleted file mode 100644 index 531b943..0000000 --- a/src/widgets/platforms/mac/qnstitledframe_mac_p.h +++ /dev/null @@ -1,205 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of qapplication_*.cpp, qwidget*.cpp, qcolor_x11.cpp, qfiledialog.cpp -// and many other. This header file may change from version to version -// without notice, or even be removed. -// -// We mean it. -// - -// Private AppKit class (dumped from classdump). - -#import -#import "qnsframeview_mac_p.h" - - -@interface NSTitledFrame : NSFrameView -{ - int resizeFlags; - id fileButton; /* NSDocumentDragButton* */ - NSSize titleCellSize; -} - -+ (float)_windowBorderThickness:(unsigned int)fp8; -+ (float)_minXWindowBorderWidth:(unsigned int)fp8; -+ (float)_maxXWindowBorderWidth:(unsigned int)fp8; -+ (float)_minYWindowBorderHeight:(unsigned int)fp8; -+ (char)_resizeFromEdge; -+ (NSRect)frameRectForContentRect:(NSRect)fp8 styleMask:(unsigned int)fp24; -+ (NSRect)contentRectForFrameRect:(NSRect)fp8 styleMask:(unsigned int)fp24; -+ (struct _NSSize)minFrameSizeForMinContentSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -+ (struct _NSSize)minContentSizeForMinFrameSize:(struct _NSSize)fp8 styleMask:(unsigned int)fp16; -+ (float)minFrameWidthWithTitle:fp8 styleMask:(unsigned int)fp12; -+ (struct _NSSize)_titleCellSizeForTitle:fp8 styleMask:(unsigned int)fp12; -+ (float)_titleCellHeight:(unsigned int)fp8; -+ (float)_windowTitlebarTitleMinHeight:(unsigned int)fp8; -+ (float)_titlebarHeight:(unsigned int)fp8; -+ (struct _NSSize)sizeOfTitlebarButtons:(unsigned int)fp8; -+ (float)windowTitlebarLinesSpacingWidth:(unsigned int)fp8; -+ (float)windowTitlebarTitleLinesSpacingWidth:(unsigned int)fp8; -+ (float)_contentToFrameMinXWidth:(unsigned int)fp8; -+ (float)_contentToFrameMaxXWidth:(unsigned int)fp8; -+ (float)_contentToFrameMinYHeight:(unsigned int)fp8; -+ (float)_contentToFrameMaxYHeight:(unsigned int)fp8; -- initWithFrame:(NSRect)fp8 styleMask:(unsigned int)fp24 owner:fp28; -- (void)dealloc; -- (void)setIsClosable:(char)fp8; -- (void)setIsResizable:(char)fp8; -- (void)_resetTitleFont; -- (void)_setUtilityWindow:(char)fp8; -- (char)isOpaque; -- (char)worksWhenModal; -- (void)propagateFrameDirtyRects:(NSRect)fp8; -- (void)_showDrawRect:(NSRect)fp8; -- (void)_drawFrameInterior:(NSRect *)fp8 clip:(NSRect)fp12; -- (void)drawFrame:(NSRect)fp8; -- (void)_drawFrameRects:(NSRect)fp8; -- (void)_drawTitlebar:(NSRect)fp8; -- (void)_drawTitlebarPattern:(int)fp8 inRect:(NSRect)fp12 clippedByRect:(NSRect)fp28 forKey:(char)fp44 alignment:(int)fp48; -- (void)_drawTitlebarLines:(int)fp8 inRect:(NSRect)fp12 clippedByRect:(NSRect)fp28; -- frameHighlightColor; -- frameShadowColor; -- (void)setFrameSize:(struct _NSSize)fp8; -- (void)setFrameOrigin:(struct _NSPoint)fp8; -- (void)tileAndSetWindowShape:(char)fp8; -- (void)tile; -- (void)_tileTitlebar; -- (void)setTitle:fp8; -- (char)_shouldRepresentFilename; -- (void)setRepresentedFilename:fp8; -- (void)_drawTitleStringIn:(NSRect)fp8 withColor:fp24; -- titleFont; -- (void)_drawResizeIndicators:(NSRect)fp8; -- titleButtonOfClass:(Class)fp8; -- initTitleButton:fp8; -- newCloseButton; -- newZoomButton; -- newMiniaturizeButton; -- newFileButton; -- fileButton; -- (void)_removeButtons; -- (void)_updateButtons; -- (char)_eventInTitlebar:fp8; -- (char)acceptsFirstMouse:fp8; -- (void)mouseDown:fp8; -- (void)mouseUp:fp8; -- (void)rightMouseDown:fp8; -- (void)rightMouseUp:fp8; -- (int)resizeEdgeForEvent:fp8; -- (struct _NSSize)_resizeDeltaFromPoint:(struct _NSPoint)fp8 toEvent:fp16; -- (NSRect)_validFrameForResizeFrame:(NSRect)fp8 fromResizeEdge:(int)fp24; -- (NSRect)frame:(NSRect)fp8 resizedFromEdge:(int)fp24 withDelta:(struct _NSSize)fp28; -- (char)constrainResizeEdge:(int *)fp8 withDelta:(struct _NSSize)fp12 elapsedTime:(float)fp20; -- (void)resizeWithEvent:fp8; -- (int)resizeFlags; -- (void)resetCursorRects; -- (void)setDocumentEdited:(char)fp8; -- (struct _NSSize)miniaturizedSize; -- (struct _NSSize)minFrameSize; -- (float)_windowBorderThickness; -- (float)_windowTitlebarXResizeBorderThickness; -- (float)_windowTitlebarYResizeBorderThickness; -- (float)_windowResizeBorderThickness; -- (float)_minXWindowBorderWidth; -- (float)_maxXWindowBorderWidth; -- (float)_minYWindowBorderHeight; -- (void)_invalidateTitleCellSize; -- (void)_invalidateTitleCellWidth; -- (float)_titleCellHeight; -- (struct _NSSize)_titleCellSize; -- (float)_titlebarHeight; -- (NSRect)titlebarRect; -- (NSRect)_maxTitlebarTitleRect; -- (NSRect)_titlebarTitleRect; -- (float)_windowTitlebarTitleMinHeight; -- (NSRect)dragRectForFrameRect:(NSRect)fp8; -- (struct _NSSize)sizeOfTitlebarButtons; -- (struct _NSSize)_sizeOfTitlebarFileButton; -- (float)_windowTitlebarButtonSpacingWidth; -- (float)_minXTitlebarButtonsWidth; -- (float)_maxXTitlebarButtonsWidth; -- (int)_numberOfTitlebarLines; -- (float)windowTitlebarLinesSpacingWidth; -- (float)windowTitlebarTitleLinesSpacingWidth; -- (float)_minLinesWidthWithSpace; -- (NSRect)_minXTitlebarLinesRectWithTitleCellRect:(NSRect)fp8; -- (NSRect)_maxXTitlebarLinesRectWithTitleCellRect:(NSRect)fp8; -- (float)_minXTitlebarDecorationMinWidth; -- (float)_maxXTitlebarDecorationMinWidth; -- (struct _NSPoint)_closeButtonOrigin; -- (struct _NSPoint)_zoomButtonOrigin; -- (struct _NSPoint)_collapseButtonOrigin; -- (struct _NSPoint)_fileButtonOrigin; -- (float)_maxYTitlebarDragHeight; -- (float)_minXTitlebarDragWidth; -- (float)_maxXTitlebarDragWidth; -- (float)_contentToFrameMinXWidth; -- (float)_contentToFrameMaxXWidth; -- (float)_contentToFrameMinYHeight; -- (float)_contentToFrameMaxYHeight; -- (NSRect)contentRect; -- (float)_windowResizeCornerThickness; -- (NSRect)_minYResizeRect; -- (NSRect)_minYminXResizeRect; -- (NSRect)_minYmaxXResizeRect; -- (NSRect)_minXResizeRect; -- (NSRect)_minXminYResizeRect; -- (NSRect)_minXmaxYResizeRect; -- (NSRect)_maxYResizeRect; -- (NSRect)_maxYminXResizeRect; -- (NSRect)_maxYmaxXResizeRect; -- (NSRect)_maxXResizeRect; -- (NSRect)_maxXminYResizeRect; -- (NSRect)_maxXmaxYResizeRect; -- (NSRect)_minXTitlebarResizeRect; -- (NSRect)_maxXTitlebarResizeRect; -- (NSRect)_minXBorderRect; -- (NSRect)_maxXBorderRect; -- (NSRect)_maxYBorderRect; -- (NSRect)_minYBorderRect; - -@end diff --git a/src/widgets/platforms/mac/qpaintdevice_mac.cpp b/src/widgets/platforms/mac/qpaintdevice_mac.cpp deleted file mode 100644 index 01f4a18..0000000 --- a/src/widgets/platforms/mac/qpaintdevice_mac.cpp +++ /dev/null @@ -1,103 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qpaintdevice.h" -#include "qpainter.h" -#include "qwidget.h" -#include "qbitmap.h" -#include "qapplication.h" -#include "qprinter.h" -#include -#include -#include -#include -#include - -QT_BEGIN_NAMESPACE - -/***************************************************************************** - Internal variables and functions - *****************************************************************************/ - -/*! \internal */ -float qt_mac_defaultDpi_x() -{ - // Mac OS X currently assumes things to be 72 dpi. - // (see http://developer.apple.com/releasenotes/GraphicsImaging/RN-ResolutionIndependentUI/) - // This may need to be re-worked as we go further in the resolution-independence stuff. - return 72; -} - -/*! \internal */ -float qt_mac_defaultDpi_y() -{ - // Mac OS X currently assumes things to be 72 dpi. - // (see http://developer.apple.com/releasenotes/GraphicsImaging/RN-ResolutionIndependentUI/) - // This may need to be re-worked as we go further in the resolution-independence stuff. - return 72; -} - - -/*! \internal - - Returns the QuickDraw CGrafPtr of the paint device. 0 is returned - if it can't be obtained. Do not hold the pointer around for long - as it can be relocated. - - \warning This function is only available on Mac OS X. -*/ - -Q_WIDGETS_EXPORT GrafPtr qt_mac_qd_context(const QPaintDevice *device) -{ - if (device->devType() == QInternal::Pixmap) { - return static_cast(static_cast(device)->macQDHandle()); - } else if(device->devType() == QInternal::Widget) { - return static_cast(static_cast(device)->macQDHandle()); - } else if(device->devType() == QInternal::Printer) { - QPaintEngine *engine = static_cast(device)->paintEngine(); - return static_cast(static_cast(engine)->handle()); - } - return 0; -} - -extern CGColorSpaceRef qt_mac_colorSpaceForDeviceType(const QPaintDevice *pdev); - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qpaintengine_mac.cpp b/src/widgets/platforms/mac/qpaintengine_mac.cpp deleted file mode 100644 index f1e397e..0000000 --- a/src/widgets/platforms/mac/qpaintengine_mac.cpp +++ /dev/null @@ -1,1538 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -QT_BEGIN_NAMESPACE - -extern int qt_antialiasing_threshold; // QApplication.cpp - -/***************************************************************************** - External functions - *****************************************************************************/ -extern CGImageRef qt_mac_create_imagemask(const QPixmap &px, const QRectF &sr); //qpixmap_mac.cpp -extern QPoint qt_mac_posInWindow(const QWidget *w); //qwidget_mac.cpp -extern OSWindowRef qt_mac_window_for(const QWidget *); //qwidget_mac.cpp -extern CGContextRef qt_mac_cg_context(const QPaintDevice *); //qpaintdevice_mac.cpp -extern void qt_mac_dispose_rgn(RgnHandle r); //qregion_mac.cpp -extern QPixmap qt_pixmapForBrush(int, bool); //qbrush.cpp - -void qt_mac_clip_cg(CGContextRef hd, const QRegion &rgn, CGAffineTransform *orig_xform); - - -/***************************************************************************** - QCoreGraphicsPaintEngine utility functions - *****************************************************************************/ - -//conversion -inline static float qt_mac_convert_color_to_cg(int c) { return ((float)c * 1000 / 255) / 1000; } -inline static int qt_mac_convert_color_from_cg(float c) { return qRound(c * 255); } -CGAffineTransform qt_mac_convert_transform_to_cg(const QTransform &t) { - return CGAffineTransformMake(t.m11(), t.m12(), t.m21(), t.m22(), t.dx(), t.dy()); -} - -inline static QCFType cgColorForQColor(const QColor &col, QPaintDevice *pdev) -{ - CGFloat components[] = { - qt_mac_convert_color_to_cg(col.red()), - qt_mac_convert_color_to_cg(col.green()), - qt_mac_convert_color_to_cg(col.blue()), - qt_mac_convert_color_to_cg(col.alpha()) - }; - return CGColorCreate(qt_mac_colorSpaceForDeviceType(pdev), components); -} - -// There's architectural problems with using native gradients -// on the Mac at the moment, so disable them. -// #define QT_MAC_USE_NATIVE_GRADIENTS - -#ifdef QT_MAC_USE_NATIVE_GRADIENTS -static bool drawGradientNatively(const QGradient *gradient) -{ - return gradient->spread() == QGradient::PadSpread; -} - -// gradiant callback -static void qt_mac_color_gradient_function(void *info, const CGFloat *in, CGFloat *out) -{ - QBrush *brush = static_cast(info); - Q_ASSERT(brush && brush->gradient()); - - const QGradientStops stops = brush->gradient()->stops(); - const int n = stops.count(); - Q_ASSERT(n >= 1); - const QGradientStop *begin = stops.constBegin(); - const QGradientStop *end = begin + n; - - qreal p = in[0]; - const QGradientStop *i = begin; - while (i != end && i->first < p) - ++i; - - QRgb c; - if (i == begin) { - c = begin->second.rgba(); - } else if (i == end) { - c = (end - 1)->second.rgba(); - } else { - const QGradientStop &s1 = *(i - 1); - const QGradientStop &s2 = *i; - qreal p1 = s1.first; - qreal p2 = s2.first; - QRgb c1 = s1.second.rgba(); - QRgb c2 = s2.second.rgba(); - int idist = 256 * (p - p1) / (p2 - p1); - int dist = 256 - idist; - c = qRgba(INTERPOLATE_PIXEL_256(qRed(c1), dist, qRed(c2), idist), - INTERPOLATE_PIXEL_256(qGreen(c1), dist, qGreen(c2), idist), - INTERPOLATE_PIXEL_256(qBlue(c1), dist, qBlue(c2), idist), - INTERPOLATE_PIXEL_256(qAlpha(c1), dist, qAlpha(c2), idist)); - } - - out[0] = qt_mac_convert_color_to_cg(qRed(c)); - out[1] = qt_mac_convert_color_to_cg(qGreen(c)); - out[2] = qt_mac_convert_color_to_cg(qBlue(c)); - out[3] = qt_mac_convert_color_to_cg(qAlpha(c)); -} -#endif - -//clipping handling -void QCoreGraphicsPaintEnginePrivate::resetClip() -{ - static bool inReset = false; - if (inReset) - return; - inReset = true; - - CGAffineTransform old_xform = CGContextGetCTM(hd); - - //setup xforms - CGContextConcatCTM(hd, CGAffineTransformInvert(old_xform)); - while (stackCount > 0) { - restoreGraphicsState(); - } - saveGraphicsState(); - inReset = false; - //reset xforms - CGContextConcatCTM(hd, CGAffineTransformInvert(CGContextGetCTM(hd))); - CGContextConcatCTM(hd, old_xform); -} - -static CGRect qt_mac_compose_rect(const QRectF &r, float off=0) -{ - return CGRectMake(r.x()+off, r.y()+off, r.width(), r.height()); -} - -static CGMutablePathRef qt_mac_compose_path(const QPainterPath &p, float off=0) -{ - CGMutablePathRef ret = CGPathCreateMutable(); - QPointF startPt; - for (int i=0; i 0 - && p.elementAt(i - 1).x == startPt.x() - && p.elementAt(i - 1).y == startPt.y()) - CGPathCloseSubpath(ret); - startPt = QPointF(elm.x, elm.y); - CGPathMoveToPoint(ret, 0, elm.x+off, elm.y+off); - break; - case QPainterPath::LineToElement: - CGPathAddLineToPoint(ret, 0, elm.x+off, elm.y+off); - break; - case QPainterPath::CurveToElement: - Q_ASSERT(p.elementAt(i+1).type == QPainterPath::CurveToDataElement); - Q_ASSERT(p.elementAt(i+2).type == QPainterPath::CurveToDataElement); - CGPathAddCurveToPoint(ret, 0, - elm.x+off, elm.y+off, - p.elementAt(i+1).x+off, p.elementAt(i+1).y+off, - p.elementAt(i+2).x+off, p.elementAt(i+2).y+off); - i+=2; - break; - default: - qFatal("QCoreGraphicsPaintEngine::drawPath(), unhandled type: %d", elm.type); - break; - } - } - if(!p.isEmpty() - && p.elementAt(p.elementCount() - 1).x == startPt.x() - && p.elementAt(p.elementCount() - 1).y == startPt.y()) - CGPathCloseSubpath(ret); - return ret; -} - -CGColorSpaceRef QCoreGraphicsPaintEngine::m_genericColorSpace = 0; -QHash QCoreGraphicsPaintEngine::m_displayColorSpaceHash; -bool QCoreGraphicsPaintEngine::m_postRoutineRegistered = false; - -CGColorSpaceRef QCoreGraphicsPaintEngine::macGenericColorSpace() -{ -#if 0 - if (!m_genericColorSpace) { -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_4 - if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_4) { - m_genericColorSpace = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB); - } else -#endif - { - m_genericColorSpace = CGColorSpaceCreateDeviceRGB(); - } - if (!m_postRoutineRegistered) { - m_postRoutineRegistered = true; - qAddPostRoutine(QCoreGraphicsPaintEngine::cleanUpMacColorSpaces); - } - } - return m_genericColorSpace; -#else - // Just return the main display colorspace for the moment. - return macDisplayColorSpace(); -#endif -} - -//pattern handling (tiling) -#if 1 -# define QMACPATTERN_MASK_MULTIPLIER 32 -#else -# define QMACPATTERN_MASK_MULTIPLIER 1 -#endif -class QMacPattern -{ -public: - QMacPattern() : as_mask(false), pdev(0), image(0) { data.bytes = 0; } - ~QMacPattern() { CGImageRelease(image); } - int width() { - if(image) - return CGImageGetWidth(image); - if(data.bytes) - return 8*QMACPATTERN_MASK_MULTIPLIER; - return data.pixmap.width(); - } - int height() { - if(image) - return CGImageGetHeight(image); - if(data.bytes) - return 8*QMACPATTERN_MASK_MULTIPLIER; - return data.pixmap.height(); - } - - //input - QColor foreground; - bool as_mask; - struct { - QPixmap pixmap; - const uchar *bytes; - } data; - QPaintDevice *pdev; - //output - CGImageRef image; -}; -static void qt_mac_draw_pattern(void *info, CGContextRef c) -{ - QMacPattern *pat = (QMacPattern*)info; - int w = 0, h = 0; - bool isBitmap = (pat->data.pixmap.depth() == 1); - if(!pat->image) { //lazy cache - if(pat->as_mask) { - Q_ASSERT(pat->data.bytes); - w = h = 8; -#if (QMACPATTERN_MASK_MULTIPLIER == 1) - CGDataProviderRef provider = CGDataProviderCreateWithData(0, pat->data.bytes, w*h, 0); - pat->image = CGImageMaskCreate(w, h, 1, 1, 1, provider, 0, false); - CGDataProviderRelease(provider); -#else - const int numBytes = (w*h)/sizeof(uchar); - uchar xor_bytes[numBytes]; - for(int i = 0; i < numBytes; ++i) - xor_bytes[i] = pat->data.bytes[i] ^ 0xFF; - CGDataProviderRef provider = CGDataProviderCreateWithData(0, xor_bytes, w*h, 0); - CGImageRef swatch = CGImageMaskCreate(w, h, 1, 1, 1, provider, 0, false); - CGDataProviderRelease(provider); - - const QColor c0(0, 0, 0, 0), c1(255, 255, 255, 255); - QPixmap pm(w*QMACPATTERN_MASK_MULTIPLIER, h*QMACPATTERN_MASK_MULTIPLIER); - pm.fill(c0); - CGContextRef pm_ctx = qt_mac_cg_context(&pm); - CGContextSetFillColorWithColor(c, cgColorForQColor(c1, pat->pdev)); - CGRect rect = CGRectMake(0, 0, w, h); - for(int x = 0; x < QMACPATTERN_MASK_MULTIPLIER; ++x) { - rect.origin.x = x * w; - for(int y = 0; y < QMACPATTERN_MASK_MULTIPLIER; ++y) { - rect.origin.y = y * h; - qt_mac_drawCGImage(pm_ctx, &rect, swatch); - } - } - pat->image = qt_mac_create_imagemask(pm, pm.rect()); - CGImageRelease(swatch); - CGContextRelease(pm_ctx); - w *= QMACPATTERN_MASK_MULTIPLIER; - h *= QMACPATTERN_MASK_MULTIPLIER; -#endif - } else { - w = pat->data.pixmap.width(); - h = pat->data.pixmap.height(); - if (isBitmap) - pat->image = qt_mac_create_imagemask(pat->data.pixmap, pat->data.pixmap.rect()); - else - pat->image = (CGImageRef)pat->data.pixmap.macCGHandle(); - } - } else { - w = CGImageGetWidth(pat->image); - h = CGImageGetHeight(pat->image); - } - - //draw - bool needRestore = false; - if (CGImageIsMask(pat->image)) { - CGContextSaveGState(c); - CGContextSetFillColorWithColor(c, cgColorForQColor(pat->foreground, pat->pdev)); - } - CGRect rect = CGRectMake(0, 0, w, h); - qt_mac_drawCGImage(c, &rect, pat->image); - if(needRestore) - CGContextRestoreGState(c); -} -static void qt_mac_dispose_pattern(void *info) -{ - QMacPattern *pat = (QMacPattern*)info; - delete pat; -} - -/***************************************************************************** - QCoreGraphicsPaintEngine member functions - *****************************************************************************/ - -inline static QPaintEngine::PaintEngineFeatures qt_mac_cg_features() -{ - return QPaintEngine::PaintEngineFeatures(QPaintEngine::AllFeatures & ~QPaintEngine::PaintOutsidePaintEvent - & ~QPaintEngine::PerspectiveTransform - & ~QPaintEngine::ConicalGradientFill - & ~QPaintEngine::LinearGradientFill - & ~QPaintEngine::RadialGradientFill - & ~QPaintEngine::BrushStroke); -} - -QCoreGraphicsPaintEngine::QCoreGraphicsPaintEngine() -: QPaintEngine(*(new QCoreGraphicsPaintEnginePrivate), qt_mac_cg_features()) -{ -} - -QCoreGraphicsPaintEngine::QCoreGraphicsPaintEngine(QPaintEnginePrivate &dptr) -: QPaintEngine(dptr, qt_mac_cg_features()) -{ -} - -QCoreGraphicsPaintEngine::~QCoreGraphicsPaintEngine() -{ -} - -bool -QCoreGraphicsPaintEngine::begin(QPaintDevice *pdev) -{ - Q_D(QCoreGraphicsPaintEngine); - if(isActive()) { // already active painting - qWarning("QCoreGraphicsPaintEngine::begin: Painter already active"); - return false; - } - - //initialization - d->pdev = pdev; - d->complexXForm = false; - d->cosmeticPen = QCoreGraphicsPaintEnginePrivate::CosmeticSetPenWidth; - d->cosmeticPenSize = 1; - d->current.clipEnabled = false; - d->pixelSize = QPoint(1,1); - d->hd = qt_mac_cg_context(pdev); - if(d->hd) { - d->saveGraphicsState(); - d->orig_xform = CGContextGetCTM(d->hd); - if (d->shading) { - CGShadingRelease(d->shading); - d->shading = 0; - } - d->setClip(0); //clear the context's clipping - } - - setActive(true); - - if(d->pdev->devType() == QInternal::Widget) { // device is a widget - QWidget *w = (QWidget*)d->pdev; - bool unclipped = w->testAttribute(Qt::WA_PaintUnclipped); - - if((w->windowType() == Qt::Desktop)) { - if(!unclipped) - qWarning("QCoreGraphicsPaintEngine::begin: Does not support clipped desktop on Mac OS X"); - // ## need to do [qt_mac_window_for(w) makeKeyAndOrderFront]; (need to rename the file) - } else if(unclipped) { - qWarning("QCoreGraphicsPaintEngine::begin: Does not support unclipped painting"); - } - } else if(d->pdev->devType() == QInternal::Pixmap) { // device is a pixmap - QPixmap *pm = (QPixmap*)d->pdev; - if(pm->isNull()) { - qWarning("QCoreGraphicsPaintEngine::begin: Cannot paint null pixmap"); - end(); - return false; - } - } - - setDirty(QPaintEngine::DirtyPen); - setDirty(QPaintEngine::DirtyBrush); - setDirty(QPaintEngine::DirtyBackground); - setDirty(QPaintEngine::DirtyHints); - return true; -} - -bool -QCoreGraphicsPaintEngine::end() -{ - Q_D(QCoreGraphicsPaintEngine); - setActive(false); - if(d->pdev->devType() == QInternal::Widget && static_cast(d->pdev)->windowType() == Qt::Desktop) { -// // ### need to do [qt_mac_window_for(static_cast(d->pdev)) orderOut]; (need to rename) - - } - if(d->shading) { - CGShadingRelease(d->shading); - d->shading = 0; - } - d->pdev = 0; - if(d->hd) { - d->restoreGraphicsState(); - CGContextSynchronize(d->hd); - CGContextRelease(d->hd); - d->hd = 0; - } - return true; -} - -void -QCoreGraphicsPaintEngine::updateState(const QPaintEngineState &state) -{ - Q_D(QCoreGraphicsPaintEngine); - QPaintEngine::DirtyFlags flags = state.state(); - - if (flags & DirtyTransform) - updateMatrix(state.transform()); - - if (flags & DirtyClipEnabled) { - if (state.isClipEnabled()) - updateClipPath(painter()->clipPath(), Qt::ReplaceClip); - else - updateClipPath(QPainterPath(), Qt::NoClip); - } - - if (flags & DirtyClipPath) { - updateClipPath(state.clipPath(), state.clipOperation()); - } else if (flags & DirtyClipRegion) { - updateClipRegion(state.clipRegion(), state.clipOperation()); - } - - // If the clip has changed we need to update all other states - // too, since they are included in the system context on OSX, - // and changing the clip resets that context back to scratch. - if (flags & (DirtyClipPath | DirtyClipRegion | DirtyClipEnabled)) - flags |= AllDirty; - - if (flags & DirtyPen) - updatePen(state.pen()); - if (flags & (DirtyBrush|DirtyBrushOrigin)) - updateBrush(state.brush(), state.brushOrigin()); - if (flags & DirtyFont) - updateFont(state.font()); - if (flags & DirtyOpacity) - updateOpacity(state.opacity()); - if (flags & DirtyHints) - updateRenderHints(state.renderHints()); - if (flags & DirtyCompositionMode) - updateCompositionMode(state.compositionMode()); - - if (flags & (DirtyPen | DirtyTransform)) { - if (!d->current.pen.isCosmetic()) { - d->cosmeticPen = QCoreGraphicsPaintEnginePrivate::CosmeticNone; - } else if (d->current.transform.m11() < d->current.transform.m22()-1.0 || - d->current.transform.m11() > d->current.transform.m22()+1.0) { - d->cosmeticPen = QCoreGraphicsPaintEnginePrivate::CosmeticTransformPath; - d->cosmeticPenSize = d->adjustPenWidth(d->current.pen.widthF()); - if (!d->cosmeticPenSize) - d->cosmeticPenSize = 1.0; - } else { - d->cosmeticPen = QCoreGraphicsPaintEnginePrivate::CosmeticSetPenWidth; - static const float sqrt2 = sqrt(2); - qreal width = d->current.pen.widthF(); - if (!width) - width = 1; - d->cosmeticPenSize = sqrt(pow(d->pixelSize.y(), 2) + pow(d->pixelSize.x(), 2)) / sqrt2 * width; - } - } -} - -void -QCoreGraphicsPaintEngine::updatePen(const QPen &pen) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - d->current.pen = pen; - d->setStrokePen(pen); -} - -void -QCoreGraphicsPaintEngine::updateBrush(const QBrush &brush, const QPointF &brushOrigin) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - d->current.brush = brush; - -#ifdef QT_MAC_USE_NATIVE_GRADIENTS - // Quartz supports only pad spread - if (const QGradient *gradient = brush.gradient()) { - if (drawGradientNatively(gradient)) { - gccaps |= QPaintEngine::LinearGradientFill | QPaintEngine::RadialGradientFill; - } else { - gccaps &= ~(QPaintEngine::LinearGradientFill | QPaintEngine::RadialGradientFill); - } - } -#endif - - if (d->shading) { - CGShadingRelease(d->shading); - d->shading = 0; - } - d->setFillBrush(brushOrigin); -} - -void -QCoreGraphicsPaintEngine::updateOpacity(qreal opacity) -{ - Q_D(QCoreGraphicsPaintEngine); - CGContextSetAlpha(d->hd, opacity); -} - -void -QCoreGraphicsPaintEngine::updateFont(const QFont &) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - updatePen(d->current.pen); -} - -void -QCoreGraphicsPaintEngine::updateMatrix(const QTransform &transform) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (qt_is_nan(transform.m11()) || qt_is_nan(transform.m12()) || qt_is_nan(transform.m13()) - || qt_is_nan(transform.m21()) || qt_is_nan(transform.m22()) || qt_is_nan(transform.m23()) - || qt_is_nan(transform.m31()) || qt_is_nan(transform.m32()) || qt_is_nan(transform.m33())) - return; - - d->current.transform = transform; - d->setTransform(transform.isIdentity() ? 0 : &transform); - d->complexXForm = (transform.m11() != 1 || transform.m22() != 1 - || transform.m12() != 0 || transform.m21() != 0); - d->pixelSize = d->devicePixelSize(d->hd); -} - -void -QCoreGraphicsPaintEngine::updateClipPath(const QPainterPath &p, Qt::ClipOperation op) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - if(op == Qt::NoClip) { - if(d->current.clipEnabled) { - d->current.clipEnabled = false; - d->current.clip = QRegion(); - d->setClip(0); - } - } else { - if(!d->current.clipEnabled) - op = Qt::ReplaceClip; - d->current.clipEnabled = true; - QRegion clipRegion(p.toFillPolygon().toPolygon(), p.fillRule()); - if(op == Qt::ReplaceClip) { - d->current.clip = clipRegion; - d->setClip(0); - if(p.isEmpty()) { - CGRect rect = CGRectMake(0, 0, 0, 0); - CGContextClipToRect(d->hd, rect); - } else { - CGMutablePathRef path = qt_mac_compose_path(p); - CGContextBeginPath(d->hd); - CGContextAddPath(d->hd, path); - if(p.fillRule() == Qt::WindingFill) - CGContextClip(d->hd); - else - CGContextEOClip(d->hd); - CGPathRelease(path); - } - } else if(op == Qt::IntersectClip) { - d->current.clip = d->current.clip.intersected(clipRegion); - d->setClip(&d->current.clip); - } - } -} - -void -QCoreGraphicsPaintEngine::updateClipRegion(const QRegion &clipRegion, Qt::ClipOperation op) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - if(op == Qt::NoClip) { - d->current.clipEnabled = false; - d->current.clip = QRegion(); - d->setClip(0); - } else { - if(!d->current.clipEnabled) - op = Qt::ReplaceClip; - d->current.clipEnabled = true; - if(op == Qt::IntersectClip) - d->current.clip = d->current.clip.intersected(clipRegion); - else if(op == Qt::ReplaceClip) - d->current.clip = clipRegion; - d->setClip(&d->current.clip); - } -} - -void -QCoreGraphicsPaintEngine::drawPath(const QPainterPath &p) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - CGMutablePathRef path = qt_mac_compose_path(p); - uchar ops = QCoreGraphicsPaintEnginePrivate::CGStroke; - if(p.fillRule() == Qt::WindingFill) - ops |= QCoreGraphicsPaintEnginePrivate::CGFill; - else - ops |= QCoreGraphicsPaintEnginePrivate::CGEOFill; - CGContextBeginPath(d->hd); - d->drawPath(ops, path); - CGPathRelease(path); -} - -void -QCoreGraphicsPaintEngine::drawRects(const QRectF *rects, int rectCount) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - for (int i=0; idrawPath(QCoreGraphicsPaintEnginePrivate::CGFill|QCoreGraphicsPaintEnginePrivate::CGStroke, - path); - CGPathRelease(path); - } -} - -void -QCoreGraphicsPaintEngine::drawPoints(const QPointF *points, int pointCount) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - if (d->current.pen.capStyle() == Qt::FlatCap) - CGContextSetLineCap(d->hd, kCGLineCapSquare); - - CGMutablePathRef path = CGPathCreateMutable(); - for(int i=0; i < pointCount; i++) { - float x = points[i].x(), y = points[i].y(); - CGPathMoveToPoint(path, 0, x, y); - CGPathAddLineToPoint(path, 0, x+0.001, y); - } - - bool doRestore = false; - if(d->cosmeticPen == QCoreGraphicsPaintEnginePrivate::CosmeticNone && !(state->renderHints() & QPainter::Antialiasing)) { - //we don't want adjusted pens for point rendering - doRestore = true; - d->saveGraphicsState(); - CGContextSetLineWidth(d->hd, d->current.pen.widthF()); - } - d->drawPath(QCoreGraphicsPaintEnginePrivate::CGStroke, path); - if (doRestore) - d->restoreGraphicsState(); - CGPathRelease(path); - if (d->current.pen.capStyle() == Qt::FlatCap) - CGContextSetLineCap(d->hd, kCGLineCapButt); -} - -void -QCoreGraphicsPaintEngine::drawEllipse(const QRectF &r) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - CGMutablePathRef path = CGPathCreateMutable(); - CGAffineTransform transform = CGAffineTransformMakeScale(r.width() / r.height(), 1); - CGPathAddArc(path, &transform,(r.x() + (r.width() / 2)) / (r.width() / r.height()), - r.y() + (r.height() / 2), r.height() / 2, 0, (2 * M_PI), false); - d->drawPath(QCoreGraphicsPaintEnginePrivate::CGFill | QCoreGraphicsPaintEnginePrivate::CGStroke, - path); - CGPathRelease(path); -} - -void -QCoreGraphicsPaintEngine::drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - CGMutablePathRef path = CGPathCreateMutable(); - CGPathMoveToPoint(path, 0, points[0].x(), points[0].y()); - for(int x = 1; x < pointCount; ++x) - CGPathAddLineToPoint(path, 0, points[x].x(), points[x].y()); - if(mode != PolylineMode && points[0] != points[pointCount-1]) - CGPathAddLineToPoint(path, 0, points[0].x(), points[0].y()); - uint op = QCoreGraphicsPaintEnginePrivate::CGStroke; - if (mode != PolylineMode) - op |= mode == OddEvenMode ? QCoreGraphicsPaintEnginePrivate::CGEOFill - : QCoreGraphicsPaintEnginePrivate::CGFill; - d->drawPath(op, path); - CGPathRelease(path); -} - -void -QCoreGraphicsPaintEngine::drawLines(const QLineF *lines, int lineCount) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - CGMutablePathRef path = CGPathCreateMutable(); - for(int i = 0; i < lineCount; i++) { - const QPointF start = lines[i].p1(), end = lines[i].p2(); - CGPathMoveToPoint(path, 0, start.x(), start.y()); - CGPathAddLineToPoint(path, 0, end.x(), end.y()); - } - d->drawPath(QCoreGraphicsPaintEnginePrivate::CGStroke, path); - CGPathRelease(path); -} - -void QCoreGraphicsPaintEngine::drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - if(pm.isNull()) - return; - - bool differentSize = (QRectF(0, 0, pm.width(), pm.height()) != sr), doRestore = false; - CGRect rect = CGRectMake(r.x(), r.y(), r.width(), r.height()); - QCFType image; - bool isBitmap = (pm.depth() == 1); - if (isBitmap) { - doRestore = true; - d->saveGraphicsState(); - - const QColor &col = d->current.pen.color(); - CGContextSetFillColorWithColor(d->hd, cgColorForQColor(col, d->pdev)); - image = qt_mac_create_imagemask(pm, sr); - } else if (differentSize) { - QCFType img = pm.toMacCGImageRef(); - image = CGImageCreateWithImageInRect(img, CGRectMake(qRound(sr.x()), qRound(sr.y()), qRound(sr.width()), qRound(sr.height()))); - } else { - image = (CGImageRef)pm.macCGHandle(); - } - qt_mac_drawCGImage(d->hd, &rect, image); - if (doRestore) - d->restoreGraphicsState(); -} - -void QCoreGraphicsPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRectF &sr, - Qt::ImageConversionFlags flags) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_UNUSED(flags); - Q_ASSERT(isActive()); - - if (img.isNull() || state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - const QImage *image; - QCFType cgimage = qt_mac_createCGImageFromQImage(img, &image); - CGRect rect = CGRectMake(r.x(), r.y(), r.width(), r.height()); - if (QRectF(0, 0, img.width(), img.height()) != sr) - cgimage = CGImageCreateWithImageInRect(cgimage, CGRectMake(sr.x(), sr.y(), - sr.width(), sr.height())); - qt_mac_drawCGImage(d->hd, &rect, cgimage); -} - -void QCoreGraphicsPaintEngine::initialize() -{ -} - -void QCoreGraphicsPaintEngine::cleanup() -{ -} - -CGContextRef -QCoreGraphicsPaintEngine::handle() const -{ - return d_func()->hd; -} - -void -QCoreGraphicsPaintEngine::drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, - const QPointF &p) -{ - Q_D(QCoreGraphicsPaintEngine); - Q_ASSERT(isActive()); - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - //save the old state - d->saveGraphicsState(); - - //setup the pattern - QMacPattern *qpattern = new QMacPattern; - qpattern->data.pixmap = pixmap; - qpattern->foreground = d->current.pen.color(); - qpattern->pdev = d->pdev; - CGPatternCallbacks callbks; - callbks.version = 0; - callbks.drawPattern = qt_mac_draw_pattern; - callbks.releaseInfo = qt_mac_dispose_pattern; - const int width = qpattern->width(), height = qpattern->height(); - CGAffineTransform trans = CGContextGetCTM(d->hd); - CGPatternRef pat = CGPatternCreate(qpattern, CGRectMake(0, 0, width, height), - trans, width, height, - kCGPatternTilingNoDistortion, true, &callbks); - CGColorSpaceRef cs = CGColorSpaceCreatePattern(0); - CGContextSetFillColorSpace(d->hd, cs); - CGFloat component = 1.0; //just one - CGContextSetFillPattern(d->hd, pat, &component); - CGSize phase = CGSizeApplyAffineTransform(CGSizeMake(-(p.x()-r.x()), -(p.y()-r.y())), trans); - CGContextSetPatternPhase(d->hd, phase); - - //fill the rectangle - CGRect mac_rect = CGRectMake(r.x(), r.y(), r.width(), r.height()); - CGContextFillRect(d->hd, mac_rect); - - //restore the state - d->restoreGraphicsState(); - //cleanup - CGColorSpaceRelease(cs); - CGPatternRelease(pat); -} - -void QCoreGraphicsPaintEngine::drawTextItem(const QPointF &pos, const QTextItem &item) -{ - Q_D(QCoreGraphicsPaintEngine); - if (d->current.transform.type() == QTransform::TxProject -#ifndef QMAC_NATIVE_GRADIENTS - || painter()->pen().brush().gradient() //Just let the base engine "emulate" the gradient -#endif - ) { - QPaintEngine::drawTextItem(pos, item); - return; - } - - if (state->compositionMode() == QPainter::CompositionMode_Destination) - return; - - const QTextItemInt &ti = static_cast(item); - - QPen oldPen = painter()->pen(); - QBrush oldBrush = painter()->brush(); - QPointF oldBrushOrigin = painter()->brushOrigin(); - updatePen(Qt::NoPen); - updateBrush(oldPen.brush(), QPointF(0, 0)); - - Q_ASSERT(type() == QPaintEngine::CoreGraphics); - - QFontEngine *fe = ti.fontEngine; - - const bool textAA = state->renderHints() & QPainter::TextAntialiasing && fe->fontDef.pointSize > qt_antialiasing_threshold && !(fe->fontDef.styleStrategy & QFont::NoAntialias); - const bool lineAA = state->renderHints() & QPainter::Antialiasing; - if(textAA != lineAA) - CGContextSetShouldAntialias(d->hd, textAA); - - if (ti.glyphs.numGlyphs) { - switch (fe->type()) { - case QFontEngine::Mac: - static_cast(fe)->draw(d->hd, pos.x(), pos.y(), ti, paintDevice()->height()); - break; - case QFontEngine::Box: - d->drawBoxTextItem(pos, ti); - break; - default: - break; - } - } - - if(textAA != lineAA) - CGContextSetShouldAntialias(d->hd, !textAA); - - updatePen(oldPen); - updateBrush(oldBrush, oldBrushOrigin); -} - -QPainter::RenderHints -QCoreGraphicsPaintEngine::supportedRenderHints() const -{ - return QPainter::RenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing | QPainter::SmoothPixmapTransform); -} -enum CGCompositeMode { - kCGCompositeModeClear = 0, - kCGCompositeModeCopy = 1, - kCGCompositeModeSourceOver = 2, - kCGCompositeModeSourceIn = 3, - kCGCompositeModeSourceOut = 4, - kCGCompositeModeSourceAtop = 5, - kCGCompositeModeDestinationOver = 6, - kCGCompositeModeDestinationIn = 7, - kCGCompositeModeDestinationOut = 8, - kCGCompositeModeDestinationAtop = 9, - kCGCompositeModeXOR = 10, - kCGCompositeModePlusDarker = 11, // (max (0, (1-d) + (1-s))) - kCGCompositeModePlusLighter = 12, // (min (1, s + d)) - }; -extern "C" { - extern void CGContextSetCompositeOperation(CGContextRef, int); -} // private function, but is in all versions of OS X. -void -QCoreGraphicsPaintEngine::updateCompositionMode(QPainter::CompositionMode mode) -{ -#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_5) - if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_5) { - int cg_mode = kCGBlendModeNormal; - switch(mode) { - case QPainter::CompositionMode_Multiply: - cg_mode = kCGBlendModeMultiply; - break; - case QPainter::CompositionMode_Screen: - cg_mode = kCGBlendModeScreen; - break; - case QPainter::CompositionMode_Overlay: - cg_mode = kCGBlendModeOverlay; - break; - case QPainter::CompositionMode_Darken: - cg_mode = kCGBlendModeDarken; - break; - case QPainter::CompositionMode_Lighten: - cg_mode = kCGBlendModeLighten; - break; - case QPainter::CompositionMode_ColorDodge: - cg_mode = kCGBlendModeColorDodge; - break; - case QPainter::CompositionMode_ColorBurn: - cg_mode = kCGBlendModeColorBurn; - break; - case QPainter::CompositionMode_HardLight: - cg_mode = kCGBlendModeHardLight; - break; - case QPainter::CompositionMode_SoftLight: - cg_mode = kCGBlendModeSoftLight; - break; - case QPainter::CompositionMode_Difference: - cg_mode = kCGBlendModeDifference; - break; - case QPainter::CompositionMode_Exclusion: - cg_mode = kCGBlendModeExclusion; - break; - case QPainter::CompositionMode_Plus: - cg_mode = kCGBlendModePlusLighter; - break; - case QPainter::CompositionMode_SourceOver: - cg_mode = kCGBlendModeNormal; - break; - case QPainter::CompositionMode_DestinationOver: - cg_mode = kCGBlendModeDestinationOver; - break; - case QPainter::CompositionMode_Clear: - cg_mode = kCGBlendModeClear; - break; - case QPainter::CompositionMode_Source: - cg_mode = kCGBlendModeCopy; - break; - case QPainter::CompositionMode_Destination: - cg_mode = -1; - break; - case QPainter::CompositionMode_SourceIn: - cg_mode = kCGBlendModeSourceIn; - break; - case QPainter::CompositionMode_DestinationIn: - cg_mode = kCGCompositeModeDestinationIn; - break; - case QPainter::CompositionMode_SourceOut: - cg_mode = kCGBlendModeSourceOut; - break; - case QPainter::CompositionMode_DestinationOut: - cg_mode = kCGBlendModeDestinationOver; - break; - case QPainter::CompositionMode_SourceAtop: - cg_mode = kCGBlendModeSourceAtop; - break; - case QPainter::CompositionMode_DestinationAtop: - cg_mode = kCGBlendModeDestinationAtop; - break; - case QPainter::CompositionMode_Xor: - cg_mode = kCGBlendModeXOR; - break; - default: - break; - } - if (cg_mode > -1) { - CGContextSetBlendMode(d_func()->hd, CGBlendMode(cg_mode)); - } - } else -#endif - // The standard porter duff ops. - if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_3 - && mode <= QPainter::CompositionMode_Xor) { - int cg_mode = kCGCompositeModeCopy; - switch (mode) { - case QPainter::CompositionMode_SourceOver: - cg_mode = kCGCompositeModeSourceOver; - break; - case QPainter::CompositionMode_DestinationOver: - cg_mode = kCGCompositeModeDestinationOver; - break; - case QPainter::CompositionMode_Clear: - cg_mode = kCGCompositeModeClear; - break; - default: - qWarning("QCoreGraphicsPaintEngine: Unhandled composition mode %d", (int)mode); - break; - case QPainter::CompositionMode_Source: - cg_mode = kCGCompositeModeCopy; - break; - case QPainter::CompositionMode_Destination: - cg_mode = CGCompositeMode(-1); - break; - case QPainter::CompositionMode_SourceIn: - cg_mode = kCGCompositeModeSourceIn; - break; - case QPainter::CompositionMode_DestinationIn: - cg_mode = kCGCompositeModeDestinationIn; - break; - case QPainter::CompositionMode_SourceOut: - cg_mode = kCGCompositeModeSourceOut; - break; - case QPainter::CompositionMode_DestinationOut: - cg_mode = kCGCompositeModeDestinationOut; - break; - case QPainter::CompositionMode_SourceAtop: - cg_mode = kCGCompositeModeSourceAtop; - break; - case QPainter::CompositionMode_DestinationAtop: - cg_mode = kCGCompositeModeDestinationAtop; - break; - case QPainter::CompositionMode_Xor: - cg_mode = kCGCompositeModeXOR; - break; - } - if (cg_mode > -1) - CGContextSetCompositeOperation(d_func()->hd, CGCompositeMode(cg_mode)); - } else { -#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_4) - bool needPrivateAPI = false; - if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_4) { - int cg_mode = kCGBlendModeNormal; - switch (mode) { - case QPainter::CompositionMode_Multiply: - cg_mode = kCGBlendModeMultiply; - break; - case QPainter::CompositionMode_Screen: - cg_mode = kCGBlendModeScreen; - break; - case QPainter::CompositionMode_Overlay: - cg_mode = kCGBlendModeOverlay; - break; - case QPainter::CompositionMode_Darken: - cg_mode = kCGBlendModeDarken; - break; - case QPainter::CompositionMode_Lighten: - cg_mode = kCGBlendModeLighten; - break; - case QPainter::CompositionMode_ColorDodge: - cg_mode = kCGBlendModeColorDodge; - break; - case QPainter::CompositionMode_ColorBurn: - cg_mode = kCGBlendModeColorBurn; - break; - case QPainter::CompositionMode_HardLight: - cg_mode = kCGBlendModeHardLight; - break; - case QPainter::CompositionMode_SoftLight: - cg_mode = kCGBlendModeSoftLight; - break; - case QPainter::CompositionMode_Difference: - cg_mode = kCGBlendModeDifference; - break; - case QPainter::CompositionMode_Exclusion: - cg_mode = kCGBlendModeExclusion; - break; - case QPainter::CompositionMode_Plus: - needPrivateAPI = true; - cg_mode = kCGCompositeModePlusLighter; - break; - default: - break; - } - if (!needPrivateAPI) - CGContextSetBlendMode(d_func()->hd, CGBlendMode(cg_mode)); - else - CGContextSetCompositeOperation(d_func()->hd, CGCompositeMode(cg_mode)); - } -#endif - } -} - -void -QCoreGraphicsPaintEngine::updateRenderHints(QPainter::RenderHints hints) -{ - Q_D(QCoreGraphicsPaintEngine); - CGContextSetShouldAntialias(d->hd, hints & QPainter::Antialiasing); - static const CGFloat ScaleFactor = qt_mac_get_scalefactor(); - if (ScaleFactor > 1.) { - CGContextSetInterpolationQuality(d->hd, kCGInterpolationHigh); - } else { - CGContextSetInterpolationQuality(d->hd, (hints & QPainter::SmoothPixmapTransform) ? - kCGInterpolationHigh : kCGInterpolationNone); - } - bool textAntialiasing = (hints & QPainter::TextAntialiasing) == QPainter::TextAntialiasing; - if (!textAntialiasing || d->disabledSmoothFonts) { - d->disabledSmoothFonts = !textAntialiasing; - CGContextSetShouldSmoothFonts(d->hd, textAntialiasing); - } -} - -/* - Returns the size of one device pixel in user-space coordinates. -*/ -QPointF QCoreGraphicsPaintEnginePrivate::devicePixelSize(CGContextRef) -{ - QPointF p1 = current.transform.inverted().map(QPointF(0, 0)); - QPointF p2 = current.transform.inverted().map(QPointF(1, 1)); - return QPointF(qAbs(p2.x() - p1.x()), qAbs(p2.y() - p1.y())); -} - -/* - Adjusts the pen width so we get correct line widths in the - non-transformed, aliased case. -*/ -float QCoreGraphicsPaintEnginePrivate::adjustPenWidth(float penWidth) -{ - Q_Q(QCoreGraphicsPaintEngine); - float ret = penWidth; - if (!complexXForm && !(q->state->renderHints() & QPainter::Antialiasing)) { - if (penWidth < 2) - ret = 1; - else if (penWidth < 3) - ret = 1.5; - else - ret = penWidth -1; - } - return ret; -} - -void -QCoreGraphicsPaintEnginePrivate::setStrokePen(const QPen &pen) -{ - //pencap - CGLineCap cglinecap = kCGLineCapButt; - if(pen.capStyle() == Qt::SquareCap) - cglinecap = kCGLineCapSquare; - else if(pen.capStyle() == Qt::RoundCap) - cglinecap = kCGLineCapRound; - CGContextSetLineCap(hd, cglinecap); - CGContextSetLineWidth(hd, adjustPenWidth(pen.widthF())); - - //join - CGLineJoin cglinejoin = kCGLineJoinMiter; - if(pen.joinStyle() == Qt::BevelJoin) - cglinejoin = kCGLineJoinBevel; - else if(pen.joinStyle() == Qt::RoundJoin) - cglinejoin = kCGLineJoinRound; - CGContextSetLineJoin(hd, cglinejoin); -// CGContextSetMiterLimit(hd, pen.miterLimit()); - - //pen style - QVector linedashes; - if(pen.style() == Qt::CustomDashLine) { - QVector customs = pen.dashPattern(); - for(int i = 0; i < customs.size(); ++i) - linedashes.append(customs.at(i)); - } else if(pen.style() == Qt::DashLine) { - linedashes.append(4); - linedashes.append(2); - } else if(pen.style() == Qt::DotLine) { - linedashes.append(1); - linedashes.append(2); - } else if(pen.style() == Qt::DashDotLine) { - linedashes.append(4); - linedashes.append(2); - linedashes.append(1); - linedashes.append(2); - } else if(pen.style() == Qt::DashDotDotLine) { - linedashes.append(4); - linedashes.append(2); - linedashes.append(1); - linedashes.append(2); - linedashes.append(1); - linedashes.append(2); - } - const CGFloat cglinewidth = pen.widthF() <= 0.0f ? 1.0f : float(pen.widthF()); - for(int i = 0; i < linedashes.size(); ++i) { - linedashes[i] *= cglinewidth; - if(cglinewidth < 3 && (cglinecap == kCGLineCapSquare || cglinecap == kCGLineCapRound)) { - if((i%2)) - linedashes[i] += cglinewidth/2; - else - linedashes[i] -= cglinewidth/2; - } - } - CGContextSetLineDash(hd, pen.dashOffset() * cglinewidth, linedashes.data(), linedashes.size()); - - // color - CGContextSetStrokeColorWithColor(hd, cgColorForQColor(pen.color(), pdev)); -} - -// Add our own patterns here to deal with the fact that the coordinate system -// is flipped vertically with Quartz2D. -static const uchar *qt_mac_patternForBrush(int brushStyle) -{ - Q_ASSERT(brushStyle > Qt::SolidPattern && brushStyle < Qt::LinearGradientPattern); - static const uchar dense1_pat[] = { 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x44, 0x00 }; - static const uchar dense2_pat[] = { 0x00, 0x22, 0x00, 0x88, 0x00, 0x22, 0x00, 0x88 }; - static const uchar dense3_pat[] = { 0x11, 0xaa, 0x44, 0xaa, 0x11, 0xaa, 0x44, 0xaa }; - static const uchar dense4_pat[] = { 0xaa, 0x55, 0xaa, 0x55, 0xaa, 0x55, 0xaa, 0x55 }; - static const uchar dense5_pat[] = { 0xee, 0x55, 0xbb, 0x55, 0xee, 0x55, 0xbb, 0x55 }; - static const uchar dense6_pat[] = { 0xff, 0xdd, 0xff, 0x77, 0xff, 0xdd, 0xff, 0x77 }; - static const uchar dense7_pat[] = { 0xff, 0xff, 0xbb, 0xff, 0xff, 0xff, 0xbb, 0xff }; - static const uchar hor_pat[] = { 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff }; - static const uchar ver_pat[] = { 0xef, 0xef, 0xef, 0xef, 0xef, 0xef, 0xef, 0xef }; - static const uchar cross_pat[] = { 0xef, 0xef, 0xef, 0xef, 0x00, 0xef, 0xef, 0xef }; - static const uchar fdiag_pat[] = { 0x7f, 0xbf, 0xdf, 0xef, 0xf7, 0xfb, 0xfd, 0xfe }; - static const uchar bdiag_pat[] = { 0xfe, 0xfd, 0xfb, 0xf7, 0xef, 0xdf, 0xbf, 0x7f }; - static const uchar dcross_pat[] = { 0x7e, 0xbd, 0xdb, 0xe7, 0xe7, 0xdb, 0xbd, 0x7e }; - static const uchar *const pat_tbl[] = { - dense1_pat, dense2_pat, dense3_pat, dense4_pat, dense5_pat, - dense6_pat, dense7_pat, - hor_pat, ver_pat, cross_pat, bdiag_pat, fdiag_pat, dcross_pat }; - return pat_tbl[brushStyle - Qt::Dense1Pattern]; -} - -void QCoreGraphicsPaintEnginePrivate::setFillBrush(const QPointF &offset) -{ - // pattern - Qt::BrushStyle bs = current.brush.style(); -#ifdef QT_MAC_USE_NATIVE_GRADIENTS - if (bs == Qt::LinearGradientPattern || bs == Qt::RadialGradientPattern) { - const QGradient *grad = static_cast(current.brush.gradient()); - if (drawGradientNatively(grad)) { - Q_ASSERT(grad->spread() == QGradient::PadSpread); - - static const CGFloat domain[] = { 0.0f, +1.0f }; - static const CGFunctionCallbacks callbacks = { 0, qt_mac_color_gradient_function, 0 }; - CGFunctionRef fill_func = CGFunctionCreate(reinterpret_cast(¤t.brush), - 1, domain, 4, 0, &callbacks); - - CGColorSpaceRef colorspace = qt_mac_colorSpaceForDeviceType(pdev); - if (bs == Qt::LinearGradientPattern) { - const QLinearGradient *linearGrad = static_cast(grad); - const QPointF start(linearGrad->start()); - const QPointF stop(linearGrad->finalStop()); - shading = CGShadingCreateAxial(colorspace, CGPointMake(start.x(), start.y()), - CGPointMake(stop.x(), stop.y()), fill_func, true, true); - } else { - Q_ASSERT(bs == Qt::RadialGradientPattern); - const QRadialGradient *radialGrad = static_cast(grad); - QPointF center(radialGrad->center()); - QPointF focal(radialGrad->focalPoint()); - qreal radius = radialGrad->radius(); - qreal focalRadius = radialGrad->focalRadius(); - shading = CGShadingCreateRadial(colorspace, CGPointMake(focal.x(), focal.y()), - focalRadius, CGPointMake(center.x(), center.y()), radius, fill_func, false, true); - } - - CGFunctionRelease(fill_func); - } - } else -#endif - if(bs != Qt::SolidPattern && bs != Qt::NoBrush -#ifndef QT_MAC_USE_NATIVE_GRADIENTS - && (bs < Qt::LinearGradientPattern || bs > Qt::ConicalGradientPattern) -#endif - ) - { - QMacPattern *qpattern = new QMacPattern; - qpattern->pdev = pdev; - CGFloat components[4] = { 1.0, 1.0, 1.0, 1.0 }; - CGColorSpaceRef base_colorspace = 0; - if(bs == Qt::TexturePattern) { - qpattern->data.pixmap = current.brush.texture(); - if(qpattern->data.pixmap.isQBitmap()) { - const QColor &col = current.brush.color(); - components[0] = qt_mac_convert_color_to_cg(col.red()); - components[1] = qt_mac_convert_color_to_cg(col.green()); - components[2] = qt_mac_convert_color_to_cg(col.blue()); - base_colorspace = QCoreGraphicsPaintEngine::macGenericColorSpace(); - } - } else { - qpattern->as_mask = true; - - qpattern->data.bytes = qt_mac_patternForBrush(bs); - const QColor &col = current.brush.color(); - components[0] = qt_mac_convert_color_to_cg(col.red()); - components[1] = qt_mac_convert_color_to_cg(col.green()); - components[2] = qt_mac_convert_color_to_cg(col.blue()); - base_colorspace = QCoreGraphicsPaintEngine::macGenericColorSpace(); - } - int width = qpattern->width(), height = qpattern->height(); - qpattern->foreground = current.brush.color(); - - CGColorSpaceRef fill_colorspace = CGColorSpaceCreatePattern(base_colorspace); - CGContextSetFillColorSpace(hd, fill_colorspace); - - CGAffineTransform xform = CGContextGetCTM(hd); - xform = CGAffineTransformConcat(qt_mac_convert_transform_to_cg(current.brush.transform()), xform); - xform = CGAffineTransformTranslate(xform, offset.x(), offset.y()); - - CGPatternCallbacks callbks; - callbks.version = 0; - callbks.drawPattern = qt_mac_draw_pattern; - callbks.releaseInfo = qt_mac_dispose_pattern; - CGPatternRef fill_pattern = CGPatternCreate(qpattern, CGRectMake(0, 0, width, height), - xform, width, height, kCGPatternTilingNoDistortion, - !base_colorspace, &callbks); - CGContextSetFillPattern(hd, fill_pattern, components); - - CGPatternRelease(fill_pattern); - CGColorSpaceRelease(fill_colorspace); - } else if(bs != Qt::NoBrush) { - CGContextSetFillColorWithColor(hd, cgColorForQColor(current.brush.color(), pdev)); - } -} - -void -QCoreGraphicsPaintEnginePrivate::setClip(const QRegion *rgn) -{ - Q_Q(QCoreGraphicsPaintEngine); - if(hd) { - resetClip(); - QRegion sysClip = q->systemClip(); - if(!sysClip.isEmpty()) - qt_mac_clip_cg(hd, sysClip, &orig_xform); - if(rgn) - qt_mac_clip_cg(hd, *rgn, 0); - } -} - -struct qt_mac_cg_transform_path { - CGMutablePathRef path; - CGAffineTransform transform; -}; - -void qt_mac_cg_transform_path_apply(void *info, const CGPathElement *element) -{ - Q_ASSERT(info && element); - qt_mac_cg_transform_path *t = (qt_mac_cg_transform_path*)info; - switch(element->type) { - case kCGPathElementMoveToPoint: - CGPathMoveToPoint(t->path, &t->transform, element->points[0].x, element->points[0].y); - break; - case kCGPathElementAddLineToPoint: - CGPathAddLineToPoint(t->path, &t->transform, element->points[0].x, element->points[0].y); - break; - case kCGPathElementAddQuadCurveToPoint: - CGPathAddQuadCurveToPoint(t->path, &t->transform, element->points[0].x, element->points[0].y, - element->points[1].x, element->points[1].y); - break; - case kCGPathElementAddCurveToPoint: - CGPathAddCurveToPoint(t->path, &t->transform, element->points[0].x, element->points[0].y, - element->points[1].x, element->points[1].y, - element->points[2].x, element->points[2].y); - break; - case kCGPathElementCloseSubpath: - CGPathCloseSubpath(t->path); - break; - default: - qDebug() << "Unhandled path transform type: " << element->type; - } -} - -void QCoreGraphicsPaintEnginePrivate::drawPath(uchar ops, CGMutablePathRef path) -{ - Q_Q(QCoreGraphicsPaintEngine); - Q_ASSERT((ops & (CGFill | CGEOFill)) != (CGFill | CGEOFill)); //can't really happen - if((ops & (CGFill | CGEOFill))) { - if (shading) { - Q_ASSERT(path); - CGContextBeginPath(hd); - CGContextAddPath(hd, path); - saveGraphicsState(); - if (ops & CGFill) - CGContextClip(hd); - else if (ops & CGEOFill) - CGContextEOClip(hd); - if (current.brush.gradient()->coordinateMode() == QGradient::ObjectBoundingMode) { - CGRect boundingBox = CGPathGetBoundingBox(path); - CGContextConcatCTM(hd, - CGAffineTransformMake(boundingBox.size.width, 0, - 0, boundingBox.size.height, - boundingBox.origin.x, boundingBox.origin.y)); - } - CGContextDrawShading(hd, shading); - restoreGraphicsState(); - ops &= ~CGFill; - ops &= ~CGEOFill; - } else if (current.brush.style() == Qt::NoBrush) { - ops &= ~CGFill; - ops &= ~CGEOFill; - } - } - if((ops & CGStroke) && current.pen.style() == Qt::NoPen) - ops &= ~CGStroke; - - if(ops & (CGEOFill | CGFill)) { - CGContextBeginPath(hd); - CGContextAddPath(hd, path); - if (ops & CGEOFill) { - CGContextEOFillPath(hd); - } else { - CGContextFillPath(hd); - } - } - - // Avoid saving and restoring the context if we can. - const bool needContextSave = (cosmeticPen != QCoreGraphicsPaintEnginePrivate::CosmeticNone || - !(q->state->renderHints() & QPainter::Antialiasing)); - if(ops & CGStroke) { - if (needContextSave) - saveGraphicsState(); - CGContextBeginPath(hd); - - // Translate a fraction of a pixel size in the y direction - // to make sure that primitives painted at pixel borders - // fills the right pixel. This is needed since the y xais - // in the Quartz coordinate system is inverted compared to Qt. - if (!(q->state->renderHints() & QPainter::Antialiasing)) { - if (current.pen.style() == Qt::SolidLine || current.pen.width() >= 3) - CGContextTranslateCTM(hd, double(pixelSize.x()) * 0.25, double(pixelSize.y()) * 0.25); - else if (current.pen.style() == Qt::DotLine && QSysInfo::MacintoshVersion == QSysInfo::MV_10_3) - ; // Do nothing. - else - CGContextTranslateCTM(hd, 0, double(pixelSize.y()) * 0.1); - } - - if (cosmeticPen != QCoreGraphicsPaintEnginePrivate::CosmeticNone) { - // If antialiazing is enabled, use the cosmetic pen size directly. - if (q->state->renderHints() & QPainter::Antialiasing) - CGContextSetLineWidth(hd, cosmeticPenSize); - else if (current.pen.widthF() <= 1) - CGContextSetLineWidth(hd, cosmeticPenSize * 0.9f); - else - CGContextSetLineWidth(hd, cosmeticPenSize); - } - if(cosmeticPen == QCoreGraphicsPaintEnginePrivate::CosmeticTransformPath) { - qt_mac_cg_transform_path t; - t.transform = qt_mac_convert_transform_to_cg(current.transform); - t.path = CGPathCreateMutable(); - CGPathApply(path, &t, qt_mac_cg_transform_path_apply); //transform the path - setTransform(0); //unset the context transform - CGContextSetLineWidth(hd, cosmeticPenSize); - CGContextAddPath(hd, t.path); - CGPathRelease(t.path); - } else { - CGContextAddPath(hd, path); - } - - CGContextStrokePath(hd); - if (needContextSave) - restoreGraphicsState(); - } -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qpaintengine_mac_p.h b/src/widgets/platforms/mac/qpaintengine_mac_p.h deleted file mode 100644 index a8e27a8..0000000 --- a/src/widgets/platforms/mac/qpaintengine_mac_p.h +++ /dev/null @@ -1,256 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#ifndef QPAINTENGINE_MAC_P_H -#define QPAINTENGINE_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include "QtGui/qpaintengine.h" -#include "private/qt_mac_p.h" -#include "private/qpaintengine_p.h" -#include "private/qpolygonclipper_p.h" -#include "private/qfont_p.h" -#include "QtCore/qhash.h" - -typedef struct CGColorSpace *CGColorSpaceRef; -QT_BEGIN_NAMESPACE - -class QCoreGraphicsPaintEnginePrivate; -class QCoreGraphicsPaintEngine : public QPaintEngine -{ - Q_DECLARE_PRIVATE(QCoreGraphicsPaintEngine) - -public: - QCoreGraphicsPaintEngine(); - ~QCoreGraphicsPaintEngine(); - - bool begin(QPaintDevice *pdev); - bool end(); - static CGColorSpaceRef macGenericColorSpace(); - static CGColorSpaceRef macDisplayColorSpace(const QWidget *widget = 0); - - void updateState(const QPaintEngineState &state); - - void updatePen(const QPen &pen); - void updateBrush(const QBrush &brush, const QPointF &pt); - void updateFont(const QFont &font); - void updateOpacity(qreal opacity); - void updateMatrix(const QTransform &matrix); - void updateTransform(const QTransform &matrix); - void updateClipRegion(const QRegion ®ion, Qt::ClipOperation op); - void updateClipPath(const QPainterPath &path, Qt::ClipOperation op); - void updateCompositionMode(QPainter::CompositionMode mode); - void updateRenderHints(QPainter::RenderHints hints); - - void drawLines(const QLineF *lines, int lineCount); - void drawRects(const QRectF *rects, int rectCount); - void drawPoints(const QPointF *p, int pointCount); - void drawEllipse(const QRectF &r); - void drawPath(const QPainterPath &path); - - void drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode); - void drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr); - void drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, const QPointF &s); - - void drawTextItem(const QPointF &pos, const QTextItem &item); - void drawImage(const QRectF &r, const QImage &pm, const QRectF &sr, - Qt::ImageConversionFlags flags = Qt::AutoColor); - - Type type() const { return QPaintEngine::CoreGraphics; } - - CGContextRef handle() const; - - static void initialize(); - static void cleanup(); - - QPainter::RenderHints supportedRenderHints() const; - - //avoid partial shadowed overload warnings... - void drawLines(const QLine *lines, int lineCount) { QPaintEngine::drawLines(lines, lineCount); } - void drawRects(const QRect *rects, int rectCount) { QPaintEngine::drawRects(rects, rectCount); } - void drawPoints(const QPoint *p, int pointCount) { QPaintEngine::drawPoints(p, pointCount); } - void drawEllipse(const QRect &r) { QPaintEngine::drawEllipse(r); } - void drawPolygon(const QPoint *points, int pointCount, PolygonDrawMode mode) - { QPaintEngine::drawPolygon(points, pointCount, mode); } - - bool supportsTransformations(qreal, const QTransform &) const { return true; }; - -protected: - friend class QMacPrintEngine; - friend class QMacPrintEnginePrivate; - friend void qt_mac_display_change_callbk(CGDirectDisplayID, CGDisplayChangeSummaryFlags, void *); - friend void qt_color_profile_changed(CFNotificationCenterRef center, void *, - CFStringRef , const void *, CFDictionaryRef); - QCoreGraphicsPaintEngine(QPaintEnginePrivate &dptr); - -private: - static bool m_postRoutineRegistered; - static CGColorSpaceRef m_genericColorSpace; - static QHash m_displayColorSpaceHash; - static void cleanUpMacColorSpaces(); - Q_DISABLE_COPY(QCoreGraphicsPaintEngine) -}; - -/***************************************************************************** - Private data - *****************************************************************************/ -class QCoreGraphicsPaintEnginePrivate : public QPaintEnginePrivate -{ - Q_DECLARE_PUBLIC(QCoreGraphicsPaintEngine) -public: - QCoreGraphicsPaintEnginePrivate() - : hd(0), shading(0), stackCount(0), complexXForm(false), disabledSmoothFonts(false) - { - } - - struct { - QPen pen; - QBrush brush; - uint clipEnabled : 1; - QRegion clip; - QTransform transform; - } current; - - //state info (shared with QD) - CGAffineTransform orig_xform; - - //cg structures - CGContextRef hd; - CGShadingRef shading; - int stackCount; - bool complexXForm; - bool disabledSmoothFonts; - enum { CosmeticNone, CosmeticTransformPath, CosmeticSetPenWidth } cosmeticPen; - - // pixel and cosmetic pen size in user coordinates. - QPointF pixelSize; - float cosmeticPenSize; - - //internal functions - enum { CGStroke=0x01, CGEOFill=0x02, CGFill=0x04 }; - void drawPath(uchar ops, CGMutablePathRef path = 0); - void setClip(const QRegion *rgn=0); - void resetClip(); - void setFillBrush(const QPointF &origin=QPoint()); - void setStrokePen(const QPen &pen); - inline void saveGraphicsState(); - inline void restoreGraphicsState(); - float penOffset(); - QPointF devicePixelSize(CGContextRef context); - float adjustPenWidth(float penWidth); - inline void setTransform(const QTransform *matrix=0) - { - CGContextConcatCTM(hd, CGAffineTransformInvert(CGContextGetCTM(hd))); - CGAffineTransform xform = orig_xform; - if(matrix) { - extern CGAffineTransform qt_mac_convert_transform_to_cg(const QTransform &); - xform = CGAffineTransformConcat(qt_mac_convert_transform_to_cg(*matrix), xform); - } - CGContextConcatCTM(hd, xform); - CGContextSetTextMatrix(hd, xform); - } -}; - -inline void QCoreGraphicsPaintEnginePrivate::saveGraphicsState() -{ - ++stackCount; - CGContextSaveGState(hd); -} - -inline void QCoreGraphicsPaintEnginePrivate::restoreGraphicsState() -{ - --stackCount; - Q_ASSERT(stackCount >= 0); - CGContextRestoreGState(hd); -} - -class QMacQuartzPaintDevice : public QPaintDevice -{ -public: - QMacQuartzPaintDevice(CGContextRef cg, int width, int height, int bytesPerLine) - : mCG(cg), mWidth(width), mHeight(height), mBytesPerLine(bytesPerLine) - { } - int devType() const { return QInternal::MacQuartz; } - CGContextRef cgContext() const { return mCG; } - int metric(PaintDeviceMetric metric) const { - switch (metric) { - case PdmWidth: - return mWidth; - case PdmHeight: - return mHeight; - case PdmWidthMM: - return (qt_defaultDpiX() * mWidth) / 2.54; - case PdmHeightMM: - return (qt_defaultDpiY() * mHeight) / 2.54; - case PdmNumColors: - return 0; - case PdmDepth: - return 32; - case PdmDpiX: - case PdmPhysicalDpiX: - return qt_defaultDpiX(); - case PdmDpiY: - case PdmPhysicalDpiY: - return qt_defaultDpiY(); - } - return 0; - } - QPaintEngine *paintEngine() const { qWarning("This function should never be called."); return 0; } -private: - CGContextRef mCG; - int mWidth; - int mHeight; - int mBytesPerLine; -}; - -QT_END_NAMESPACE - -#endif // QPAINTENGINE_MAC_P_H diff --git a/src/widgets/platforms/mac/qpixmap_mac.cpp b/src/widgets/platforms/mac/qpixmap_mac.cpp deleted file mode 100644 index 3b2452c..0000000 --- a/src/widgets/platforms/mac/qpixmap_mac.cpp +++ /dev/null @@ -1,1062 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qpixmap.h" -#include "qimage.h" -#include "qapplication.h" -#include "qbitmap.h" -#include "qmatrix.h" -#include "qtransform.h" -#include "qlibrary.h" -#include "qvarlengtharray.h" -#include "qdebug.h" -#include -#include -#include -#include -#include -#include -#include - -#include -#include - -QT_BEGIN_NAMESPACE - -/***************************************************************************** - Externals - *****************************************************************************/ -extern const uchar *qt_get_bitflip_array(); //qimage.cpp -extern CGContextRef qt_mac_cg_context(const QPaintDevice *pdev); //qpaintdevice_mac.cpp -extern RgnHandle qt_mac_get_rgn(); //qregion_mac.cpp -extern void qt_mac_dispose_rgn(RgnHandle r); //qregion_mac.cpp -extern QRegion qt_mac_convert_mac_region(RgnHandle rgn); //qregion_mac.cpp - -static int qt_pixmap_serial = 0; - -Q_WIDGETS_EXPORT quint32 *qt_mac_pixmap_get_base(const QPixmap *pix) -{ - if (QApplicationPrivate::graphics_system_name == QLatin1String("raster")) - return reinterpret_cast(static_cast(pix->data.data())->buffer()->bits()); - else - return static_cast(pix->data.data())->pixels; -} - -Q_WIDGETS_EXPORT int qt_mac_pixmap_get_bytes_per_line(const QPixmap *pix) -{ - if (QApplicationPrivate::graphics_system_name == QLatin1String("raster")) - return static_cast(pix->data.data())->buffer()->bytesPerLine(); - else - return static_cast(pix->data.data())->bytesPerRow; -} - -void qt_mac_cgimage_data_free(void *info, const void *memoryToFree, size_t) -{ - QMacPlatformPixmap *pmdata = static_cast(info); - if (!pmdata) { - free(const_cast(memoryToFree)); - } else { - if (QMacPlatformPixmap::validDataPointers.contains(pmdata) == false) { - free(const_cast(memoryToFree)); - return; - } - if (pmdata->pixels == pmdata->pixelsToFree) { - // something we aren't expecting, just free it. - Q_ASSERT(memoryToFree != pmdata->pixelsToFree); - free(const_cast(memoryToFree)); - } else { - free(pmdata->pixelsToFree); - pmdata->pixelsToFree = static_cast(const_cast(memoryToFree)); - } - pmdata->cg_dataBeingReleased = 0; - } -} - -/***************************************************************************** - QPixmap member functions - *****************************************************************************/ - -static inline QRgb qt_conv16ToRgb(ushort c) { - static const int qt_rbits = (565/100); - static const int qt_gbits = (565/10%10); - static const int qt_bbits = (565%10); - static const int qt_red_shift = qt_bbits+qt_gbits-(8-qt_rbits); - static const int qt_green_shift = qt_bbits-(8-qt_gbits); - static const int qt_neg_blue_shift = 8-qt_bbits; - static const int qt_blue_mask = (1<> qt_red_shift; - const int tg = g >> qt_green_shift; - const int tb = b << qt_neg_blue_shift; - - return qRgb(tr,tg,tb); -} - -QSet QMacPlatformPixmap::validDataPointers; - -QMacPlatformPixmap::QMacPlatformPixmap(PixelType type) - : QPlatformPixmap(type, MacClass), has_alpha(0), has_mask(0), - uninit(true), pixels(0), pixelsSize(0), pixelsToFree(0), - bytesPerRow(0), cg_data(0), cg_dataBeingReleased(0), cg_mask(0), - pengine(0) -{ -} - -QPlatformPixmap *QMacPlatformPixmap::createCompatiblePlatformPixmap() const -{ - return new QMacPlatformPixmap(pixelType()); -} - -#define BEST_BYTE_ALIGNMENT 16 -#define COMPTUE_BEST_BYTES_PER_ROW(bpr) \ - (((bpr) + (BEST_BYTE_ALIGNMENT - 1)) & ~(BEST_BYTE_ALIGNMENT - 1)) - -void QMacPlatformPixmap::resize(int width, int height) -{ - setSerialNumber(++qt_pixmap_serial); - - w = width; - h = height; - is_null = (w <= 0 || h <= 0); - d = (pixelType() == BitmapType ? 1 : 32); - bool make_null = w <= 0 || h <= 0; // create null pixmap - if (make_null || d == 0) { - w = 0; - h = 0; - is_null = true; - d = 0; - if (!make_null) - qWarning("Qt: QPixmap: Invalid pixmap parameters"); - return; - } - - if (w < 1 || h < 1) - return; - - //create the pixels - bytesPerRow = w * sizeof(quint32); // Minimum bytes per row. - - // Quartz2D likes things as a multple of 16 (for now). - bytesPerRow = COMPTUE_BEST_BYTES_PER_ROW(bytesPerRow); - macCreatePixels(); -} - -#undef COMPUTE_BEST_BYTES_PER_ROW - -void QMacPlatformPixmap::fromImage(const QImage &img, - Qt::ImageConversionFlags flags) -{ - setSerialNumber(++qt_pixmap_serial); - - // the conversion code only handles format >= - // Format_ARGB32_Premultiplied at the moment.. - if (img.format() > QImage::Format_ARGB32_Premultiplied) { - QImage image; - if (img.hasAlphaChannel()) - image = img.convertToFormat(QImage::Format_ARGB32_Premultiplied); - else - image = img.convertToFormat(QImage::Format_RGB32); - fromImage(image, flags); - return; - } - - w = img.width(); - h = img.height(); - is_null = (w <= 0 || h <= 0); - d = (pixelType() == BitmapType ? 1 : img.depth()); - - QImage image = img; - int dd = QPixmap::defaultDepth(); - bool force_mono = (dd == 1 || - (flags & Qt::ColorMode_Mask)==Qt::MonoOnly); - if (force_mono) { // must be monochrome - if (d != 1) { - image = image.convertToFormat(QImage::Format_MonoLSB, flags); // dither - d = 1; - } - } else { // can be both - bool conv8 = false; - if(d > 8 && dd <= 8) { // convert to 8 bit - if ((flags & Qt::DitherMode_Mask) == Qt::AutoDither) - flags = (flags & ~Qt::DitherMode_Mask) - | Qt::PreferDither; - conv8 = true; - } else if ((flags & Qt::ColorMode_Mask) == Qt::ColorOnly) { - conv8 = d == 1; // native depth wanted - } else if (d == 1) { - if (image.colorCount() == 2) { - QRgb c0 = image.color(0); // Auto: convert to best - QRgb c1 = image.color(1); - conv8 = qMin(c0,c1) != qRgb(0,0,0) || qMax(c0,c1) != qRgb(255,255,255); - } else { - // eg. 1-color monochrome images (they do exist). - conv8 = true; - } - } - if (conv8) { - image = image.convertToFormat(QImage::Format_Indexed8, flags); - d = 8; - } - } - - if (image.depth()==1) { - image.setColor(0, QColor(Qt::color0).rgba()); - image.setColor(1, QColor(Qt::color1).rgba()); - } - - if (d == 16 || d == 24) { - image = image.convertToFormat(QImage::Format_RGB32, flags); - fromImage(image, flags); - return; - } - - // different size or depth, make a new pixmap - resize(w, h); - - quint32 *dptr = pixels, *drow; - const uint dbpr = bytesPerRow; - - const QImage::Format sfmt = image.format(); - const unsigned short sbpr = image.bytesPerLine(); - - // use const_cast to prevent a detach - const uchar *sptr = const_cast(image).bits(), *srow; - - for (int y = 0; y < h; ++y) { - drow = dptr + (y * (dbpr / 4)); - srow = sptr + (y * sbpr); - switch(sfmt) { - case QImage::Format_MonoLSB: - case QImage::Format_Mono:{ - for (int x = 0; x < w; ++x) { - char one_bit = *(srow + (x / 8)); - if (sfmt == QImage::Format_Mono) - one_bit = one_bit >> (7 - (x % 8)); - else - one_bit = one_bit >> (x % 8); - if ((one_bit & 0x01)) - *(drow+x) = 0xFF000000; - else - *(drow+x) = 0xFFFFFFFF; - } - break; - } - case QImage::Format_Indexed8: { - int numColors = image.numColors(); - if (numColors > 0) { - for (int x = 0; x < w; ++x) { - int index = *(srow + x); - *(drow+x) = PREMUL(image.color(qMin(index, numColors))); - } - } - } break; - case QImage::Format_RGB32: - for (int x = 0; x < w; ++x) - *(drow+x) = *(((quint32*)srow) + x) | 0xFF000000; - break; - case QImage::Format_ARGB32: - case QImage::Format_ARGB32_Premultiplied: - for (int x = 0; x < w; ++x) { - if(sfmt == QImage::Format_RGB32) - *(drow+x) = 0xFF000000 | (*(((quint32*)srow) + x) & 0x00FFFFFF); - else if(sfmt == QImage::Format_ARGB32_Premultiplied) - *(drow+x) = *(((quint32*)srow) + x); - else - *(drow+x) = PREMUL(*(((quint32*)srow) + x)); - } - break; - default: - qWarning("Qt: internal: Oops: Forgot a format [%d] %s:%d", sfmt, - __FILE__, __LINE__); - break; - } - } - if (sfmt != QImage::Format_RGB32) { //setup the alpha - bool alphamap = image.depth() == 32; - if (sfmt == QImage::Format_Indexed8) { - const QVector rgb = image.colorTable(); - for (int i = 0, count = image.colorCount(); i < count; ++i) { - const int alpha = qAlpha(rgb[i]); - if (alpha != 0xff) { - alphamap = true; - break; - } - } - } - macSetHasAlpha(alphamap); - } - uninit = false; -} - -int get_index(QImage * qi,QRgb mycol) -{ - int loopc; - for(loopc=0;loopccolorCount();loopc++) { - if(qi->color(loopc)==mycol) - return loopc; - } - qi->setColorCount(qi->colorCount()+1); - qi->setColor(qi->colorCount(),mycol); - return qi->colorCount(); -} - -QImage QMacPlatformPixmap::toImage() const -{ - QImage::Format format = QImage::Format_MonoLSB; - if (d != 1) //Doesn't support index color modes - format = (has_alpha ? QImage::Format_ARGB32_Premultiplied : - QImage::Format_RGB32); - - QImage image(w, h, format); - quint32 *sptr = pixels, *srow; - const uint sbpr = bytesPerRow; - if (format == QImage::Format_MonoLSB) { - image.fill(0); - image.setColorCount(2); - image.setColor(0, QColor(Qt::color0).rgba()); - image.setColor(1, QColor(Qt::color1).rgba()); - for (int y = 0; y < h; ++y) { - uchar *scanLine = image.scanLine(y); - srow = sptr + (y * (sbpr/4)); - for (int x = 0; x < w; ++x) { - if (!(*(srow + x) & RGB_MASK)) - scanLine[x >> 3] |= (1 << (x & 7)); - } - } - } else { - for (int y = 0; y < h; ++y) { - srow = sptr + (y * (sbpr / 4)); - memcpy(image.scanLine(y), srow, w * 4); - } - - } - - return image; -} - -void QMacPlatformPixmap::fill(const QColor &fillColor) - -{ - { //we don't know what backend to use so we cannot paint here - quint32 *dptr = pixels; - Q_ASSERT_X(dptr, "QPixmap::fill", "No dptr"); - const quint32 colr = PREMUL(fillColor.rgba()); - const int nbytes = bytesPerRow * h; - if (!colr) { - memset(dptr, 0, nbytes); - } else { - for (uint i = 0; i < nbytes / sizeof(quint32); ++i) - *(dptr + i) = colr; - } - } - - // If we had an alpha channel from before, don't - // switch it off. Only go from no alpha to alpha: - if (fillColor.alpha() != 255) - macSetHasAlpha(true); -} - -QPixmap QMacPlatformPixmap::alphaChannel() const -{ - if (!has_alpha) - return QPixmap(); - - QMacPlatformPixmap *alpha = new QMacPlatformPixmap(PixmapType); - alpha->resize(w, h); - macGetAlphaChannel(alpha, false); - return QPixmap(alpha); -} - -void QMacPlatformPixmap::setAlphaChannel(const QPixmap &alpha) -{ - has_mask = true; - QMacPlatformPixmap *alphaData = static_cast(alpha.data.data()); - macSetAlphaChannel(alphaData, false); -} - -QBitmap QMacPlatformPixmap::mask() const -{ - if (!has_mask && !has_alpha) - return QBitmap(); - - QMacPlatformPixmap *mask = new QMacPlatformPixmap(BitmapType); - mask->resize(w, h); - macGetAlphaChannel(mask, true); - return QPixmap(mask); -} - -void QMacPlatformPixmap::setMask(const QBitmap &mask) -{ - if (mask.isNull()) { - QMacPlatformPixmap opaque(PixmapType); - opaque.resize(w, h); - opaque.fill(QColor(255, 255, 255, 255)); - macSetAlphaChannel(&opaque, true); - has_alpha = has_mask = false; - return; - } - - has_alpha = false; - has_mask = true; - QMacPlatformPixmap *maskData = static_cast(mask.data.data()); - macSetAlphaChannel(maskData, true); -} - -int QMacPlatformPixmap::metric(QPaintDevice::PaintDeviceMetric theMetric) const -{ - switch (theMetric) { - case QPaintDevice::PdmWidth: - return w; - case QPaintDevice::PdmHeight: - return h; - case QPaintDevice::PdmWidthMM: - return qRound(metric(QPaintDevice::PdmWidth) * 25.4 / qreal(metric(QPaintDevice::PdmDpiX))); - case QPaintDevice::PdmHeightMM: - return qRound(metric(QPaintDevice::PdmHeight) * 25.4 / qreal(metric(QPaintDevice::PdmDpiY))); - case QPaintDevice::PdmNumColors: - return 1 << d; - case QPaintDevice::PdmDpiX: - case QPaintDevice::PdmPhysicalDpiX: { - extern float qt_mac_defaultDpi_x(); //qpaintdevice_mac.cpp - return int(qt_mac_defaultDpi_x()); - } - case QPaintDevice::PdmDpiY: - case QPaintDevice::PdmPhysicalDpiY: { - extern float qt_mac_defaultDpi_y(); //qpaintdevice_mac.cpp - return int(qt_mac_defaultDpi_y()); - } - case QPaintDevice::PdmDepth: - return d; - default: - qWarning("QPixmap::metric: Invalid metric command"); - } - return 0; -} - -QMacPlatformPixmap::~QMacPlatformPixmap() -{ - validDataPointers.remove(this); - if (cg_mask) { - CGImageRelease(cg_mask); - cg_mask = 0; - } - - delete pengine; // Make sure we aren't drawing on the context anymore. - if (cg_data) { - CGImageRelease(cg_data); - } else if (!cg_dataBeingReleased && pixels != pixelsToFree) { - free(pixels); - } - free(pixelsToFree); -} - -void QMacPlatformPixmap::macSetAlphaChannel(const QMacPlatformPixmap *pix, bool asMask) -{ - if (!pixels || !h || !w || pix->w != w || pix->h != h) - return; - - quint32 *dptr = pixels, *drow; - const uint dbpr = bytesPerRow; - const unsigned short sbpr = pix->bytesPerRow; - quint32 *sptr = pix->pixels, *srow; - for (int y=0; y < h; ++y) { - drow = dptr + (y * (dbpr/4)); - srow = sptr + (y * (sbpr/4)); - if(d == 1) { - for (int x=0; x < w; ++x) { - if((*(srow+x) & RGB_MASK)) - *(drow+x) = 0xFFFFFFFF; - } - } else if(d == 8) { - for (int x=0; x < w; ++x) - *(drow+x) = (*(drow+x) & RGB_MASK) | (*(srow+x) << 24); - } else if(asMask) { - for (int x=0; x < w; ++x) { - if(*(srow+x) & RGB_MASK) - *(drow+x) = (*(drow+x) & RGB_MASK); - else - *(drow+x) = (*(drow+x) & RGB_MASK) | 0xFF000000; - *(drow+x) = PREMUL(*(drow+x)); - } - } else { - for (int x=0; x < w; ++x) { - const uchar alpha = qGray(qRed(*(srow+x)), qGreen(*(srow+x)), qBlue(*(srow+x))); - const uchar destAlpha = qt_div_255(alpha * qAlpha(*(drow+x))); -#if 1 - *(drow+x) = (*(drow+x) & RGB_MASK) | (destAlpha << 24); -#else - *(drow+x) = qRgba(qt_div_255(qRed(*(drow+x) * alpha)), - qt_div_255(qGreen(*(drow+x) * alpha)), - qt_div_255(qBlue(*(drow+x) * alpha)), destAlpha); -#endif - *(drow+x) = PREMUL(*(drow+x)); - } - } - } - macSetHasAlpha(true); -} - -void QMacPlatformPixmap::macGetAlphaChannel(QMacPlatformPixmap *pix, bool asMask) const -{ - quint32 *dptr = pix->pixels, *drow; - const uint dbpr = pix->bytesPerRow; - const unsigned short sbpr = bytesPerRow; - quint32 *sptr = pixels, *srow; - for(int y=0; y < h; ++y) { - drow = dptr + (y * (dbpr/4)); - srow = sptr + (y * (sbpr/4)); - if(asMask) { - for (int x = 0; x < w; ++x) { - if (*(srow + x) & qRgba(0, 0, 0, 255)) - *(drow + x) = 0x00000000; - else - *(drow + x) = 0xFFFFFFFF; - } - } else { - for (int x = 0; x < w; ++x) { - const int alpha = qAlpha(*(srow + x)); - *(drow + x) = qRgb(alpha, alpha, alpha); - } - } - } -} - -void QMacPlatformPixmap::macSetHasAlpha(bool b) -{ - has_alpha = b; - macReleaseCGImageRef(); -} - -void QMacPlatformPixmap::macCreateCGImageRef() -{ - Q_ASSERT(cg_data == 0); - //create the cg data - CGColorSpaceRef colorspace = QCoreGraphicsPaintEngine::macDisplayColorSpace(); - QCFType provider = CGDataProviderCreateWithData(this, - pixels, bytesPerRow * h, - qt_mac_cgimage_data_free); - validDataPointers.insert(this); - uint cgflags = kCGImageAlphaPremultipliedFirst; -#ifdef kCGBitmapByteOrder32Host //only needed because CGImage.h added symbols in the minor version - cgflags |= kCGBitmapByteOrder32Host; -#endif - cg_data = CGImageCreate(w, h, 8, 32, bytesPerRow, colorspace, - cgflags, provider, 0, 0, kCGRenderingIntentDefault); -} - -void QMacPlatformPixmap::macReleaseCGImageRef() -{ - if (!cg_data) - return; // There's nothing we need to do - - cg_dataBeingReleased = cg_data; - CGImageRelease(cg_data); - cg_data = 0; - - if (pixels != pixelsToFree) { - macCreatePixels(); - } else { - pixelsToFree = 0; - } -} - - -// We create our space in memory to paint on here. If we already have existing pixels -// copy them over. This is to preserve the fact that CGImageRef's are immutable. -void QMacPlatformPixmap::macCreatePixels() -{ - const int numBytes = bytesPerRow * h; - quint32 *base_pixels; - if (pixelsToFree && pixelsToFree != pixels) { - // Reuse unused block of memory lying around from a previous callback. - base_pixels = pixelsToFree; - pixelsToFree = 0; - } else { - // We need a block of memory to do stuff with. - base_pixels = static_cast(malloc(numBytes)); - } - - if (pixels) - memcpy(base_pixels, pixels, pixelsSize); - pixels = base_pixels; - pixelsSize = numBytes; -} - -#if 0 -QPixmap QMacPlatformPixmap::transformed(const QTransform &transform, - Qt::TransformationMode mode) const -{ - int w, h; // size of target pixmap - const int ws = width(); - const int hs = height(); - - QTransform mat(transform.m11(), transform.m12(), - transform.m21(), transform.m22(), 0., 0.); - if (transform.m12() == 0.0F && transform.m21() == 0.0F && - transform.m11() >= 0.0F && transform.m22() >= 0.0F) - { - h = int(qAbs(mat.m22()) * hs + 0.9999); - w = int(qAbs(mat.m11()) * ws + 0.9999); - h = qAbs(h); - w = qAbs(w); - } else { // rotation or shearing - QPolygonF a(QRectF(0,0,ws+1,hs+1)); - a = mat.map(a); - QRectF r = a.boundingRect().normalized(); - w = int(r.width() + 0.9999); - h = int(r.height() + 0.9999); - } - mat = QPixmap::trueMatrix(mat, ws, hs); - if (!h || !w) - return QPixmap(); - - // create destination - QMacPlatformPixmap *pm = new QMacPlatformPixmap(pixelType(), w, h); - const quint32 *sptr = pixels; - quint32 *dptr = pm->pixels; - memset(dptr, 0, (pm->bytesPerRow * pm->h)); - - // do the transform - if (mode == Qt::SmoothTransformation) { -#warning QMacPlatformPixmap::transformed not properly implemented - qWarning("QMacPlatformPixmap::transformed not properly implemented"); -#if 0 - QPainter p(&pm); - p.setRenderHint(QPainter::Antialiasing); - p.setRenderHint(QPainter::SmoothPixmapTransform); - p.setTransform(mat); - p.drawPixmap(0, 0, *this); -#endif - } else { - bool invertible; - mat = mat.inverted(&invertible); - if (!invertible) - return QPixmap(); - - const int bpp = 32; - const int xbpl = (w * bpp) / 8; - if (!qt_xForm_helper(mat, 0, QT_XFORM_TYPE_MSBFIRST, bpp, - (uchar*)dptr, xbpl, (pm->bytesPerRow) - xbpl, - h, (uchar*)sptr, (bytesPerRow), ws, hs)) { - qWarning("QMacPlatformPixmap::transform(): failure"); - return QPixmap(); - } - } - - // update the alpha - pm->macSetHasAlpha(true); - return QPixmap(pm); -} -#endif - -QT_BEGIN_INCLUDE_NAMESPACE -#include -#include -QT_END_INCLUDE_NAMESPACE - -// Load and resolve the symbols we need from OpenGL manually so QtGui doesn't have to link against the OpenGL framework. -typedef CGLError (*PtrCGLChoosePixelFormat)(const CGLPixelFormatAttribute *, CGLPixelFormatObj *, long *); -typedef CGLError (*PtrCGLClearDrawable)(CGLContextObj); -typedef CGLError (*PtrCGLCreateContext)(CGLPixelFormatObj, CGLContextObj, CGLContextObj *); -typedef CGLError (*PtrCGLDestroyContext)(CGLContextObj); -typedef CGLError (*PtrCGLDestroyPixelFormat)(CGLPixelFormatObj); -typedef CGLError (*PtrCGLSetCurrentContext)(CGLContextObj); -typedef CGLError (*PtrCGLSetFullScreen)(CGLContextObj); -typedef void (*PtrglFinish)(); -typedef void (*PtrglPixelStorei)(GLenum, GLint); -typedef void (*PtrglReadBuffer)(GLenum); -typedef void (*PtrglReadPixels)(GLint, GLint, GLsizei, GLsizei, GLenum, GLenum, GLvoid *); - -static PtrCGLChoosePixelFormat ptrCGLChoosePixelFormat = 0; -static PtrCGLClearDrawable ptrCGLClearDrawable = 0; -static PtrCGLCreateContext ptrCGLCreateContext = 0; -static PtrCGLDestroyContext ptrCGLDestroyContext = 0; -static PtrCGLDestroyPixelFormat ptrCGLDestroyPixelFormat = 0; -static PtrCGLSetCurrentContext ptrCGLSetCurrentContext = 0; -static PtrCGLSetFullScreen ptrCGLSetFullScreen = 0; -static PtrglFinish ptrglFinish = 0; -static PtrglPixelStorei ptrglPixelStorei = 0; -static PtrglReadBuffer ptrglReadBuffer = 0; -static PtrglReadPixels ptrglReadPixels = 0; - -static bool resolveOpenGLSymbols() -{ - if (ptrCGLChoosePixelFormat == 0) { - QLibrary library(QLatin1String("/System/Library/Frameworks/OpenGL.framework/OpenGL")); - ptrCGLChoosePixelFormat = (PtrCGLChoosePixelFormat)(library.resolve("CGLChoosePixelFormat")); - ptrCGLClearDrawable = (PtrCGLClearDrawable)(library.resolve("CGLClearDrawable")); - ptrCGLCreateContext = (PtrCGLCreateContext)(library.resolve("CGLCreateContext")); - ptrCGLDestroyContext = (PtrCGLDestroyContext)(library.resolve("CGLDestroyContext")); - ptrCGLDestroyPixelFormat = (PtrCGLDestroyPixelFormat)(library.resolve("CGLDestroyPixelFormat")); - ptrCGLSetCurrentContext = (PtrCGLSetCurrentContext)(library.resolve("CGLSetCurrentContext")); - ptrCGLSetFullScreen = (PtrCGLSetFullScreen)(library.resolve("CGLSetFullScreen")); - ptrglFinish = (PtrglFinish)(library.resolve("glFinish")); - ptrglPixelStorei = (PtrglPixelStorei)(library.resolve("glPixelStorei")); - ptrglReadBuffer = (PtrglReadBuffer)(library.resolve("glReadBuffer")); - ptrglReadPixels = (PtrglReadPixels)(library.resolve("glReadPixels")); - } - return ptrCGLChoosePixelFormat && ptrCGLClearDrawable && ptrCGLCreateContext - && ptrCGLDestroyContext && ptrCGLDestroyPixelFormat && ptrCGLSetCurrentContext - && ptrCGLSetFullScreen && ptrglFinish && ptrglPixelStorei - && ptrglReadBuffer && ptrglReadPixels; -} - -// Inverts the given pixmap in the y direction. -static void qt_mac_flipPixmap(void *data, int rowBytes, int height) -{ - int bottom = height - 1; - void *base = data; - void *buffer = malloc(rowBytes); - - int top = 0; - while ( top < bottom ) - { - void *topP = (void *)((top * rowBytes) + (intptr_t)base); - void *bottomP = (void *)((bottom * rowBytes) + (intptr_t)base); - - bcopy( topP, buffer, rowBytes ); - bcopy( bottomP, topP, rowBytes ); - bcopy( buffer, bottomP, rowBytes ); - - ++top; - --bottom; - } - free(buffer); -} - -// Grabs displayRect from display and places it into buffer. -static void qt_mac_grabDisplayRect(CGDirectDisplayID display, const QRect &displayRect, void *buffer) -{ - if (display == kCGNullDirectDisplay) - return; - - CGLPixelFormatAttribute attribs[] = { - kCGLPFAFullScreen, - kCGLPFADisplayMask, - (CGLPixelFormatAttribute)0, /* Display mask bit goes here */ - (CGLPixelFormatAttribute)0 - }; - - attribs[2] = (CGLPixelFormatAttribute)CGDisplayIDToOpenGLDisplayMask(display); - - // Build a full-screen GL context - CGLPixelFormatObj pixelFormatObj; - long numPixelFormats; - - ptrCGLChoosePixelFormat( attribs, &pixelFormatObj, &numPixelFormats ); - - if (!pixelFormatObj) // No full screen context support - return; - - CGLContextObj glContextObj; - ptrCGLCreateContext(pixelFormatObj, 0, &glContextObj); - ptrCGLDestroyPixelFormat(pixelFormatObj) ; - if (!glContextObj) - return; - - ptrCGLSetCurrentContext(glContextObj); - ptrCGLSetFullScreen(glContextObj) ; - - ptrglReadBuffer(GL_FRONT); - - ptrglFinish(); // Finish all OpenGL commands - ptrglPixelStorei(GL_PACK_ALIGNMENT, 4); // Force 4-byte alignment - ptrglPixelStorei(GL_PACK_ROW_LENGTH, 0); - ptrglPixelStorei(GL_PACK_SKIP_ROWS, 0); - ptrglPixelStorei(GL_PACK_SKIP_PIXELS, 0); - - // Fetch the data in XRGB format, matching the bitmap context. - ptrglReadPixels(GLint(displayRect.x()), GLint(displayRect.y()), - GLint(displayRect.width()), GLint(displayRect.height()), -#ifdef __BIG_ENDIAN__ - GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, buffer -#else - GL_BGRA, GL_UNSIGNED_INT_8_8_8_8, buffer -#endif - ); - - ptrCGLSetCurrentContext(0); - ptrCGLClearDrawable(glContextObj); // disassociate from full screen - ptrCGLDestroyContext(glContextObj); // and destroy the context -} - -// Returns a pixmap containing the screen contents at rect. -static QPixmap qt_mac_grabScreenRect(const QRect &rect) -{ - if (!resolveOpenGLSymbols()) - return QPixmap(); - - const int maxDisplays = 128; // 128 displays should be enough for everyone. - CGDirectDisplayID displays[maxDisplays]; - CGDisplayCount displayCount; - const CGRect cgRect = CGRectMake(rect.x(), rect.y(), rect.width(), rect.height()); - const CGDisplayErr err = CGGetDisplaysWithRect(cgRect, maxDisplays, displays, &displayCount); - - if (err && displayCount == 0) - return QPixmap(); - - long bytewidth = rect.width() * 4; // Assume 4 bytes/pixel for now - bytewidth = (bytewidth + 3) & ~3; // Align to 4 bytes - QVarLengthArray buffer(rect.height() * bytewidth); - - for (uint i = 0; i < displayCount; ++i) { - const CGRect bounds = CGDisplayBounds(displays[i]); - // Translate to display-local coordinates - QRect displayRect = rect.translated(qRound(-bounds.origin.x), qRound(-bounds.origin.y)); - // Adjust for inverted y axis. - displayRect.moveTop(qRound(bounds.size.height) - displayRect.y() - rect.height()); - qt_mac_grabDisplayRect(displays[i], displayRect, buffer.data()); - } - - qt_mac_flipPixmap(buffer.data(), bytewidth, rect.height()); - QCFType bitmap = CGBitmapContextCreate(buffer.data(), rect.width(), - rect.height(), 8, bytewidth, - QCoreGraphicsPaintEngine::macGenericColorSpace(), - kCGImageAlphaNoneSkipFirst); - QCFType image = CGBitmapContextCreateImage(bitmap); - return QPixmap::fromMacCGImageRef(image); -} - - -QPixmap QPixmap::grabWindow(WId window, int x, int y, int w, int h) -{ - QWidget *widget = QWidget::find(window); - if (widget == 0) - return QPixmap(); - - if(w == -1) - w = widget->width() - x; - if(h == -1) - h = widget->height() - y; - - QPoint globalCoord(0, 0); - globalCoord = widget->mapToGlobal(globalCoord); - QRect rect(globalCoord.x() + x, globalCoord.y() + y, w, h); - - return qt_mac_grabScreenRect(rect); -} - -/*! \internal - - Returns the QuickDraw CGrafPtr of the pixmap. 0 is returned if it can't - be obtained. Do not hold the pointer around for long as it can be - relocated. - - \warning This function is only available on Mac OS X. - \warning As of Qt 4.6, this function \e{always} returns zero. -*/ - -Qt::HANDLE QPixmap::macQDHandle() const -{ - return 0; -} - -/*! \internal - - Returns the QuickDraw CGrafPtr of the pixmap's alpha channel. 0 is - returned if it can't be obtained. Do not hold the pointer around for - long as it can be relocated. - - \warning This function is only available on Mac OS X. - \warning As of Qt 4.6, this function \e{always} returns zero. -*/ - -Qt::HANDLE QPixmap::macQDAlphaHandle() const -{ - return 0; -} - -/*! \internal - - Returns the CoreGraphics CGContextRef of the pixmap. 0 is returned if - it can't be obtained. It is the caller's responsiblity to - CGContextRelease the context when finished using it. - - \warning This function is only available on Mac OS X. -*/ - -Qt::HANDLE QPixmap::macCGHandle() const -{ - if (isNull()) - return 0; - - if (data->classId() == QPlatformPixmap::MacClass) { - QMacPlatformPixmap *d = static_cast(data.data()); - if (!d->cg_data) - d->macCreateCGImageRef(); - CGImageRef ret = d->cg_data; - CGImageRetain(ret); - return ret; - } else if (data->classId() == QPlatformPixmap::RasterClass) { - return qt_mac_image_to_cgimage(static_cast(data.data())->image); - } - return 0; -} - -bool QMacPlatformPixmap::hasAlphaChannel() const -{ - return has_alpha; -} - -CGImageRef qt_mac_create_imagemask(const QPixmap &pixmap, const QRectF &sr) -{ - QMacPlatformPixmap *px = static_cast(pixmap.data.data()); - if (px->cg_mask) { - if (px->cg_mask_rect == sr) { - CGImageRetain(px->cg_mask); //reference for the caller - return px->cg_mask; - } - CGImageRelease(px->cg_mask); - px->cg_mask = 0; - } - - const int sx = qRound(sr.x()), sy = qRound(sr.y()), sw = qRound(sr.width()), sh = qRound(sr.height()); - const int sbpr = px->bytesPerRow; - const uint nbytes = sw * sh; - // alpha is always 255 for bitmaps, ignore it in this case. - const quint32 mask = px->depth() == 1 ? 0x00ffffff : 0xffffffff; - quint8 *dptr = static_cast(malloc(nbytes)); - quint32 *sptr = px->pixels, *srow; - for(int y = sy, offset=0; y < sh; ++y) { - srow = sptr + (y * (sbpr / 4)); - for(int x = sx; x < sw; ++x) - *(dptr+(offset++)) = (*(srow+x) & mask) ? 255 : 0; - } - QCFType provider = CGDataProviderCreateWithData(0, dptr, nbytes, qt_mac_cgimage_data_free); - px->cg_mask = CGImageMaskCreate(sw, sh, 8, 8, nbytes / sh, provider, 0, 0); - px->cg_mask_rect = sr; - CGImageRetain(px->cg_mask); //reference for the caller - return px->cg_mask; -} - - -/*! \internal */ -QPaintEngine* QMacPlatformPixmap::paintEngine() const -{ - if (!pengine) { - QMacPlatformPixmap *that = const_cast(this); - that->pengine = new QCoreGraphicsPaintEngine(); - } - return pengine; -} - -void QMacPlatformPixmap::copy(const QPlatformPixmap *data, const QRect &rect) -{ - if (data->pixelType() == BitmapType) { - QBitmap::fromImage(toImage().copy(rect)); - return; - } - - const QMacPlatformPixmap *macData = static_cast(data); - - resize(rect.width(), rect.height()); - - has_alpha = macData->has_alpha; - has_mask = macData->has_mask; - uninit = false; - - const int x = rect.x(); - const int y = rect.y(); - char *dest = reinterpret_cast(pixels); - const char *src = reinterpret_cast(macData->pixels + x) + y * macData->bytesPerRow; - for (int i = 0; i < h; ++i) { - memcpy(dest, src, w * 4); - dest += bytesPerRow; - src += macData->bytesPerRow; - } - - has_alpha = macData->has_alpha; - has_mask = macData->has_mask; -} - -bool QMacPlatformPixmap::scroll(int dx, int dy, const QRect &rect) -{ - Q_UNUSED(dx); - Q_UNUSED(dy); - Q_UNUSED(rect); - return false; -} - -/*! - \since 4.2 - - Creates a \c CGImageRef equivalent to the QPixmap. Returns the \c CGImageRef handle. - - It is the caller's responsibility to release the \c CGImageRef data - after use. - - \warning This function is only available on Mac OS X. - - \sa fromMacCGImageRef() -*/ -CGImageRef QPixmap::toMacCGImageRef() const -{ - return (CGImageRef)macCGHandle(); -} - -/*! - \since 4.2 - - Returns a QPixmap that is equivalent to the given \a image. - - \warning This function is only available on Mac OS X. - - \sa toMacCGImageRef(), {QPixmap#Pixmap Conversion}{Pixmap Conversion} -*/ -QPixmap QPixmap::fromMacCGImageRef(CGImageRef image) -{ - const size_t w = CGImageGetWidth(image), - h = CGImageGetHeight(image); - QPixmap ret(w, h); - ret.fill(Qt::transparent); - CGRect rect = CGRectMake(0, 0, w, h); - CGContextRef ctx = qt_mac_cg_context(&ret); - qt_mac_drawCGImage(ctx, &rect, image); - CGContextRelease(ctx); - return ret; -} - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qpixmap_mac_p.h b/src/widgets/platforms/mac/qpixmap_mac_p.h deleted file mode 100644 index 582eef2..0000000 --- a/src/widgets/platforms/mac/qpixmap_mac_p.h +++ /dev/null @@ -1,134 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#ifndef QPIXMAP_MAC_P_H -#define QPIXMAP_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#include -#include -#include - -QT_BEGIN_NAMESPACE - -class QMacPlatformPixmap : public QPlatformPixmap -{ -public: - QMacPlatformPixmap(PixelType type); - ~QMacPlatformPixmap(); - - QPlatformPixmap *createCompatiblePlatformPixmap() const; - - void resize(int width, int height); - void fromImage(const QImage &image, Qt::ImageConversionFlags flags); - void copy(const QPlatformPixmap *data, const QRect &rect); - bool scroll(int dx, int dy, const QRect &rect); - - int metric(QPaintDevice::PaintDeviceMetric metric) const; - void fill(const QColor &color); - QBitmap mask() const; - void setMask(const QBitmap &mask); - bool hasAlphaChannel() const; -// QPixmap transformed(const QTransform &matrix, -// Qt::TransformationMode mode) const; - void setAlphaChannel(const QPixmap &alphaChannel); - QPixmap alphaChannel() const; - QImage toImage() const; - QPaintEngine* paintEngine() const; - -private: - - uint has_alpha : 1, has_mask : 1, uninit : 1; - - void macSetHasAlpha(bool b); - void macGetAlphaChannel(QMacPlatformPixmap *, bool asMask) const; - void macSetAlphaChannel(const QMacPlatformPixmap *, bool asMask); - void macCreateCGImageRef(); - void macCreatePixels(); - void macReleaseCGImageRef(); - /* - pixels stores the pixmap data. pixelsToFree is either 0 or some memory - block that was bound to a CGImageRef and released, and for which the - release callback has been called. There are two uses to pixelsToFree: - - 1. If pixels == pixelsToFree, then we know that the CGImageRef is done\ - with the data and we can modify pixels without breaking CGImageRef's - mutability invariant. - - 2. If pixels != pixelsToFree and pixelsToFree != 0, then we can reuse - pixelsToFree later on instead of malloc'ing memory. - */ - quint32 *pixels; - uint pixelsSize; - quint32 *pixelsToFree; - uint bytesPerRow; - QRectF cg_mask_rect; - CGImageRef cg_data, cg_dataBeingReleased, cg_mask; - static QSet validDataPointers; - - QPaintEngine *pengine; - - friend class QPixmap; - friend class QRasterBuffer; - friend class QRasterPaintEngine; - friend class QCoreGraphicsPaintEngine; - friend CGImageRef qt_mac_create_imagemask(const QPixmap&, const QRectF&); - friend quint32 *qt_mac_pixmap_get_base(const QPixmap*); - friend int qt_mac_pixmap_get_bytes_per_line(const QPixmap*); - friend void qt_mac_cgimage_data_free(void *, const void*, size_t); - friend IconRef qt_mac_create_iconref(const QPixmap&); - friend CGContextRef qt_mac_cg_context(const QPaintDevice*); - friend QColor qcolorForThemeTextColor(ThemeTextColor themeColor); -}; - -QT_END_NAMESPACE - -#endif // QPIXMAP_MAC_P_H diff --git a/src/widgets/platforms/mac/qprintengine_mac.mm b/src/widgets/platforms/mac/qprintengine_mac.mm deleted file mode 100644 index 9902b32..0000000 --- a/src/widgets/platforms/mac/qprintengine_mac.mm +++ /dev/null @@ -1,840 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include -#include -#include - -#ifndef QT_NO_PRINTER - -QT_BEGIN_NAMESPACE - -extern QSizeF qt_paperSizeToQSizeF(QPrinter::PaperSize size); - -QMacPrintEngine::QMacPrintEngine(QPrinter::PrinterMode mode) : QPaintEngine(*(new QMacPrintEnginePrivate)) -{ - Q_D(QMacPrintEngine); - d->mode = mode; - d->initialize(); -} - -bool QMacPrintEngine::begin(QPaintDevice *dev) -{ - Q_D(QMacPrintEngine); - - Q_ASSERT(dev && dev->devType() == QInternal::Printer); - if (!static_cast(dev)->isValid()) - return false; - - if (d->state == QPrinter::Idle && !d->isPrintSessionInitialized()) // Need to reinitialize - d->initialize(); - - d->paintEngine->state = state; - d->paintEngine->begin(dev); - Q_ASSERT_X(d->state == QPrinter::Idle, "QMacPrintEngine", "printer already active"); - - if (PMSessionValidatePrintSettings(d->session, d->settings, kPMDontWantBoolean) != noErr - || PMSessionValidatePageFormat(d->session, d->format, kPMDontWantBoolean) != noErr) { - d->state = QPrinter::Error; - return false; - } - - if (!d->outputFilename.isEmpty()) { - QCFType outFile = CFURLCreateWithFileSystemPath(kCFAllocatorSystemDefault, - QCFString(d->outputFilename), - kCFURLPOSIXPathStyle, - false); - if (PMSessionSetDestination(d->session, d->settings, kPMDestinationFile, - kPMDocumentFormatPDF, outFile) != noErr) { - qWarning("QMacPrintEngine::begin: Problem setting file [%s]", d->outputFilename.toUtf8().constData()); - return false; - } - } - OSStatus status = noErr; - status = PMSessionBeginCGDocumentNoDialog(d->session, d->settings, d->format); - - if (status != noErr) { - d->state = QPrinter::Error; - return false; - } - - d->state = QPrinter::Active; - setActive(true); - d->newPage_helper(); - return true; -} - -bool QMacPrintEngine::end() -{ - Q_D(QMacPrintEngine); - if (d->state == QPrinter::Aborted) - return true; // I was just here a function call ago :) - if(d->paintEngine->type() == QPaintEngine::CoreGraphics) { - // We dont need the paint engine to call restoreGraphicsState() - static_cast(d->paintEngine)->d_func()->stackCount = 0; - static_cast(d->paintEngine)->d_func()->hd = 0; - } - d->paintEngine->end(); - if (d->state != QPrinter::Idle) - d->releaseSession(); - d->state = QPrinter::Idle; - return true; -} - -QPaintEngine * -QMacPrintEngine::paintEngine() const -{ - return d_func()->paintEngine; -} - -Qt::HANDLE QMacPrintEngine::handle() const -{ - QCoreGraphicsPaintEngine *cgEngine = static_cast(paintEngine()); - return cgEngine->d_func()->hd; -} - -QMacPrintEnginePrivate::~QMacPrintEnginePrivate() -{ - [printInfo release]; - delete paintEngine; -} - -void QMacPrintEnginePrivate::setPaperSize(QPrinter::PaperSize ps) -{ - Q_Q(QMacPrintEngine); - QSizeF newSize = qt_paperSizeToQSizeF(ps); - QCFType formats; - PMPrinter printer; - - if (PMSessionGetCurrentPrinter(session, &printer) == noErr - && PMSessionCreatePageFormatList(session, printer, &formats) == noErr) { - CFIndex total = CFArrayGetCount(formats); - PMPageFormat tmp; - PMRect paper; - for (CFIndex idx = 0; idx < total; ++idx) { - tmp = static_cast( - const_cast(CFArrayGetValueAtIndex(formats, idx))); - PMGetUnadjustedPaperRect(tmp, &paper); - int wMM = int((paper.right - paper.left) / 72 * 25.4 + 0.5); - int hMM = int((paper.bottom - paper.top) / 72 * 25.4 + 0.5); - if (newSize.width() == wMM && newSize.height() == hMM) { - PMCopyPageFormat(tmp, format); - // reset the orientation and resolution as they are lost in the copy. - q->setProperty(QPrintEngine::PPK_Orientation, orient); - if (PMSessionValidatePageFormat(session, format, kPMDontWantBoolean) != noErr) { - // Don't know, warn for the moment. - qWarning("QMacPrintEngine, problem setting format and resolution for this page size"); - } - break; - } - } - } -} - -QPrinter::PaperSize QMacPrintEnginePrivate::paperSize() const -{ - PMRect paper; - PMGetUnadjustedPaperRect(format, &paper); - int wMM = int((paper.right - paper.left) / 72 * 25.4 + 0.5); - int hMM = int((paper.bottom - paper.top) / 72 * 25.4 + 0.5); - for (int i = QPrinter::A4; i < QPrinter::NPaperSize; ++i) { - QSizeF s = qt_paperSizeToQSizeF(QPrinter::PaperSize(i)); - if (s.width() == wMM && s.height() == hMM) - return (QPrinter::PaperSize)i; - } - return QPrinter::Custom; -} - -QList QMacPrintEnginePrivate::supportedResolutions() const -{ - Q_ASSERT_X(session, "QMacPrinterEngine::supportedResolutions", - "must have a valid printer session"); - UInt32 resCount; - QList resolutions; - PMPrinter printer; - if (PMSessionGetCurrentPrinter(session, &printer) == noErr) { - PMResolution res; - OSStatus status = PMPrinterGetPrinterResolutionCount(printer, &resCount); - if (status == kPMNotImplemented) { -#if (MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_5) - // *Sigh* we have to use the non-indexed version. - if (PMPrinterGetPrinterResolution(printer, kPMMinSquareResolution, &res) == noErr) - resolutions.append(int(res.hRes)); - if (PMPrinterGetPrinterResolution(printer, kPMMaxSquareResolution, &res) == noErr) { - QVariant var(int(res.hRes)); - if (!resolutions.contains(var)) - resolutions.append(var); - } - if (PMPrinterGetPrinterResolution(printer, kPMDefaultResolution, &res) == noErr) { - QVariant var(int(res.hRes)); - if (!resolutions.contains(var)) - resolutions.append(var); - } -#endif - } else if (status == noErr) { - // According to the docs, index start at 1. - for (UInt32 i = 1; i <= resCount; ++i) { - if (PMPrinterGetIndexedPrinterResolution(printer, i, &res) == noErr) - resolutions.append(QVariant(int(res.hRes))); - } - } else { - qWarning("QMacPrintEngine::supportedResolutions: Unexpected error: %ld", long(status)); - } - } - return resolutions; -} - -bool QMacPrintEnginePrivate::shouldSuppressStatus() const -{ - if (suppressStatus == true) - return true; - - // Supress displaying the automatic progress dialog if we are printing - // from a non-gui thread. - return (qApp->thread() != QThread::currentThread()); -} - -QPrinter::PrinterState QMacPrintEngine::printerState() const -{ - return d_func()->state; -} - -bool QMacPrintEngine::newPage() -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - OSStatus err = - PMSessionEndPageNoDialog(d->session); - if (err != noErr) { - if (err == kPMCancel) { - // User canceled, we need to abort! - abort(); - } else { - // Not sure what the problem is... - qWarning("QMacPrintEngine::newPage: Cannot end current page. %ld", long(err)); - d->state = QPrinter::Error; - } - return false; - } - return d->newPage_helper(); -} - -bool QMacPrintEngine::abort() -{ - Q_D(QMacPrintEngine); - if (d->state != QPrinter::Active) - return false; - bool ret = end(); - d->state = QPrinter::Aborted; - return ret; -} - -static inline int qt_get_PDMWidth(PMPageFormat pformat, bool fullPage, - const PMResolution &resolution) -{ - int val = 0; - PMRect r; - qreal hRatio = resolution.hRes / 72; - if (fullPage) { - if (PMGetAdjustedPaperRect(pformat, &r) == noErr) - val = qRound((r.right - r.left) * hRatio); - } else { - if (PMGetAdjustedPageRect(pformat, &r) == noErr) - val = qRound((r.right - r.left) * hRatio); - } - return val; -} - -static inline int qt_get_PDMHeight(PMPageFormat pformat, bool fullPage, - const PMResolution &resolution) -{ - int val = 0; - PMRect r; - qreal vRatio = resolution.vRes / 72; - if (fullPage) { - if (PMGetAdjustedPaperRect(pformat, &r) == noErr) - val = qRound((r.bottom - r.top) * vRatio); - } else { - if (PMGetAdjustedPageRect(pformat, &r) == noErr) - val = qRound((r.bottom - r.top) * vRatio); - } - return val; -} - - -int QMacPrintEngine::metric(QPaintDevice::PaintDeviceMetric m) const -{ - Q_D(const QMacPrintEngine); - int val = 1; - switch (m) { - case QPaintDevice::PdmWidth: - if (d->hasCustomPaperSize) { - val = qRound(d->customSize.width()); - if (d->hasCustomPageMargins) { - val -= qRound(d->leftMargin + d->rightMargin); - } else { - QList margins = property(QPrintEngine::PPK_PageMargins).toList(); - val -= qRound(margins.at(0).toDouble() + margins.at(2).toDouble()); - } - } else { - val = qt_get_PDMWidth(d->format, property(PPK_FullPage).toBool(), d->resolution); - } - break; - case QPaintDevice::PdmHeight: - if (d->hasCustomPaperSize) { - val = qRound(d->customSize.height()); - if (d->hasCustomPageMargins) { - val -= qRound(d->topMargin + d->bottomMargin); - } else { - QList margins = property(QPrintEngine::PPK_PageMargins).toList(); - val -= qRound(margins.at(1).toDouble() + margins.at(3).toDouble()); - } - } else { - val = qt_get_PDMHeight(d->format, property(PPK_FullPage).toBool(), d->resolution); - } - break; - case QPaintDevice::PdmWidthMM: - val = metric(QPaintDevice::PdmWidth); - val = int((val * 254 + 5 * d->resolution.hRes) / (10 * d->resolution.hRes)); - break; - case QPaintDevice::PdmHeightMM: - val = metric(QPaintDevice::PdmHeight); - val = int((val * 254 + 5 * d->resolution.vRes) / (10 * d->resolution.vRes)); - break; - case QPaintDevice::PdmPhysicalDpiX: - case QPaintDevice::PdmPhysicalDpiY: { - PMPrinter printer; - if(PMSessionGetCurrentPrinter(d->session, &printer) == noErr) { - PMResolution resolution; - PMPrinterGetOutputResolution(printer, d->settings, &resolution); - val = (int)resolution.vRes; - break; - } - //otherwise fall through - } - case QPaintDevice::PdmDpiY: - val = (int)d->resolution.vRes; - break; - case QPaintDevice::PdmDpiX: - val = (int)d->resolution.hRes; - break; - case QPaintDevice::PdmNumColors: - val = (1 << metric(QPaintDevice::PdmDepth)); - break; - case QPaintDevice::PdmDepth: - val = 24; - break; - default: - val = 0; - qWarning("QPrinter::metric: Invalid metric command"); - } - return val; -} - -void QMacPrintEnginePrivate::initialize() -{ - Q_Q(QMacPrintEngine); - - Q_ASSERT(!printInfo); - - if (!paintEngine) - paintEngine = new QCoreGraphicsPaintEngine(); - - q->gccaps = paintEngine->gccaps; - - fullPage = false; - - QMacCocoaAutoReleasePool pool; - printInfo = [[NSPrintInfo alloc] initWithDictionary:[NSDictionary dictionary]]; - session = static_cast([printInfo PMPrintSession]); - - PMPrinter printer; - if (session && PMSessionGetCurrentPrinter(session, &printer) == noErr) { - QList resolutions = supportedResolutions(); - if (!resolutions.isEmpty() && mode != QPrinter::ScreenResolution) { - if (resolutions.count() > 1 && mode == QPrinter::HighResolution) { - int max = 0; - for (int i = 0; i < resolutions.count(); ++i) { - int value = resolutions.at(i).toInt(); - if (value > max) - max = value; - } - resolution.hRes = resolution.vRes = max; - } else { - resolution.hRes = resolution.vRes = resolutions.at(0).toInt(); - } - if(resolution.hRes == 0) - resolution.hRes = resolution.vRes = 600; - } else { - resolution.hRes = resolution.vRes = qt_defaultDpi(); - } - } - - settings = static_cast([printInfo PMPrintSettings]); - format = static_cast([printInfo PMPageFormat]); - - - QHash::const_iterator propC; - for (propC = valueCache.constBegin(); propC != valueCache.constEnd(); propC++) { - q->setProperty(propC.key(), propC.value()); - } -} - -void QMacPrintEnginePrivate::releaseSession() -{ - PMSessionEndPageNoDialog(session); - PMSessionEndDocumentNoDialog(session); - [printInfo release]; - printInfo = 0; - session = 0; -} - -bool QMacPrintEnginePrivate::newPage_helper() -{ - Q_Q(QMacPrintEngine); - Q_ASSERT(state == QPrinter::Active); - - if (PMSessionError(session) != noErr) { - q->abort(); - return false; - } - - // pop the stack of saved graphic states, in case we get the same - // context back - either way, the stack count should be 0 when we - // get the new one - QCoreGraphicsPaintEngine *cgEngine = static_cast(paintEngine); - while (cgEngine->d_func()->stackCount > 0) - cgEngine->d_func()->restoreGraphicsState(); - - OSStatus status = - PMSessionBeginPageNoDialog(session, format, 0); - if(status != noErr) { - state = QPrinter::Error; - return false; - } - - QRect page = q->property(QPrintEngine::PPK_PageRect).toRect(); - QRect paper = q->property(QPrintEngine::PPK_PaperRect).toRect(); - - CGContextRef cgContext; - OSStatus err = noErr; - err = PMSessionGetCGGraphicsContext(session, &cgContext); - if(err != noErr) { - qWarning("QMacPrintEngine::newPage: Cannot retrieve CoreGraphics context: %ld", long(err)); - state = QPrinter::Error; - return false; - } - cgEngine->d_func()->hd = cgContext; - - // Set the resolution as a scaling ration of 72 (the default). - CGContextScaleCTM(cgContext, 72 / resolution.hRes, 72 / resolution.vRes); - - CGContextScaleCTM(cgContext, 1, -1); - CGContextTranslateCTM(cgContext, 0, -paper.height()); - if (!fullPage) - CGContextTranslateCTM(cgContext, page.x() - paper.x(), page.y() - paper.y()); - cgEngine->d_func()->orig_xform = CGContextGetCTM(cgContext); - cgEngine->d_func()->setClip(0); - cgEngine->state->dirtyFlags = QPaintEngine::DirtyFlag(QPaintEngine::AllDirty - & ~(QPaintEngine::DirtyClipEnabled - | QPaintEngine::DirtyClipRegion - | QPaintEngine::DirtyClipPath)); - if (cgEngine->painter()->hasClipping()) - cgEngine->state->dirtyFlags |= QPaintEngine::DirtyClipEnabled; - cgEngine->syncState(); - return true; -} - - -void QMacPrintEngine::updateState(const QPaintEngineState &state) -{ - d_func()->paintEngine->updateState(state); -} - -void QMacPrintEngine::drawRects(const QRectF *r, int num) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawRects(r, num); -} - -void QMacPrintEngine::drawPoints(const QPointF *points, int pointCount) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawPoints(points, pointCount); -} - -void QMacPrintEngine::drawEllipse(const QRectF &r) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawEllipse(r); -} - -void QMacPrintEngine::drawLines(const QLineF *lines, int lineCount) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawLines(lines, lineCount); -} - -void QMacPrintEngine::drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawPolygon(points, pointCount, mode); -} - -void QMacPrintEngine::drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawPixmap(r, pm, sr); -} - -void QMacPrintEngine::drawImage(const QRectF &r, const QImage &pm, const QRectF &sr, Qt::ImageConversionFlags flags) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawImage(r, pm, sr, flags); -} - -void QMacPrintEngine::drawTextItem(const QPointF &p, const QTextItem &ti) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawTextItem(p, ti); -} - -void QMacPrintEngine::drawTiledPixmap(const QRectF &dr, const QPixmap &pixmap, const QPointF &sr) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawTiledPixmap(dr, pixmap, sr); -} - -void QMacPrintEngine::drawPath(const QPainterPath &path) -{ - Q_D(QMacPrintEngine); - Q_ASSERT(d->state == QPrinter::Active); - d->paintEngine->drawPath(path); -} - - -void QMacPrintEngine::setProperty(PrintEnginePropertyKey key, const QVariant &value) -{ - Q_D(QMacPrintEngine); - - d->valueCache.insert(key, value); - if (!d->session) - return; - - switch (key) { - case PPK_CollateCopies: - break; - case PPK_ColorMode: - break; - case PPK_Creator: - break; - case PPK_DocumentName: - break; - case PPK_PageOrder: - break; - case PPK_PaperSource: - break; - case PPK_SelectionOption: - break; - case PPK_Resolution: { - PMPrinter printer; - UInt32 count; - if (PMSessionGetCurrentPrinter(d->session, &printer) != noErr) - break; - if (PMPrinterGetPrinterResolutionCount(printer, &count) != noErr) - break; - PMResolution resolution = { 0.0, 0.0 }; - PMResolution bestResolution = { 0.0, 0.0 }; - int dpi = value.toInt(); - int bestDistance = INT_MAX; - for (UInt32 i = 1; i <= count; ++i) { // Yes, it starts at 1 - if (PMPrinterGetIndexedPrinterResolution(printer, i, &resolution) == noErr) { - if (dpi == int(resolution.hRes)) { - bestResolution = resolution; - break; - } else { - int distance = qAbs(dpi - int(resolution.hRes)); - if (distance < bestDistance) { - bestDistance = distance; - bestResolution = resolution; - } - } - } - } - PMSessionValidatePageFormat(d->session, d->format, kPMDontWantBoolean); - break; - } - - case PPK_FullPage: - d->fullPage = value.toBool(); - break; - case PPK_CopyCount: // fallthrough - case PPK_NumberOfCopies: - PMSetCopies(d->settings, value.toInt(), false); - break; - case PPK_Orientation: { - if (d->state == QPrinter::Active) { - qWarning("QMacPrintEngine::setOrientation: Orientation cannot be changed during a print job, ignoring change"); - } else { - QPrinter::Orientation newOrientation = QPrinter::Orientation(value.toInt()); - if (d->hasCustomPaperSize && (d->orient != newOrientation)) - d->customSize = QSizeF(d->customSize.height(), d->customSize.width()); - d->orient = newOrientation; - PMOrientation o = d->orient == QPrinter::Portrait ? kPMPortrait : kPMLandscape; - PMSetOrientation(d->format, o, false); - PMSessionValidatePageFormat(d->session, d->format, kPMDontWantBoolean); - } - break; } - case PPK_OutputFileName: - d->outputFilename = value.toString(); - break; - case PPK_PaperSize: - d->setPaperSize(QPrinter::PaperSize(value.toInt())); - break; - case PPK_PrinterName: { - bool printerNameSet = false; - OSStatus status = noErr; - QCFType printerList; - status = PMServerCreatePrinterList(kPMServerLocal, &printerList); - if (status == noErr) { - CFIndex count = CFArrayGetCount(printerList); - for (CFIndex i=0; i(const_cast(CFArrayGetValueAtIndex(printerList, i))); - QString name = QCFString::toQString(PMPrinterGetName(printer)); - if (name == value.toString()) { - status = PMSessionSetCurrentPMPrinter(d->session, printer); - printerNameSet = true; - break; - } - } - } - if (status != noErr) - qWarning("QMacPrintEngine::setPrinterName: Error setting printer: %ld", long(status)); - if (!printerNameSet) { - qWarning("QMacPrintEngine::setPrinterName: Failed to set printer named '%s'.", qPrintable(value.toString())); - d->releaseSession(); - d->state = QPrinter::Idle; - } - break; } - case PPK_SuppressSystemPrintStatus: - d->suppressStatus = value.toBool(); - break; - case PPK_CustomPaperSize: - { - PMOrientation orientation; - PMGetOrientation(d->format, &orientation); - d->hasCustomPaperSize = true; - d->customSize = value.toSizeF(); - if (orientation != kPMPortrait) - d->customSize = QSizeF(d->customSize.height(), d->customSize.width()); - break; - } - case PPK_PageMargins: - { - QList margins(value.toList()); - Q_ASSERT(margins.size() == 4); - d->leftMargin = margins.at(0).toDouble(); - d->topMargin = margins.at(1).toDouble(); - d->rightMargin = margins.at(2).toDouble(); - d->bottomMargin = margins.at(3).toDouble(); - d->hasCustomPageMargins = true; - break; - } - - default: - break; - } -} - -QVariant QMacPrintEngine::property(PrintEnginePropertyKey key) const -{ - Q_D(const QMacPrintEngine); - QVariant ret; - - if (!d->session && d->valueCache.contains(key)) - return *d->valueCache.find(key); - - switch (key) { - case PPK_CollateCopies: - ret = false; - break; - case PPK_ColorMode: - ret = QPrinter::Color; - break; - case PPK_Creator: - break; - case PPK_DocumentName: - break; - case PPK_FullPage: - ret = d->fullPage; - break; - case PPK_NumberOfCopies: - ret = 1; - break; - case PPK_CopyCount: { - UInt32 copies = 1; - PMGetCopies(d->settings, &copies); - ret = (uint) copies; - break; - } - case PPK_SupportsMultipleCopies: - ret = true; - break; - case PPK_Orientation: - PMOrientation orientation; - PMGetOrientation(d->format, &orientation); - ret = orientation == kPMPortrait ? QPrinter::Portrait : QPrinter::Landscape; - break; - case PPK_OutputFileName: - ret = d->outputFilename; - break; - case PPK_PageOrder: - break; - case PPK_PaperSource: - break; - case PPK_PageRect: { - // PageRect is returned in device pixels - QRect r; - PMRect macrect, macpaper; - qreal hRatio = d->resolution.hRes / 72; - qreal vRatio = d->resolution.vRes / 72; - if (d->hasCustomPaperSize) { - r = QRect(0, 0, qRound(d->customSize.width() * hRatio), qRound(d->customSize.height() * vRatio)); - if (d->hasCustomPageMargins) { - r.adjust(qRound(d->leftMargin * hRatio), qRound(d->topMargin * vRatio), - -qRound(d->rightMargin * hRatio), -qRound(d->bottomMargin * vRatio)); - } else { - QList margins = property(QPrintEngine::PPK_PageMargins).toList(); - r.adjust(qRound(margins.at(0).toDouble() * hRatio), - qRound(margins.at(1).toDouble() * vRatio), - -qRound(margins.at(2).toDouble() * hRatio), - -qRound(margins.at(3).toDouble()) * vRatio); - } - } else if (PMGetAdjustedPageRect(d->format, ¯ect) == noErr - && PMGetAdjustedPaperRect(d->format, &macpaper) == noErr) - { - if (d->fullPage || d->hasCustomPageMargins) { - r.setCoords(int(macpaper.left * hRatio), int(macpaper.top * vRatio), - int(macpaper.right * hRatio), int(macpaper.bottom * vRatio)); - r.translate(-r.x(), -r.y()); - if (d->hasCustomPageMargins) { - r.adjust(qRound(d->leftMargin * hRatio), qRound(d->topMargin * vRatio), - -qRound(d->rightMargin * hRatio), -qRound(d->bottomMargin * vRatio)); - } - } else { - r.setCoords(int(macrect.left * hRatio), int(macrect.top * vRatio), - int(macrect.right * hRatio), int(macrect.bottom * vRatio)); - r.translate(int(-macpaper.left * hRatio), int(-macpaper.top * vRatio)); - } - } - ret = r; - break; } - case PPK_PaperSize: - ret = d->paperSize(); - break; - case PPK_PaperRect: { - QRect r; - PMRect macrect; - if (d->hasCustomPaperSize) { - r = QRect(0, 0, qRound(d->customSize.width()), qRound(d->customSize.height())); - } else if (PMGetAdjustedPaperRect(d->format, ¯ect) == noErr) { - qreal hRatio = d->resolution.hRes / 72; - qreal vRatio = d->resolution.vRes / 72; - r.setCoords(int(macrect.left * hRatio), int(macrect.top * vRatio), - int(macrect.right * hRatio), int(macrect.bottom * vRatio)); - r.translate(-r.x(), -r.y()); - } - ret = r; - break; } - case PPK_PrinterName: { - PMPrinter printer; - OSStatus status = PMSessionGetCurrentPrinter(d->session, &printer); - if (status != noErr) - qWarning("QMacPrintEngine::printerName: Failed getting current PMPrinter: %ld", long(status)); - if (printer) - ret = QCFString::toQString(PMPrinterGetName(printer)); - break; } - case PPK_Resolution: { - ret = d->resolution.hRes; - break; - } - case PPK_SupportedResolutions: - ret = d->supportedResolutions(); - break; - case PPK_CustomPaperSize: - ret = d->customSize; - break; - case PPK_PageMargins: - { - QList margins; - if (d->hasCustomPageMargins) { - margins << d->leftMargin << d->topMargin - << d->rightMargin << d->bottomMargin; - } else { - PMPaperMargins paperMargins; - PMPaper paper; - PMGetPageFormatPaper(d->format, &paper); - PMPaperGetMargins(paper, &paperMargins); - margins << paperMargins.left << paperMargins.top - << paperMargins.right << paperMargins.bottom; - } - ret = margins; - break; - } - default: - break; - } - return ret; -} - -QT_END_NAMESPACE - -#endif // QT_NO_PRINTER diff --git a/src/widgets/platforms/mac/qprintengine_mac_p.h b/src/widgets/platforms/mac/qprintengine_mac_p.h deleted file mode 100644 index 349dfd1..0000000 --- a/src/widgets/platforms/mac/qprintengine_mac_p.h +++ /dev/null @@ -1,162 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -#ifndef QPRINTENGINE_MAC_P_H -#define QPRINTENGINE_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists purely as an -// implementation detail. This header file may change from version to -// version without notice, or even be removed. -// -// We mean it. -// - -#ifndef QT_NO_PRINTER - -#include "QtGui/qprinter.h" -#include "QtGui/qprintengine.h" -#include "private/qpaintengine_mac_p.h" -#include "private/qpainter_p.h" - -#ifdef __OBJC__ -@class NSPrintInfo; -#else -typedef void NSPrintInfo; -#endif - -QT_BEGIN_NAMESPACE - -class QPrinterPrivate; -class QMacPrintEnginePrivate; -class QMacPrintEngine : public QPaintEngine, public QPrintEngine -{ - Q_DECLARE_PRIVATE(QMacPrintEngine) -public: - QMacPrintEngine(QPrinter::PrinterMode mode); - - Qt::HANDLE handle() const; - - bool begin(QPaintDevice *dev); - bool end(); - virtual QPaintEngine::Type type() const { return QPaintEngine::MacPrinter; } - - QPaintEngine *paintEngine() const; - - void setProperty(PrintEnginePropertyKey key, const QVariant &value); - QVariant property(PrintEnginePropertyKey key) const; - - QPrinter::PrinterState printerState() const; - - bool newPage(); - bool abort(); - int metric(QPaintDevice::PaintDeviceMetric) const; - - //forwarded functions - - void updateState(const QPaintEngineState &state); - - virtual void drawLines(const QLineF *lines, int lineCount); - virtual void drawRects(const QRectF *r, int num); - virtual void drawPoints(const QPointF *p, int pointCount); - virtual void drawEllipse(const QRectF &r); - virtual void drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode); - virtual void drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr); - virtual void drawImage(const QRectF &r, const QImage &pm, const QRectF &sr, Qt::ImageConversionFlags flags); - virtual void drawTextItem(const QPointF &p, const QTextItem &ti); - virtual void drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, const QPointF &s); - virtual void drawPath(const QPainterPath &); - -private: - friend class QPrintDialog; - friend class QPageSetupDialog; -}; - -class QMacPrintEnginePrivate : public QPaintEnginePrivate -{ - Q_DECLARE_PUBLIC(QMacPrintEngine) -public: - QPrinter::PrinterMode mode; - QPrinter::PrinterState state; - QPrinter::Orientation orient; - NSPrintInfo *printInfo; - PMPageFormat format; - PMPrintSettings settings; - PMPrintSession session; - PMResolution resolution; - QString outputFilename; - bool fullPage; - QPaintEngine *paintEngine; - bool suppressStatus; - bool hasCustomPaperSize; - QSizeF customSize; - bool hasCustomPageMargins; - qreal leftMargin; - qreal topMargin; - qreal rightMargin; - qreal bottomMargin; - QHash valueCache; - QMacPrintEnginePrivate() : mode(QPrinter::ScreenResolution), state(QPrinter::Idle), - orient(QPrinter::Portrait), printInfo(0), format(0), settings(0), - session(0), paintEngine(0), suppressStatus(false), - hasCustomPaperSize(false), hasCustomPageMargins(false) {} - ~QMacPrintEnginePrivate(); - void initialize(); - void releaseSession(); - bool newPage_helper(); - void setPaperSize(QPrinter::PaperSize ps); - QPrinter::PaperSize paperSize() const; - QList supportedResolutions() const; - inline bool isPrintSessionInitialized() const - { - return printInfo != 0; - } - bool shouldSuppressStatus() const; -}; - -QT_END_NAMESPACE - -#endif // QT_NO_PRINTER - -#endif // QPRINTENGINE_WIN_P_H diff --git a/src/widgets/platforms/mac/qprinterinfo_mac.cpp b/src/widgets/platforms/mac/qprinterinfo_mac.cpp deleted file mode 100644 index 98492a5..0000000 --- a/src/widgets/platforms/mac/qprinterinfo_mac.cpp +++ /dev/null @@ -1,120 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 "qprinterinfo.h" -#include "qprinterinfo_p.h" - -#include "private/qt_mac_p.h" - -QT_BEGIN_NAMESPACE - -#ifndef QT_NO_PRINTER - -extern QPrinter::PaperSize qSizeFTopaperSize(const QSizeF &size); - -QList QPrinterInfo::availablePrinters() -{ - QList printers; - - QCFType array; - if (PMServerCreatePrinterList(kPMServerLocal, &array) == noErr) { - CFIndex count = CFArrayGetCount(array); - for (int i = 0; i < count; ++i) { - PMPrinter printer = static_cast(const_cast(CFArrayGetValueAtIndex(array, i))); - QString printerName = QCFString::toQString(PMPrinterGetName(printer)); - - QPrinterInfo printerInfo(printerName); - if (PMPrinterIsDefault(printer)) - printerInfo.d_ptr->isDefault = true; - printers.append(printerInfo); - } - } - - return printers; -} - -QPrinterInfo QPrinterInfo::defaultPrinter() -{ - QList printers = availablePrinters(); - foreach (const QPrinterInfo &printerInfo, printers) { - if (printerInfo.isDefault()) - return printerInfo; - } - - return printers.value(0); -} - -QList QPrinterInfo::supportedPaperSizes() const -{ - const Q_D(QPrinterInfo); - - QList paperSizes; - if (isNull()) - return paperSizes; - - PMPrinter cfPrn = PMPrinterCreateFromPrinterID(QCFString::toCFStringRef(d->name)); - if (!cfPrn) - return paperSizes; - - CFArrayRef array; - if (PMPrinterGetPaperList(cfPrn, &array) != noErr) { - PMRelease(cfPrn); - return paperSizes; - } - - int count = CFArrayGetCount(array); - for (int i = 0; i < count; ++i) { - PMPaper paper = static_cast(const_cast(CFArrayGetValueAtIndex(array, i))); - double width, height; - if (PMPaperGetWidth(paper, &width) == noErr && PMPaperGetHeight(paper, &height) == noErr) { - QSizeF size(width * 0.3527, height * 0.3527); - paperSizes.append(qSizeFTopaperSize(size)); - } - } - - PMRelease(cfPrn); - - return paperSizes; -} - -#endif // QT_NO_PRINTER - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qregion_mac.cpp b/src/widgets/platforms/mac/qregion_mac.cpp deleted file mode 100644 index 71e7a3b..0000000 --- a/src/widgets/platforms/mac/qregion_mac.cpp +++ /dev/null @@ -1,50 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include "qcoreapplication.h" -#include - -QT_BEGIN_NAMESPACE - -QRegion::QRegionData QRegion::shared_empty = { Q_BASIC_ATOMIC_INITIALIZER(1), 0 }; - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qt_cocoa_helpers_mac.mm b/src/widgets/platforms/mac/qt_cocoa_helpers_mac.mm deleted file mode 100644 index 348b989..0000000 --- a/src/widgets/platforms/mac/qt_cocoa_helpers_mac.mm +++ /dev/null @@ -1,1438 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -QT_BEGIN_NAMESPACE - -// Cmd + left mousebutton should produce a right button -// press (mainly for mac users with one-button mice): -static bool qt_leftButtonIsRightButton = false; - -Q_GLOBAL_STATIC(QMacWindowFader, macwindowFader); - -QMacWindowFader::QMacWindowFader() - : m_duration(0.250) -{ -} - -QMacWindowFader *QMacWindowFader::currentFader() -{ - return macwindowFader(); -} - -void QMacWindowFader::registerWindowToFade(QWidget *window) -{ - m_windowsToFade.append(window); -} - -void QMacWindowFader::performFade() -{ - const QWidgetList myWidgetsToFade = m_windowsToFade; - const int widgetCount = myWidgetsToFade.count(); - QMacCocoaAutoReleasePool pool; - [NSAnimationContext beginGrouping]; - [[NSAnimationContext currentContext] setDuration:NSTimeInterval(m_duration)]; - - for (int i = 0; i < widgetCount; ++i) { - QWidget *widget = m_windowsToFade.at(i); - OSWindowRef window = qt_mac_window_for(widget); - [[window animator] setAlphaValue:0.0]; - QTimer::singleShot(qRound(m_duration * 1000), widget, SLOT(hide())); - } - [NSAnimationContext endGrouping]; - m_duration = 0.250; - m_windowsToFade.clear(); -} - -extern bool qt_sendSpontaneousEvent(QObject *receiver, QEvent *event); // qapplication.cpp; -extern QWidget * mac_mouse_grabber; -extern QWidget *qt_button_down; //qapplication_mac.cpp -extern QPointer qt_last_mouse_receiver; -extern OSViewRef qt_mac_effectiveview_for(const QWidget *w); -extern void qt_mac_updateCursorWithWidgetUnderMouse(QWidget *widgetUnderMouse); // qcursor_mac.mm - -void macWindowFade(void * /*OSWindowRef*/ window, float durationSeconds) -{ - QMacCocoaAutoReleasePool pool; - OSWindowRef wnd = static_cast(window); - if (wnd) { - QWidget *widget; - widget = [wnd QT_MANGLE_NAMESPACE(qt_qwidget)]; - if (widget) { - QMacWindowFader::currentFader()->setFadeDuration(durationSeconds); - QMacWindowFader::currentFader()->registerWindowToFade(widget); - QMacWindowFader::currentFader()->performFade(); - } - } -} -struct dndenum_mapper -{ - NSDragOperation mac_code; - Qt::DropAction qt_code; - bool Qt2Mac; -}; - -#ifdef __OBJC__ - -static dndenum_mapper dnd_enums[] = { - { NSDragOperationLink, Qt::LinkAction, true }, - { NSDragOperationMove, Qt::MoveAction, true }, - { NSDragOperationCopy, Qt::CopyAction, true }, - { NSDragOperationGeneric, Qt::CopyAction, false }, - { NSDragOperationEvery, Qt::ActionMask, false }, - { NSDragOperationNone, Qt::IgnoreAction, false } -}; - -NSDragOperation qt_mac_mapDropAction(Qt::DropAction action) -{ - for (int i=0; dnd_enums[i].qt_code; i++) { - if (dnd_enums[i].Qt2Mac && (action & dnd_enums[i].qt_code)) { - return dnd_enums[i].mac_code; - } - } - return NSDragOperationNone; -} - -NSDragOperation qt_mac_mapDropActions(Qt::DropActions actions) -{ - NSDragOperation nsActions = NSDragOperationNone; - for (int i=0; dnd_enums[i].qt_code; i++) { - if (dnd_enums[i].Qt2Mac && (actions & dnd_enums[i].qt_code)) - nsActions |= dnd_enums[i].mac_code; - } - return nsActions; -} - -Qt::DropAction qt_mac_mapNSDragOperation(NSDragOperation nsActions) -{ - Qt::DropAction action = Qt::IgnoreAction; - for (int i=0; dnd_enums[i].mac_code; i++) { - if (nsActions & dnd_enums[i].mac_code) - return dnd_enums[i].qt_code; - } - return action; -} - -Qt::DropActions qt_mac_mapNSDragOperations(NSDragOperation nsActions) -{ - Qt::DropActions actions = Qt::IgnoreAction; - for (int i=0; dnd_enums[i].mac_code; i++) { - if (nsActions & dnd_enums[i].mac_code) - actions |= dnd_enums[i].qt_code; - } - return actions; -} - -Q_GLOBAL_STATIC(DnDParams, currentDnDParameters); -DnDParams *macCurrentDnDParameters() -{ - return currentDnDParameters(); -} -#endif - -void macWindowToolbarShow(const QWidget *widget, bool show ) -{ - OSWindowRef wnd = qt_mac_window_for(widget); - if (NSToolbar *toolbar = [wnd toolbar]) { - QMacCocoaAutoReleasePool pool; - if (show != [toolbar isVisible]) { - [toolbar setVisible:show]; - } else { - // The toolbar may be in sync, but we are not, update our framestrut. - qt_widget_private(const_cast(widget))->updateFrameStrut(); - } - } -} - - -void macWindowToolbarSet( void * /*OSWindowRef*/ window, void *toolbarRef ) -{ - OSWindowRef wnd = static_cast(window); - [wnd setToolbar:static_cast(toolbarRef)]; -} - -bool macWindowToolbarIsVisible( void * /*OSWindowRef*/ window ) -{ - OSWindowRef wnd = static_cast(window); - if (NSToolbar *toolbar = [wnd toolbar]) - return [toolbar isVisible]; - return false; -} - -void macWindowSetHasShadow( void * /*OSWindowRef*/ window, bool hasShadow ) -{ - OSWindowRef wnd = static_cast(window); - [wnd setHasShadow:BOOL(hasShadow)]; -} - -void macWindowFlush(void * /*OSWindowRef*/ window) -{ - OSWindowRef wnd = static_cast(window); - [wnd flushWindowIfNeeded]; -} - -void qt_mac_update_mouseTracking(QWidget *widget) -{ - [qt_mac_nativeview_for(widget) updateTrackingAreas]; -} - -OSStatus qt_mac_drawCGImage(CGContextRef inContext, const CGRect *inBounds, CGImageRef inImage) -{ - // Verbatim copy if HIViewDrawCGImage (as shown on Carbon-Dev) - OSStatus err = noErr; - - require_action(inContext != NULL, InvalidContext, err = paramErr); - require_action(inBounds != NULL, InvalidBounds, err = paramErr); - require_action(inImage != NULL, InvalidImage, err = paramErr); - - CGContextSaveGState( inContext ); - CGContextTranslateCTM (inContext, 0, inBounds->origin.y + CGRectGetMaxY(*inBounds)); - CGContextScaleCTM(inContext, 1, -1); - - CGContextDrawImage(inContext, *inBounds, inImage); - - CGContextRestoreGState(inContext); -InvalidImage: -InvalidBounds: -InvalidContext: - return err; -} - -bool qt_mac_checkForNativeSizeGrip(const QWidget *widget) -{ - return [[reinterpret_cast(widget->effectiveWinId()) window] showsResizeIndicator]; -} -struct qt_mac_enum_mapper -{ - int mac_code; - int qt_code; -#if defined(DEBUG_MOUSE_MAPS) -# define QT_MAC_MAP_ENUM(x) x, #x - const char *desc; -#else -# define QT_MAC_MAP_ENUM(x) x -#endif -}; - -//mouse buttons -static qt_mac_enum_mapper qt_mac_mouse_symbols[] = { -{ kEventMouseButtonPrimary, QT_MAC_MAP_ENUM(Qt::LeftButton) }, -{ kEventMouseButtonSecondary, QT_MAC_MAP_ENUM(Qt::RightButton) }, -{ kEventMouseButtonTertiary, QT_MAC_MAP_ENUM(Qt::MidButton) }, -{ 4, QT_MAC_MAP_ENUM(Qt::XButton1) }, -{ 5, QT_MAC_MAP_ENUM(Qt::XButton2) }, -{ 0, QT_MAC_MAP_ENUM(0) } -}; -Qt::MouseButtons qt_mac_get_buttons(int buttons) -{ -#ifdef DEBUG_MOUSE_MAPS - qDebug("Qt: internal: **Mapping buttons: %d (0x%04x)", buttons, buttons); -#endif - Qt::MouseButtons ret = Qt::NoButton; - for(int i = 0; qt_mac_mouse_symbols[i].qt_code; i++) { - if (buttons & (0x01<<(qt_mac_mouse_symbols[i].mac_code-1))) { -#ifdef DEBUG_MOUSE_MAPS - qDebug("Qt: internal: got button: %s", qt_mac_mouse_symbols[i].desc); -#endif - ret |= Qt::MouseButtons(qt_mac_mouse_symbols[i].qt_code); - } - } - return ret; -} -Qt::MouseButton qt_mac_get_button(EventMouseButton button) -{ -#ifdef DEBUG_MOUSE_MAPS - qDebug("Qt: internal: **Mapping button: %d (0x%04x)", button, button); -#endif - Qt::MouseButtons ret = 0; - for(int i = 0; qt_mac_mouse_symbols[i].qt_code; i++) { - if (button == qt_mac_mouse_symbols[i].mac_code) { -#ifdef DEBUG_MOUSE_MAPS - qDebug("Qt: internal: got button: %s", qt_mac_mouse_symbols[i].desc); -#endif - return Qt::MouseButton(qt_mac_mouse_symbols[i].qt_code); - } - } - return Qt::NoButton; -} - -void macSendToolbarChangeEvent(QWidget *widget) -{ - QToolBarChangeEvent ev(!(GetCurrentKeyModifiers() & cmdKey)); - qt_sendSpontaneousEvent(widget, &ev); -} - -Q_GLOBAL_STATIC(QMacTabletHash, tablet_hash) -QMacTabletHash *qt_mac_tablet_hash() -{ - return tablet_hash(); -} - - -// Clears the QWidget pointer that each QCocoaView holds. -void qt_mac_clearCocoaViewQWidgetPointers(QWidget *widget) -{ - QT_MANGLE_NAMESPACE(QCocoaView) *cocoaView = reinterpret_cast(qt_mac_nativeview_for(widget)); - if (cocoaView && [cocoaView respondsToSelector:@selector(qt_qwidget)]) { - [cocoaView qt_clearQWidget]; - } -} - -void qt_dispatchTabletProximityEvent(void * /*NSEvent * */ tabletEvent) -{ - NSEvent *proximityEvent = static_cast(tabletEvent); - // simply construct a Carbon proximity record and handle it all in one spot. - TabletProximityRec carbonProximityRec = { [proximityEvent vendorID], - [proximityEvent tabletID], - [proximityEvent pointingDeviceID], - [proximityEvent deviceID], - [proximityEvent systemTabletID], - [proximityEvent vendorPointingDeviceType], - [proximityEvent pointingDeviceSerialNumber], - [proximityEvent uniqueID], - [proximityEvent capabilityMask], - [proximityEvent pointingDeviceType], - [proximityEvent isEnteringProximity] }; - qt_dispatchTabletProximityEvent(carbonProximityRec); -} - -void qt_dispatchTabletProximityEvent(const ::TabletProximityRec &proxRec) -{ - QTabletDeviceData proximityDevice; - proximityDevice.tabletUniqueID = proxRec.uniqueID; - proximityDevice.capabilityMask = proxRec.capabilityMask; - - switch (proxRec.pointerType) { - case NSUnknownPointingDevice: - default: - proximityDevice.tabletPointerType = QTabletEvent::UnknownPointer; - break; - case NSPenPointingDevice: - proximityDevice.tabletPointerType = QTabletEvent::Pen; - break; - case NSCursorPointingDevice: - proximityDevice.tabletPointerType = QTabletEvent::Cursor; - break; - case NSEraserPointingDevice: - proximityDevice.tabletPointerType = QTabletEvent::Eraser; - break; - } - uint bits = proxRec.vendorPointerType; - if (bits == 0 && proximityDevice.tabletUniqueID != 0) { - // Fallback. It seems that the driver doesn't always include all the information. - // High-End Wacom devices store their "type" in the uper bits of the Unique ID. - // I'm not sure how to handle it for consumer devices, but I'll test that in a bit. - bits = proximityDevice.tabletUniqueID >> 32; - } - // Defined in the "EN0056-NxtGenImpGuideX" - // on Wacom's Developer Website (www.wacomeng.com) - if (((bits & 0x0006) == 0x0002) && ((bits & 0x0F06) != 0x0902)) { - proximityDevice.tabletDeviceType = QTabletEvent::Stylus; - } else { - switch (bits & 0x0F06) { - case 0x0802: - proximityDevice.tabletDeviceType = QTabletEvent::Stylus; - break; - case 0x0902: - proximityDevice.tabletDeviceType = QTabletEvent::Airbrush; - break; - case 0x0004: - proximityDevice.tabletDeviceType = QTabletEvent::FourDMouse; - break; - case 0x0006: - proximityDevice.tabletDeviceType = QTabletEvent::Puck; - break; - case 0x0804: - proximityDevice.tabletDeviceType = QTabletEvent::RotationStylus; - break; - default: - proximityDevice.tabletDeviceType = QTabletEvent::NoDevice; - } - } - // The deviceID is "unique" while in the proximity, it's a key that we can use for - // linking up TabletDeviceData to an event (especially if there are two devices in action). - bool entering = proxRec.enterProximity; - if (entering) { - qt_mac_tablet_hash()->insert(proxRec.deviceID, proximityDevice); - } else { - qt_mac_tablet_hash()->remove(proxRec.deviceID); - } - - QTabletEvent qtabletProximity(entering ? QEvent::TabletEnterProximity - : QEvent::TabletLeaveProximity, - QPoint(), QPoint(), QPointF(), proximityDevice.tabletDeviceType, - proximityDevice.tabletPointerType, 0., 0, 0, 0., 0., 0, 0, - proximityDevice.tabletUniqueID); - - qt_sendSpontaneousEvent(qApp, &qtabletProximity); -} - - -Qt::KeyboardModifiers qt_cocoaModifiers2QtModifiers(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; -} - -Qt::KeyboardModifiers qt_cocoaDragOperation2QtModifiers(uint dragOperations) -{ - Qt::KeyboardModifiers qtMods =Qt::NoModifier; - if (dragOperations & NSDragOperationLink) - qtMods |= Qt::MetaModifier; - if (dragOperations & NSDragOperationGeneric) - qtMods |= Qt::ControlModifier; - if (dragOperations & NSDragOperationCopy) - qtMods |= Qt::AltModifier; - return qtMods; -} - -static inline QEvent::Type cocoaEvent2QtEvent(NSUInteger eventType) -{ - // Handle the trivial cases that can be determined from the type. - switch (eventType) { - case NSKeyDown: - return QEvent::KeyPress; - case NSKeyUp: - return QEvent::KeyRelease; - case NSLeftMouseDown: - case NSRightMouseDown: - case NSOtherMouseDown: - return QEvent::MouseButtonPress; - case NSLeftMouseUp: - case NSRightMouseUp: - case NSOtherMouseUp: - return QEvent::MouseButtonRelease; - case NSMouseMoved: - case NSLeftMouseDragged: - case NSRightMouseDragged: - case NSOtherMouseDragged: - return QEvent::MouseMove; - case NSScrollWheel: - return QEvent::Wheel; - } - return QEvent::None; -} - -static bool mustUseCocoaKeyEvent() -{ - QCFType source = TISCopyCurrentKeyboardInputSource(); - return TISGetInputSourceProperty(source, kTISPropertyUnicodeKeyLayoutData) == 0; -} - -bool qt_dispatchKeyEventWithCocoa(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent) -{ - NSEvent *event = static_cast(keyEvent); - NSString *keyChars = [event charactersIgnoringModifiers]; - int keyLength = [keyChars length]; - if (keyLength == 0) - return false; // Dead Key, nothing to do! - bool ignoreText = false; - Qt::Key qtKey = Qt::Key_unknown; - if (keyLength == 1) { - QChar ch([keyChars characterAtIndex:0]); - if (ch.isLower()) - ch = ch.toUpper(); - qtKey = cocoaKey2QtKey(ch); - // Do not set the text for Function-Key Unicodes characters (0xF700–0xF8FF). - ignoreText = (ch.unicode() >= 0xF700 && ch.unicode() <= 0xF8FF); - } - Qt::KeyboardModifiers keyMods = qt_cocoaModifiers2QtModifiers([event modifierFlags]); - QString text; - - // To quote from the Carbon port: This is actually wrong--but it is the best that - // can be done for now because of the Control/Meta mapping issues - // (we always get text on the Mac) - if (!ignoreText && !(keyMods & (Qt::ControlModifier | Qt::MetaModifier))) - text = QCFString::toQString(reinterpret_cast(keyChars)); - - UInt32 macScanCode = 1; - QKeyEventEx ke(cocoaEvent2QtEvent([event type]), qtKey, keyMods, text, [event isARepeat], qMax(1, keyLength), - macScanCode, [event keyCode], [event modifierFlags]); - return qt_sendSpontaneousEvent(widgetToGetEvent, &ke) && ke.isAccepted(); -} - -Qt::MouseButton cocoaButton2QtButton(NSInteger buttonNum) -{ - if (buttonNum == 0) - return Qt::LeftButton; - if (buttonNum == 1) - return Qt::RightButton; - if (buttonNum == 2) - return Qt::MidButton; - if (buttonNum == 3) - return Qt::XButton1; - if (buttonNum == 4) - return Qt::XButton2; - return Qt::NoButton; -} - -bool qt_dispatchKeyEvent(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent) -{ - NSEvent *event = static_cast(keyEvent); - EventRef key_event = static_cast(const_cast([event eventRef])); - Q_ASSERT(key_event); - unsigned int info = 0; - - if ([event type] == NSKeyDown) { - NSString *characters = [event characters]; - if ([characters length]) { - unichar value = [characters characterAtIndex:0]; - qt_keymapper_private()->updateKeyMap(0, key_event, (void *)&value); - info = value; - } - } - - if (qt_mac_sendMacEventToWidget(widgetToGetEvent, key_event)) - return true; - - if (mustUseCocoaKeyEvent()) - return qt_dispatchKeyEventWithCocoa(keyEvent, widgetToGetEvent); - - bool consumed = qt_keymapper_private()->translateKeyEvent(widgetToGetEvent, 0, key_event, &info, true); - return consumed && (info != 0); -} - -void qt_dispatchModifiersChanged(void * /*NSEvent * */flagsChangedEvent, QWidget *widgetToGetEvent) -{ - UInt32 modifiers = 0; - // Sync modifiers with Qt - NSEvent *event = static_cast(flagsChangedEvent); - EventRef key_event = static_cast(const_cast([event eventRef])); - Q_ASSERT(key_event); - GetEventParameter(key_event, kEventParamKeyModifiers, typeUInt32, 0, - sizeof(modifiers), 0, &modifiers); - extern void qt_mac_send_modifiers_changed(quint32 modifiers, QObject *object); - qt_mac_send_modifiers_changed(modifiers, widgetToGetEvent); -} - -QPointF flipPoint(const NSPoint &p) -{ - return QPointF(p.x, flipYCoordinate(p.y)); -} - -NSPoint flipPoint(const QPoint &p) -{ - return NSMakePoint(p.x(), flipYCoordinate(p.y())); -} - -NSPoint flipPoint(const QPointF &p) -{ - return NSMakePoint(p.x(), flipYCoordinate(p.y())); -} - -#ifdef __OBJC__ - -void qt_mac_handleNonClientAreaMouseEvent(NSWindow *window, NSEvent *event) -{ - QWidget *widgetToGetEvent = [window QT_MANGLE_NAMESPACE(qt_qwidget)]; - if (widgetToGetEvent == 0) - return; - - NSEventType evtType = [event type]; - QPoint qlocalPoint; - QPoint qglobalPoint; - bool processThisEvent = false; - bool fakeNCEvents = false; - bool fakeMouseEvents = false; - - // Check if this is a mouse event. - if (evtType == NSLeftMouseDown || evtType == NSLeftMouseUp - || evtType == NSRightMouseDown || evtType == NSRightMouseUp - || evtType == NSOtherMouseDown || evtType == NSOtherMouseUp - || evtType == NSMouseMoved || evtType == NSLeftMouseDragged - || evtType == NSRightMouseDragged || evtType == NSOtherMouseDragged) { - // Check if we want to pass this message to another window - if (mac_mouse_grabber && mac_mouse_grabber != widgetToGetEvent) { - NSWindow *grabWindow = static_cast(qt_mac_window_for(mac_mouse_grabber)); - if (window != grabWindow) { - window = grabWindow; - widgetToGetEvent = mac_mouse_grabber; - fakeNCEvents = true; - } - } - // Dont generate normal NC mouse events for Left Button dragged - if(evtType != NSLeftMouseDragged || fakeNCEvents) { - NSPoint windowPoint = [event locationInWindow]; - NSPoint globalPoint = [[event window] convertBaseToScreen:windowPoint]; - NSRect frameRect = [window frame]; - if (fakeNCEvents || NSMouseInRect(globalPoint, frameRect, NO)) { - NSRect contentRect = [window contentRectForFrameRect:frameRect]; - qglobalPoint = QPoint(flipPoint(globalPoint).toPoint()); - QWidget *w = widgetToGetEvent->childAt(widgetToGetEvent->mapFromGlobal(qglobalPoint)); - // check that the mouse pointer is on the non-client area and - // there are not widgets in it. - if (fakeNCEvents || (!NSMouseInRect(globalPoint, contentRect, NO) && !w)) { - qglobalPoint = QPoint(flipPoint(globalPoint).toPoint()); - qlocalPoint = widgetToGetEvent->mapFromGlobal(qglobalPoint); - processThisEvent = true; - } - } - } - } - // This is not an NC area mouse message. - if (!processThisEvent) - return; - - // If the window is frame less, generate fake mouse events instead. (floating QToolBar) - // or if someone already got an explicit or implicit grab - if (mac_mouse_grabber || qt_button_down || - (fakeNCEvents && (widgetToGetEvent->window()->windowFlags() & Qt::FramelessWindowHint))) - fakeMouseEvents = true; - - Qt::MouseButton button; - QEvent::Type eventType; - // Convert to Qt::Event type - switch (evtType) { - case NSLeftMouseDown: - button = Qt::LeftButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonPress - : QEvent::MouseButtonPress; - break; - case NSLeftMouseUp: - button = Qt::LeftButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonRelease - : QEvent::MouseButtonRelease; - break; - case NSRightMouseDown: - button = Qt::RightButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonPress - : QEvent::MouseButtonPress; - break; - case NSRightMouseUp: - button = Qt::RightButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonRelease - : QEvent::MouseButtonRelease; - break; - case NSOtherMouseDown: - button = cocoaButton2QtButton([event buttonNumber]); - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonPress - : QEvent::MouseButtonPress; - break; - case NSOtherMouseUp: - button = cocoaButton2QtButton([event buttonNumber]); - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonRelease - : QEvent::MouseButtonRelease; - break; - case NSMouseMoved: - button = Qt::NoButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseMove - : QEvent::MouseMove; - break; - case NSLeftMouseDragged: - button = Qt::LeftButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseMove - : QEvent::MouseMove; - break; - case NSRightMouseDragged: - button = Qt::RightButton; - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseMove - : QEvent::MouseMove; - break; - case NSOtherMouseDragged: - button = cocoaButton2QtButton([event buttonNumber]); - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseMove - : QEvent::MouseMove; - break; - default: - qWarning("not handled! Non client area mouse message"); - return; - } - - Qt::KeyboardModifiers keyMods = qt_cocoaModifiers2QtModifiers([event modifierFlags]); - if (eventType == QEvent::NonClientAreaMouseButtonPress || eventType == QEvent::MouseButtonPress) { - NSInteger clickCount = [event clickCount]; - if (clickCount % 2 == 0) - eventType = (!fakeMouseEvents) ? QEvent::NonClientAreaMouseButtonDblClick - : QEvent::MouseButtonDblClick; - if (button == Qt::LeftButton && (keyMods & Qt::MetaModifier)) { - button = Qt::RightButton; - qt_leftButtonIsRightButton = true; - } - } else if (eventType == QEvent::NonClientAreaMouseButtonRelease || eventType == QEvent::MouseButtonRelease) { - if (button == Qt::LeftButton && qt_leftButtonIsRightButton) { - button = Qt::RightButton; - qt_leftButtonIsRightButton = false; - } - } - - Qt::MouseButtons buttons = 0; - { - UInt32 mac_buttons; - if (GetEventParameter((EventRef)[event eventRef], kEventParamMouseChord, typeUInt32, 0, - sizeof(mac_buttons), 0, &mac_buttons) == noErr) - buttons = qt_mac_get_buttons(mac_buttons); - } - - QMouseEvent qme(eventType, qlocalPoint, qglobalPoint, button, buttons, keyMods); - qt_sendSpontaneousEvent(widgetToGetEvent, &qme); - - // We don't need to set the implicit grab widget here because we won't - // reach this point if then event type is Press over a Qt widget. - // However we might need to unset it if the event is Release. - if (eventType == QEvent::MouseButtonRelease) - qt_button_down = 0; -} - -QWidget *qt_mac_getTargetForKeyEvent(QWidget *widgetThatReceivedEvent) -{ - if (QWidget *popup = QApplication::activePopupWidget()) { - QWidget *focusInPopup = popup->focusWidget(); - return focusInPopup ? focusInPopup : popup; - } - - QWidget *widgetToGetKey = qApp->focusWidget(); - if (!widgetToGetKey) - widgetToGetKey = widgetThatReceivedEvent; - - return widgetToGetKey; -} - -// This function will find the widget that should receive the -// mouse event. Because of explicit/implicit mouse grabs, popups, -// etc, this might not end up being the same as the widget under -// the mouse (which is more interresting when handling enter/leave -// events -QWidget *qt_mac_getTargetForMouseEvent( - // You can call this function without providing an event. - NSEvent *event, - QEvent::Type eventType, - QPoint &returnLocalPoint, - QPoint &returnGlobalPoint, - QWidget *nativeWidget, - QWidget **returnWidgetUnderMouse) -{ - Q_UNUSED(event); - NSPoint nsglobalpoint = event ? [[event window] convertBaseToScreen:[event locationInWindow]] : [NSEvent mouseLocation]; - returnGlobalPoint = flipPoint(nsglobalpoint).toPoint(); - QWidget *mouseGrabber = QWidget::mouseGrabber(); - bool buttonDownNotBlockedByModal = qt_button_down && !QApplicationPrivate::isBlockedByModal(qt_button_down); - QWidget *popup = QApplication::activePopupWidget(); - - // Resolve the widget under the mouse: - QWidget *widgetUnderMouse = 0; - if (popup || qt_button_down || !nativeWidget || !nativeWidget->isVisible()) { - // Using QApplication::widgetAt for finding the widget under the mouse - // is most safe, since it ignores cocoas own mouse down redirections (which - // we need to be prepared for when using nativeWidget as starting point). - // (the only exception is for QMacNativeWidget, where QApplication::widgetAt fails). - // But it is also slower (I guess), so we try to avoid it and use nativeWidget if we can: - widgetUnderMouse = QApplication::widgetAt(returnGlobalPoint); - } - - if (!widgetUnderMouse && nativeWidget) { - // Entering here should be the common case. We - // also handle the QMacNativeWidget fallback case. - QPoint p = nativeWidget->mapFromGlobal(returnGlobalPoint); - widgetUnderMouse = nativeWidget->childAt(p); - if (!widgetUnderMouse && nativeWidget->rect().contains(p)) - widgetUnderMouse = nativeWidget; - } - - if (widgetUnderMouse) { - // Check if widgetUnderMouse is blocked by a modal - // window, or the mouse if over the frame strut: - if (widgetUnderMouse == qt_button_down) { - // Small optimization to avoid an extra call to isBlockedByModal: - if (buttonDownNotBlockedByModal == false) - widgetUnderMouse = 0; - } else if (QApplicationPrivate::isBlockedByModal(widgetUnderMouse)) { - widgetUnderMouse = 0; - } - - if (widgetUnderMouse && widgetUnderMouse->isWindow()) { - // Exclude the titlebar (and frame strut) when finding widget under mouse: - QPoint p = widgetUnderMouse->mapFromGlobal(returnGlobalPoint); - if (!widgetUnderMouse->rect().contains(p)) - widgetUnderMouse = 0; - } - } - if (returnWidgetUnderMouse) - *returnWidgetUnderMouse = widgetUnderMouse; - - // Resolve the target for the mouse event. Default will be - // widgetUnderMouse, except if there is a grab (popup/mouse/button-down): - if (popup && !mouseGrabber) { - // We special case handling of popups, since they have an implicitt mouse grab. - QWidget *candidate = buttonDownNotBlockedByModal ? qt_button_down : widgetUnderMouse; - if (!popup->isAncestorOf(candidate)) { - // INVARIANT: we have a popup, but the candidate is not - // in it. But the popup will grab the mouse anyway, - // except if the user scrolls: - if (eventType == QEvent::Wheel) - return 0; - returnLocalPoint = popup->mapFromGlobal(returnGlobalPoint); - return popup; - } else if (popup == candidate) { - // INVARIANT: The candidate is the popup itself, and not a child: - returnLocalPoint = popup->mapFromGlobal(returnGlobalPoint); - return popup; - } else { - // INVARIANT: The candidate is a child inside the popup: - returnLocalPoint = candidate->mapFromGlobal(returnGlobalPoint); - return candidate; - } - } - - QWidget *target = mouseGrabber; - if (!target && buttonDownNotBlockedByModal) - target = qt_button_down; - if (!target) - target = widgetUnderMouse; - if (!target) - return 0; - - returnLocalPoint = target->mapFromGlobal(returnGlobalPoint); - return target; -} - -QPointer qt_last_native_mouse_receiver = 0; - -static inline void qt_mac_checkEnterLeaveForNativeWidgets(QWidget *maybeEnterWidget) -{ - // Dispatch enter/leave for the cases where QApplicationPrivate::sendMouseEvent do - // not. This will in general be the cases when alien widgets are not involved: - // 1. from a native widget to another native widget or - // 2. from a native widget to no widget - // 3. from no widget to a native or alien widget - - if (qt_button_down || QWidget::mouseGrabber()) - return; - - if ((maybeEnterWidget == qt_last_native_mouse_receiver) && qt_last_native_mouse_receiver) - return; - if (maybeEnterWidget) { - if (!qt_last_native_mouse_receiver) { - // case 3 - QApplicationPrivate::dispatchEnterLeave(maybeEnterWidget, 0); - qt_last_native_mouse_receiver = maybeEnterWidget->internalWinId() ? maybeEnterWidget : maybeEnterWidget->nativeParentWidget(); - } else if (maybeEnterWidget->internalWinId()) { - // case 1 - QApplicationPrivate::dispatchEnterLeave(maybeEnterWidget, qt_last_native_mouse_receiver); - qt_last_native_mouse_receiver = maybeEnterWidget->internalWinId() ? maybeEnterWidget : maybeEnterWidget->nativeParentWidget(); - } // else at lest one of the widgets are alien, so enter/leave will be handled in QApplicationPrivate - } else { - if (qt_last_native_mouse_receiver) { - // case 2 - QApplicationPrivate::dispatchEnterLeave(0, qt_last_native_mouse_receiver); - qt_last_mouse_receiver = 0; - qt_last_native_mouse_receiver = 0; - } - } -} - -bool qt_mac_handleMouseEvent(NSEvent *event, QEvent::Type eventType, Qt::MouseButton button, QWidget *nativeWidget) -{ - // Give the Input Manager a chance to process the mouse events. - NSInputManager *currentIManager = [NSInputManager currentInputManager]; - if (currentIManager && [currentIManager wantsToHandleMouseEvents]) { - [currentIManager handleMouseEvent:event]; - } - - // Find the widget that should receive the event, and the widget under the mouse. Those - // can differ if an implicit or explicit mouse grab is active: - QWidget *widgetUnderMouse = 0; - QPoint localPoint, globalPoint; - QWidget *widgetToGetMouse = qt_mac_getTargetForMouseEvent(event, eventType, localPoint, globalPoint, nativeWidget, &widgetUnderMouse); - if (!widgetToGetMouse) - return false; - - // From here on, we let nativeWidget actually be the native widget under widgetUnderMouse. The reason - // for this, is that qt_mac_getTargetForMouseEvent will set cocoa's mouse event redirection aside when - // determining which widget is under the mouse (in other words, it will usually ignore nativeWidget). - // nativeWidget will be used in QApplicationPrivate::sendMouseEvent to correctly dispatch enter/leave events. - if (widgetUnderMouse) - nativeWidget = widgetUnderMouse->internalWinId() ? widgetUnderMouse : widgetUnderMouse->nativeParentWidget(); - if (!nativeWidget) - return false; - NSView *view = qt_mac_effectiveview_for(nativeWidget); - - // Handle tablet events (if any) first. - if (qt_mac_handleTabletEvent(view, event)) { - // Tablet event was handled. In Qt we aren't supposed to send the mouse event. - return true; - } - - EventRef carbonEvent = static_cast(const_cast([event eventRef])); - if (qt_mac_sendMacEventToWidget(widgetToGetMouse, carbonEvent)) - return true; - - // Keep previousButton to make sure we don't send double click - // events when the user double clicks using two different buttons: - static Qt::MouseButton previousButton = Qt::NoButton; - - Qt::KeyboardModifiers keyMods = qt_cocoaModifiers2QtModifiers([event modifierFlags]); - NSInteger clickCount = [event clickCount]; - Qt::MouseButtons buttons = 0; - { - UInt32 mac_buttons; - if (GetEventParameter(carbonEvent, kEventParamMouseChord, typeUInt32, 0, - sizeof(mac_buttons), 0, &mac_buttons) == noErr) - buttons = qt_mac_get_buttons(mac_buttons); - } - - // Send enter/leave events for the cases when QApplicationPrivate::sendMouseEvent do not: - qt_mac_checkEnterLeaveForNativeWidgets(widgetUnderMouse); - - switch (eventType) { - default: - qWarning("not handled! %d", eventType); - break; - case QEvent::MouseMove: - if (button == Qt::LeftButton && qt_leftButtonIsRightButton) - button = Qt::RightButton; - break; - case QEvent::MouseButtonPress: - qt_button_down = widgetUnderMouse; - if (clickCount % 2 == 0 && (previousButton == Qt::NoButton || previousButton == button)) - eventType = QEvent::MouseButtonDblClick; - if (button == Qt::LeftButton && (keyMods & Qt::MetaModifier)) { - button = Qt::RightButton; - qt_leftButtonIsRightButton = true; - } - break; - case QEvent::MouseButtonRelease: - if (button == Qt::LeftButton && qt_leftButtonIsRightButton) { - button = Qt::RightButton; - qt_leftButtonIsRightButton = false; - } - qt_button_down = 0; - break; - } - - qt_mac_updateCursorWithWidgetUnderMouse(widgetUnderMouse); - - DnDParams *dndParams = currentDnDParameters(); - dndParams->view = view; - dndParams->theEvent = event; - dndParams->globalPoint = globalPoint; - - // Send the mouse event: - QMouseEvent qme(eventType, localPoint, globalPoint, button, buttons, keyMods); - QApplicationPrivate::sendMouseEvent( - widgetToGetMouse, &qme, widgetUnderMouse, nativeWidget, - &qt_button_down, qt_last_mouse_receiver, true); - - if (eventType == QEvent::MouseButtonPress && button == Qt::RightButton) { - QContextMenuEvent qcme(QContextMenuEvent::Mouse, localPoint, globalPoint, keyMods); - qt_sendSpontaneousEvent(widgetToGetMouse, &qcme); - } - - if (eventType == QEvent::MouseButtonRelease) { - // A mouse button was released, which means that the implicit grab was - // released. We therefore need to re-check if should send (delayed) enter leave events: - // qt_button_down has now become NULL since the call at the top of the function. Also, since - // the relase might have closed a window, we dont give the nativeWidget hint - qt_mac_getTargetForMouseEvent(0, QEvent::None, localPoint, globalPoint, nativeWidget, &widgetUnderMouse); - qt_mac_checkEnterLeaveForNativeWidgets(widgetUnderMouse); - } - - previousButton = button; - return true; -} -#endif - -bool qt_mac_handleTabletEvent(void * /*QCocoaView * */view, void * /*NSEvent * */tabletEvent) -{ - QT_MANGLE_NAMESPACE(QCocoaView) *theView = static_cast(view); - NSView *theNSView = static_cast(view); - NSEvent *theTabletEvent = static_cast(tabletEvent); - - NSEventType eventType = [theTabletEvent type]; - if (eventType != NSTabletPoint && [theTabletEvent subtype] != NSTabletPointEventSubtype) - return false; // Not a tablet event. - - NSPoint windowPoint = [theTabletEvent locationInWindow]; - NSPoint globalPoint = [[theTabletEvent window] convertBaseToScreen:windowPoint]; - - QWidget *qwidget = [theView qt_qwidget]; - QWidget *widgetToGetMouse = qwidget; - QWidget *popup = qAppInstance()->activePopupWidget(); - if (popup && popup != qwidget->window()) - widgetToGetMouse = popup; - - if (qt_mac_sendMacEventToWidget(widgetToGetMouse, - static_cast(const_cast([theTabletEvent eventRef])))) - return true; - if (widgetToGetMouse != qwidget) { - theNSView = qt_mac_nativeview_for(widgetToGetMouse); - windowPoint = [[theNSView window] convertScreenToBase:globalPoint]; - } - NSPoint localPoint = [theNSView convertPoint:windowPoint fromView:nil]; - // Tablet events do not handle WA_TransparentForMouseEvents ATM - // In theory, people who set the WA_TransparentForMouseEvents attribute won't handle - // tablet events either in which case they will fall into the mouse event case and get - // them passed on. This will NOT handle the raw events, but that might not be a big problem. - - const QMacTabletHash *tabletHash = qt_mac_tablet_hash(); - if (!tabletHash->contains([theTabletEvent deviceID])) { - qWarning("QCocoaView handleTabletEvent: This tablet device is unknown" - " (received no proximity event for it). Discarding event."); - return false; - } - const QTabletDeviceData &deviceData = tabletHash->value([theTabletEvent deviceID]); - - - QEvent::Type qType; - switch (eventType) { - case NSLeftMouseDown: - case NSRightMouseDown: - qType = QEvent::TabletPress; - break; - case NSLeftMouseUp: - case NSRightMouseUp: - qType = QEvent::TabletRelease; - break; - case NSMouseMoved: - case NSTabletPoint: - case NSLeftMouseDragged: - case NSRightMouseDragged: - default: - qType = QEvent::TabletMove; - break; - } - - qreal pressure; - if (eventType != NSMouseMoved) { - pressure = [theTabletEvent pressure]; - } else { - pressure = 0.0; - } - - NSPoint tilt = [theTabletEvent tilt]; - int xTilt = qRound(tilt.x * 60.0); - int yTilt = qRound(tilt.y * -60.0); - qreal tangentialPressure = 0; - qreal rotation = 0; - int z = 0; - if (deviceData.capabilityMask & 0x0200) - z = [theTabletEvent absoluteZ]; - - if (deviceData.capabilityMask & 0x0800) - tangentialPressure = [theTabletEvent tangentialPressure]; - - rotation = [theTabletEvent rotation]; - QPointF hiRes = flipPoint(globalPoint); - QTabletEvent qtabletEvent(qType, QPoint(localPoint.x, localPoint.y), - hiRes.toPoint(), hiRes, - deviceData.tabletDeviceType, deviceData.tabletPointerType, - pressure, xTilt, yTilt, tangentialPressure, rotation, z, - qt_cocoaModifiers2QtModifiers([theTabletEvent modifierFlags]), - deviceData.tabletUniqueID); - - qt_sendSpontaneousEvent(widgetToGetMouse, &qtabletEvent); - return qtabletEvent.isAccepted(); -} - -void qt_mac_updateContentBorderMetricts(void * /*OSWindowRef */window, const ::HIContentBorderMetrics &metrics) -{ - OSWindowRef theWindow = static_cast(window); - if ([theWindow styleMask] & NSTexturedBackgroundWindowMask) - [theWindow setContentBorderThickness:metrics.top forEdge:NSMaxYEdge]; - [theWindow setContentBorderThickness:metrics.bottom forEdge:NSMinYEdge]; -} - -void qt_mac_replaceDrawRect(void * /*OSWindowRef */window, QWidgetPrivate *widget) -{ - QMacCocoaAutoReleasePool pool; - OSWindowRef theWindow = static_cast(window); - if(!theWindow) - return; - id theClass = [[[theWindow contentView] superview] class]; - // What we do here is basically to add a new selector to NSThemeFrame called - // "drawRectOriginal:" which will contain the original implementation of - // "drawRect:". After that we get the new implementation from QCocoaWindow - // and exchange them. The new implementation is called drawRectSpecial. - // We cannot just add the method because it might have been added before and since - // we cannot remove a method once it has been added we need to ask QCocoaWindow if - // we did the swap or not. - if(!widget->drawRectOriginalAdded) { - Method m2 = class_getInstanceMethod(theClass, @selector(drawRect:)); - if(!m2) { - // This case is pretty extreme, no drawRect means no drawing! - return; - } - class_addMethod(theClass, @selector(drawRectOriginal:), method_getImplementation(m2), method_getTypeEncoding(m2)); - widget->drawRectOriginalAdded = true; - } - if(widget->originalDrawMethod) { - Method m0 = class_getInstanceMethod([theWindow class], @selector(drawRectSpecial:)); - if(!m0) { - // Ok, this means the methods were never swapped. Just ignore - return; - } - Method m1 = class_getInstanceMethod(theClass, @selector(drawRect:)); - if(!m1) { - // Ok, this means the methods were never swapped. Just ignore - return; - } - // We have the original method here. Proceed and swap the methods. - method_exchangeImplementations(m1, m0); - widget->originalDrawMethod = false; - [theWindow display]; - } -} - -void qt_mac_replaceDrawRectOriginal(void * /*OSWindowRef */window, QWidgetPrivate *widget) -{ - QMacCocoaAutoReleasePool pool; - OSWindowRef theWindow = static_cast(window); - id theClass = [[[theWindow contentView] superview] class]; - // Now we need to revert the methods to their original state. - // We cannot remove the method, so we just keep track of it in QCocoaWindow. - Method m0 = class_getInstanceMethod([theWindow class], @selector(drawRectSpecial:)); - if(!m0) { - // Ok, this means the methods were never swapped. Just ignore - return; - } - Method m1 = class_getInstanceMethod(theClass, @selector(drawRect:)); - if(!m1) { - // Ok, this means the methods were never swapped. Just ignore - return; - } - method_exchangeImplementations(m1, m0); - widget->originalDrawMethod = true; - [theWindow display]; -} - -void qt_mac_showBaseLineSeparator(void * /*OSWindowRef */window, bool show) -{ - if(!window) - return; - QMacCocoaAutoReleasePool pool; - OSWindowRef theWindow = static_cast(window); - NSToolbar *macToolbar = [theWindow toolbar]; - [macToolbar setShowsBaselineSeparator:show]; -} - -QStringList qt_mac_NSArrayToQStringList(void *nsarray) -{ - QStringList result; - NSArray *array = static_cast(nsarray); - for (NSUInteger i=0; i<[array count]; ++i) - result << qt_mac_NSStringToQString([array objectAtIndex:i]); - return result; -} - -void *qt_mac_QStringListToNSMutableArrayVoid(const QStringList &list) -{ - NSMutableArray *result = [NSMutableArray arrayWithCapacity:list.size()]; - for (int i=0; i(QCFString::toCFStringRef(list[i]))]; - } - return result; -} - -void qt_syncCocoaTitleBarButtons(OSWindowRef window, QWidget *widgetForWindow) -{ - if (!widgetForWindow) - return; - - Qt::WindowFlags flags = widgetForWindow->windowFlags(); - bool customize = flags & Qt::CustomizeWindowHint; - - NSButton *btn = [window standardWindowButton:NSWindowZoomButton]; - // BOOL is not an int, so the bitwise AND doesn't work. - bool go = uint(customize && !(flags & Qt::WindowMaximizeButtonHint)) == 0; - [btn setEnabled:go]; - - btn = [window standardWindowButton:NSWindowMiniaturizeButton]; - go = uint(customize && !(flags & Qt::WindowMinimizeButtonHint)) == 0; - [btn setEnabled:go]; - - btn = [window standardWindowButton:NSWindowCloseButton]; - go = uint(customize && !(flags & Qt::WindowSystemMenuHint - || flags & Qt::WindowCloseButtonHint)) == 0; - [btn setEnabled:go]; - - [window setShowsToolbarButton:uint(flags & Qt::MacWindowToolBarButtonHint) != 0]; -} - -// Carbon: Make sure you call QDEndContext on the context when done with it. -CGContextRef qt_mac_graphicsContextFor(QWidget *widget) -{ - if (!widget) - return 0; - - CGContextRef context = (CGContextRef)[[NSGraphicsContext graphicsContextWithWindow:qt_mac_window_for(widget)] graphicsPort]; - return context; -} - -void qt_mac_dispatchPendingUpdateRequests(QWidget *widget) -{ - if (!widget) - return; - [qt_mac_nativeview_for(widget) displayIfNeeded]; -} - -CGFloat qt_mac_get_scalefactor() -{ - return [[NSScreen mainScreen] userSpaceScaleFactor]; -} - -QString qt_mac_get_pasteboardString(OSPasteboardRef paste) -{ - QMacCocoaAutoReleasePool pool; - NSPasteboard *pb = nil; - CFStringRef pbname; - if (PasteboardCopyName(paste, &pbname) == noErr) { - pb = [NSPasteboard pasteboardWithName:const_cast(reinterpret_cast(pbname))]; - CFRelease(pbname); - } else { - pb = [NSPasteboard generalPasteboard]; - } - if (pb) { - NSString *text = [pb stringForType:NSStringPboardType]; - if (text) - return qt_mac_NSStringToQString(text); - } - return QString(); -} - -QPixmap qt_mac_convert_iconref(const IconRef icon, int width, int height) -{ - QPixmap ret(width, height); - ret.fill(QColor(0, 0, 0, 0)); - - CGRect rect = CGRectMake(0, 0, width, height); - - CGContextRef ctx = qt_mac_cg_context(&ret); - CGAffineTransform old_xform = CGContextGetCTM(ctx); - CGContextConcatCTM(ctx, CGAffineTransformInvert(old_xform)); - CGContextConcatCTM(ctx, CGAffineTransformIdentity); - - ::RGBColor b; - b.blue = b.green = b.red = 255*255; - PlotIconRefInContext(ctx, &rect, kAlignNone, kTransformNone, &b, kPlotIconRefNormalFlags, icon); - CGContextRelease(ctx); - return ret; -} - -void qt_mac_constructQIconFromIconRef(const IconRef icon, const IconRef overlayIcon, QIcon *retIcon, QStyle::StandardPixmap standardIcon) -{ - int size = 16; - while (size <= 128) { - - const QString cacheKey = QLatin1String("qt_mac_constructQIconFromIconRef") + QString::number(standardIcon) + QString::number(size); - QPixmap mainIcon; - if (standardIcon >= QStyle::SP_CustomBase) { - mainIcon = qt_mac_convert_iconref(icon, size, size); - } else if (QPixmapCache::find(cacheKey, mainIcon) == false) { - mainIcon = qt_mac_convert_iconref(icon, size, size); - QPixmapCache::insert(cacheKey, mainIcon); - } - - if (overlayIcon) { - int littleSize = size / 2; - QPixmap overlayPix = qt_mac_convert_iconref(overlayIcon, littleSize, littleSize); - QPainter painter(&mainIcon); - painter.drawPixmap(size - littleSize, size - littleSize, overlayPix); - } - - retIcon->addPixmap(mainIcon); - size += size; // 16 -> 32 -> 64 -> 128 - } -} - -void qt_mac_post_retranslateAppMenu() -{ - QMacCocoaAutoReleasePool pool; - qt_cocoaPostMessage([NSApp QT_MANGLE_NAMESPACE(qt_qcocoamenuLoader)], @selector(qtTranslateApplicationMenu)); -} - -QWidgetPrivate *QMacScrollOptimization::_target = 0; -bool QMacScrollOptimization::_inWheelEvent = false; -int QMacScrollOptimization::_dx = 0; -int QMacScrollOptimization::_dy = 0; -QRect QMacScrollOptimization::_scrollRect = QRect(0, 0, -1, -1); - -// This method implements the magic for the drawRectSpecial method. -// We draw a line at the upper edge of the content view in order to -// override the title baseline. -void macDrawRectOnTop(void * /*OSWindowRef */window) -{ - OSWindowRef theWindow = static_cast(window); - NSView *contentView = [theWindow contentView]; - if(!contentView) - return; - // Get coordinates of the content view - NSRect contentRect = [contentView frame]; - // Draw a line on top of the already drawn line. - // We need to check if we are active or not to use the proper color. - if([theWindow isKeyWindow] || [theWindow isMainWindow]) { - [[NSColor colorWithCalibratedRed:1.0 green:1.0 blue:1.0 alpha:1.0] set]; - } else { - [[NSColor colorWithCalibratedRed:1.0 green:1.0 blue:1.0 alpha:1.0] set]; - } - NSPoint origin = NSMakePoint(0, contentRect.size.height); - NSPoint end = NSMakePoint(contentRect.size.width, contentRect.size.height); - [NSBezierPath strokeLineFromPoint:origin toPoint:end]; -} - -// This method will (or at least should) get called only once. -// Its mission is to find out if we are active or not. If we are active -// we assume that we were launched via finder, otherwise we assume -// we were called from the command line. The distinction is important, -// since in the first case we don't need to trigger a paintEvent, while -// in the second case we do. -void macSyncDrawingOnFirstInvocation(void * /*OSWindowRef */window) -{ - OSWindowRef theWindow = static_cast(window); - NSApplication *application = [NSApplication sharedApplication]; - NSToolbar *toolbar = [theWindow toolbar]; - if([application isActive]) { - // Launched from finder - [toolbar setShowsBaselineSeparator:NO]; - } else { - // Launched from commandline - [toolbar setVisible:false]; - [toolbar setShowsBaselineSeparator:NO]; - [toolbar setVisible:true]; - [theWindow display]; - } -} - -void qt_cocoaStackChildWindowOnTopOfOtherChildren(QWidget *childWidget) -{ - if (!childWidget) - return; - - QWidget *parent = childWidget->parentWidget(); - if (childWidget->isWindow() && parent) { - if ([[qt_mac_window_for(parent) childWindows] containsObject:qt_mac_window_for(childWidget)]) { - QWidgetPrivate *d = qt_widget_private(childWidget); - d->setSubWindowStacking(false); - d->setSubWindowStacking(true); - } - } -} - -void qt_mac_display(QWidget *widget) -{ - NSView *theNSView = qt_mac_nativeview_for(widget); - [theNSView display]; -} - -void qt_mac_setNeedsDisplay(QWidget *widget) -{ - NSView *theNSView = qt_mac_nativeview_for(widget); - [theNSView setNeedsDisplay:YES]; -} - -void qt_mac_setNeedsDisplayInRect(QWidget *widget, QRegion region) -{ - NSView *theNSView = qt_mac_nativeview_for(widget); - if (region.isEmpty()) { - [theNSView setNeedsDisplay:YES]; - return; - } - - QVector rects = region.rects(); - for (int i = 0; i < rects.count(); ++i) { - const QRect &rect = rects.at(i); - NSRect nsrect = NSMakeRect(rect.x(), rect.y(), rect.width(), rect.height()); - [theNSView setNeedsDisplayInRect:nsrect]; - } - -} - - -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qt_cocoa_helpers_mac_p.h b/src/widgets/platforms/mac/qt_cocoa_helpers_mac_p.h deleted file mode 100644 index bae479e..0000000 --- a/src/widgets/platforms/mac/qt_cocoa_helpers_mac_p.h +++ /dev/null @@ -1,308 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#ifndef QT_COCOA_HELPERS_MAC_P_H -#define QT_COCOA_HELPERS_MAC_P_H - -// -// W A R N I N G -// ------------- -// -// This file is not part of the Qt API. It exists for the convenience -// of qapplication_*.cpp, qwidget*.cpp, qcolor_x11.cpp, qfiledialog.cpp -// and many other. This header file may change from version to version -// without notice, or even be removed. -// -// We mean it. -// - -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include "private/qt_mac_p.h" - -struct HIContentBorderMetrics; - -#ifdef __OBJC__ - // If the source file including this file also includes e.g. Cocoa/Cocoa.h, typedef-ing NSPoint will - // fail since NSPoint will already be a type. So we try to detect this. If the build fails, ensure - // that the inclusion of cocoa headers happends before the inclusion of this file. - #include -#else - #ifdef Q_WS_MAC32 - typedef struct _NSPoint NSPoint; // Just redefine here so I don't have to pull in all of Cocoa. - #else - typedef struct CGPoint NSPoint; - #endif -#endif - -QT_BEGIN_NAMESPACE - -Qt::MouseButtons qt_mac_get_buttons(int buttons); -Qt::MouseButton qt_mac_get_button(EventMouseButton button); -void macWindowFade(void * /*OSWindowRef*/ window, float durationSeconds = 0.15); -void macWindowToolbarShow(const QWidget *widget, bool show ); -void macWindowToolbarSet( void * /*OSWindowRef*/ window, void* toolbarRef ); -bool macWindowToolbarIsVisible( void * /*OSWindowRef*/ window ); -void macWindowSetHasShadow( void * /*OSWindowRef*/ window, bool hasShadow ); -void macWindowFlush(void * /*OSWindowRef*/ window); -void macSendToolbarChangeEvent(QWidget *widget); -void qt_mac_updateContentBorderMetricts(void * /*OSWindowRef */window, const ::HIContentBorderMetrics &metrics); -void qt_mac_replaceDrawRect(void * /*OSWindowRef */window, QWidgetPrivate *widget); -void qt_mac_replaceDrawRectOriginal(void * /*OSWindowRef */window, QWidgetPrivate *widget); -void qt_mac_showBaseLineSeparator(void * /*OSWindowRef */window, bool show); -void qt_mac_update_mouseTracking(QWidget *widget); -OSStatus qt_mac_drawCGImage(CGContextRef cg, const CGRect *inbounds, CGImageRef); -bool qt_mac_checkForNativeSizeGrip(const QWidget *widget); -void qt_dispatchTabletProximityEvent(void * /*NSEvent * */ tabletEvent); -bool qt_dispatchKeyEventWithCocoa(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent); -// These methods exists only for supporting unified mode. -void macDrawRectOnTop(void * /*OSWindowRef */ window); -void macSyncDrawingOnFirstInvocation(void * /*OSWindowRef */window); -void qt_cocoaStackChildWindowOnTopOfOtherChildren(QWidget *widget); -bool qt_dispatchKeyEvent(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent); -void qt_dispatchModifiersChanged(void * /*NSEvent * */flagsChangedEvent, QWidget *widgetToGetEvent); -bool qt_mac_handleTabletEvent(void * /*QCocoaView * */view, void * /*NSEvent * */event); -inline QApplication *qAppInstance() { return static_cast(QCoreApplication::instance()); } -struct ::TabletProximityRec; -void qt_dispatchTabletProximityEvent(const ::TabletProximityRec &proxRec); -Qt::KeyboardModifiers qt_cocoaModifiers2QtModifiers(ulong modifierFlags); -Qt::KeyboardModifiers qt_cocoaDragOperation2QtModifiers(uint dragOperations); -QPixmap qt_mac_convert_iconref(const IconRef icon, int width, int height); -void qt_mac_constructQIconFromIconRef(const IconRef icon, const IconRef overlayIcon, QIcon *retIcon, - QStyle::StandardPixmap standardIcon = QStyle::SP_CustomBase); - -#ifdef __OBJC__ -struct DnDParams -{ - NSView *view; - NSEvent *theEvent; - QPoint globalPoint; - NSDragOperation performedAction; -}; - -DnDParams *macCurrentDnDParameters(); -NSDragOperation qt_mac_mapDropAction(Qt::DropAction action); -NSDragOperation qt_mac_mapDropActions(Qt::DropActions actions); -Qt::DropAction qt_mac_mapNSDragOperation(NSDragOperation nsActions); -Qt::DropActions qt_mac_mapNSDragOperations(NSDragOperation nsActions); - -QWidget *qt_mac_getTargetForKeyEvent(QWidget *widgetThatReceivedEvent); -QWidget *qt_mac_getTargetForMouseEvent(NSEvent *event, QEvent::Type eventType, - QPoint &returnLocalPoint, QPoint &returnGlobalPoint, QWidget *nativeWidget, QWidget **returnWidgetUnderMouse); -bool qt_mac_handleMouseEvent(NSEvent *event, QEvent::Type eventType, Qt::MouseButton button, QWidget *nativeWidget); -void qt_mac_handleNonClientAreaMouseEvent(NSWindow *window, NSEvent *event); -#endif - -inline int flipYCoordinate(int y) -{ - return QApplication::desktop()->screenGeometry(0).height() - y; -} - -inline qreal flipYCoordinate(qreal y) -{ - return QApplication::desktop()->screenGeometry(0).height() - y; -} - -QPointF flipPoint(const NSPoint &p); -NSPoint flipPoint(const QPoint &p); -NSPoint flipPoint(const QPointF &p); - -QStringList qt_mac_NSArrayToQStringList(void *nsarray); -void *qt_mac_QStringListToNSMutableArrayVoid(const QStringList &list); - -void qt_syncCocoaTitleBarButtons(OSWindowRef window, QWidget *widgetForWindow); - -CGFloat qt_mac_get_scalefactor(); -QString qt_mac_get_pasteboardString(OSPasteboardRef paste); - -#ifdef __OBJC__ -inline NSMutableArray *qt_mac_QStringListToNSMutableArray(const QStringList &qstrlist) -{ return reinterpret_cast(qt_mac_QStringListToNSMutableArrayVoid(qstrlist)); } - -inline QString qt_mac_NSStringToQString(const NSString *nsstr) -{ return QCFString::toQString(reinterpret_cast(nsstr)); } - -inline NSString *qt_mac_QStringToNSString(const QString &qstr) -{ return [const_cast(reinterpret_cast(QCFString::toCFStringRef(qstr))) autorelease]; } - -#endif - -class QMacScrollOptimization { - // This class is made to optimize for the case when the user - // scrolls both horizontally and vertically at the same - // time. This will result in two QWheelEvents (one for each - // direction), which will typically result in two calls to - // QWidget::_scroll_sys. Rather than copying pixels twize on - // screen because of this, we add this helper class to try to - // get away with only one blit. - static QWidgetPrivate *_target; - static bool _inWheelEvent; - static int _dx; - static int _dy; - static QRect _scrollRect; - -public: - static void initDelayedScroll() - { - _inWheelEvent = true; - } - - static bool delayScroll(QWidgetPrivate *target, int dx, int dy, const QRect &scrollRect) - { - if (!_inWheelEvent) - return false; - if (_target && _target != target) - return false; - if (_scrollRect.width() != -1 && _scrollRect != scrollRect) - return false; - - _target = target; - _dx += dx; - _dy += dy; - _scrollRect = scrollRect; - return true; - } - - static void performDelayedScroll() - { - if (!_inWheelEvent) - return; - _inWheelEvent = false; - if (!_target) - return; - - _target->scroll_sys(_dx, _dy, _scrollRect); - - _target = 0; - _dx = 0; - _dy = 0; - _scrollRect = QRect(0, 0, -1, -1); - } -}; - -void qt_mac_post_retranslateAppMenu(); - -void qt_mac_display(QWidget *widget); -void qt_mac_setNeedsDisplay(QWidget *widget); -void qt_mac_setNeedsDisplayInRect(QWidget *widget, QRegion region); - - -// Utility functions to ease the use of Core Graphics contexts. - -inline void qt_mac_retain_graphics_context(CGContextRef context) -{ - CGContextRetain(context); - CGContextSaveGState(context); -} - -inline void qt_mac_release_graphics_context(CGContextRef context) -{ - CGContextRestoreGState(context); - CGContextRelease(context); -} - -inline void qt_mac_draw_image(CGContextRef context, CGContextRef imageContext, CGRect area, CGRect drawingArea) -{ - CGImageRef image = CGBitmapContextCreateImage(imageContext); - CGImageRef subImage = CGImageCreateWithImageInRect(image, area); - - CGContextTranslateCTM (context, 0, drawingArea.origin.y + CGRectGetMaxY(drawingArea)); - CGContextScaleCTM(context, 1, -1); - CGContextDrawImage(context, drawingArea, subImage); - - CGImageRelease(subImage); - CGImageRelease(image); -} - -QT_END_NAMESPACE - -#endif // QT_COCOA_HELPERS_MAC_P_H diff --git a/src/widgets/platforms/mac/qt_mac.cpp b/src/widgets/platforms/mac/qt_mac.cpp deleted file mode 100644 index adf8f70..0000000 --- a/src/widgets/platforms/mac/qt_mac.cpp +++ /dev/null @@ -1,129 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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 -#include -#include -#include - -QT_BEGIN_NAMESPACE -static CTFontRef CopyCTThemeFont(ThemeFontID themeID) -{ - CTFontUIFontType ctID = HIThemeGetUIFontType(themeID); - return CTFontCreateUIFontForLanguage(ctID, 0, 0); -} - -QFont qfontForThemeFont(ThemeFontID themeID) -{ - QCFType ctfont = CopyCTThemeFont(themeID); - QString familyName = QCFString(CTFontCopyFamilyName(ctfont)); - QCFType dict = CTFontCopyTraits(ctfont); - CFNumberRef num = static_cast(CFDictionaryGetValue(dict, kCTFontWeightTrait)); - float fW; - CFNumberGetValue(num, kCFNumberFloat32Type, &fW); - QFont::Weight wght = fW > 0. ? QFont::Bold : QFont::Normal; - num = static_cast(CFDictionaryGetValue(dict, kCTFontSlantTrait)); - CFNumberGetValue(num, kCFNumberFloatType, &fW); - bool italic = (fW != 0.0); - return QFont(familyName, CTFontGetSize(ctfont), wght, italic); -} - -#if (MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_5) - -static inline QColor leopardBrush(ThemeBrush brush) -{ - QCFType cgClr = 0; - HIThemeBrushCreateCGColor(brush, &cgClr); - return qcolorFromCGColor(cgClr); -} -#endif - -QColor qcolorForTheme(ThemeBrush brush) -{ - return leopardBrush(brush); -} - -QColor qcolorForThemeTextColor(ThemeTextColor themeColor) -{ -#ifdef Q_OS_MAC32 - RGBColor c; - GetThemeTextColor(themeColor, 32, true, &c); - QColor color = QColor(c.red / 256, c.green / 256, c.blue / 256); - return color; -#else - // There is no equivalent to GetThemeTextColor in 64-bit and it was rather bad that - // I didn't file a request to implement this for Snow Leopard. So, in the meantime - // I've encoded the values from the GetThemeTextColor. This is not exactly ideal - // as if someone really wants to mess with themeing, these colors will be wrong. - // It also means that we need to make sure the values for differences between - // OS releases (and it will be likely that we are a step behind.) - switch (themeColor) { - case kThemeTextColorAlertActive: - case kThemeTextColorTabFrontActive: - case kThemeTextColorBevelButtonActive: - case kThemeTextColorListView: - case kThemeTextColorPlacardActive: - case kThemeTextColorPopupButtonActive: - case kThemeTextColorPopupLabelActive: - case kThemeTextColorPushButtonActive: - return Qt::black; - case kThemeTextColorAlertInactive: - case kThemeTextColorDialogInactive: - case kThemeTextColorPlacardInactive: - return QColor(69, 69, 69, 255); - case kThemeTextColorPopupButtonInactive: - case kThemeTextColorPopupLabelInactive: - case kThemeTextColorPushButtonInactive: - case kThemeTextColorTabFrontInactive: - case kThemeTextColorBevelButtonInactive: - return QColor(127, 127, 127, 255); - default: { - QNativeImage nativeImage(16,16, QNativeImage::systemFormat()); - CGRect cgrect = CGRectMake(0, 0, 16, 16); - HIThemeSetTextFill(themeColor, 0, nativeImage.cg, kHIThemeOrientationNormal); - CGContextFillRect(nativeImage.cg, cgrect); - QColor color = nativeImage.image.pixel(0,0); - return QColor(nativeImage.image.pixel(0 , 0)); - } - } -#endif -} -QT_END_NAMESPACE diff --git a/src/widgets/platforms/mac/qwidget_mac.mm b/src/widgets/platforms/mac/qwidget_mac.mm deleted file mode 100644 index 6c8413e..0000000 --- a/src/widgets/platforms/mac/qwidget_mac.mm +++ /dev/null @@ -1,3089 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). -** All rights reserved. -** Contact: Nokia Corporation (qt-info@nokia.com) -** -** This file is part of the QtGui module 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$ -** -****************************************************************************/ - -/**************************************************************************** -** -** Copyright (c) 2007-2008, Apple, Inc. -** -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions are met: -** -** * Redistributions of source code must retain the above copyright notice, -** this list of conditions and the following disclaimer. -** -** * Redistributions in binary form must reproduce the above copyright notice, -** this list of conditions and the following disclaimer in the documentation -** and/or other materials provided with the distribution. -** -** * Neither the name of Apple, Inc. nor the names of its contributors -** may be used to endorse or promote products derived from this software -** without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -** CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -** EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -** PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -** PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -** LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -** NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -** SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -** -****************************************************************************/ - -#include -#include - -#include "qapplication.h" -#include "qapplication_p.h" -#include "qbitmap.h" -#include "qcursor.h" -#include "qdesktopwidget.h" -#include "qevent.h" -#include "qfileinfo.h" -#include "qimage.h" -#include "qlayout.h" -#include "qmenubar.h" -#include -#include -#include -#include "qpainter.h" -#include "qstyle.h" -#include "qtimer.h" -#include "qfocusframe.h" -#include "qdebug.h" -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "qwidget_p.h" -#include "qevent_p.h" -#include "qdnd_p.h" -#include -#include "qmainwindow.h" - -QT_BEGIN_NAMESPACE - -// qmainwindow.cpp -extern QMainWindowLayout *qt_mainwindow_layout(const QMainWindow *window); - -#define XCOORD_MAX 16383 -#define WRECT_MAX 8191 - - - -/***************************************************************************** - QWidget debug facilities - *****************************************************************************/ -//#define DEBUG_WINDOW_RGNS -//#define DEBUG_WINDOW_CREATE -//#define DEBUG_WINDOW_STATE -//#define DEBUG_WIDGET_PAINT - -/***************************************************************************** - QWidget globals - *****************************************************************************/ - -static bool qt_mac_raise_process = true; -static OSWindowRef qt_root_win = 0; -QWidget *mac_mouse_grabber = 0; -QWidget *mac_keyboard_grabber = 0; - - -/***************************************************************************** - Externals - *****************************************************************************/ -extern QPointer qt_button_down; //qapplication_mac.cpp -extern QWidget *qt_mac_modal_blocked(QWidget *); //qapplication_mac.mm -extern void qt_event_request_activate(QWidget *); //qapplication_mac.mm -extern bool qt_event_remove_activate(); //qapplication_mac.mm -extern void qt_mac_event_release(QWidget *w); //qapplication_mac.mm -extern void qt_event_request_showsheet(QWidget *); //qapplication_mac.mm -extern void qt_event_request_window_change(QWidget *); //qapplication_mac.mm -extern QPointer qt_last_mouse_receiver; //qapplication_mac.mm -extern QPointer qt_last_native_mouse_receiver; //qt_cocoa_helpers_mac.mm -extern IconRef qt_mac_create_iconref(const QPixmap &); //qpixmap_mac.cpp -extern void qt_mac_set_cursor(const QCursor *, const QPoint &); //qcursor_mac.mm -extern void qt_mac_update_cursor(); //qcursor_mac.mm -extern bool qt_nograb(); -extern CGImageRef qt_mac_create_cgimage(const QPixmap &, bool); //qpixmap_mac.cpp -extern RgnHandle qt_mac_get_rgn(); //qregion_mac.cpp -extern QRegion qt_mac_convert_mac_region(RgnHandle rgn); //qregion_mac.cpp -extern void qt_mac_setMouseGrabCursor(bool set, QCursor *cursor = 0); // qcursor_mac.mm -extern QPointer topLevelAt_cache; // qapplication_mac.mm -/***************************************************************************** - QWidget utility functions - *****************************************************************************/ -void Q_GUI_EXPORT qt_mac_set_raise_process(bool b) { qt_mac_raise_process = b; } -static QSize qt_mac_desktopSize() -{ - int w = 0, h = 0; - CGDisplayCount cg_count; - CGGetActiveDisplayList(0, 0, &cg_count); - QVector displays(cg_count); - CGGetActiveDisplayList(cg_count, displays.data(), &cg_count); - Q_ASSERT(cg_count == (CGDisplayCount)displays.size()); - for(int i = 0; i < (int)cg_count; ++i) { - CGRect r = CGDisplayBounds(displays.at(i)); - w = qMax(w, qRound(r.origin.x + r.size.width)); - h = qMax(h, qRound(r.origin.y + r.size.height)); - } - return QSize(w, h); -} - -static NSDrawer *qt_mac_drawer_for(const QWidget *widget) -{ - NSView *widgetView = reinterpret_cast(widget->window()->effectiveWinId()); - NSArray *windows = [NSApp windows]; - for (NSWindow *window in windows) { - NSArray *drawers = [window drawers]; - for (NSDrawer *drawer in drawers) { - if ([drawer contentView] == widgetView) - return drawer; - } - } - return 0; -} - -static void qt_mac_destructView(OSViewRef view) -{ - NSWindow *window = [view window]; - if ([window contentView] == view) - [window setContentView:[[NSView alloc] initWithFrame:[view bounds]]]; - [view removeFromSuperview]; - [view release]; -} - -static void qt_mac_destructWindow(OSWindowRef window) -{ - if ([window isVisible] && [window isSheet]){ - [NSApp endSheet:window]; - [window orderOut:window]; - } - - [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] resignDelegateForWindow:window]; - [window release]; -} - -static void qt_mac_destructDrawer(NSDrawer *drawer) -{ - [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] resignDelegateForDrawer:drawer]; - [drawer release]; -} - -bool qt_mac_can_clickThrough(const QWidget *w) -{ - static int qt_mac_carbon_clickthrough = -1; - if (qt_mac_carbon_clickthrough < 0) - qt_mac_carbon_clickthrough = !qgetenv("QT_MAC_NO_COCOA_CLICKTHROUGH").isEmpty(); - bool ret = !qt_mac_carbon_clickthrough; - for ( ; w; w = w->parentWidget()) { - if (w->testAttribute(Qt::WA_MacNoClickThrough)) { - ret = false; - break; - } - } - return ret; -} - -bool qt_mac_is_macsheet(const QWidget *w) -{ - if (!w) - return false; - - Qt::WindowModality modality = w->windowModality(); - if (modality == Qt::ApplicationModal) - return false; - return w->parentWidget() && (modality == Qt::WindowModal || w->windowType() == Qt::Sheet); -} - -bool qt_mac_is_macdrawer(const QWidget *w) -{ - return (w && w->parentWidget() && w->windowType() == Qt::Drawer); -} - -bool qt_mac_insideKeyWindow(const QWidget *w) -{ - return [[reinterpret_cast(w->effectiveWinId()) window] isKeyWindow]; - return false; -} - -bool qt_mac_set_drawer_preferred_edge(QWidget *w, Qt::DockWidgetArea where) //users of Qt for Mac OS X can use this.. -{ - if(!qt_mac_is_macdrawer(w)) - return false; - - NSDrawer *drawer = qt_mac_drawer_for(w); - if (!drawer) - return false; - NSRectEdge edge; - if (where & Qt::LeftDockWidgetArea) - edge = NSMinXEdge; - else if (where & Qt::RightDockWidgetArea) - edge = NSMaxXEdge; - else if (where & Qt::TopDockWidgetArea) - edge = NSMaxYEdge; - else if (where & Qt::BottomDockWidgetArea) - edge = NSMinYEdge; - else - return false; - - if (edge == [drawer preferredEdge]) //no-op - return false; - - if (w->isVisible()) { - [drawer close]; - [drawer openOnEdge:edge]; - } - [drawer setPreferredEdge:edge]; - return true; -} - -QPoint qt_mac_posInWindow(const QWidget *w) -{ - QPoint ret = w->data->wrect.topLeft(); - while(w && !w->isWindow()) { - ret += w->pos(); - w = w->parentWidget(); - } - return ret; -} - -//find a QWidget from a OSWindowRef -QWidget *qt_mac_find_window(OSWindowRef window) -{ - return [window QT_MANGLE_NAMESPACE(qt_qwidget)]; -} - -inline static void qt_mac_set_fullscreen_mode(bool b) -{ - extern bool qt_mac_app_fullscreen; //qapplication_mac.mm - if(qt_mac_app_fullscreen == b) - return; - qt_mac_app_fullscreen = b; - if (b) { - SetSystemUIMode(kUIModeAllHidden, kUIOptionAutoShowMenuBar); - } else { - SetSystemUIMode(kUIModeNormal, 0); - } -} - -Q_GUI_EXPORT OSViewRef qt_mac_nativeview_for(const QWidget *w) -{ - return reinterpret_cast(w->internalWinId()); -} - -Q_GUI_EXPORT OSViewRef qt_mac_effectiveview_for(const QWidget *w) -{ - // Get the first non-alien (parent) widget for - // w, and return its NSView (if it has one): - return reinterpret_cast(w->effectiveWinId()); -} - -Q_GUI_EXPORT OSViewRef qt_mac_get_contentview_for(OSWindowRef w) -{ - return [w contentView]; -} - -bool qt_mac_sendMacEventToWidget(QWidget *widget, EventRef ref) -{ - return widget->macEvent(0, ref); -} - -Q_GUI_EXPORT OSWindowRef qt_mac_window_for(OSViewRef view) -{ - if (view) - return [view window]; - return 0; -} - -static bool qt_isGenuineQWidget(OSViewRef ref) -{ - return [ref isKindOfClass:[QT_MANGLE_NAMESPACE(QCocoaView) class]]; -} - -bool qt_isGenuineQWidget(const QWidget *window) -{ - if (!window) - return false; - - if (!window->internalWinId()) - return true; //alien - - return qt_isGenuineQWidget(OSViewRef(window->internalWinId())); -} - -Q_GUI_EXPORT OSWindowRef qt_mac_window_for(const QWidget *w) -{ - if (OSViewRef hiview = qt_mac_effectiveview_for(w)) { - OSWindowRef window = qt_mac_window_for(hiview); - if (window) - return window; - - if (qt_isGenuineQWidget(hiview)) { - // This is a workaround for NSToolbar. When a widget is hidden - // by clicking the toolbar button, Cocoa reparents the widgets - // to another window (but Qt doesn't know about it). - // When we start showing them, it reparents back, - // but at this point it's window is nil, but the window it's being brought - // into (the Qt one) is for sure created. - // This stops the hierarchy moving under our feet. - QWidget *toplevel = w->window(); - if (toplevel != w) { - hiview = qt_mac_nativeview_for(toplevel); - if (OSWindowRef w = qt_mac_window_for(hiview)) - return w; - } - - toplevel->d_func()->createWindow_sys(); - // Reget the hiview since "create window" could potentially move the view (I guess). - hiview = qt_mac_nativeview_for(toplevel); - return qt_mac_window_for(hiview); - } - } - return 0; -} - - - -inline static bool updateRedirectedToGraphicsProxyWidget(QWidget *widget, const QRect &rect) -{ - if (!widget) - return false; - -#ifndef QT_NO_GRAPHICSVIEW - QWidget *tlw = widget->window(); - QWExtra *extra = qt_widget_private(tlw)->extra; - if (extra && extra->proxyWidget) { - extra->proxyWidget->update(rect.translated(widget->mapTo(tlw, QPoint()))); - return true; - } -#endif - - return false; -} - -inline static bool updateRedirectedToGraphicsProxyWidget(QWidget *widget, const QRegion &rgn) -{ - if (!widget) - return false; - -#ifndef QT_NO_GRAPHICSVIEW - QWidget *tlw = widget->window(); - QWExtra *extra = qt_widget_private(tlw)->extra; - if (extra && extra->proxyWidget) { - const QPoint offset(widget->mapTo(tlw, QPoint())); - const QVector rects = rgn.rects(); - for (int i = 0; i < rects.size(); ++i) - extra->proxyWidget->update(rects.at(i).translated(offset)); - return true; - } -#endif - - return false; -} - -void QWidgetPrivate::macSetNeedsDisplay(QRegion region) -{ - Q_Q(QWidget); - if (NSView *nativeView = qt_mac_nativeview_for(q)) { - // INVARIANT: q is _not_ alien. So we can optimize a little: - if (region.isEmpty()) { - [nativeView setNeedsDisplay:YES]; - } else { - QVector rects = region.rects(); - for (int i = 0; inativeParentWidget()) { - // INVARIANT: q is alien, and effectiveWidget is native. - if (NSView *effectiveView = qt_mac_nativeview_for(effectiveWidget)) { - if (region.isEmpty()) { - const QRect &rect = q->rect(); - QPoint p = q->mapTo(effectiveWidget, rect.topLeft()); - NSRect nsrect = NSMakeRect(p.x(), p.y(), rect.width(), rect.height()); - [effectiveView setNeedsDisplayInRect:nsrect]; - } else { - QVector rects = region.rects(); - for (int i = 0; imapTo(effectiveWidget, rect.topLeft()); - NSRect nsrect = NSMakeRect(p.x(), p.y(), rect.width(), rect.height()); - [effectiveView setNeedsDisplayInRect:nsrect]; - } - } - } - } -} - -void QWidgetPrivate::macUpdateIsOpaque() -{ - Q_Q(QWidget); - if (!q->testAttribute(Qt::WA_WState_Created)) - return; - if (isRealWindow() && !q->testAttribute(Qt::WA_MacBrushedMetal)) { - bool opaque = isOpaque; - if (extra && extra->imageMask) - opaque = false; // we are never opaque when we have a mask. - [qt_mac_window_for(q) setOpaque:opaque]; - } -} -static OSWindowRef qt_mac_create_window(QWidget *widget, WindowClass wclass, - NSUInteger wattr, const QRect &crect) -{ - // Determine if we need to add in our "custom window" attribute. Cocoa is rather clever - // in deciding if we need the maximize button or not (i.e., it's resizeable, so you - // must need a maximize button). So, the only buttons we have control over are the - // close and minimize buttons. If someone wants to customize and NOT have the maximize - // button, then we have to do our hack. We only do it for these cases because otherwise - // the window looks different when activated. This "QtMacCustomizeWindow" attribute is - // intruding on a public space and WILL BREAK in the future. - // One can hope that there is a more public API available by that time. - Qt::WindowFlags flags = widget ? widget->windowFlags() : Qt::WindowFlags(0); - if ((flags & Qt::CustomizeWindowHint)) { - if ((flags & (Qt::WindowCloseButtonHint | Qt::WindowSystemMenuHint - | Qt::WindowMinimizeButtonHint | Qt::WindowTitleHint)) - && !(flags & Qt::WindowMaximizeButtonHint)) - wattr |= QtMacCustomizeWindow; - } - - // If we haven't created the desktop widget, you have to pass the rectangle - // in "cocoa coordinates" (i.e., top points to the lower left coordinate). - // Otherwise, we do the conversion for you. Since we are the only ones that - // create the desktop widget, this is OK (but confusing). - NSRect geo = NSMakeRect(crect.left(), - (qt_root_win != 0) ? flipYCoordinate(crect.bottom() + 1) : crect.top(), - crect.width(), crect.height()); - QMacCocoaAutoReleasePool pool; - OSWindowRef window; - switch (wclass) { - case kMovableModalWindowClass: - case kModalWindowClass: - case kSheetWindowClass: - case kFloatingWindowClass: - case kOverlayWindowClass: - case kHelpWindowClass: { - NSPanel *panel; - BOOL needFloating = NO; - BOOL worksWhenModal = widget && (widget->windowType() == Qt::Popup); - // Add in the extra flags if necessary. - switch (wclass) { - case kSheetWindowClass: - wattr |= NSDocModalWindowMask; - break; - case kFloatingWindowClass: - case kHelpWindowClass: - needFloating = YES; - wattr |= NSUtilityWindowMask; - break; - default: - break; - } - panel = [[QT_MANGLE_NAMESPACE(QCocoaPanel) alloc] QT_MANGLE_NAMESPACE(qt_initWithQWidget):widget contentRect:geo styleMask:wattr]; - [panel setFloatingPanel:needFloating]; - [panel setWorksWhenModal:worksWhenModal]; - window = panel; - break; - } - case kDrawerWindowClass: { - NSDrawer *drawer = [[NSDrawer alloc] initWithContentSize:geo.size preferredEdge:NSMinXEdge]; - [[QT_MANGLE_NAMESPACE(QCocoaWindowDelegate) sharedDelegate] becomeDelegateForDrawer:drawer widget:widget]; - QWidget *parentWidget = widget->parentWidget(); - if (parentWidget) - [drawer setParentWindow:qt_mac_window_for(parentWidget)]; - [drawer setLeadingOffset:0.0]; - [drawer setTrailingOffset:25.0]; - window = [[drawer contentView] window]; // Just to make sure we actually return a window - break; - } - default: - window = [[QT_MANGLE_NAMESPACE(QCocoaWindow) alloc] QT_MANGLE_NAMESPACE(qt_initWithQWidget):widget contentRect:geo styleMask:wattr]; - break; - } - qt_syncCocoaTitleBarButtons(window, widget); - return window; -} - -OSViewRef qt_mac_create_widget(QWidget *widget, QWidgetPrivate *widgetPrivate, OSViewRef parent) -{ - QMacCocoaAutoReleasePool pool; - QT_MANGLE_NAMESPACE(QCocoaView) *view = [[QT_MANGLE_NAMESPACE(QCocoaView) alloc] initWithQWidget:widget widgetPrivate:widgetPrivate]; - -#ifdef ALIEN_DEBUG - qDebug() << "Creating NSView for" << widget; -#endif - - if (view && parent) - [parent addSubview:view]; - return view; -} - -void qt_mac_unregister_widget() -{ -} - -void QWidgetPrivate::toggleDrawers(bool visible) -{ - for (int i = 0; i < children.size(); ++i) { - register QObject *object = children.at(i); - if (!object->isWidgetType()) - continue; - QWidget *widget = static_cast(object); - if(qt_mac_is_macdrawer(widget)) { - bool oldState = widget->testAttribute(Qt::WA_WState_ExplicitShowHide); - if(visible) { - if (!widget->testAttribute(Qt::WA_WState_ExplicitShowHide)) - widget->show(); - } else { - widget->hide(); - if(!oldState) - widget->setAttribute(Qt::WA_WState_ExplicitShowHide, false); - } - } - } -} - -/***************************************************************************** - QWidgetPrivate member functions - *****************************************************************************/ -bool QWidgetPrivate::qt_mac_update_sizer(QWidget *w, int up) -{ - // I'm not sure what "up" is - if(!w || !w->isWindow()) - return false; - - QTLWExtra *topData = w->d_func()->topData(); - QWExtra *extraData = w->d_func()->extraData(); - // topData->resizer is only 4 bits, so subtracting -1 from zero causes bad stuff - // to happen, prevent that here (you really want the thing hidden). - if (up >= 0 || topData->resizer != 0) - topData->resizer += up; - OSWindowRef windowRef = qt_mac_window_for(OSViewRef(w->effectiveWinId())); - { - } - bool remove_grip = (topData->resizer || (w->windowFlags() & Qt::FramelessWindowHint) - || (extraData->maxw && extraData->maxh && - extraData->maxw == extraData->minw && extraData->maxh == extraData->minh)); - [windowRef setShowsResizeIndicator:!remove_grip]; - return true; -} - -void QWidgetPrivate::qt_clean_root_win() -{ - QMacCocoaAutoReleasePool pool; - [qt_root_win release]; - qt_root_win = 0; -} - -bool QWidgetPrivate::qt_create_root_win() -{ - if(qt_root_win) - return false; - const QSize desktopSize = qt_mac_desktopSize(); - QRect desktopRect(QPoint(0, 0), desktopSize); - qt_root_win = qt_mac_create_window(0, kOverlayWindowClass, NSBorderlessWindowMask, desktopRect); - if(!qt_root_win) - return false; - qAddPostRoutine(qt_clean_root_win); - return true; -} - -bool QWidgetPrivate::qt_widget_rgn(QWidget *widget, short wcode, RgnHandle rgn, bool force = false) -{ - bool ret = false; - Q_UNUSED(widget); - Q_UNUSED(wcode); - Q_UNUSED(rgn); - Q_UNUSED(force); - return ret; -} - -/***************************************************************************** - QWidget member functions - *****************************************************************************/ -void QWidgetPrivate::determineWindowClass() -{ - Q_Q(QWidget); -#if !defined(QT_NO_MAINWINDOW) && !defined(QT_NO_TOOLBAR) - // Make sure that QMainWindow has the MacWindowToolBarButtonHint when the - // unifiedTitleAndToolBarOnMac property is ON. This is to avoid reentry of - // setParent() triggered by the QToolBar::event(QEvent::ParentChange). - QMainWindow *mainWindow = qobject_cast(q); - if (mainWindow && mainWindow->unifiedTitleAndToolBarOnMac()) { - data.window_flags |= Qt::MacWindowToolBarButtonHint; - } -#endif - - const Qt::WindowType type = q->windowType(); - Qt::WindowFlags &flags = data.window_flags; - const bool popup = (type == Qt::Popup); - if (type == Qt::ToolTip || type == Qt::SplashScreen || popup) - flags |= Qt::FramelessWindowHint; - - WindowClass wclass = kSheetWindowClass; - if(qt_mac_is_macdrawer(q)) - wclass = kDrawerWindowClass; - else if (q->testAttribute(Qt::WA_ShowModal) && flags & Qt::CustomizeWindowHint) - wclass = kDocumentWindowClass; - else if(popup || (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_5 && type == Qt::SplashScreen)) - wclass = kModalWindowClass; - else if(type == Qt::Dialog) - wclass = kMovableModalWindowClass; - else if(type == Qt::ToolTip) - wclass = kHelpWindowClass; - else if(type == Qt::Tool || (QSysInfo::MacintoshVersion < QSysInfo::MV_10_5 - && type == Qt::SplashScreen)) - wclass = kFloatingWindowClass; - else if(q->testAttribute(Qt::WA_ShowModal)) - wclass = kMovableModalWindowClass; - else - wclass = kDocumentWindowClass; - - WindowAttributes wattr = NSBorderlessWindowMask; - if(qt_mac_is_macsheet(q)) { - //grp = GetWindowGroupOfClass(kMovableModalWindowClass); - wclass = kSheetWindowClass; - wattr = NSTitledWindowMask | NSResizableWindowMask; - } else { - // Shift things around a bit to get the correct window class based on the presence - // (or lack) of the border. - bool customize = flags & Qt::CustomizeWindowHint; - bool framelessWindow = (flags & Qt::FramelessWindowHint || (customize && !(flags & Qt::WindowTitleHint))); - if (framelessWindow) { - if (wclass == kDocumentWindowClass) { - wclass = kSimpleWindowClass; - } else if (wclass == kFloatingWindowClass) { - wclass = kToolbarWindowClass; - } else if (wclass == kMovableModalWindowClass) { - wclass = kModalWindowClass; - } - } else { - wattr |= NSTitledWindowMask; - if (wclass != kModalWindowClass) - wattr |= NSResizableWindowMask; - } - // Only add extra decorations (well, buttons) for widgets that can have them - // and have an actual border we can put them on. - if (wclass != kModalWindowClass - && wclass != kSheetWindowClass && wclass != kPlainWindowClass - && !framelessWindow && wclass != kDrawerWindowClass - && wclass != kHelpWindowClass) { - if (flags & Qt::WindowMinimizeButtonHint) - wattr |= NSMiniaturizableWindowMask; - if (flags & Qt::WindowSystemMenuHint || flags & Qt::WindowCloseButtonHint) - wattr |= NSClosableWindowMask; - } else { - // Clear these hints so that we aren't call them on invalid windows - flags &= ~(Qt::WindowMaximizeButtonHint | Qt::WindowMinimizeButtonHint - | Qt::WindowCloseButtonHint | Qt::WindowSystemMenuHint); - } - } - if (q->testAttribute(Qt::WA_MacBrushedMetal)) - wattr |= NSTexturedBackgroundWindowMask; - -#ifdef DEBUG_WINDOW_CREATE -#define ADD_DEBUG_WINDOW_NAME(x) { x, #x } - struct { - UInt32 tag; - const char *name; - } known_attribs[] = { - ADD_DEBUG_WINDOW_NAME(kWindowCompositingAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowStandardHandlerAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowMetalAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowHideOnSuspendAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowStandardHandlerAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowCollapseBoxAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowHorizontalZoomAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowVerticalZoomAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowResizableAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowNoActivatesAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowNoUpdatesAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowOpaqueForEventsAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowLiveResizeAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowCloseBoxAttribute), - ADD_DEBUG_WINDOW_NAME(kWindowHideOnSuspendAttribute), - { 0, 0 } - }, known_classes[] = { - ADD_DEBUG_WINDOW_NAME(kHelpWindowClass), - ADD_DEBUG_WINDOW_NAME(kPlainWindowClass), - ADD_DEBUG_WINDOW_NAME(kDrawerWindowClass), - ADD_DEBUG_WINDOW_NAME(kUtilityWindowClass), - ADD_DEBUG_WINDOW_NAME(kToolbarWindowClass), - ADD_DEBUG_WINDOW_NAME(kSheetWindowClass), - ADD_DEBUG_WINDOW_NAME(kFloatingWindowClass), - ADD_DEBUG_WINDOW_NAME(kUtilityWindowClass), - ADD_DEBUG_WINDOW_NAME(kDocumentWindowClass), - ADD_DEBUG_WINDOW_NAME(kToolbarWindowClass), - ADD_DEBUG_WINDOW_NAME(kMovableModalWindowClass), - ADD_DEBUG_WINDOW_NAME(kModalWindowClass), - { 0, 0 } - }; - qDebug("Qt: internal: ************* Creating new window %p (%s::%s)", q, q->metaObject()->className(), - q->objectName().toLocal8Bit().constData()); - bool found_class = false; - for(int i = 0; known_classes[i].name; i++) { - if(wclass == known_classes[i].tag) { - found_class = true; - qDebug("Qt: internal: ** Class: %s", known_classes[i].name); - break; - } - } - if(!found_class) - qDebug("Qt: internal: !! Class: Unknown! (%d)", (int)wclass); - if(wattr) { - WindowAttributes tmp_wattr = wattr; - qDebug("Qt: internal: ** Attributes:"); - for(int i = 0; tmp_wattr && known_attribs[i].name; i++) { - if((tmp_wattr & known_attribs[i].tag) == known_attribs[i].tag) { - tmp_wattr ^= known_attribs[i].tag; - } - } - if(tmp_wattr) - qDebug("Qt: internal: !! Attributes: Unknown (%d)", (int)tmp_wattr); - } -#endif - - topData()->wclass = wclass; - topData()->wattr = wattr; -} - -#undef ADD_DEBUG_WINDOW_NAME - -void QWidgetPrivate::setWindowLevel() -{ - Q_Q(QWidget); - const QWidget * const windowParent = q->window()->parentWidget(); - const QWidget * const primaryWindow = windowParent ? windowParent->window() : 0; - NSInteger winLevel = -1; - - if (q->windowType() == Qt::Popup) { - winLevel = NSPopUpMenuWindowLevel; - // Popup should be in at least the same level as its parent. - if (primaryWindow) { - OSWindowRef parentRef = qt_mac_window_for(primaryWindow); - winLevel = qMax([parentRef level], winLevel); - } - } else if (q->windowType() == Qt::Tool) { - winLevel = NSFloatingWindowLevel; - } else if (q->windowType() == Qt::Dialog) { - // Correct modality level (NSModalPanelWindowLevel) will be - // set by cocoa when creating a modal session later. - winLevel = NSNormalWindowLevel; - } - - // StayOnTop window should appear above Tool windows. - if (data.window_flags & Qt::WindowStaysOnTopHint) - winLevel = NSPopUpMenuWindowLevel; - // Tooltips should appear above StayOnTop windows. - if (q->windowType() == Qt::ToolTip) - winLevel = NSScreenSaverWindowLevel; - // All other types are Normal level. - if (winLevel == -1) - winLevel = NSNormalWindowLevel; - [qt_mac_window_for(q) setLevel:winLevel]; -} - -void QWidgetPrivate::finishCreateWindow_sys_Cocoa(void * /*NSWindow * */ voidWindowRef) -{ - Q_Q(QWidget); - QMacCocoaAutoReleasePool pool; - NSWindow *windowRef = static_cast(voidWindowRef); - const Qt::WindowType type = q->windowType(); - Qt::WindowFlags &flags = data.window_flags; - QWidget *parentWidget = q->parentWidget(); - - const bool popup = (type == Qt::Popup); - const bool dialog = (type == Qt::Dialog - || type == Qt::Sheet - || type == Qt::Drawer - || (flags & Qt::MSWindowsFixedSizeDialogHint)); - QTLWExtra *topExtra = topData(); - - if ((popup || type == Qt::Tool || type == Qt::ToolTip) && !q->isModal()) { - [windowRef setHidesOnDeactivate:YES]; - } else { - [windowRef setHidesOnDeactivate:NO]; - } - if (q->testAttribute(Qt::WA_MacNoShadow)) - [windowRef setHasShadow:NO]; - else - [windowRef setHasShadow:YES]; - Q_UNUSED(parentWidget); - Q_UNUSED(dialog); - - data.fstrut_dirty = true; // when we create a toplevel widget, the frame strut should be dirty - - OSViewRef nsview = (OSViewRef)data.winid; - if (!nsview) { - nsview = qt_mac_create_widget(q, this, 0); - setWinId(WId(nsview)); - } - [windowRef setContentView:nsview]; - [nsview setHidden:NO]; - transferChildren(); - - // Tell Cocoa explicit that we wan't the view to receive key events - // (regardless of focus policy) because this is how it works on other - // platforms (and in the carbon port): - [windowRef makeFirstResponder:nsview]; - - if (topExtra->posFromMove) { - updateFrameStrut(); - - const QRect &fStrut = frameStrut(); - const QRect &crect = data.crect; - const QRect frameRect(QPoint(crect.left(), crect.top()), - QSize(fStrut.left() + fStrut.right() + crect.width(), - fStrut.top() + fStrut.bottom() + crect.height())); - NSRect cocoaFrameRect = NSMakeRect(frameRect.x(), flipYCoordinate(frameRect.bottom() + 1), - frameRect.width(), frameRect.height()); - [windowRef setFrame:cocoaFrameRect display:NO]; - topExtra->posFromMove = false; - } - - if (q->testAttribute(Qt::WA_WState_WindowOpacitySet)){ - q->setWindowOpacity(topExtra->opacity / 255.0f); - } else if (qt_mac_is_macsheet(q)){ - CGFloat alpha = [qt_mac_window_for(q) alphaValue]; - if (alpha >= 1.0) { - q->setWindowOpacity(0.95f); - q->setAttribute(Qt::WA_WState_WindowOpacitySet, false); - } - } else{ - // If the window has been recreated after beeing e.g. a sheet, - // make sure that we don't report a faulty opacity: - q->setWindowOpacity(1.0f); - q->setAttribute(Qt::WA_WState_WindowOpacitySet, false); - } - - // Its more performant to handle the mouse cursor - // ourselves, expecially when using alien widgets: - [windowRef disableCursorRects]; - - setWindowLevel(); - macUpdateHideOnSuspend(); - macUpdateOpaqueSizeGrip(); - macUpdateIgnoreMouseEvents(); - setWindowTitle_helper(extra->topextra->caption); - setWindowIconText_helper(extra->topextra->iconText); - setWindowModified_sys(q->isWindowModified()); - updateFrameStrut(); - syncCocoaMask(); - macUpdateIsOpaque(); - qt_mac_update_sizer(q); - applyMaxAndMinSizeOnWindow(); -} - - -/* - Recreates widget window. Useful if immutable - properties for it has changed. - */ -void QWidgetPrivate::recreateMacWindow() -{ - Q_Q(QWidget); - OSViewRef myView = qt_mac_nativeview_for(q); - OSWindowRef oldWindow = qt_mac_window_for(myView); - QMacCocoaAutoReleasePool pool; - [myView removeFromSuperview]; - determineWindowClass(); - createWindow_sys(); - if (NSToolbar *toolbar = [oldWindow toolbar]) { - OSWindowRef newWindow = qt_mac_window_for(myView); - [newWindow setToolbar:toolbar]; - [toolbar setVisible:[toolbar isVisible]]; - } - if ([oldWindow isVisible]){ - if ([oldWindow isSheet]) - [NSApp endSheet:oldWindow]; - [oldWindow orderOut:oldWindow]; - show_sys(); - } - - // Release the window after creating the new window, because releasing it early - // may cause the app to quit ("close on last window closed attribute") - qt_mac_destructWindow(oldWindow); -} - -void QWidgetPrivate::createWindow_sys() -{ - Q_Q(QWidget); - Qt::WindowFlags &flags = data.window_flags; - QWidget *parentWidget = q->parentWidget(); - - QTLWExtra *topExtra = topData(); - if (topExtra->embedded) - return; // Simply return because this view "is" the top window. - quint32 wattr = topExtra->wattr; - - if(parentWidget && (parentWidget->window()->windowFlags() & Qt::WindowStaysOnTopHint)) // If our parent has Qt::WStyle_StaysOnTop, so must we - flags |= Qt::WindowStaysOnTopHint; - - data.fstrut_dirty = true; - - OSWindowRef windowRef = qt_mac_create_window(q, topExtra->wclass, wattr, data.crect); - if (windowRef == 0) - qWarning("QWidget: Internal error: %s:%d: If you reach this error please contact Qt Support and include the\n" - " WidgetFlags used in creating the widget.", __FILE__, __LINE__); - finishCreateWindow_sys_Cocoa(windowRef); -} - -void QWidgetPrivate::create_sys(WId window, bool initializeWindow, bool destroyOldWindow) -{ - Q_Q(QWidget); - QMacCocoaAutoReleasePool pool; - - OSViewRef destroyid = 0; - - Qt::WindowType type = q->windowType(); - Qt::WindowFlags flags = data.window_flags; - QWidget *parentWidget = q->parentWidget(); - - bool topLevel = (flags & Qt::Window); - bool popup = (type == Qt::Popup); - bool dialog = (type == Qt::Dialog - || type == Qt::Sheet - || type == Qt::Drawer - || (flags & Qt::MSWindowsFixedSizeDialogHint)); - bool desktop = (type == Qt::Desktop); - - // Determine this early for top-levels so, we can use it later. - if (topLevel) - determineWindowClass(); - - if (desktop) { - QSize desktopSize = qt_mac_desktopSize(); - q->setAttribute(Qt::WA_WState_Visible); - data.crect.setRect(0, 0, desktopSize.width(), desktopSize.height()); - dialog = popup = false; // force these flags off - } else { - if (topLevel && (type != Qt::Drawer)) { - if (QDesktopWidget *dsk = QApplication::desktop()) { // calc pos/size from screen - const bool wasResized = q->testAttribute(Qt::WA_Resized); - const bool wasMoved = q->testAttribute(Qt::WA_Moved); - int deskn = dsk->primaryScreen(); - if (parentWidget && parentWidget->windowType() != Qt::Desktop) - deskn = dsk->screenNumber(parentWidget); - QRect screenGeo = dsk->screenGeometry(deskn); - if (!wasResized) { - NSRect newRect = [NSWindow frameRectForContentRect:NSMakeRect(0, 0, - screenGeo.width() / 2., - 4 * screenGeo.height() / 10.) - styleMask:topData()->wattr]; - data.crect.setSize(QSize(newRect.size.width, newRect.size.height)); - // Constrain to minimums and maximums we've set - if (extra->minw > 0) - data.crect.setWidth(qMax(extra->minw, data.crect.width())); - if (extra->minh > 0) - data.crect.setHeight(qMax(extra->minh, data.crect.height())); - if (extra->maxw > 0) - data.crect.setWidth(qMin(extra->maxw, data.crect.width())); - if (extra->maxh > 0) - data.crect.setHeight(qMin(extra->maxh, data.crect.height())); - } - if (!wasMoved && !q->testAttribute(Qt::WA_DontShowOnScreen)) - data.crect.moveTopLeft(QPoint(screenGeo.width()/4, - 3 * screenGeo.height() / 10)); - } - } - } - - - if(!window) // always initialize - initializeWindow=true; - - hd = 0; - if(window) { // override the old window (with a new NSView) - OSViewRef nativeView = OSViewRef(window); - OSViewRef parent = 0; - [nativeView retain]; - if (destroyOldWindow) - destroyid = qt_mac_nativeview_for(q); - bool transfer = false; - setWinId((WId)nativeView); - if(topLevel) { - for(int i = 0; i < 2; ++i) { - if(i == 1) { - if(!initializeWindow) - break; - createWindow_sys(); - } - if(OSWindowRef windowref = qt_mac_window_for(nativeView)) { - [windowref retain]; - if (initializeWindow) { - parent = qt_mac_get_contentview_for(windowref); - } else { - parent = [nativeView superview]; - } - break; - } - } - if(!parent) - transfer = true; - } else if (parentWidget) { - // I need to be added to my parent, therefore my parent needs an NSView - // Alien note: a 'window' was supplied as argument, meaning this widget - // is not alien. So therefore the parent cannot be alien either. - parentWidget->createWinId(); - parent = qt_mac_nativeview_for(parentWidget); - } - if(parent != nativeView && parent) { - [parent addSubview:nativeView]; - } - if(transfer) - transferChildren(); - data.fstrut_dirty = true; // we'll re calculate this later - q->setAttribute(Qt::WA_WState_Visible, - ![nativeView isHidden] - ); - if(initializeWindow) { - NSRect bounds = NSMakeRect(data.crect.x(), data.crect.y(), data.crect.width(), data.crect.height()); - [nativeView setFrame:bounds]; - q->setAttribute(Qt::WA_WState_Visible, [nativeView isHidden]); - } - } else if (desktop) { // desktop widget - if (!qt_root_win) - QWidgetPrivate::qt_create_root_win(); - Q_ASSERT(qt_root_win); - WId rootWinID = 0; - [qt_root_win retain]; - if (OSViewRef rootContentView = [qt_root_win contentView]) { - rootWinID = (WId)rootContentView; - [rootContentView retain]; - } - setWinId(rootWinID); - } else if (topLevel) { - determineWindowClass(); - if(OSViewRef osview = qt_mac_create_widget(q, this, 0)) { - NSRect bounds = NSMakeRect(data.crect.x(), flipYCoordinate(data.crect.y()), - data.crect.width(), data.crect.height()); - [osview setFrame:bounds]; - setWinId((WId)osview); - } - } else { - data.fstrut_dirty = false; // non-toplevel widgets don't have a frame, so no need to update the strut - - if (q->testAttribute(Qt::WA_NativeWindow) == false || q->internalWinId() != 0) { - // INVARIANT: q is Alien, and we should not create an NSView to back it up. - } else - if (OSViewRef osview = qt_mac_create_widget(q, this, qt_mac_nativeview_for(parentWidget))) { - NSRect bounds = NSMakeRect(data.crect.x(), data.crect.y(), data.crect.width(), data.crect.height()); - [osview setFrame:bounds]; - setWinId((WId)osview); - if (q->isVisible()) { - // If q were Alien before, but now became native (e.g. if a call to - // winId was done from somewhere), we need to show the view immidiatly: - QMacCocoaAutoReleasePool pool; - [osview setHidden:NO]; - } - } - } - - updateIsOpaque(); - - if (q->testAttribute(Qt::WA_DropSiteRegistered)) - registerDropSite(true); - if (q->hasFocus()) - setFocus_sys(); - if (!topLevel && initializeWindow) - setWSGeometry(); - if (destroyid) - qt_mac_destructView(destroyid); -} - -/*! - Returns the QuickDraw handle of the widget. Use of this function is not - portable. This function will return 0 if QuickDraw is not supported, or - if the handle could not be created. - - \warning This function is only available on Mac OS X. -*/ - -Qt::HANDLE -QWidget::macQDHandle() const -{ - return 0; -} - -/*! - Returns the CoreGraphics handle of the widget. Use of this function is - not portable. This function will return 0 if no painter context can be - established, or if the handle could not be created. - - \warning This function is only available on Mac OS X. -*/ -Qt::HANDLE -QWidget::macCGHandle() const -{ - return handle(); -} - -void qt_mac_updateParentUnderAlienWidget(QWidget *alienWidget) -{ - QWidget *nativeParent = alienWidget->nativeParentWidget(); - if (!nativeParent) - return; - - QPoint globalPos = alienWidget->mapToGlobal(QPoint(0, 0)); - QRect dirtyRect = QRect(nativeParent->mapFromGlobal(globalPos), alienWidget->size()); - nativeParent->update(dirtyRect); -} - -void QWidget::destroy(bool destroyWindow, bool destroySubWindows) -{ - Q_D(QWidget); - QMacCocoaAutoReleasePool pool; - d->aboutToDestroy(); - if (!isWindow() && parentWidget()) - parentWidget()->d_func()->invalidateBuffer(d->effectiveRectFor(geometry())); - if (!internalWinId()) - qt_mac_updateParentUnderAlienWidget(this); - d->deactivateWidgetCleanup(); - qt_mac_event_release(this); - if(testAttribute(Qt::WA_WState_Created)) { - setAttribute(Qt::WA_WState_Created, false); - QObjectList chldrn = children(); - for(int i = 0; i < chldrn.size(); i++) { // destroy all widget children - QObject *obj = chldrn.at(i); - if(obj->isWidgetType()) - static_cast(obj)->destroy(destroySubWindows, destroySubWindows); - } - if(mac_mouse_grabber == this) - releaseMouse(); - if(mac_keyboard_grabber == this) - releaseKeyboard(); - - if(testAttribute(Qt::WA_ShowModal)) // just be sure we leave modal - QApplicationPrivate::leaveModal(this); - else if((windowType() == Qt::Popup)) - qApp->d_func()->closePopup(this); - if (destroyWindow) { - if(OSViewRef hiview = qt_mac_nativeview_for(this)) { - OSWindowRef window = 0; - NSDrawer *drawer = nil; - if (qt_mac_is_macdrawer(this)) { - drawer = qt_mac_drawer_for(this); - } else - if (isWindow()) - window = qt_mac_window_for(hiview); - - // Because of how "destruct" works, we have to do just a normal release for the root_win. - if (window && window == qt_root_win) { - [hiview release]; - } else { - qt_mac_destructView(hiview); - } - if (drawer) - qt_mac_destructDrawer(drawer); - if (window) - qt_mac_destructWindow(window); - } - } - QT_TRY { - d->setWinId(0); - } QT_CATCH (const std::bad_alloc &) { - // swallow - destructors must not throw - } - } -} - -void QWidgetPrivate::transferChildren() -{ - Q_Q(QWidget); - if (!q->internalWinId()) - return; // Can't add any views anyway - - QObjectList chlist = q->children(); - for (int i = 0; i < chlist.size(); ++i) { - QObject *obj = chlist.at(i); - if (obj->isWidgetType()) { - QWidget *w = (QWidget *)obj; - if (!w->isWindow()) { - // This seems weird, no need to call it in a loop right? - if (!topData()->caption.isEmpty()) - setWindowTitle_helper(extra->topextra->caption); - if (w->internalWinId()) { - // New NSWindows get an extra reference when drops are - // registered (at least in 10.5) which means that we may - // access the window later and get a crash (becasue our - // widget is dead). Work around this be having the drop - // site disabled until it is part of the new hierarchy. - bool oldRegistered = w->testAttribute(Qt::WA_DropSiteRegistered); - w->setAttribute(Qt::WA_DropSiteRegistered, false); - [qt_mac_nativeview_for(w) retain]; - [qt_mac_nativeview_for(w) removeFromSuperview]; - [qt_mac_nativeview_for(q) addSubview:qt_mac_nativeview_for(w)]; - [qt_mac_nativeview_for(w) release]; - w->setAttribute(Qt::WA_DropSiteRegistered, oldRegistered); - } - } - } - } -} - -void QWidgetPrivate::setSubWindowStacking(bool set) -{ - // After hitting too many unforeseen bugs trying to put Qt on top of the cocoa child - // window API, we have decided to revert this behaviour as much as we can. We - // therefore now only allow child windows to exist for children of modal dialogs. - static bool use_behaviour_qt473 = !qgetenv("QT_MAC_USE_CHILDWINDOWS").isEmpty(); - - // This will set/remove a visual relationship between parent and child on screen. - // The reason for doing this is to ensure that a child always stacks infront of - // its parent. Unfortunatly is turns out that [NSWindow addChildWindow] has - // several unwanted side-effects, one of them being the moving of a child when - // moving the parent, which we choose to accept. A way tougher side-effect is - // that Cocoa will hide the parent if you hide the child. And in the case of - // a tool window, since it will normally hide when you deactivate the - // application, Cocoa will hide the parent upon deactivate as well. The result often - // being no more visible windows on screen. So, to make a long story short, we only - // allow parent-child relationships between windows that both are either a plain window - // or a dialog. - - Q_Q(QWidget); - if (!q->isWindow()) - return; - NSWindow *qwin = [qt_mac_nativeview_for(q) window]; - if (!qwin) - return; - Qt::WindowType qtype = q->windowType(); - if (set && !(qtype == Qt::Window || qtype == Qt::Dialog)) - return; - if (set && ![qwin isVisible]) - return; - - if (QWidget *parent = q->parentWidget()) { - if (NSWindow *pwin = [qt_mac_nativeview_for(parent) window]) { - if (set) { - Qt::WindowType ptype = parent->window()->windowType(); - if ([pwin isVisible] - && (ptype == Qt::Window || ptype == Qt::Dialog) - && ![qwin parentWindow] - && (use_behaviour_qt473 || parent->windowModality() == Qt::ApplicationModal)) { - NSInteger level = [qwin level]; - [pwin addChildWindow:qwin ordered:NSWindowAbove]; - if ([qwin level] < level) - [qwin setLevel:level]; - } - } else { - [pwin removeChildWindow:qwin]; - } - } - } - - // Only set-up child windows for q if q is modal: - if (set && !use_behaviour_qt473 && q->windowModality() != Qt::ApplicationModal) - return; - - QObjectList widgets = q->children(); - for (int i=0; i(widgets.at(i)); - if (child && child->isWindow()) { - if (NSWindow *cwin = [qt_mac_nativeview_for(child) window]) { - if (set) { - Qt::WindowType ctype = child->window()->windowType(); - if ([cwin isVisible] && (ctype == Qt::Window || ctype == Qt::Dialog) && ![cwin parentWindow]) { - NSInteger level = [cwin level]; - [qwin addChildWindow:cwin ordered:NSWindowAbove]; - if ([cwin level] < level) - [cwin setLevel:level]; - } - } else { - [qwin removeChildWindow:qt_mac_window_for(child)]; - } - } - } - } -} - -void QWidgetPrivate::setParent_sys(QWidget *parent, Qt::WindowFlags f) -{ - Q_Q(QWidget); - QMacCocoaAutoReleasePool pool; - QTLWExtra *topData = maybeTopData(); - bool wasCreated = q->testAttribute(Qt::WA_WState_Created); - bool wasWindow = q->isWindow(); - OSViewRef old_id = 0; - - if (q->isVisible() && q->parentWidget() && parent != q->parentWidget()) - q->parentWidget()->d_func()->invalidateBuffer(effectiveRectFor(q->geometry())); - - // Maintain the glWidgets list on parent change: remove "our" gl widgets - // from the list on the old parent and grandparents. - if (glWidgets.isEmpty() == false) { - QWidget *current = q->parentWidget(); - while (current) { - for (QList::const_iterator it = glWidgets.constBegin(); - it != glWidgets.constEnd(); ++it) - current->d_func()->glWidgets.removeAll(*it); - - if (current->isWindow()) - break; - current = current->parentWidget(); - } - } - - bool oldToolbarVisible = false; - NSDrawer *oldDrawer = nil; - NSToolbar *oldToolbar = 0; - if (wasCreated && !(q->windowType() == Qt::Desktop)) { - old_id = qt_mac_nativeview_for(q); - if (qt_mac_is_macdrawer(q)) { - oldDrawer = qt_mac_drawer_for(q); - } - if (wasWindow) { - OSWindowRef oldWindow = qt_mac_window_for(old_id); - oldToolbar = [oldWindow toolbar]; - if (oldToolbar) { - [oldToolbar retain]; - oldToolbarVisible = [oldToolbar isVisible]; - [oldWindow setToolbar:nil]; - } - } - } - QWidget* oldtlw = q->window(); - - if (q->testAttribute(Qt::WA_DropSiteRegistered)) - q->setAttribute(Qt::WA_DropSiteRegistered, false); - - //recreate and setup flags - QObjectPrivate::setParent_helper(parent); - bool explicitlyHidden = q->testAttribute(Qt::WA_WState_Hidden) && q->testAttribute(Qt::WA_WState_ExplicitShowHide); - if (wasCreated && !qt_isGenuineQWidget(q)) - return; - - if (!q->testAttribute(Qt::WA_WState_WindowOpacitySet)) { - q->setWindowOpacity(1.0f); - q->setAttribute(Qt::WA_WState_WindowOpacitySet, false); - } - - setWinId(0); //do after the above because they may want the id - - data.window_flags = f; - q->setAttribute(Qt::WA_WState_Created, false); - q->setAttribute(Qt::WA_WState_Visible, false); - q->setAttribute(Qt::WA_WState_Hidden, false); - adjustFlags(data.window_flags, q); - // keep compatibility with previous versions, we need to preserve the created state. - // (but we recreate the winId for the widget being reparented, again for compatibility, - // unless this is an alien widget. ) - const bool nonWindowWithCreatedParent = !q->isWindow() && parent->testAttribute(Qt::WA_WState_Created); - const bool nativeWidget = q->internalWinId() != 0; - if (wasCreated || (nativeWidget && nonWindowWithCreatedParent)) { - createWinId(); - if (q->isWindow()) { - // Simply transfer our toolbar over. Everything should stay put, unlike in Carbon. - if (oldToolbar && !(f & Qt::FramelessWindowHint)) { - OSWindowRef newWindow = qt_mac_window_for(q); - [newWindow setToolbar:oldToolbar]; - [oldToolbar release]; - [oldToolbar setVisible:oldToolbarVisible]; - } - } - } - if (q->isWindow() || (!parent || parent->isVisible()) || explicitlyHidden) - q->setAttribute(Qt::WA_WState_Hidden); - q->setAttribute(Qt::WA_WState_ExplicitShowHide, explicitlyHidden); - - if (wasCreated) { - transferChildren(); - - if (topData && - (!topData->caption.isEmpty() || !topData->filePath.isEmpty())) - setWindowTitle_helper(q->windowTitle()); - } - - if (q->testAttribute(Qt::WA_AcceptDrops) - || (!q->isWindow() && q->parentWidget() - && q->parentWidget()->testAttribute(Qt::WA_DropSiteRegistered))) - q->setAttribute(Qt::WA_DropSiteRegistered, true); - - //cleanup - if (old_id) { //don't need old window anymore - OSWindowRef window = (oldtlw == q) ? qt_mac_window_for(old_id) : 0; - qt_mac_destructView(old_id); - - if (oldDrawer) { - qt_mac_destructDrawer(oldDrawer); - } else - if (window) - qt_mac_destructWindow(window); - } - - // Maintain the glWidgets list on parent change: add "our" gl widgets - // to the list on the new parent and grandparents. - if (glWidgets.isEmpty() == false) { - QWidget *current = q->parentWidget(); - while (current) { - current->d_func()->glWidgets += glWidgets; - if (current->isWindow()) - break; - current = current->parentWidget(); - } - } - invalidateBuffer(q->rect()); - qt_event_request_window_change(q); -} - -QPoint QWidget::mapToGlobal(const QPoint &pos) const -{ - Q_D(const QWidget); - if (!internalWinId()) { - QPoint p = pos + data->crect.topLeft(); - return isWindow() ? p : parentWidget()->mapToGlobal(p); - } - QPoint tmp = d->mapToWS(pos); - NSPoint hi_pos = NSMakePoint(tmp.x(), tmp.y()); - hi_pos = [qt_mac_nativeview_for(this) convertPoint:hi_pos toView:nil]; - NSRect win_rect = [qt_mac_window_for(this) frame]; - hi_pos.x += win_rect.origin.x; - hi_pos.y += win_rect.origin.y; - // If we aren't the desktop we need to flip, if you flip the desktop on itself, you get the other problem. - return ((window()->windowFlags() & Qt::Desktop) == Qt::Desktop) ? QPointF(hi_pos.x, hi_pos.y).toPoint() - : flipPoint(hi_pos).toPoint(); -} - -QPoint QWidget::mapFromGlobal(const QPoint &pos) const -{ - Q_D(const QWidget); - if (!internalWinId()) { - QPoint p = isWindow() ? pos : parentWidget()->mapFromGlobal(pos); - return p - data->crect.topLeft(); - } - NSRect win_rect = [qt_mac_window_for(this) frame]; - // The Window point is in "Cocoa coordinates," but the view is in "Qt coordinates" - // so make sure to keep them in sync. - NSPoint hi_pos = NSMakePoint(pos.x()-win_rect.origin.x, - flipYCoordinate(pos.y())-win_rect.origin.y); - hi_pos = [qt_mac_nativeview_for(this) convertPoint:hi_pos fromView:0]; - return d->mapFromWS(QPoint(qRound(hi_pos.x), qRound(hi_pos.y))); -} - -void QWidgetPrivate::updateSystemBackground() -{ -} - -void QWidgetPrivate::setCursor_sys(const QCursor &) -{ - qt_mac_update_cursor(); -} - -void QWidgetPrivate::unsetCursor_sys() -{ - qt_mac_update_cursor(); -} - -void QWidgetPrivate::setWindowTitle_sys(const QString &caption) -{ - Q_Q(QWidget); - if (q->isWindow()) { - QMacCocoaAutoReleasePool pool; - [qt_mac_window_for(q) setTitle:qt_mac_QStringToNSString(caption)]; - } -} - -void QWidgetPrivate::setWindowModified_sys(bool mod) -{ - Q_Q(QWidget); - if (q->isWindow() && q->testAttribute(Qt::WA_WState_Created)) { - [qt_mac_window_for(q) setDocumentEdited:mod]; - } -} - -void QWidgetPrivate::setWindowFilePath_sys(const QString &filePath) -{ - Q_Q(QWidget); - QMacCocoaAutoReleasePool pool; - QFileInfo fi(filePath); - [qt_mac_window_for(q) setRepresentedFilename:fi.exists() ? qt_mac_QStringToNSString(filePath) : @""]; -} - -void QWidgetPrivate::setWindowIcon_sys(bool forceReset) -{ - Q_Q(QWidget); - - if (!q->testAttribute(Qt::WA_WState_Created)) - return; - - QTLWExtra *topData = this->topData(); - if (topData->iconPixmap && !forceReset) // already set - return; - - QIcon icon = q->windowIcon(); - QPixmap *pm = 0; - if (!icon.isNull()) { - // now create the extra - if (!topData->iconPixmap) { - pm = new QPixmap(icon.pixmap(QSize(22, 22))); - topData->iconPixmap = pm; - } else { - pm = topData->iconPixmap; - } - } - if (q->isWindow()) { - QMacCocoaAutoReleasePool pool; - if (icon.isNull()) - return; - NSButton *iconButton = [qt_mac_window_for(q) standardWindowButton:NSWindowDocumentIconButton]; - if (iconButton == nil) { - QCFString string(q->windowTitle()); - const NSString *tmpString = reinterpret_cast((CFStringRef)string); - [qt_mac_window_for(q) setRepresentedURL:[NSURL fileURLWithPath:const_cast(tmpString)]]; - iconButton = [qt_mac_window_for(q) standardWindowButton:NSWindowDocumentIconButton]; - } - if (icon.isNull()) { - [iconButton setImage:nil]; - } else { - QPixmap scaled = pm->scaled(QSize(16,16), Qt::KeepAspectRatio, Qt::SmoothTransformation); - NSImage *image = static_cast(qt_mac_create_nsimage(scaled)); - [iconButton setImage:image]; - [image release]; - } - } -} - -void QWidgetPrivate::setWindowIconText_sys(const QString &iconText) -{ - Q_Q(QWidget); - if(q->isWindow() && !iconText.isEmpty()) { - QMacCocoaAutoReleasePool pool; - [qt_mac_window_for(q) setMiniwindowTitle:qt_mac_QStringToNSString(iconText)]; - } -} - -void QWidget::grabMouse() -{ - if(isVisible() && !qt_nograb()) { - if(mac_mouse_grabber) - mac_mouse_grabber->releaseMouse(); - mac_mouse_grabber=this; - qt_mac_setMouseGrabCursor(true); - } -} - -#ifndef QT_NO_CURSOR -void QWidget::grabMouse(const QCursor &cursor) -{ - if(isVisible() && !qt_nograb()) { - if(mac_mouse_grabber) - mac_mouse_grabber->releaseMouse(); - mac_mouse_grabber=this; - qt_mac_setMouseGrabCursor(true, const_cast(&cursor)); - } -} -#endif - -void QWidget::releaseMouse() -{ - if(!qt_nograb() && mac_mouse_grabber == this) { - mac_mouse_grabber = 0; - qt_mac_setMouseGrabCursor(false); - } -} - -void QWidget::grabKeyboard() -{ - if(!qt_nograb()) { - if(mac_keyboard_grabber) - mac_keyboard_grabber->releaseKeyboard(); - mac_keyboard_grabber = this; - } -} - -void QWidget::releaseKeyboard() -{ - if(!qt_nograb() && mac_keyboard_grabber == this) - mac_keyboard_grabber = 0; -} - -QWidget *QWidget::mouseGrabber() -{ - return mac_mouse_grabber; -} - -QWidget *QWidget::keyboardGrabber() -{ - return mac_keyboard_grabber; -} - -void QWidget::activateWindow() -{ - QWidget *tlw = window(); - if(!tlw->isVisible() || !tlw->isWindow() || (tlw->windowType() == Qt::Desktop)) - return; - qt_event_remove_activate(); - - QWidget *fullScreenWidget = tlw; - QWidget *parentW = tlw; - // Find the oldest parent or the parent with fullscreen, whichever comes first. - while (parentW) { - fullScreenWidget = parentW->window(); - if (fullScreenWidget->windowState() & Qt::WindowFullScreen) - break; - parentW = fullScreenWidget->parentWidget(); - } - - if (fullScreenWidget->windowType() != Qt::ToolTip) { - qt_mac_set_fullscreen_mode((fullScreenWidget->windowState() & Qt::WindowFullScreen) && - qApp->desktop()->screenNumber(this) == 0); - } - - bool windowActive; - OSWindowRef win = qt_mac_window_for(tlw); - QMacCocoaAutoReleasePool pool; - windowActive = [win isKeyWindow]; - if ((tlw->windowType() == Qt::Popup) - || (tlw->windowType() == Qt::Tool) - || qt_mac_is_macdrawer(tlw) - || windowActive) { - [win makeKeyWindow]; - } else if(!isMinimized()) { - [win makeKeyAndOrderFront:win]; - } -} - -QWindowSurface *QWidgetPrivate::createDefaultWindowSurface_sys() -{ - return new QMacWindowSurface(q_func()); -} - -void QWidgetPrivate::update_sys(const QRect &r) -{ - Q_Q(QWidget); - if (updateRedirectedToGraphicsProxyWidget(q, r)) - return; - dirtyOnWidget += r; - macSetNeedsDisplay(r != q->rect() ? r : QRegion()); -} - -void QWidgetPrivate::update_sys(const QRegion &rgn) -{ - Q_Q(QWidget); - if (updateRedirectedToGraphicsProxyWidget(q, rgn)) - return; - dirtyOnWidget += rgn; - macSetNeedsDisplay(rgn); -} - -bool QWidgetPrivate::isRealWindow() const -{ - return q_func()->isWindow() && !topData()->embedded; -} - -void QWidgetPrivate::show_sys() -{ - Q_Q(QWidget); - if ((q->windowType() == Qt::Desktop)) //desktop is always visible - return; - - invalidateBuffer(q->rect()); - if (q->testAttribute(Qt::WA_OutsideWSRange)) - return; - QMacCocoaAutoReleasePool pool; - q->setAttribute(Qt::WA_Mapped); - if (q->testAttribute(Qt::WA_DontShowOnScreen)) - return; - - bool realWindow = isRealWindow(); - - data.fstrut_dirty = true; - if (realWindow) { - bool isCurrentlyMinimized = (q->windowState() & Qt::WindowMinimized); - setModal_sys(); - OSWindowRef window = qt_mac_window_for(q); - - // Make sure that we end up sending a repaint event to - // the widget if the window has been visible one before: - [qt_mac_get_contentview_for(window) setNeedsDisplay:YES]; - if(qt_mac_is_macsheet(q)) { - qt_event_request_showsheet(q); - } else if(qt_mac_is_macdrawer(q)) { - NSDrawer *drawer = qt_mac_drawer_for(q); - [drawer openOnEdge:[drawer preferredEdge]]; - } else { - // sync the opacity value back (in case of a fade). - [window setAlphaValue:q->windowOpacity()]; - - QWidget *top = 0; - if (QApplicationPrivate::tryModalHelper(q, &top)) { - [window makeKeyAndOrderFront:window]; - // If this window is app modal, we need to start spinning - // a modal session for it. Interrupting - // the event dispatcher will make this happend: - if (data.window_modality == Qt::ApplicationModal) - QEventDispatcherMac::instance()->interrupt(); - } else { - // The window is modally shaddowed, so we need to make - // sure that we don't pop in front of the modal window: - [window orderFront:window]; - if (!top->testAttribute(Qt::WA_DontShowOnScreen)) { - if (NSWindow *modalWin = qt_mac_window_for(top)) - [modalWin orderFront:window]; - } - } - setSubWindowStacking(true); - qt_mac_update_cursor(); - if (q->windowType() == Qt::Popup) { - qt_button_down = 0; - if (q->focusWidget()) - q->focusWidget()->d_func()->setFocus_sys(); - else - setFocus_sys(); - } - toggleDrawers(true); - } - if (isCurrentlyMinimized) { //show in collapsed state - [window miniaturize:window]; - } else if (!q->testAttribute(Qt::WA_ShowWithoutActivating)) { - } - } else if(topData()->embedded || !q->parentWidget() || q->parentWidget()->isVisible()) { - if (NSView *view = qt_mac_nativeview_for(q)) { - // INVARIANT: q is native. Just show the view: - [view setHidden:NO]; - } else { - // INVARIANT: q is alien. Update q instead: - q->update(); - } - } - - if ([NSApp isActive] && !qt_button_down && !QWidget::mouseGrabber()){ - // Update enter/leave immidiatly, don't wait for a move event. But only - // if no grab exists (even if the grab points to this widget, it seems, ref X11) - QPoint qlocal, qglobal; - QWidget *widgetUnderMouse = 0; - qt_mac_getTargetForMouseEvent(0, QEvent::Enter, qlocal, qglobal, 0, &widgetUnderMouse); - QApplicationPrivate::dispatchEnterLeave(widgetUnderMouse, qt_last_mouse_receiver); - qt_last_mouse_receiver = widgetUnderMouse; - qt_last_native_mouse_receiver = widgetUnderMouse ? - (widgetUnderMouse->internalWinId() ? widgetUnderMouse : widgetUnderMouse->nativeParentWidget()) : 0; - } - - topLevelAt_cache = 0; - qt_event_request_window_change(q); -} - -QPoint qt_mac_nativeMapFromParent(const QWidget *child, const QPoint &pt) -{ - NSPoint nativePoint = [qt_mac_nativeview_for(child) convertPoint:NSMakePoint(pt.x(), pt.y()) fromView:qt_mac_nativeview_for(child->parentWidget())]; - return QPoint(nativePoint.x, nativePoint.y); -} - - -void QWidgetPrivate::hide_sys() -{ - Q_Q(QWidget); - if((q->windowType() == Qt::Desktop)) //you can't hide the desktop! - return; - QMacCocoaAutoReleasePool pool; - if(q->isWindow()) { - setSubWindowStacking(false); - OSWindowRef window = qt_mac_window_for(q); - if(qt_mac_is_macsheet(q)) { - [NSApp endSheet:window]; - [window orderOut:window]; - } else if(qt_mac_is_macdrawer(q)) { - [qt_mac_drawer_for(q) close]; - } else { - [window orderOut:window]; - // Unfortunately it is not as easy as just hiding the window, we need - // to find out if we were in full screen mode. If we were and this is - // the last window in full screen mode then we need to unset the full screen - // mode. If this is not the last visible window in full screen mode then we - // don't change the full screen mode. - if(q->isFullScreen()) - { - bool keepFullScreen = false; - QWidgetList windowList = qApp->topLevelWidgets(); - int windowCount = windowList.count(); - for(int i = 0; i < windowCount; i++) - { - QWidget *w = windowList[i]; - // If it is the same window, we don't need to check :-) - if(q == w) - continue; - // If they are not visible or if they are minimized then - // we just ignore them. - if(!w->isVisible() || w->isMinimized()) - continue; - // Is it full screen? - // Notice that if there is one window in full screen mode then we - // cannot switch the full screen mode off, therefore we just abort. - if(w->isFullScreen()) { - keepFullScreen = true; - break; - } - } - // No windows in full screen mode, so let just unset that flag. - if(!keepFullScreen) - qt_mac_set_fullscreen_mode(false); - } - toggleDrawers(false); - qt_mac_update_cursor(); - } - } else { - invalidateBuffer(q->rect()); - if (NSView *view = qt_mac_nativeview_for(q)) { - // INVARIANT: q is native. Just hide the view: - [view setHidden:YES]; - } else { - // INVARIANT: q is alien. Repaint where q is placed instead: - qt_mac_updateParentUnderAlienWidget(q); - } - } - - if ([NSApp isActive] && !qt_button_down && !QWidget::mouseGrabber()){ - // Update enter/leave immidiatly, don't wait for a move event. But only - // if no grab exists (even if the grab points to this widget, it seems, ref X11) - QPoint qlocal, qglobal; - QWidget *widgetUnderMouse = 0; - qt_mac_getTargetForMouseEvent(0, QEvent::Leave, qlocal, qglobal, 0, &widgetUnderMouse); - QApplicationPrivate::dispatchEnterLeave(widgetUnderMouse, qt_last_native_mouse_receiver); - qt_last_mouse_receiver = widgetUnderMouse; - qt_last_native_mouse_receiver = widgetUnderMouse ? - (widgetUnderMouse->internalWinId() ? widgetUnderMouse : widgetUnderMouse->nativeParentWidget()) : 0; - } - - topLevelAt_cache = 0; - qt_event_request_window_change(q); - deactivateWidgetCleanup(); - qt_mac_event_release(q); -} - -void QWidget::setWindowState(Qt::WindowStates newstate) -{ - Q_D(QWidget); - bool needShow = false; - Qt::WindowStates oldstate = windowState(); - if (oldstate == newstate) - return; - - QMacCocoaAutoReleasePool pool; - bool needSendStateChange = true; - if(isWindow()) { - if((oldstate & Qt::WindowFullScreen) != (newstate & Qt::WindowFullScreen)) { - if(newstate & Qt::WindowFullScreen) { - if(QTLWExtra *tlextra = d->topData()) { - if(tlextra->normalGeometry.width() < 0) { - if(!testAttribute(Qt::WA_Resized)) - adjustSize(); - tlextra->normalGeometry = geometry(); - } - tlextra->savedFlags = windowFlags(); - } - needShow = isVisible(); - const QRect fullscreen(qApp->desktop()->screenGeometry(qApp->desktop()->screenNumber(this))); - setParent(parentWidget(), Qt::Window | Qt::FramelessWindowHint | (windowFlags() & 0xffff0000)); //save - setGeometry(fullscreen); - if(!qApp->desktop()->screenNumber(this)) - qt_mac_set_fullscreen_mode(true); - } else { - needShow = isVisible(); - if(!qApp->desktop()->screenNumber(this)) - qt_mac_set_fullscreen_mode(false); - setParent(parentWidget(), d->topData()->savedFlags); - setGeometry(d->topData()->normalGeometry); - d->topData()->normalGeometry.setRect(0, 0, -1, -1); - } - } - - d->createWinId(); - - OSWindowRef window = qt_mac_window_for(this); - if((oldstate & Qt::WindowMinimized) != (newstate & Qt::WindowMinimized)) { - if (newstate & Qt::WindowMinimized) { - [window miniaturize:window]; - } else { - [window deminiaturize:window]; - } - needSendStateChange = oldstate == windowState(); // Collapse didn't change our flags. - } - - if((newstate & Qt::WindowMaximized) && !((newstate & Qt::WindowFullScreen))) { - if(QTLWExtra *tlextra = d->topData()) { - if(tlextra->normalGeometry.width() < 0) { - if(!testAttribute(Qt::WA_Resized)) - adjustSize(); - tlextra->normalGeometry = geometry(); - } - } - } else if(!(newstate & Qt::WindowFullScreen)) { -// d->topData()->normalGeometry = QRect(0, 0, -1, -1); - } - -#ifdef DEBUG_WINDOW_STATE -#define WSTATE(x) qDebug("%s -- %s --> %s", #x, (oldstate & x) ? "true" : "false", (newstate & x) ? "true" : "false") - WSTATE(Qt::WindowMinimized); - WSTATE(Qt::WindowMaximized); - WSTATE(Qt::WindowFullScreen); -#undef WSTATE -#endif - if(!(newstate & (Qt::WindowMinimized|Qt::WindowFullScreen)) && - ((oldstate & Qt::WindowFullScreen) || (oldstate & Qt::WindowMinimized) || - (oldstate & Qt::WindowMaximized) != (newstate & Qt::WindowMaximized))) { - if(newstate & Qt::WindowMaximized) { - data->fstrut_dirty = true; - NSToolbar *toolbarRef = [window toolbar]; - if (toolbarRef && !isVisible() && ![toolbarRef isVisible]) { - // HIToolbar, needs to be shown so that it's in the structure window - // Typically this is part of a main window and will get shown - // during the show, but it's will make the maximize all wrong. - // ### Not sure this is right for NSToolbar... - [toolbarRef setVisible:true]; -// ShowHideWindowToolbar(window, true, false); - d->updateFrameStrut(); // In theory the dirty would work, but it's optimized out if the window is not visible :( - } - // Everything should be handled by Cocoa. - [window zoom:window]; - needSendStateChange = oldstate == windowState(); // Zoom didn't change flags. - } else if(oldstate & Qt::WindowMaximized && !(oldstate & Qt::WindowFullScreen)) { - [window zoom:window]; - if(QTLWExtra *tlextra = d->topData()) { - setGeometry(tlextra->normalGeometry); - tlextra->normalGeometry.setRect(0, 0, -1, -1); - } - } - } - } - - data->window_state = newstate; - - if(needShow) - show(); - - if(newstate & Qt::WindowActive) - activateWindow(); - - qt_event_request_window_change(this); - if (needSendStateChange) { - QWindowStateChangeEvent e(oldstate); - QApplication::sendEvent(this, &e); - } -} - -void QWidgetPrivate::setFocus_sys() -{ - Q_Q(QWidget); - if (q->testAttribute(Qt::WA_WState_Created)) { - QMacCocoaAutoReleasePool pool; - NSView *view = qt_mac_nativeview_for(q); - [[view window] makeFirstResponder:view]; - } -} - -NSComparisonResult compareViews2Raise(id view1, id view2, void *context) -{ - id topView = reinterpret_cast(context); - if (view1 == topView) - return NSOrderedDescending; - if (view2 == topView) - return NSOrderedAscending; - return NSOrderedSame; -} - -void QWidgetPrivate::raise_sys() -{ - Q_Q(QWidget); - if((q->windowType() == Qt::Desktop)) - return; - - QMacCocoaAutoReleasePool pool; - if (isRealWindow()) { - // With the introduction of spaces it is not as simple as just raising the window. - // First we need to check if we are in the right space. If we are, then we just continue - // as usual. The problem comes when we are not in the active space. There are two main cases: - // 1. Our parent was moved to a new space. In this case we want the window to be raised - // in the same space as its parent. - // 2. We don't have a parent. For this case we will just raise the window and let Cocoa - // switch to the corresponding space. - // NOTICE: There are a lot of corner cases here. We are keeping this simple for now, if - // required we will introduce special handling for some of them. - if (!q->testAttribute(Qt::WA_DontShowOnScreen) && q->isVisible()) { - OSWindowRef window = qt_mac_window_for(q); - // isOnActiveSpace is available only from 10.6 onwards, so we need to check if it is - // available before calling it. - if([window respondsToSelector:@selector(isOnActiveSpace)]) { - if(![window performSelector:@selector(isOnActiveSpace)]) { - QWidget *parentWidget = q->parentWidget(); - if(parentWidget) { - OSWindowRef parentWindow = qt_mac_window_for(parentWidget); - if(parentWindow && [parentWindow respondsToSelector:@selector(isOnActiveSpace)]) { - if ([parentWindow performSelector:@selector(isOnActiveSpace)]) { - // The window was created in a different space. Therefore if we want - // to show it in the current space we need to recreate it in the new - // space. - recreateMacWindow(); - window = qt_mac_window_for(q); - } - } - } - } - } - [window orderFront:window]; - } - if (qt_mac_raise_process) { //we get to be the active process now - ProcessSerialNumber psn; - GetCurrentProcess(&psn); - SetFrontProcessWithOptions(&psn, kSetFrontProcessFrontWindowOnly); - } - } else { - NSView *view = qt_mac_nativeview_for(q); - NSView *parentView = [view superview]; - [parentView sortSubviewsUsingFunction:compareViews2Raise context:reinterpret_cast(view)]; - } - topLevelAt_cache = 0; -} - -NSComparisonResult compareViews2Lower(id view1, id view2, void *context) -{ - id topView = reinterpret_cast(context); - if (view1 == topView) - return NSOrderedAscending; - if (view2 == topView) - return NSOrderedDescending; - return NSOrderedSame; -} - -void QWidgetPrivate::lower_sys() -{ - Q_Q(QWidget); - if((q->windowType() == Qt::Desktop)) - return; - if (isRealWindow()) { - OSWindowRef window = qt_mac_window_for(q); - [window orderBack:window]; - } else { - NSView *view = qt_mac_nativeview_for(q); - NSView *parentView = [view superview]; - [parentView sortSubviewsUsingFunction:compareViews2Lower context:reinterpret_cast(view)]; - } - topLevelAt_cache = 0; -} - -NSComparisonResult compareViews2StackUnder(id view1, id view2, void *context) -{ - const QHash &viewOrder = *reinterpret_cast *>(context); - if (viewOrder[view1] < viewOrder[view2]) - return NSOrderedAscending; - if (viewOrder[view1] > viewOrder[view2]) - return NSOrderedDescending; - return NSOrderedSame; -} - -void QWidgetPrivate::stackUnder_sys(QWidget *w) -{ - // stackUnder - Q_Q(QWidget); - if(!w || q->isWindow() || (q->windowType() == Qt::Desktop)) - return; - // Do the same trick as lower_sys() and put this widget before the widget passed in. - NSView *myView = qt_mac_nativeview_for(q); - NSView *wView = qt_mac_nativeview_for(w); - - QHash viewOrder; - NSView *parentView = [myView superview]; - NSArray *subviews = [parentView subviews]; - NSUInteger index = 1; - // make a hash of view->zorderindex and make sure z-value is always odd, - // so that when we modify the order we create a new (even) z-value which - // will not interfere with others. - for (NSView *subview in subviews) { - viewOrder.insert(subview, index * 2); - ++index; - } - viewOrder[myView] = viewOrder[wView] - 1; - - [parentView sortSubviewsUsingFunction:compareViews2StackUnder context:reinterpret_cast(&viewOrder)]; -} - - -/* - Helper function for non-toplevel widgets. Helps to map Qt's 32bit - coordinate system to OS X's 16bit coordinate system. - - Sets the geometry of the widget to data.crect, but clipped to sizes - that OS X can handle. Unmaps widgets that are completely outside the - valid range. - - Maintains data.wrect, which is the geometry of the OS X widget, - measured in this widget's coordinate system. - - if the parent is not clipped, parentWRect is empty, otherwise - parentWRect is the geometry of the parent's OS X rect, measured in - parent's coord sys -*/ -void QWidgetPrivate::setWSGeometry(bool dontShow, const QRect &oldRect) -{ - Q_Q(QWidget); - Q_ASSERT(q->testAttribute(Qt::WA_WState_Created)); - - if (!q->internalWinId() && QApplicationPrivate::graphicsSystem() != 0) { - // We have no view to move, and no paint engine that - // we can update dirty regions on. So just return: - return; - } - - QMacCocoaAutoReleasePool pool; - - /* - There are up to four different coordinate systems here: - Qt coordinate system for this widget. - X coordinate system for this widget (relative to wrect). - Qt coordinate system for parent - X coordinate system for parent (relative to parent's wrect). - */ - - // wrect is the same as crect, except that it is - // clipped to fit inside parent (and screen): - QRect wrect; - - // wrectInParentCoordSys will be the same as wrect, except that it is - // originated in q's parent rather than q itself. It starts out in - // parent's Qt coord system, and ends up in parent's coordinate system: - QRect wrectInParentCoordSys = data.crect; - - // If q's parent has been clipped, parentWRect will - // be filled with the parents clipped crect: - QRect parentWRect; - - // Embedded have different meaning on each platform, and on - // Mac, it means that q is a QMacNativeWidget. - bool isEmbeddedWindow = (q->isWindow() && topData()->embedded); - NSView *nsview = qt_mac_nativeview_for(q); - if (!isEmbeddedWindow) { - parentWRect = q->parentWidget()->data->wrect; - } else { - // INVARIANT: q's parent view is not owned by Qt. So we need to - // do some extra calls to get the clipped rect of the parent view: - NSView *parentView = [qt_mac_nativeview_for(q) superview]; - if (parentView) { - NSRect tmpRect = [parentView frame]; - parentWRect = QRect(tmpRect.origin.x, tmpRect.origin.y, - tmpRect.size.width, tmpRect.size.height); - } else { - const QRect wrectRange(-WRECT_MAX,-WRECT_MAX, 2*WRECT_MAX, 2*WRECT_MAX); - parentWRect = wrectRange; - } - } - - if (parentWRect.isValid()) { - // INVARIANT: q's parent has been clipped. - // So we fit our own wrects inside it: - if (!parentWRect.contains(wrectInParentCoordSys) && !isEmbeddedWindow) { - wrectInParentCoordSys &= parentWRect; - wrect = wrectInParentCoordSys; - // Make sure wrect is originated in q's coordinate system: - wrect.translate(-data.crect.topLeft()); - } - // // Make sure wrectInParentCoordSys originated in q's parent coordinate system: - wrectInParentCoordSys.translate(-parentWRect.topLeft()); - } else { - // INVARIANT: we dont know yet the clipping rect of q's parent. - // So we may or may not have to adjust our wrects: - - if (data.wrect.isValid() && QRect(QPoint(),data.crect.size()).contains(data.wrect)) { - // This is where the main optimization is: we have an old wrect from an earlier - // setGeometry call, and the new crect is smaller than it. If the final wrect is - // also inside the old wrect, we can just move q and its children to the new - // location without any clipping: - - // vrect will be the part of q that's will be visible inside - // q's parent. If it inside the old wrect, then we can just move: - QRect vrect = wrectInParentCoordSys & q->parentWidget()->rect(); - vrect.translate(-data.crect.topLeft()); - - if (data.wrect.contains(vrect)) { - wrectInParentCoordSys = data.wrect; - wrectInParentCoordSys.translate(data.crect.topLeft()); - if (nsview) { - // INVARIANT: q is native. Set view frame: - NSRect bounds = NSMakeRect(wrectInParentCoordSys.x(), wrectInParentCoordSys.y(), - wrectInParentCoordSys.width(), wrectInParentCoordSys.height()); - [nsview setFrame:bounds]; - } else { - // INVARIANT: q is alien. Repaint wrect instead (includes old and new wrect): - QWidget *parent = q->parentWidget(); - QPoint globalPosWRect = parent->mapToGlobal(data.wrect.topLeft()); - - QWidget *nativeParent = q->nativeParentWidget(); - QRect dirtyWRect = QRect(nativeParent->mapFromGlobal(globalPosWRect), data.wrect.size()); - - nativeParent->update(dirtyWRect); - } - if (q->testAttribute(Qt::WA_OutsideWSRange)) { - q->setAttribute(Qt::WA_OutsideWSRange, false); - if (!dontShow) { - q->setAttribute(Qt::WA_Mapped); - // If q is Alien, the following call does nothing: - [nsview setHidden:NO]; - } - } - return; - } - } - - } - - // unmap if we are outside the valid window system coord system - bool outsideRange = !wrectInParentCoordSys.isValid(); - bool mapWindow = false; - if (q->testAttribute(Qt::WA_OutsideWSRange) != outsideRange) { - q->setAttribute(Qt::WA_OutsideWSRange, outsideRange); - if (outsideRange) { - // If q is Alien, the following call does nothing: - [nsview setHidden:YES]; - q->setAttribute(Qt::WA_Mapped, false); - } else if (!q->isHidden()) { - mapWindow = true; - } - } - - if (outsideRange) - return; - - // Store the new clipped rect: - bool jump = (data.wrect != wrect); - data.wrect = wrect; - - // and now recursively for all children... - // ### can be optimized - for (int i = 0; i < children.size(); ++i) { - QObject *object = children.at(i); - if (object->isWidgetType()) { - QWidget *w = static_cast(object); - if (!w->isWindow() && w->testAttribute(Qt::WA_WState_Created)) - w->d_func()->setWSGeometry(); - } - } - - if (nsview) { - // INVARIANT: q is native. Move the actual NSView: - NSRect bounds = NSMakeRect( - wrectInParentCoordSys.x(), wrectInParentCoordSys.y(), - wrectInParentCoordSys.width(), wrectInParentCoordSys.height()); - [nsview setFrame:bounds]; - if (jump) - q->update(); - } else if (QApplicationPrivate::graphicsSystem() == 0){ - // INVARIANT: q is alien and we use native paint engine. - // Schedule updates where q is moved from and to: - const QWidget *parent = q->parentWidget(); - const QPoint globalPosOldWRect = parent->mapToGlobal(oldRect.topLeft()); - const QPoint globalPosNewWRect = parent->mapToGlobal(wrectInParentCoordSys.topLeft()); - - QWidget *nativeParent = q->nativeParentWidget(); - const QRegion dirtyOldWRect = QRect(nativeParent->mapFromGlobal(globalPosOldWRect), oldRect.size()); - const QRegion dirtyNewWRect = QRect(nativeParent->mapFromGlobal(globalPosNewWRect), wrectInParentCoordSys.size()); - - const bool sizeUnchanged = oldRect.size() == wrectInParentCoordSys.size(); - const bool posUnchanged = oldRect.topLeft() == wrectInParentCoordSys.topLeft(); - - // Resolve/minimize the region that needs to update: - if (sizeUnchanged && q->testAttribute(Qt::WA_OpaquePaintEvent)) { - // INVARIANT: q is opaque, and is only moved (not resized). So in theory we only - // need to blit pixels, and skip a repaint. But we can only make this work if we - // had access to the backbuffer, so we need to update all: - nativeParent->update(dirtyOldWRect | dirtyNewWRect); - } else if (posUnchanged && q->testAttribute(Qt::WA_StaticContents)) { - // We only need to redraw exposed areas: - nativeParent->update(dirtyNewWRect - dirtyOldWRect); - } else { - nativeParent->update(dirtyOldWRect | dirtyNewWRect); - } - } - - if (mapWindow && !dontShow) { - q->setAttribute(Qt::WA_Mapped); - // If q is Alien, the following call does nothing: - [nsview setHidden:NO]; - } -} - -void QWidgetPrivate::adjustWithinMaxAndMinSize(int &w, int &h) -{ - if (QWExtra *extra = extraData()) { - w = qMin(w, extra->maxw); - h = qMin(h, extra->maxh); - w = qMax(w, extra->minw); - h = qMax(h, extra->minh); - - // Deal with size increment - if (QTLWExtra *top = topData()) { - if(top->incw) { - w = w/top->incw; - w *= top->incw; - } - if(top->inch) { - h = h/top->inch; - h *= top->inch; - } - } - } - - if (isRealWindow()) { - w = qMax(0, w); - h = qMax(0, h); - } -} - -void QWidgetPrivate::applyMaxAndMinSizeOnWindow() -{ - Q_Q(QWidget); - QMacCocoaAutoReleasePool pool; - - const float max_f(20000); -#define SF(x) ((x > max_f) ? max_f : x) - NSSize max = NSMakeSize(SF(extra->maxw), SF(extra->maxh)); - NSSize min = NSMakeSize(SF(extra->minw), SF(extra->minh)); -#undef SF - [qt_mac_window_for(q) setContentMinSize:min]; - [qt_mac_window_for(q) setContentMaxSize:max]; -} - -void QWidgetPrivate::setGeometry_sys(int x, int y, int w, int h, bool isMove) -{ - Q_Q(QWidget); - Q_ASSERT(q->testAttribute(Qt::WA_WState_Created)); - - if(q->windowType() == Qt::Desktop) - return; - - QMacCocoaAutoReleasePool pool; - bool realWindow = isRealWindow(); - - if (realWindow && !q->testAttribute(Qt::WA_DontShowOnScreen)){ - adjustWithinMaxAndMinSize(w, h); - if (!isMove && !q->testAttribute(Qt::WA_Moved) && !q->isVisible()) { - // INVARIANT: The location of the window has not yet been set. The default will - // instead be to center it on the desktop, or over the parent, if any. Since we now - // resize the window, we need to adjust the top left position to keep the window - // centeralized. And we need to to this now (and before show) in case the positioning - // of other windows (e.g. sub-windows) depend on this position: - if (QWidget *p = q->parentWidget()) { - x = p->geometry().center().x() - (w / 2); - y = p->geometry().center().y() - (h / 2); - } else { - QRect availGeo = QApplication::desktop()->availableGeometry(q); - x = availGeo.center().x() - (w / 2); - y = availGeo.center().y() - (h / 2); - } - } - - QSize olds = q->size(); - const bool isResize = (olds != QSize(w, h)); - NSWindow *window = qt_mac_window_for(q); - const QRect &fStrut = frameStrut(); - const QRect frameRect(QPoint(x - fStrut.left(), y - fStrut.top()), - QSize(fStrut.left() + fStrut.right() + w, - fStrut.top() + fStrut.bottom() + h)); - NSRect cocoaFrameRect = NSMakeRect(frameRect.x(), flipYCoordinate(frameRect.bottom() + 1), - frameRect.width(), frameRect.height()); - // The setFrame call will trigger a 'windowDidResize' notification for the corresponding - // NSWindow. The pending flag is set, so that the resize event can be send as non-spontaneous. - if (isResize) - q->setAttribute(Qt::WA_PendingResizeEvent); - QPoint currTopLeft = data.crect.topLeft(); - if (currTopLeft.x() == x && currTopLeft.y() == y - && cocoaFrameRect.size.width != 0 - && cocoaFrameRect.size.height != 0) { - [window setFrame:cocoaFrameRect display:realWindow]; - } else { - // The window is moved and resized (or resized to zero). - // Since Cocoa usually only sends us a resize callback after - // setting a window frame, we issue an explicit move as - // well. To stop Cocoa from optimize away the move (since the move - // would have the same origin as the setFrame call) we shift the - // window back and forth inbetween. - cocoaFrameRect.origin.y += 1; - [window setFrame:cocoaFrameRect display:realWindow]; - cocoaFrameRect.origin.y -= 1; - [window setFrameOrigin:cocoaFrameRect.origin]; - } - } else { - setGeometry_sys_helper(x, y, w, h, isMove); - } - - topLevelAt_cache = 0; -} - -void QWidgetPrivate::setGeometry_sys_helper(int x, int y, int w, int h, bool isMove) -{ - Q_Q(QWidget); - bool realWindow = isRealWindow(); - - QPoint oldp = q->pos(); - QSize olds = q->size(); - // Apply size restrictions, applicable for Windows & Widgets. - if (QWExtra *extra = extraData()) { - w = qBound(extra->minw, w, extra->maxw); - h = qBound(extra->minh, h, extra->maxh); - } - const bool isResize = (olds != QSize(w, h)); - - if (!realWindow && !isResize && QPoint(x, y) == oldp) - return; - - if (isResize) - data.window_state = data.window_state & ~Qt::WindowMaximized; - - const bool visible = q->isVisible(); - data.crect = QRect(x, y, w, h); - - if (realWindow) { - adjustWithinMaxAndMinSize(w, h); - qt_mac_update_sizer(q); - - [qt_mac_nativeview_for(q) setFrame:NSMakeRect(0, 0, w, h)]; - } else { - const QRect oldRect(oldp, olds); - if (!isResize && QApplicationPrivate::graphicsSystem()) - moveRect(oldRect, x - oldp.x(), y - oldp.y()); - - setWSGeometry(false, oldRect); - - if (isResize && QApplicationPrivate::graphicsSystem()) - invalidateBuffer_resizeHelper(oldp, olds); - } - - if(isMove || isResize) { - if(!visible) { - if(isMove && q->pos() != oldp) - q->setAttribute(Qt::WA_PendingMoveEvent, true); - if(isResize) - q->setAttribute(Qt::WA_PendingResizeEvent, true); - } else { - if(isResize) { //send the resize event.. - QResizeEvent e(q->size(), olds); - QApplication::sendEvent(q, &e); - } - if(isMove && q->pos() != oldp) { //send the move event.. - QMoveEvent e(q->pos(), oldp); - QApplication::sendEvent(q, &e); - } - } - } - qt_event_request_window_change(q); -} - -void QWidgetPrivate::setConstraints_sys() -{ - updateMaximizeButton_sys(); - applyMaxAndMinSizeOnWindow(); -} - -void QWidgetPrivate::updateMaximizeButton_sys() -{ - Q_Q(QWidget); - if (q->data->window_flags & Qt::CustomizeWindowHint) - return; - - OSWindowRef window = qt_mac_window_for(q); - QTLWExtra * tlwExtra = topData(); - QMacCocoaAutoReleasePool pool; - NSButton *maximizeButton = [window standardWindowButton:NSWindowZoomButton]; - if (extra->maxw && extra->maxh - && extra->maxw == extra->minw - && extra->maxh == extra->minh) { - // The window has a fixed size, so gray out the maximize button: - if (!tlwExtra->savedWindowAttributesFromMaximized) { - tlwExtra->savedWindowAttributesFromMaximized = (![maximizeButton isHidden] && [maximizeButton isEnabled]); - } - [maximizeButton setEnabled:NO]; - - - } else { - if (tlwExtra->savedWindowAttributesFromMaximized) { - [maximizeButton setEnabled:YES]; - tlwExtra->savedWindowAttributesFromMaximized = 0; - } - } - - -} - -void QWidgetPrivate::scroll_sys(int dx, int dy) -{ - if (QApplicationPrivate::graphicsSystem() && !paintOnScreen()) { - // INVARIANT: Alien paint engine - scrollChildren(dx, dy); - scrollRect(q_func()->rect(), dx, dy); - } else { - scroll_sys(dx, dy, QRect()); - } -} - -void QWidgetPrivate::scroll_sys(int dx, int dy, const QRect &qscrollRect) -{ - if (QMacScrollOptimization::delayScroll(this, dx, dy, qscrollRect)) - return; - - Q_Q(QWidget); - if (QApplicationPrivate::graphicsSystem() && !paintOnScreen()) { - // INVARIANT: Alien paint engine - scrollRect(qscrollRect, dx, dy); - return; - } - - static int accelEnv = -1; - if (accelEnv == -1) { - accelEnv = qgetenv("QT_NO_FAST_SCROLL").toInt() == 0; - } - - // Scroll the whole widget if qscrollRect is not valid: - QRect validScrollRect = qscrollRect.isValid() ? qscrollRect : q->rect(); - validScrollRect &= clipRect(); - - // If q is overlapped by other widgets, we cannot just blit pixels since - // this will move overlapping widgets as well. In case we just update: - const bool overlapped = isOverlapped(validScrollRect.translated(data.crect.topLeft())); - const bool accelerateScroll = accelEnv && isOpaque && !overlapped; - const bool isAlien = (q->internalWinId() == 0); - const QPoint scrollDelta(dx, dy); - - // If qscrollRect is valid, we are _not_ supposed to scroll q's children (as documented). - // But we do scroll children (and the whole of q) if qscrollRect is invalid. This case is - // documented as undefined, but we exploit it to help factor our code into one function. - const bool scrollChildren = !qscrollRect.isValid(); - - if (!q->updatesEnabled()) { - // We are told not to update anything on q at this point. So unless - // we are supposed to scroll children, we bail out early: - if (!scrollChildren || q->children().isEmpty()) - return; - } - - if (!accelerateScroll) { - if (overlapped) { - QRegion region(validScrollRect); - subtractOpaqueSiblings(region); - update_sys(region); - }else { - update_sys(qscrollRect); - } - return; - } - - QMacCocoaAutoReleasePool pool; - - // First move all native children. Alien children will indirectly be - // moved when the parent is scrolled. All directly or indirectly moved - // children will receive a move event before the function call returns. - QWidgetList movedChildren; - if (scrollChildren) { - QObjectList children = q->children(); - - for (int i=0; i(obj)) { - if (!w->isWindow()) { - w->data->crect = QRect(w->pos() + scrollDelta, w->size()); - if (NSView *view = qt_mac_nativeview_for(w)) { - // INVARIANT: w is not alien - [view setFrame:NSMakeRect( - w->data->crect.x(), w->data->crect.y(), - w->data->crect.width(), w->data->crect.height())]; - } - movedChildren.append(w); - } - } - } - } - - if (q->testAttribute(Qt::WA_WState_Created) && q->isVisible()) { - // Scroll q itself according to the qscrollRect, and - // call update on any exposed areas so that they get redrawn: - - - QWidget *nativeWidget = isAlien ? q->nativeParentWidget() : q; - if (!nativeWidget) - return; - OSViewRef view = qt_mac_nativeview_for(nativeWidget); - if (!view) - return; - - // Calculate the rectangles that needs to be redrawn - // after the scroll. This will be source rect minus destination rect: - QRect deltaXRect; - if (dx != 0) { - deltaXRect.setY(validScrollRect.y()); - deltaXRect.setHeight(validScrollRect.height()); - if (dx > 0) { - deltaXRect.setX(validScrollRect.x()); - deltaXRect.setWidth(dx); - } else { - deltaXRect.setX(validScrollRect.x() + validScrollRect.width() + dx); - deltaXRect.setWidth(-dx); - } - } - - QRect deltaYRect; - if (dy != 0) { - deltaYRect.setX(validScrollRect.x()); - deltaYRect.setWidth(validScrollRect.width()); - if (dy > 0) { - deltaYRect.setY(validScrollRect.y()); - deltaYRect.setHeight(dy); - } else { - deltaYRect.setY(validScrollRect.y() + validScrollRect.height() + dy); - deltaYRect.setHeight(-dy); - } - } - - if (isAlien) { - // Adjust the scroll rect to the location as seen from the native parent: - QPoint scrollTopLeftInsideNative = nativeWidget->mapFromGlobal(q->mapToGlobal(validScrollRect.topLeft())); - validScrollRect.moveTo(scrollTopLeftInsideNative); - } - - // Make the pixel copy rect within the validScrollRect bounds: - NSRect nsscrollRect = NSMakeRect( - validScrollRect.x() + (dx < 0 ? -dx : 0), - validScrollRect.y() + (dy < 0 ? -dy : 0), - validScrollRect.width() + (dx > 0 ? -dx : 0), - validScrollRect.height() + (dy > 0 ? -dy : 0)); - - NSSize deltaSize = NSMakeSize(dx, dy); - [view scrollRect:nsscrollRect by:deltaSize]; - - // Some areas inside the scroll rect might have been marked as dirty from before, which - // means that they are scheduled to be redrawn. But as we now scroll, those dirty rects - // should also move along to ensure that q receives repaints on the correct places. - // Since some of the dirty rects might lay outside, or only intersect with, the scroll - // rect, the old calls to setNeedsDisplay still makes sense. - // NB: Using [view translateRectsNeedingDisplayInRect:nsscrollRect by:deltaSize] have - // so far not been proven fruitful to solve this problem. - const QVector &dirtyRectsToScroll = dirtyOnWidget.rects(); - for (int i=0; ipos(), w->pos() - scrollDelta); - QApplication::sendEvent(w, &e); - } -} - -int QWidget::metric(PaintDeviceMetric m) const -{ - switch(m) { - case PdmHeightMM: - return qRound(metric(PdmHeight) * 25.4 / qreal(metric(PdmDpiY))); - case PdmWidthMM: - return qRound(metric(PdmWidth) * 25.4 / qreal(metric(PdmDpiX))); - case PdmHeight: - case PdmWidth: - if (m == PdmWidth) - return data->crect.width(); - else - return data->crect.height(); - case PdmDepth: - return 32; - case PdmNumColors: - return INT_MAX; - case PdmDpiX: - case PdmPhysicalDpiX: { - Q_D(const QWidget); - if (d->extra && d->extra->customDpiX) - return d->extra->customDpiX; - else if (d->parent) - return static_cast(d->parent)->metric(m); - extern float qt_mac_defaultDpi_x(); //qpaintdevice_mac.cpp - return int(qt_mac_defaultDpi_x()); } - case PdmDpiY: - case PdmPhysicalDpiY: { - Q_D(const QWidget); - if (d->extra && d->extra->customDpiY) - return d->extra->customDpiY; - else if (d->parent) - return static_cast(d->parent)->metric(m); - extern float qt_mac_defaultDpi_y(); //qpaintdevice_mac.cpp - return int(qt_mac_defaultDpi_y()); } - default: //leave this so the compiler complains when new ones are added - qWarning("QWidget::metric: Unhandled parameter %d", m); - return QPaintDevice::metric(m); - } - return 0; -} - -void QWidgetPrivate::createSysExtra() -{ - extra->imageMask = 0; -} - -void QWidgetPrivate::deleteSysExtra() -{ - if (extra->imageMask) - CFRelease(extra->imageMask); -} - -void QWidgetPrivate::createTLSysExtra() -{ - extra->topextra->resizer = 0; - extra->topextra->isSetGeometry = 0; - extra->topextra->isMove = 0; - extra->topextra->wattr = 0; - extra->topextra->wclass = 0; - extra->topextra->group = 0; - extra->topextra->windowIcon = 0; - extra->topextra->savedWindowAttributesFromMaximized = 0; -} - -void QWidgetPrivate::deleteTLSysExtra() -{ -} - -void QWidgetPrivate::updateFrameStrut() -{ - Q_Q(QWidget); - - QWidgetPrivate *that = const_cast(this); - - that->data.fstrut_dirty = false; - QTLWExtra *top = that->topData(); - - // 1 Get the window frame - OSWindowRef oswnd = qt_mac_window_for(q); - NSRect frameW = [oswnd frame]; - // 2 Get the content frame - so now - NSRect frameC = [oswnd contentRectForFrameRect:frameW]; - top->frameStrut.setCoords(frameC.origin.x - frameW.origin.x, - (frameW.origin.y + frameW.size.height) - (frameC.origin.y + frameC.size.height), - (frameW.origin.x + frameW.size.width) - (frameC.origin.x + frameC.size.width), - frameC.origin.y - frameW.origin.y); -} - -void QWidgetPrivate::registerDropSite(bool on) -{ - Q_Q(QWidget); - if (!q->testAttribute(Qt::WA_WState_Created)) - return; - NSWindow *win = qt_mac_window_for(q); - if (on) { - if ([win isKindOfClass:[QT_MANGLE_NAMESPACE(QCocoaWindow) class]]) - [static_cast(win) registerDragTypes]; - else if ([win isKindOfClass:[QT_MANGLE_NAMESPACE(QCocoaPanel) class]]) - [static_cast(win) registerDragTypes]; - } -} - -void QWidgetPrivate::registerTouchWindow(bool enable) -{ - Q_UNUSED(enable); -#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_6 - if (QSysInfo::MacintoshVersion < QSysInfo::MV_10_6) - return; - - Q_Q(QWidget); - if (enable == touchEventsEnabled) - return; - - QT_MANGLE_NAMESPACE(QCocoaView) *view = static_cast(qt_mac_effectiveview_for(q)); - if (!view) - return; - - if (enable) { - ++view->alienTouchCount; - if (view->alienTouchCount == 1) { - touchEventsEnabled = true; - [view setAcceptsTouchEvents:YES]; - } - } else { - --view->alienTouchCount; - if (view->alienTouchCount == 0) { - touchEventsEnabled = false; - [view setAcceptsTouchEvents:NO]; - } - } -#endif -} - -void QWidgetPrivate::setMask_sys(const QRegion ®ion) -{ - Q_UNUSED(region); - Q_Q(QWidget); - - if (!q->internalWinId()) - return; - - if (extra->mask.isEmpty()) { - extra->maskBits = QImage(); - finishCocoaMaskSetup(); - } else { - syncCocoaMask(); - } - - topLevelAt_cache = 0; -} - -void QWidgetPrivate::setWindowOpacity_sys(qreal level) -{ - Q_Q(QWidget); - - if (!q->isWindow()) - return; - - level = qBound(0.0, level, 1.0); - topData()->opacity = (uchar)(level * 255); - if (!q->testAttribute(Qt::WA_WState_Created)) - return; - - OSWindowRef oswindow = qt_mac_window_for(q); - [oswindow setAlphaValue:level]; -} - -void QWidgetPrivate::syncCocoaMask() -{ - Q_Q(QWidget); - if (!q->testAttribute(Qt::WA_WState_Created) || !extra) - return; - - if (extra->hasMask) { - if(extra->maskBits.size() != q->size()) { - extra->maskBits = QImage(q->size(), QImage::Format_Mono); - } - extra->maskBits.fill(QColor(Qt::color1).rgba()); - extra->maskBits.setNumColors(2); - extra->maskBits.setColor(0, QColor(Qt::color0).rgba()); - extra->maskBits.setColor(1, QColor(Qt::color1).rgba()); - QPainter painter(&extra->maskBits); - painter.setBrush(Qt::color1); - painter.setPen(Qt::NoPen); - painter.drawRects(extra->mask.rects()); - painter.end(); - finishCocoaMaskSetup(); - } -} - -void QWidgetPrivate::finishCocoaMaskSetup() -{ - Q_Q(QWidget); - - if (!q->testAttribute(Qt::WA_WState_Created) || !extra) - return; - - // Technically this is too late to release, because the data behind the image - // has already been released. But it's more tidy to do it here. - // If you are seeing a crash, consider doing a CFRelease before changing extra->maskBits. - if (extra->imageMask) { - CFRelease(extra->imageMask); - extra->imageMask = 0; - } - - if (!extra->maskBits.isNull()) { - QCFType dataProvider = CGDataProviderCreateWithData(0, - extra->maskBits.bits(), - extra->maskBits.numBytes(), - 0); // shouldn't need to release. - CGFloat decode[2] = {1, 0}; - extra->imageMask = CGImageMaskCreate(extra->maskBits.width(), extra->maskBits.height(), - 1, 1, extra->maskBits.bytesPerLine(), dataProvider, - decode, false); - } - if (q->isWindow()) { - NSWindow *window = qt_mac_window_for(q); - [window setOpaque:(extra->imageMask == 0)]; - [window invalidateShadow]; - } - macSetNeedsDisplay(QRegion()); -} - -struct QPaintEngineCleanupHandler -{ - inline QPaintEngineCleanupHandler() : engine(0) {} - inline ~QPaintEngineCleanupHandler() { delete engine; } - QPaintEngine *engine; -}; - -Q_GLOBAL_STATIC(QPaintEngineCleanupHandler, engineHandler) - -QPaintEngine *QWidget::paintEngine() const -{ - QPaintEngine *&pe = engineHandler()->engine; - if (!pe) - pe = new QCoreGraphicsPaintEngine(); - if (pe->isActive()) { - QPaintEngine *engine = new QCoreGraphicsPaintEngine(); - engine->setAutoDestruct(true); - return engine; - } - return pe; -} - -void QWidgetPrivate::setModal_sys() -{ - Q_Q(QWidget); - if (!q->testAttribute(Qt::WA_WState_Created) || !q->isWindow()) - return; - const QWidget * const windowParent = q->window()->parentWidget(); - const QWidget * const primaryWindow = windowParent ? windowParent->window() : 0; - OSWindowRef windowRef = qt_mac_window_for(q); - - QMacCocoaAutoReleasePool pool; - bool alreadySheet = [windowRef styleMask] & NSDocModalWindowMask; - - if (windowParent && q->windowModality() == Qt::WindowModal){ - // INVARIANT: Window should be window-modal (which implies a sheet). - if (!alreadySheet) { - // NB: the following call will call setModal_sys recursivly: - recreateMacWindow(); - windowRef = qt_mac_window_for(q); - } - if ([windowRef isKindOfClass:[NSPanel class]]){ - // If the primary window of the sheet parent is a child of a modal dialog, - // the sheet parent should not be modally shaddowed. - // This goes for the sheet as well: - OSWindowRef ref = primaryWindow ? qt_mac_window_for(primaryWindow) : 0; - bool isDialog = ref ? [ref isKindOfClass:[NSPanel class]] : false; - bool worksWhenModal = isDialog ? [static_cast(ref) worksWhenModal] : false; - if (worksWhenModal) - [static_cast(windowRef) setWorksWhenModal:YES]; - } - } else { - // INVARIANT: Window shold _not_ be window-modal (and as such, not a sheet). - if (alreadySheet){ - // NB: the following call will call setModal_sys recursivly: - recreateMacWindow(); - windowRef = qt_mac_window_for(q); - } - if (q->windowModality() == Qt::NonModal - && primaryWindow && primaryWindow->windowModality() == Qt::ApplicationModal) { - // INVARIANT: Our window has a parent that is application modal. - // This means that q is supposed to be on top of this window and - // not be modally shaddowed: - if ([windowRef isKindOfClass:[NSPanel class]]) - [static_cast(windowRef) setWorksWhenModal:YES]; - } - } - -} - -void QWidgetPrivate::macUpdateHideOnSuspend() -{ - Q_Q(QWidget); - if (!q->testAttribute(Qt::WA_WState_Created) || !q->isWindow() || q->windowType() != Qt::Tool) - return; - if(q->testAttribute(Qt::WA_MacAlwaysShowToolWindow)) - [qt_mac_window_for(q) setHidesOnDeactivate:NO]; - else - [qt_mac_window_for(q) setHidesOnDeactivate:YES]; -} - -void QWidgetPrivate::macUpdateOpaqueSizeGrip() -{ - Q_Q(QWidget); - - if (!q->testAttribute(Qt::WA_WState_Created) || !q->isWindow()) - return; - -} - -void QWidgetPrivate::macUpdateSizeAttribute() -{ - Q_Q(QWidget); - QEvent event(QEvent::MacSizeChange); - QApplication::sendEvent(q, &event); - for (int i = 0; i < children.size(); ++i) { - QWidget *w = qobject_cast(children.at(i)); - if (w && (!w->isWindow() || w->testAttribute(Qt::WA_WindowPropagation)) - && !q->testAttribute(Qt::WA_MacMiniSize) // no attribute set? inherit from parent - && !w->testAttribute(Qt::WA_MacSmallSize) - && !w->testAttribute(Qt::WA_MacNormalSize)) - w->d_func()->macUpdateSizeAttribute(); - } - resolveFont(); -} - -void QWidgetPrivate::macUpdateIgnoreMouseEvents() -{ -} - -void QWidgetPrivate::macUpdateMetalAttribute() -{ - Q_Q(QWidget); - bool realWindow = isRealWindow(); - if (!q->testAttribute(Qt::WA_WState_Created) || !realWindow) - return; - - if (realWindow) { - // Cocoa doesn't let us change the style mask once it's been changed - // So, that means we need to recreate the window. - OSWindowRef cocoaWindow = qt_mac_window_for(q); - if ([cocoaWindow styleMask] & NSTexturedBackgroundWindowMask) - return; - recreateMacWindow(); - } -} - -void QWidgetPrivate::setEnabled_helper_sys(bool enable) -{ - Q_Q(QWidget); - NSView *view = qt_mac_nativeview_for(q); - if ([view isKindOfClass:[NSControl class]]) - [static_cast(view) setEnabled:enable]; -} - -QT_END_NAMESPACE diff --git a/src/widgets/styles/qmacstyle_mac.mm b/src/widgets/styles/qmacstyle_mac.mm index ca9b5cf..fff3c3c 100644 --- a/src/widgets/styles/qmacstyle_mac.mm +++ b/src/widgets/styles/qmacstyle_mac.mm @@ -44,6 +44,8 @@ .../doc/src/qstyles.qdoc. */ +#include + #include "qmacstyle_mac.h" #include "qmacstyle_mac_p.h" #include "qmacstylepixmaps_mac_p.h" diff --git a/src/widgets/widgets/qmenu.cpp b/src/widgets/widgets/qmenu.cpp index a255b84..fa9fc5c 100644 --- a/src/widgets/widgets/qmenu.cpp +++ b/src/widgets/widgets/qmenu.cpp @@ -74,12 +74,6 @@ # include #endif -#if defined(Q_OS_MAC) && !defined(QT_NO_EFFECTS) -# include -# include -#endif - - QT_BEGIN_NAMESPACE QMenu *QMenuPrivate::mouseDown = 0; diff --git a/src/widgets/widgets/qmenu_p.h b/src/widgets/widgets/qmenu_p.h index a6e700b..072e6ed 100644 --- a/src/widgets/widgets/qmenu_p.h +++ b/src/widgets/widgets/qmenu_p.h @@ -55,9 +55,6 @@ #include "QtWidgets/qmenubar.h" #include "QtWidgets/qstyleoption.h" -#ifdef Q_OS_MAC -#include "QtWidgets/qmacdefines_mac.h" -#endif #include "QtCore/qdatetime.h" #include "QtCore/qmap.h" #include "QtCore/qhash.h" diff --git a/src/widgets/widgets/qmenubar.h b/src/widgets/widgets/qmenubar.h index 84fb378..13e9336 100644 --- a/src/widgets/widgets/qmenubar.h +++ b/src/widgets/widgets/qmenubar.h @@ -43,10 +43,6 @@ #define QMENUBAR_H #include -#ifdef Q_OS_MAC -#include "QtWidgets/qmacdefines_mac.h" -#endif - QT_BEGIN_HEADER @@ -157,12 +153,6 @@ private: friend class QMenu; friend class QMenuPrivate; friend class QWindowsStyle; - -#ifdef Q_OS_MAC - friend class QApplicationPrivate; - friend class QWidgetPrivate; - friend bool qt_mac_activate_action(MenuRef, uint, QAction::ActionEvent, bool); -#endif }; #endif // QT_NO_MENUBAR diff --git a/tests/auto/other/macgui/guitest.cpp b/tests/auto/other/macgui/guitest.cpp index 6ab5a64..8383fd0 100644 --- a/tests/auto/other/macgui/guitest.cpp +++ b/tests/auto/other/macgui/guitest.cpp @@ -48,7 +48,7 @@ #include #ifdef Q_OS_MAC -# include +# include #endif