File indexing completed on 2024-05-12 05:52:06
0001 /* 0002 SPDX-FileCopyrightText: 2022 Waqar Ahmed <waqar.17a@gmail.com> 0003 SPDX-License-Identifier: LGPL-2.0-or-later 0004 */ 0005 0006 #pragma once 0007 0008 #include "diffeditor.h" 0009 #include <QWidget> 0010 0011 #include "kateprivate_export.h" 0012 0013 #include <KTextEditor/Document> 0014 0015 namespace KSyntaxHighlighting 0016 { 0017 class SyntaxHighlighter; 0018 } 0019 0020 /** 0021 * - Small wrapper over DiffWidget. It tries to reuse an existing diff widget instead of opening a new one 0022 * - Two DiffWidgets are considered equal if their DiffParams.arguments match 0023 * - The diff is always recalculated 0024 */ 0025 class DiffWidgetManager 0026 { 0027 public: 0028 static void openDiff(const QByteArray &diff, DiffParams p, class KTextEditor::MainWindow *mw); 0029 static void diffDocs(KTextEditor::Document *l, KTextEditor::Document *r, class KTextEditor::MainWindow *mw); 0030 0031 private: 0032 static DiffWidget *existingDiffWidgetForParams(KTextEditor::MainWindow *mw, const DiffParams &p); 0033 }; 0034 0035 class KATE_PRIVATE_EXPORT DiffWidget : public QWidget 0036 { 0037 Q_OBJECT 0038 friend DiffWidgetManager; 0039 friend class DiffWidgetTests; 0040 0041 public: 0042 explicit DiffWidget(DiffParams p, QWidget *parent = nullptr); 0043 ~DiffWidget(); 0044 0045 void diffDocs(KTextEditor::Document *l, KTextEditor::Document *r); 0046 0047 void openDiff(const QByteArray &diff); 0048 0049 Q_INVOKABLE bool shouldClose() 0050 { 0051 return true; 0052 } 0053 0054 bool isHunk(int line) const; 0055 bool isFileNameLine(int line) const 0056 { 0057 return std::find(m_linesWithFileName.begin(), m_linesWithFileName.end(), line) != m_linesWithFileName.end(); 0058 } 0059 int hunkLineCount(int hunkLine); 0060 0061 protected: 0062 void showEvent(QShowEvent *e) override; 0063 0064 private: 0065 void clearData(); 0066 void handleStyleChange(int); 0067 void handleStageUnstage(DiffEditor *e, int startLine, int endLine, int actionType, DiffParams::Flag); 0068 void handleStageUnstage_unified(int startLine, int endLine, int actionType, DiffParams::Flag); 0069 void handleStageUnstage_sideBySide(DiffEditor *e, int startLine, int endLine, int actionType, DiffParams::Flag); 0070 void handleStageUnstage_raw(int startLine, int endLine, int actionType, DiffParams::Flag flags); 0071 void doStageUnStage(int startLine, int endLine, int actionType, DiffParams::Flag); 0072 void onError(const QByteArray &error, int code); 0073 void parseAndShowDiff(const QByteArray &raw); 0074 void parseAndShowDiffUnified(const QByteArray &raw); 0075 enum ApplyFlags { None = 0, Staged = 1, Discard = 2 }; 0076 void applyDiff(const QString &diff, ApplyFlags flags); 0077 void runGitDiff(); 0078 static QStringList diffDocsGitArgs(KTextEditor::Document *l, KTextEditor::Document *r); 0079 void showWithFullContext(); 0080 0081 void jumpToNextFile(); 0082 void jumpToPrevFile(); 0083 void jumpToNextHunk(); 0084 void jumpToPrevHunk(); 0085 0086 // Struct representing a view line to diff line in the original diff 0087 // Lines which are added or removed are stored, context lines and 0088 // other metaData is ignored 0089 struct ViewLineToDiffLine { 0090 int line; 0091 int diffLine; 0092 // Only used in side-by-side mode 0093 bool added; 0094 }; 0095 0096 class DiffEditor *m_left; 0097 class DiffEditor *m_right; 0098 class QPlainTextEdit *const m_commitInfo; 0099 class Toolbar *const m_toolbar; 0100 KSyntaxHighlighting::AbstractHighlighter *leftHl; 0101 KSyntaxHighlighting::AbstractHighlighter *rightHl; 0102 DiffStyle m_style = SideBySide; 0103 DiffParams m_params; 0104 QByteArray m_rawDiff; // Raw diff saved as is 0105 std::vector<ViewLineToDiffLine> m_lineToRawDiffLine; 0106 std::vector<ViewLineToDiffLine> m_lineToDiffHunkLine; 0107 std::vector<int> m_linesWithFileName; 0108 bool m_stopScrollSync = false; 0109 bool m_blockShowEvent = true; 0110 };