~ubuntu-branches/ubuntu/intrepid/kid3/intrepid

« back to all changes in this revision

Viewing changes to kid3/framelist.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Michele Angrisano
  • Date: 2008-01-09 23:20:54 UTC
  • mfrom: (1.1.6 upstream)
  • Revision ID: james.westby@ubuntu.com-20080109232054-gtcjxz4ahdnzbt01
Tags: 0.10-1ubuntu1
* Merge from Debian unstable, remaining changes:
  - debian/rules:
    + Use dh_icons instead dh_iconcache.
  - debian/control:
    + Update maintainer field.

Show diffs side-by-side

added added

removed removed

Lines of Context:
5
5
 * \b Project: Kid3
6
6
 * \author Urs Fleisch
7
7
 * \date 9 Jan 2003
 
8
 *
 
9
 * Copyright (C) 2003-2007  Urs Fleisch
 
10
 *
 
11
 * This file is part of Kid3.
 
12
 *
 
13
 * Kid3 is free software; you can redistribute it and/or modify
 
14
 * it under the terms of the GNU General Public License as published by
 
15
 * the Free Software Foundation; either version 2 of the License, or
 
16
 * (at your option) any later version.
 
17
 *
 
18
 * Kid3 is distributed in the hope that it will be useful,
 
19
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 
20
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
21
 * GNU General Public License for more details.
 
22
 *
 
23
 * You should have received a copy of the GNU General Public License
 
24
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
8
25
 */
9
26
 
10
27
#include <qimage.h>
11
28
#include <qpainter.h>
12
29
#include <qcombobox.h>
 
30
#include <qtextedit.h>
 
31
#include <qlineedit.h>
 
32
#include <qspinbox.h>
 
33
#include <qdialog.h>
 
34
#include <qpushbutton.h>
 
35
#include <qfile.h>
 
36
#include <qinputdialog.h>
13
37
#if QT_VERSION >= 0x040000
14
 
#include <Q3ListBox>
 
38
#include <QListWidget>
15
39
#include <QVBoxLayout>
16
40
#include <QLabel>
17
41
#include <QPaintEvent>
 
42
#include <QTextCursor>
18
43
#else
19
44
#include <qlistbox.h>
 
45
#include <qlayout.h>
 
46
#include <qptrlist.h>
20
47
#endif
21
48
 
22
49
#include "taggedfile.h"
23
50
#include "framelist.h"
 
51
#include "frametable.h"
 
52
#include "kid3.h"
 
53
#ifdef CONFIG_USE_KDE
 
54
#include <kfiledialog.h>
 
55
#else
 
56
#include <qfiledialog.h>
 
57
#endif
 
58
 
 
59
 
 
60
/** QTextEdit with label above */
 
61
class LabeledTextEdit : public QWidget {
 
62
public:
 
63
        /**
 
64
         * Constructor.
 
65
         *
 
66
         * @param parent parent widget
 
67
         */
 
68
        LabeledTextEdit(QWidget* parent);
 
69
 
 
70
        /**
 
71
         * Get text.
 
72
         *
 
73
         * @return text.
 
74
         */
 
75
        QString text() const {
 
76
                return m_edit->QCM_toPlainText();
 
77
        }
 
78
 
 
79
        /**
 
80
         * Set text.
 
81
         *
 
82
         * @param txt text
 
83
         */
 
84
        void setText(const QString& txt) {
 
85
                m_edit->QCM_setPlainText(txt);
 
86
        }
 
87
 
 
88
        /**
 
89
         * Set label.
 
90
         *
 
91
         * @param txt label
 
92
         */
 
93
        void setLabel(const QString& txt) { m_label->setText(txt); }
 
94
 
 
95
private:
 
96
        /** Label above edit */
 
97
        QLabel* m_label;
 
98
        /** Text editor */
 
99
        QTextEdit* m_edit;
 
100
};
 
101
 
 
102
 
 
103
/** LineEdit with label above */
 
104
class LabeledLineEdit : public QWidget {
 
105
public:
 
106
        /**
 
107
         * Constructor.
 
108
         *
 
109
         * @param parent parent widget
 
110
         */
 
111
        LabeledLineEdit(QWidget* parent);
 
112
 
 
113
        /**
 
114
         * Get text.
 
115
         *
 
116
         * @return text.
 
117
         */
 
118
        QString text() const { return m_edit->text(); }
 
119
 
 
120
        /**
 
121
         * Set text.
 
122
         *
 
123
         * @param txt text
 
124
         */
 
125
        void setText(const QString& txt) { m_edit->setText(txt); }
 
126
 
 
127
        /**
 
128
         * Set label.
 
129
         *
 
130
         * @param txt label
 
131
         */
 
132
        void setLabel(const QString& txt) { m_label->setText(txt); }
 
133
 
 
134
private:
 
135
        /** Label above edit */
 
136
        QLabel* m_label;
 
137
        /** Line editor */
 
138
        QLineEdit* m_edit;
 
139
};
 
140
 
 
141
 
 
142
/** Combo box with label above */
 
143
class LabeledComboBox : public QWidget {
 
144
public:
 
145
        /**
 
146
         * Constructor.
 
147
         *
 
148
         * @param parent parent widget
 
149
         * @param strlst list with ComboBox items, terminated by NULL
 
150
         */
 
151
        LabeledComboBox(QWidget* parent, const char** strlst);
 
152
 
 
153
        /**
 
154
         * Get index of selected item.
 
155
         *
 
156
         * @return index.
 
157
         */
 
158
        int currentItem() const {
 
159
                return m_combo->QCM_currentIndex();
 
160
        }
 
161
 
 
162
        /**
 
163
         * Set index of selected item.
 
164
         *
 
165
         * @param idx index
 
166
         */
 
167
        void setCurrentItem(int idx) {
 
168
                m_combo->QCM_setCurrentIndex(idx);
 
169
        }
 
170
 
 
171
        /**
 
172
         * Set label.
 
173
         *
 
174
         * @param txt label
 
175
         */
 
176
        void setLabel(const QString& txt) { m_label->setText(txt); }
 
177
 
 
178
private:
 
179
        /** Label above combo box */
 
180
        QLabel* m_label;
 
181
        /** Combo box */
 
182
        QComboBox* m_combo;
 
183
};
 
184
 
 
185
 
 
186
/** QSpinBox with label above */
 
187
class LabeledSpinBox : public QWidget {
 
188
public:
 
189
        /**
 
190
         * Constructor.
 
191
         *
 
192
         * @param parent parent widget
 
193
         */
 
194
        LabeledSpinBox(QWidget* parent);
 
195
 
 
196
        /**
 
197
         * Get value.
 
198
         *
 
199
         * @return text.
 
200
         */
 
201
        int value() const { return m_spinbox->value(); }
 
202
 
 
203
        /**
 
204
         * Set value.
 
205
         *
 
206
         * @param value value
 
207
         */
 
208
        void setValue(int value) { m_spinbox->setValue(value); }
 
209
 
 
210
        /**
 
211
         * Set label.
 
212
         *
 
213
         * @param txt label
 
214
         */
 
215
        void setLabel(const QString& txt) { m_label->setText(txt); }
 
216
 
 
217
private:
 
218
        /** Label above edit */
 
219
        QLabel* m_label;
 
220
        /** Text editor */
 
221
        QSpinBox* m_spinbox;
 
222
};
 
223
 
 
224
 
 
225
/** Window to view image */
 
