AbstractListModel с двумя столбцами, как выбрать, какой столбец показывать в ListView? - PullRequest
0 голосов
/ 18 апреля 2020

У меня есть подклассы QAbstractListModel с двумя столбцами, что-то вроде:

class MediaList : public QAbstractListModel {

public:
    QVariant data(QModelIndex const& index, int role) const override
    {
        if (index.column() == 0)
            return QVariant(m_songs.at(index.row()));
        if (index.column() == 1)
            return QVariant(m_videos.at(index.row()));
        return QVariant();
    }

    int rowCount(QModelIndex const& parent = QModelIndex()) const override
    {
        return m_videos.size() < m_songs.size() ? m_songs.size() : m_videos.size();
    }

private:
    QStringList m_songs;
    QStringList m_videos;
};

Очевидно, что это еще не все, но это основная идея. Затем я открываю его для QML через функцию context в Qt. Теперь в QML у меня есть что-то вроде этого:

ListView {
    model: myMediaList
    delegate: Text {
        text: modelData
    }
}

И он правильно показывает «песни» в виде списка текстовых строк. Но как мне сказать, чтобы вместо этого использовался столбец 1, чтобы вместо этого я мог видеть «видео»?

1 Ответ

2 голосов
/ 18 апреля 2020

Я думаю, что QAbstractListModel не должен иметь более одного столбца:

Класс QAbstractListModel предоставляет абстрактную модель, которая может быть разделена на подклассы для создания моделей одномерного списка.

[...]

Поскольку модель представляет собой одномерную структуру, функция rowCount () возвращает общее количество элементов в модели. Функция columnCount () реализована для взаимодействия со всеми видами представлений, но по умолчанию сообщает представлениям, что модель содержит только один столбец.

https://doc.qt.io/qt-5/qabstractlistmodel.html#details

Вместо этого вы можете использовать роли модели:

// In MediaList's header:
enum MediaListRole {
    SongRole = Qt::UserRole,
    VideoRole
};

// ...    

QVariant data(QModelIndex const& index, int role) const override
{
    if (role == SongRole)
        return QVariant(m_songs.at(index.row()));
    else if (role == VideoRole)
        return QVariant(m_videos.at(index.row()));
    return QVariant();
}

QHash<int, QByteArray> roleNames() const
{
    QHash<int, QByteArray> names;
    names.insert(SongRole, "song");
    names.insert(VideoRole, "video");
    return names;
}

Затем в QML:

delegate: Text {
    text: model.song
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...