Qt的GCC和LLVM版本编译promote组件失败的处理
Qt GCC和LLVM版本编译失败的解决措施以前都是使用MSVC套件来编译Qt的项目. 新的公司因为是在Linux下开发, 不得不使用我一直很不喜欢的GCC, 慢慢地, 其实也就习惯了. 再后来, 因为要交叉编译Windows版本, mingw也不得不用了起来.
前几天Qt发布了6.8 LTS版本, 在家里的电脑升级的时候想想就顺便把LLVM套件也给装上了. 然后就发现编译失败了.
我在界面里面定义了一个自定义的QWidget的ui界面类, Pageing.然后, 在另一个ui界面类SampleListForm里面, 将一个QWidget给promote到了Paging.
用MSVC编译啥问题没有, 尝鲜使用LLVM, 就编译失败了, ui_SampleListForm.h里面报错说找不到Paging.h. 我想会不会是没有装好的缘故, 于是在另一台电脑也升级了6.8, 装了LLVM编译套件, 发现也不行. 然后又安装了GCC, 也是同样的编译错误, 只有MSVC编译是正确的.
给Qt提了bug, 几次交流之后, 对方建议我在CMakeLists.txt中增加下面一行: tar ...
iconfont图标字体Windows下不能用
公司里面的程序有Linux版本和Windows版本, 但是实际上只有Linux的开发环境, 因此Windows版本其实是mxe下面交叉编译出来的mingw32位版本. 今天发现一个很奇怪的事情, 原本是使用iconfont作为工具栏图标字体的, 在Linux下完全正常. 没想到编译了一下Windows版本, 发现运行时竟然显示不出来图标字体.
这事儿可就奇特了.
我想根本原因还是在mxe或mingw32上面, 可是实在是没有精力去折腾这事儿. 又不得不再将所有的图标再下了一遍图像文件, 然后用宏编译开关来区分是编译Windows版本还是Linux版本.
对RESTful Server的支持类
Qt6中新增的Http Server类Qt6中新增了Http Server的支持, 这个东西很简单, 就是一个玩具, 但是作为需要嵌入到应用程序里面做一个小server的情况还是比较适合的. 它的使用有点类似于FastApi的风格.
坑人的题目
坑人的题目之前做过的面试题, 做错了. 实在是有点坑人, 不过也确实从来没有想到过这个问题, 记录下来
123456789101112131415161718192021222324252627struct Base{ virtual ~Base(){} virtual void print(const std::string& str="B"){ std::cout << "B: " << str << std::endl; }};struct Derived : public Base{ virtual ~Derived(){} virtual void print(const std::string& str="D"){ std::cout << "D: " << str ...
简单的QDebug的封装
简单的QDebug封装以前习惯了使用qDebug()的<<来打印调试输出. 但是新公司是Linux的程序, 默认它会打印到控制台上, 这就很令人讨厌了. 如果直接关掉QDebug, 又会让别的也用不了. 就自然想能不能通过DEBUG和RELEASE来区分. 然后使用<<, 没法简单的做这件事情. 就想简单地将它封装一下, 封装成函数调用的方式. 想起很早以前玩过的C语言宏的花招, 试了两下就试出来了.
123456789101112131415161718192021222324#define CONCATE(x,y) x##y#define GET_NTH_ARG(_1, _2, _3, _4, _5, _6, _7, _8, n, ...) n#define GET_ARG_COUNT(...) GET_NTH_ARG(__VA_ARGS__, 8, 7, 6, 5, 4, 3, 2, 1)#define _dbg_show(arg) << arg#define _DEBUG_1(f, arg) f(arg)#define _DEBUG_2( ...
Qt的CMake文件写法
Qt使用CMake编写工程长期以来都是使用qmake管理Qt的源代码工程, 从Qt6开始, 官方改用CMake了, 但是我习惯了qmake, 觉得cmake有诸多不便, 仍然是习惯使用qmake. 直到不久前换东家, 新公司使用Qt5.9, 开发环境是Linux, 还没有creator可用, 只能用vscode做编辑器. 编译工具也是使用cmake. 这才不得不认认真真回来钻研一下cmake和qt在cmake下的用法.
不过, 说真的, 以前没有注意到, 如果开发工具不好, 对开发效率真的有着极大的负面作用. 比如说, 我是Qt12开始使用的, 大部分时间是使用Qt5.15版本和Qt6.2版本在Windows下开发. 而现在的公司是Qt5.9, C++编译器是不完全的C++14, 还只有VSCode可用. 不知道谁写的CMakefile, vscode解析就会失败, 到现在我也没有找到原因. 唯一的好处是确实锻炼了API的记忆能力, 不像以前, 只要几个大概, 自然IDE会给你联想.
基本的CMake工程Qt的帮助中有比较详细的说明, 因为比较老, 没有新的IDE使用的那么花哨, ...
slot定义方法的变迁
connect()中slot定义的变迁随着C++的演进, 代码的写作方式也会发生变化.
这是Qt5之前的时代的Demo里面的写法, 当需要将slot函数作为参数传递的时候, 使用的是SLOT()宏.
123456789101112131415161718192021fontColorToolButton->setMenu(createColorMenu(SLOT(textColorChanged()), Qt::black));...fillColorToolButton->setMenu(createColorMenu(SLOT(itemColorChanged()), Qt::white));...QMenu *MainWindow::createColorMenu(const char *slot, QColor defaultColor){ ... QMenu *colorMenu = new QMenu(this); for (int i = 0; i < colors.count(); ++i) { ...
Boost的contract库
看一篇文章, 里面提到契约式编程, 说在C++标准还没有明确下来之前, 可以利用已有的库, 想起来Boost里面似乎有一个, 但是我从来没有关心过. 觉得还是不要这么孤陋寡闻的好, 于是打开找找, 果然找到了.
Qt对象的内存优化
当你的自定义类需要利用Qt的容器类存储时, 可以对类做更精细的指定, 从而指导Qt使用更合适的内存管理算法.
Qt里面有一个宏, Q_DECALARE_TYPEINFO, 它的原型为: Q_DECLARE_TYPEINFO(Type, Flags). 其中, Type是要设置的类, 而Flags可以取下面的值:
Q_PRIMITIVE_TYPE, 它的意思是这个类的行为类似于基本类型, 可以通过简单地零初始化内存来创建, 也不需要有销毁操作, 并且可以用memcpy()来创建副本.
参考std::is_trivial的定义, 它的意思大概也是一样的, 指的是它要么是基本类型, 要么是没有定义函数的POD.
Q_RELOCATABLE_TYPE, 表示这个类虽然有构造函数和/或析构函数, 但是利用memcpy在内存中移动.
Q_MOVABLE_TYPE: 同Q_RELOCATABLE_TYPE, Qt更建议使用Q_RELOCATABLE_TYPE. 并且, 这里的MOVABLE和
Q_COMPLEX_TYPE, 这个是缺省值. 它表示这个类的实例不能在内存中 ...