C++ 如何重写(重新实现)QFileSystemModel中的成员函数

C++ 如何重写(重新实现)QFileSystemModel中的成员函数,c++,qt,class,overriding,C++,Qt,Class,Overriding,我已经为此挣扎了一段时间 Qt的QFileSystemModel在获取数百个文件时速度非常慢,因为图标获取算法非常糟糕 我想完全禁用图标。它们是在非虚拟的QFileSystemModel::data方法中获取的(QFileSystemModel的源代码可在此处找到:) 这是我试图运行的代码: class FileModel : public QFileSystemModel { using QFileSystemModel::data; public: QVariant QFil

我已经为此挣扎了一段时间

Qt的
QFileSystemModel
在获取数百个文件时速度非常慢,因为图标获取算法非常糟糕

我想完全禁用图标。它们是在非虚拟的
QFileSystemModel::data
方法中获取的(QFileSystemModel的源代码可在此处找到:)

这是我试图运行的代码:

class FileModel : public QFileSystemModel {
    using QFileSystemModel::data;
public:
    QVariant QFileSystemModel::data(const QModelIndex &index, int role) const
    {
     // my own implementation here
    }
}
但它失败了

无法定义成员函数QFileSystemModel::data witin FileModel

更新

我已经成功覆盖了该函数,这就是我现在所拥有的:

class FileModel : public QFileSystemModel {
public:
    QVariant data(const QModelIndex &index, int role) const
    {
    // Here goes Qt's implementation
    Q_D(const QFileSystemModel);
    if (!index.isValid() || index.model() != this)
        return QVariant();
    switch (role) {
    case Qt::EditRole:
    case Qt::DisplayRole:
        switch (index.column()) {
        case 0: return d->name(index);
        case 1: return d->size(index);
        case 2: return d->type(index);
        case 3: return d->time(index);
        default:
            qWarning("data: invalid display value column %d", index.column());
            break;
        }
        break;
    case FilePathRole:
        return filePath(index);
    case FileNameRole:
        return d->name(index);
    case Qt::DecorationRole:
        if (index.column() == 0) {
            QIcon icon = d->icon(index); // This is the part I need to change
            if (icon.isNull()) {
                if (d->node(index)->isDir())
                    icon = d->fileInfoGatherer.iconProvider()->icon(QFileIconProvider::Folder);
                else
                    icon = d->fileInfoGatherer.iconProvider()->icon(QFileIconProvider::File);
            }
            return icon;
        }
        break;
    case Qt::TextAlignmentRole:
        if (index.column() == 1)
            return Qt::AlignRight;
        break;
    case FilePermissions:
        int p = permissions(index);
        return p;
    }
    return QVariant();
}
};
然而,这段代码并不编译。这是我得到的错误:
'const QFileSystemModelPrivate*QFileSystemModel::d_func()const'是private

看起来这是预期的,因为有一种设置“图标提供程序”的方法:

参数a
QFileIconProvider
,看起来是一个相当简单的类,您可以实现自己的一个实例,方法是从
QFileInfo
获取图标(基本上是一个文件名):

您可以实现其中的一个,它只为所有内容返回相同的图标。如果您发现这并不能解决您的问题,那么以下内容对我来说很好…FWIW:

class FileModel : public QFileSystemModel {
public:
    QVariant data(const QModelIndex &index, int role) const
    {
        if (role == Qt::DecorationRole) {
            return QVariant (QIcon ());
        }    

        return QFileSystemModel::data(index, role);
    }
};

如果基类中的函数是虚函数,那么它在派生类中也是虚函数。以下将打印“C”:

#包括
甲级{
公众:
虚空数据()=0;
};
B类:公共A{
公众:

无效数据(){std::无法从声明中删除QFileSystemModel::part,也不要使用part。这里不需要它
数据
必须是虚拟的。
QFileSystemModel
派生自
QAbstractItemModel
,而在该类中
数据
是一个纯虚拟函数。请看Kamil的说法。Moritz:您不需要虚拟keyword如果基已经声明了虚函数、纯函数或其他函数。谢谢,但这不起作用。QFileSystemModel仅在调用
QFileSystemNode::icon()时使用QFileIconProvider为文件夹和常规文件构建图标
失败。我找不到
QFileSystemNode
类,即使我找到了,更改它也比更改
QFileSystemModel
类困难得多。查看源代码…你是说在获得装饰角色时,它正在通过
d->icon
路径(这对你来说很慢)不调用提供者?或者你认为这是其他原因吗?这是你试图覆盖的方法的来源:Yes,d->icon()调用
QFileSystemNode::icon
,运行大约需要2毫秒。将其乘以5000个文件,您将得到10秒的UI冻结,因为QIcon只能在主UI线程中使用。@Alex
QFileSystemNode::icon
最初也是由
QFileIconProvider
填充的:这是由于“pimpl习惯用法”…有一些私有实现的东西没有进入公共头集中。不过,你不必担心QFileSystemModel的实现,你能不能测试参数并根据需要进行处理,否则就传递到基中…?请参阅更新的代码。你是对的,这是vi然而,我得到了这个错误:
不完整类型“const struct QFileSystemModelPrivate”的无效使用
为什么不把完整的源代码发布到你的类的某个地方,这样我们就可以查看实际的代码,而不必介意读你写的东西?
#include <iostream>

class A {
public:
  virtual void data() = 0;
};

class B: public A {
public:
  void data() { std::cout << "B\n"; }
};

class C: public B {
public:
  void data() { std::cout << "C\n"; }
};

int
main() {
  C c;
  A *a = &c;
  a->data();

  return 0;
}