226
class ImageViewer : public QDialog {
 
227
public:
 
228
        /**
 
229
         * Constructor.
 
230
         *
 
231
         * @param parent parent widget
 
232
         * @param img    image to display in window
 
233
         */
 
234
        ImageViewer(QWidget* parent, QImage* img);
 
235
 
 
236
protected:
 
237
        /**
 
238
         * Paint image, called when window has to be drawn.
 
239
         */
 
240
        void paintEvent(QPaintEvent*);
 
241
 
 
242
private:
 
243
        /** image to view */
 
244
        QImage* m_image; 
 
245
};
24
246
 
25
247
 
26
248
/**
27
249
 * Constructor.
28
250
 *
29
251
 * @param parent parent widget
30
 
 * @param name   internal name or 0
31
252
 */
32
 
LabeledTextEdit::LabeledTextEdit(QWidget* parent, const char* name) :
33
 
    QWidget(parent, name)
 
253
LabeledTextEdit::LabeledTextEdit(QWidget* parent) :
 
254
    QWidget(parent)
34
255
{
35
 
        m_layout = new QVBoxLayout(this);
 
256
        QVBoxLayout* layout = new QVBoxLayout(this);
36
257
        m_label = new QLabel(this);
37
258
        m_edit = new QTextEdit(this);
38
 
        if (m_layout && m_label && m_edit) {
39
 
                m_edit->setTextFormat(Qt::PlainText);
40
 
                m_layout->addWidget(m_label);
41
 
                m_layout->addWidget(m_edit);
 
259
        if (layout && m_label && m_edit) {
 
260
                layout->setMargin(0);
 
261
                layout->setSpacing(2);
 
262
                m_edit->QCM_setTextFormat_PlainText();
 
263
                layout->addWidget(m_label);
 
264
                layout->addWidget(m_edit);
42
265
        }
43
266
}
44
267
 
46
269
 * Constructor.
47
270
 *
48
271
 * @param parent parent widget
49
 
 * @param name   internal name or 0
50
272
 */
51
 
LabeledLineEdit::LabeledLineEdit(QWidget* parent, const char* name) :
52
 
    QWidget(parent, name)
 
273
LabeledLineEdit::LabeledLineEdit(QWidget* parent) :
 
274
    QWidget(parent)
53
275
{
54
 
        m_layout = new QVBoxLayout(this);
 
276
        QVBoxLayout* layout = new QVBoxLayout(this);
55
277
        m_label = new QLabel(this);
56
278
        m_edit = new QLineEdit(this);
57
 
        if (m_layout && m_label && m_edit) {
58
 
                m_layout->addWidget(m_label);
59
 
                m_layout->addWidget(m_edit);
 
279
        if (layout && m_label && m_edit) {
 
280
                layout->setMargin(0);
 
281
                layout->setSpacing(2);
 
282
                layout->addWidget(m_label);
 
283
                layout->addWidget(m_edit);
60
284
        }
61
285
}
62
286
 
64
288
 * Constructor.
65
289
 *
66
290
 * @param parent parent widget
67
 
 * @param name   internal name or 0
68
291
 * @param strlst list with ComboBox items, terminated by NULL
69
292
 */
70
 
LabeledComboBox::LabeledComboBox(QWidget* parent, const char* name,
71
 
                                 const char **strlst) : QWidget(parent, name)
 
293
LabeledComboBox::LabeledComboBox(QWidget* parent,
 
294
                                 const char **strlst) : QWidget(parent)
72
295
{
73
 
        m_layout = new QVBoxLayout(this);
 
296
        QVBoxLayout* layout = new QVBoxLayout(this);
74
297
        m_label = new QLabel(this);
75
298
        m_combo = new QComboBox(this);
76
 
        if (m_layout && m_label && m_combo) {
 
299
        if (layout && m_label && m_combo) {
 
300
                layout->setMargin(0);
 
301
                layout->setSpacing(2);
 
302
                QStringList strList;
77
303
                while (*strlst) {
78
 
                        m_combo->insertItem(i18n(*strlst++));
 
304
                        strList += QCM_translate(*strlst++);
79
305
                }
80
 
                m_layout->addWidget(m_label);
81
 
                m_layout->addWidget(m_combo);
 
306
                m_combo->QCM_addItems(strList);
 
307
                layout->addWidget(m_label);
 
308
                layout->addWidget(m_combo);
82
309
        }
83
310
}
84
311
 
86
313
 * Constructor.
87
314
 *
88
315
 * @param parent parent widget
89
 
 * @param name   internal name or 0
90
316
 */
91
 
LabeledSpinBox::LabeledSpinBox(QWidget* parent, const char* name) :
92
 
    QWidget(parent, name)
 
317
LabeledSpinBox::LabeledSpinBox(QWidget* parent) :
 
318
    QWidget(parent)
93
319
{
94
 
        m_layout = new QVBoxLayout(this);
 
320
        QVBoxLayout* layout = new QVBoxLayout(this);
95
321
        m_label = new QLabel(this);
96
322
        m_spinbox = new QSpinBox(this);
97
 
        if (m_layout && m_label && m_spinbox) {
98
 
                m_layout->addWidget(m_label);
99
 
                m_layout->addWidget(m_spinbox);
 
323
        if (layout && m_label && m_spinbox) {
 
324
                layout->setMargin(0);
 
325
                layout->setSpacing(2);
 
326
                layout->addWidget(m_label);
 
327
                layout->addWidget(m_spinbox);
100
328
        }
101
329
}
102
330
 
104
332
 * Constructor.
105
333
 *
106
334
 * @param parent parent widget
107
 
 * @param name   internal name or 0
108
335
 * @param img    image to display in window
109
336
 */
110
 
ImageViewer::ImageViewer(QWidget* parent, const char* name, QImage* img) :
111
 
    QDialog(parent, name, true), m_image(img)
 
337
ImageViewer::ImageViewer(QWidget* parent, QImage* img) :
 
338
    QDialog(parent), m_image(img)
112
339
{
 
340
        setModal(true);
113
341
        setFixedSize(m_image->width(), m_image->height());
114
 
        setCaption(i18n("View Picture"));
 
342
        QCM_setWindowTitle(i18n("View Picture"));
115
343
}
116
344
 
117
345
/**
124
352
}
125
353
 
126
354
 
127
 
/** List box to select frame */
128
 
Q3ListBox* FrameList::s_listbox = 0;
129
 
 
130
 
/**
131
 
 * Constructor.
132
 
 */
133
 
FrameList::FrameList() : m_file(0) {}
 
355
/** Field edit dialog */
 
356
class EditFrameDialog : public QDialog {
 
357
public:
 
358
 /**
 
359
        * Constructor.
 
360
        *
 
361
        * @param parent  parent widget
 
362
        * @param caption window title
 
363
        * @param text    text to edit
 
364
        */
 
365
        EditFrameDialog(QWidget* parent, const QString& caption,
 
366
                                                                        const QString& text);
 
367
 
 
368
        /**
 
369
         * Destructor.
 
370
         */
 
371
        virtual ~EditFrameDialog();
 
372
 
 
373
        /**
 
374
         * Set text to edit.
 
375
         * @param text text
 
376
         */
 
377
        void setText(const QString& text) {
 
378
                m_edit->QCM_setPlainText(text);
 
379
        }
 
380
 
 
381
        /**
 
382
         * Get edited text.
 
383
         * @return text.
 
384
         */
 
385
        QString getText() const { return m_edit->QCM_toPlainText(); }
 
386
 
 
387
private:
 
388
        QTextEdit* m_edit;
 
389
        QPushButton* m_okButton;
 
390
        QPushButton* m_cancelButton;
 
391
};
 
392
 
 
393
/**
 
394
 * Constructor.
 
395
 *
 
396
 * @param parent  parent widget
 
397
 * @param caption window title
 
398
 * @param text    text to edit
 
399
 */
 
400
EditFrameDialog::EditFrameDialog(QWidget* parent, const QString& caption,
 
401
                                                                                                                                 const QString& text) :
 
402
        QDialog(parent)
 
403
{
 
404
        setModal(true);
 
405
        QCM_setWindowTitle(caption);
 
406
        QVBoxLayout* vlayout = new QVBoxLayout(this);
 
407
        if (vlayout) {
 
408
                vlayout->setSpacing(6);
 
409
                vlayout->setMargin(6);
 
410
                m_edit = new QTextEdit(this);
 
411
                if (m_edit) {
 
412
                        m_edit->QCM_setPlainText(text);
 
413
#if QT_VERSION >= 0x040200
 
414
                        m_edit->moveCursor(QTextCursor::End);
 
415
#elif QT_VERSION >= 0x040000
 
416
                        QTextCursor cursor = m_edit->textCursor();
 
417
                        cursor.movePosition(QTextCursor::End);
 
418
                        m_edit->setTextCursor(cursor);
 
419
#else
 
420
                        m_edit->moveCursor(QTextEdit::MoveEnd, false);
 
421
#endif
 
422
                        vlayout->addWidget(m_edit);
 
423
                }
 
424
        }
 
425
        QHBoxLayout* hlayout = new QHBoxLayout;
 
426
        QSpacerItem* hspacer = new QSpacerItem(16, 0, QSizePolicy::Expanding,
 
427
                                           QSizePolicy::Minimum);
 
428
        m_okButton = new QPushButton(i18n("&OK"), this);
 
429
        m_cancelButton = new QPushButton(i18n("&Cancel"), this);
 
430
        if (hlayout && m_okButton && m_cancelButton) {
 
431
                hlayout->addItem(hspacer);
 
432
                hlayout->addWidget(m_okButton);
 
433
                hlayout->addWidget(m_cancelButton);
 
434
                m_okButton->setDefault(true);
 
435
                connect(m_okButton, SIGNAL(clicked()), this, SLOT(accept()));
 
436
                connect(m_cancelButton, SIGNAL(clicked()), this, SLOT(reject()));
 
437
                vlayout->addLayout(hlayout);
 
438
        }
 
439
#if QT_VERSION >= 0x040000
 
440
        setMinimumWidth(400);
 
441
#else
 
442
        resize(400, -1);
 
443
#endif
 
444
}
 
445
 
 
446
/**
 
447
 * Destructor.
 
448
 */
 
449
EditFrameDialog::~EditFrameDialog() {
 
450
}
 
451
 
 
452
 
 
453
/** Base class for field controls */
 
454
class FieldControl : public QObject {
 
455
public:
 
456
        /**
 
457
         * Constructor.
 
458
         */
 
459
        FieldControl() {}
 
460
 
 
461
        /**
 
462
         * Destructor.
 
463
         */
 
464
        virtual ~FieldControl() {}
 
465
 
 
466
        /**
 
467
         * Update field from data in field control.
 
468
         */
 
469
        virtual void updateTag() = 0;
 
470
 
 
471
        /**
 
472
         * Create widget to edit field data.
 
473
         *
 
474
         * @param parent parent widget
 
475
         *
 
476
         * @return widget to edit field data.
 
477
         */
 
478
        virtual QWidget* createWidget(QWidget* parent) = 0;
 
479
};
 
480
 
 
481
/** List of field control pointers. */
 
482
#if QT_VERSION >= 0x040000
 
483
typedef QList<FieldControl*> FieldControlList;
 
484
#else
 
485
typedef QPtrList<FieldControl> FieldControlList;
 
486
#endif
 
487
 
 
488
 
 
489
/** Base class for MP3 field controls */
 
490
class Mp3FieldControl : public FieldControl {
 
491
public:
 
492
        /**
 
493
         * Constructor.
 
494
         * @param field field to edit
 
495
         */
 
496
        Mp3FieldControl(Frame::Field& field) :
 
497
                m_field(field) {}
 
498
 
 
499
        /**
 
500
         * Destructor.
 
501
         */
 
502
        virtual ~Mp3FieldControl() {}
 
503
 
 
504
protected:
 
505
        /**
 
506
         * Get description for ID3_Field.
 
507
         *
 
508
         * @param id ID of field
 
509
         * @return description or NULL if id unknown.
 
510
         */
 
511
        const char* getFieldIDString(Frame::Field::Id id) const;
 
512
 
 
513
        /** field */
 
514
        Frame::Field& m_field;
 
515
};
 
516
 
 
517
/** Control to edit standard UTF text fields */
 
518
class TextFieldControl : public Mp3FieldControl {
 
519
public:
 
520
        /**
 
521
         * Constructor.
 
522
         * @param field field to edit
 
523
         */
 
524
        TextFieldControl(Frame::Field& field) :
 
525
                Mp3FieldControl(field) {}
 
526
 
 
527
        /**
 
528
         * Destructor.
 
529
         */
 
530
        virtual ~TextFieldControl() {}
 
531
 
 
532
        /**
 
533
         * Update field from data in field control.
 
534
         */
 
535
        virtual void updateTag();
 
536
 
 
537
        /**
 
538
         * Create widget to edit field data.
 
539
         *
 
540
         * @param parent parent widget
 
541
         *
 
542
         * @return widget to edit field data.
 
543
         */
 
544
        virtual QWidget* createWidget(QWidget* parent);
 
545
 
 
546
protected:
 
547
        /** Text editor widget */
 
548
        LabeledTextEdit* m_edit;
 
549
};
 
550
 
 
551
/** Control to edit single line text fields */
 
552
class LineFieldControl : public Mp3FieldControl {
 
553
public:
 
554
        /**
 
555
         * Constructor.
 
556
         * @param field field to edit
 
557
         */
 
558
        LineFieldControl(Frame::Field& field) :
 
559
                Mp3FieldControl(field) {}
 
560
 
 
561
        /**
 
562
         * Destructor.
 
563
         */
 
564
        virtual ~LineFieldControl() {}
 
565
 
 
566
        /**
 
567
         * Update field from data in field control.
 
568
         */
 
569
        virtual void updateTag();
 
570
 
 
571
        /**
 
572
         * Create widget to edit field data.
 
573
         *
 
574
         * @param parent parent widget
 
575
         *
 
576
         * @return widget to edit field data.
 
577
         */
 
578
        virtual QWidget* createWidget(QWidget* parent);
 
579
 
 
580
protected:
 
581
        /** Line editor widget */
 
582
        LabeledLineEdit* m_edit;
 
583
};
 
584
 
 
585
/** Control to edit integer fields */
 
586
class IntFieldControl : public Mp3FieldControl {
 
587
public:
 
588
        /**
 
589
         * Constructor.
 
590
         * @param field field to edit
 
591
         */
 
592
        IntFieldControl(Frame::Field& field) :
 
593
                Mp3FieldControl(field) {}
 
594
 
 
595
        /**
 
596
         * Destructor.
 
597
         */
 
598
        virtual ~IntFieldControl() {}
 
599
 
 
600
        /**
 
601
         * Update field from data in field control.
 
602
         */
 
603
        virtual void updateTag();
 
604
 
 
605
        /**
 
606
         * Create widget to edit field data.
 
607
         *
 
608
         * @param parent parent widget
 
609
         *
 
610
         * @return widget to edit field data.
 
611
         */
 
612
        virtual QWidget* createWidget(QWidget* parent);
 
613
 
 
614
protected:
 
615
        /** Spin box widget */
 
616
        LabeledSpinBox* m_numInp;
 
617
};
 
618
 
 
619
/** Control to edit integer fields using a combo box with given values */
 
620
class IntComboBoxControl : public Mp3FieldControl {
 
621
public:
 
622
        /**
 
623
         * Constructor.
 
624
         * @param field field to edit
 
625
         * @param lst list of strings with possible selections, NULL terminated
 
626
         */
 
627
        IntComboBoxControl(Frame::Field& field,
 
628
                                                                                 const char **lst) :
 
629
                Mp3FieldControl(field), m_strLst(lst) {}
 
630
 
 
631
        /**
 
632
         * Destructor.
 
633
         */
 
634
        virtual ~IntComboBoxControl() {}
 
635
 
 
636
        /**
 
637
         * Update field from data in field control.
 
638
         */
 
639
        virtual void updateTag();
 
640
 
 
641
        /**
 
642
         * Create widget to edit field data.
 
643
         *
 
644
         * @param parent parent widget
 
645
         *
 
646
         * @return widget to edit field data.
 
647
         */
 
648
        virtual QWidget* createWidget(QWidget* parent);
 
649
 
 
650
protected:
 
651
        /** Combo box widget */
 
652
        LabeledComboBox* m_ptInp;
 
653
        /** List of strings with possible selections */
 
654
        const char** m_strLst;
 
655
};
 
656
 
 
657
/** Control to import, export and view data from binary fields */
 
658
class BinFieldControl : public Mp3FieldControl {
 
659
public:
 
660
        /**
 
661
         * Constructor.
 
662
         * @param field field to edit
 
663
         */
 
664
        BinFieldControl(Frame::Field& field) :
 
665
                Mp3FieldControl(field) {}
 
666
 
 
667
        /**
 
668
         * Destructor.
 
669
         */
 
670
        virtual ~BinFieldControl() {}
 
671
 
 
672
        /**
 
673
         * Update field from data in field control.
 
674
         */
 
675
        virtual void updateTag();
 
676
 
 
677
        /**
 
678
         * Create widget to edit field data.
 
679
         *
 
680
         * @param parent parent widget
 
681
         *
 
682
         * @return widget to edit field data.
 
683
         */
 
684
        virtual QWidget* createWidget(QWidget* parent);
 
685
 
 
686
protected:
 
687
        /** Import, Export, View buttons */
 
688
        BinaryOpenSave* m_bos;
 
689
};
 
690
 
 
691
 
 
692
/**
 
693
 * Constructor.
 
694
 *
 
695
 * @param parent parent widget
 
696
 * @param field  field containing binary data
 
697
 */
 
698
BinaryOpenSave::BinaryOpenSave(QWidget* parent, const Frame::Field& field) :
 
699
        QWidget(parent), m_byteArray(field.m_value.toByteArray()),
 
700
        m_isChanged(false)
 
701
{
 
702
        QHBoxLayout* layout = new QHBoxLayout(this);
 
703
        m_label = new QLabel(this);
 
704
        QPushButton* openButton = new QPushButton(i18n("&Import"), this);
 
705
        QPushButton* saveButton = new QPushButton(i18n("&Export"), this);
 
706
        QPushButton* viewButton = new QPushButton(i18n("&View"), this);
 
707
        if (layout && m_label && openButton && saveButton && viewButton) {
 
708
                layout->setMargin(0);
 
709
                layout->setSpacing(6);
 
710
                layout->addWidget(m_label);
 
711
                layout->addWidget(openButton);
 
712
                layout->addWidget(saveButton);
 
713
                layout->addWidget(viewButton);
 
714
                connect(openButton, SIGNAL(clicked()), this, SLOT(loadData()));
 
715
                connect(saveButton, SIGNAL(clicked()), this, SLOT(saveData()));
 
716
                connect(viewButton, SIGNAL(clicked()), this, SLOT(viewData()));
 
717
        }
 
718
}
 
719
 
 
720
/**
 
721
 * Request name of file to import binary data from.
 
722
 * The data is imported later when Ok is pressed in the parent dialog.
 
723
 */
 
724
void BinaryOpenSave::loadData()
 
725
{
 
726
#ifdef CONFIG_USE_KDE
 
727
        QString loadfilename = KFileDialog::getOpenFileName(
 
728
                Kid3App::getDirName(), QString::null, this);
 
729
#else
 
730
        QString loadfilename = QFileDialog::QCM_getOpenFileName(this, Kid3App::getDirName());
 
731
#endif
 
732
        if (!loadfilename.isEmpty()) {
 
733
                QFile file(loadfilename);
 
734
                if (file.open(QCM_ReadOnly)) {
 
735
                        size_t size = file.size();
 
736
                        char* data = new char[size];
 
737
                        if (data) {
 
738
                                QDataStream stream(&file);
 
739
                                stream.QCM_readRawData(data, size);
 
740
                                QCM_duplicate(m_byteArray, data, size);
 
741
                                m_isChanged = true;
 
742
                                delete [] data;
 
743
                        }
 
744
                        file.close();
 
745
                }
 
746
        }
 
747
}
 
748
 
 
749
/**
 
750
 * Request name of file and export binary data.
 
751
 */
 
752
void BinaryOpenSave::saveData()
 
753
{
 
754
#ifdef CONFIG_USE_KDE
 
755
        QString fn = KFileDialog::getSaveFileName(Kid3App::getDirName(), QString::null,
 
756
                                                                                                                                                                                this);
 
757
#else
 
758
        QString fn = QFileDialog::QCM_getSaveFileName(this, Kid3App::getDirName());
 
759
#endif
 
760
        if (!fn.isEmpty()) {
 
761
                QFile file(fn);
 
762
                if (file.open(QCM_WriteOnly)) {
 
763
                        QDataStream stream(&file);
 
764
                        stream.QCM_writeRawData(m_byteArray.data(), m_byteArray.size());
 
765
                        file.close();
 
766
                }
 
767
        }
 
768
}
 
769
 
 
770
/**
 
771
 * Create image from binary data and display it in window.
 
772
 */
 
773
void BinaryOpenSave::viewData()
 
774
{
 
775
        QImage image;
 
776
        if (image.loadFromData(m_byteArray)) {
 
777
                ImageViewer iv(this, &image);
 
778
                iv.exec();
 
779
        }
 
780
}
 
781
 
 
782
/**
 
783
 * Get description for ID3_Field.
 
784
 *
 
785
 * @param id ID of field
 
786
 * @return description or NULL if id unknown.
 
787
 */
 
788
const char* Mp3FieldControl::getFieldIDString(Frame::Field::Id id) const
 
789
{
 
790
        static const char* const idStr[] = {
 
791
                "Unknown",
 
792
                I18N_NOOP("Text Encoding"),
 
793
                I18N_NOOP("Text"),
 
794
                I18N_NOOP("URL"),
 
795
                I18N_NOOP("Data"),
 
796
                I18N_NOOP("Description"),
 
797
                I18N_NOOP("Owner"),
 
798
                I18N_NOOP("Email"),
 
799
                I18N_NOOP("Rating"),
 
800
                I18N_NOOP("Filename"),
 
801
                I18N_NOOP("Language"),
 
802
                I18N_NOOP("Picture Type"),
 
803
                I18N_NOOP("Image format"),
 
804
                I18N_NOOP("Mimetype"),
 
805
                I18N_NOOP("Counter"),
 
806
                I18N_NOOP("Identifier"),
 
807
                I18N_NOOP("Volume Adjustment"),
 
808
                I18N_NOOP("Number of Bits"),
 
809
                I18N_NOOP("Volume Change Right"),
 
810
                I18N_NOOP("Volume Change Left"),
 
811
                I18N_NOOP("Peak Volume Right"),
 
812
                I18N_NOOP("Peak Volume Left"),
 
813
                I18N_NOOP("Timestamp Format"),
 
814
                I18N_NOOP("Content Type")
 
815
        };
 
816
        class not_used { int array_size_check[
 
817
                        sizeof(idStr) / sizeof(idStr[0]) == Frame::Field::ID_ContentType + 1
 
818
                        ? 1 : -1 ]; };
 
819
        return idStr[id <= Frame::Field::ID_ContentType ? id : 0];
 
820
}
 
821
 
 
822
/**
 
823
 * Update field with data from dialog.
 
824
 */
 
825
void TextFieldControl::updateTag()
 
826
{
 
827
        m_field.m_value = m_edit->text();
 
828
}
 
829
 
 
830
/**
 
831
 * Create widget for dialog.
 
832
 *
 
833
 * @param parent parent widget
 
834
 * @return widget to edit field.
 
835
 */
 
836
QWidget* TextFieldControl::createWidget(QWidget* parent)
 
837
{
 
838
        m_edit = new LabeledTextEdit(parent);
 
839
        if (m_edit == NULL)
 
840
                return NULL;
 
841
 
 
842
        m_edit->setLabel(QCM_translate(getFieldIDString(static_cast<Frame::Field::Id>(m_field.m_id))));
 
843
        m_edit->setText(m_field.m_value.toString());
 
844
        return m_edit;
 
845
}
 
846
 
 
847
/**
 
848
 * Update field with data from dialog.
 
849
 */
 
850
void LineFieldControl::updateTag()
 
851
{
 
852
        m_field.m_value = m_edit->text();
 
853
}
 
854
 
 
855
/**
 
856
 * Create widget for dialog.
 
857
 *
 
858
 * @param parent parent widget
 
859
 * @return widget to edit field.
 
860
 */
 
861
QWidget* LineFieldControl::createWidget(QWidget* parent)
 
862
{
 
863
        m_edit = new LabeledLineEdit(parent);
 
864
        if (m_edit) {
 
865
                m_edit->setLabel(QCM_translate(getFieldIDString(static_cast<Frame::Field::Id>(m_field.m_id))));
 
866
                m_edit->setText(m_field.m_value.toString());
 
867
        }
 
868
        return m_edit;
 
869
}
 
870
 
 
871
/**
 
872
 * Update field with data from dialog.
 
873
 */
 
874
void IntFieldControl::updateTag()
 
875
{
 
876
        m_field.m_value = m_numInp->value();
 
877
}
 
878
 
 
879
/**
 
880
 * Create widget for dialog.
 
881
 *
 
882
 * @param parent parent widget
 
883
 * @return widget to edit field.
 
884
 */
 
885
QWidget* IntFieldControl::createWidget(QWidget* parent)
 
886
{
 
887
        m_numInp = new LabeledSpinBox(parent);
 
888
        if (m_numInp) {
 
889
                m_numInp->setLabel(QCM_translate(getFieldIDString(static_cast<Frame::Field::Id>(m_field.m_id))));
 
890
                m_numInp->setValue(m_field.m_value.toInt());
 
891
        }
 
892
        return m_numInp;
 
893
}
 
894
 
 
895
/**
 
896
 * Update field with data from dialog.
 
897
 */
 
898
void IntComboBoxControl::updateTag()
 
899
{
 
900
        m_field.m_value = m_ptInp->currentItem();
 
901
}
 
902
 
 
903
/**
 
904
 * Create widget for dialog.
 
905
 *
 
906
 * @param parent parent widget
 
907
 * @return widget to edit field.
 
908
 */
 
909
QWidget* IntComboBoxControl::createWidget(QWidget* parent)
 
910
{
 
911
        m_ptInp = new LabeledComboBox(parent, m_strLst);
 
912
        if (m_ptInp) {
 
913
                m_ptInp->setLabel(QCM_translate(getFieldIDString(static_cast<Frame::Field::Id>(m_field.m_id))));
 
914
                m_ptInp->setCurrentItem(m_field.m_value.toInt());
 
915
        }
 
916
        return m_ptInp;
 
917
}
 
918
 
 
919
/**
 
920
 * Update field with data from dialog.
 
921
 */
 
922
void BinFieldControl::updateTag()
 
923
{
 
924
        if (m_bos && m_bos->isChanged()) {
 
925
                m_field.m_value = m_bos->getData();
 
926
        }
 
927
}
 
928
 
 
929
/**
 
930
 * Create widget for dialog.
 
931
 *
 
932
 * @param parent parent widget
 
933
 * @return widget to edit field.
 
934
 */
 
935
QWidget* BinFieldControl::createWidget(QWidget* parent)
 
936
{
 
937
        m_bos = new BinaryOpenSave(parent, m_field);
 
938
        if (m_bos) {
 
939
                m_bos->setLabel(QCM_translate(getFieldIDString(static_cast<Frame::Field::Id>(m_field.m_id))));
 
940
        }
 
941
        return m_bos;
 
942
}
 
943
 
 
944
 
 
945
/** Field edit dialog */
 
946
class EditFrameFieldsDialog : public QDialog {
 
947
public:
 
948
        /**
 
949
         * Constructor.
 
950
         *
 
951
         * @param parent  parent widget
 
952
         * @param caption caption
 
953
         * @param fields  fields to edit
 
954
         */
 
955
        EditFrameFieldsDialog(QWidget* parent, const QString& caption,
 
956
                                                                                                const Frame::FieldList& fields);
 
957
 
 
958
        /**
 
959
         * Destructor.
 
960
         */
 
961
        virtual ~EditFrameFieldsDialog();
 
962
 
 
963
        /**
 
964
         * Update fields and get edited fields.
 
965
         *
 
966
         * @return field list.
 
967
         */
 
968
        const Frame::FieldList& getUpdatedFieldList();
 
969
 
 
970
private:
 
971
        Frame::FieldList m_fields;
 
972
        FieldControlList m_fieldcontrols; 
 
973
};
 
974
 
 
975
/**
 
976
 * Constructor.
 
977
 *
 
978
 * @param parent  parent widget
 
979
 * @param caption caption
 
980
 * @param fields  fields to edit
 
981
 */
 
982
EditFrameFieldsDialog::EditFrameFieldsDialog(QWidget* parent, const QString& caption,
 
983
                                                                                        const Frame::FieldList& fields) :
 
984
        QDialog(parent), m_fields(fields)
 
985
{
 
986
        setModal(true);
 
987
        QCM_setWindowTitle(caption);
 
988
#if QT_VERSION >= 0x040000
 
989
        qDeleteAll(m_fieldcontrols);
 
990
#else
 
991
        m_fieldcontrols.setAutoDelete(true);
 
992
#endif
 
993
        m_fieldcontrols.clear();
 
994
        QVBoxLayout* vlayout = new QVBoxLayout(this);
 
995
        if (vlayout) {
 
996
                vlayout->setSpacing(6);
 
997
                vlayout->setMargin(6);
 
998
 
 
999
                for (Frame::FieldList::iterator fldIt = m_fields.begin();
 
1000
                                 fldIt != m_fields.end();
 
1001
                                 ++fldIt) {
 
1002
                        Frame::Field& fld = *fldIt;
 
1003
                        switch (fld.m_value.type()) {
 
1004
                                case QVariant::Int:
 
1005
                                case QVariant::UInt:
 
1006
                                        if (fld.m_id == Frame::Field::ID_TextEnc) {
 
1007
                                                static const char* strlst[] = {
 
1008
                                                        I18N_NOOP("ISO-8859-1"),
 
1009
                                                        I18N_NOOP("UTF16"),
 
1010
                                                        I18N_NOOP("UTF16BE"),
 
1011
                                                        I18N_NOOP("UTF8"),
 
1012
                                                        NULL
 
1013
                                                };
 
1014
                                                IntComboBoxControl* cbox =
 
1015
                                                        new IntComboBoxControl(fld, strlst);
 
1016
                                                if (cbox) {
 
1017
                                                        m_fieldcontrols.append(cbox);
 
1018
                                                }
 
1019
                                        }
 
1020
                                        else if (fld.m_id == Frame::Field::ID_PictureType) {
 
1021
                                                static const char* strlst[] = {
 
1022
                                                        I18N_NOOP("Other"),
 
1023
                                                        I18N_NOOP("32x32 pixels PNG file icon"),
 
1024
                                                        I18N_NOOP("Other file icon"),
 
1025
                                                        I18N_NOOP("Cover (front)"),
 
1026
                                                        I18N_NOOP("Cover (back)"),
 
1027
                                                        I18N_NOOP("Leaflet page"),
 
1028
                                                        I18N_NOOP("Media"),
 
1029
                                                        I18N_NOOP("Lead artist/lead performer/soloist"),
 
1030
                                                        I18N_NOOP("Artist/performer"),
 
1031
                                                        I18N_NOOP("Conductor"),
 
1032
                                                        I18N_NOOP("Band/Orchestra"),
 
1033
                                                        I18N_NOOP("Composer"),
 
1034
                                                        I18N_NOOP("Lyricist/text writer"),
 
1035
                                                        I18N_NOOP("Recording Location"),
 
1036
                                                        I18N_NOOP("During recording"),
 
1037
                                                        I18N_NOOP("During performance"),
 
1038
                                                        I18N_NOOP("Movie/video screen capture"),
 
1039
                                                        I18N_NOOP("A bright coloured fish"),
 
1040
                                                        I18N_NOOP("Illustration"),
 
1041
                                                        I18N_NOOP("Band/artist logotype"),
 
1042
                                                        I18N_NOOP("Publisher/Studio logotype"),
 
1043
                                                        NULL
 
1044
                                                };
 
1045
                                                IntComboBoxControl* cbox =
 
1046
                                                        new IntComboBoxControl(fld, strlst);
 
1047
                                                if (cbox) {
 
1048
                                                        m_fieldcontrols.append(cbox);
 
1049
                                                }
 
1050
                                        }
 
1051
                                        else if (fld.m_id == Frame::Field::ID_TimestampFormat) {
 
1052
                                                static const char* strlst[] = {
 
1053
                                                        I18N_NOOP("Other"),
 
1054
                                                        I18N_NOOP("MPEG frames as unit"),
 
1055
                                                        I18N_NOOP("Milliseconds as unit"),
 
1056
                                                        NULL
 
1057
                                                };
 
1058
                                                IntComboBoxControl* cbox =
 
1059
                                                        new IntComboBoxControl(fld, strlst);
 
1060
                                                if (cbox) {
 
1061
                                                        m_fieldcontrols.append(cbox);
 
1062
                                                }
 
1063
                                        }
 
1064
                                        else if (fld.m_id == Frame::Field::ID_ContentType) {
 
1065
                                                static const char* strlst[] = {
 
1066
                                                        I18N_NOOP("Other"),
 
1067
                                                        I18N_NOOP("Lyrics"),
 
1068
                                                        I18N_NOOP("Text transcription"),
 
1069
                                                        I18N_NOOP("Movement/part name"),
 
1070
                                                        I18N_NOOP("Events"),
 
1071
                                                        I18N_NOOP("Chord"),
 
1072
                                                        I18N_NOOP("Trivia/pop up"),
 
1073
                                                        NULL
 
1074
                                                };
 
1075
                                                IntComboBoxControl* cbox =
 
1076
                                                        new IntComboBoxControl(fld, strlst);
 
1077
                                                if (cbox) {
 
1078
                                                        m_fieldcontrols.append(cbox);
 
1079
                                                }
 
1080
                                        }
 
1081
                                        else {
 
1082
                                                IntFieldControl* intctl =
 
1083
                                                        new IntFieldControl(fld);
 
1084
                                                if (intctl) {
 
1085
                                                        m_fieldcontrols.append(intctl);
 
1086
                                                }
 
1087
                                        }
 
1088
                                        break;
 
1089
 
 
1090
                                case QVariant::String:
 
1091
                                        if (fld.m_id == Frame::Field::ID_Text) {
 
1092
                                                // Large textedit for text fields
 
1093
                                                TextFieldControl* textctl =
 
1094
                                                        new TextFieldControl(fld);
 
1095
                                                if (textctl) {
 
1096
                                                        m_fieldcontrols.append(textctl);
 
1097
                                                }
 
1098
                                        }
 
1099
                                        else {
 
1100
                                                LineFieldControl* textctl =
 
1101
                                                        new LineFieldControl(fld);
 
1102
                                                if (textctl) {
 
1103
                                                        m_fieldcontrols.append(textctl);
 
1104
                                                }
 
1105
                                        }
 
1106
                                        break;
 
1107
 
 
1108
                                case QVariant::ByteArray:
 
1109
                                {
 
1110
                                        BinFieldControl* binctl =
 
1111
                                                new BinFieldControl(fld);
 
1112
                                        if (binctl) {
 
1113
                                                m_fieldcontrols.append(binctl);
 
1114
                                        }
 
1115
                                        break;
 
1116
                                }
 
1117
 
 
1118
                                default:
 
1119
                                        qDebug("Unknown type %d in field %d", fld.m_value.type(), fld.m_id);
 
1120
                        }
 
1121
                }
 
1122
 
 
1123
#if QT_VERSION >= 0x040000
 
1124
                QListIterator<FieldControl*> it(m_fieldcontrols);
 
1125
                while (it.hasNext()) {
 
1126
                        vlayout->addWidget(it.next()->createWidget(this));
 
1127
                }
 
1128
#else
 
1129
                FieldControl* fldCtl = m_fieldcontrols.first();
 
1130
                while (fldCtl != NULL) {
 
1131
                        vlayout->addWidget(fldCtl->createWidget(this));
 
1132
                        fldCtl = m_fieldcontrols.next();
 
1133
                }
 
1134
#endif
 
1135
        }
 
1136
        QHBoxLayout* hlayout = new QHBoxLayout;
 
1137
        QSpacerItem* hspacer = new QSpacerItem(16, 0, QSizePolicy::Expanding,
 
1138
                                           QSizePolicy::Minimum);
 
1139
        QPushButton* okButton = new QPushButton(i18n("&OK"), this);
 
1140
        QPushButton* cancelButton = new QPushButton(i18n("&Cancel"), this);
 
1141
        if (hlayout && okButton && cancelButton) {
 
1142
                hlayout->addItem(hspacer);
 
1143
                hlayout->addWidget(okButton);
 
1144
                hlayout->addWidget(cancelButton);
 
1145
                okButton->setDefault(true);
 
1146
                connect(okButton, SIGNAL(clicked()), this, SLOT(accept()));
 
1147
                connect(cancelButton, SIGNAL(clicked()), this, SLOT(reject()));
 
1148
                vlayout->addLayout(hlayout);
 
1149
        }
 
1150
#if QT_VERSION >= 0x040000
 
1151
        setMinimumWidth(525);
 
1152
#else
 
1153
        resize(525, -1);
 
1154
#endif
 
1155
}
 
1156
 
 
1157
/**
 
1158
 * Destructor.
 
1159
 */
 
1160
EditFrameFieldsDialog::~EditFrameFieldsDialog()
 
1161
{
 
1162
#if QT_VERSION >= 0x040000
 
1163
        qDeleteAll(m_fieldcontrols);
 
1164
        m_fieldcontrols.clear();
 
1165
#endif
 
1166
}
 
1167
 
 
1168
/**
 
1169
 * Update fields and get edited fields.
 
1170
 *
 
1171
 * @return field list.
 
1172
 */
 
1173
const Frame::FieldList& EditFrameFieldsDialog::getUpdatedFieldList()
 
1174
{
 
1175
#if QT_VERSION >= 0x040000
 
1176
        QListIterator<FieldControl*> it(m_fieldcontrols);
 
1177
        while (it.hasNext()) {
 
1178
                it.next()->updateTag();
 
1179
        }
 
1180
#else
 
1181
        FieldControl* fldCtl = m_fieldcontrols.first();
 
1182
        while (fldCtl != NULL) {
 
1183
                fldCtl->updateTag();
 
1184
                fldCtl = m_fieldcontrols.next();
 
1185
        }
 
1186
#endif
 
1187
        return m_fields;
 
1188
}
 
1189
 
 
1190
 
 
1191
/**
 
1192
 * Constructor.
 
1193
 *
 
1194
 * @param ft frame table
 
1195
 */
 
1196
FrameList::FrameList(FrameTable* ft) :
 
1197
        m_file(0), m_frameTable(ft)
 
1198
{
 
1199
}
134
1200
 
135
1201
/**
136
1202
 * Destructor.
142
1208
 */
143
1209
void FrameList::clear()
144
1210
{
145
 
        s_listbox->clear();
 
1211
        m_frameTable->frames().clear();
 
1212
        m_frameTable->framesToTable();
146
1213
        m_file = 0;
147
1214
}
148
1215
 
161
1228
 */
162
1229
void FrameList::reloadTags()
163
1230
{
164
 
        int selectedRow = -1;
165
 
        int topRow = s_listbox->topItem();
166
 
        for (int i = 0; i < static_cast<int>(s_listbox->count()); ++i) {
167
 
                if (s_listbox->isSelected(i)) {
168
 
                        selectedRow = i;
169
 
                        break;
170
 
                }
171
 
        }
 
1231
        m_frameTable->saveCursor();
172
1232
        setTags(m_file);
173
 
        if (topRow >= 0 && topRow < static_cast<int>(s_listbox->count())) {
174
 
                s_listbox->setTopItem(topRow);
175
 
        }
176
 
        if (selectedRow >= 0 && selectedRow < static_cast<int>(s_listbox->count())) {
177
 
                s_listbox->setSelected(selectedRow, true);
178
 
        }
 
1233
        m_frameTable->restoreCursor();
179
1234
}
180
1235
 
181
1236
/**
184
1239
 * @return ID of selected item,
185
1240
 *         -1 if not item is selected.
186
1241
 */
187
 
int FrameList::getSelectedId()
188
 
{
189
 
        Q3ListBoxItem* lbi;
190
 
        FrameListItem* fli;
191
 
        return
192
 
                (lbi = s_listbox->selectedItem()) != 0 &&
193
 
                (fli = dynamic_cast<FrameListItem*>(lbi)) != 0 ? fli->getId() : -1;
 
1242
int FrameList::getSelectedId() const
 
1243
{
 
1244
        const Frame* currentFrame = m_frameTable->getCurrentFrame();
 
1245
        return currentFrame ? currentFrame->getIndex() : -1;
 
1246
}
 
1247
 
 
1248
/**
 
1249
 * Get frame of selected frame list item.
 
1250
 *
 
1251
 * @param frame the selected frame is returned here
 
1252
 *
 
1253
 * @return false if not item is selected.
 
1254
 */
 
1255
bool FrameList::getSelectedFrame(Frame& frame) const
 
1256
{
 
1257
        const Frame* currentFrame = m_frameTable->getCurrentFrame();
 
1258
        if (currentFrame) {
 
1259
                frame = *currentFrame;
 
1260
                return true;
 
1261
        }
 
1262
        return false;
194
1263
}
195
1264
 
196
1265
/**
200
1269
 */
201
1270
void FrameList::setSelectedId(int id)
202
1271
{
203
 
        Q3ListBoxItem* lbi = s_listbox->firstItem();
204
 
        while (lbi) {
205
 
                FrameListItem* fli = dynamic_cast<FrameListItem*>(lbi);
206
 
                if (fli && fli->getId() == id) {
207
 
                        s_listbox->setSelected(lbi, true);
208
 
                        break;
209
 
                }
210
 
                lbi = lbi->next();
211
 
        }
 
1272
        m_frameTable->selectFrameWithIndex(id);
212
1273
}
213
1274
 
214
1275
/**
216
1277
 *
217
1278
 * @return name, QString::null if nothing selected.
218
1279
 */
219
 
QString FrameList::getSelectedName()
 
1280
QString FrameList::getSelectedName() const
220
1281
{
221
 
        return s_listbox ? s_listbox->currentText() : QString::null;
 
1282
        const Frame* currentFrame = m_frameTable->getCurrentFrame();
 
1283
        return currentFrame ? currentFrame->getName() : QString::null;
222
1284
}
223
1285
 
224
1286
/**
230
1292
 */
231
1293
bool FrameList::selectByName(const QString& name)
232
1294
{
233
 
        if (s_listbox) {
234
 
                Q3ListBoxItem* lbi = s_listbox->findItem(name);
235
 
                if (lbi) {
236
 
                        s_listbox->setSelected(lbi, true);
237
 
                        return true;
238
 
                }
239
 
        }
240
 
        return false;
 
1295
        return m_frameTable->selectFrameWithName(name);
241
1296
}
242
1297
 
243
1298
/**
245
1300
 */
246
1301
void FrameList::clearListBox()
247
1302
{
248
 
        if (s_listbox) {
249
 
                s_listbox->clear();
250
 
        }
 
1303
        if (m_frameTable) {
 
1304
                m_frameTable->frames().clear();
 
1305
                m_frameTable->framesToTable();
 
1306
        }
 
1307
}
 
1308
 
 
1309
/**
 
1310
 * Fill listbox with frame descriptions.
 
1311
 * Before using this method, the listbox and file have to be set.
 
1312
 * @see setListBox(), setTags()
 
1313
 */
 
1314
void FrameList::readTags()
 
1315
{
 
1316
        if (m_file) {
 
1317
                m_file->getAllFramesV2(m_frameTable->frames());
 
1318
                m_frameTable->framesToTable();
 
1319
        }
 
1320
}
 
1321
 
 
1322
/**
 
1323
 * Set file and fill the list box with its frames.
 
1324
 * The listbox has to be set with setListBox() before calling this
 
1325
 * function.
 
1326
 *
 
1327
 * @param taggedFile file
 
1328
 */
 
1329
void FrameList::setTags(TaggedFile* taggedFile)
 
1330
{
 
1331
        m_file = taggedFile;
 
1332
}
 
1333
 
 
1334
/**
 
1335
 * Create dialog to edit a frame and update the fields
 
1336
 * if Ok is returned.
 
1337
 *
 
1338
 * @param frame frame to edit
 
1339
 *
 
1340
 * @return true if Ok selected in dialog.
 
1341
 */
 
1342
bool FrameList::editFrame(Frame& frame)
 
1343
{
 
1344
        bool result = true;
 
1345
        QString name(frame.getName(true));
 
1346
        if (!name.isEmpty()) {
 
1347
#if QT_VERSION >= 0x040000
 
1348
                name = QCM_translate(name.toLatin1().data());
 
1349
#else
 
1350
                name = QCM_translate(name);
 
1351
#endif
 
1352
        }
 
1353
        if (frame.getFieldList().empty()) {
 
1354
                EditFrameDialog* dialog =
 
1355
                        new EditFrameDialog(0, name, frame.getValue());
 
1356
                result = dialog && dialog->exec() == QDialog::Accepted;
 
1357
                if (result) {
 
1358
                        frame.setValue(dialog->getText());
 
1359
                }
 
1360
        } else {
 
1361
                EditFrameFieldsDialog* dialog =
 
1362
                        new EditFrameFieldsDialog(0, name, frame.getFieldList());
 
1363
                result = dialog && dialog->exec() == QDialog::Accepted;
 
1364
                if (result) {
 
1365
                        frame.setFieldList(dialog->getUpdatedFieldList());
 
1366
                        frame.setValueFromFieldList();
 
1367
                }
 
1368
        }
 
1369
        if (result && m_file) {
 
1370
                if (m_file->setFrameV2(frame)) {
 
1371
                        m_file->markTag2Changed();
 
1372
                }
 
1373
        }
 
1374
        return result;
 
1375
}
 
1376
 
 
1377
/**
 
1378
 * Create dialog to edit the selected frame and update the fields
 
1379
 * if Ok is returned.
 
1380
 *
 
1381
 * @return true if Ok selected in dialog.
 
1382
 */
 
1383
bool FrameList::editFrame()
 
1384
{
 
1385
        if (getSelectedFrame(m_frame)) {
 
1386
                return editFrame(m_frame);
 
1387
        }
 
1388
        return false;
 
1389
}
 
1390
 
 
1391
/**
 
1392
 * Delete selected frame.
 
1393
 *
 
1394
 * @return false if frame not found.
 
1395
 */
 
1396
bool FrameList::deleteFrame()
 
1397
{
 
1398
        m_frameTable->saveCursor();
 
1399
        Frame frame;
 
1400
        if (getSelectedFrame(frame) && m_file) {
 
1401
                m_file->deleteFrameV2(frame);
 
1402
                readTags();
 
1403
                m_frameTable->restoreCursor();
 
1404
                return true;
 
1405
        }
 
1406
        return false;
 
1407
}
 
1408
 
 
1409
/**
 
1410
 * Add a new frame.
 
1411
 *
 
1412
 * @param edit    true to edit frame after adding it
 
1413
 *
 
1414
 * @return true if frame added.
 
1415
 */
 
1416
bool FrameList::addFrame(bool edit)
 
1417
{
 
1418
        if (m_file) {
 
1419
                if (!m_file->addFrameV2(m_frame)) {
 
1420
                        return false;
 
1421
                }
 
1422
                if (edit) {
 
1423
                        if (!editFrame(m_frame)) {
 
1424
                                m_file->deleteFrameV2(m_frame);
 
1425
                                m_file->markTag2Changed(false);
 
1426
                                return false;
 
1427
                        }
 
1428
                }
 
1429
                int index = m_frame.getIndex();
 
1430
                readTags(); // refresh listbox
 
1431
                if (index != -1) {
 
1432
                        setSelectedId(index);
 
1433
#if QT_VERSION < 0x040000
 
1434
                        m_frameTable->ensureCellVisible(m_frameTable->currentRow(), m_frameTable->currentColumn()); 
 
1435
#endif
 
1436
                }
 
1437
                return true;
 
1438
        }
 
1439
        return false;
 
1440
}
 
1441
 
 
1442
/**
 
1443
 * Get type of frame from name.
 
1444
 *
 
1445
 * @param name name, spaces and case are ignored
 
1446
 *
 
1447
 * @return type.
 
1448
 */
 
1449
static Frame::Type getTypeFromName(QString name)
 
1450
{
 
1451
        static QMap<QString, int> strNumMap;
 
1452
        if (strNumMap.empty()) {
 
1453
                // first time initialization
 
1454
                for (int i = 0; i <= Frame::FT_LastFrame; ++i) {
 
1455
                        Frame::Type type = static_cast<Frame::Type>(i);
 
1456
                        strNumMap.insert(QCM_translate(Frame::getNameFromType(type)).remove(' ').QCM_toUpper(),
 
1457
                                                                                         type);
 
1458
                }
 
1459
        }
 
1460
        QMap<QString, int>::const_iterator it =
 
1461
                strNumMap.find(name.remove(' ').QCM_toUpper());
 
1462
        if (it != strNumMap.end()) {
 
1463
                return static_cast<Frame::Type>(*it);
 
1464
        }
 
1465
        return Frame::FT_Other;
 
1466
}
 
1467
 
 
1468
/**
 
1469
 * Display a dialog to select a frame type.
 
1470
 *
 
1471
 * @return false if no frame selected.
 
1472
 */
 
1473
bool FrameList::selectFrame()
 
1474
{
 
1475
        // strange, but necessary to get the strings translated with Qt4 without KDE
 
1476
        const char* const title = I18N_NOOP("Add Frame");
 
1477
        const char* const msg = I18N_NOOP("Select the frame ID");
 
1478
        bool ok = false;
 
1479
        if (m_file) {
 
1480
                QString name = QInputDialog::QCM_getItem(
 
1481
                        0, QCM_translate(title),
 
1482
                        QCM_translate(msg), m_file->getFrameIds(), 0, true, &ok);
 
1483
                if (ok) {
 
1484
                        Frame::Type type = getTypeFromName(name);
 
1485
                        m_frame = Frame(type, "", name, -1);
 
1486
                }
 
1487
        }
 
1488
        return ok;
 
1489
}
 
1490
 
 
1491
/**
 
1492
 * Paste the selected frame from the copy buffer.
 
1493
 *
 
1494
 * @return true if frame pasted.
 
1495
 */
 
1496
bool FrameList::pasteFrame() {
 
1497
        if (m_file && m_frame.getType() != Frame::FT_UnknownFrame) {
 
1498
                m_file->addFrameV2(m_frame);
 
1499
                m_file->setFrameV2(m_frame);
 
1500
                return true;
 
1501
        }
 
1502
        return false;
251
1503
}