Форум программистов, компьютерный форум, киберфорум
Наши страницы
C++ Qt
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.67/3: Рейтинг темы: голосов - 3, средняя оценка - 4.67
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
1

Ошибка при вызове метода

06.07.2019, 20:42. Просмотров 526. Ответов 17
Метки нет (Все метки)

Доброго времени суток.
Где-то в файле mainwindow.cpp в слоте я пишу:
C++ (Qt)
1
DraftsmanCube::diagonalA_C();
В этом методе diagonalA_C отрисовывается диагональ А-С с помощью QPainter, но отсюда он не вызывается... Шо не так?
Error

mainwindow.cpp:331:40: error: call to non-static member function without an object argument

Этот метод я расписал в public: в class DraftsmanCube. Т.е. там и сам метод объявлен и тело метода там же написал

P.S. Дописал в DraftsmanCube.h к void diagonal... "static", у указателя убрал (this) (потому что на него ругался...) и ошибки пропали, но он не рисует теперь...

На сколько я понимаю сейчас, весь косяк в том, что он не понимает на чем ему рисовать, но без static в файле mainwindow.cpp метод не вызывается...
C++ (Qt)
1
2
3
4
5
6
    static void diagonalA_C(){
        QPainter *DrawDiagonal = new QPainter();
        DrawDiagonal->setPen(QPen(Qt::red, 3, Qt::SolidLine));
        DrawDiagonal->drawLine(QLineF(QPointF(10, 125), QPointF(125,87))); //A-C
        delete DrawDiagonal;
    }
C++ (Qt)
1
2
3
4
                    if (itemData[i]->text() == "Диагональ")
                    {
                        DraftsmanCube::diagonalA_C();
                    }
0
QA
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
06.07.2019, 20:42
Ответы с готовыми решениями:

Ошибка при вызове метода setText
Если первый setText в func() закоментить, то работает, иначе аварийное завершение программы с...

Ошибка при вызове QImage::scaled
насколько я знаю метод scaled возвращает изображение с новой шириной и высотой тогда объясните...

Вылетает ошибка Приложение остановлено при вызове show()
Доброго времени суток. Проблема такая, имеется класс PartToolBar уноследованный от QToolBar и на...

Проблемы при вызове формы
Всем привет! Сделал вызов формы из главной формы при нажатии на кнопку, но создается новая форма, а...

SIGABRT при вызове деструктора
mainwindow.h #ifndef MAINWINDOW_H #define MAINWINDOW_H #include <QMainWindow> #include...

17
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
06.07.2019, 21:36 2
Вы посмотрите примеры, как работает QPainter.
Для начала пишут либо
C++ (Qt)
1
QPainter *DrawDiagonal = new QPainter(this);
либо
C++ (Qt)
1
DrawDiagonal->begin(this);
а если не this, то на чём он рисует, а после завершения рисования надо вызвать
C++ (Qt)
1
DrawDiagonal->end();
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
06.07.2019, 21:41  [ТС] 3
peter_irich, Перечитайте сообщение, я там ваше предложение объяснил
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
06.07.2019, 21:53 4
Да, действительно, но почему не объявить и создать эту функцию в mainwindow.cpp?
Или где хотите, но тогда рисуйте, например, в объекте типа QPixmap, а потом выводите
его в своём paintEvent().
0
06.07.2019, 21:53
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
06.07.2019, 22:47  [ТС] 5
peter_irich, DraftsmanCube - это отдельный собственный Widget у которого не функция, а метод diagonalA_C

Немного поразбирался в static и понял, что он сюды не подходит. Мне нужно вызвать метод класса DraftsmanCube::diagonalA_C(), чтобы он выполнился для уже существующего объекта который называется у меня *Cube. Как направить этот метод именно для этого объекта я не понимаю

Решение - написал такую строчку, но от этого метод не начал рисовать...
C++ (Qt)
1
Cube->diagonalA_C();
В отладчике посмотрел, через эту строчку проходит, все норм, но почему-то не рисует...

