File indexing completed on 2023-10-01 08:39:27

0001 /***************************************************************************
0002  *   Copyright (C) 2009 Matthias Fuchs <mat69@gmx.net>                     *
0003  *                                                                         *
0004  *   This program is free software; you can redistribute it and/or modify  *
0005  *   it under the terms of the GNU General Public License as published by  *
0006  *   the Free Software Foundation; either version 2 of the License, or     *
0007  *   (at your option) any later version.                                   *
0008  *                                                                         *
0009  *   This program is distributed in the hope that it will be useful,       *
0010  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
0011  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
0012  *   GNU General Public License for more details.                          *
0013  *                                                                         *
0014  *   You should have received a copy of the GNU General Public License     *
0015  *   along with this program; if not, write to the                         *
0016  *   Free Software Foundation, Inc.,                                       *
0017  *   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA .        *
0018  ***************************************************************************/
0019 
0020 #ifndef FILEMODEL_H
0021 #define FILEMODEL_H
0022 
0023 #include "kget_export.h"
0024 #include "transfer.h"
0025 
0026 #include <QUrl>
0027 
0028 #include <QAbstractItemModel>
0029 #include <QList>
0030 #include <QVariant>
0031 
0032 #include <QIcon>
0033 #include <kio/global.h>
0034 
0035 class FileModel;
0036 
0037 class KGET_EXPORT FileItem
0038 {
0039 public:
0040     explicit FileItem(const QString &name, FileItem *parent = nullptr);
0041     ~FileItem();
0042 
0043     enum DataType { File = 0, Status, Size, ChecksumVerified, SignatureVerified };
0044 
0045     void appendChild(FileItem *child);
0046 
0047     FileItem *child(int row);
0048     int childCount() const;
0049     /**
0050      * Returns true if the index represents a file
0051      */
0052     bool isFile() const;
0053     int columnCount() const;
0054     QVariant data(int column, int role) const;
0055     bool setData(int column, const QVariant &value, FileModel *model, int role = Qt::EditRole);
0056     int row() const;
0057     FileItem *parent();
0058 
0059 private:
0060     /**
0061      * Add the totalsize to the parent
0062      */
0063     void addSize(KIO::fileoffset_t size, FileModel *model);
0064 
0065     /**
0066      * If all siblings of this have the same state the parent of item will also be set
0067      * to that state
0068      */
0069     void checkParents(Qt::CheckState state, FileModel *model);
0070 
0071     /**
0072      * All children of item will be set to state
0073      */
0074     void checkChildren(Qt::CheckState state, FileModel *model);
0075 
0076 private:
0077     QList<FileItem *> m_childItems;
0078     mutable QIcon m_mimeType;
0079     QString m_name;
0080     Qt::CheckState m_state;
0081     Job::Status m_status;
0082     KIO::fileoffset_t m_totalSize;
0083     int m_checkusmVerified;
0084     int m_signatureVerified;
0085     FileItem *m_parent;
0086 };
0087 
0088 /**
0089  * This model represents the files that are being downloaded
0090  * @note whenever a method takes a url as argument use the url to the file
0091  * destination on your hard disk, the file does not need to exist though
0092  */
0093 
0094 class KGET_EXPORT FileModel : public QAbstractItemModel
0095 {
0096     Q_OBJECT
0097 
0098     friend class FileItem;
0099 
0100 public:
0101     FileModel(const QList<QUrl> &files, const QUrl &destDirectory, QObject *parent = nullptr);
0102     ~FileModel() override;
0103 
0104     QVariant data(const QModelIndex &index, int role) const override;
0105     bool setData(const QModelIndex &index, const QVariant &value, int role = Qt::EditRole) override;
0106     Qt::ItemFlags flags(const QModelIndex &index) const override;
0107     QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override;
0108     QModelIndex index(int row, int column, const QModelIndex &parent = QModelIndex()) const override;
0109     QModelIndex index(const QUrl &file, int column);
0110     QModelIndex parent(const QModelIndex &index) const override;
0111     int rowCount(const QModelIndex &parent = QModelIndex()) const override;
0112     int columnCount(const QModelIndex &parent = QModelIndex()) const override;
0113 
0114     void rename(const QModelIndex &file, const QString &newName);
0115 
0116     /**
0117      * Returns a list of pointers to all files of this model
0118      * @note it would be possible to directly interact with the model data that way,
0119      * though that is discouraged
0120      */
0121     QModelIndexList fileIndexes(int column) const;
0122 
0123     /**
0124      * The url on the filesystem (no check if the file exists yet!) of index,
0125      * it can be a folder or file
0126      */
0127     QUrl getUrl(const QModelIndex &index);
0128 
0129     /**
0130      * Set the url to the directory the files are stored in, the filemodel stores
0131      * its entries as relative path to the base directory
0132      * @param newDirectory the base directory for the model
0133      */
0134     void setDirectory(const QUrl &newDirectory);
0135 
0136     /**
0137      * Set a custom status text for status
0138      * @note QString() removes the custom text for status
0139      */
0140     void setCustomStatusText(Job::Status status, const QString &text);
0141 
0142     /**
0143      * Set a custom status icon for status
0144      * @note QIcon() removes the custom icon for status
0145      */
0146     void setCustomStatusIcon(Job::Status status, const QIcon &icon);
0147 
0148     /**
0149      * Checks if the download for file has been finished
0150      */
0151     bool downloadFinished(const QUrl &file);
0152 
0153     /**
0154      * Returns true if the index represents a file
0155      */
0156     bool isFile(const QModelIndex &index) const;
0157 
0158 public Q_SLOTS:
0159     /**
0160      * Watches if the check state changes, the result of that will be emitted
0161      * when stopWatchCheckState() is being called()
0162      */
0163     void watchCheckState();
0164 
0165     /**
0166      * Emits checkStateChanged if a CheckState of an entry changed
0167      */
0168     void stopWatchCheckState();
0169 
0170 Q_SIGNALS:
0171     void rename(const QUrl &oldUrl, const QUrl &newUrl);
0172     void checkStateChanged();
0173     void fileFinished(const QUrl &file);
0174 
0175 private:
0176     void setupModelData(const QList<QUrl> &files);
0177 
0178     /**
0179      * The url on the filesystem (no check if the file exists yet!) of item,
0180      * it can be a folder or file
0181      */
0182     QUrl getUrl(FileItem *item);
0183 
0184     /**
0185      * Get the path of item
0186      * @note path means here the part between m_destDirectory and the filename
0187      * e.g. m_destDirectory = "file:///home/user/Downloads", path = "Great Album/",
0188      * filename = "Song 1.ogg"
0189      */
0190     QString getPath(FileItem *item);
0191 
0192     /**
0193      * Get the item of the corresponding url
0194      */
0195     FileItem *getItem(const QUrl &file);
0196 
0197     void changeData(int row, int column, FileItem *item, bool fileFinished = false);
0198 
0199 private Q_SLOTS:
0200     void renameFailed(const QUrl &beforeRename, const QUrl &afterRename);
0201 
0202 private:
0203     FileItem *m_rootItem;
0204     QUrl m_destDirectory;
0205     QList<QVariant> m_header;
0206     bool m_checkStateChanged;
0207 
0208     QHash<QUrl, FileItem *> m_itemCache; // used to make getItem faster
0209 
0210     /**
0211      * Stores links to all files
0212      */
0213     QList<FileItem *> m_files;
0214 
0215     QHash<Job::Status, QString> m_customStatusTexts;
0216     QHash<Job::Status, QIcon> m_customStatusIcons;
0217 };
0218 
0219 #endif