crossplatform.ru

Здравствуйте, гость ( Вход | Регистрация )

 
Ответить в данную темуНачать новую тему
> QGraphicsItem кривые безье
lpenguin
  опции профиля:
сообщение 26.11.2010, 18:53
Сообщение #1


Новичок


Группа: Новичок
Сообщений: 2
Регистрация: 26.11.2010
Пользователь №: 2223

Спасибо сказали: 0 раз(а)




Репутация:   0  


Пытаюсь сейчас в Qt отрисовать граф, соотвественно, если между двумя вершинами есть больше чем 2 (или больше) ребра,
я рисую их с помощью метода QPainterPath.cubicTo как кривые, чтобы их "раздвинуть". Примерно так:


Проблема вот в чем - ребра это классы, унаследованные от QGraphicsItem, и нужно чтобы при наведении на одно из ребер оно подсвечивалось. Переопределил paint (в нем с помощью QPainterPath отрисовывается кривая) , boundingRect (это границы того QPainterPath ) и shape( возвращает QPainterPath) - однако если с одной стороны ребер больше чем два, то выделяется все время только одно, которое больше отстоит от вершин. На картинке подсвечивается либо верхнее, либо нижнее например. Вроде все довольно просто, однако как-будто ребра перекрывают одно другое. =(

вот код paint:
Раскрывающийся текст
void EdgeItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget)
{

    if (option->state.testFlag(QStyle::State_HasFocus) )
     {
        painter->setBrush(QColor(255, 255, 190));

     }
     else if (option->state.testFlag(QStyle::State_MouseOver))
     {
         painter->setPen(QPen(m_color, 3, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin));
     }
     else
     {
         painter->setPen(QPen(m_color, 2, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin));
     }
    painter->setRenderHint(QPainter::Antialiasing );
    painter->drawPath( m_path );
}


shape:
QPainterPath EdgeItem::shape () const{
    return m_path;
}


boundingRect
QRectF EdgeItem::boundingRect() const
{
        return m_path.boundingRect();
}


может кто-нибудь подсказать в чем дело?
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Алексей1153
  опции профиля:
сообщение 26.11.2010, 19:09
Сообщение #2


фрилансер
******

Группа: Участник
Сообщений: 2941
Регистрация: 19.6.2010
Из: Обливион
Пользователь №: 1822

Спасибо сказали: 215 раз(а)




Репутация:   34  


я в таких случаях поступаю очень просто: запоминаю последнее место отрисовки объекта. Потом, когда курсор проходит над запомненной коодинатой, нужно включить соответствующий триггер.
Поскольку у тебя кривая линия, нужно запоминать описание множества точек этой линии
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Litkevich Yuriy
  опции профиля:
сообщение 26.11.2010, 21:15
Сообщение #3


разработчик РЭА
*******

Группа: Сомодератор
Сообщений: 9669
Регистрация: 9.1.2008
Из: Тюмень
Пользователь №: 64

Спасибо сказали: 807 раз(а)




Репутация:   94  


Алексей1153, это какой-то жуткий вариант.
Надо один раз разобраться с причиной проблемы и всё.

Цитата(lpenguin @ 26.11.2010, 20:53) *
то выделяется все время только одно, которое больше отстоит от вершин
а не рисуется ли оно после внутренних? Т.е. находится ли оно ближе к наблюдателю, чем внутренние рёбра
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
lpenguin
  опции профиля:
сообщение 26.11.2010, 22:04
Сообщение #4


Новичок


Группа: Новичок
Сообщений: 2
Регистрация: 26.11.2010
Пользователь №: 2223

Спасибо сказали: 0 раз(а)




Репутация:   0  


Цитата(Алексей1153 @ 26.11.2010, 19:09) *
Поскольку у тебя кривая линия, нужно запоминать описание множества точек этой линии

Да можно было бы нарисовать все ребро по точкам, но я то хотел пользоваться Qtшными функциями, и для подсветки тоже Qtшными инструментами, благо все есть =)

Цитата(Litkevich Yuriy @ 26.11.2010, 21:15) *
а не рисуется ли оно после внутренних? Т.е. находится ли оно ближе к наблюдателю, чем внутренние рёбра

да, сначала рисуются ближние ребра, а самое дальнее добавлется на сцену последним. Но ведь это не должно никак влиять на определение есть ли курсор над элементом или нет. А всетаки есть ощущение что это расчитывается из boundingRect, а не shape.
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
igor_bogomolov
  опции профиля:
сообщение 26.11.2010, 23:44
Сообщение #5


Профессионал
*****

Группа: Сомодератор
Сообщений: 1215
Регистрация: 22.3.2009
Из: Саратов
Пользователь №: 630

Спасибо сказали: 235 раз(а)




Репутация:   29  


lpenguin в качестве варианта. Попробуйте переопределить события мыши. Зная позицию курсора можно получить список элементов под ней QList<QGraphicsItem *>items ( const QPoint & pos ) const. Дальше получая их QPainterPath определять кривую над которой находится указанель мыши bool QPainterPath::contains ( const QPointF & point ) const
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Litkevich Yuriy
  опции профиля:
сообщение 27.11.2010, 12:40
Сообщение #6


разработчик РЭА
*******

Группа: Сомодератор
Сообщений: 9669
Регистрация: 9.1.2008
Из: Тюмень
Пользователь №: 64

Спасибо сказали: 807 раз(а)




Репутация:   94  


Цитата(lpenguin @ 27.11.2010, 0:04) *
А всетаки есть ощущение что это расчитывается из boundingRect, а не shape.
сначала используется охватывающий прямоугольник, как только мышь в нём, проверяется контур (shape). Я одно время с этим тоже воевал. И не помню, где именно я ошибся, что-то у меня не билось с контуром.
Задача была выделять окружность, щёлкая в область ±несколько пикселей от её границы. Так, чтобы можно было легко выделять несколько наложенных друг на друга окружностей.
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение
Алексей1153
  опции профиля:
сообщение 27.11.2010, 20:14
Сообщение #7


фрилансер
******

Группа: Участник
Сообщений: 2941
Регистрация: 19.6.2010
Из: Обливион
Пользователь №: 1822

Спасибо сказали: 215 раз(а)




Репутация:   34  


Цитата(Litkevich Yuriy @ 26.11.2010, 23:15) *
это какой-то жуткий вариант.

для не-точки - да , согласен :) Но для точки - идеален. Для окружности тоже (точка - частный случай окружности). Что нарисовалось, то и выделилось - никаких косяков
Перейти в начало страницы
 
Быстрая цитата+Цитировать сообщение

Быстрый ответОтветить в данную темуНачать новую тему
Теги
Нет тегов для показа


2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0




RSS Текстовая версия Сейчас: 22.12.2024, 12:18