Russian Qt Forum
Сентябрь 30, 2024, 02:28 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1] 2   Вниз
  Печать  
Автор Тема: Сохраниение качества SVG-картинки  (Прочитано 9828 раз)
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« : Февраль 11, 2010, 15:21 »

Во многие виджеты можно воткнуть картинку, явно в документации не говориться о том, что можно использовать и SVG. Хотя есть какие-то размытые оговорки о модуле SVG.
В частности поместить картинку можно на кнопку или на метку.
Однако если я изменю размер носителя, например, метки. То SVG-картинка ведёт себя также, как если бы она была растровым рисунком.
Я не могу понять как влиять на SVG. Как сделать так, чтобы сначала задаться желаемым размером и затем бы она превратилась в растр? Иначе качество сильно страдает.
Таже проблема и при использовании QGraphicsPixmapItem
Код
C++ (Qt)
QGraphicsPixmapItem* pPixmapItem1 = new QGraphicsPixmapItem("./misc/onSwitch.svg");
Записан

Юра.
Rcus
Гость
« Ответ #1 : Февраль 11, 2010, 17:35 »

А у меня такая строка не компилится
Код:
main@krchome:/tmp/sample$ make
g++ -c -pipe -O2 -Wall -W -D_REENTRANT -DQT_NO_DEBUG -DQT_GUI_LIB -DQT_CORE_LIB -DQT_SHARED -I/usr/share/qt4/mkspecs/linux-g++ -I. -I/usr/include/qt4/QtCore -I/usr/include/qt4/QtGui -I/usr/include/qt4 -I. -I. -o main.o main.cpp
main.cpp: In function ‘int main(int, char**)’:
main.cpp:5: error: no matching function for call to ‘QGraphicsPixmapItem::QGraphicsPixmapItem(const char [13])’
/usr/include/qt4/QtGui/qgraphicsitem.h:924: note: candidates are: QGraphicsPixmapItem::QGraphicsPixmapItem(const QGraphicsPixmapItem&)
/usr/include/qt4/QtGui/qgraphicsitem.h:885: note:                 QGraphicsPixmapItem::QGraphicsPixmapItem(const QPixmap&, QGraphicsItem*, QGraphicsScene*)
/usr/include/qt4/QtGui/qgraphicsitem.h:879: note:                 QGraphicsPixmapItem::QGraphicsPixmapItem(QGraphicsItem*, QGraphicsScene*)
make: *** [main.o] Error 1
main@krchome:/tmp/sample$ g++ --version
g++ (Ubuntu 4.4.3-2ubuntu1) 4.4.3
Хотя если предположить что компилятор будет искать конструкторы преобразования то подозреваю что вызовется QString -> QPixmap -> QGraphicsPixmapItem.

Про установку SVG на виджеты не знаю, есть QSvgIconEngine для QIcon, но он должен работать так если не нашел QPixmap запрошенного размера в кеше то растеризует заново.
Записан
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #2 : Февраль 11, 2010, 18:57 »

>>А у меня такая строка не компилится
QT += svg
Непонимающий
Записан

Юра.
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #3 : Февраль 11, 2010, 19:00 »

Можешь попробовать в Дизайнере в метку запихнуть SVG-рисунок. А потом изменять размер метки (при включенном растяжении содержимого). Рисунок будет иметь только умалчиваемый для данного SVG размер, а дальше масштабируется уже растровый, со всеми вытекающими последствиями
Записан

Юра.
BRE
Гость
« Ответ #4 : Февраль 11, 2010, 19:11 »

Юра, посмотри на класс QSvgWidget и его реализацию.
Записан
Rcus
Гость
« Ответ #5 : Февраль 11, 2010, 19:13 »

>>А у меня такая строка не компилится
QT += svg
Непонимающий
И как это поможет? Полный текст main.cpp:
Код
C++ (Qt)
#include <QGraphicsPixmapItem>
 
int main(int, char**)
{
   QGraphicsPixmapItem *item = new QGraphicsPixmapItem("./sample.svg");
   Q_UNUSED(item);
}
 
Можешь попробовать в Дизайнере в метку запихнуть SVG-рисунок. А потом изменять размер метки (при включенном растяжении содержимого). Рисунок будет иметь только умалчиваемый для данного SVG размер, а дальше масштабируется уже растровый, со всеми вытекающими последствиями
И uic сгенерит примерно следующий код.
Код
C++ (Qt)
label->setPixmap(QPixmap(QString::fromUtf8("../../usr/share/icons/hicolor/scalable/actions/jockey-certified.svg")));
Упражнение по исполнению кода в уме выполняется достаточно легко и объясняет суть явления.
Записан
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #6 : Февраль 11, 2010, 20:04 »

