Qt-Application 意外杀死字符(drawText 产生错误)

标签 qt qt5 qpainter

我有一个非常简单的应用程序,用于向图片添加水印。因此,您可以将图片放入 QListWidget 中,它会显示缩略图和路径,调整文本、透明度、输出格式等一些内容。按开始后,它将受版权保护的图片保存在您的目的地中选择。这与 QPainter 一起使用,在图片上绘制 Logo 和文本。

一切都能正常工作。但这是一个神秘的错误:

应用程序会杀死随机字母。这真的很奇怪,因为我无法重现它。每次执行和选项组合都会有所不同。例如:

  • 有时我无法在界面的QLineEdit中写出一些字母(比如E、4和0不存在,或者他改变了字母所以一些特殊符号)。
  • QListWidget 中的项目文本未完全显示,有时完全丢失。但我可以正常提取文本并使用路径。
  • 在执行时,我有一个 QTextBrowser 作为日志来显示一些有趣的东西,例如字体大小。尽管字体在结果图片上正常显示,但它显示“4”或“6”,而不是更高且正确的尺寸。有时某些字母之间会出现奇怪的白色 block
  • 使用 QPainter 在图片上绘制文本时,也会出现字母缺失的情况。有时,所有字母都打印在一起。当使用小像素尺寸(如 12)时,此错误似乎更常见:

        //Text//
    int fontSize = (watermarkHeight-(4*frame));
    int fontX = 2*frame;
    int fontY = (result.height()-(watermarkHeight-2*frame));
    int fontWidth = watermarkWidth;
    QRect place(fontX,fontY,fontWidth,fontSize);
    
    QFont font("Helvetica Neue", QFont::Light);
    font.setPixelSize(fontSize);
    emit log(QString::number(fontSize));
    pixPaint.setFont(font);
    pixPaint.setPen(QColor(255,255,255,textOpacity));
    pixPaint.drawText(place,text);
    

并非所有这些错误都会同时出现!有时我没有任何错误...

也许以前有人遇到过类似的错误。不幸的是我没有在互联网上找到类似的东西。我没有发布很多代码片段,因为我认为(并希望)这是一个普遍问题。如果您需要具体的帮助我,请告诉我 =)

我添加了示例图片:

  • 在行编辑中,我简单地写了 ABCDEFGHIJKLMNOPQRSTUVWXYZ01234567890(看看他对 7 和 9 做了什么)
  • 图片下角的这个小方 block 应该是“ABC...”的东西
  • “62”在文本浏览器中看起来很奇怪

example screenshot

我在 Windows 7 64 位计算机上使用 Qt 5.0.1。

编辑:每次将第一张图片添加到列表后,他都会发现这些警告:

QFontEngine::loadEngine: GetTextMetrics failed ()
QWindowsFontEngine: GetTextMetrics failed ()

但是当我更改高度(以及字体的 pointSize)时,即使使用启动参数,它也不再发出。

编辑2:感谢您的帮助!我更正了我的代码,以便他只使用正确的字体和正确的大小,但它仍然不起作用。当我删除 QPainter::drawText() 函数时,它工作正常(没有文本)。但是当我添加文本时,一切都出现了问题。我现在有这样的东西:

    //Text//
    QList<int> smoothSizes = fontDatabase->smoothSizes("Verdana","Standard");
    int fontSize = (watermarkHeight-(4*frame))*0.75;
    emit log("Requested:  "+QString::number(fontSize));

    if(!smoothSizes.contains(fontSize)){
        for(int i = 0; i<smoothSizes.length(); i++){
            if(smoothSizes.at(i) > fontSize && i>0){
                fontSize = smoothSizes.at(i-1);
                break;
            }
        }
    }

    int fontX = 2*frame;
    int fontY = (result.height()-(watermarkHeight/2)+frame);

    QFont font = fontDatabase->font("Verdana","Standard",fontSize);

    QFontInfo info(font);
    emit log("Corrected: "+QString::number(fontSize));
    emit log("Okay?: "+QString::number(info.exactMatch()));

    pixPaint.setFont(font);
    const QFontMetrics fontMetrics = pixPaint.fontMetrics();

    if(info.exactMatch()){
        pixPaint.setPen(QColor(255,255,255,textOpacity));
        pixPaint.drawText(fontX,fontY+(fontMetrics.height()-fontMetrics.ascent()),text);
    }

最佳答案

听起来好像您正在破坏进程中的随机内存,或者您的 Windows 安装严重损坏。可能您的字体请求与选择得非常糟糕的系统字体相匹配。

QFont 上设置的任何内容都只是一个请求。要获取所选实际字体的参数,您必须创建一个QFontInfo,并从那里获取您的信息。

想象一下,您请求的 QFont 系统上不存在,或者无法缩放到特定尺寸。在某些时候,字体对象需要变形以反射(reflect)实际发生的情况 - 这会非常令人困惑。因此,QFontInfo 提供有关实际使用的字体的信息。将 QFontInfo 视为响应,将 QFont 视为请求。

关于Qt-Application 意外杀死字符(drawText 产生错误),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21908334/

相关文章:

c++ - Qt Creator C++,为状态栏添加许多标签

c++ - 将 QList 转换为 QVariant

c++ - Qt Creator closeEvent问题

javascript - JWPlayer 在 Qt5 QWebView 中不可见

c++ - 编译 QTermWidget

c++ - 绘制设备返回引擎 == 0,类型 : 1

c++ - QPainter彩色文本(语法着色)

c++ - Qt:绘制高 DPI QPixmaps

c++ - QGridLayout addWidget(CustomWidget) 不工作

c++ - Qt 将附加参数传递给插槽并保留发出的信号数据