Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. How To Install Custom Icon in QFileDialog
QtWS25 Last Chance

How To Install Custom Icon in QFileDialog

Scheduled Pinned Locked Moved Solved General and Desktop
3 Posts 2 Posters 1.6k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • K Offline
    K Offline
    kendavistoo
    wrote on last edited by
    #1

    In order to make my project folders distinguishable I have added a ".PjtsZr" suffix to their name. When I call QFileDialog to select one of these folders, I want them to have a different folder icon within the dialog. I use the following to use the QFileDialog:

        QFileDialog dialog(this,  "Select Project Directory", "~/");
        dialog.setFileMode(QFileDialog::DirectoryOnly);
        dialog.setOption(QFileDialog::DontUseNativeDialog, true);
        dialog.setWindowFlags(Qt::Dialog);
        dialog.setViewMode(QFileDialog::List);
    
        QString dirPath;
    
        if (dialog.exec() == QDialog::Accepted) {
            dirPath = dialog.selectedFiles().value(0);
        }
    
        QDir dir(dirPath);
    

    It has been suggested on the internet to use the QSortFilterProxyModel Class to see the items of the QFileDialog, and this seems to work. But, once I detect a directory with the ".PjtsZr" extension, how do I change its icon?

    //---------- filterAcceptsRow ----------
    
    bool PjtFileFilterProxyModel::filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const
    {
        QModelIndex index0 = sourceModel()->index(sourceRow, 0, sourceParent);
        QFileSystemModel* fileModel = qobject_cast<QFileSystemModel*>(sourceModel());
    
        QString p = QDir::homePath();
        QString homeName = gLastNameOfPath(p);
    
        //----------
    
        if (fileModel!=NULL && fileModel->isDir(index0))
        {
            QString modelStr = fileModel->fileName(index0);
    
            if (modelStr.compare(homeName) == 0){
                qDebug() << "HELLO PROXY   home:    "<<modelStr;
                return true;
            }//if
    
            //----------
    
            if (modelStr.endsWith("PjtsZr")){
    
                qDebug()<<"GOT ONE!!!     "<<fileModel->filePath(index0);
    
                QString pjtDirPath = fileModel->filePath(index0);
                QDir pjtDir(pjtDirPath);
    
                return true;
            }//if
    
            return true;
        }//if
    
        else{
            return false;
        }//else
    
        // uncomment below to execute default implementation
        //return QSortFilterProxyModel::filterAcceptsRow(sourceRow, sourceParent);
    }
    
    1 Reply Last reply
    0
    • Christian EhrlicherC Offline
      Christian EhrlicherC Offline
      Christian Ehrlicher
      Lifetime Qt Champion
      wrote on last edited by
      #2

      You can set your proxy model with http://doc.qt.io/qt-5/qfiledialog.html#setProxyModel

      Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
      Visit the Qt Academy at https://academy.qt.io/catalog

      1 Reply Last reply
      2
      • K Offline
        K Offline
        kendavistoo
        wrote on last edited by
        #3

        Thanks, Christian Ehrlicher, your suggestion was essential.

        I finally solved the problem. Notice that globals.h contains all of the nic-nak Qt "#include"'s necessary to make it work.

        pjticonprovider.h:

        #ifndef GLOBALS_H
        #include "globals.h"
        #endif
        
        const static int    PV_FILE_FOLDER   = 0;
        const static int    PV_PINK_FOLDER   = 1;
        const static int    PV_OOPS          = 2;
        
        class PjtIconProvider : public QFileIconProvider
        {
        public:
            PjtIconProvider();
            ~PjtIconProvider();
        
            //QIcon icon( const QFileInfo & info ) const;
        
            QIcon icon(const QFileInfo & info) const;
        
        private:
            QIcon pinkFolder;
            QIcon defaultFolder;
            QIcon oopsIcon;
        };
        

        pjticonprovider.cpp:

        #include "pjticonprovider.h"
        
        //---------- CONSTRUCTOR PjtIconProvider -----------
        PjtIconProvider :: PjtIconProvider()
        {
            qDebug()<<"CONSTRUCTOR PjtIconProvider";
        
            defaultFolder = QIcon(":/Icons/FolderIcon.svg");
            pinkFolder    = QIcon(":/Icons/PinkIcon.png");
            oopsIcon      = QIcon(":/Icons/OopsIcon.png");
        }
        //---------- DESTRUCTOR ~PjtIconProvider -----------
        PjtIconProvider :: ~PjtIconProvider()
        {
            qDebug()<<"DESTRUCTOR PjtIconProvider";
        }
        //---------- icon -----------
        QIcon PjtIconProvider :: icon( const QFileInfo & info) const
        {
            QString name = info.fileName();
        
            if (name.endsWith("PjtsZr")){
                return pinkFolder;
            }//if
        
            else if(( ! name.isEmpty()) and ( ! name.isNull())){
                return defaultFolder;
            }//elseif
        
            return oopsIcon;
        

        pjtfilefilterproxymodel.h:

        #ifndef PJTICONPROVIDER_H
        #include "pjticonprovider.h"
        #endif
        
        #ifndef GLOBALS_H
        #include "globals.h"
        #endif
        
        class PjtFileFilterProxyModel : public QSortFilterProxyModel
        {
            Q_OBJECT
        public:
            PjtFileFilterProxyModel();
            ~PjtFileFilterProxyModel();
        
            PjtIconProvider *provider;
        protected:
            virtual bool filterAcceptsRow(int source_row, const QModelIndex& source_parent) const;
        };
        

        pjtfilefilterproxymodel.cpp:

        #include "pjtfilefilterproxymodel.h"
        
        //---------- CONSTRUCTOR PjtFileFilterProxyModel ----------
        PjtFileFilterProxyModel :: PjtFileFilterProxyModel()
        {
            qDebug()<<"CONSTRUCTOR PjtFileFilterProxyModel";
        
            provider = new PjtIconProvider();
        }
        
        //---------- DESTRUCTOR PjtFileFilterProxyModel ----------
        PjtFileFilterProxyModel :: ~PjtFileFilterProxyModel()
        {
            qDebug()<<"DESTRUCTOR PjtFileFilterProxyModel";
        
            delete provider;
        }
        
        //---------- filterAcceptsRow ----------
        bool PjtFileFilterProxyModel::filterAcceptsRow(int sourceRow, const QModelIndex &sourceParent) const
        {
            QModelIndex index0 = sourceModel()->index(sourceRow, 0, sourceParent);
            QFileSystemModel* fileModel = qobject_cast<QFileSystemModel*>(sourceModel());
        
            fileModel->setIconProvider(provider);
        
        QFileInfo info = fileModel->fileInfo(index0);
        qDebug()<<info.fileName();
        
            return true;
        
            // uncomment below to execute default implementation
            //return QSortFilterProxyModel::filterAcceptsRow(sourceRow, sourceParent);
        }
        

        Notice that the UI of the QFileDialog still is awkward, but will be fixed soon. Here is the slot within MainWindow which handles the dialog:

        //---------- SLOT openProject ----------
        void MainWindow :: SlotOpenProject()
        {
            qDebug()<<"    openProject";
        
            statusMessageKey = S_OPEN_A_PROJECT;
            doFreshStatusMessage = true;
        
            QString     dirPath;
        
            QFileDialog dialog(this, "Select Project Directory", "/home" );
            dialog.setNameFilter("*/PjtsZr");
            dialog.setOption( QFileDialog::DontUseNativeDialog );
            dialog.setOption( QFileDialog::ShowDirsOnly );
            dialog.setOption( QFileDialog::DontResolveSymlinks );
        
            PjtFileFilterProxyModel* proxyModel = new PjtFileFilterProxyModel();
            dialog.setProxyModel(proxyModel);
        
            QDialogButtonBox *button_box = findChild<QDialogButtonBox *>();
            button_box->addButton("Select", QDialogButtonBox::AcceptRole);
        
            dialog.exec();
        
            QStringList sList = dialog.selectedFiles();
            QString selectedPjt( sList.at(0) );
        
        qDebug()<<"<<<<<<<<<<<<<<<<<<<<<<<<<<<      selected:  "<<selectedPjt;
        
        }//openProject
        
        1 Reply Last reply
        0

        • Login

        • Login or register to search.
        • First post
          Last post
        0
        • Categories
        • Recent
        • Tags
        • Popular
        • Users
        • Groups
        • Search
        • Get Qt Extensions
        • Unsolved