QFileSystemModel и QTreeView - странное поведение при сбросе представления

Я написал это на официальном форуме Qt, но он кажется мертвым, поэтому я скопирую его сюда.

Я пишу небольшую программу для копирования файлов. Я использую QTreeView и унаследовал от QFileSystemModel, поэтому я смог добавить флажки в каждую строку в QTreeView. Я также использую метод setNameFilters, связанный с QLineEdit, поэтому пользователь может указать, какие расширения файлов он хочет отображать в файле QTreeView. Я заметил следующее поведение:

1) Когда я запускаю программу и ввожу расширения для фильтрации (не трогая ни одного узла из QTreeView) все работает нормально и файлы с указанными мной расширениями только отображаются (и папки конечно). Когда я меняю расширения и вид обновляется, на моем диске "C:/" все обновляется и отображается только новый набор расширений. Когда я расширяю какой-то другой диск, который я раньше не трогал, он также правильно показывает файлы.

2) Когда я запускаю программу и расширяю, скажем, мои диски "C:/" и "D:/", я вижу все каталоги и файлы (ожидаемое поведение). Затем я пишу некоторые расширения, и представление обновляется. Расширяю диск "C:/" и все работает нормально, отображаются только файлы с указанными мной расширениями. Потом захожу на "D:/" диск и вот проблема. Он отображает все файлы. Он игнорирует фильтры, которые я предоставил. Когда я открываю диск "E:/", который я раньше не открывал, файлы фильтруются правильно, как и на диске "C:/".

Я пришел к выводу, что такое поведение как-то связано с методом setRootPath, потому что для моего QTreeView только на "C:/" диске фильтры работают корректно. Все остальные диски, которые были расширены до смены фильтров, не работают. Те, что не расширены, работают нормально.

Вопрос в том, как заставить это работать, чтобы после того, как пользователь меняет фильтры и запускается метод reset (), обновляется весь QTreeView, а не только корневой путь и нерасширенные элементы? Может быть, существует какой-то корневой путь, по которому все диски являются дочерними, и он будет работать должным образом? Или, может быть, мне следует создать в QTreeView какую-нибудь виртуальную папку с именем "MyComputer" и сделать ее родительской для всех дисков? Но как получить список всех доступных дисков?

Я надеюсь, что то, что я написал, понятно для вас, и вы можете помочь мне заставить это работать.

Редактировать: добавление соответствующего кода. Если вам нужно больше, просто спросите.

//setting up the model and view
QString rPath = "C:/";
rTree_model = new TreeModel(this); //TreeModel inherits from QFileSystemModel
rTree_model->setRootPath(rPath);

ui->rTree->setModel(rTree_model); //applies the model for the qtreeview (ui->rTree)

//(...)

//action when extensions were provided by user
QString extensions = QString(ui->extensionBox->text()); //gets extensions provided by user
QStringList filters;
if(extensions.length() > 0) {
    filters = extensions.split(";", QString::SkipEmptyParts); //splits extensions provided with ';' as separator
    rTree_model->setNameFilters(filters); //applies filters
    ui->rTree->reset(); //resets the view
}

person sobol6803    schedule 23.06.2013    source источник
comment
Можете ли вы опубликовать код, который поможет нам воспроизвести вашу проблему?   -  person Pavel Strakhov    schedule 23.06.2013
comment
@Riateche Вот, пожалуйста.   -  person sobol6803    schedule 23.06.2013
comment
Что делает TreeModel::reset()? Это просто реализация по умолчанию?   -  person Phlucious    schedule 26.06.2013
comment
@Phlucious, это именно так: ссылка. И это не метод из модели, а из qtreeview (элемент GUI).   -  person sobol6803    schedule 26.06.2013
comment
Я воспроизвел эту ошибку в Qt 4.8.2. Я посмотрю, смогу ли я что-нибудь придумать.   -  person Phlucious    schedule 27.06.2013


Ответы (1)


Попробуйте изменить корневой путь на Мой компьютер вместо C:/. Кажется, он работает с QFileSystemModel в Windows 7 x64 и Qt 4.8.2, но я не могу ничего гарантировать для других платформ.

rTree_model = new TreeModel(this);
QString rPath = model->myComputer().toString();   //causes the QFileSystemWatcher to watch every drive?
rTree_model->setRootPath(rPath);

ui->rTree->setModel(rTree_model);
person Phlucious    schedule 26.06.2013
comment
Ты обалденный! :) Я знал, что что-то с этим путем, но я не знал, что существует метод myComputer(). Я думаю, если бы у меня было больше времени, я бы нашел его в конце концов. В любом случае, теперь это работает, и вы получаете награду (через 14 часов это невозможно сделать сейчас). Вы заслужили это! :) - person sobol6803; 27.06.2013
comment
Рад, что это сработало! Кстати, не знаю, на каких форумах Qt вы изначально размещали сообщения, но я добился определенного успеха на qtcentre.org со своими вопросами. - person Phlucious; 27.06.2013
comment
Я разместил его на официальном форуме qt-project.org. Спасибо за совет, посмотрю этот сайт. :) - person sobol6803; 27.06.2013
comment
Вы можете просто передать пустую строку от имени пользователя root — результат будет таким же, как при получении имени «Мой компьютер». - person user362515; 22.06.2017