2016-08-01 150 views
2

如何使用SWIG来绑定到Qt应用程序,我们的情况几乎相同,在这种post的情况下,它说:我们可以使用SWIG为Qt应用程序创建python绑定吗?

  • 我们有一个大C++/QT与的一大口装订应用核心。
  • 我们想在python中创建新的UI工具,它需要使用我们的C++小部件中的一些 。所以我们需要绑定我们的C++小部件。由于我们的核心 绑定是用Swig编写的(我们对此感到满意),为了兼容性,我们需要将我们的 小部件与相同的绑定工具绑定。

看来他们已经成功地创造了痛饮Qt的结合,但似乎不容易将保鲜膜QT使用痛饮因为宏Q_OBJECT QT应用程序会生成预编译时在编译时使用这些文件建设部文件。我试过这个:

>> swig -c++ -python application.i 
application.h:46: Error: Syntax error in input(3) 

它总是给第46行的错误指示Q_OBJECT。

我也发现herehere说,用swig包装QT是不可能的,我对此很困惑,如果不可行或者如果可行的话,有人会对此有所了解,举个简单的例子使用SWIG包装QT。提前致谢。

更新源文件:application.h

#ifndef APPLICATION_H_ 
#define APPLICATION_H_ 

#include <QApplication> 

class frameApplication : public QApplication 
{ 
    Q_OBJECT 

public: 
    frameApplication(){}; 
    virtual ~frameApplication(); 

private slots: 
    void OnExitApp(); 

}; 
#endif // APPLICATION_H_ 

application.i

%module application 
%{ 
#include "application.h" 
%} 
%include "application.h" 

这是application.h的简化版本,使用上述SWIG命令,错误消息仍然是除行号外相同。

+0

是的,不仅仅是Q_OBJECT,而且还有Q_SINGAL/Q_SLOTS等 – BruceSun

+0

这就是为什么swig无法处理QT应用的原因,引用了上面的链接之一:“我不确定是否有完整的Qt宏的列表,但在这里它们的所有概念都可以通过C++表达出来,这就是它们在内部做的事情,它们有一个名为moc(Meta-Object Compiler)的工具,它在任何其他步骤之前运行在它们的代码上,它生成标准的C++然后编译,问题在于它只产生“真正的”cpp文件,而不是“真正的”头文件,并且正如文档中所述,SWIG不能依赖C++源文件正常工作。 – BruceSun

+0

叹息,如果C++编译器**本身**可以处理这些文件,那么SWIG也可以处理它们。我做了很多次。它工作正常。它们是有效的C++源代码,用于大声哭泣,人们不得不相信另一种想法!在我之后重复:**具有Qt宏的.cpp/.h文件不变地传递给C++编译器,并且是有效的C++ **。这就是C++框架的整个**点**。唯一认为moc所做的就是生成几个成员定义(不是声明!)和一些静态数据 - 这些都不是Swig或编译器所需要的。 –

回答

2

我们可以使用SWIG为Qt应用程序制作python绑定吗?

发生此错误是因为您的头文件使用了SWIG不知道的宏。当然,C++编译器也不会了解它们。

SWIG需要预处理您的输入。要做到这一点,它需要知道这两个包含Qt路径,以及Qt头文件工作所需的定义。

使用widgets包我的具体项目,上OSX Qt的安装,SWIG需要下面的参数,例如:

-DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB \ 
-I/Qt/5.6.0/lib/QtWidgets.framework/Headers \ 
-I/Qt/5.6.0/lib/QtGui.framework/Headers \ 
-I/Qt/5.6.0/lib/QtCore.framework/Headers \ 
-I/Qt/5.6.0/mkspecs/macx-clang 

痛饮走一段很长的方式来保持沉默丢失包含文件。即使在包含文件丢失的情况下,它也会尽力解析输入,并对各种标识符即使未定义也做了一些假设,但在提供未知宏时不会做太多工作展开为单个标识符。

获得必要的定义(-D)和包含路径(-I)选项的最简单方法是构建代码并从编译器的命令行获取这些代码。 SWIG 有目的地使用与大多数C/C++编译器相同的选项语法 - 使数据传递更容易。

应该说SWIG对信号和插槽没有特别的了解:它们只是C++方法。由SWIG生成的任何绑定都不支持使用Qt 5的新connect语法来链接信号和插槽。您仍然可以使用,你通过C字符串方法签名connect了Qt 4语法,例如:

// with SIGNAL/SLOT macros 
connect(obj1, SIGNAL(foo(QString)), obj2, SLOT(bar(QString))); 
// without SIGNAL/SLOT macros - as you would call from a SWIG binding 
connect(obj1, "2foo(QString)\0", obj2, "1bar(QString)\0"); 

方法签名需要一个额外的空终止的后缀。信号的前缀为'2',插槽的前缀为'1',其他可调用方法的前缀为'0'

除非您使用专用QMetaObjectBuilder,否则您将无法定义新信号或可调用方法;见here

相关问题