Russian Qt Forum
Ноябрь 01, 2024, 07:27
Добро пожаловать,
Гость
. Пожалуйста,
войдите
или
зарегистрируйтесь
.
Вам не пришло
письмо с кодом активации?
1 час
1 день
1 неделя
1 месяц
Навсегда
Войти
Начало
Форум
WIKI (Вики)
FAQ
Помощь
Поиск
Войти
Регистрация
Russian Qt Forum
>
Forum
>
Qt
>
2D и 3D графика
>
Drag-n-drop нескольких QGraphicsItem
Страниц: [
1
]
2
Вниз
« предыдущая тема
следующая тема »
Печать
Автор
Тема: Drag-n-drop нескольких QGraphicsItem (Прочитано 9408 раз)
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Drag-n-drop нескольких QGraphicsItem
«
:
Август 18, 2015, 16:02 »
Давно и успешно работает DnD одного айтема по QGraphicsScene. Сейчас используется стандартный механизм - в наследнике QGraphicsItem переопределен метод mouseMoveEvent(QGraphicsSceneMouseEvent *event). Внутри него, чтобы начался собственно драг, как рекомендованно в документации, делается
Код:
QDrag* drag = new QDrag( event->widget() );
далее в драг MIME-пакуются нужные данные, приклеивается картинка и собственно начинается drag->exec(). Как положено, если он вернул Qt::IgnoreAction (то есть, бросили в непотребном месте), то айтем возвращается на то место сцены, откуда его драгнули. Всё пучком. Однако пришло время сделать тоже самое для неизвестного заранее числа выделенных айтемов.
И тут пока не совсем ясно - есть вроде бы два пути:
1) Разделить эту функцию на две - одна собственно ловит начало драга, другая его собственно производит. Если выбран более чем один айтем, то в одном из них (который потащили) определяется факт начала драга, а потом для всех выбранных айтемов вызываются функции, производящие собственно драги. У каждого айтема свой драг со своим MIME-пакетом данных. И тогда по идее каждый айтем должен поехать. Но... А могут ли вообще существовать несколько одновременно выполняемых QDrag? Вроде бы эта функциональность реализована средствами ОС, и тут становится еще более не понятно - а все ли хостовые для Qt операционки умеют адекватно таскать несколько MIME-нутых объектов, и умеют ли вообще таскать больше одного?
2) Вроде бы более простой вариант - оставить как есть, но формировать картинку драга из изображения всех подхваченных элементов, в одном месте отрывать их от сцены, запихивать их данные в MIME
одного драга
, а при падении ронять их из этого майма руками последовательно, один за другим. Что в реализации очевидно будет гораздо более муторно и громоздко, особенно при падении.
Дополнительную сложность представляет то, что сцена не одна - их две, и соответственно группа может перетаскиваться между двумя сценами, либо может быть ошибочно брошена вне любой из сцен.
Кто-нибудь делал мульти-драг нескольких айтемов? Как в общем поступили? Можно общее словесное описание модели, без кода?
Записан
2^7-1 == 127, задумайтесь...
GreatSnake
Джедай : наставник для всех
Offline
Сообщений: 2921
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #1 :
Август 18, 2015, 16:30 »
Цитата: Гурман от Август 18, 2015, 16:02
А могут ли вообще существовать несколько одновременно выполняемых QDrag?
Нет.
Записан
Qt 5.11/4.8.7 (X11/Win)
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #2 :
Август 18, 2015, 17:13 »
Ну то есть, путь номер 2 только... Там вроде всё понятно, и также понятно, что решение не получится элегантным.
«
Последнее редактирование: Август 18, 2015, 17:16 от Гурман
»
Записан
2^7-1 == 127, задумайтесь...
Igors
Джедай : наставник для всех
Offline
Сообщений: 11445
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #3 :
Август 18, 2015, 17:23 »
Вариант 1 не достоин обсуждения
Цитата: Гурман от Август 18, 2015, 16:02
2) ...но формировать картинку драга из изображения всех подхваченных элементов..
Именно так делает Qt - и это безобразно (да простят меня фаны, но и на солнце есть пятна). Никому и нафиг не нужна громадная ползающая простыня. Где-то здесь болтается пример, делал DnD строк в таблице. Одна строка - один листик. Две строки - два. Три и более - три листика, все, больше наращивать drag image нет смысла. Общий размер "таскаемого" не больше 100 пыкселей. "Use metaphor" как учит "Human Interface.."
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #4 :
Август 18, 2015, 17:36 »
Цитата: Igors от Август 18, 2015, 17:23
Именно так делает Qt
где он так делает?
Цитата: Igors от Август 18, 2015, 17:23
- и это безобразно (да простят меня фаны, но и на солнце есть пятна). Никому и нафиг не нужна громадная ползающая простыня.
смотря что именно таскается... в случае схемы из множества элементов, реально пользователь будет таскать только несколько лежащих рядом друг с другом - на предмет освобождения пространства, или для красоты размещения
ну и, наконец, если самому изображение формировать, ничто не мешает "растворить" его края, и даже сделать пользовательскую настройку размеров таскаемого изображения
Записан
2^7-1 == 127, задумайтесь...
Igors
Джедай : наставник для всех
Offline
Сообщений: 11445
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #5 :
Август 18, 2015, 18:09 »
Цитата: Гурман от Август 18, 2015, 17:36
где он так делает?
Та везде, QTableWidget, QTreeWidget и.т.п. Попробуйте выбрать много айтемов и тащить.. (можно просто в дызайнере). Неужели нравится?
Цитата: Гурман от Август 18, 2015, 17:36
смотря что именно таскается... в случае схемы из множества элементов, реально пользователь будет таскать только несколько лежащих рядом друг с другом - на предмет освобождения пространства, или для красоты размещения
ну и, наконец, если самому изображение формировать, ничто не мешает "растворить" его края, и даже сделать пользовательскую настройку размеров таскаемого изображения
Забейте на это и сделайте "абстрактный" таскаемый имедж - так намного и лучше и дешевле.
Что касается самих данных. Корректный, академический подход - драг сам содержит все что драгается. Даже если источник уже удален - дроп должен сработать. Часто это сводится к сериализации в том или ином виде. Не всегда так удобно делать - часто куда легче проскочить напр используя selection источника. В любом случае - откуда проблемы? Ну дропнули 2 (или 10, 100) вместо только одного, в чем (принципиальные) сложности-то?
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #6 :
Август 18, 2015, 18:59 »
Цитата: Igors от Август 18, 2015, 18:09
Та везде, QTableWidget, QTreeWidget и.т.п. Попробуйте выбрать много айтемов и тащить.. (можно просто в дызайнере). Неужели нравится?
Не знаю, не пробовал.
Цитата: Igors от Август 18, 2015, 18:09
Забейте на это и сделайте "абстрактный" таскаемый имедж - так намного и лучше и дешевле.
Нет, так не пойдет. У меня схема, и пользователь перетаскивает элементы схемы, которые могут иметь самые разные изображения, сейчас я просто беру текущее изображение элемента, и его делаю битмапом, подгоняю курсор под позицию начала. Выглядит очень естественно - лежит на схеме элемент, его взяли и перенесли. Если выделяется много элементов, их тоже надо взять и перенести. Можно при переносе действительно не рисовать все элементы (циркулярный градиент прозрачности на изображение драга наложить), но пользователь должен видеть что именно и куда он тащит.
Цитата: Igors от Август 18, 2015, 18:09
Что касается самих данных. Корректный, академический подход - драг сам содержит все что драгается. Даже если источник уже удален - дроп должен сработать. Часто это сводится к сериализации в том или ином виде. Не всегда так удобно делать - часто куда легче проскочить напр используя selection источника. В любом случае - откуда проблемы? Ну дропнули 2 (или 10, 100) вместо только одного, в чем (принципиальные) сложности-то?
Таскаемые объекты у меня в принципе не могут быть удалены во время драга (только при завершении приложения). Но внутреннее состояние объектов может измениться во время драга (в любом объекте даже во время драга может работать нить, или он может сигнал получить), и упасть должен изменённый консистентный объект, а не тот, который начинали тащить. Если точнее - то у меня таскают и роняют не сам объект, а только его изображение на схеме. Поэтому вместо сериализованного объекта, драг у меня содержит просто указатель на объект. Теперь вместо одного указателя надо запихивать в драг массив указателей при начале переноса, и при падении соответственно доставать все указатели и ронять все объекты, причём каждый в его относительную позицию от начала драга - чтобы они попадали относительно друг друга примерно так же, как их со схемы подняли. Придётся эти относительные позиции тоже вместе с указателями в драг запихивать, поскольку одной только позиции самого дропа теперь недостаточно, у каждого объекта будет своя позиция дропа. Логических сложностей вроде бы нет, просто заметно больше придётся добавить кода. Вручную всё, ибо увы, в Qt мульти-драг никак не поддерживается на нижнем уровне.
«
Последнее редактирование: Август 18, 2015, 19:01 от Гурман
»
Записан
2^7-1 == 127, задумайтесь...
Igors
Джедай : наставник для всех
Offline
Сообщений: 11445
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #7 :
Август 18, 2015, 19:37 »
Цитата: Гурман от Август 18, 2015, 18:59
Нет, так не пойдет. У меня схема, ...
Не "пойдет". а "полетит" - нужно только отказаться от предрассудков засевших в наших головах (да, это трудно, мы всегда переоцениваем собственный опыт)
Цитата: Гурман от Август 18, 2015, 18:59
Таскаемые объекты у меня в принципе не могут быть удалены во время драга (только при завершении приложения). Но внутреннее состояние объектов может измениться во время драга (в любом объекте даже во время драга может работать нить, или он может сигнал получить), и упасть должен изменённый консистентный объект, а не тот, который начинали тащить. Если точнее - то у меня таскают и роняют не сам объект, а только его изображение на схеме. Поэтому вместо сериализованного объекта, драг у меня содержит просто указатель на объект. Теперь вместо одного указателя надо запихивать в драг массив указателей при начале переноса, и при падении соответственно доставать все указатели и ронять все объекты, причём каждый в его относительную позицию от начала драга - чтобы они попадали относительно друг друга примерно так же, как их со схемы подняли. Придётся эти относительные позиции тоже вместе с указателями в драг запихивать, поскольку одной только позиции самого дропа теперь недостаточно, у каждого объекта будет своя позиция дропа. Логических сложностей вроде бы нет,
Ну это глухая специфика задачи - надо так надо. Случай очень редкий - обычно принимающему все равно "как были выбраны" - то ли это айтемы (0, 1, 2) то ли (100, 200, 300) - его дело "принять" и обычно "подряд". Что-то мутить с позицией - ой вряд ли
Цитата: Гурман от Август 18, 2015, 18:59
просто заметно больше придётся добавить кода. Вручную всё, ибо увы, в Qt мульти-драг никак не поддерживается на нижнем уровне.
Вы уж меня извините, но просто неудобно (и обидно) слышать такой "поросячий визг" от человека примерно моего возраста. Хуже молодого, "ах, попку не подмыли" - ничего, сами подмоетесь
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #8 :
Август 18, 2015, 20:13 »
Цитата: Igors от Август 18, 2015, 19:37
Ну это глухая специфика задачи - надо так надо. Случай очень редкий - обычно принимающему все равно "как были выбраны" - то ли это айтемы (0, 1, 2) то ли (100, 200, 300) - его дело "принять" и обычно "подряд". Что-то мутить с позицией - ой вряд ли
Не вряд ли, а точно. Чтобы было понятнее о чем речь - c рисовалками блочных диаграмм типа
Visio
или чем-то аналогичным (OpenOffice Draw) приходилось иметь дело? Вот аналогично нарисована схема, выделяются на ней несколько элементов с зажатой кнопкой Ctrl, и перетаскиваются в другое место схемы. При этом взаимное расположение элементов не меняется, то есть, координаты каждого учитывать надо. Совсем не редкий случай.
Цитата: Гурман от Август 18, 2015, 18:59
Вы уж меня извините, но просто неудобно (и обидно) слышать такой "поросячий визг" от человека примерно моего возраста. Хуже молодого, "ах, попку не подмыли" - ничего, сами подмоетесь
Не нашел никакого "поросячьего визга", это глупость какая-то. Есть констатация факта - мульти-драг довольно востребованная операция, которая в Qt никак не поддерживается. Хотя решение, на самом деле, получится типовое, вполне могло бы быть библиотечным.
«
Последнее редактирование: Август 18, 2015, 20:24 от Гурман
»
Записан
2^7-1 == 127, задумайтесь...
Old
Джедай : наставник для всех
Offline
Сообщений: 4350
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #9 :
Август 18, 2015, 21:20 »
Цитата: Гурман от Август 18, 2015, 17:13
Ну то есть, путь номер 2 только... Там вроде всё понятно, и также понятно, что решение не получится элегантным.
Только это и остается.
Судя по описанию вы undo-стек не реализовывали? В данном случае вы бы использовали его механизмы для удаления/вставки и промежуточного хранения объектов.
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #10 :
Август 18, 2015, 21:34 »
Цитата: Old от Август 18, 2015, 21:20
Цитата: Гурман от Август 18, 2015, 17:13
Ну то есть, путь номер 2 только... Там вроде всё понятно, и также понятно, что решение не получится элегантным.
Только это и остается.
Судя по описанию вы undo-стек не реализовывали? В данном случае вы бы использовали его механизмы для удаления/вставки и промежуточного хранения объектов.
нет, но в планах, с начала не было очевидно, как его делать, поскольку не было очевидно, какие объекты как будут работать, сейчас основное реализовано, и undo-redo более-менее просматривается
Записан
2^7-1 == 127, задумайтесь...
Old
Джедай : наставник для всех
Offline
Сообщений: 4350
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #11 :
Август 18, 2015, 21:41 »
Цитата: Гурман от Август 18, 2015, 21:34
нет, но в планах, с начала не было очевидно, как его делать, поскольку не было очевидно, какие объекты как будут работать, сейчас основное реализовано, и undo-redo более-менее просматривается
Ну раз оно уже просматривается, то должны просматриваться контейнеры для объектов, в которые они будут помещаться при удалении, для того, что бы была возможность при redo их восстановить. Т.е. для этого (так же как и для перетаскивания) понадобятся операции удалить со сцены объекты в промежуточный контейнер и вернуть на сцену объекты из промежуточного контейнера. С помощью них перетаскивание сведется к удалению и вставке в новое место (или в старое если перетаскивание отменили).
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #12 :
Август 18, 2015, 22:52 »
Цитата: Old от Август 18, 2015, 21:41
Цитата: Гурман от Август 18, 2015, 21:34
нет, но в планах, с начала не было очевидно, как его делать, поскольку не было очевидно, какие объекты как будут работать, сейчас основное реализовано, и undo-redo более-менее просматривается
Ну раз оно уже просматривается, то должны просматриваться контейнеры для объектов, в которые они будут помещаться при удалении, для того, что бы была возможность при redo их восстановить. Т.е. для этого (так же как и для перетаскивания) понадобятся операции удалить со сцены объекты в промежуточный контейнер и вернуть на сцену объекты из промежуточного контейнера. С помощью них перетаскивание сведется к удалению и вставке в новое место (или в старое если перетаскивание отменили).
Нет, тут всё не так... в подробности нет смысла вдаваться, но никакие контейнеры в моём случае не нужны. Перетаскивание по одному объекту и так давным давно работает, надо сделать на его основе перетаскивание многих. Как делать, ясно, но переделка получается не в десять строк.
Записан
2^7-1 == 127, задумайтесь...
Old
Джедай : наставник для всех
Offline
Сообщений: 4350
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #13 :
Август 18, 2015, 23:00 »
Я не на чем не настаиваю.
Просто если undo-стек в планах, то реализуйте перетаскивание с видами на него. Что бы функции используемые для перетаскивании в дальнейшем можно было использовать для реализации других операций, как то групповое удаление объектов со сцены и откат этой операции (и наоборот).
Записан
Гурман
Гуру общения
Offline
Сообщений: 1442
Qt 2.2, 3.3, 4.5, 4,7, 4.8, 5.3, 5.6, 5.9, 5.12
Re: Drag-n-drop нескольких QGraphicsItem
«
Ответ #14 :
Август 18, 2015, 23:08 »
Цитата: Old от Август 18, 2015, 23:00
Я не на чем не настаиваю.
Просто если undo-стек в планах, то реализуйте перетаскивание с видами на него. Что бы функции используемые для перетаскивании в дальнейшем можно было использовать для реализации других операций, как то групповое удаление объектов со сцены и откат этой операции (и наоборот).
Вот фишка в том, что те объекты, которые перетаскиваются, никогда не удаляются, а те, которые удаляются, никогда не перетаскиваются.
Записан
2^7-1 == 127, задумайтесь...
Страниц: [
1
]
2
Вверх
Печать
« предыдущая тема
следующая тема »
Перейти в:
Пожалуйста, выберите назначение:
-----------------------------
Qt
-----------------------------
=> Вопросы новичков
=> Уроки и статьи
=> Установка, сборка, отладка, тестирование
=> Общие вопросы
=> Пользовательский интерфейс (GUI)
=> Qt Quick
=> Model-View (MV)
=> Базы данных
=> Работа с сетью
=> Многопоточное программирование, процессы
=> Мультимедиа
=> 2D и 3D графика
=> OpenGL
=> Печать
=> Интернационализация, локализация
=> QSS
=> XML
=> Qt Script, QtWebKit
=> ActiveX
=> Qt Embedded
=> Дополнительные компоненты
=> Кладовая готовых решений
=> Вклад сообщества в Qt
=> Qt-инструментарий
-----------------------------
Программирование
-----------------------------
=> Общий
=> С/C++
=> Python
=> Алгоритмы
=> Базы данных
=> Разработка игр
-----------------------------
Компиляторы и платформы
-----------------------------
=> Linux
=> Windows
=> Mac OS X
=> Компиляторы
===> Visual C++
-----------------------------
Разное
-----------------------------
=> Новости
===> Новости Qt сообщества
===> Новости IT сферы
=> Говорилка
=> Юмор
=> Объявления
Загружается...