annotationpopup.cpp 7.53 KB
Newer Older
1 2 3 4 5 6 7 8 9
/***************************************************************************
 *   Copyright (C) 2006 by Tobias Koenig <tokoe@kde.org>                   *
 *                                                                         *
 *   This program is free software; you can redistribute it and/or modify  *
 *   it under the terms of the GNU General Public License as published by  *
 *   the Free Software Foundation; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 ***************************************************************************/

10 11
#include "annotationpopup.h"

Laurent Montel's avatar
Laurent Montel committed
12 13
#include <KLocalizedString>
#include <QMenu>
Laurent Montel's avatar
Laurent Montel committed
14
#include <QIcon>
15 16 17 18 19

#include "annotationpropertiesdialog.h"

#include "core/annotations.h"
#include "core/document.h"
20
#include "guiutils.h"
21
#include "okmenutitle.h"
22

23 24
Q_DECLARE_METATYPE( AnnotationPopup::AnnotPagePair )

25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45
namespace {

bool annotationHasFileAttachment( Okular::Annotation *annotation )
{
    return ( annotation->subType() == Okular::Annotation::AFileAttachment || annotation->subType() == Okular::Annotation::ARichMedia );
}

Okular::EmbeddedFile* embeddedFileFromAnnotation( Okular::Annotation *annotation )
{
    if ( annotation->subType() == Okular::Annotation::AFileAttachment )
    {
        const Okular::FileAttachmentAnnotation *fileAttachAnnot = static_cast<Okular::FileAttachmentAnnotation*>( annotation );
        return fileAttachAnnot->embeddedFile();
    }
    else if ( annotation->subType() == Okular::Annotation::ARichMedia )
    {
        const Okular::RichMediaAnnotation *richMediaAnnot = static_cast<Okular::RichMediaAnnotation*>( annotation );
        return richMediaAnnot->embeddedFile();
    }
    else
    {
46
        return nullptr;
47 48 49 50 51
    }
}

}

52
AnnotationPopup::AnnotationPopup( Okular::Document *document, MenuMode mode,
53
                                  QWidget *parent )
54
    : mParent( parent ), mDocument( document ), mMenuMode( mode )
55 56 57
{
}

58
void AnnotationPopup::addAnnotation( Okular::Annotation* annotation, int pageNumber )
59
{
60
    AnnotPagePair pair( annotation, pageNumber );
61 62
    if ( !mAnnotations.contains( pair ) )
      mAnnotations.append( pair );
63 64
}

