Qt 文件对话框渲染不正确并崩溃

Posted

技术标签:

【中文标题】Qt 文件对话框渲染不正确并崩溃【英文标题】:Qt File Dialog Rendered Incorrectly and Crashes 【发布时间】:2015-10-08 05:50:58 【问题描述】:

我正在使用QFileDialog::getOpenFileName 函数来打开一个文件。但是,在运行 Windows 7 的客户端计算机上,这要么显示一个损坏的打开文件对话框,如屏幕截图所示,要么使整个应用程序崩溃。

我用来打开文件对话框的代码是:

void MainWindow::on_action_triggered() 
    auto filename = QFileDialog::getSaveFileName(this, "Generate Report", "", "CSV files (*.csv)");

    if (filename.isEmpty()) 
        return;
    

    // Do operations on filename...

我正在使用 Qt 5.5 和 Visual Studio 2013。

【问题讨论】:

getOpenFileNamegetSaveFileName 或两者都会发生这种情况吗? 尝试调试版本,可能你错过了发布中的一些 dll。 @Mailerdaimon 两者都会发生。 我对Qt一无所知,但是在Win32中你需要调用CoInitialize()或OleInitialize()来使用通用文件对话框。也许有一个 init 方法被遗漏了? 只是一个猜测 - 但你可以尝试初始化启动目录 - 说:C:?我要问的原因是双重的 - 它可能是 Windows 试图在现在无效的“以前的位置”恢复,或者它可能是一个 Qt 级别的错误,它错误地处理了 WIN32/WIN64。如果您发现 Qt 有效,请使用 Qt 记录一个错误 :) 【参考方案1】:

在这种特殊情况下,问题最终是 Qt 与安装在客户计算机上的戴尔备份和恢复软件不兼容,其中包括不兼容的外壳扩展。我使用的解决方案是删除备份和恢复软件,但听起来命名空间 Qt 也是一种选择。更多信息请访问QTBUG-41416。

【讨论】:

【参考方案2】:

我猜是目录有问题。作为路径提供的这个空字符串可能有问题。 尝试以这种方式修复:

auto filename = QFileDialog::getSaveFileName(this, 
                                             tr("Generate Report"),
                                             QString(),
                                             tr("CSV files (*.csv)"));
// or this way
auto filename = QFileDialog::getSaveFileName(this,
                                             tr("Generate Report"),
                                             QDir::home().absolutePath(),
                                             tr("CSV files (*.csv)"));

【讨论】:

干杯!我已经向客户发送了一个包含这两个的应用程序进行测试。如果不是这个,我猜它可能是一些 cmets 建议的狡猾的 shell 扩展。 不幸的是,我尝试了不带参数的变体、默认构造的 QString 以及相同结果的现有目录。不过谢谢! 能否提供崩溃调用堆栈?如果你自己构建 Qt 是最简单的。【参考方案3】:

您的问题的根源似乎是内存损坏。要找到它,请安装 Microsoft Application Verifier 并使用 Basics\Heaps 配置您的应用程序。即使原始问题没有重现,您也可以在自己的计算机上执行此操作。之后,尝试重现问题,我猜你会发现你的内存损坏。

更新 现在问题没有在您的机器上重现并且您说对话框已挂起,我建议执行以下附加步骤(您可以在 TeamViewer 会话中自己完成所有操作以使其更容易)

    在客户机器上为您的 EXE 启用应用程序验证程序。作为副作用,这会启用堆跟踪。 在挂起期间捕获(一系列)转储。在系列中至少有一个完整的转储。例如,您可以使用 SysInternals Process Explorer 来完成。稍后分析它们,您将能够看到应用程序在做什么。不要忘记为您的 EXE 生成和保存 PDB 文件(调试信息)(尽管我认为挂起的文件会在您的 exe 之外)。

【讨论】:

试一试,不幸的是没有运气。 我建议您询问您的客户他正在执行的精确操作。对于内存损坏,缓冲区溢出是非常典型的。也就是说,有些东西可能比你预期的要大。 我给客户发了一个最小的程序,它只打开了一个文件对话框(没有别的),它仍然出现问题。 我想我会担保客户机器上的外壳扩展不好。如果您仍然有兴趣找到问题的根源,我可以提供高级故障排除步骤,包括使用堆跟踪捕获小型转储。 干杯!我实际上已将崩溃报告器集成到向我发送小型转储的应用程序中。不幸的是,对话框似乎只是挂起并且最近没有崩溃:(

以上是关于Qt 文件对话框渲染不正确并崩溃的主要内容,如果未能解决你的问题,请参考以下文章

Qt 标准对话框示例:打开文件

使用 Mac 保存对话框时崩溃

QT 对话框的样式不正确

QT学习笔记3

gnome 上的 PyQt5 有奇怪的文件对话框

QT二进制读取图像文件并显示