1 /***************************************************************************
2 titlewidget.cpp - description
5 copyright : (C) 2008 by Marco Gittler
6 email : g.marco@freenet.de
7 ***************************************************************************/
9 /***************************************************************************
11 * This program is free software; you can redistribute it and/or modify *
12 * it under the terms of the GNU General Public License as published by *
13 * the Free Software Foundation; either version 2 of the License, or *
14 * (at your option) any later version. *
16 ***************************************************************************/
18 #include "titlewidget.h"
19 #include "kdenlivesettings.h"
24 #include <KGlobalSettings>
25 #include <KFileDialog>
26 #include <KStandardDirs>
27 #include <KMessageBox>
28 #include <kio/netaccess.h>
29 #include <kdeversion.h>
31 #include <QDomDocument>
32 #include <QGraphicsItem>
33 #include <QGraphicsSvgItem>
37 #include <QSignalMapper>
38 #include <QTextBlockFormat>
39 #include <QTextCursor>
41 #if QT_VERSION >= 0x040600
42 #include <QGraphicsEffect>
43 #include <QGraphicsBlurEffect>
44 #include <QGraphicsDropShadowEffect>
47 int settingUp = false;
49 const int IMAGEITEM = 7;
50 const int RECTITEM = 3;
51 const int TEXTITEM = 8;
53 const int NOEFFECT = 0;
54 const int BLUREFFECT = 1;
55 const int SHADOWEFFECT = 2;
56 const int TYPEWRITEREFFECT = 3;
58 TitleWidget::TitleWidget(KUrl url, Timecode tc, QString projectTitlePath, Render *render, QWidget *parent) :
61 m_startViewport(NULL),
65 m_unicodeDialog(new UnicodeDialog(UnicodeDialog::InputHex)),
66 m_projectTitlePath(projectTitlePath),
70 setFont(KGlobalSettings::toolBarFont());
71 frame_properties->setEnabled(false);
72 frame_properties->setFixedHeight(frame_toolbar->height());
74 itemzoom->setSuffix(i18n("%"));
75 m_frameWidth = render->renderWidth();
76 m_frameHeight = render->renderHeight();
77 showToolbars(TITLE_SELECT);
79 //TODO: get default title duration instead of hardcoded one
80 title_duration->setText(m_tc.getTimecode(GenTime(5000 / 1000.0)));
82 connect(kcolorbutton, SIGNAL(clicked()), this, SLOT(slotChangeBackground())) ;
83 connect(horizontalSlider, SIGNAL(valueChanged(int)), this, SLOT(slotChangeBackground())) ;
85 connect(fontColorButton, SIGNAL(clicked()), this, SLOT(slotUpdateText())) ;
86 connect(font_family, SIGNAL(currentFontChanged(const QFont &)), this, SLOT(slotUpdateText())) ;
87 connect(font_size, SIGNAL(valueChanged(int)), this, SLOT(slotUpdateText())) ;
88 connect(textAlpha, SIGNAL(valueChanged(int)), this, SLOT(slotUpdateText()));
89 connect(font_weight_box, SIGNAL(currentIndexChanged(int)), this, SLOT(slotUpdateText()));
91 connect(font_family, SIGNAL(editTextChanged(const QString &)), this, SLOT(slotFontText(const QString&)));
93 connect(rectFAlpha, SIGNAL(valueChanged(int)), this, SLOT(rectChanged()));
94 connect(rectBAlpha, SIGNAL(valueChanged(int)), this, SLOT(rectChanged()));
95 connect(rectFColor, SIGNAL(clicked()), this, SLOT(rectChanged()));
96 connect(rectBColor, SIGNAL(clicked()), this, SLOT(rectChanged()));
97 connect(rectLineWidth, SIGNAL(valueChanged(int)), this, SLOT(rectChanged()));
99 /*connect(startViewportX, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));
100 connect(startViewportY, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));
101 connect(startViewportSize, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));
102 connect(endViewportX, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));
103 connect(endViewportY, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));
104 connect(endViewportSize, SIGNAL(valueChanged(int)), this, SLOT(setupViewports()));*/
107 effect_list->addItem(i18n("None"), NOEFFECT);
108 effect_list->addItem(i18n("Typewriter"), TYPEWRITEREFFECT);
109 effect_list->addItem(i18n("Blur"), BLUREFFECT);
112 connect(zValue, SIGNAL(valueChanged(int)), this, SLOT(zIndexChanged(int)));
113 connect(itemzoom, SIGNAL(valueChanged(int)), this, SLOT(itemScaled(int)));
114 connect(itemrotate, SIGNAL(valueChanged(int)), this, SLOT(itemRotate(int)));
115 connect(itemhcenter, SIGNAL(clicked()), this, SLOT(itemHCenter()));
116 connect(itemvcenter, SIGNAL(clicked()), this, SLOT(itemVCenter()));
117 connect(itemtop, SIGNAL(clicked()), this, SLOT(itemTop()));
118 connect(itembottom, SIGNAL(clicked()), this, SLOT(itemBottom()));
119 connect(itemleft, SIGNAL(clicked()), this, SLOT(itemLeft()));
120 connect(itemright, SIGNAL(clicked()), this, SLOT(itemRight()));
121 connect(effect_list, SIGNAL(currentIndexChanged(int)), this, SLOT(slotAddEffect(int)));
122 connect(typewriter_delay, SIGNAL(valueChanged(int)), this, SLOT(slotEditTypewriter(int)));
123 connect(typewriter_start, SIGNAL(valueChanged(int)), this, SLOT(slotEditTypewriter(int)));
124 connect(blur_radius, SIGNAL(valueChanged(int)), this, SLOT(slotEditBlur(int)));
125 connect(shadow_radius, SIGNAL(valueChanged(int)), this, SLOT(slotEditShadow()));
126 connect(shadow_x, SIGNAL(valueChanged(int)), this, SLOT(slotEditShadow()));
127 connect(shadow_y, SIGNAL(valueChanged(int)), this, SLOT(slotEditShadow()));
128 effect_stack->setHidden(true);
129 effect_frame->setEnabled(false);
131 connect(origin_x_left, SIGNAL(clicked()), this, SLOT(slotOriginXClicked()));
132 connect(origin_y_top, SIGNAL(clicked()), this, SLOT(slotOriginYClicked()));
134 m_signalMapper = new QSignalMapper(this);
135 m_signalMapper->setMapping(value_w, ValueWidth);
136 m_signalMapper->setMapping(value_h, ValueHeight);
137 connect(value_w, SIGNAL(valueChanged(int)), m_signalMapper, SLOT(map()));
138 connect(value_h, SIGNAL(valueChanged(int)), m_signalMapper, SLOT(map()));
139 connect(m_signalMapper, SIGNAL(mapped(int)), this, SLOT(slotValueChanged(int)));
141 connect(value_x, SIGNAL(valueChanged(int)), this, SLOT(slotAdjustSelectedItem()));
142 connect(value_y, SIGNAL(valueChanged(int)), this, SLOT(slotAdjustSelectedItem()));
143 connect(value_w, SIGNAL(valueChanged(int)), this, SLOT(slotAdjustSelectedItem()));
144 connect(value_h, SIGNAL(valueChanged(int)), this, SLOT(slotAdjustSelectedItem()));
145 connect(buttonFitZoom, SIGNAL(clicked()), this, SLOT(slotAdjustZoom()));
146 connect(buttonRealSize, SIGNAL(clicked()), this, SLOT(slotZoomOneToOne()));
147 connect(buttonItalic, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
148 connect(buttonUnder, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
149 connect(buttonAlignLeft, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
150 connect(buttonAlignRight, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
151 connect(buttonAlignCenter, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
152 connect(buttonAlignNone, SIGNAL(clicked()), this, SLOT(slotUpdateText()));
153 //connect(buttonInsertUnicode, SIGNAL(clicked()), this, SLOT(slotInsertUnicode()));
154 connect(displayBg, SIGNAL(stateChanged(int)), this, SLOT(displayBackgroundFrame()));
156 connect(m_unicodeDialog, SIGNAL(charSelected(QString)), this, SLOT(slotInsertUnicodeString(QString)));
159 connect(this, SIGNAL(accepted()), this, SLOT(slotAccepted()));
161 font_weight_box->blockSignals(true);
162 font_weight_box->addItem(i18nc("Font style", "Light"), QFont::Light);
163 font_weight_box->addItem(i18nc("Font style", "Normal"), QFont::Normal);
164 font_weight_box->addItem(i18nc("Font style", "Demi-Bold"), QFont::DemiBold);
165 font_weight_box->addItem(i18nc("Font style", "Bold"), QFont::Bold);
166 font_weight_box->addItem(i18nc("Font style", "Black"), QFont::Black);
167 font_weight_box->setToolTip(i18n("Font weight"));
168 font_weight_box->setCurrentIndex(1);
169 font_weight_box->blockSignals(false);
171 buttonFitZoom->setIcon(KIcon("zoom-fit-best"));
172 buttonRealSize->setIcon(KIcon("zoom-original"));
173 buttonItalic->setIcon(KIcon("format-text-italic"));
174 buttonUnder->setIcon(KIcon("format-text-underline"));
175 buttonAlignCenter->setIcon(KIcon("format-justify-center"));
176 buttonAlignLeft->setIcon(KIcon("format-justify-left"));
177 buttonAlignRight->setIcon(KIcon("format-justify-right"));
178 buttonAlignNone->setIcon(KIcon("kdenlive-align-none"));
180 buttonAlignNone->setToolTip(i18n("No alignment"));
181 buttonAlignRight->setToolTip(i18n("Align right"));
182 buttonAlignLeft->setToolTip(i18n("Align left"));
183 buttonAlignCenter->setToolTip(i18n("Align center"));
185 m_unicodeAction = new QAction(KIcon("kdenlive-insert-unicode"), QString(), this);
186 m_unicodeAction->setShortcut(Qt::SHIFT + Qt::CTRL + Qt::Key_U);
187 m_unicodeAction->setToolTip(i18n("Insert Unicode character") + ' ' + m_unicodeAction->shortcut().toString());
188 connect(m_unicodeAction, SIGNAL(triggered()), this, SLOT(slotInsertUnicode()));
189 buttonInsertUnicode->setDefaultAction(m_unicodeAction);
191 m_zUp = new QAction(KIcon("kdenlive-zindex-up"), QString(), this);
192 m_zUp->setShortcut(Qt::Key_PageUp);
193 m_zUp->setToolTip(i18n("Raise object"));
194 connect(m_zUp, SIGNAL(triggered()), this, SLOT(slotZIndexUp()));
195 zUp->setDefaultAction(m_zUp);
197 m_zDown = new QAction(KIcon("kdenlive-zindex-down"), QString(), this);
198 m_zDown->setShortcut(Qt::Key_PageDown);
199 m_zDown->setToolTip(i18n("Lower object"));
200 connect(m_zDown, SIGNAL(triggered()), this, SLOT(slotZIndexDown()));
201 zDown->setDefaultAction(m_zDown);
203 m_zTop = new QAction(KIcon("kdenlive-zindex-top"), QString(), this);
204 m_zTop->setShortcut(Qt::Key_Home);
205 m_zTop->setToolTip(i18n("Raise object to top"));
206 connect(m_zTop, SIGNAL(triggered()), this, SLOT(slotZIndexTop()));
207 zTop->setDefaultAction(m_zTop);
209 m_zBottom = new QAction(KIcon("kdenlive-zindex-bottom"), QString(), this);
210 m_zBottom->setShortcut(Qt::Key_End);
211 m_zBottom->setToolTip(i18n("Lower object to bottom"));
212 connect(m_zBottom, SIGNAL(triggered()), this, SLOT(slotZIndexBottom()));
213 zBottom->setDefaultAction(m_zBottom);
215 zDown->setIcon(KIcon("kdenlive-zindex-down"));
216 zTop->setIcon(KIcon("kdenlive-zindex-top"));
217 zBottom->setIcon(KIcon("kdenlive-zindex-bottom"));
218 connect(zDown, SIGNAL(clicked()), this, SLOT(slotZIndexDown()));
219 connect(zTop, SIGNAL(clicked()), this, SLOT(slotZIndexTop()));
220 connect(zBottom, SIGNAL(clicked()), this, SLOT(slotZIndexBottom()));
222 origin_x_left->setToolTip(i18n("Invert x axis and change 0 point"));
223 origin_y_top->setToolTip(i18n("Invert y axis and change 0 point"));
224 rectBColor->setToolTip(i18n("Select fill color"));
225 rectFColor->setToolTip(i18n("Select border color"));
226 rectBAlpha->setToolTip(i18n("Fill transparency"));
227 rectFAlpha->setToolTip(i18n("Border transparency"));
228 zoom_slider->setToolTip(i18n("Zoom"));
229 buttonRealSize->setToolTip(i18n("Original size (1:1)"));
230 buttonFitZoom->setToolTip(i18n("Fit zoom"));
231 kcolorbutton->setToolTip(i18n("Select background color"));
232 horizontalSlider->setToolTip(i18n("Background Transparency"));
234 itemhcenter->setIcon(KIcon("kdenlive-align-hor"));
235 itemhcenter->setToolTip(i18n("Align item horizontally"));
236 itemvcenter->setIcon(KIcon("kdenlive-align-vert"));
237 itemvcenter->setToolTip(i18n("Align item vertically"));
238 itemtop->setIcon(KIcon("kdenlive-align-top"));
239 itemtop->setToolTip(i18n("Align item to top"));
240 itembottom->setIcon(KIcon("kdenlive-align-bottom"));
241 itembottom->setToolTip(i18n("Align item to bottom"));
242 itemright->setIcon(KIcon("kdenlive-align-right"));
243 itemright->setToolTip(i18n("Align item to right"));
244 itemleft->setIcon(KIcon("kdenlive-align-left"));
245 itemleft->setToolTip(i18n("Align item to left"));
248 QHBoxLayout *layout = new QHBoxLayout;
249 frame_toolbar->setLayout(layout);
250 layout->setContentsMargins(0, 0, 0, 0);
251 QToolBar *m_toolbar = new QToolBar("titleToolBar", this);
252 int s = style()->pixelMetric(QStyle::PM_SmallIconSize);
253 m_toolbar->setIconSize(QSize(s, s));
255 m_buttonCursor = m_toolbar->addAction(KIcon("transform-move"), QString());
256 m_buttonCursor->setCheckable(true);
257 m_buttonCursor->setShortcut(Qt::ALT + Qt::Key_S);
258 m_buttonCursor->setToolTip(i18n("Selection Tool") + ' ' + m_buttonCursor->shortcut().toString());
259 connect(m_buttonCursor, SIGNAL(triggered()), this, SLOT(slotSelectTool()));
261 m_buttonText = m_toolbar->addAction(KIcon("insert-text"), QString());
262 m_buttonText->setCheckable(true);
263 m_buttonText->setShortcut(Qt::ALT + Qt::Key_T);
264 m_buttonText->setToolTip(i18n("Add Text") + ' ' + m_buttonText->shortcut().toString());
265 connect(m_buttonText, SIGNAL(triggered()), this, SLOT(slotTextTool()));
267 m_buttonRect = m_toolbar->addAction(KIcon("kdenlive-insert-rect"), QString());
268 m_buttonRect->setCheckable(true);
269 m_buttonRect->setShortcut(Qt::ALT + Qt::Key_R);
270 m_buttonRect->setToolTip(i18n("Add Rectangle") + ' ' + m_buttonRect->shortcut().toString());
271 connect(m_buttonRect, SIGNAL(triggered()), this, SLOT(slotRectTool()));
273 m_buttonImage = m_toolbar->addAction(KIcon("insert-image"), QString());
274 m_buttonImage->setCheckable(false);
275 m_buttonImage->setShortcut(Qt::ALT + Qt::Key_I);
276 m_buttonImage->setToolTip(i18n("Add Image") + ' ' + m_buttonImage->shortcut().toString());
277 connect(m_buttonImage, SIGNAL(triggered()), this, SLOT(slotImageTool()));
279 m_toolbar->addSeparator();
281 m_buttonLoad = m_toolbar->addAction(KIcon("document-open"), i18n("Open Document"));
282 m_buttonLoad->setCheckable(false);
283 m_buttonLoad->setShortcut(Qt::CTRL + Qt::Key_O);
284 connect(m_buttonLoad, SIGNAL(triggered()), this, SLOT(loadTitle()));
286 m_buttonSave = m_toolbar->addAction(KIcon("document-save-as"), i18n("Save As"));
287 m_buttonSave->setCheckable(false);
288 m_buttonSave->setShortcut(Qt::CTRL + Qt::Key_S);
289 connect(m_buttonSave, SIGNAL(triggered()), this, SLOT(saveTitle()));
291 layout->addWidget(m_toolbar);
293 // initialize graphic scene
294 m_scene = new GraphicsSceneRectMove(this);
295 graphicsView->setScene(m_scene);
296 m_titledocument.setScene(m_scene, m_frameWidth, m_frameHeight);
297 connect(m_scene, SIGNAL(changed(QList<QRectF>)), this, SLOT(slotChanged()));
299 // a gradient background
300 /*QRadialGradient *gradient = new QRadialGradient(0, 0, 10);
301 gradient->setSpread(QGradient::ReflectSpread);
302 scene->setBackgroundBrush(*gradient);*/
304 m_frameImage = new QGraphicsPixmapItem();
306 qtrans.scale(2.0, 2.0);
307 m_frameImage->setTransform(qtrans);
308 m_frameImage->setZValue(-1200);
309 m_frameImage->setFlags(0);
310 displayBackgroundFrame();
311 graphicsView->scene()->addItem(m_frameImage);
313 connect(m_scene, SIGNAL(selectionChanged()), this , SLOT(selectionChanged()));
314 connect(m_scene, SIGNAL(itemMoved()), this , SLOT(selectionChanged()));
315 connect(m_scene, SIGNAL(sceneZoom(bool)), this , SLOT(slotZoom(bool)));
316 connect(m_scene, SIGNAL(actionFinished()), this , SLOT(slotSelectTool()));
317 //connect(m_scene, SIGNAL(actionFinished()), this , SLOT(selectionChanged()));
318 connect(m_scene, SIGNAL(newRect(QGraphicsRectItem *)), this , SLOT(slotNewRect(QGraphicsRectItem *)));
319 connect(m_scene, SIGNAL(newText(QGraphicsTextItem *)), this , SLOT(slotNewText(QGraphicsTextItem *)));
320 connect(zoom_slider, SIGNAL(valueChanged(int)), this , SLOT(slotUpdateZoom(int)));
322 QPen framepen(Qt::DotLine);
323 framepen.setColor(Qt::red);
325 m_frameBorder = new QGraphicsRectItem(QRectF(0, 0, m_frameWidth, m_frameHeight));
326 m_frameBorder->setPen(framepen);
327 m_frameBorder->setZValue(-1100);
328 m_frameBorder->setBrush(Qt::transparent);
329 m_frameBorder->setFlags(0);
330 graphicsView->scene()->addItem(m_frameBorder);
332 // mbd: load saved settings
335 graphicsView->show();
336 //graphicsView->setRenderHint(QPainter::Antialiasing);
337 graphicsView->setInteractive(true);
338 //graphicsView->resize(400, 300);
339 kDebug() << "// TITLE WIDGWT: " << graphicsView->viewport()->width() << "x" << graphicsView->viewport()->height();
340 //toolBox->setItemEnabled(2, false);
341 m_startViewport = new QGraphicsRectItem(QRectF(0, 0, m_frameWidth, m_frameHeight));
342 m_endViewport = new QGraphicsRectItem(QRectF(0, 0, m_frameWidth, m_frameHeight));
343 m_startViewport->setData(0, m_frameWidth);
344 m_startViewport->setData(1, m_frameHeight);
345 m_endViewport->setData(0, m_frameWidth);
346 m_endViewport->setData(1, m_frameHeight);
348 if (!url.isEmpty()) loadTitle(url);
351 QTimer::singleShot(200, this, SLOT(slotAdjustZoom()));
354 connect(anim_start, SIGNAL(toggled(bool)), this, SLOT(slotAnimStart(bool)));
355 connect(anim_end, SIGNAL(toggled(bool)), this, SLOT(slotAnimEnd(bool)));
357 buttonBox->button(QDialogButtonBox::Ok)->setEnabled(KdenliveSettings::hastitleproducer());
360 TitleWidget::~TitleWidget()
364 delete m_buttonImage;
365 delete m_buttonCursor;
368 delete m_unicodeAction;
374 delete m_unicodeDialog;
375 delete m_frameBorder;
377 delete m_startViewport;
378 delete m_endViewport;
380 delete m_signalMapper;
384 QStringList TitleWidget::getFreeTitleInfo(const KUrl &projectUrl, bool isClone)
387 QString titlePath = projectUrl.path(KUrl::AddTrailingSlash) + "titles/";
388 KStandardDirs::makeDir(titlePath);
389 titlePath.append((isClone == false) ? "title" : "clone");
392 while (path.isEmpty() || QFile::exists(path)) {
394 path = titlePath + QString::number(counter).rightJustified(3, '0', false) + ".png";
396 result.append(((isClone == false) ? i18n("Title") : i18n("Clone")) + ' ' + QString::number(counter).rightJustified(3, '0', false));
402 QString TitleWidget::getTitleResourceFromName(const KUrl &projectUrl, const QString &titleName)
405 QString titlePath = projectUrl.path(KUrl::AddTrailingSlash) + "titles/";
406 KStandardDirs::makeDir(titlePath);
407 return titlePath + titleName + ".png";
411 QStringList TitleWidget::extractImageList(QString xml)
414 if (xml.isEmpty()) return result;
417 QDomNodeList images = doc.elementsByTagName("content");
418 for (int i = 0; i < images.count(); i++) {
419 if (images.at(i).toElement().hasAttribute("url"))
420 result.append(images.at(i).toElement().attribute("url"));
427 void TitleWidget::resizeEvent(QResizeEvent * /*event*/)
432 void TitleWidget::slotTextTool()
434 m_scene->setTool(TITLE_TEXT);
435 showToolbars(TITLE_TEXT);
436 checkButton(TITLE_TEXT);
439 void TitleWidget::slotRectTool()
441 m_scene->setTool(TITLE_RECTANGLE);
442 showToolbars(TITLE_RECTANGLE);
443 checkButton(TITLE_RECTANGLE);
446 void TitleWidget::slotSelectTool()
448 m_scene->setTool(TITLE_SELECT);
450 // Find out which toolbars need to be shown, depending on selected item
451 TITLETOOL t = TITLE_SELECT;
452 QList<QGraphicsItem *> l = graphicsView->scene()->selectedItems();
454 switch (l.at(0)->type()) {
468 if (t == TITLE_RECTANGLE && (l.at(0) == m_endViewport || l.at(0) == m_startViewport)) {
469 //graphicsView->centerOn(l.at(0));
475 updateCoordinates(l.at(0));
476 updateDimension(l.at(0));
477 updateRotZoom(l.at(0));
480 checkButton(TITLE_SELECT);
483 void TitleWidget::slotImageTool()
485 // TODO: find a way to get a list of all supported image types...
486 QString allExtensions = "image/gif image/jpeg image/png image/x-tga image/x-bmp image/svg+xml image/tiff image/x-xcf-gimp image/x-vnd.adobe.photoshop image/x-pcx image/x-exr";
487 KUrl url = KFileDialog::getOpenUrl(KUrl(), allExtensions, this, i18n("Load Image")); //"*.svg *.png *.jpg *.jpeg *.gif *.raw"
488 if (!url.isEmpty()) {
489 if (url.path().endsWith(".svg")) {
490 QGraphicsSvgItem *svg = new QGraphicsSvgItem(url.toLocalFile());
491 svg->setFlags(QGraphicsItem::ItemIsMovable | QGraphicsItem::ItemIsSelectable);
492 svg->setZValue(m_count++);
493 svg->setData(Qt::UserRole, url.path());
494 graphicsView->scene()->addItem(svg);
496 QPixmap pix(url.path());
497 QGraphicsPixmapItem *image = new QGraphicsPixmapItem(pix);
498 image->setShapeMode(QGraphicsPixmapItem::BoundingRectShape);
499 image->setFlags(QGraphicsItem::ItemIsMovable | QGraphicsItem::ItemIsSelectable);
500 image->setData(Qt::UserRole, url.path());
501 image->setZValue(m_count++);
502 graphicsView->scene()->addItem(image);
505 m_scene->setTool(TITLE_SELECT);
506 showToolbars(TITLE_SELECT);
507 checkButton(TITLE_SELECT);
510 void TitleWidget::showToolbars(TITLETOOL toolType)
512 toolbar_stack->setCurrentIndex((int) toolType);
515 void TitleWidget::enableToolbars(TITLETOOL toolType)
517 // TITLETOOL is defined in graphicsscenerectmove.h
519 if (toolType == TITLE_RECTANGLE || toolType == TITLE_IMAGE) enable = true;
520 value_w->setEnabled(enable);
521 value_h->setEnabled(enable);
524 void TitleWidget::checkButton(TITLETOOL toolType)
526 bool bSelect = false;
538 case TITLE_RECTANGLE:
548 m_buttonCursor->setChecked(bSelect);
549 m_buttonText->setChecked(bText);
550 m_buttonRect->setChecked(bRect);
551 m_buttonImage->setChecked(bImage);
554 void TitleWidget::displayBackgroundFrame()
556 if (!displayBg->isChecked()) {
557 QPixmap bg(m_frameWidth / 2, m_frameHeight / 2);
558 QPixmap pattern(20, 20);
560 QColor bgcolor(210, 210, 210);
563 p.fillRect(QRect(0, 0, 10, 10), bgcolor);
564 p.fillRect(QRect(10, 10, 20, 20), bgcolor);
569 p.fillRect(bg.rect(), br);
571 m_frameImage->setPixmap(bg);
573 m_frameImage->setPixmap(QPixmap::fromImage(m_render->extractFrame((int) m_render->seekPosition().frames(m_render->fps()), m_frameWidth / 2, m_frameHeight / 2)));
577 void TitleWidget::initAnimation()
579 align_box->setEnabled(false);
580 QPen startpen(Qt::DotLine);
581 QPen endpen(Qt::DashDotLine);
582 startpen.setColor(QColor(100, 200, 100, 140));
583 endpen.setColor(QColor(200, 100, 100, 140));
585 m_startViewport->setPen(startpen);
586 m_endViewport->setPen(endpen);
588 m_startViewport->setZValue(-1000);
589 m_endViewport->setZValue(-1000);
591 m_startViewport->setFlags(0);
592 m_endViewport->setFlags(0);
594 graphicsView->scene()->addItem(m_startViewport);
595 graphicsView->scene()->addItem(m_endViewport);
597 connect(keep_aspect, SIGNAL(toggled(bool)), this, SLOT(slotKeepAspect(bool)));
598 connect(resize50, SIGNAL(clicked()), this, SLOT(slotResize50()));
599 connect(resize100, SIGNAL(clicked()), this, SLOT(slotResize100()));
600 connect(resize200, SIGNAL(clicked()), this, SLOT(slotResize200()));
603 void TitleWidget::slotUpdateZoom(int pos)
605 m_scene->setZoom((double) pos / 100);
606 zoom_label->setText(QString::number(pos) + '%');
609 void TitleWidget::slotZoom(bool up)
611 int pos = zoom_slider->value();
614 zoom_slider->setValue(pos);
617 void TitleWidget::slotAdjustZoom()
619 /*double scalex = graphicsView->width() / (double)(m_frameWidth * 1.2);
620 double scaley = graphicsView->height() / (double)(m_frameHeight * 1.2);
621 if (scalex > scaley) scalex = scaley;
622 int zoompos = (int)(scalex * 7 + 0.5);*/
623 graphicsView->fitInView(m_frameBorder, Qt::KeepAspectRatio);
624 int zoompos = graphicsView->matrix().m11() * 100;
625 zoom_slider->setValue(zoompos);
626 graphicsView->centerOn(m_frameBorder);
629 void TitleWidget::slotZoomOneToOne()
631 zoom_slider->setValue(100);
632 graphicsView->centerOn(m_frameBorder);
635 void TitleWidget::slotNewRect(QGraphicsRectItem * rect)
637 updateAxisButtons(rect); // back to default
639 QColor f = rectFColor->color();
640 f.setAlpha(rectFAlpha->value());
642 penf.setWidth(rectLineWidth->value());
644 QColor b = rectBColor->color();
645 b.setAlpha(rectBAlpha->value());
646 rect->setBrush(QBrush(b));
647 rect->setZValue(m_count++);
648 //setCurrentItem(rect);
649 //graphicsView->setFocus();
652 void TitleWidget::slotNewText(QGraphicsTextItem *tt)
654 updateAxisButtons(tt); // back to default
656 QFont font = font_family->currentFont();
657 font.setPixelSize(font_size->value());
659 font.setWeight(font_weight_box->itemData(font_weight_box->currentIndex()).toInt());
660 font.setItalic(buttonItalic->isChecked());
661 font.setUnderline(buttonUnder->isChecked());
664 QColor color = fontColorButton->color();
665 color.setAlpha(textAlpha->value());
666 tt->setDefaultTextColor(color);
667 tt->setZValue(m_count++);
671 void TitleWidget::setFontBoxWeight(int weight)
673 int index = font_weight_box->findData(weight);
675 index = font_weight_box->findData(QFont::Normal);
677 font_weight_box->setCurrentIndex(index);
680 void TitleWidget::setCurrentItem(QGraphicsItem *item)
682 m_scene->setSelectedItem(item);
685 void TitleWidget::zIndexChanged(int v)
687 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
693 void TitleWidget::selectionChanged()
695 if (m_scene->tool() != TITLE_SELECT) return;
696 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
697 //toolBox->setItemEnabled(2, false);
698 //toolBox->setItemEnabled(3, false);
699 value_x->blockSignals(true);
700 value_y->blockSignals(true);
701 value_w->blockSignals(true);
702 value_h->blockSignals(true);
703 itemzoom->blockSignals(true);
704 itemrotate->blockSignals(true);
706 effect_stack->setHidden(true);
707 effect_frame->setEnabled(false);
708 effect_list->setCurrentIndex(0);
709 bool blockX = !origin_x_left->signalsBlocked();
710 bool blockY = !origin_y_top->signalsBlocked();
711 if (blockX) origin_x_left->blockSignals(true);
712 if (blockY) origin_y_top->blockSignals(true);
713 origin_x_left->setChecked(false);
714 origin_y_top->setChecked(false);
717 enableToolbars(TITLE_SELECT);
718 if (blockX) origin_x_left->blockSignals(false);
719 if (blockY) origin_y_top->blockSignals(false);
720 itemzoom->setEnabled(false);
721 itemrotate->setEnabled(false);
722 frame_properties->setEnabled(false);
723 } else if (l.size() == 1) {
724 effect_frame->setEnabled(true);
725 frame_properties->setEnabled(true);
726 if (l.at(0) != m_startViewport && l.at(0) != m_endViewport) {
727 itemzoom->setEnabled(true);
728 itemrotate->setEnabled(true);
730 itemzoom->setEnabled(false);
731 itemrotate->setEnabled(false);
734 if (l.at(0)->type() == TEXTITEM) {
735 showToolbars(TITLE_TEXT);
736 QGraphicsTextItem* i = static_cast <QGraphicsTextItem *>(l.at(0));
737 if (!i->data(100).isNull()) {
738 // Item has an effect
739 QStringList effdata = i->data(100).toStringList();
740 QString effectName = effdata.takeFirst();
741 if (effectName == "typewriter") {
742 QStringList params = effdata.at(0).split(';');
743 typewriter_delay->setValue(params.at(0).toInt());
744 typewriter_start->setValue(params.at(1).toInt());
745 effect_list->setCurrentIndex(effect_list->findData((int) TYPEWRITEREFFECT));
746 effect_stack->setHidden(false);
749 #if QT_VERSION >= 0x040600
750 if (i->graphicsEffect()) {
751 QGraphicsBlurEffect *blur = static_cast <QGraphicsBlurEffect *>(i->graphicsEffect());
753 effect_list->setCurrentIndex(effect_list->findData((int) BLUREFFECT));
754 int rad = (int) blur->blurRadius();
755 blur_radius->setValue(rad);
756 effect_stack->setHidden(false);
758 QGraphicsDropShadowEffect *shad = static_cast <QGraphicsDropShadowEffect *>(i->graphicsEffect());
760 effect_list->setCurrentIndex(effect_list->findData((int) SHADOWEFFECT));
761 shadow_radius->setValue(shad->blurRadius());
762 shadow_x->setValue(shad->xOffset());
763 shadow_y->setValue(shad->yOffset());
764 effect_stack->setHidden(false);
768 effect_list->blockSignals(true);
769 effect_list->setCurrentIndex(effect_list->findData((int) NOEFFECT));
770 effect_list->blockSignals(false);
771 effect_stack->setHidden(true);
774 effect_list->blockSignals(true);
775 effect_list->setCurrentIndex(effect_list->findData((int) NOEFFECT));
776 effect_list->blockSignals(false);
777 effect_stack->setHidden(true);
780 //if (l[0]->hasFocus())
781 //toolBox->setCurrentIndex(0);
782 //toolBox->setItemEnabled(2, true);
783 font_size->blockSignals(true);
784 font_family->blockSignals(true);
785 font_weight_box->blockSignals(true);
786 buttonItalic->blockSignals(true);
787 buttonUnder->blockSignals(true);
788 fontColorButton->blockSignals(true);
789 textAlpha->blockSignals(true);
790 buttonAlignLeft->blockSignals(true);
791 buttonAlignRight->blockSignals(true);
792 buttonAlignNone->blockSignals(true);
793 buttonAlignCenter->blockSignals(true);
795 QFont font = i->font();
796 font_family->setCurrentFont(font);
797 font_size->setValue(font.pixelSize());
798 buttonItalic->setChecked(font.italic());
799 buttonUnder->setChecked(font.underline());
800 setFontBoxWeight(font.weight());
802 QColor color = i->defaultTextColor();
803 fontColorButton->setColor(color);
804 textAlpha->setValue(color.alpha());
806 QTextCursor cur = i->textCursor();
807 QTextBlockFormat format = cur.blockFormat();
808 if (i->textWidth() == -1) buttonAlignNone->setChecked(true);
809 else if (format.alignment() == Qt::AlignHCenter) buttonAlignCenter->setChecked(true);
810 else if (format.alignment() == Qt::AlignRight) buttonAlignRight->setChecked(true);
811 else if (format.alignment() == Qt::AlignLeft) buttonAlignLeft->setChecked(true);
813 font_size->blockSignals(false);
814 font_family->blockSignals(false);
815 font_weight_box->blockSignals(false);
816 buttonItalic->blockSignals(false);
817 buttonUnder->blockSignals(false);
818 fontColorButton->blockSignals(false);
819 textAlpha->blockSignals(false);
820 buttonAlignLeft->blockSignals(false);
821 buttonAlignRight->blockSignals(false);
822 buttonAlignNone->blockSignals(false);
823 buttonAlignCenter->blockSignals(false);
825 updateAxisButtons(i);
826 updateCoordinates(i);
828 enableToolbars(TITLE_TEXT);
830 } else if ((l.at(0))->type() == RECTITEM) {
831 showToolbars(TITLE_RECTANGLE);
833 QGraphicsRectItem *rec = static_cast <QGraphicsRectItem *>(l.at(0));
834 if (rec == m_startViewport || rec == m_endViewport) {
835 /*toolBox->setCurrentIndex(3);
836 toolBox->widget(0)->setEnabled(false);
837 toolBox->widget(1)->setEnabled(false);*/
838 enableToolbars(TITLE_SELECT);
840 /*toolBox->widget(0)->setEnabled(true);
841 toolBox->widget(1)->setEnabled(true);
842 toolBox->setCurrentIndex(0);*/
843 //toolBox->setItemEnabled(3, true);
844 rectFAlpha->setValue(rec->pen().color().alpha());
845 rectBAlpha->setValue(rec->brush().color().alpha());
846 //kDebug() << rec->brush().color().alpha();
847 QColor fcol = rec->pen().color();
848 QColor bcol = rec->brush().color();
849 //fcol.setAlpha(255);
850 //bcol.setAlpha(255);
851 rectFColor->setColor(fcol);
852 rectBColor->setColor(bcol);
854 rectLineWidth->setValue(rec->pen().width());
855 enableToolbars(TITLE_RECTANGLE);
858 updateAxisButtons(l.at(0));
859 updateCoordinates(rec);
860 updateDimension(rec);
862 } else if (l.at(0)->type() == IMAGEITEM) {
863 showToolbars(TITLE_IMAGE);
865 updateCoordinates(l.at(0));
866 updateDimension(l.at(0));
868 enableToolbars(TITLE_IMAGE);
871 //toolBox->setCurrentIndex(0);
872 showToolbars(TITLE_SELECT);
873 enableToolbars(TITLE_SELECT);
874 frame_properties->setEnabled(false);
876 zValue->setValue((int)l.at(0)->zValue());
877 itemzoom->setValue((int)(m_transformations.value(l.at(0)).scalex * 100.0 + 0.5));
878 itemrotate->setValue((int)(m_transformations.value(l.at(0)).rotate));
879 value_x->blockSignals(false);
880 value_y->blockSignals(false);
881 value_w->blockSignals(false);
882 value_h->blockSignals(false);
883 itemzoom->blockSignals(false);
884 itemrotate->blockSignals(false);
888 void TitleWidget::slotValueChanged(int type)
890 QList<QGraphicsItem *> l = graphicsView->scene()->selectedItems();
891 if (l.size() > 0 && l.at(0)->type() == IMAGEITEM) {
896 val = value_w->value();
899 val = value_h->value();
903 QGraphicsItem *i = l.at(0);
904 Transform t = m_transformations.value(i);
906 // Ratio width:height
907 double phi = (double) i->boundingRect().width() / i->boundingRect().height();
908 double alpha = (double) t.rotate / 180.0 * M_PI;
918 // Add 0.5 because otherwise incrementing by 1 might have no effect
919 length = val / (cos(alpha) + 1 / phi * sin(alpha)) + 0.5;
920 scale = length / i->boundingRect().width();
923 length = val / (phi * sin(alpha) + cos(alpha)) + 0.5;
924 scale = length / i->boundingRect().height();
931 qtrans.scale(scale, scale);
932 qtrans.rotate(t.rotate);
933 i->setTransform(qtrans);
934 m_transformations[i] = t;
941 /** \brief Updates position/size of the selected item when a value
942 * of an item (coordinates, size) has changed */
943 void TitleWidget::slotAdjustSelectedItem()
945 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
947 if (l.at(0)->type() == RECTITEM) {
949 QGraphicsRectItem *rec = static_cast <QGraphicsRectItem *>(l.at(0));
951 rec->setRect(QRect(0, 0, value_w->value(), value_h->value()));
952 } else if (l.at(0)->type() == TEXTITEM) {
954 updatePosition(l.at(0));
955 } else if (l.at(0)->type() == IMAGEITEM) {
957 updatePosition(l.at(0));
962 /** \brief Updates width/height int the text fields, regarding transformation matrix */
963 void TitleWidget::updateDimension(QGraphicsItem *i)
965 value_w->blockSignals(true);
966 value_h->blockSignals(true);
967 zValue->blockSignals(true);
969 zValue->setValue((int) i->zValue());
970 if (i->type() == IMAGEITEM) {
971 // Get multipliers for rotation/scaling
973 /*Transform t = m_transformations.value(i);
974 QRectF r = i->boundingRect();
975 int width = (int) ( abs(r.width()*t.scalex * cos(t.rotate/180.0*M_PI))
976 + abs(r.height()*t.scaley * sin(t.rotate/180.0*M_PI)) );
977 int height = (int) ( abs(r.height()*t.scaley * cos(t.rotate/180*M_PI))
978 + abs(r.width()*t.scalex * sin(t.rotate/180*M_PI)) );*/
980 value_w->setValue(i->sceneBoundingRect().width());
981 value_h->setValue(i->sceneBoundingRect().height());
982 } else if (i->type() == RECTITEM) {
983 QGraphicsRectItem *r = static_cast <QGraphicsRectItem *>(i);
984 value_w->setValue((int) r->rect().width());
985 value_h->setValue((int) r->rect().height());
986 } else if (i->type() == TEXTITEM) {
987 QGraphicsTextItem *t = static_cast <QGraphicsTextItem *>(i);
988 value_w->setValue((int) t->boundingRect().width());
989 value_h->setValue((int) t->boundingRect().height());
992 zValue->blockSignals(false);
993 value_w->blockSignals(false);
994 value_h->blockSignals(false);
997 /** \brief Updates the coordinates in the text fields from the item */
998 void TitleWidget::updateCoordinates(QGraphicsItem *i)
1000 // Block signals emitted by this method
1001 value_x->blockSignals(true);
1002 value_y->blockSignals(true);
1004 if (i->type() == TEXTITEM) {
1006 QGraphicsTextItem *rec = static_cast <QGraphicsTextItem *>(i);
1008 // Set the correct x coordinate value
1009 if (origin_x_left->isChecked()) {
1010 // Origin (0 point) is at m_frameWidth, coordinate axis is inverted
1011 value_x->setValue((int)(m_frameWidth - rec->pos().x() - rec->boundingRect().width()));
1013 // Origin is at 0 (default)
1014 value_x->setValue((int) rec->pos().x());
1018 if (origin_y_top->isChecked()) {
1019 value_y->setValue((int)(m_frameHeight - rec->pos().y() - rec->boundingRect().height()));
1021 value_y->setValue((int) rec->pos().y());
1024 } else if (i->type() == RECTITEM) {
1026 QGraphicsRectItem *rec = static_cast <QGraphicsRectItem *>(i);
1028 if (origin_x_left->isChecked()) {
1029 // Origin (0 point) is at m_frameWidth
1030 value_x->setValue((int)(m_frameWidth - rec->pos().x() - rec->rect().width()));
1032 // Origin is at 0 (default)
1033 value_x->setValue((int) rec->pos().x());
1036 if (origin_y_top->isChecked()) {
1037 value_y->setValue((int)(m_frameHeight - rec->pos().y() - rec->rect().height()));
1039 value_y->setValue((int) rec->pos().y());
1042 } else if (i->type() == IMAGEITEM) {
1044 if (origin_x_left->isChecked()) {
1045 value_x->setValue((int)(m_frameWidth - i->pos().x() - i->sceneBoundingRect().width()));
1047 value_x->setValue((int) i->pos().x());
1050 if (origin_y_top->isChecked()) {
1051 value_y->setValue((int)(m_frameHeight - i->pos().y() - i->sceneBoundingRect().height()));
1053 value_y->setValue((int) i->pos().y());
1058 // Stop blocking signals now
1059 value_x->blockSignals(false);
1060 value_y->blockSignals(false);
1063 void TitleWidget::updateRotZoom(QGraphicsItem *i)
1065 itemzoom->blockSignals(true);
1066 itemrotate->blockSignals(false);
1068 Transform t = m_transformations.value(i);
1069 itemzoom->setValue((int)(t.scalex * 100.0 + 0.5));
1070 itemrotate->setValue((int)(t.rotate));
1072 itemzoom->blockSignals(false);
1073 itemrotate->blockSignals(false);
1076 /** \brief Updates the position of an item by reading coordinates from the text fields */
1077 void TitleWidget::updatePosition(QGraphicsItem *i)
1079 if (i->type() == TEXTITEM) {
1080 QGraphicsTextItem *rec = static_cast <QGraphicsTextItem *>(i);
1083 if (origin_x_left->isChecked()) {
1084 /* Origin of the x axis is at m_frameWidth,
1085 * and distance from right border of the item to the right
1086 * border of the frame is taken.
1087 * See comment to slotOriginXClicked().
1089 posX = m_frameWidth - value_x->value() - rec->boundingRect().width();
1091 posX = value_x->value();
1095 if (origin_y_top->isChecked()) {
1096 /* Same for y axis */
1097 posY = m_frameHeight - value_y->value() - rec->boundingRect().height();
1099 posY = value_y->value();
1102 rec->setPos(posX, posY);
1104 } else if (i->type() == RECTITEM) {
1106 QGraphicsRectItem *rec = static_cast <QGraphicsRectItem *>(i);
1109 if (origin_x_left->isChecked()) {
1110 posX = m_frameWidth - value_x->value() - rec->rect().width();
1112 posX = value_x->value();
1116 if (origin_y_top->isChecked()) {
1117 posY = m_frameHeight - value_y->value() - rec->rect().height();
1119 posY = value_y->value();
1122 rec->setPos(posX, posY);
1124 } else if (i->type() == IMAGEITEM) {
1126 if (origin_x_left->isChecked()) {
1127 // Use the sceneBoundingRect because this also regards transformations like zoom
1128 posX = m_frameWidth - value_x->value() - i->sceneBoundingRect().width();
1130 posX = value_x->value();
1134 if (origin_y_top->isChecked()) {
1135 posY = m_frameHeight - value_y->value() - i->sceneBoundingRect().height();
1137 posY = value_y->value();
1140 i->setPos(posX, posY);
1146 void TitleWidget::updateTextOriginX()
1148 if (origin_x_left->isChecked()) {
1149 origin_x_left->setText(i18n("\u2212X"));
1151 origin_x_left->setText(i18n("+X"));
1155 void TitleWidget::slotOriginXClicked()
1157 // Update the text displayed on the button.
1158 updateTextOriginX();
1160 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1161 if (l.size() >= 1) {
1162 updateCoordinates(l.at(0));
1164 // Remember x axis setting
1165 l.at(0)->setData(TitleDocument::OriginXLeft, origin_x_left->isChecked() ?
1166 TitleDocument::AxisInverted : TitleDocument::AxisDefault);
1168 graphicsView->setFocus();
1171 void TitleWidget::updateTextOriginY()
1173 if (origin_y_top->isChecked()) {
1174 origin_y_top->setText(i18n("\u2212Y"));
1176 origin_y_top->setText(i18n("+Y"));
1180 void TitleWidget::slotOriginYClicked()
1182 // Update the text displayed on the button.
1183 updateTextOriginY();
1185 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1186 if (l.size() >= 1) {
1187 updateCoordinates(l.at(0));
1189 l.at(0)->setData(TitleDocument::OriginYTop, origin_y_top->isChecked() ?
1190 TitleDocument::AxisInverted : TitleDocument::AxisDefault);
1193 graphicsView->setFocus();
1196 void TitleWidget::updateAxisButtons(QGraphicsItem *i)
1198 int xAxis = i->data(TitleDocument::OriginXLeft).toInt();
1199 int yAxis = i->data(TitleDocument::OriginYTop).toInt();
1200 origin_x_left->blockSignals(true);
1201 origin_y_top->blockSignals(true);
1203 if (xAxis == TitleDocument::AxisInverted) {
1204 origin_x_left->setChecked(true);
1206 origin_x_left->setChecked(false);
1208 updateTextOriginX();
1210 if (yAxis == TitleDocument::AxisInverted) {
1211 origin_y_top->setChecked(true);
1213 origin_y_top->setChecked(false);
1215 updateTextOriginY();
1217 origin_x_left->blockSignals(false);
1218 origin_y_top->blockSignals(false);
1221 void TitleWidget::slotChangeBackground()
1223 QColor color = kcolorbutton->color();
1224 color.setAlpha(horizontalSlider->value());
1225 m_frameBorder->setBrush(QBrush(color));
1229 * Something (yeah) has changed in our QGraphicsScene.
1231 void TitleWidget::slotChanged()
1233 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1234 if (l.size() >= 1 && l.at(0)->type() == TEXTITEM) {
1235 textChanged(static_cast <QGraphicsTextItem *>(l.at(0)));
1240 * If the user has set origin_x_left (everything also for y),
1241 * we need to look whether a text element has been selected. If yes,
1242 * we need to ensure that the right border of the text field
1243 * remains fixed also when some text has been entered.
1245 * This is also known as right-justified, with the difference that
1246 * it is not valid for text but for its boundingRect. Text may still
1247 * be left-justified.
1249 void TitleWidget::textChanged(QGraphicsTextItem *i)
1254 if (origin_x_left->isChecked() || origin_y_top->isChecked()) {
1256 if (!i->toPlainText().isEmpty()) {
1260 * Don't do anything if the string is empty. If the position
1261 * would be updated here, a newly created text field would
1262 * be set to the position of the last selected text field.
1268 void TitleWidget::slotInsertUnicode()
1270 m_unicodeDialog->exec();
1273 void TitleWidget::slotInsertUnicodeString(QString text)
1275 QList<QGraphicsItem *> l = graphicsView->scene()->selectedItems();
1277 if (l.at(0)->type() == TEXTITEM) {
1278 QGraphicsTextItem *t = static_cast <QGraphicsTextItem *>(l.at(0));
1279 t->textCursor().insertText(text);
1284 void TitleWidget::slotUpdateText()
1286 QFont font = font_family->currentFont();
1287 font.setPixelSize(font_size->value());
1288 font.setItalic(buttonItalic->isChecked());
1289 font.setUnderline(buttonUnder->isChecked());
1290 font.setWeight(font_weight_box->itemData(font_weight_box->currentIndex()).toInt());
1291 QColor color = fontColorButton->color();
1292 color.setAlpha(textAlpha->value());
1294 QGraphicsTextItem* item = NULL;
1295 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1296 if (l.size() == 1 && l.at(0)->type() == TEXTITEM) {
1297 item = static_cast <QGraphicsTextItem *>(l.at(0));
1300 //if (item->textCursor().selection ().isEmpty())
1301 QTextCursor cur = item->textCursor();
1302 QTextBlockFormat format = cur.blockFormat();
1303 if (buttonAlignLeft->isChecked() || buttonAlignCenter->isChecked() || buttonAlignRight->isChecked()) {
1304 item->setTextWidth(item->boundingRect().width());
1305 if (buttonAlignCenter->isChecked()) format.setAlignment(Qt::AlignHCenter);
1306 else if (buttonAlignRight->isChecked()) format.setAlignment(Qt::AlignRight);
1307 else if (buttonAlignLeft->isChecked()) format.setAlignment(Qt::AlignLeft);
1309 format.setAlignment(Qt::AlignLeft);
1310 item->setTextWidth(-1);
1314 item->setFont(font);
1315 item->setDefaultTextColor(color);
1316 cur.select(QTextCursor::Document);
1317 cur.setBlockFormat(format);
1318 item->setTextCursor(cur);
1319 cur.clearSelection();
1320 item->setTextCursor(cur);
1325 void TitleWidget::rectChanged()
1327 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1328 if (l.size() == 1 && l.at(0)->type() == RECTITEM && !settingUp) {
1329 QGraphicsRectItem *rec = static_cast<QGraphicsRectItem *>(l.at(0));
1330 QColor f = rectFColor->color();
1331 f.setAlpha(rectFAlpha->value());
1333 penf.setWidth(rectLineWidth->value());
1335 QColor b = rectBColor->color();
1336 b.setAlpha(rectBAlpha->value());
1337 rec->setBrush(QBrush(b));
1341 void TitleWidget::itemScaled(int val)
1343 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1344 if (l.size() == 1) {
1345 Transform x = m_transformations.value(l.at(0));
1346 x.scalex = (double)val / 100.0;
1347 x.scaley = (double)val / 100.0;
1349 qtrans.scale(x.scalex, x.scaley);
1350 qtrans.rotate(x.rotate);
1351 l[0]->setTransform(qtrans);
1352 m_transformations[l.at(0)] = x;
1353 updateDimension(l.at(0));
1357 void TitleWidget::itemRotate(int val)
1359 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1360 if (l.size() == 1) {
1361 Transform x = m_transformations[l.at(0)];
1362 x.rotate = (double)val;
1364 qtrans.scale(x.scalex, x.scaley);
1365 qtrans.rotate(x.rotate);
1366 l[0]->setTransform(qtrans);
1367 m_transformations[l.at(0)] = x;
1368 updateDimension(l.at(0));
1372 void TitleWidget::itemHCenter()
1374 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1375 if (l.size() == 1) {
1376 QGraphicsItem *item = l.at(0);
1377 QRectF br = item->sceneBoundingRect();
1378 int width = (int)br.width();
1379 int newPos = (int)((m_frameWidth - width) / 2);
1380 newPos += item->pos().x() - br.left(); // Check item transformation
1381 item->setPos(newPos, item->pos().y());
1382 updateCoordinates(item);
1386 void TitleWidget::itemVCenter()
1388 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1389 if (l.size() == 1) {
1390 QGraphicsItem *item = l.at(0);
1391 QRectF br = item->sceneBoundingRect();
1392 int height = (int)br.height();
1393 int newPos = (int)((m_frameHeight - height) / 2);
1394 newPos += item->pos().y() - br.top(); // Check item transformation
1395 item->setPos(item->pos().x(), newPos);
1396 updateCoordinates(item);
1400 void TitleWidget::itemTop()
1402 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1403 if (l.size() == 1) {
1404 QGraphicsItem *item = l.at(0);
1405 QRectF br = item->sceneBoundingRect();
1407 if (br.top() > 0) diff = -br.top();
1408 else diff = -br.bottom();
1409 item->moveBy(0, diff);
1410 updateCoordinates(item);
1414 void TitleWidget::itemBottom()
1416 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1417 if (l.size() == 1) {
1418 QGraphicsItem *item = l.at(0);
1419 QRectF br = item->sceneBoundingRect();
1421 if (br.bottom() > m_frameHeight) diff = m_frameHeight - br.top();
1422 else diff = m_frameHeight - br.bottom();
1423 item->moveBy(0, diff);
1424 updateCoordinates(item);
1428 void TitleWidget::itemLeft()
1430 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1431 if (l.size() == 1) {
1432 QGraphicsItem *item = l.at(0);
1433 QRectF br = item->sceneBoundingRect();
1435 if (br.left() > 0) diff = -br.left();
1436 else diff = -br.right();
1437 item->moveBy(diff, 0);
1438 updateCoordinates(item);
1442 void TitleWidget::itemRight()
1444 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1445 if (l.size() == 1) {
1446 QGraphicsItem *item = l.at(0);
1447 QRectF br = item->sceneBoundingRect();
1449 if (br.right() < m_frameWidth) diff = m_frameWidth - br.right();
1450 else diff = m_frameWidth - br.left();
1451 item->moveBy(diff, 0);
1452 updateCoordinates(item);
1456 void TitleWidget::setupViewports()
1458 //double aspect_ratio = 4.0 / 3.0;//read from project
1459 //better zoom centered, but render uses only the created rect, so no problem to change the zoom function
1460 /*QRectF sp(0, 0, startViewportSize->value() * m_frameWidth / 100.0 , startViewportSize->value()* m_frameHeight / 100.0);
1461 QRectF ep(0, 0, endViewportSize->value() * m_frameWidth / 100.0, endViewportSize->value() * m_frameHeight / 100.0);
1462 // use a polygon thiat uses 16:9 and 4:3 rects forpreview the size in all aspect ratios ?
1463 QPolygonF spoly(sp);
1464 QPolygonF epoly(ep);
1465 spoly.translate(startViewportX->value(), startViewportY->value());
1466 epoly.translate(endViewportX->value(), endViewportY->value());
1467 m_startViewport->setPolygon(spoly);
1468 m_endViewport->setPolygon(epoly);
1469 if (! insertingValues) {
1470 m_startViewport->setData(0, startViewportX->value());
1471 m_startViewport->setData(1, startViewportY->value());
1472 m_startViewport->setData(2, startViewportSize->value());
1474 m_endViewport->setData(0, endViewportX->value());
1475 m_endViewport->setData(1, endViewportY->value());
1476 m_endViewport->setData(2, endViewportSize->value());
1480 void TitleWidget::loadTitle(KUrl url)
1482 if (url.isEmpty()) url = KFileDialog::getOpenUrl(KUrl(m_projectTitlePath), "application/x-kdenlivetitle", this, i18n("Load Title"));
1483 if (!url.isEmpty()) {
1484 QList<QGraphicsItem *> items = m_scene->items();
1485 for (int i = 0; i < items.size(); i++) {
1486 if (items.at(i)->zValue() > -1000) delete items.at(i);
1488 m_scene->clearTextSelection();
1492 if (KIO::NetAccess::download(url, tmpfile, 0)) {
1493 QFile file(tmpfile);
1494 if (file.open(QIODevice::ReadOnly)) {
1495 doc.setContent(&file, false);
1498 KIO::NetAccess::removeTempFile(tmpfile);
1503 m_count = m_titledocument.loadDocument(url, m_startViewport, m_endViewport, &out) + 1;
1505 title_duration->setText(m_tc.getTimecode(GenTime(out, m_render->fps())));
1506 insertingValues = true;
1507 startViewportX->setValue(m_startViewport->data(0).toInt());
1508 startViewportY->setValue(m_startViewport->data(1).toInt());
1509 startViewportSize->setValue(m_startViewport->data(2).toInt());
1510 endViewportX->setValue(m_endViewport->data(0).toInt());
1511 endViewportY->setValue(m_endViewport->data(1).toInt());
1512 endViewportSize->setValue(m_endViewport->data(2).toInt());
1514 insertingValues = false;
1520 void TitleWidget::saveTitle(KUrl url)
1522 if (anim_start->isChecked()) slotAnimStart(false);
1523 if (anim_end->isChecked()) slotAnimEnd(false);
1524 if (url.isEmpty()) {
1525 KFileDialog *fs = new KFileDialog(KUrl(m_projectTitlePath), "application/x-kdenlivetitle", this);
1526 fs->setOperationMode(KFileDialog::Saving);
1527 fs->setMode(KFile::File);
1528 #if KDE_IS_VERSION(4,2,0)
1529 fs->setConfirmOverwrite(true);
1531 fs->setKeepLocation(true);
1533 url = fs->selectedUrl();
1536 if (!url.isEmpty()) {
1537 if (m_titledocument.saveDocument(url, m_startViewport, m_endViewport, m_tc.getFrameCount(title_duration->text())) == false)
1538 KMessageBox::error(this, i18n("Cannot write to file %1", url.path()));
1542 QDomDocument TitleWidget::xml()
1544 QDomDocument doc = m_titledocument.xml(m_startViewport, m_endViewport);
1545 doc.documentElement().setAttribute("out", m_tc.getFrameCount(title_duration->text()));
1549 int TitleWidget::duration() const
1551 return m_tc.getFrameCount(title_duration->text());
1554 void TitleWidget::setXml(QDomDocument doc)
1557 m_count = m_titledocument.loadFromXml(doc, m_startViewport, m_endViewport, &out);
1559 title_duration->setText(m_tc.getTimecode(GenTime(out, m_render->fps())));
1560 /*if (doc.documentElement().hasAttribute("out")) {
1561 GenTime duration = GenTime(doc.documentElement().attribute("out").toDouble() / 1000.0);
1562 title_duration->setText(m_tc.getTimecode(duration));
1564 else title_duration->setText(m_tc.getTimecode(GenTime(5000)));*/
1566 QDomElement e = doc.documentElement();
1567 m_transformations.clear();
1568 QList <QGraphicsItem *> items = graphicsView->scene()->items();
1569 const double PI = 4.0 * atan(1.0);
1570 for (int i = 0; i < items.count(); i++) {
1571 QTransform t = items.at(i)->transform();
1575 x.rotate = 180. / PI * atan2(-t.m21(), t.m11());
1576 m_transformations[items.at(i)] = x;
1578 // mbd: Update the GUI color selectors to match the stuff from the loaded document
1579 QColor background_color = m_titledocument.getBackgroundColor();
1580 horizontalSlider->blockSignals(true);
1581 kcolorbutton->blockSignals(true);
1582 horizontalSlider->setValue(background_color.alpha());
1583 background_color.setAlpha(255);
1584 kcolorbutton->setColor(background_color);
1585 horizontalSlider->blockSignals(false);
1586 kcolorbutton->blockSignals(false);
1588 /*startViewportX->setValue(m_startViewport->data(0).toInt());
1589 startViewportY->setValue(m_startViewport->data(1).toInt());
1590 startViewportSize->setValue(m_startViewport->data(2).toInt());
1591 endViewportX->setValue(m_endViewport->data(0).toInt());
1592 endViewportY->setValue(m_endViewport->data(1).toInt());
1593 endViewportSize->setValue(m_endViewport->data(2).toInt());*/
1595 QTimer::singleShot(200, this, SLOT(slotAdjustZoom()));
1599 /** \brief Connected to the accepted signal - calls writeChoices */
1600 void TitleWidget::slotAccepted()
1602 if (anim_start->isChecked()) slotAnimStart(false);
1603 if (anim_end->isChecked()) slotAnimEnd(false);
1607 /** \brief Store the current choices of font, background and rect values */
1608 void TitleWidget::writeChoices()
1610 // Get a pointer to a shared configuration instance, then get the TitleWidget group.
1611 KSharedConfigPtr config = KGlobal::config();
1612 KConfigGroup titleConfig(config, "TitleWidget");
1613 // Write the entries
1614 titleConfig.writeEntry("font_family", font_family->currentFont());
1615 //titleConfig.writeEntry("font_size", font_size->value());
1616 titleConfig.writeEntry("font_pixel_size", font_size->value());
1617 titleConfig.writeEntry("font_color", fontColorButton->color());
1618 titleConfig.writeEntry("font_alpha", textAlpha->value());
1619 titleConfig.writeEntry("font_weight", font_weight_box->itemData(font_weight_box->currentIndex()).toInt());
1620 titleConfig.writeEntry("font_italic", buttonItalic->isChecked());
1621 titleConfig.writeEntry("font_underlined", buttonUnder->isChecked());
1623 titleConfig.writeEntry("rect_foreground_color", rectFColor->color());
1624 titleConfig.writeEntry("rect_foreground_alpha", rectFAlpha->value());
1625 titleConfig.writeEntry("rect_background_color", rectBColor->color());
1626 titleConfig.writeEntry("rect_background_alpha", rectBAlpha->value());
1627 titleConfig.writeEntry("rect_line_width", rectLineWidth->value());
1629 titleConfig.writeEntry("background_color", kcolorbutton->color());
1630 titleConfig.writeEntry("background_alpha", horizontalSlider->value());
1632 //! \todo Not sure if I should sync - it is probably safe to do it
1637 /** \brief Read the last stored choices into the dialog */
1638 void TitleWidget::readChoices()
1640 // Get a pointer to a shared configuration instance, then get the TitleWidget group.
1641 KSharedConfigPtr config = KGlobal::config();
1642 KConfigGroup titleConfig(config, "TitleWidget");
1644 font_family->setCurrentFont(titleConfig.readEntry("font_family", font_family->currentFont()));
1645 font_size->setValue(titleConfig.readEntry("font_pixel_size", font_size->value()));
1646 fontColorButton->setColor(titleConfig.readEntry("font_color", fontColorButton->color()));
1647 textAlpha->setValue(titleConfig.readEntry("font_alpha", textAlpha->value()));
1649 if (titleConfig.readEntry("font_bold", false)) weight = QFont::Bold;
1650 else weight = titleConfig.readEntry("font_weight", font_weight_box->itemData(font_weight_box->currentIndex()).toInt());
1651 setFontBoxWeight(weight);
1652 buttonItalic->setChecked(titleConfig.readEntry("font_italic", buttonItalic->isChecked()));
1653 buttonUnder->setChecked(titleConfig.readEntry("font_underlined", buttonUnder->isChecked()));
1655 rectFColor->setColor(titleConfig.readEntry("rect_foreground_color", rectFColor->color()));
1656 rectFAlpha->setValue(titleConfig.readEntry("rect_foreground_alpha", rectFAlpha->value()));
1657 rectBColor->setColor(titleConfig.readEntry("rect_background_color", rectBColor->color()));
1658 rectBAlpha->setValue(titleConfig.readEntry("rect_background_alpha", rectBAlpha->value()));
1659 rectLineWidth->setValue(titleConfig.readEntry("rect_line_width", rectLineWidth->value()));
1661 kcolorbutton->setColor(titleConfig.readEntry("background_color", kcolorbutton->color()));
1662 horizontalSlider->setValue(titleConfig.readEntry("background_alpha", horizontalSlider->value()));
1665 void TitleWidget::adjustFrameSize()
1667 m_frameWidth = m_titledocument.frameWidth();
1668 m_frameHeight = m_titledocument.frameHeight();
1669 m_frameBorder->setRect(0, 0, m_frameWidth, m_frameHeight);
1670 displayBackgroundFrame();
1673 void TitleWidget::slotAnimStart(bool anim)
1675 if (anim && anim_end->isChecked()) {
1676 anim_end->setChecked(false);
1677 m_endViewport->setZValue(-1000);
1678 m_endViewport->setBrush(QBrush());
1681 QList<QGraphicsItem *> list = m_scene->items();
1682 for (int i = 0; i < list.count(); i++) {
1683 if (list.at(i)->zValue() > -1000) {
1684 list.at(i)->setFlag(QGraphicsItem::ItemIsMovable, !anim);
1685 list.at(i)->setFlag(QGraphicsItem::ItemIsSelectable, !anim);
1688 align_box->setEnabled(anim);
1689 itemzoom->setEnabled(!anim);
1690 itemrotate->setEnabled(!anim);
1691 frame_toolbar->setEnabled(!anim);
1692 toolbar_stack->setEnabled(!anim);
1694 keep_aspect->setChecked(!m_startViewport->data(0).isNull());
1695 m_startViewport->setZValue(1100);
1696 QColor col = m_startViewport->pen().color();
1698 m_startViewport->setBrush(col);
1699 m_startViewport->setFlags(QGraphicsItem::ItemIsMovable | QGraphicsItem::ItemIsSelectable);
1700 m_startViewport->setSelected(true);
1703 if (m_startViewport->childItems().isEmpty()) addAnimInfoText();
1705 m_startViewport->setZValue(-1000);
1706 m_startViewport->setBrush(QBrush());
1707 m_startViewport->setFlags(0);
1708 if (!anim_end->isChecked()) deleteAnimInfoText();
1713 void TitleWidget::slotAnimEnd(bool anim)
1715 if (anim && anim_start->isChecked()) {
1716 anim_start->setChecked(false);
1717 m_startViewport->setZValue(-1000);
1718 m_startViewport->setBrush(QBrush());
1721 QList<QGraphicsItem *> list = m_scene->items();
1722 for (int i = 0; i < list.count(); i++) {
1723 if (list.at(i)->zValue() > -1000) {
1724 list.at(i)->setFlag(QGraphicsItem::ItemIsMovable, !anim);
1725 list.at(i)->setFlag(QGraphicsItem::ItemIsSelectable, !anim);
1728 align_box->setEnabled(anim);
1729 itemzoom->setEnabled(!anim);
1730 itemrotate->setEnabled(!anim);
1731 frame_toolbar->setEnabled(!anim);
1732 toolbar_stack->setEnabled(!anim);
1734 keep_aspect->setChecked(!m_endViewport->data(0).isNull());
1735 m_endViewport->setZValue(1100);
1736 QColor col = m_endViewport->pen().color();
1738 m_endViewport->setBrush(col);
1739 m_endViewport->setFlags(QGraphicsItem::ItemIsMovable | QGraphicsItem::ItemIsSelectable);
1740 m_endViewport->setSelected(true);
1743 if (m_endViewport->childItems().isEmpty()) addAnimInfoText();
1745 m_endViewport->setZValue(-1000);
1746 m_endViewport->setBrush(QBrush());
1747 m_endViewport->setFlags(0);
1748 if (!anim_start->isChecked()) deleteAnimInfoText();
1752 void TitleWidget::addAnimInfoText()
1754 // add text to anim viewport
1755 QGraphicsTextItem *t = new QGraphicsTextItem(i18n("Start"), m_startViewport);
1756 QGraphicsTextItem *t2 = new QGraphicsTextItem(i18n("End"), m_endViewport);
1757 QFont font = t->font();
1758 font.setPixelSize(m_startViewport->rect().width() / 10);
1759 QColor col = m_startViewport->pen().color();
1761 t->setDefaultTextColor(col);
1763 font.setPixelSize(m_endViewport->rect().width() / 10);
1764 col = m_endViewport->pen().color();
1766 t2->setDefaultTextColor(col);
1770 void TitleWidget::updateInfoText()
1772 // update info text font
1773 if (!m_startViewport->childItems().isEmpty()) {
1774 QGraphicsTextItem *item = static_cast <QGraphicsTextItem *>(m_startViewport->childItems().at(0));
1776 QFont font = item->font();
1777 font.setPixelSize(m_startViewport->rect().width() / 10);
1778 item->setFont(font);
1781 if (!m_endViewport->childItems().isEmpty()) {
1782 QGraphicsTextItem *item = static_cast <QGraphicsTextItem *>(m_endViewport->childItems().at(0));
1784 QFont font = item->font();
1785 font.setPixelSize(m_endViewport->rect().width() / 10);
1786 item->setFont(font);
1791 void TitleWidget::deleteAnimInfoText()
1793 // end animation editing, remove info text
1794 while (!m_startViewport->childItems().isEmpty()) {
1795 QGraphicsItem *item = m_startViewport->childItems().at(0);
1796 m_scene->removeItem(item);
1799 while (!m_endViewport->childItems().isEmpty()) {
1800 QGraphicsItem *item = m_endViewport->childItems().at(0);
1801 m_scene->removeItem(item);
1807 void TitleWidget::slotKeepAspect(bool keep)
1809 if (m_endViewport->zValue() == 1100) {
1810 m_endViewport->setData(0, keep == true ? m_frameWidth : QVariant());
1811 m_endViewport->setData(1, keep == true ? m_frameHeight : QVariant());
1813 m_startViewport->setData(0, keep == true ? m_frameWidth : QVariant());
1814 m_startViewport->setData(1, keep == true ? m_frameHeight : QVariant());
1818 void TitleWidget::slotResize50()
1820 if (m_endViewport->zValue() == 1100) {
1821 m_endViewport->setRect(0, 0, m_frameWidth / 2, m_frameHeight / 2);
1822 } else m_startViewport->setRect(0, 0, m_frameWidth / 2, m_frameHeight / 2);
1825 void TitleWidget::slotResize100()
1827 if (m_endViewport->zValue() == 1100) {
1828 m_endViewport->setRect(0, 0, m_frameWidth, m_frameHeight);
1829 } else m_startViewport->setRect(0, 0, m_frameWidth, m_frameHeight);
1832 void TitleWidget::slotResize200()
1834 if (m_endViewport->zValue() == 1100) {
1835 m_endViewport->setRect(0, 0, m_frameWidth * 2, m_frameHeight * 2);
1836 } else m_startViewport->setRect(0, 0, m_frameWidth * 2, m_frameHeight * 2);
1839 void TitleWidget::slotAddEffect(int ix)
1841 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1842 int effect = effect_list->itemData(ix).toInt();
1843 if (effect == NOEFFECT) {
1844 if (l.size() == 1) l[0]->setData(100, QVariant());
1845 effect_stack->setHidden(true);
1848 effect_stack->setCurrentIndex(effect - 1);
1849 effect_stack->setHidden(false);
1850 if (effect == TYPEWRITEREFFECT) {
1851 if (l.size() == 1 && l.at(0)->type() == TEXTITEM) {
1852 QStringList effdata = QStringList() << "typewriter" << QString::number(typewriter_delay->value()) + ";" + QString::number(typewriter_start->value());
1853 l[0]->setData(100, effdata);
1856 #if QT_VERSION < 0x040600
1859 if (effect == BLUREFFECT) {
1861 if (l.size() == 1) {
1862 QGraphicsEffect *eff = new QGraphicsBlurEffect();
1863 l[0]->setGraphicsEffect(eff);
1865 } else if (effect == SHADOWEFFECT) {
1866 if (l.size() == 1) {
1867 QGraphicsEffect *eff = new QGraphicsDropShadowEffect();
1868 l[0]->setGraphicsEffect(eff);
1876 void TitleWidget::slotFontText(const QString& s)
1879 if (f.exactMatch()) {
1880 // Font really exists (could also just be a «d» if the user
1881 // starts typing «dejavu» for example).
1882 font_family->setCurrentFont(f);
1884 // Note: Typing dejavu serif does not recognize the font (takes sans)
1885 // in older Qt versions.
1888 void TitleWidget::slotEditTypewriter(int ix)
1890 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1891 if (l.size() == 1) {
1892 QStringList effdata = QStringList() << "typewriter" << QString::number(typewriter_delay->value()) + ";" + QString::number(typewriter_start->value());
1893 l[0]->setData(100, effdata);
1897 void TitleWidget::slotEditBlur(int ix)
1899 #if QT_VERSION < 0x040600
1902 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1903 if (l.size() == 1) {
1904 QGraphicsEffect *eff = l[0]->graphicsEffect();
1905 QGraphicsBlurEffect *blur = static_cast <QGraphicsBlurEffect *>(eff);
1906 if (blur) blur->setBlurRadius(ix);
1911 void TitleWidget::slotEditShadow()
1913 #if QT_VERSION < 0x040600
1916 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1917 if (l.size() == 1) {
1918 QGraphicsEffect *eff = l[0]->graphicsEffect();
1919 QGraphicsDropShadowEffect *shadow = static_cast <QGraphicsDropShadowEffect *>(eff);
1921 shadow->setBlurRadius(shadow_radius->value());
1922 shadow->setOffset(shadow_x->value(), shadow_y->value());
1928 qreal TitleWidget::zIndexBounds(bool maxBound)
1930 qreal bound = maxBound ? -99 : 99;
1931 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1933 QList<QGraphicsItem*> lItems = graphicsView->scene()->items(l[0]->sceneBoundingRect(), Qt::IntersectsItemShape);
1934 if (lItems.size() > 0) {
1935 int n = lItems.size();
1938 for (int i = 0; i < n; i++) {
1939 z = lItems[i]->zValue();
1940 if (z > bound && !lItems[i]->isSelected()) {
1945 // Get minimum z index.
1946 for (int i = 0; i < n; i++) {
1947 z = lItems[i]->zValue();
1948 if (z < bound && !lItems[i]->isSelected() && z > -999) {
1949 // There are items at the very bottom (background e.g.) with z-index < -1000.
1959 void TitleWidget::slotZIndexUp()
1961 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1962 if (l.size() >= 1) {
1963 qreal currentZ = l[0]->zValue();
1964 qreal max = zIndexBounds(true);
1965 if (currentZ <= max) {
1966 l[0]->setZValue(currentZ + 1);
1967 updateDimension(l[0]);
1972 void TitleWidget::slotZIndexTop()
1974 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1975 if (l.size() >= 1) {
1976 qreal currentZ = l[0]->zValue();
1977 qreal max = zIndexBounds(true);
1978 if (currentZ <= max) {
1979 l[0]->setZValue(max + 1);
1980 updateDimension(l[0]);
1985 void TitleWidget::slotZIndexDown()
1987 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
1988 if (l.size() >= 1) {
1989 qreal currentZ = l[0]->zValue();
1990 qreal min = zIndexBounds(false);
1991 if (currentZ >= min) {
1992 l[0]->setZValue(currentZ - 1);
1993 updateDimension(l[0]);
1998 void TitleWidget::slotZIndexBottom()
2000 QList<QGraphicsItem*> l = graphicsView->scene()->selectedItems();
2001 if (l.size() >= 1) {
2002 qreal currentZ = l[0]->zValue();
2003 qreal min = zIndexBounds(false);
2004 if (currentZ >= min) {
2005 l[0]->setZValue(min - 1);
2006 updateDimension(l[0]);