65
void AnnotationPopup::exec( const QPoint point )
66
{
67 68 69
    if ( mAnnotations.isEmpty() )
        return;

Vishesh Handa's avatar
Vishesh Handa committed
70
    QMenu menu( mParent );
71

72
    QAction *action = nullptr;
73

74
    const char *actionTypeId = "actionType";
75

Laurent Montel's avatar
Laurent Montel committed
76 77 78 79 80
    const QString openId = QStringLiteral( "open" );
    const QString deleteId = QStringLiteral( "delete" );
    const QString deleteAllId = QStringLiteral( "deleteAll" );
    const QString propertiesId = QStringLiteral( "properties" );
    const QString saveId = QStringLiteral( "save" );
81

82
    if ( mMenuMode == SingleAnnotationMode )
83
    {
84 85 86 87
        const bool onlyOne = (mAnnotations.count() == 1);

        const AnnotPagePair &pair = mAnnotations.at(0);

88
        menu.addAction( new OKMenuTitle( &menu, i18np( "Annotation", "%1 Annotations", mAnnotations.count() ) ) );
89

Laurent Montel's avatar
Laurent Montel committed
90
        action = menu.addAction( QIcon::fromTheme( QStringLiteral("comment") ), i18n( "&Open Pop-up Note" ) );
91
        action->setData( QVariant::fromValue( pair ) );
92
        action->setEnabled( onlyOne );
93 94
        action->setProperty( actionTypeId, openId );

Laurent Montel's avatar
Laurent Montel committed
95
        action = menu.addAction( QIcon::fromTheme( QStringLiteral("list-remove") ), i18n( "&Delete" ) );
96 97 98
        action->setEnabled( mDocument->isAllowed( Okular::AllowNotes ) );
        action->setProperty( actionTypeId, deleteAllId );

99
        for ( const AnnotPagePair &pair : qAsConst(mAnnotations) )
100 101 102 103
        {
            if ( !mDocument->canRemovePageAnnotation( pair.annotation ) )
                action->setEnabled( false );
        }
104

Laurent Montel's avatar
Laurent Montel committed
105
        action = menu.addAction( QIcon::fromTheme( QStringLiteral("configure") ), i18n( "&Properties" ) );
106
        action->setData( QVariant::fromValue( pair ) );
107
        action->setEnabled( onlyOne );
108 109
        action->setProperty( actionTypeId, propertiesId );

110
        if ( onlyOne && annotationHasFileAttachment( pair.annotation ) )
111
        {
112 113 114 115
            const Okular::EmbeddedFile *embeddedFile = embeddedFileFromAnnotation( pair.annotation );
            if ( embeddedFile )
            {
                const QString saveText = i18nc( "%1 is the name of the file to save", "&Save '%1'...", embeddedFile->name() );
116

117
                menu.addSeparator();
Laurent Montel's avatar
Laurent Montel committed
118
                action = menu.addAction( QIcon::fromTheme( QStringLiteral("document-save") ), saveText );
119 120 121
                action->setData( QVariant::fromValue( pair ) );
                action->setProperty( actionTypeId, saveId );
            }
122
        }
123
    }
124 125
    else
    {
126
        for ( const AnnotPagePair &pair : qAsConst(mAnnotations) )
127
        {
128
            menu.addAction( new OKMenuTitle( &menu, GuiUtils::captionForAnnotation( pair.annotation ) ) );
129

Laurent Montel's avatar
Laurent Montel committed
130
            action = menu.addAction( QIcon::fromTheme( QStringLiteral("comment") ), i18n( "&Open Pop-up Note" ) );
131 132 133
            action->setData( QVariant::fromValue( pair ) );
            action->setProperty( actionTypeId, openId );

Laurent Montel's avatar
Laurent Montel committed
134
            action = menu.addAction( QIcon::fromTheme( QStringLiteral("list-remove") ), i18n( "&Delete" ) );
135 136 137 138 139
            action->setEnabled( mDocument->isAllowed( Okular::AllowNotes ) &&
                                mDocument->canRemovePageAnnotation( pair.annotation ) );
            action->setData( QVariant::fromValue( pair ) );
            action->setProperty( actionTypeId, deleteId );

Laurent Montel's avatar
Laurent Montel committed
140
            action = menu.addAction( QIcon::fromTheme( QStringLiteral("configure") ), i18n( "&Properties" ) );
141 142 143
            action->setData( QVariant::fromValue( pair ) );
            action->setProperty( actionTypeId, propertiesId );

144
            if ( annotationHasFileAttachment( pair.annotation ) )
145
            {
146 147 148 149 150 151
                const Okular::EmbeddedFile *embeddedFile = embeddedFileFromAnnotation( pair.annotation );
                if ( embeddedFile )
                {
                    const QString saveText = i18nc( "%1 is the name of the file to save", "&Save '%1'...", embeddedFile->name() );

                    menu.addSeparator();
Laurent Montel's avatar
Laurent Montel committed
152
                    action = menu.addAction( QIcon::fromTheme( QStringLiteral("document-save") ), saveText );
153 154 155
                    action->setData( QVariant::fromValue( pair ) );
                    action->setProperty( actionTypeId, saveId );
                }
156 157 158
            }
        }
    }
159

160 161 162 163
    QAction *choice = menu.exec( point.isNull() ? QCursor::pos() : point );

    // check if the user really selected an action
    if ( choice ) {
164 165 166 167 168 169 170 171
        const AnnotPagePair pair = choice->data().value<AnnotPagePair>();

        const QString actionType = choice->property( actionTypeId ).toString();
        if ( actionType == openId ) {
            emit openAnnotationWindow( pair.annotation, pair.pageNumber );
        } else if( actionType == deleteId ) {
            if ( pair.pageNumber != -1 )
                mDocument->removePageAnnotation( pair.pageNumber, pair.annotation );
172
        } else if( actionType == deleteAllId ) {
173
            for ( const AnnotPagePair &pair : qAsConst(mAnnotations) )
174 175 176 177
            {
                if ( pair.pageNumber != -1 )
                    mDocument->removePageAnnotation( pair.pageNumber, pair.annotation );
            }
178 179 180
        } else if( actionType == propertiesId ) {
            if ( pair.pageNumber != -1 ) {
                AnnotsPropertiesDialog propdialog( mParent, mDocument, pair.pageNumber, pair.annotation );
181 182
                propdialog.exec();
            }
183
        } else if( actionType == saveId ) {
184 185
            Okular::EmbeddedFile *embeddedFile = embeddedFileFromAnnotation( pair.annotation );
            GuiUtils::saveEmbeddedFile( embeddedFile, mParent );
186 187 188
        }
    }
}