DiffEditor: fix revert chunk for diffs of modified files

Apply chunk action doesn't make sense for that case,
will stay disabled.

Task-number: QTCREATORBUG-17136
Change-Id: Idce31b3aa9d354536a01607c10b20273158961d5
Reviewed-by: Tobias Hunger <tobias.hunger@qt.io>
This commit is contained in:
Jarek Kobus
2016-10-19 16:44:25 +02:00
committed by Jarek Kobus
parent 344f255fa9
commit 8224c1c95d
7 changed files with 81 additions and 18 deletions

View File

@@ -87,7 +87,9 @@ DiffEditorController *DiffEditorDocument::controller() const
return m_controller; return m_controller;
} }
QString DiffEditorDocument::makePatch(int fileIndex, int chunkIndex, bool revert, bool addPrefix) const QString DiffEditorDocument::makePatch(int fileIndex, int chunkIndex,
bool revert, bool addPrefix,
const QString &overriddenFileName) const
{ {
if (fileIndex < 0 || chunkIndex < 0) if (fileIndex < 0 || chunkIndex < 0)
return QString(); return QString();
@@ -102,7 +104,8 @@ QString DiffEditorDocument::makePatch(int fileIndex, int chunkIndex, bool revert
const ChunkData &chunkData = fileData.chunks.at(chunkIndex); const ChunkData &chunkData = fileData.chunks.at(chunkIndex);
const bool lastChunk = (chunkIndex == fileData.chunks.count() - 1); const bool lastChunk = (chunkIndex == fileData.chunks.count() - 1);
const QString fileName = revert const QString fileName = !overriddenFileName.isEmpty()
? overriddenFileName : revert
? fileData.rightFileInfo.fileName ? fileData.rightFileInfo.fileName
: fileData.leftFileInfo.fileName; : fileData.leftFileInfo.fileName;

View File

@@ -46,7 +46,9 @@ public:
DiffEditorController *controller() const; DiffEditorController *controller() const;
QString makePatch(int fileIndex, int chunkIndex, bool revert, bool addPrefix = false) const; QString makePatch(int fileIndex, int chunkIndex,
bool revert, bool addPrefix = false,
const QString &overriddenFileName = QString()) const;
void setDiffFiles(const QList<FileData> &data, const QString &directory, void setDiffFiles(const QList<FileData> &data, const QString &directory,
const QString &startupFile = QString()); const QString &startupFile = QString());

View File

@@ -143,6 +143,7 @@ void DiffCurrentFileController::reload()
fileData.rightFileInfo.fileName = m_fileName; fileData.rightFileInfo.fileName = m_fileName;
fileData.leftFileInfo.typeInfo = tr("Saved"); fileData.leftFileInfo.typeInfo = tr("Saved");
fileData.rightFileInfo.typeInfo = tr("Modified"); fileData.rightFileInfo.typeInfo = tr("Modified");
fileData.rightFileInfo.patchBehaviour = DiffFileInfo::PatchEditor;
if (!leftFileExists) if (!leftFileExists)
fileData.fileOperation = FileData::NewFile; fileData.fileOperation = FileData::NewFile;
@@ -201,6 +202,7 @@ void DiffOpenFilesController::reload()
fileData.rightFileInfo.fileName = fileName; fileData.rightFileInfo.fileName = fileName;
fileData.leftFileInfo.typeInfo = tr("Saved"); fileData.leftFileInfo.typeInfo = tr("Saved");
fileData.rightFileInfo.typeInfo = tr("Modified"); fileData.rightFileInfo.typeInfo = tr("Modified");
fileData.rightFileInfo.patchBehaviour = DiffFileInfo::PatchEditor;
if (!leftFileExists) if (!leftFileExists)
fileData.fileOperation = FileData::NewFile; fileData.fileOperation = FileData::NewFile;
@@ -261,6 +263,7 @@ void DiffModifiedFilesController::reload()
fileData.rightFileInfo.fileName = fileName; fileData.rightFileInfo.fileName = fileName;
fileData.leftFileInfo.typeInfo = tr("Saved"); fileData.leftFileInfo.typeInfo = tr("Saved");
fileData.rightFileInfo.typeInfo = tr("Modified"); fileData.rightFileInfo.typeInfo = tr("Modified");
fileData.rightFileInfo.patchBehaviour = DiffFileInfo::PatchEditor;
if (!leftFileExists) if (!leftFileExists)
fileData.fileOperation = FileData::NewFile; fileData.fileOperation = FileData::NewFile;

View File

@@ -32,6 +32,7 @@
#include <coreplugin/patchtool.h> #include <coreplugin/patchtool.h>
#include <texteditor/fontsettings.h> #include <texteditor/fontsettings.h>
#include <texteditor/textdocument.h>
#include <extensionsystem/pluginmanager.h> #include <extensionsystem/pluginmanager.h>
@@ -42,6 +43,7 @@
#include <QDir> #include <QDir>
#include <QMenu> #include <QMenu>
#include <QMessageBox> #include <QMessageBox>
#include <QTemporaryFile>
#include <QTextCodec> #include <QTextCodec>
using namespace Core; using namespace Core;
@@ -77,27 +79,60 @@ void DiffEditorWidgetController::patch(bool revert)
return; return;
} }
const int strip = m_document->baseDirectory().isEmpty() ? -1 : 0;
const FileData fileData = m_contextFileData.at(m_contextMenuFileIndex); const FileData fileData = m_contextFileData.at(m_contextMenuFileIndex);
const QString fileName = revert const QString fileName = revert
? fileData.rightFileInfo.fileName ? fileData.rightFileInfo.fileName
: fileData.leftFileInfo.fileName; : fileData.leftFileInfo.fileName;
const DiffFileInfo::PatchBehaviour patchBehaviour = revert
? fileData.rightFileInfo.patchBehaviour
: fileData.leftFileInfo.patchBehaviour;
const QString workingDirectory = m_document->baseDirectory().isEmpty() const QString workingDirectory = m_document->baseDirectory().isEmpty()
? QFileInfo(fileName).absolutePath() ? QFileInfo(fileName).absolutePath()
: m_document->baseDirectory(); : m_document->baseDirectory();
const QString absFileName = QFileInfo(workingDirectory + '/' + QFileInfo(fileName).fileName()).absoluteFilePath();
if (patchBehaviour == DiffFileInfo::PatchFile) {
const int strip = m_document->baseDirectory().isEmpty() ? -1 : 0;
const QString patch = m_document->makePatch(m_contextMenuFileIndex, m_contextMenuChunkIndex, revert); const QString patch = m_document->makePatch(m_contextMenuFileIndex, m_contextMenuChunkIndex, revert);
if (patch.isEmpty()) if (patch.isEmpty())
return; return;
const QString absFileName = QFileInfo(workingDirectory + '/' + fileName).absoluteFilePath();
FileChangeBlocker fileChangeBlocker(absFileName); FileChangeBlocker fileChangeBlocker(absFileName);
if (PatchTool::runPatch(EditorManager::defaultTextCodec()->fromUnicode(patch), if (PatchTool::runPatch(EditorManager::defaultTextCodec()->fromUnicode(patch),
workingDirectory, strip, revert)) workingDirectory, strip, revert))
m_document->reload(); m_document->reload();
} else { // PatchEditor
TextEditor::TextDocument *textDocument = qobject_cast<TextEditor::TextDocument *>(
DocumentModel::documentForFilePath(absFileName));
if (!textDocument)
return;
QTemporaryFile contentsCopy;
if (!contentsCopy.open())
return;
contentsCopy.write(textDocument->contents());
contentsCopy.close();
const QString contentsCopyFileName = contentsCopy.fileName();
const QString contentsCopyDir = QFileInfo(contentsCopyFileName).absolutePath();
const QString patch = m_document->makePatch(m_contextMenuFileIndex,
m_contextMenuChunkIndex, revert, false, QFileInfo(contentsCopyFileName).fileName());
if (patch.isEmpty())
return;
if (PatchTool::runPatch(EditorManager::defaultTextCodec()->fromUnicode(patch),
contentsCopyDir, 0, revert)) {
QString errorString;
if (textDocument->reload(&errorString, contentsCopyFileName))
m_document->reload();
}
}
} }
void DiffEditorWidgetController::jumpToOriginalFile(const QString &fileName, void DiffEditorWidgetController::jumpToOriginalFile(const QString &fileName,

View File

@@ -38,12 +38,18 @@ class Diff;
class DIFFEDITOR_EXPORT DiffFileInfo { class DIFFEDITOR_EXPORT DiffFileInfo {
public: public:
enum PatchBehaviour {
PatchFile,
PatchEditor
};
DiffFileInfo() {} DiffFileInfo() {}
DiffFileInfo(const QString &file) : fileName(file) {} DiffFileInfo(const QString &file) : fileName(file) {}
DiffFileInfo(const QString &file, const QString &type) DiffFileInfo(const QString &file, const QString &type)
: fileName(file), typeInfo(type) {} : fileName(file), typeInfo(type) {}
QString fileName; QString fileName;
QString typeInfo; QString typeInfo;
PatchBehaviour patchBehaviour = PatchFile;
}; };
class DIFFEDITOR_EXPORT TextLineData { class DIFFEDITOR_EXPORT TextLineData {

View File

@@ -634,7 +634,11 @@ Core::IDocument::OpenResult TextDocument::openImpl(QString *errorString, const Q
readResult = read(realFileName, &content, errorString); readResult = read(realFileName, &content, errorString);
const int chunks = content.size(); const int chunks = content.size();
// Don't call setUndoRedoEnabled(true) when reload is true and filenames are different,
// since it will reset the undo's clear index
if (!reload || fileName == realFileName)
d->m_document.setUndoRedoEnabled(reload); d->m_document.setUndoRedoEnabled(reload);
QTextCursor c(&d->m_document); QTextCursor c(&d->m_document);
c.beginEditBlock(); c.beginEditBlock();
if (reload) { if (reload) {
@@ -663,6 +667,10 @@ Core::IDocument::OpenResult TextDocument::openImpl(QString *errorString, const Q
} }
c.endEditBlock(); c.endEditBlock();
// Don't call setUndoRedoEnabled(true) when reload is true and filenames are different,
// since it will reset the undo's clear index
if (!reload || fileName == realFileName)
d->m_document.setUndoRedoEnabled(true); d->m_document.setUndoRedoEnabled(true);
TextDocumentLayout *documentLayout = TextDocumentLayout *documentLayout =
@@ -686,6 +694,11 @@ bool TextDocument::reload(QString *errorString, QTextCodec *codec)
} }
bool TextDocument::reload(QString *errorString) bool TextDocument::reload(QString *errorString)
{
return reload(errorString, filePath().toString());
}
bool TextDocument::reload(QString *errorString, const QString &realFileName)
{ {
emit aboutToReload(); emit aboutToReload();
TextDocumentLayout *documentLayout = TextDocumentLayout *documentLayout =
@@ -695,7 +708,7 @@ bool TextDocument::reload(QString *errorString)
marks = documentLayout->documentClosing(); // removes text marks non-permanently marks = documentLayout->documentClosing(); // removes text marks non-permanently
const QString &file = filePath().toString(); const QString &file = filePath().toString();
bool success = openImpl(errorString, file, file, /*reload =*/ true) == OpenResult::Success; bool success = openImpl(errorString, file, realFileName, /*reload =*/ true) == OpenResult::Success;
if (documentLayout) if (documentLayout)
documentLayout->documentReloaded(marks, this); // re-adds text marks documentLayout->documentReloaded(marks, this); // re-adds text marks

View File

@@ -118,6 +118,7 @@ public:
OpenResult open(QString *errorString, const QString &fileName, OpenResult open(QString *errorString, const QString &fileName,
const QString &realFileName) override; const QString &realFileName) override;
virtual bool reload(QString *errorString); virtual bool reload(QString *errorString);
bool reload(QString *errorString, const QString &realFileName);
bool setPlainText(const QString &text); bool setPlainText(const QString &text);
QTextDocument *document() const; QTextDocument *document() const;