На сколько я понимаю, нужно как-то в методе указать, что надо рисовать на *Cube, но только как?
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
06.07.2019, 23:16 6
Я не знаю, в чём заключается различие между функцией и методом, но в любом случае можно вызвать
функцию одного класса из другого с параметром, вот и передавайте по ссылке объект QPixmap
или в чём хотите рисовать, а потом выводите его у себя. Соответственно ваш QPainter должен быть
не от this, а от этого QPixmap.
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
06.07.2019, 23:33  [ТС] 7
peter_irich, Вы все равно не так немного поняли, но я использовал вашу идею. Выдало в консоль вот это
QWidget:aintEngine: Should no longer be called
QPainter::begin: Paint device returned engine == 0, type: 1
QPainter::setPen: Painter not active
А получилось вот так:
C++ (Qt)
1
Cube->diagonalA_C(*Cube);
а в методе написал:
C++ (Qt)
1
2
3
void diagonalA_C(DraftsmanCube &ptr){
....
}
И в качестве родителя QPainter принимает &ptr

Случайно никаких методов перерисовки моего Widget-а вызывать не надо?
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
07.07.2019, 08:41 8
Я же всё равно не знаю, что такое Cube, т.е. что представляет собой его класс.
В любом случае над рисовать в том, в чём может рисовать QPainter, полного списка я на память не знаю.
Рисуйте в методе в QPixmap, а в Cube передавайте уже его в paintEvent() и пусть он сам его отрисовывает
как целое. Если это неудобно или нежелательно, то сделайте Cube таким, чтобы Qpainter мог в нём рисовать
без проблем. Сейчас же это как-то происходит.

Если виджет находится на экране, то принудительно его перерисовывать не надо, для него достаточно,
чтобы он был видимым. Перерисовывать надо то, что выводится в paintEvent().
0
Анна по жизни
278 / 167 / 62
Регистрация: 13.03.2019
Сообщений: 406
07.07.2019, 11:54 9
C++ (Qt)
1
2
3
4
if (itemData[i]->text() == "Диагональ")
                    {
                        DraftsmanCube::diagonalA_C();
                    }
Отрисовка должна происходить в методе DraftsmanCube:aintEvent(), следовательно, именно там должен вызываться метод diagonalA_C() . В mainWindow должно указать конкретному экземпляру:"С этого момента ты должен отрисовывать диагональ АС", но не вызывать его метод отрисовки (тем более, в этом случае диагональ отрисуется один раз, а при следующем вызове DraftsmanCube:aintEvent() она затрётся)

У DraftsmanCube должен быть метод, через который у экземпляра взведётся.снимается флажок, ответственный за отрисовку диагонали. А сама отрисовка должна происходить в paintEvent().
Кстати, не стоит каждый раз создавать и удалять объект QPainter, может, лучше передавать его в качестве аргумента: DraftsmanCube::diagonalA_C(QPainter *painter).
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
07.07.2019, 16:35 10
У меня в одной программе может использоваться либо свой paintEvent(), либо paintEvent() в другом виджете,
Этот виджет является экземпляром другого класса, его экземпляр создаваётся в главной программе и,
когда надо, делается видимым, а помещён он на то же место, на котором рисует собственный paintEvent().
У него нет рамки и прочего, что обычно есть у окна. При такой схеме трудностей или вопросов с тем,
на чём рисовать.
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
07.07.2019, 17:38  [ТС] 11
Анна по жизни, После создания объекта и расположения на форме у меня отрисовывается моя фигура в :aintEvent(QPaintEvent *); Если в :aintEvent(QPaintEvent *); произойдут изменения он Painter перерисует?
Цитата Сообщение от Анна по жизни Посмотреть сообщение
С этого момента ты должен отрисовывать диагональ АС
virtual void paintEvent(QPaintEvent *); - находится в protected, доступ получить не могу.
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
07.07.2019, 18:13 12
Я удивляюсь, вы берётесь создавать программы в Qt и не знаете, что делать с функциями из protected.
Посмотрите всё же примеры программ.

Выше ошибка, должно быть так:
При такой схеме трудностей или вопросов с тем, на чём рисовать, нет.
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
07.07.2019, 18:40  [ТС] 13
Проще говоря. Как вызвать из файла .cpp класса MainWindow, virtual void paintEvent(QPaintEvent *); который объявлен в protected класса DraftsmanCube?

