]> cloud.milkyroute.net Git - dolphin.git/blob - src/panels/information/metadatawidget.cpp
SVN_SILENT made messages (.desktop file)
[dolphin.git] / src / panels / information / metadatawidget.cpp
1 /***************************************************************************
2 * Copyright (C) 2007 by Sebastian Trueg <trueg@kde.org> *
3 * *
4 * This program is free software; you can redistribute it and/or modify *
5 * it under the terms of the GNU General Public License as published by *
6 * the Free Software Foundation; either version 2 of the License, or *
7 * (at your option) any later version. *
8 * *
9 * This program is distributed in the hope that it will be useful, *
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
12 * GNU General Public License for more details. *
13 * *
14 * You should have received a copy of the GNU General Public License *
15 * along with this program; if not, write to the *
16 * Free Software Foundation, Inc., *
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA *
18 ***************************************************************************/
19
20 #include "metadatawidget.h"
21
22 #include "commentwidget.h"
23
24 #include <config-nepomuk.h>
25
26 #include <klocale.h>
27 #include <KDebug>
28 #include <KMessageBox>
29
30 #include <QtCore/QEvent>
31 #include <QtCore/QMutex>
32 #include <QtCore/QMutexLocker>
33 #include <QtCore/QThread>
34 #include <QtGui/QLabel>
35 #include <QtGui/QGridLayout>
36 #include <QtGui/QTextEdit>
37
38 #ifdef HAVE_NEPOMUK
39 #include "nepomukmassupdatejob.h"
40 #include <nepomuk/kmetadatatagwidget.h>
41 #include <nepomuk/resourcemanager.h>
42 #include <nepomuk/resource.h>
43 #include <nepomuk/variant.h>
44 #include <nepomuk/kratingwidget.h>
45 #include <Soprano/Vocabulary/Xesam>
46 #include "resourcetaggingwidget.h"
47 #endif
48
49
50 bool MetaDataWidget::metaDataAvailable()
51 {
52 #ifdef HAVE_NEPOMUK
53 return !Nepomuk::ResourceManager::instance()->init();
54 #else
55 return false;
56 #endif
57 }
58
59
60 class MetaDataWidget::Private
61 {
62 public:
63 #ifdef HAVE_NEPOMUK
64 void loadComment(const QString& comment);
65
66 CommentWidget* editComment;
67 KRatingWidget* ratingWidget;
68 Nepomuk::ResourceTaggingWidget* tagWidget;
69
70 // shared data between the GUI-thread and
71 // the loader-thread (see LoadFilesThread):
72 QMutex mutex;
73 struct SharedData
74 {
75 int rating;
76 QString comment;
77 QList<Nepomuk::Resource> fileRes;
78 QMap<KUrl, Nepomuk::Resource> files;
79 } sharedData;
80
81 /**
82 * Loads the meta data of files and writes
83 * the result into a shared data pool that
84 * can be used by the widgets in the GUI thread.
85 */
86 class LoadFilesThread : public QThread
87 {
88 public:
89 LoadFilesThread(SharedData* sharedData, QMutex* mutex);
90 ~LoadFilesThread();
91 void loadFiles(const KUrl::List& urls);
92 virtual void run();
93
94 private:
95 SharedData* m_sharedData;
96 QMutex* m_mutex;
97 KUrl::List m_urls;
98 bool m_canceled;
99 };
100
101 LoadFilesThread* loadFilesThread;
102 #endif
103 };
104
105 #ifdef HAVE_NEPOMUK
106 void MetaDataWidget::Private::loadComment(const QString& comment)
107 {
108 editComment->setComment( comment );
109 }
110
111 MetaDataWidget::Private::LoadFilesThread::LoadFilesThread(
112 MetaDataWidget::Private::SharedData* sharedData,
113 QMutex* mutex) :
114 m_sharedData(sharedData),
115 m_mutex(mutex),
116 m_urls()
117 {
118 }
119
120 MetaDataWidget::Private::LoadFilesThread::~LoadFilesThread()
121 {
122 // this thread may very well be deleted during execution. We need
123 // to protect it from crashes here
124 m_canceled = true;
125 wait();
126 }
127
128 void MetaDataWidget::Private::LoadFilesThread::loadFiles(const KUrl::List& urls)
129 {
130 QMutexLocker locker( m_mutex );
131 m_urls = urls;
132 m_canceled = false;
133 start();
134 }
135
136 void MetaDataWidget::Private::LoadFilesThread::run()
137 {
138 QMutexLocker locker( m_mutex );
139 const KUrl::List urls = m_urls;
140 locker.unlock();
141
142 bool first = true;
143 QList<Nepomuk::Resource> fileRes;
144 QMap<KUrl, Nepomuk::Resource> files;
145 unsigned int rating = 0;
146 QString comment;
147 Q_FOREACH( const KUrl &url, urls ) {
148 if ( m_canceled )
149 return;
150 Nepomuk::Resource file( url, Soprano::Vocabulary::Xesam::File() );
151 files.insert( url, file );
152 fileRes.append( file );
153
154 if ( !first && rating != file.rating() ) {
155 rating = 0; // reset rating
156 }
157 else if ( first ) {
158 rating = file.rating();
159 }
160
161 if ( !first && comment != file.description() ) {
162 comment.clear();
163 }
164 else if ( first ) {
165 comment = file.description();
166 }
167 first = false;
168 }
169
170 locker.relock();
171 m_sharedData->rating = rating;
172 m_sharedData->comment = comment;
173 m_sharedData->fileRes = fileRes;
174 m_sharedData->files = files;
175 }
176 #endif
177
178 MetaDataWidget::MetaDataWidget(QWidget* parent) :
179 QWidget(parent)
180 {
181 #ifdef HAVE_NEPOMUK
182 d = new Private;
183 d->editComment = new CommentWidget(this);
184 d->editComment->setFocusPolicy(Qt::ClickFocus);
185 d->ratingWidget = new KRatingWidget(this);
186 d->ratingWidget->setAlignment( Qt::AlignCenter );
187 d->tagWidget = new Nepomuk::ResourceTaggingWidget(this);
188 connect(d->ratingWidget, SIGNAL(ratingChanged(unsigned int)), this, SLOT(slotRatingChanged(unsigned int)));
189 connect(d->editComment, SIGNAL(commentChanged(const QString&)), this, SLOT(slotCommentChanged(const QString&)));
190 connect( d->tagWidget, SIGNAL( tagClicked( const Nepomuk::Tag& ) ), this, SLOT( slotTagClicked( const Nepomuk::Tag& ) ) );
191
192 d->sharedData.rating = 0;
193 d->loadFilesThread = new Private::LoadFilesThread(&d->sharedData, &d->mutex);
194 connect(d->loadFilesThread, SIGNAL(finished()), this, SLOT(slotLoadingFinished()));
195
196 QVBoxLayout* lay = new QVBoxLayout(this);
197 lay->setMargin(0);
198 lay->addWidget(d->ratingWidget);
199 lay->addWidget(d->editComment);
200 lay->addWidget( d->tagWidget );
201 #else
202 d = 0;
203 #endif
204 }
205
206
207 MetaDataWidget::~MetaDataWidget()
208 {
209 #ifdef HAVE_NEPOMUK
210 delete d->loadFilesThread;
211 #endif
212 delete d;
213 }
214
215 void MetaDataWidget::setRatingVisible(bool visible)
216 {
217 #ifdef HAVE_NEPOMUK
218 d->ratingWidget->setVisible(visible);
219 #else
220 Q_UNUSED(visible);
221 #endif
222 }
223
224
225 bool MetaDataWidget::isRatingVisible() const
226 {
227 #ifdef HAVE_NEPOMUK
228 return d->ratingWidget->isVisible();
229 #else
230 return false;
231 #endif
232 }
233
234
235 void MetaDataWidget::setCommentVisible(bool visible)
236 {
237 #ifdef HAVE_NEPOMUK
238 d->editComment->setVisible(visible);
239 #else
240 Q_UNUSED(visible);
241 #endif
242 }
243
244
245 bool MetaDataWidget::isCommentVisible() const
246 {
247 #ifdef HAVE_NEPOMUK
248 return d->editComment->isVisible();
249 #else
250 return false;
251 #endif
252 }
253
254
255 void MetaDataWidget::setTagsVisible(bool visible)
256 {
257 #ifdef HAVE_NEPOMUK
258 d->tagWidget->setVisible(visible);
259 #else
260 Q_UNUSED(visible);
261 #endif
262 }
263
264
265 bool MetaDataWidget::areTagsVisible() const
266 {
267 #ifdef HAVE_NEPOMUK
268 return d->tagWidget->isVisible();
269 #else
270 return false;
271 #endif
272 }
273
274
275 void MetaDataWidget::setFile(const KUrl& url)
276 {
277 kDebug() << url;
278 KUrl::List urls;
279 urls.append( url );
280 setFiles( urls );
281 }
282
283 void MetaDataWidget::setFiles(const KUrl::List& urls)
284 {
285 #ifdef HAVE_NEPOMUK
286 d->loadFilesThread->loadFiles( urls );
287 #else
288 Q_UNUSED( urls );
289 #endif
290 }
291
292
293 void MetaDataWidget::slotCommentChanged( const QString& s )
294 {
295 #ifdef HAVE_NEPOMUK
296 QMutexLocker locker( &d->mutex );
297 Nepomuk::MassUpdateJob* job = Nepomuk::MassUpdateJob::commentResources( d->sharedData.files.values(), s );
298 connect( job, SIGNAL( result( KJob* ) ),
299 this, SLOT( metadataUpdateDone() ) );
300 setEnabled( false ); // no updates during execution
301 job->start();
302 #else
303 Q_UNUSED( s );
304 #endif
305 }
306
307
308 void MetaDataWidget::slotRatingChanged(unsigned int rating)
309 {
310 #ifdef HAVE_NEPOMUK
311 QMutexLocker locker( &d->mutex );
312 Nepomuk::MassUpdateJob* job = Nepomuk::MassUpdateJob::rateResources( d->sharedData.files.values(), rating );
313 connect( job, SIGNAL( result( KJob* ) ),
314 this, SLOT( metadataUpdateDone() ) );
315 setEnabled( false ); // no updates during execution
316 job->start();
317 #else
318 Q_UNUSED( rating );
319 #endif
320 }
321
322
323 void MetaDataWidget::metadataUpdateDone()
324 {
325 setEnabled( true );
326 }
327
328
329 bool MetaDataWidget::eventFilter(QObject* obj, QEvent* event)
330 {
331 return QWidget::eventFilter(obj, event);
332 }
333
334
335 void MetaDataWidget::slotTagClicked( const Nepomuk::Tag& tag )
336 {
337 Q_UNUSED( tag );
338 #ifdef HAVE_NEPOMUK
339 d->tagWidget->showTagPopup( QCursor::pos() );
340 #endif
341 }
342
343 void MetaDataWidget::slotLoadingFinished()
344 {
345 #ifdef HAVE_NEPOMUK
346 QMutexLocker locker( &d->mutex );
347 d->ratingWidget->setRating( d->sharedData.rating );
348 d->loadComment( d->sharedData.comment );
349 d->tagWidget->setResources( d->sharedData.fileRes );
350 #endif
351 }
352
353 #include "metadatawidget.moc"