File indexing completed on 2024-04-14 03:55:30

0001 /*
0002     SPDX-FileCopyrightText: 2003 Christoph Cullmann <cullmann@kde.org>
0003 
0004     SPDX-License-Identifier: LGPL-2.0-or-later
0005 */
0006 
0007 #ifndef KATE_CONFIG_H
0008 #define KATE_CONFIG_H
0009 
0010 #include <ktexteditor_export.h>
0011 
0012 #include <ktexteditor/document.h>
0013 #include <ktexteditor/view.h>
0014 
0015 #include <functional>
0016 #include <map>
0017 #include <memory>
0018 
0019 #include <QBitArray>
0020 #include <QColor>
0021 #include <QList>
0022 #include <QObject>
0023 
0024 class KConfigGroup;
0025 namespace KTextEditor
0026 {
0027 class ViewPrivate;
0028 }
0029 namespace KTextEditor
0030 {
0031 class DocumentPrivate;
0032 }
0033 class KateRenderer;
0034 
0035 namespace KTextEditor
0036 {
0037 class EditorPrivate;
0038 }
0039 
0040 class KConfig;
0041 
0042 /**
0043  * Base Class for the Kate Config Classes
0044  * Current childs are KateDocumentConfig/KateDocumentConfig/KateDocumentConfig
0045  */
0046 class KTEXTEDITOR_EXPORT KateConfig
0047 {
0048 public:
0049     /**
0050      * Start some config changes.
0051      * This method is needed to init some kind of transaction for config changes,
0052      * update will only be done once, at configEnd() call.
0053      */
0054     void configStart();
0055 
0056     /**
0057      * End a config change transaction, update the concerned
0058      * KateDocumentConfig/KateDocumentConfig/KateDocumentConfig
0059      */
0060     void configEnd();
0061 
0062     /**
0063      * Is this a global config object?
0064      * @return true when this is a global config object
0065      */
0066     bool isGlobal() const
0067     {
0068         return !m_parent;
0069     }
0070 
0071     /**
0072      * All known config keys.
0073      * This will use the knowledge about all registered keys of the global object.
0074      * @return all known config keys
0075      */
0076     QStringList configKeys() const
0077     {
0078         return m_parent ? m_parent->configKeys() : *m_configKeys.get();
0079     }
0080 
0081     /**
0082      * Is given key set in this config object?
0083      * @param key config key, aka enum from KateConfig* classes
0084      * @return is the wanted key set?
0085      */
0086     bool isSet(const int key) const
0087     {
0088         return m_configEntries.find(key) != m_configEntries.end();
0089     }
0090 
0091     /**
0092      * Get a config value.
0093      * @param key config key, aka enum from KateConfig* classes
0094      * @return value for the wanted key, will assert if key is not valid
0095      */
0096     QVariant value(const int key) const;
0097 
0098     /**
0099      * Set a config value.
0100      * Will assert if key is invalid.
0101      * Might not alter the value if given value fails validation.
0102      * @param key config key, aka enum from KateConfig* classes
0103      * @param value value to set
0104      * @return true on success
0105      */
0106     bool setValue(const int key, const QVariant &value);
0107 
0108     /**
0109      * Get a config value for the string key.
0110      * @param key config key, aka commandName from KateConfig* classes
0111      * @return value for the wanted key, will return invalid variant if key is not known
0112      */
0113     QVariant value(const QString &key) const;
0114 
0115     /**
0116      * Set a config value.
0117      * Will do nothing if key is not known or the given value fails validation.
0118      * @param key config key, aka commandName from KateConfig* classes
0119      * @param value value to set
0120      * @return true on success
0121      */
0122     bool setValue(const QString &key, const QVariant &value);
0123 
0124 protected:
0125     /**
0126      * Construct a KateConfig.
0127      * @param parent parent config object, if any
0128      */
0129     KateConfig(const KateConfig *parent = nullptr);
0130 
0131     /**
0132      * Virtual Destructor
0133      */
0134     virtual ~KateConfig();
0135 
0136     /**
0137      * One config entry.
0138      */
0139     class ConfigEntry
0140     {
0141     public:
0142         /**
0143          * Construct one config entry.
0144          * @param enumId value of the enum for this config entry
0145          * @param configId value of the key for the KConfig file for this config entry
0146          * @param command command name
0147          * @param defaultVal default value
0148          * @param valid validator function, default none
0149          */
0150         ConfigEntry(int enumId, const char *configId, QString command, QVariant defaultVal, std::function<bool(const QVariant &)> valid = nullptr)
0151             : enumKey(enumId)
0152             , configKey(configId)
0153             , commandName(command)
0154             , defaultValue(defaultVal)
0155             , value(defaultVal)
0156             , validator(valid)
0157         {
0158         }
0159 
0160         /**
0161          * Enum key for this config entry, shall be unique
0162          */
0163         const int enumKey;
0164 
0165         /**
0166          * KConfig entry key for this config entry, shall be unique in its group
0167          * e.g. "Tab Width"
0168          */
0169         const char *const configKey;
0170 
0171         /**
0172          * Command name as used in e.g. ConfigInterface or modeline/command line
0173          * e.g. tab-width
0174          */
0175         const QString commandName;
0176 
0177         /**
0178          * Default value if nothing special was configured
0179          */
0180         const QVariant defaultValue;
0181 
0182         /**
0183          * The concrete value, per default == defaultValue
0184          */
0185         QVariant value;
0186 
0187         /**
0188          * An optional validator function, only when these returns true
0189          * we accept a given new value.
0190          * Is no validator set, we accept any value.
0191          */
0192         std::function<bool(const QVariant &)> validator;
0193     };
0194 
0195     /**
0196      * Read all config entries from given config group.
0197      * @param config config group to read from
0198      */
0199     void readConfigEntries(const KConfigGroup &config);
0200 
0201     /**
0202      * Write all config entries to given config group.
0203      * @param config config group to write to
0204      */
0205     void writeConfigEntries(KConfigGroup &config) const;
0206 
0207     /**
0208      * Register a new config entry.
0209      * Used by the sub classes to register all there known ones.
0210      * @param entry new entry to add
0211      */
0212     void addConfigEntry(ConfigEntry &&entry);
0213 
0214     /**
0215      * Finalize the config entries.
0216      * Called by the sub classes after all entries are registered
0217      */
0218     void finalizeConfigEntries();
0219 
0220     /**
0221      * do the real update
0222      */
0223     virtual void updateConfig() = 0;
0224 
0225 private:
0226     /**
0227      * Get full map of config entries, aka the m_configEntries of the top config object
0228      * @return full map with all config entries
0229      */
0230     const std::map<int, ConfigEntry> &fullConfigEntries() const
0231     {
0232         return m_parent ? m_parent->fullConfigEntries() : m_configEntries;
0233     }
0234     /**
0235      * Get hash of config entries, aka the m_configKeyToEntry of the top config object
0236      * @return full hash with all config entries
0237      */
0238     const QHash<QString, const ConfigEntry *> &fullConfigKeyToEntry() const
0239     {
0240         return m_parent ? m_parent->fullConfigKeyToEntry() : *m_configKeyToEntry.get();
0241     }
0242 
0243 private:
0244     /**
0245      * parent config object, if any
0246      */
0247     const KateConfig *const m_parent = nullptr;
0248 
0249     /**
0250      * two cases:
0251      *   - we have m_parent == nullptr => this contains all known config entries
0252      *   - we have m_parent != nullptr => this contains all set config entries for this level of configuration
0253      *
0254      * uses a map ATM for deterministic iteration e.g. for read/writeConfig
0255      */
0256     std::map<int, ConfigEntry> m_configEntries;
0257 
0258     /**
0259      * All known config keys, filled only for the object with m_parent == nullptr
0260      */
0261     std::unique_ptr<QStringList> m_configKeys;
0262 
0263     /**
0264      * Hash of config keys => config entry, filled only for the object with m_parent == nullptr
0265      */
0266     std::unique_ptr<QHash<QString, const ConfigEntry *>> m_configKeyToEntry;
0267 
0268 protected:
0269     /**
0270      * recursion depth
0271      */
0272     int configSessionNumber = 0;
0273 };
0274 
0275 class KTEXTEDITOR_EXPORT KateGlobalConfig : public KateConfig
0276 {
0277 private:
0278     friend class KTextEditor::EditorPrivate;
0279 
0280     /**
0281      * only used in KTextEditor::EditorPrivate for the static global fallback !!!
0282      */
0283     KateGlobalConfig();
0284 
0285 public:
0286     static KateGlobalConfig *global()
0287     {
0288         return s_global;
0289     }
0290 
0291     /**
0292      * Known config entries
0293      */
0294     enum ConfigEntryTypes {
0295         /**
0296          * Encoding prober
0297          */
0298         EncodingProberType,
0299 
0300         /**
0301          * Fallback encoding
0302          */
0303         FallbackEncoding
0304     };
0305 
0306 public:
0307     /**
0308      * Read config from object
0309      */
0310     void readConfig(const KConfigGroup &config);
0311 
0312     /**
0313      * Write config to object
0314      */
0315     void writeConfig(KConfigGroup &config);
0316 
0317 protected:
0318     void updateConfig() override;
0319 
0320 public:
0321     QString fallbackEncoding() const
0322     {
0323         return value(FallbackEncoding).toString();
0324     }
0325 
0326     bool setFallbackEncoding(const QString &encoding)
0327     {
0328         return setValue(FallbackEncoding, encoding);
0329     }
0330 
0331 private:
0332     static KateGlobalConfig *s_global;
0333 };
0334 
0335 class KTEXTEDITOR_EXPORT KateDocumentConfig : public KateConfig
0336 {
0337 private:
0338     friend class KTextEditor::EditorPrivate;
0339 
0340     KateDocumentConfig();
0341 
0342 public:
0343     /**
0344      * Construct a DocumentConfig
0345      */
0346     explicit KateDocumentConfig(KTextEditor::DocumentPrivate *doc);
0347 
0348     inline static KateDocumentConfig *global()
0349     {
0350         return s_global;
0351     }
0352 
0353     /**
0354      * Known config entries
0355      */
0356     enum ConfigEntryTypes {
0357         /**
0358          * Tabulator width
0359          */
0360         TabWidth,
0361 
0362         /**
0363          * Indentation width
0364          */
0365         IndentationWidth,
0366 
0367         /**
0368          * On-the-fly spellcheck enabled?
0369          */
0370         OnTheFlySpellCheck,
0371 
0372         /**
0373          * Indent pasted text?
0374          */
0375         IndentOnTextPaste,
0376 
0377         /**
0378          * Replace tabs with spaces?
0379          */
0380         ReplaceTabsWithSpaces,
0381 
0382         /**
0383          * Backup files for local files?
0384          */
0385         BackupOnSaveLocal,
0386 
0387         /**
0388          * Backup files for remote files?
0389          */
0390         BackupOnSaveRemote,
0391 
0392         /**
0393          * Prefix for backup files
0394          */
0395         BackupOnSavePrefix,
0396 
0397         /**
0398          * Suffix for backup files
0399          */
0400         BackupOnSaveSuffix,
0401 
0402         /**
0403          * Indentation mode, like "normal"
0404          */
0405         IndentationMode,
0406 
0407         /**
0408          * Tab handling, like indent, insert tab, smart
0409          */
0410         TabHandlingMode,
0411 
0412         /**
0413          * Static word wrap?
0414          */
0415         StaticWordWrap,
0416 
0417         /**
0418          * Static word wrap column
0419          */
0420         StaticWordWrapColumn,
0421 
0422         /**
0423          * PageUp/Down moves cursor?
0424          */
0425         PageUpDownMovesCursor,
0426 
0427         /**
0428          * Smart Home key?
0429          */
0430         SmartHome,
0431 
0432         /**
0433          * Show Tabs?
0434          */
0435         ShowTabs,
0436 
0437         /**
0438          * Indent on tab?
0439          */
0440         IndentOnTab,
0441 
0442         /**
0443          * Keep extra space?
0444          */
0445         KeepExtraSpaces,
0446 
0447         /**
0448          * Backspace key indents?
0449          */
0450         BackspaceIndents,
0451 
0452         /**
0453          * Show spaces mode like none, all, ...
0454          */
0455         ShowSpacesMode,
0456 
0457         /**
0458          * Trailing Marker Size
0459          */
0460         TrailingMarkerSize,
0461 
0462         /**
0463          * Remove spaces mode
0464          */
0465         RemoveSpacesMode,
0466 
0467         /**
0468          * Ensure newline at end of file
0469          */
0470         NewlineAtEOF,
0471 
0472         /**
0473          * Overwrite mode?
0474          */
0475         OverwriteMode,
0476 
0477         /**
0478          * Encoding
0479          */
0480         Encoding,
0481 
0482         /**
0483          * End of line mode: dos, mac, unix
0484          */
0485         EndOfLine,
0486 
0487         /**
0488          * Allow EOL detection
0489          */
0490         AllowEndOfLineDetection,
0491 
0492         /**
0493          * Use Byte Order Mark
0494          */
0495         ByteOrderMark,
0496 
0497         /**
0498          * Swap file mode
0499          */
0500         SwapFile,
0501 
0502         /**
0503          * Swap file directory
0504          */
0505         SwapFileDirectory,
0506 
0507         /**
0508          * Swap file sync interval
0509          */
0510         SwapFileSyncInterval,
0511 
0512         /**
0513          * Line length limit
0514          */
0515         LineLengthLimit,
0516 
0517         /**
0518          * Camel Cursor Movement?
0519          */
0520         CamelCursor,
0521 
0522         /**
0523          * Automatically detect file indentation
0524          */
0525         AutoDetectIndent,
0526 
0527         /**
0528          * Automatically save?
0529          */
0530         AutoSave,
0531         /**
0532          * Automatically save on focus lost
0533          */
0534         AutoSaveOnFocusOut,
0535         /**
0536          * Auto save interval
0537          */
0538         AutoSaveInteral,
0539 
0540         /**
0541          * Should we auto-reload if the old state is in version control?
0542          */
0543         AutoReloadIfStateIsInVersionControl
0544     };
0545 
0546 public:
0547     /**
0548      * Read config from object
0549      */
0550     void readConfig(const KConfigGroup &config);
0551 
0552     /**
0553      * Write config to object
0554      */
0555     void writeConfig(KConfigGroup &config);
0556 
0557 protected:
0558     void updateConfig() override;
0559 
0560 public:
0561     int tabWidth() const
0562     {
0563         return value(TabWidth).toInt();
0564     }
0565 
0566     void setTabWidth(int tabWidth)
0567     {
0568         setValue(TabWidth, QVariant(tabWidth));
0569     }
0570 
0571     int indentationWidth() const
0572     {
0573         return value(IndentationWidth).toInt();
0574     }
0575 
0576     void setIndentationWidth(int indentationWidth)
0577     {
0578         setValue(IndentationWidth, QVariant(indentationWidth));
0579     }
0580 
0581     bool onTheFlySpellCheck() const
0582     {
0583         return value(OnTheFlySpellCheck).toBool();
0584     }
0585 
0586     void setOnTheFlySpellCheck(bool on)
0587     {
0588         setValue(OnTheFlySpellCheck, QVariant(on));
0589     }
0590 
0591     bool indentPastedText() const
0592     {
0593         return value(IndentOnTextPaste).toBool();
0594     }
0595 
0596     void setIndentPastedText(bool on)
0597     {
0598         setValue(IndentOnTextPaste, QVariant(on));
0599     }
0600 
0601     bool replaceTabsDyn() const
0602     {
0603         return value(ReplaceTabsWithSpaces).toBool();
0604     }
0605 
0606     void setReplaceTabsDyn(bool on)
0607     {
0608         setValue(ReplaceTabsWithSpaces, QVariant(on));
0609     }
0610 
0611     bool backupOnSaveLocal() const
0612     {
0613         return value(BackupOnSaveLocal).toBool();
0614     }
0615 
0616     void setBackupOnSaveLocal(bool on)
0617     {
0618         setValue(BackupOnSaveLocal, QVariant(on));
0619     }
0620 
0621     bool backupOnSaveRemote() const
0622     {
0623         return value(BackupOnSaveRemote).toBool();
0624     }
0625 
0626     void setBackupOnSaveRemote(bool on)
0627     {
0628         setValue(BackupOnSaveRemote, QVariant(on));
0629     }
0630 
0631     QString backupPrefix() const
0632     {
0633         return value(BackupOnSavePrefix).toString();
0634     }
0635 
0636     void setBackupPrefix(const QString &prefix)
0637     {
0638         setValue(BackupOnSavePrefix, QVariant(prefix));
0639     }
0640 
0641     QString backupSuffix() const
0642     {
0643         return value(BackupOnSaveSuffix).toString();
0644     }
0645 
0646     void setBackupSuffix(const QString &suffix)
0647     {
0648         setValue(BackupOnSaveSuffix, QVariant(suffix));
0649     }
0650 
0651     QString indentationMode() const
0652     {
0653         return value(IndentationMode).toString();
0654     }
0655 
0656     void setIndentationMode(const QString &identationMode)
0657     {
0658         setValue(IndentationMode, identationMode);
0659     }
0660 
0661     enum TabHandling {
0662         tabInsertsTab = 0,
0663         tabIndents = 1,
0664         tabSmart = 2 //!< indents in leading space, otherwise inserts tab
0665     };
0666 
0667     enum WhitespaceRendering { None, Trailing, All };
0668 
0669     int tabHandling() const
0670     {
0671         return value(TabHandlingMode).toInt();
0672     }
0673 
0674     void setTabHandling(int tabHandling)
0675     {
0676         setValue(TabHandlingMode, tabHandling);
0677     }
0678 
0679     bool wordWrap() const
0680     {
0681         return value(StaticWordWrap).toBool();
0682     }
0683 
0684     void setWordWrap(bool on)
0685     {
0686         setValue(StaticWordWrap, on);
0687     }
0688 
0689     int wordWrapAt() const
0690     {
0691         return value(StaticWordWrapColumn).toInt();
0692     }
0693 
0694     void setWordWrapAt(int col)
0695     {
0696         setValue(StaticWordWrapColumn, col);
0697     }
0698 
0699     bool pageUpDownMovesCursor() const
0700     {
0701         return value(PageUpDownMovesCursor).toBool();
0702     }
0703 
0704     void setPageUpDownMovesCursor(bool on)
0705     {
0706         setValue(PageUpDownMovesCursor, on);
0707     }
0708 
0709     void setKeepExtraSpaces(bool on)
0710     {
0711         setValue(KeepExtraSpaces, on);
0712     }
0713 
0714     bool keepExtraSpaces() const
0715     {
0716         return value(KeepExtraSpaces).toBool();
0717     }
0718 
0719     void setBackspaceIndents(bool on)
0720     {
0721         setValue(BackspaceIndents, on);
0722     }
0723 
0724     bool backspaceIndents() const
0725     {
0726         return value(BackspaceIndents).toBool();
0727     }
0728 
0729     void setSmartHome(bool on)
0730     {
0731         setValue(SmartHome, on);
0732     }
0733 
0734     bool smartHome() const
0735     {
0736         return value(SmartHome).toBool();
0737     }
0738 
0739     void setShowTabs(bool on)
0740     {
0741         setValue(ShowTabs, on);
0742     }
0743 
0744     bool showTabs() const
0745     {
0746         return value(ShowTabs).toBool();
0747     }
0748 
0749     void setShowSpaces(WhitespaceRendering mode)
0750     {
0751         setValue(ShowSpacesMode, mode);
0752     }
0753 
0754     WhitespaceRendering showSpaces() const
0755     {
0756         return WhitespaceRendering(value(ShowSpacesMode).toInt());
0757     }
0758 
0759     void setMarkerSize(int markerSize)
0760     {
0761         setValue(TrailingMarkerSize, markerSize);
0762     }
0763 
0764     int markerSize() const
0765     {
0766         return value(TrailingMarkerSize).toInt();
0767     }
0768 
0769     /**
0770      * Remove trailing spaces on save.
0771      * triState = 0: never remove trailing spaces
0772      * triState = 1: remove trailing spaces of modified lines (line modification system)
0773      * triState = 2: remove trailing spaces in entire document
0774      */
0775     void setRemoveSpaces(int triState)
0776     {
0777         setValue(RemoveSpacesMode, triState);
0778     }
0779 
0780     int removeSpaces() const
0781     {
0782         return value(RemoveSpacesMode).toInt();
0783     }
0784 
0785     void setNewLineAtEof(bool on)
0786     {
0787         setValue(NewlineAtEOF, on);
0788     }
0789 
0790     bool newLineAtEof() const
0791     {
0792         return value(NewlineAtEOF).toBool();
0793     }
0794 
0795     void setOvr(bool on)
0796     {
0797         setValue(OverwriteMode, on);
0798     }
0799 
0800     bool ovr() const
0801     {
0802         return value(OverwriteMode).toBool();
0803     }
0804 
0805     void setTabIndents(bool on)
0806     {
0807         setValue(IndentOnTab, on);
0808     }
0809 
0810     bool tabIndentsEnabled() const
0811     {
0812         return value(IndentOnTab).toBool();
0813     }
0814 
0815     QString encoding() const
0816     {
0817         return value(Encoding).toString();
0818     }
0819 
0820     bool setEncoding(const QString &encoding)
0821     {
0822         return setValue(Encoding, encoding);
0823     }
0824 
0825     enum Eol { eolUnix = 0, eolDos = 1, eolMac = 2 };
0826 
0827     int eol() const
0828     {
0829         return value(EndOfLine).toInt();
0830     }
0831 
0832     /**
0833      * Get current end of line string.
0834      * Based on current set eol mode.
0835      * @return current end of line string
0836      */
0837     QString eolString() const;
0838 
0839     void setEol(int mode)
0840     {
0841         setValue(EndOfLine, mode);
0842     }
0843 
0844     bool bom() const
0845     {
0846         return value(ByteOrderMark).toBool();
0847     }
0848 
0849     void setBom(bool bom)
0850     {
0851         setValue(ByteOrderMark, bom);
0852     }
0853 
0854     bool allowEolDetection() const
0855     {
0856         return value(AllowEndOfLineDetection).toBool();
0857     }
0858 
0859     void setAllowEolDetection(bool on)
0860     {
0861         setValue(AllowEndOfLineDetection, on);
0862     }
0863 
0864     QString swapDirectory() const
0865     {
0866         return value(SwapFileDirectory).toString();
0867     }
0868 
0869     void setSwapDirectory(const QString &directory)
0870     {
0871         setValue(SwapFileDirectory, directory);
0872     }
0873 
0874     enum SwapFileMode { DisableSwapFile = 0, EnableSwapFile, SwapFilePresetDirectory };
0875 
0876     SwapFileMode swapFileMode() const
0877     {
0878         return SwapFileMode(value(SwapFile).toInt());
0879     }
0880 
0881     void setSwapFileMode(int mode)
0882     {
0883         setValue(SwapFile, mode);
0884     }
0885 
0886     int swapSyncInterval() const
0887     {
0888         return value(SwapFileSyncInterval).toInt();
0889     }
0890 
0891     void setSwapSyncInterval(int interval)
0892     {
0893         setValue(SwapFileSyncInterval, interval);
0894     }
0895 
0896     int lineLengthLimit() const
0897     {
0898         return value(LineLengthLimit).toInt();
0899     }
0900 
0901     void setLineLengthLimit(int limit)
0902     {
0903         setValue(LineLengthLimit, limit);
0904     }
0905 
0906     void setCamelCursor(bool on)
0907     {
0908         setValue(CamelCursor, on);
0909     }
0910 
0911     bool camelCursor() const
0912     {
0913         return value(CamelCursor).toBool();
0914     }
0915 
0916     void setAutoDetectIndent(bool on)
0917     {
0918         setValue(AutoDetectIndent, on);
0919     }
0920 
0921     bool autoDetectIndent() const
0922     {
0923         return value(AutoDetectIndent).toBool();
0924     }
0925 
0926     bool autoSave() const
0927     {
0928         return value(AutoSave).toBool();
0929     }
0930 
0931     bool autoSaveOnFocusOut() const
0932     {
0933         return value(AutoSaveOnFocusOut).toBool();
0934     }
0935 
0936     int autoSaveInterval() const
0937     {
0938         return value(AutoSaveInteral).toInt();
0939     }
0940 
0941 private:
0942     static KateDocumentConfig *s_global;
0943     KTextEditor::DocumentPrivate *m_doc = nullptr;
0944 };
0945 
0946 class KTEXTEDITOR_EXPORT KateViewConfig : public KateConfig
0947 {
0948 private:
0949     friend class KTextEditor::EditorPrivate;
0950 
0951     /**
0952      * only used in KTextEditor::EditorPrivate for the static global fallback !!!
0953      */
0954     KTEXTEDITOR_NO_EXPORT
0955     KateViewConfig();
0956 
0957 public:
0958     /**
0959      * Construct a ViewConfig
0960      */
0961     explicit KateViewConfig(KTextEditor::ViewPrivate *view);
0962 
0963     /**
0964      * Cu ViewConfig
0965      */
0966     ~KateViewConfig() override;
0967 
0968     inline static KateViewConfig *global()
0969     {
0970         return s_global;
0971     }
0972 
0973     /**
0974      * All known config keys
0975      * Keep them sorted alphabetically for our convenience.
0976      * Keep the same order when adding config entries with addConfigEntry() in
0977      * KateViewConfig::KateViewConfig() otherwise the code will assert.
0978      */
0979     enum ConfigEntryTypes {
0980         AllowMarkMenu,
0981         AutoBrackets,
0982         AutoCenterLines,
0983         AutomaticCompletionInvocation,
0984         AutomaticCompletionPreselectFirst,
0985         BackspaceRemoveComposedCharacters,
0986         BookmarkSorting,
0987         CharsToEncloseSelection,
0988         ClipboardHistoryEntries,
0989         DefaultMarkType,
0990         DynWordWrapAlignIndent,
0991         DynWordWrapIndicators,
0992         DynWrapAnywhere,
0993         DynWrapAtStaticMarker,
0994         DynamicWordWrap,
0995         EnterToInsertCompletion,
0996         FoldFirstLine,
0997         InputMode,
0998         KeywordCompletion,
0999         MaxHistorySize,
1000         MousePasteAtCursorPosition,
1001         PersistentSelection,
1002         ScrollBarMiniMapWidth,
1003         ScrollPastEnd,
1004         SearchFlags,
1005         TabCompletion,
1006         ShowBracketMatchPreview,
1007         ShowFoldingBar,
1008         ShowFoldingPreview,
1009         ShowIconBar,
1010         ShowLineCount,
1011         ShowLineModification,
1012         ShowLineNumbers,
1013         ShowScrollBarMarks,
1014         ShowScrollBarMiniMap,
1015         ShowScrollBarMiniMapAll,
1016         ShowScrollBarPreview,
1017         ShowScrollbars,
1018         ShowWordCount,
1019         TextDragAndDrop,
1020         SmartCopyCut,
1021         UserSetsOfCharsToEncloseSelection,
1022         ViInputModeStealKeys,
1023         ViRelativeLineNumbers,
1024         WordCompletion,
1025         WordCompletionMinimalWordLength,
1026         WordCompletionRemoveTail,
1027         ShowFocusFrame,
1028         ShowDocWithCompletion,
1029         MultiCursorModifier,
1030         ShowFoldingOnHoverOnly,
1031         ShowStatusbarLineColumn,
1032         ShowStatusbarDictionary,
1033         ShowStatusbarInputMode,
1034         ShowStatusbarHighlightingMode,
1035         ShowStatusbarTabSettings,
1036         ShowStatusbarFileEncoding,
1037         StatusbarLineColumnCompact,
1038         ShowStatusbarEOL,
1039         EnableAccessibility,
1040     };
1041 
1042 public:
1043     /**
1044      * Read config from object
1045      */
1046     void readConfig(const KConfigGroup &config);
1047 
1048     /**
1049      * Write config to object
1050      */
1051     void writeConfig(KConfigGroup &config);
1052 
1053 protected:
1054     void updateConfig() override;
1055 
1056 public:
1057     bool dynWordWrap() const
1058     {
1059         return value(DynamicWordWrap).toBool();
1060     }
1061     void setDynWordWrap(bool on)
1062     {
1063         setValue(DynamicWordWrap, on);
1064     }
1065     bool dynWrapAnywhere() const
1066     {
1067         return value(DynWrapAnywhere).toBool();
1068     }
1069 
1070     bool dynWrapAtStaticMarker() const
1071     {
1072         return value(DynWrapAtStaticMarker).toBool();
1073     }
1074 
1075     int dynWordWrapIndicators() const
1076     {
1077         return value(DynWordWrapIndicators).toInt();
1078     }
1079 
1080     int dynWordWrapAlignIndent() const
1081     {
1082         return value(DynWordWrapAlignIndent).toInt();
1083     }
1084 
1085     bool lineNumbers() const
1086     {
1087         return value(ShowLineNumbers).toBool();
1088     }
1089 
1090     bool scrollBarMarks() const
1091     {
1092         return value(ShowScrollBarMarks).toBool();
1093     }
1094 
1095     bool scrollBarPreview() const
1096     {
1097         return value(ShowScrollBarPreview).toBool();
1098     }
1099 
1100     bool scrollBarMiniMap() const
1101     {
1102         return value(ShowScrollBarMiniMap).toBool();
1103     }
1104 
1105     bool scrollBarMiniMapAll() const
1106     {
1107         return value(ShowScrollBarMiniMapAll).toBool();
1108     }
1109 
1110     int scrollBarMiniMapWidth() const
1111     {
1112         return value(ScrollBarMiniMapWidth).toInt();
1113     }
1114 
1115     /* Whether to show scrollbars */
1116     enum ScrollbarMode { AlwaysOn = 0, ShowWhenNeeded, AlwaysOff };
1117 
1118     int showScrollbars() const
1119     {
1120         return value(ShowScrollbars).toInt();
1121     }
1122 
1123     bool showFocusFrame() const
1124     {
1125         return value(ShowFocusFrame).toBool();
1126     }
1127 
1128     bool showDocWithCompletion() const
1129     {
1130         return value(ShowDocWithCompletion).toBool();
1131     }
1132 
1133     Qt::KeyboardModifiers multiCursorModifiers() const
1134     {
1135         return static_cast<Qt::KeyboardModifiers>(value(MultiCursorModifier).toInt());
1136     }
1137 
1138     void setMultiCursorModifiers(Qt::KeyboardModifiers m)
1139     {
1140         setValue(MultiCursorModifier, (int)m);
1141     }
1142 
1143     bool iconBar() const
1144     {
1145         return value(ShowIconBar).toBool();
1146     }
1147 
1148     bool foldingBar() const
1149     {
1150         return value(ShowFoldingBar).toBool();
1151     }
1152 
1153     bool foldingPreview() const
1154     {
1155         return value(ShowFoldingPreview).toBool();
1156     }
1157 
1158     bool lineModification() const
1159     {
1160         return value(ShowLineModification).toBool();
1161     }
1162 
1163     int bookmarkSort() const
1164     {
1165         return value(BookmarkSorting).toInt();
1166     }
1167 
1168     int autoCenterLines() const
1169     {
1170         return value(AutoCenterLines).toInt();
1171     }
1172 
1173     enum SearchFlags {
1174         IncMatchCase = 1 << 0,
1175         IncHighlightAll = 1 << 1,
1176         IncFromCursor = 1 << 2,
1177         PowerMatchCase = 1 << 3,
1178         PowerHighlightAll = 1 << 4,
1179         PowerFromCursor = 1 << 5,
1180         // PowerSelectionOnly = 1 << 6, Better not save to file // Sebastian
1181         PowerModePlainText = 1 << 7,
1182         PowerModeWholeWords = 1 << 8,
1183         PowerModeEscapeSequences = 1 << 9,
1184         PowerModeRegularExpression = 1 << 10,
1185         PowerUsePlaceholders = 1 << 11
1186     };
1187 
1188     uint searchFlags() const
1189     {
1190         return value(SearchFlags).toUInt();
1191     }
1192     void setSearchFlags(uint flags)
1193     {
1194         setValue(SearchFlags, flags);
1195     }
1196 
1197     int maxHistorySize() const
1198     {
1199         return value(MaxHistorySize).toInt();
1200     }
1201 
1202     uint defaultMarkType() const
1203     {
1204         return value(DefaultMarkType).toUInt();
1205     }
1206 
1207     bool allowMarkMenu() const
1208     {
1209         return value(AllowMarkMenu).toBool();
1210     }
1211 
1212     bool persistentSelection() const
1213     {
1214         return value(PersistentSelection).toBool();
1215     }
1216 
1217     KTextEditor::View::InputMode inputMode() const
1218     {
1219         return static_cast<KTextEditor::View::InputMode>(value(InputMode).toUInt());
1220     }
1221 
1222     bool viInputModeStealKeys() const
1223     {
1224         return value(ViInputModeStealKeys).toBool();
1225     }
1226 
1227     bool viRelativeLineNumbers() const
1228     {
1229         return value(ViRelativeLineNumbers).toBool();
1230     }
1231 
1232     // Do we still need the enum and related functions below?
1233     enum TextToSearch { Nowhere = 0, SelectionOnly = 1, SelectionWord = 2, WordOnly = 3, WordSelection = 4 };
1234 
1235     bool automaticCompletionInvocation() const
1236     {
1237         return value(AutomaticCompletionInvocation).toBool();
1238     }
1239 
1240     bool automaticCompletionPreselectFirst() const
1241     {
1242         return value(AutomaticCompletionPreselectFirst).toBool();
1243     }
1244 
1245     bool tabCompletion() const
1246     {
1247         return value(TabCompletion).toBool();
1248     }
1249 
1250     bool wordCompletion() const
1251     {
1252         return value(WordCompletion).toBool();
1253     }
1254 
1255     bool keywordCompletion() const
1256     {
1257         return value(KeywordCompletion).toBool();
1258     }
1259 
1260     int wordCompletionMinimalWordLength() const
1261     {
1262         return value(WordCompletionMinimalWordLength).toInt();
1263     }
1264 
1265     bool wordCompletionRemoveTail() const
1266     {
1267         return value(WordCompletionRemoveTail).toBool();
1268     }
1269 
1270     bool textDragAndDrop() const
1271     {
1272         return value(TextDragAndDrop).toBool();
1273     }
1274 
1275     bool smartCopyCut() const
1276     {
1277         return value(SmartCopyCut).toBool();
1278     }
1279 
1280     bool mousePasteAtCursorPosition() const
1281     {
1282         return value(MousePasteAtCursorPosition).toBool();
1283     }
1284 
1285     int clipboardHistoryEntries() const
1286     {
1287         return value(ClipboardHistoryEntries).toInt();
1288     }
1289 
1290     bool scrollPastEnd() const
1291     {
1292         return value(ScrollPastEnd).toBool();
1293     }
1294 
1295     bool foldFirstLine() const
1296     {
1297         return value(FoldFirstLine).toBool();
1298     }
1299 
1300     bool showWordCount() const
1301     {
1302         return value(ShowWordCount).toBool();
1303     }
1304     void setShowWordCount(bool on)
1305     {
1306         setValue(ShowWordCount, on);
1307     }
1308 
1309     bool showLineCount() const
1310     {
1311         return value(ShowLineCount).toBool();
1312     }
1313 
1314     void setShowLineCount(bool on)
1315     {
1316         setValue(ShowLineCount, on);
1317     }
1318 
1319     bool autoBrackets() const
1320     {
1321         return value(AutoBrackets).toBool();
1322     }
1323 
1324     bool encloseSelectionInChars() const
1325     {
1326         return !value(CharsToEncloseSelection).toString().isEmpty();
1327     }
1328 
1329     QString charsToEncloseSelection() const
1330     {
1331         return value(CharsToEncloseSelection).toString();
1332     }
1333 
1334     bool backspaceRemoveComposed() const
1335     {
1336         return value(BackspaceRemoveComposedCharacters).toBool();
1337     }
1338 
1339     bool showFoldingOnHoverOnly() const
1340     {
1341         return value(ShowFoldingOnHoverOnly).toBool();
1342     }
1343 
1344 private:
1345     static KateViewConfig *s_global;
1346     KTextEditor::ViewPrivate *m_view = nullptr;
1347 };
1348 
1349 class KTEXTEDITOR_EXPORT KateRendererConfig : public KateConfig
1350 {
1351 private:
1352     friend class KTextEditor::EditorPrivate;
1353 
1354     /**
1355      * only used in KTextEditor::EditorPrivate for the static global fallback !!!
1356      */
1357     KTEXTEDITOR_NO_EXPORT
1358     KateRendererConfig();
1359 
1360 public:
1361     /**
1362      * Construct a RendererConfig
1363      */
1364     explicit KateRendererConfig(KateRenderer *renderer);
1365 
1366     /**
1367      * Cu RendererConfig
1368      */
1369     ~KateRendererConfig() override;
1370 
1371     inline static KateRendererConfig *global()
1372     {
1373         return s_global;
1374     }
1375 
1376     /**
1377      * All known config keys
1378      * Keep them sorted alphabetic for our convenience
1379      */
1380     enum ConfigEntryTypes {
1381         /**
1382          * auto-select the color theme based on application palette
1383          */
1384         AutoColorThemeSelection
1385     };
1386 
1387 public:
1388     /**
1389      * Read config from object
1390      */
1391     void readConfig(const KConfigGroup &config);
1392 
1393     /**
1394      * Write config to object
1395      */
1396     void writeConfig(KConfigGroup &config);
1397 
1398 protected:
1399     void updateConfig() override;
1400 
1401 public:
1402     const QString &schema() const;
1403     void setSchema(QString schema);
1404 
1405     /**
1406      * Reload the schema from the schema manager.
1407      * For the global instance, have all other instances reload.
1408      * Used by the schema config page to apply changes.
1409      */
1410     void reloadSchema();
1411 
1412     /**
1413      * Base font to use for the views and co.
1414      * Will be adjusted there to avoid rendering artifacts for HiDPI stuff.
1415      * @return base font to use
1416      */
1417     const QFont &baseFont() const;
1418 
1419     void setFont(const QFont &font);
1420 
1421     bool wordWrapMarker() const;
1422     void setWordWrapMarker(bool on);
1423 
1424     const QColor &backgroundColor() const;
1425     void setBackgroundColor(const QColor &col);
1426 
1427     const QColor &selectionColor() const;
1428     void setSelectionColor(const QColor &col);
1429 
1430     const QColor &highlightedLineColor() const;
1431     void setHighlightedLineColor(const QColor &col);
1432 
1433     const QColor &lineMarkerColor(KTextEditor::Document::MarkTypes type = KTextEditor::Document::markType01) const; // markType01 == Bookmark
1434 
1435     const QColor &highlightedBracketColor() const;
1436     void setHighlightedBracketColor(const QColor &col);
1437 
1438     const QColor &wordWrapMarkerColor() const;
1439     void setWordWrapMarkerColor(const QColor &col);
1440 
1441     const QColor &tabMarkerColor() const;
1442     void setTabMarkerColor(const QColor &col);
1443 
1444     const QColor &indentationLineColor() const;
1445     void setIndentationLineColor(const QColor &col);
1446 
1447     const QColor &iconBarColor() const;
1448     void setIconBarColor(const QColor &col);
1449 
1450     const QColor &foldingColor() const;
1451     void setFoldingColor(const QColor &col);
1452 
1453     // the line number color is used for the line numbers on the left bar
1454     const QColor &lineNumberColor() const;
1455     void setLineNumberColor(const QColor &col);
1456     const QColor &currentLineNumberColor() const;
1457     void setCurrentLineNumberColor(const QColor &col);
1458 
1459     // the color of the separator between line numbers and icon bar
1460     const QColor &separatorColor() const;
1461     void setSeparatorColor(const QColor &col);
1462 
1463     const QColor &spellingMistakeLineColor() const;
1464     void setSpellingMistakeLineColor(const QColor &col);
1465 
1466     bool showIndentationLines() const;
1467     void setShowIndentationLines(bool on);
1468 
1469     bool showWholeBracketExpression() const;
1470     void setShowWholeBracketExpression(bool on);
1471 
1472     static bool animateBracketMatching();
1473     void setAnimateBracketMatching(bool on);
1474 
1475     const QColor &templateBackgroundColor() const;
1476     const QColor &templateEditablePlaceholderColor() const;
1477     const QColor &templateFocusedEditablePlaceholderColor() const;
1478     const QColor &templateNotEditablePlaceholderColor() const;
1479 
1480     const QColor &modifiedLineColor() const;
1481     void setModifiedLineColor(const QColor &col);
1482 
1483     const QColor &savedLineColor() const;
1484     void setSavedLineColor(const QColor &col);
1485 
1486     const QColor &searchHighlightColor() const;
1487     void setSearchHighlightColor(const QColor &col);
1488 
1489     const QColor &replaceHighlightColor() const;
1490     void setReplaceHighlightColor(const QColor &col);
1491 
1492     void setLineHeightMultiplier(qreal value);
1493 
1494     qreal lineHeightMultiplier() const
1495     {
1496         return s_global->m_lineHeightMultiplier;
1497     }
1498 
1499 private:
1500     /**
1501      * Read the schema properties from the config file.
1502      */
1503     KTEXTEDITOR_NO_EXPORT
1504     void setSchemaInternal(const QString &schema);
1505 
1506 private:
1507     QString m_schema;
1508     QFont m_font;
1509     QColor m_backgroundColor;
1510     QColor m_selectionColor;
1511     QColor m_highlightedLineColor;
1512     QColor m_highlightedBracketColor;
1513     QColor m_wordWrapMarkerColor;
1514     QColor m_tabMarkerColor;
1515     QColor m_indentationLineColor;
1516     QColor m_iconBarColor;
1517     QColor m_foldingColor;
1518     QColor m_lineNumberColor;
1519     QColor m_currentLineNumberColor;
1520     QColor m_separatorColor;
1521     QColor m_spellingMistakeLineColor;
1522     std::vector<QColor> m_lineMarkerColor;
1523 
1524     QColor m_templateBackgroundColor;
1525     QColor m_templateEditablePlaceholderColor;
1526     QColor m_templateFocusedEditablePlaceholderColor;
1527     QColor m_templateNotEditablePlaceholderColor;
1528 
1529     QColor m_modifiedLineColor;
1530     QColor m_savedLineColor;
1531     QColor m_searchHighlightColor;
1532     QColor m_replaceHighlightColor;
1533 
1534     qreal m_lineHeightMultiplier = 1.0;
1535 
1536     bool m_wordWrapMarker = false;
1537     bool m_showIndentationLines = false;
1538     bool m_showWholeBracketExpression = false;
1539     bool m_animateBracketMatching = false;
1540 
1541     bool m_schemaSet : 1;
1542     bool m_fontSet : 1;
1543     bool m_wordWrapMarkerSet : 1;
1544     bool m_showIndentationLinesSet : 1;
1545     bool m_showWholeBracketExpressionSet : 1;
1546     bool m_backgroundColorSet : 1;
1547     bool m_selectionColorSet : 1;
1548     bool m_highlightedLineColorSet : 1;
1549     bool m_highlightedBracketColorSet : 1;
1550     bool m_wordWrapMarkerColorSet : 1;
1551     bool m_tabMarkerColorSet : 1;
1552     bool m_indentationLineColorSet : 1;
1553     bool m_iconBarColorSet : 1;
1554     bool m_foldingColorSet : 1;
1555     bool m_lineNumberColorSet : 1;
1556     bool m_currentLineNumberColorSet : 1;
1557     bool m_separatorColorSet : 1;
1558     bool m_spellingMistakeLineColorSet : 1;
1559     bool m_templateColorsSet : 1;
1560     bool m_modifiedLineColorSet : 1;
1561     bool m_savedLineColorSet : 1;
1562     bool m_searchHighlightColorSet : 1;
1563     bool m_replaceHighlightColorSet : 1;
1564     QBitArray m_lineMarkerColorSet;
1565 
1566 private:
1567     static KateRendererConfig *s_global;
1568     KateRenderer *m_renderer = nullptr;
1569 };
1570 
1571 #endif