[rkward-cvs] SF.net SVN: rkward:[2518] trunk/rkward/rkward
tfry at users.sourceforge.net
tfry at users.sourceforge.net
Fri Jun 5 20:42:07 UTC 2009
Revision: 2518
http://rkward.svn.sourceforge.net/rkward/?rev=2518&view=rev
Author: tfry
Date: 2009-06-05 20:42:07 +0000 (Fri, 05 Jun 2009)
Log Message:
-----------
Geometry handling of windows devices works, now. Other things don't, yet.
Modified Paths:
--------------
trunk/rkward/rkward/qwinhost/README.txt
trunk/rkward/rkward/qwinhost/qwinhost.cpp
trunk/rkward/rkward/qwinhost/qwinhost.h
trunk/rkward/rkward/rbackend/rembedinternal.cpp
trunk/rkward/rkward/rkwardapplication.cpp
trunk/rkward/rkward/windows/rkwindowcatcher.cpp
Added Paths:
-----------
trunk/rkward/rkward/qwinhost/qwinhost.cpp.orig
trunk/rkward/rkward/qwinhost/qwinhost.h.orig
Modified: trunk/rkward/rkward/qwinhost/README.txt
===================================================================
--- trunk/rkward/rkward/qwinhost/README.txt 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/qwinhost/README.txt 2009-06-05 20:42:07 UTC (rev 2518)
@@ -1,5 +1,6 @@
-This directory contains the files qwinhost.cpp and qwinhost.h which are part
-of the "Qt/MFC Migration Framework" version 2.8 from Qt solutions.
+The files qwinhost.cpp and qwinhost.h in this directory are derivatives
+of the files of the same names in the "Qt/MFC Migration Framework"
+version 2.8 from Qt solutions.
http://www.qtsoftware.com/products/appdev/add-on-products/catalog/4/Windows/qtwinmigrate/
These files are
@@ -8,10 +9,18 @@
The applicable licences are contained in this directory in full form.
-The files qwinhost.cpp and qwinhost.h are unmodified copies from the
-"Qt/MFC Migration Framework" version 2.8. Nethertheless, since these files are
-usually part of a larger package, this copy must be regarded as a
-modified work. The original copyright holder(s) Nokia Corporation and/or its
+The files qwinhost.cpp.orig and qwinhost.h.orig are unmodified copies from the
+"Qt/MFC Migration Framework" version 2.8. The files qwinhost.cpp and qwinhost.h
+are modified for the needs of this project.
+
+The original copyright holder(s) Nokia Corporation and/or its
subsidiary(-ies) are not to be held responsible for any malfunctioning.
These files are used on windows, only.
+
+Changes with respect to the qwinhost.cpp.orig and qwinhost.h.orig:
+
+2009-06-05:
+- Support for auto-destruction of client
+- Notification when client is destroyed
+- Notification when client window title changes
\ No newline at end of file
Modified: trunk/rkward/rkward/qwinhost/qwinhost.cpp
===================================================================
--- trunk/rkward/rkward/qwinhost/qwinhost.cpp 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/qwinhost/qwinhost.cpp 2009-06-05 20:42:07 UTC (rev 2518)
@@ -53,8 +53,10 @@
#include "qwinhost.h"
#include <QtCore/QEvent>
-#include <qt_windows.h>
+//static
+QMap<HWND, QWinHost*> QWinHost::winhosts;
+
/*!
\class QWinHost qwinhost.h
\brief The QWinHost class provides an API to use native Win32
@@ -87,7 +89,7 @@
QWidget::setParent or move the QWinHost into a different layout.
*/
QWinHost::QWinHost(QWidget *parent, Qt::WFlags f)
-: QWidget(parent, f), wndproc(0),own_hwnd(false), hwnd(0)
+: QWidget(parent, f), wndproc(0),auto_destruct(false), hwnd(0)
{
setAttribute(Qt::WA_NoBackground);
setAttribute(Qt::WA_NoSystemBackground);
@@ -116,10 +118,23 @@
#endif
}
- if (hwnd && own_hwnd)
+ if (hwnd) {
+ winhosts.remove(hwnd);
+ }
+
+ if (hwnd && isAutoDestruct()) {
+ setAutoDestruct(false);
+ SendMessage(hwnd, WM_CLOSE, 0, 0);
DestroyWindow(hwnd);
+qDebug ("destruct");
+ }
}
+// static
+QWinHost *QWinHost::findHost (HWND client) {
+ return (winhosts.value(client));
+}
+
/*!
Reimplement this virtual function to create and return the native
Win32 window. \a parent is the handle to this widget, and \a
@@ -143,46 +158,21 @@
return 0;
}
-/*!
- Ensures that the window provided a child of this widget, unless
- it is a WS_OVERLAPPED window.
-*/
-void QWinHost::fixParent()
-{
- if (!hwnd)
- return;
- if (!::IsWindow(hwnd)) {
- hwnd = 0;
- return;
- }
- if (::GetParent(hwnd) == winId())
- return;
- long style = GetWindowLong(hwnd, GWL_STYLE);
- if (style & WS_OVERLAPPED)
- return;
- ::SetParent(hwnd, winId());
-}
/*!
Sets the native Win32 window to \a window. If \a window is not a child
window of this widget, then it is reparented to become one. If \a window
is not a child window (i.e. WS_OVERLAPPED is set), then this function does nothing.
- The lifetime of the window handle will be managed by Windows, QWinHost does not
- call DestroyWindow. To verify that the handle is destroyed when expected, handle
- WM_DESTROY in the window procedure.
-
- \sa window(), createWindow()
+ \sa window(), createWindow(), setAutoDestruct()
*/
void QWinHost::setWindow(HWND window)
{
- if (hwnd && own_hwnd)
+ if (hwnd && isAutoDestruct())
DestroyWindow(hwnd);
hwnd = window;
fixParent();
-
- own_hwnd = false;
}
/*!
@@ -196,44 +186,83 @@
return hwnd;
}
+/*!
+ \see setAutoDestruct()
+*/
+bool QWinHost::isAutoDestruct() const
+{
+ return auto_destruct;
+}
+
+/*!
+ \a destruct if this is false (the default), the lifetime of the window handle
+ will be managed by Windows, QWinHost does not
+ call DestroyWindow. To verify that the handle is destroyed when expected, handle
+ WM_DESTROY in the window procedure. If \a destruct is true, the client window
+ will be destroyed, when this window is destroyed.
+
+ For windows created by createWindow(), this is set to true, else the default is false.
+
+ \sa isAutoDestruct()
+ */
+void QWinHost::setAutoDestruct(bool destruct)
+{
+ auto_destruct = destruct;
+}
+
void *getWindowProc(QWinHost *host)
{
return host ? host->wndproc : 0;
}
+bool QWinHost::handleWindowCallback (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) {
+qDebug ("%p, %x, %x, %x", hwnd, msg, wParam, lParam);
+ switch(msg) {
+ case WM_LBUTTONDOWN:
+ if (::GetFocus() != hwnd && (focusPolicy() & Qt::ClickFocus)) {
+#warning TODO: async handling!
+ setFocus(Qt::MouseFocusReason);
+ }
+ break;
+
+ case WM_SYSKEYDOWN:
+ case WM_SYSKEYUP:
+ QT_WA({
+ SendMessage(winId(), msg, wParam, lParam);
+ }, {
+ SendMessageA(winId(), msg, wParam, lParam);
+ })
+ break;
+
+ case WM_KEYDOWN:
+ if (wParam == VK_TAB) {
+ QT_WA({
+ SendMessage(winId(), msg, wParam, lParam);
+ }, {
+ SendMessageA(winId(), msg, wParam, lParam);
+ })
+ }
+ break;
+ case WM_SETTEXT:
+ clientTitleChanged((char *) lParam);
+ break;
+ case WM_DESTROY:
+qDebug ("client destruct");
+ clientDestroyed();
+ break;
+ default:
+ break;
+ }
+}
+
+
LRESULT CALLBACK WinHostProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
- QWinHost *widget = qobject_cast<QWinHost*>(QWidget::find(::GetParent(hwnd)));
+ QWinHost *widget = QWinHost::findHost(hwnd);
WNDPROC oldproc = (WNDPROC)getWindowProc(widget);
if (widget) {
- switch(msg) {
- case WM_LBUTTONDOWN:
- if (::GetFocus() != hwnd && (widget->focusPolicy() & Qt::ClickFocus)) {
- widget->setFocus(Qt::MouseFocusReason);
- }
- break;
-
- case WM_SYSKEYDOWN:
- case WM_SYSKEYUP:
- QT_WA({
- SendMessage(widget->winId(), msg, wParam, lParam);
- }, {
- SendMessageA(widget->winId(), msg, wParam, lParam);
- })
- break;
-
- case WM_KEYDOWN:
- if (wParam == VK_TAB) {
- QT_WA({
- SendMessage(widget->winId(), msg, wParam, lParam);
- }, {
- SendMessageA(widget->winId(), msg, wParam, lParam);
- })
- }
- break;
-
- default:
- break;
+ if (!widget->handleWindowCallback (hwnd, msg, wParam, lParam)) {
+ return 0;
}
}
@@ -249,18 +278,26 @@
}
/*!
- \reimp
+ Ensures that the window provided a child of this widget, unless
+ it is a WS_OVERLAPPED window.
*/
-bool QWinHost::event(QEvent *e)
+void QWinHost::fixParent()
{
- switch(e->type()) {
- case QEvent::Polish:
- if (!hwnd) {
- hwnd = createWindow(winId(), qWinAppInst());
- fixParent();
- own_hwnd = hwnd != 0;
- }
- if (hwnd && !wndproc && GetParent(hwnd) == winId()) {
+ if (!hwnd)
+ return;
+ if (!::IsWindow(hwnd)) {
+ hwnd = 0;
+ return;
+ }
+ if (::GetParent(hwnd) == winId())
+ return;
+ long style = GetWindowLong(hwnd, GWL_STYLE);
+ if (style & WS_OVERLAPPED)
+ return;
+ ::SetParent(hwnd, winId());
+
+ winhosts.insert(hwnd, this);
+
#if defined(GWLP_WNDPROC)
QT_WA({
wndproc = (void*)GetWindowLongPtr(hwnd, GWLP_WNDPROC);
@@ -279,14 +316,21 @@
})
#endif
- LONG style;
- QT_WA({
- style = GetWindowLong(hwnd, GWL_STYLE);
- }, {
- style = GetWindowLongA(hwnd, GWL_STYLE);
- })
if (style & WS_TABSTOP)
setFocusPolicy(Qt::FocusPolicy(focusPolicy() | Qt::StrongFocus));
+}
+
+/*!
+ \reimp
+*/
+bool QWinHost::event(QEvent *e)
+{
+ switch(e->type()) {
+ case QEvent::Polish:
+ if (!hwnd) {
+ hwnd = createWindow(winId(), qWinAppInst());
+ fixParent();
+ setAutoDestruct(hwnd != 0);
}
break;
case QEvent::WindowBlocked:
Copied: trunk/rkward/rkward/qwinhost/qwinhost.cpp.orig (from rev 2516, trunk/rkward/rkward/qwinhost/qwinhost.cpp)
===================================================================
--- trunk/rkward/rkward/qwinhost/qwinhost.cpp.orig (rev 0)
+++ trunk/rkward/rkward/qwinhost/qwinhost.cpp.orig 2009-06-05 20:42:07 UTC (rev 2518)
@@ -0,0 +1,355 @@
+/****************************************************************************
+**
+** This file is part of a Qt Solutions component.
+**
+** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
+**
+** Contact: Qt Software Information (qt-info at nokia.com)
+**
+** Commercial Usage
+** Licensees holding valid Qt Commercial licenses may use this file in
+** accordance with the Qt Solutions Commercial License Agreement provided
+** with the Software or, alternatively, in accordance with the terms
+** contained in a written agreement between you and Nokia.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.0, 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.
+**
+** Please note Third Party Software included with Qt Solutions may impose
+** additional restrictions and it is the user's responsibility to ensure
+** that they have met the licensing requirements of the GPL, LGPL, or Qt
+** Solutions Commercial license and the relevant license of the Third
+** Party Software they are using.
+**
+** If you are unsure which license is appropriate for your use, please
+** contact the sales department at qt-sales at nokia.com.
+**
+****************************************************************************/
+
+// Implementation of the QWinHost classes
+
+#ifdef QT3_SUPPORT
+#undef QT3_SUPPORT
+#endif
+
+#include "qwinhost.h"
+
+#include <QtCore/QEvent>
+#include <qt_windows.h>
+
+/*!
+ \class QWinHost qwinhost.h
+ \brief The QWinHost class provides an API to use native Win32
+ windows in Qt applications.
+
+ QWinHost exists to provide a QWidget that can act as a parent for
+ any native Win32 control. Since QWinHost is a proper QWidget, it
+ can be used as a toplevel widget (e.g. 0 parent) or as a child of
+ any other QWidget.
+
+ QWinHost integrates the native control into the Qt user interface,
+ e.g. handles focus switches and laying out.
+
+ Applications moving to Qt may have custom Win32 controls that will
+ take time to rewrite with Qt. Such applications can use these
+ custom controls as children of QWinHost widgets. This allows the
+ application's user interface to be replaced gradually.
+
+ When the QWinHost is destroyed, and the Win32 window hasn't been
+ set with setWindow(), the window will also be destroyed.
+*/
+
+/*!
+ Creates an instance of QWinHost. \a parent and \a f are
+ passed on to the QWidget constructor. The widget has by default
+ no background.
+
+ \warning You cannot change the parent widget of the QWinHost instance
+ after the native window has been created, i.e. do not call
+ QWidget::setParent or move the QWinHost into a different layout.
+*/
+QWinHost::QWinHost(QWidget *parent, Qt::WFlags f)
+: QWidget(parent, f), wndproc(0),own_hwnd(false), hwnd(0)
+{
+ setAttribute(Qt::WA_NoBackground);
+ setAttribute(Qt::WA_NoSystemBackground);
+}
+
+/*!
+ Destroys the QWinHost object. If the hosted Win32 window has not
+ been set explicitly using setWindow() the window will be
+ destroyed.
+*/
+QWinHost::~QWinHost()
+{
+ if (wndproc) {
+#if defined(GWLP_WNDPROC)
+ QT_WA({
+ SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)wndproc);
+ },{
+ SetWindowLongPtrA(hwnd, GWLP_WNDPROC, (LONG_PTR)wndproc);
+ })
+#else
+ QT_WA({
+ SetWindowLong(hwnd, GWL_WNDPROC, (LONG)wndproc);
+ },{
+ SetWindowLongA(hwnd, GWL_WNDPROC, (LONG)wndproc);
+ })
+#endif
+ }
+
+ if (hwnd && own_hwnd)
+ DestroyWindow(hwnd);
+}
+
+/*!
+ Reimplement this virtual function to create and return the native
+ Win32 window. \a parent is the handle to this widget, and \a
+ instance is the handle to the application instance. The returned HWND
+ must be a child of the \a parent HWND.
+
+ The default implementation returns null. The window returned by a
+ reimplementation of this function is owned by this QWinHost
+ instance and will be destroyed in the destructor.
+
+ This function is called by the implementation of polish() if no
+ window has been set explicitly using setWindow(). Call polish() to
+ force this function to be called.
+
+ \sa setWindow()
+*/
+HWND QWinHost::createWindow(HWND parent, HINSTANCE instance)
+{
+ Q_UNUSED(parent);
+ Q_UNUSED(instance);
+ return 0;
+}
+
+/*!
+ Ensures that the window provided a child of this widget, unless
+ it is a WS_OVERLAPPED window.
+*/
+void QWinHost::fixParent()
+{
+ if (!hwnd)
+ return;
+ if (!::IsWindow(hwnd)) {
+ hwnd = 0;
+ return;
+ }
+ if (::GetParent(hwnd) == winId())
+ return;
+ long style = GetWindowLong(hwnd, GWL_STYLE);
+ if (style & WS_OVERLAPPED)
+ return;
+ ::SetParent(hwnd, winId());
+}
+
+/*!
+ Sets the native Win32 window to \a window. If \a window is not a child
+ window of this widget, then it is reparented to become one. If \a window
+ is not a child window (i.e. WS_OVERLAPPED is set), then this function does nothing.
+
+ The lifetime of the window handle will be managed by Windows, QWinHost does not
+ call DestroyWindow. To verify that the handle is destroyed when expected, handle
+ WM_DESTROY in the window procedure.
+
+ \sa window(), createWindow()
+*/
+void QWinHost::setWindow(HWND window)
+{
+ if (hwnd && own_hwnd)
+ DestroyWindow(hwnd);
+
+ hwnd = window;
+ fixParent();
+
+ own_hwnd = false;
+}
+
+/*!
+ Returns the handle to the native Win32 window, or null if no
+ window has been set or created yet.
+
+ \sa setWindow(), createWindow()
+*/
+HWND QWinHost::window() const
+{
+ return hwnd;
+}
+
+void *getWindowProc(QWinHost *host)
+{
+ return host ? host->wndproc : 0;
+}
+
+LRESULT CALLBACK WinHostProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ QWinHost *widget = qobject_cast<QWinHost*>(QWidget::find(::GetParent(hwnd)));
+ WNDPROC oldproc = (WNDPROC)getWindowProc(widget);
+ if (widget) {
+ switch(msg) {
+ case WM_LBUTTONDOWN:
+ if (::GetFocus() != hwnd && (widget->focusPolicy() & Qt::ClickFocus)) {
+ widget->setFocus(Qt::MouseFocusReason);
+ }
+ break;
+
+ case WM_SYSKEYDOWN:
+ case WM_SYSKEYUP:
+ QT_WA({
+ SendMessage(widget->winId(), msg, wParam, lParam);
+ }, {
+ SendMessageA(widget->winId(), msg, wParam, lParam);
+ })
+ break;
+
+ case WM_KEYDOWN:
+ if (wParam == VK_TAB) {
+ QT_WA({
+ SendMessage(widget->winId(), msg, wParam, lParam);
+ }, {
+ SendMessageA(widget->winId(), msg, wParam, lParam);
+ })
+ }
+ break;
+
+ default:
+ break;
+ }
+ }
+
+ QT_WA({
+ if (oldproc)
+ return CallWindowProc(oldproc, hwnd, msg, wParam, lParam);
+ return DefWindowProc(hwnd,msg,wParam,lParam);
+ }, {
+ if (oldproc)
+ return CallWindowProcA(oldproc, hwnd, msg, wParam, lParam);
+ return DefWindowProcA(hwnd,msg,wParam,lParam);
+ })
+}
+
+/*!
+ \reimp
+*/
+bool QWinHost::event(QEvent *e)
+{
+ switch(e->type()) {
+ case QEvent::Polish:
+ if (!hwnd) {
+ hwnd = createWindow(winId(), qWinAppInst());
+ fixParent();
+ own_hwnd = hwnd != 0;
+ }
+ if (hwnd && !wndproc && GetParent(hwnd) == winId()) {
+#if defined(GWLP_WNDPROC)
+ QT_WA({
+ wndproc = (void*)GetWindowLongPtr(hwnd, GWLP_WNDPROC);
+ SetWindowLongPtr(hwnd, GWLP_WNDPROC, (LONG_PTR)WinHostProc);
+ }, {
+ wndproc = (void*)GetWindowLongPtrA(hwnd, GWLP_WNDPROC);
+ SetWindowLongPtrA(hwnd, GWLP_WNDPROC, (LONG_PTR)WinHostProc);
+ })
+#else
+ QT_WA({
+ wndproc = (void*)GetWindowLong(hwnd, GWL_WNDPROC);
+ SetWindowLong(hwnd, GWL_WNDPROC, (LONG)WinHostProc);
+ }, {
+ wndproc = (void*)GetWindowLongA(hwnd, GWL_WNDPROC);
+ SetWindowLongA(hwnd, GWL_WNDPROC, (LONG)WinHostProc);
+ })
+#endif
+
+ LONG style;
+ QT_WA({
+ style = GetWindowLong(hwnd, GWL_STYLE);
+ }, {
+ style = GetWindowLongA(hwnd, GWL_STYLE);
+ })
+ if (style & WS_TABSTOP)
+ setFocusPolicy(Qt::FocusPolicy(focusPolicy() | Qt::StrongFocus));
+ }
+ break;
+ case QEvent::WindowBlocked:
+ if (hwnd)
+ EnableWindow(hwnd, false);
+ break;
+ case QEvent::WindowUnblocked:
+ if (hwnd)
+ EnableWindow(hwnd, true);
+ break;
+ }
+ return QWidget::event(e);
+}
+
+/*!
+ \reimp
+*/
+void QWinHost::showEvent(QShowEvent *e)
+{
+ QWidget::showEvent(e);
+
+ if (hwnd)
+ SetWindowPos(hwnd, HWND_TOP, 0, 0, width(), height(), SWP_SHOWWINDOW);
+}
+
+/*!
+ \reimp
+*/
+void QWinHost::focusInEvent(QFocusEvent *e)
+{
+ QWidget::focusInEvent(e);
+
+ if (hwnd)
+ ::SetFocus(hwnd);
+}
+
+/*!
+ \reimp
+*/
+void QWinHost::resizeEvent(QResizeEvent *e)
+{
+ QWidget::resizeEvent(e);
+
+ if (hwnd)
+ SetWindowPos(hwnd, HWND_TOP, 0, 0, width(), height(), 0);
+}
+
+/*!
+ \reimp
+*/
+bool QWinHost::winEvent(MSG *msg, long *result)
+{
+ switch (msg->message)
+ {
+ case WM_SETFOCUS:
+ if (hwnd) {
+ ::SetFocus(hwnd);
+ return true;
+ }
+ default:
+ break;
+ }
+
+ return QWidget::winEvent(msg, result);
+}
+
Modified: trunk/rkward/rkward/qwinhost/qwinhost.h
===================================================================
--- trunk/rkward/rkward/qwinhost/qwinhost.h 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/qwinhost/qwinhost.h 2009-06-05 20:42:07 UTC (rev 2518)
@@ -51,6 +51,8 @@
#define QWINHOST_H
#include <QtGui/QWidget>
+#include <QtCore/QMap>
+#include <qt_windows.h>
#if defined(Q_WS_WIN)
# if !defined(QT_QTWINMIGRATE_EXPORT) && !defined(QT_QTWINMIGRATE_IMPORT)
@@ -78,6 +80,15 @@
void setWindow(HWND);
HWND window() const;
+ bool isAutoDestruct() const;
+ void setAutoDestruct(bool);
+
+ static QWinHost *findHost(HWND);
+
+ virtual bool handleWindowCallback (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);
+signals:
+ void clientDestroyed();
+ void clientTitleChanged(const QString& new_title);
protected:
virtual HWND createWindow(HWND parent, HINSTANCE instance);
@@ -93,8 +104,10 @@
friend void* getWindowProc(QWinHost*);
void *wndproc;
- bool own_hwnd;
+ bool auto_destruct;
HWND hwnd;
+
+ static QMap<HWND, QWinHost*> winhosts;
};
#endif // QWINHOST_H
Copied: trunk/rkward/rkward/qwinhost/qwinhost.h.orig (from rev 2516, trunk/rkward/rkward/qwinhost/qwinhost.h)
===================================================================
--- trunk/rkward/rkward/qwinhost/qwinhost.h.orig (rev 0)
+++ trunk/rkward/rkward/qwinhost/qwinhost.h.orig 2009-06-05 20:42:07 UTC (rev 2518)
@@ -0,0 +1,100 @@
+/****************************************************************************
+**
+** This file is part of a Qt Solutions component.
+**
+** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
+**
+** Contact: Qt Software Information (qt-info at nokia.com)
+**
+** Commercial Usage
+** Licensees holding valid Qt Commercial licenses may use this file in
+** accordance with the Qt Solutions Commercial License Agreement provided
+** with the Software or, alternatively, in accordance with the terms
+** contained in a written agreement between you and Nokia.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.0, 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.
+**
+** Please note Third Party Software included with Qt Solutions may impose
+** additional restrictions and it is the user's responsibility to ensure
+** that they have met the licensing requirements of the GPL, LGPL, or Qt
+** Solutions Commercial license and the relevant license of the Third
+** Party Software they are using.
+**
+** If you are unsure which license is appropriate for your use, please
+** contact the sales department at qt-sales at nokia.com.
+**
+****************************************************************************/
+
+
+// Declaration of the QWinHost classes
+
+#ifndef QWINHOST_H
+#define QWINHOST_H
+
+#include <QtGui/QWidget>
+
+#if defined(Q_WS_WIN)
+# if !defined(QT_QTWINMIGRATE_EXPORT) && !defined(QT_QTWINMIGRATE_IMPORT)
+# define QT_QTWINMIGRATE_EXPORT
+# elif defined(QT_QTWINMIGRATE_IMPORT)
+# if defined(QT_QTWINMIGRATE_EXPORT)
+# undef QT_QTWINMIGRATE_EXPORT
+# endif
+# define QT_QTWINMIGRATE_EXPORT __declspec(dllimport)
+# elif defined(QT_QTWINMIGRATE_EXPORT)
+# undef QT_QTWINMIGRATE_EXPORT
+# define QT_QTWINMIGRATE_EXPORT __declspec(dllexport)
+# endif
+#else
+# define QT_QTWINMIGRATE_EXPORT
+#endif
+
+class QT_QTWINMIGRATE_EXPORT QWinHost : public QWidget
+{
+ Q_OBJECT
+public:
+ QWinHost(QWidget *parent = 0, Qt::WFlags f = 0);
+ ~QWinHost();
+
+ void setWindow(HWND);
+ HWND window() const;
+
+protected:
+ virtual HWND createWindow(HWND parent, HINSTANCE instance);
+
+ bool event(QEvent *e);
+ void showEvent(QShowEvent *);
+ void focusInEvent(QFocusEvent*);
+ void resizeEvent(QResizeEvent*);
+
+ bool winEvent(MSG *msg, long *result);
+
+private:
+ void fixParent();
+ friend void* getWindowProc(QWinHost*);
+
+ void *wndproc;
+ bool own_hwnd;
+ HWND hwnd;
+};
+
+#endif // QWINHOST_H
Modified: trunk/rkward/rkward/rbackend/rembedinternal.cpp
===================================================================
--- trunk/rkward/rkward/rbackend/rembedinternal.cpp 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/rbackend/rembedinternal.cpp 2009-06-05 20:42:07 UTC (rev 2518)
@@ -455,22 +455,7 @@
if (!r_running) return; // already shut down
r_running = false;
-// Code-recipe below essentially copied from http://stat.ethz.ch/R-manual/R-devel/doc/manual/R-exts.html#Linking-GUIs-and-other-front_ends-to-R
-// modified quite a bit for our needs.
-
- if (!suicidal) {
- R_dot_Last ();
- }
-
- R_RunExitFinalizers();
-
- R_CleanTempDir ();
-
- /* close all the graphics devices */
- if (!suicidal) Rf_KillAllDevices ();
-#ifndef Q_WS_WIN
- fpu_setup ((Rboolean) FALSE);
-#endif
+ Rf_endEmbeddedR (suicidal);
}
#if 0
Modified: trunk/rkward/rkward/rkwardapplication.cpp
===================================================================
--- trunk/rkward/rkward/rkwardapplication.cpp 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/rkwardapplication.cpp 2009-06-05 20:42:07 UTC (rev 2518)
@@ -52,24 +52,6 @@
toplevel_windows.clear ();
EnumWindows (EnumWindowsCallback, 0);
};
-
-// TODO: this is a test, only
- BOOL CALLBACK ChildWindowCallback (HWND hwnd, LPARAM) {
- WINDOWINFO info;
- info.cbSize = sizeof (WINDOWINFO);
- GetWindowInfo (hwnd, &info);
-qDebug ("%p: rect: %d, %d, %d, %d, client: %d, %d, %d, %d, style: %d, exstyle: %d, status: %d, borders: %d %d", hwnd,
- info.rcWindow.left, info.rcWindow.top, info.rcWindow.right, info.rcWindow.bottom,
- info.rcClient.left, info.rcClient.top, info.rcClient.right, info.rcClient.bottom,
- info.dwStyle, info.dwExStyle, info.dwWindowStatus, info.cxWindowBorders, info.cyWindowBorders);
-
- return true;
- }
-
- void showWindowChildren (HWND hwnd) {
- ChildWindowCallback (hwnd, 0);
- EnumChildWindows (hwnd, ChildWindowCallback, 0);
- }
}
#endif //Q_WS_WIN
@@ -136,10 +118,7 @@
if (candidate_windows.size ()) {
RK_ASSERT (candidate_windows.size () < 2);
- for (int i = 0; i < candidate_windows.size (); ++i) {
- qDebug ("candidate: %d", i);
- RKWardApplicationPrivate::showWindowChildren (candidate_windows[i]);
- }
+#warning TODO: the above assert fails. More windows get created. Sieve out the invisible ones, first?
return candidate_windows[0];
} // else
return 0;
Modified: trunk/rkward/rkward/windows/rkwindowcatcher.cpp
===================================================================
--- trunk/rkward/rkward/windows/rkwindowcatcher.cpp 2009-06-04 19:58:09 UTC (rev 2517)
+++ trunk/rkward/rkward/windows/rkwindowcatcher.cpp 2009-06-05 20:42:07 UTC (rev 2518)
@@ -69,6 +69,7 @@
#include <qlabel.h>
#ifdef Q_WS_WIN
# include "../qwinhost/qwinhost.h"
+# include <windows.h>
#else
# include <QX11EmbedContainer>
#endif
@@ -108,17 +109,30 @@
layout->addWidget (scroll_widget);
xembed_container = new KVBox (box_widget); // QX11EmbedContainer can not be reparented (between the box_widget, and the scroll_widget) directly. Therefore we place it into a container, and reparent that instead
- dynamic_size = true;
- dynamic_size_action->setChecked (true);
#ifdef Q_WS_WIN
-# warning TODO: set geometry
+ // unfortunately, trying to get KWindowInfo as below hangs on windows (KDElibs 4.2.3)
+ WINDOWINFO wininfo;
+ wininfo.cbSize = sizeof (WINDOWINFO);
+ GetWindowInfo (embedded, &wininfo);
+
+ // clip off the window frame and menubar
+ xembed_container->setContentsMargins (wininfo.rcWindow.left - wininfo.rcClient.left, wininfo.rcWindow.top - wininfo.rcClient.top,
+ wininfo.rcClient.right - wininfo.rcWindow.right, wininfo.rcClient.bottom - wininfo.rcWindow.bottom);
+ // set a fixed size until the window is shown
+ xembed_container->setFixedSize (wininfo.rcClient.right - wininfo.rcClient.left, wininfo.rcClient.bottom - wininfo.rcClient.top);
+ move (wininfo.rcClient.left, wininfo.rcClient.top);
#else
- KWindowInfo wininfo = KWindowSystem::windowInfo (embedded, NET::WMName | NET::WMFrameExtents);
+ KWindowInfo wininfo = KWindowSystem::windowInfo (embedded, NET::WMName | NET::WMGeometry);
RK_ASSERT (wininfo.valid ());
- setGeometry (wininfo.frameGeometry ());
+
+ // set a fixed size until the window is shown
+ xembed_container->setFixedSize (wininfo.geometry ().width (), wininfo.geometry ().height ());
+ move (wininfo.geometry ().topLeft());
setCaption (wininfo.name ());
#endif
+ dynamic_size = false;
+ dynamic_size_action->setChecked (false);
// somehow in Qt 4.4.3, when the RKCaughtWindow is reparented the first time, the QX11EmbedContainer may kill its client. Hence we delay the actual embedding until after the window was shown.
// In some previous version of Qt, this was not an issue, but I did not track the versions.
@@ -131,15 +145,22 @@
RK_TRACE (MISC);
#ifdef Q_WS_WIN
+# warning TODO: set name
capture = new QWinHost (xembed_container);
capture->setWindow (embedded);
-# warning TODO: deletion
+ capture->setAutoDestruct (true);
+ connect (capture, SIGNAL (clientDestroyed()), this, SLOT (deleteLater()), Qt::QueuedConnection);
+ connect (capture, SIGNAL (clientTitleChanged(const QString&)), this, SLOT (setWindowTitle(const QString&)), Qt::QueuedConnection);
#else
capture = new QX11EmbedContainer (xembed_container);
+
capture->embedClient (embedded);
connect (capture, SIGNAL (clientClosed ()), this, SLOT (deleteLater ()));
#endif
+ // make xembed_container resizable, again, now that it actually has a content
+ dynamic_size_action->setChecked (true);
+ fixedSizeToggled ();
}
RKCaughtX11Window::~RKCaughtX11Window () {
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
More information about the rkward-tracker
mailing list