Цитата Сообщение от peter_irich Посмотреть сообщение
Я удивляюсь, вы берётесь создавать программы в Qt и не знаете, что делать с функциями из protected.
Объясните, ну пожааааааалуйста, очень вас прошу. Не понимаю то, что написано в примерах

Единственное что я могу предположить, это то, что мне нужно унаследовать MainWindow от DraftsmanCube и тогда я смогу вызвать все что угодно из protected

В mainwindow.cpp у меня есть следующие строчки:
C++ (Qt)
1
2
3
4
5
6
7
8
if (ThisIsText == "Диагональ") //Логика программы (Если диагональ пользователь выбрал, то true)
{
      Cube->diagonalA_C(); /*Вызывается метод (Там он устанавливает значение bool переменной на true, а в painEvent у 
DraftsmanCube есть строчка, где при значении этой переменной true рисуется диагональ) который я объявил в DraftsmanCube в 
public. Вызывается без ошибок только так, в остальных случаях выдает разные ошибки. Cube это указатель на объект класса 
DraftsmanCube который уже создан и во всю работает в программе*/
      Cube->paintEvent(); //Как вызвать метод paintEvent не знаю ибо постоянно на меня обваливаются ошибки....
}
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
07.07.2019, 19:30 14
Неправильно предполагаете. Возьмите толстую книгу, лучше в электронном виде, и почитайте,
там и обучение и примеры. Обычно рекомендуют книгу "Макс Шлее, Qt 5.3".
А как вызвать, я написал выше в сообщении от 16.35.
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
07.07.2019, 19:37  [ТС] 15
peter_irich, Про QPainter и про QPaintEvent я читал уже в этой книге. Можете просто написать, как в моем случае должно сработать? Пожалуйста
0
peter_irich
76 / 69 / 22
Регистрация: 18.10.2017
Сообщений: 646
07.07.2019, 20:14 16
Я не знаю, как у вас должно сработать, т.к. не знаю вашей программы.
Если в этой книге вы читали о paintEvent(), то должны знать, как к ней обращаться.
Возьмите ещё Жасмин Бланшет, Марк Саммерфилд " Qt 4: программирование GUI на C++",
там примеры с разъяснениями. Когда мне в начале 2000-х потребовалось научиться создавать программы на Qt,
так я откуда-то из США выписал книгу на английском, кажется, ещё по Qt 2, чек туда посылал, посмотрел и начал работать.
За вас вашу работу делать никто не будет и чтобы научиться, надо самому пробовать, а не воспроизводить
чужие советы.
0
Анна по жизни
278 / 167 / 62
Регистрация: 13.03.2019
Сообщений: 406
08.07.2019, 11:29 17
Цитата Сообщение от MetMark Посмотреть сообщение
virtual void paintEvent(QPaintEvent *); - находится в protected, доступ получить не могу.
И не надо.

Установи флажок, по которому Cube будет рисовать диагональ, и вызови Cube->update().

Добавлено через 7 минут
https://doc.qt.io/qt-5/qtwidgets-widgets-analogclock-example.html#
Посмотри пример. Тут update() вызывается каждую секунду, чтобы перерисовать стрелки часов.
0
MetMark
0 / 0 / 0
Регистрация: 04.05.2018
Сообщений: 212
08.07.2019, 11:53  [ТС] 18
Анна по жизни, Да, я новую тему создал и уже догадался. Спасибо вам большое! Есть же добрые люди!!! Спасибо огромное вам!
0
08.07.2019, 11:53
Answers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
08.07.2019, 11:53

Задержка при вызове cv::VideoCapture::read()
Написала (ну почти скопировала отсюда) видеоплеер. Сделала переход к следующему видео в плейлисте...

QDoubleSpinBox - segfault при вызове value(), setValue()
Доброго времени суток. Странная проблема, не ожидал, что она может здесь вообще возникнуть. Гугл...

SIGSEGV при вызове функции из dll
Здравствуйте. Вообщем имею такую траблу: Некая функция DLL принимает в качестве аргумента ссылку...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
18
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2020, vBulletin Solutions, Inc.