прошу прощения, вместо сырой строки с именем файла, должно быть:
QPixmap("./misc/onSwitch.svg")

>>объясняет суть явления
Суть явления я и так понял, я не понял:
"Как сделать так, чтобы сначала задаться желаемым размером и затем бы она превратилась в растр?"
Записан

Юра.
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #7 : Февраль 11, 2010, 20:08 »

BRE, реализацию именно этого класса я не смотрел, я смотрел QPixmap, но там у маня мозги закипели. Сильно навёрнуто.

Но и туда попробую залезть.

В идеале яб хотел примерно следующее:
Код
C++ (Qt)
QSvgImage svg("./misc/onSwitch.svg");
svg.resize(100, 100, Qt::KeepAspectRatio);
label->setPixmap(svg.pixmap());
QGraphicsPixmapItem *item = new QGraphicsPixmapItem(svg.pixmap());
Записан

Юра.
Rcus
Гость
« Ответ #8 : Февраль 11, 2010, 20:17 »

А чем вам не нравится QIcon("somefile.svg").pixmap(w,h) ?
Записан
SABROG
Гость
« Ответ #9 : Февраль 11, 2010, 20:21 »

Что если попробовать QGraphicsSvgItem? А для QGraphicsPixmapItem попробовать вызвать:

Код
C++ (Qt)
item->setCacheMode(QGraphicsItem::NoCache);
 

Как вариант, переопределить QGraphicsItem::paint() и вызывать QSvgRenderer()
« Последнее редактирование: Февраль 11, 2010, 20:40 от SABROG » Записан
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #10 : Февраль 11, 2010, 20:40 »

>>А чем вам не нравится QIcon("somefile.svg").pixmap(w,h) ?
Надо попробовать, будет ли при этом качество хорошее. НО есть минус, мне нужно будет всякий раз проверять текущий размер объекта в который помещена SVG'шка.

>>Что если попробовать QGraphicsSvgItem?
Тоже вариант, изначально я грузил разного формата картинки и стремился использовать один и тот же класс. И предполагал, что QPixmap сам в состоянии разруливать мастабирование SVG'шек
« Последнее редактирование: Февраль 11, 2010, 20:42 от lit-uriy » Записан

Юра.
SABROG
Гость
« Ответ #11 : Февраль 11, 2010, 20:55 »

Судя по всему качество SVG картинки зависит от размера QPixmap'a, а этот размер не меняется при изменении размера QGraphicsItem. Можно попробовать изначально поставить размер QPixmap'a не 100x100, а больше в несколько раз чем QGraphicsItem. И не давать пользователям менять размер итема на сцене больше чем этот.
Записан
lit-uriy
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3880


Просмотр профиля WWW
« Ответ #12 : Февраль 11, 2010, 21:03 »

попробовал для QGraphicsSvgItem, Да качество такое какого хотелось.
НО выделение (прямоугольной области) и перемещение элементов, стало сильно тормозить.
По экспериментировал с режимом кэширования:
NoCache - качество картинки хорошее, тормозит
DeviceCoordinateCache - качество картинки хорошее, тормозит
ItemCoordinateCache - качество, как и при масштабировании растра, летает

Собственно и в  Асистенте о последнем режиме написано, что качество падает.
Записан

Юра.
BRE
Гость
« Ответ #13 : Февраль 11, 2010, 21:13 »

Отслеживай изменение размера картинки и перерендеривай (или перерендерь Улыбающийся ) ее на QPixmap. Думаю будет и скорость, и качество.
Записан
SABROG
Гость
« Ответ #14 : Февраль 11, 2010, 21:25 »

Отслеживай изменение размера картинки и перерендеривай (или перерендерь Улыбающийся ) ее на QPixmap. Думаю будет и скорость, и качество.

Я думал об этом, но мне кажется рендерер будет подтормаживать. Хотя попробовать стоит.

Что если пойти другим путем. Если задействовать QPixmapCache, но сначала определить сколько картинок и какого размера он будет содержать. Нужно найти в каких диапозонах изменения размера итема растровая картинка не будет сильно резать глаза при трансформации, при достижении этой границы уже генерировать следующий кэш. Предположим меняем размеры итема с 0x0 до 50x50 - одна картинка, 51x51 до 100x100 - вторая, 101x101 - 200x200 - третья. И при запросе нового размера итема выбираем нужный пиксмап из кэша.
Записан
Страниц: [1] 2   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.257 секунд. Запросов: 22.