|
194 / 29 / 5
Регистрация: 11.04.2015
Сообщений: 735
|
||||||||||||||||||||||||||||||||||||
Построение объектов на кастомной графической сцене17.05.2022, 13:00. Показов 1441. Ответов 5
Метки нет (Все метки)
Всем доброго времени суток!
Не так давно я начал активно заниматься графикой (если таким громким словом можно назвать мои потуги) в Qt, поэтому проше не судить строго. Прошу помощи в осознании логики создания и управления новыми объектами в окне GraphicsView, помещённом в окно главного приложения (UI), созданном с помощью дизайнера форм. Что я делаю: создаю форму и добавляю туда GraphicsView. В MainWindow.cpp создаю сцену, определяющуюся не стандартным классом QGraphicsScene, а кастомным классом paintScene, наследующимся от стандартного. Далее я создаю класс paint_polygon, который должен помогать выводить на сцену полигональные фигуры по моему усмотрению. Что я хотел бы получить: по одиночному нажатию левой кнопкой мыши по граф. сцене в месте нажатия должен появляться маркер, а за курсором мыши должен начать ездить (двигаться и менять размер, если движение мыши того требует) сектор (сколько-то-градусный "раструб"), начинающийся в маркере и центром дуги касающийся курсора мыши (приложу изображение ниже). "Ездить" сектор должен до тех пор, пока я не нажму на ЛКМ ещё раз - по второму нажатию по ЛКМ сектор должен закрепиться на сцене в текущем виде и сохраниться в какое-то хранилище таких объектов, откуда мы в дальнейшем сможем получать информацию о каждом из них. Что есть сейчас: кастомная сцена, на которой удаётся создать квадрат - объект класса paint_polygon. Далее я хотел научиться двигать его по сцене мышкой (как в куче примеров), но с кастомной сценой что-то пошло не так - Qt не понимает, что я жмакаю по квадрату, а не по сцене, и создаёт ещё один квадрат. Вероятно, я что-то упускаю в наследовании, хотя делаю один-в-один с примерами (отдельный пример для перетаскивания, и отдельный - для кастомизации сцены) и ошибок при сборке не возникает. Код приложу (а если нужно, и весь проект, но на Qt 5.15.2 всё работает). По сути, я хотел бы разобраться с тем, почему не работает то, что есть сейчас (идеи кончились - не заработало), но если кто-нибудь подскажет, как реализовать изначально задуманное - буду невероятно благодарен! mainwindow.h
mainwindow.cpp
main.cpp
paintScene.h
paintScene.cpp
paint_polygon.h
paint_polygon.cpp
P.S. Этот код, почему-то, удаляет новосозданный кубик, если кликнуть ЛКМ после создания кубика, не перемещая указатель мыши (или если попасть мышью в его центр). Такого функционала я в коде не вижу в принципе, но предполагаю, что это может так отработать искомое мной перемещение кубика; тогда два вопроса - куда он переезжает и почему реагирует только на клик ровно по центру объекта?
0
|
||||||||||||||||||||||||||||||||||||
| 17.05.2022, 13:00 | |
|
Ответы с готовыми решениями:
5
Дерганая анимация на графической сцене Пропадают элементы на графической сцене Обращение к графической сцене из объекта, входящего в нее |
|
Покинул чат.
1132 / 727 / 195
Регистрация: 30.03.2021
Сообщений: 2,379
|
||||||||||||||||||||||||||||||||||||||||||
| 19.05.2022, 01:40 | ||||||||||||||||||||||||||||||||||||||||||
Сообщение было отмечено Ромуальд_7 как решение
Решение
не разбирался в Вашем коде, нафигачил свой вариант-не думал что он выйдет несколько более обьемным чем хотелось, разобраться будет сложно, наверное... (выкладываю "как есть", хотя наверное тут многое можно упростить)
Поэтому вот краткое описание проекта: Кликните здесь для просмотра всего текста
Проект без использования дизайнера(снимите галочку "добавить форму" при создании) -класс CustomScene: кастомная сцена, перехватывает события мыши и создает/двигает фигуры из класса Figure. -класс Figure: рассчет и отрисовка фигуры на графической сцене. Наследован от QGraphicsItem. -класс FigureButton: это кнопка на форме, при нажатии на которую сцене передается тип фигуры, которую следует создать. Наследован от QWidget, включает в себя графический вид и сцену для отображения на кнопке рисунка фигуры. -класс MainWindow управляет компоновкой формы, связи ее элементов сигналами/слотами файл main.cpp -дефолтный. customscene.h Кликните здесь для просмотра всего текста
customscene.cpp Кликните здесь для просмотра всего текста
figure.h Кликните здесь для просмотра всего текста
figure.cpp Кликните здесь для просмотра всего текста
figurebutton.h Кликните здесь для просмотра всего текста
figurebutton.cpp Кликните здесь для просмотра всего текста
mainwindow.h Кликните здесь для просмотра всего текста
mainwindow.cpp Кликните здесь для просмотра всего текста
результат:
2
|
||||||||||||||||||||||||||||||||||||||||||
|
Покинул чат.
1132 / 727 / 195
Регистрация: 30.03.2021
Сообщений: 2,379
|
|
| 19.05.2022, 02:00 | |
|
зы: код особо не тестил, так что если где чего упустил/недопилил/набыдлокодил-на критику не обижаюсь.
1
|
|
|
194 / 29 / 5
Регистрация: 11.04.2015
Сообщений: 735
|
||
| 20.05.2022, 16:42 [ТС] | ||
|
sdf45, гениально! Огромное Вам спасибо!
однако, если Вы не возражаете, существует пара вопросов, поскольку я не вполне осознаю некоторые моменты.Скажите, пожалуйста, правильно ли я понимаю, что именно НЕОБХОДИМО создавать кастомную граф. сцену во всех подобных ситуациях, поскольку стандартным событием QMouseEvent, обрабатывающимся непосредственно внутри mainwindow.cpp, не получится корректно (и/или без костылей) обрабатывать события мыши на граф. сцене? Также я правда не понимаю - оно (Qt) правда не умеет само определять нажатие на конкретный объект на сцене? То есть, matlab, например, работает иначе - при помощи одного и того же обработчика событий нажатия на клавиши мыши верхнего уровня (уровня всего GUI) делается абсолютно всё - только код успевай писать; так, например, нажатие на граф. поле там провоцирует отклик граф. элемента, по которому попали (и если их в этой точке несколько, выбирается лежащий на верхнем слое). Я вижу в Вашем файле кучку коннектов, с механизмом работы которых я ещё не разобрался, но мне уже страшно Правильно ли я понимаю, что эти connect'ы как раз и заставляют нажатие мышью на объект обрабатываться исключительным образом, минуя главное окно, а за тем и сцену?И не могли бы Вы рассказать, что именно делает класс figurebutton? Это тот ряд кнопок на панели слева? Добавлено через 11 минут P.S. Про figurebutton - я тупой - вопрос снимаю ![]() Добавлено через 49 минут P.P.S. А, и для чего происходит рекурсивный вызов функций, вроде QGraphicsScene::mousePressEvent(mouseEve nt); ? Де-факто, рекурсивной эта конструкция не оказывается, однако выглядит именно так, и предназначение её не вполне ясно, ведь работает и без этого вызова.
0
|
||
|
Покинул чат.
1132 / 727 / 195
Регистрация: 30.03.2021
Сообщений: 2,379
|
|||||||||||||||||||||
| 20.05.2022, 21:08 | |||||||||||||||||||||
|
Кликните здесь для просмотра всего текста
В первом случае ловим событие виджетом (который для QGraphicsScene ,будет QGraphicsView, на котором расположена сцена) Во втором случае ловим непосредственно сценой, виджет событий не получает. Можно конечно ловить события виджетом окна, переводить координаты из глобальных в коорд. систему сцены, но зачем, если можно проще. Что касается кастомной сцены-совсем не обязательно, если нет необходимости в дополнительном функционале. Вы можете обрабатывать события в кастомном графическом элементе, порожденным от QGraphicsItem, либо установить для него флаги itemIsMovable | itemIsSelextable | itemIsFocusable - и Qt все сделает сам - итем можно будет выделять, перемещать, а так же обрабатывать события Hover Кликните здесь для просмотра всего текста
Когда кликаем (ловим это событие) в графической сцене, мы должны знать, нажата ли кнопка создания фигуры на форме. Если кнопка нажата, то активируем флаг "создаем фигуру", первый клик мышкой на сцене определяет первую точку фигуры, двигая мышью и нажав лкм второй раз-определяем вторую точку фигуры, создаем фигуру и добавляем на сцену.
Так же если мы нажимаем на кнопку, остальные кнопки надо отжать, поэтому связываем
Всю эту канитель надо было делать на QGroupButton как я выше написал. Если ниодна из кнопок не нажата, в сцене устанавливается флаг "выбираем и двигаем фигуры", при котором при нажатии лкм определяется, есть ли фигура под курсором (itemAt) и если есть-сохраняем в поле класса. Если двигаем мышкой-двигаем и эту сохраненную фигуру (setPos). Там еще я несколько криво сделал манипуляции с zValue фигур, но переделывать тоже лень.
1
|
|||||||||||||||||||||
|
194 / 29 / 5
Регистрация: 11.04.2015
Сообщений: 735
|
||
| 21.05.2022, 22:28 [ТС] | ||
![]() Также благодарю и за прочие разъяснения - действительно стало понятнее.
0
|
||
| 21.05.2022, 22:28 | |
|
Помогаю со студенческими работами здесь
6
Поиск объектов на сцене
Перемещение объектов по сцене Проверка на наличие объектов на сцене Искать еще темы с ответами Или воспользуйтесь поиском по форуму: |
|
Новые блоги и статьи
|
|||
|
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога
Финальные проекты на Си и на C++:
hello-sdl3-c. zip
hello-sdl3-cpp. zip
Результат:
|
Установка CMake и MinGW 13.1 для сборки С и C++ приложений из консоли и из Qt Creator в EXE
8Observer8 10.03.2026
Содержание блога
MinGW - это коллекция инструментов для сборки приложений в EXE. CMake - это система сборки приложений. Здесь описаны базовые шаги для старта программирования с помощью CMake и. . .
|
Как дизайн сайта влияет на конверсию: 7 решений, которые реально повышают заявки
Neotwalker 08.03.2026
Многие до сих пор воспринимают дизайн сайта как “красивую оболочку”. На практике всё иначе: дизайн напрямую влияет на то, оставит человек заявку или уйдёт через несколько секунд.
Даже если у вас. . .
|
Модульная разработка через nuget packages
DevAlt 07.03.2026
Сложившийся в . Net-среде способ разработки чаще всего предполагает
монорепозиторий в котором находятся все исходники.
При создании нового решения, мы просто добавляем нужные проекты
и имеем. . .
|
|
Модульный подход на примере F#
DevAlt 06.03.2026
В блоге дяди Боба наткнулся на такое определение:
В этой книге («Подход, основанный на вариантах использования») Ивар утверждает,
что архитектура программного обеспечения — это
структуры,. . .
|
Управление камерой с помощью скрипта OrbitControls.js на Three.js: Вращение, зум и панорамирование
8Observer8 05.03.2026
Содержание блога
Финальная демка в браузере работает на Desktop и мобильных браузерах. Итоговый код: orbit-controls-threejs-js. zip. Сканируйте QR-код на мобильном. Вращайте камеру одним пальцем,. . .
|
SDL3 для Web (WebAssembly): Синхронизация спрайтов SDL3 и тел Box2D
8Observer8 04.03.2026
Содержание блога
Финальная демка в браузере. Итоговый код: finish-sync-physics-sprites-sdl3-c. zip
На первой гифке отладочные линии отключены, а на второй включены:. . .
|
SDL3 для Web (WebAssembly): Идентификация объектов на Box2D v3 - использование userData и событий коллизий
8Observer8 02.03.2026
Содержание блога
Финальная демка в браузере. Итоговый код: finish-collision-events-sdl3-c. zip Сканируйте QR-код на мобильном и вы увидите, что появится джойстик для управления главным героем.
. . .
|