Merge branch 'sourcegit-scm:develop' into develop

This commit is contained in:
Paolo Ghibaudo 2024-07-18 08:52:47 +02:00 committed by GitHub
commit 3668d4904c
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 211 additions and 172 deletions

View file

@ -9,7 +9,7 @@ on:
jobs: jobs:
build-windows: build-windows:
name: Build Windows x64 name: Build Windows x64
runs-on: windows-latest runs-on: windows-2019
steps: steps:
- name: Checkout sources - name: Checkout sources
uses: actions/checkout@v4 uses: actions/checkout@v4
@ -30,7 +30,7 @@ jobs:
path: publish path: publish
build-macos-intel: build-macos-intel:
name: Build macOS (Intel) name: Build macOS (Intel)
runs-on: macos-latest runs-on: macos-13
steps: steps:
- name: Checkout sources - name: Checkout sources
uses: actions/checkout@v4 uses: actions/checkout@v4
@ -76,7 +76,7 @@ jobs:
path: sourcegit.osx-arm64.tar path: sourcegit.osx-arm64.tar
build-linux: build-linux:
name: Build Linux name: Build Linux
runs-on: ubuntu-latest runs-on: ubuntu-20.04
steps: steps:
- name: Checkout sources - name: Checkout sources
uses: actions/checkout@v4 uses: actions/checkout@v4

View file

@ -188,6 +188,8 @@ namespace SourceGit
else else
Models.CommitGraph.SetDefaultPens(overrides.GraphPenThickness); Models.CommitGraph.SetDefaultPens(overrides.GraphPenThickness);
Models.Commit.OpacityForNotMerged = overrides.OpacityForNotMergedCommits;
app.Resources.MergedDictionaries.Add(resDic); app.Resources.MergedDictionaries.Add(resDic);
app._themeOverrides = resDic; app._themeOverrides = resDic;
} }

View file

@ -14,20 +14,30 @@ namespace SourceGit.Commands
_findFirstMerged = needFindHead; _findFirstMerged = needFindHead;
} }
public QueryCommits(string repo, int maxCount, string messageFilter) public QueryCommits(string repo, int maxCount, string messageFilter, bool isFile)
{ {
var argsBuilder = new StringBuilder(); string search;
var words = messageFilter.Split(new[] { ' ', '\t', '\r' }, StringSplitOptions.RemoveEmptyEntries); if (isFile)
foreach (var word in words)
{ {
var escaped = word.Trim().Replace("\"", "\\\"", StringComparison.Ordinal); search = $"-- \"{messageFilter}\"";
argsBuilder.Append($"--grep=\"{escaped}\" ");
} }
argsBuilder.Append("--all-match"); else
{
var argsBuilder = new StringBuilder();
var words = messageFilter.Split(new[] { ' ', '\t', '\r' }, StringSplitOptions.RemoveEmptyEntries);
foreach (var word in words)
{
var escaped = word.Trim().Replace("\"", "\\\"", StringComparison.Ordinal);
argsBuilder.Append($"--grep=\"{escaped}\" ");
}
argsBuilder.Append("--all-match -i");
search = argsBuilder.ToString();
}
WorkingDirectory = repo; WorkingDirectory = repo;
Context = repo; Context = repo;
Args = $"log -{maxCount} --date-order --no-show-signature --decorate=full --pretty=format:%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s " + argsBuilder.ToString(); Args = $"log -{maxCount} --date-order --no-show-signature --decorate=full --pretty=format:%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s --branches --remotes " + search;
_findFirstMerged = false; _findFirstMerged = false;
} }

View file

@ -1,5 +1,4 @@
using Avalonia.Data.Converters; using Avalonia.Data.Converters;
using Avalonia.Media;
namespace SourceGit.Converters namespace SourceGit.Converters
{ {
@ -7,11 +6,5 @@ namespace SourceGit.Converters
{ {
public static readonly FuncValueConverter<bool, double> ToPageTabWidth = public static readonly FuncValueConverter<bool, double> ToPageTabWidth =
new FuncValueConverter<bool, double>(x => x ? 200 : double.NaN); new FuncValueConverter<bool, double>(x => x ? 200 : double.NaN);
public static readonly FuncValueConverter<bool, double> HalfIfFalse =
new FuncValueConverter<bool, double>(x => x ? 1 : 0.5);
public static readonly FuncValueConverter<bool, FontWeight> BoldIfTrue =
new FuncValueConverter<bool, FontWeight>(x => x ? FontWeight.Bold : FontWeight.Regular);
} }
} }

View file

@ -2,11 +2,18 @@
using System.Collections.Generic; using System.Collections.Generic;
using Avalonia; using Avalonia;
using Avalonia.Media;
namespace SourceGit.Models namespace SourceGit.Models
{ {
public class Commit public class Commit
{ {
public static double OpacityForNotMerged
{
get;
set;
} = 0.5;
public string SHA { get; set; } = string.Empty; public string SHA { get; set; } = string.Empty;
public User Author { get; set; } = User.Invalid; public User Author { get; set; } = User.Invalid;
public ulong AuthorTime { get; set; } = 0; public ulong AuthorTime { get; set; } = 0;
@ -25,5 +32,8 @@ namespace SourceGit.Models
public bool IsCommitterVisible => !Author.Equals(Committer) || AuthorTime != CommitterTime; public bool IsCommitterVisible => !Author.Equals(Committer) || AuthorTime != CommitterTime;
public bool IsCurrentHead => Decorators.Find(x => x.Type is DecoratorType.CurrentBranchHead or DecoratorType.CurrentCommitHead) != null; public bool IsCurrentHead => Decorators.Find(x => x.Type is DecoratorType.CurrentBranchHead or DecoratorType.CurrentCommitHead) != null;
public double Opacity => IsMerged ? 1 : OpacityForNotMerged;
public FontWeight FontWeight => IsCurrentHead ? FontWeight.Bold : FontWeight.Regular;
} }
} }

View file

@ -69,6 +69,80 @@ namespace SourceGit.Models
public string Repo { get; set; } = null; public string Repo { get; set; } = null;
public DiffOption Option { get; set; } = null; public DiffOption Option { get; set; } = null;
public TextDiffSelection MakeSelection(int startLine, int endLine, bool isSideBySide, bool isOldSide)
{
var rs = new TextDiffSelection();
rs.StartLine = startLine;
rs.EndLine = endLine;
for (int i = 0; i < startLine - 1; i++)
{
var line = Lines[i];
if (line.Type == TextDiffLineType.Added)
{
rs.HasLeftChanges = true;
rs.IgnoredAdds++;
}
else if (line.Type == TextDiffLineType.Deleted)
{
rs.HasLeftChanges = true;
rs.IgnoredDeletes++;
}
}
for (int i = startLine - 1; i < endLine; i++)
{
var line = Lines[i];
if (line.Type == TextDiffLineType.Added)
{
if (!isSideBySide)
{
rs.HasChanges = true;
break;
}
else if (isOldSide)
{
rs.HasLeftChanges = true;
}
else
{
rs.HasChanges = true;
}
}
else if (line.Type == TextDiffLineType.Deleted)
{
if (!isSideBySide)
{
rs.HasChanges = true;
break;
}
else if (isOldSide)
{
rs.HasChanges = true;
}
else
{
rs.HasLeftChanges = true;
}
}
}
if (!rs.HasLeftChanges)
{
for (int i = endLine; i < Lines.Count; i++)
{
var line = Lines[i];
if (line.Type == TextDiffLineType.Added || line.Type == TextDiffLineType.Deleted)
{
rs.HasLeftChanges = true;
break;
}
}
}
return rs;
}
public void GenerateNewPatchFromSelection(Change change, string fileBlobGuid, TextDiffSelection selection, bool revert, string output) public void GenerateNewPatchFromSelection(Change change, string fileBlobGuid, TextDiffSelection selection, bool revert, string output)
{ {
var isTracked = !string.IsNullOrEmpty(fileBlobGuid); var isTracked = !string.IsNullOrEmpty(fileBlobGuid);
@ -392,9 +466,6 @@ namespace SourceGit.Models
System.IO.File.WriteAllText(output, builder.ToString()); System.IO.File.WriteAllText(output, builder.ToString());
} }
[GeneratedRegex(@"^@@ \-(\d+),?\d* \+(\d+),?\d* @@")]
private static partial Regex REG_INDICATOR();
private bool ProcessIndicatorForPatch(StringBuilder builder, TextDiffLine indicator, int idx, int start, int end, int ignoreRemoves, int ignoreAdds, bool revert, bool tailed) private bool ProcessIndicatorForPatch(StringBuilder builder, TextDiffLine indicator, int idx, int start, int end, int ignoreRemoves, int ignoreAdds, bool revert, bool tailed)
{ {
var match = REG_INDICATOR().Match(indicator.Content); var match = REG_INDICATOR().Match(indicator.Content);
@ -554,6 +625,9 @@ namespace SourceGit.Models
builder.Append($"\n@@ -{oldStart},{oldCount} +{newStart},{newCount} @@"); builder.Append($"\n@@ -{oldStart},{oldCount} +{newStart},{newCount} @@");
return true; return true;
} }
[GeneratedRegex(@"^@@ \-(\d+),?\d* \+(\d+),?\d* @@")]
private static partial Regex REG_INDICATOR();
} }
public class LFSDiff public class LFSDiff

View file

@ -8,6 +8,7 @@ namespace SourceGit.Models
{ {
public Dictionary<string, Color> BasicColors { get; set; } = new Dictionary<string, Color>(); public Dictionary<string, Color> BasicColors { get; set; } = new Dictionary<string, Color>();
public double GraphPenThickness { get; set; } = 2; public double GraphPenThickness { get; set; } = 2;
public double OpacityForNotMergedCommits { get; set; } = 0.5;
public List<Color> GraphColors { get; set; } = new List<Color>(); public List<Color> GraphColors { get; set; } = new List<Color>();
} }
} }

View file

@ -566,10 +566,10 @@ namespace SourceGit.ViewModels
break; break;
case 2: case 2:
visible = new Commands.QueryCommits(FullPath, 1000, _searchCommitFilter).Result(); visible = new Commands.QueryCommits(FullPath, 1000, _searchCommitFilter, false).Result();
break; break;
case 3: case 3:
visible = new Commands.QueryCommits(FullPath, $"-1000 -- \"{_searchCommitFilter}\"", false).Result(); visible = new Commands.QueryCommits(FullPath, 1000, _searchCommitFilter, true).Result();
break; break;
} }

View file

@ -1,5 +1,8 @@
using System.Collections.Generic; using System;
using System.Collections.Generic;
using Avalonia; using Avalonia;
using CommunityToolkit.Mvvm.ComponentModel; using CommunityToolkit.Mvvm.ComponentModel;
namespace SourceGit.ViewModels namespace SourceGit.ViewModels
@ -53,6 +56,45 @@ namespace SourceGit.ViewModels
_syncScrollOffset = previous._syncScrollOffset; _syncScrollOffset = previous._syncScrollOffset;
} }
public void ConvertsToCombinedRange(Models.TextDiff combined, ref int startLine, ref int endLine, bool isOldSide)
{
endLine = Math.Min(endLine, combined.Lines.Count);
var oneSide = isOldSide ? Old : New;
var firstContentLine = -1;
for (int i = startLine - 1; i < endLine; i++)
{
var line = oneSide[i];
if (line.Type != Models.TextDiffLineType.None)
{
firstContentLine = i;
break;
}
}
if (firstContentLine < 0)
return;
var endContentLine = -1;
for (int i = Math.Min(endLine - 1, oneSide.Count - 1); i >= startLine - 1; i--)
{
var line = oneSide[i];
if (line.Type != Models.TextDiffLineType.None)
{
endContentLine = i;
break;
}
}
if (endContentLine < 0)
return;
var firstContent = oneSide[firstContentLine];
var endContent = oneSide[endContentLine];
startLine = combined.Lines.IndexOf(firstContent) + 1;
endLine = combined.Lines.IndexOf(endContent) + 1;
}
private void FillEmptyLines() private void FillEmptyLines()
{ {
if (Old.Count < New.Count) if (Old.Count < New.Count)

View file

@ -103,8 +103,8 @@
<TextBlock Classes="monospace" <TextBlock Classes="monospace"
Text="{Binding Subject}" Text="{Binding Subject}"
Opacity="{Binding IsMerged, Converter={x:Static c:BoolConverters.HalfIfFalse}}" Opacity="{Binding Opacity}"
FontWeight="{Binding IsCurrentHead, Converter={x:Static c:BoolConverters.BoldIfTrue}}"/> FontWeight="{Binding FontWeight}"/>
</StackPanel> </StackPanel>
</Border> </Border>
</DataTemplate> </DataTemplate>
@ -124,13 +124,13 @@
VerticalAlignment="Center" VerticalAlignment="Center"
IsHitTestVisible="False" IsHitTestVisible="False"
User="{Binding Author}" User="{Binding Author}"
Opacity="{Binding IsMerged, Converter={x:Static c:BoolConverters.HalfIfFalse}}"/> Opacity="{Binding Opacity}"/>
<TextBlock Grid.Column="1" <TextBlock Grid.Column="1"
Classes="monospace" Classes="monospace"
Text="{Binding Author.Name}" Text="{Binding Author.Name}"
Margin="8,0,0,0" Margin="8,0,0,0"
Opacity="{Binding IsMerged, Converter={x:Static c:BoolConverters.HalfIfFalse}}" Opacity="{Binding Opacity}"
FontWeight="{Binding IsCurrentHead, Converter={x:Static c:BoolConverters.BoldIfTrue}}"/> FontWeight="{Binding FontWeight}"/>
</Grid> </Grid>
</DataTemplate> </DataTemplate>
</DataGridTemplateColumn.CellTemplate> </DataGridTemplateColumn.CellTemplate>
@ -147,8 +147,8 @@
Text="{Binding SHA, Converter={x:Static c:StringConverters.ToShortSHA}}" Text="{Binding SHA, Converter={x:Static c:StringConverters.ToShortSHA}}"
Margin="8,0" Margin="8,0"
HorizontalAlignment="Center" HorizontalAlignment="Center"
Opacity="{Binding IsMerged, Converter={x:Static c:BoolConverters.HalfIfFalse}}" Opacity="{Binding Opacity}"
FontWeight="{Binding IsCurrentHead, Converter={x:Static c:BoolConverters.BoldIfTrue}}"/> FontWeight="{Binding FontWeight}"/>
</DataTemplate> </DataTemplate>
</DataGridTemplateColumn.CellTemplate> </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn> </DataGridTemplateColumn>
@ -169,8 +169,8 @@
<v:CommitTimeTextBlock Classes="monospace" <v:CommitTimeTextBlock Classes="monospace"
Margin="8,0" Margin="8,0"
HorizontalAlignment="Center" HorizontalAlignment="Center"
Opacity="{Binding IsMerged, Converter={x:Static c:BoolConverters.HalfIfFalse}}" Opacity="{Binding Opacity}"
FontWeight="{Binding IsCurrentHead, Converter={x:Static c:BoolConverters.BoldIfTrue}}" FontWeight="{Binding FontWeight}"
Timestamp="{Binding CommitterTime}" Timestamp="{Binding CommitterTime}"
ShowAsDateTime="{Binding Source={x:Static vm:Preference.Instance}, Path=!DisplayTimeAsPeriodInHistories}"/> ShowAsDateTime="{Binding Source={x:Static vm:Preference.Instance}, Path=!DisplayTimeAsPeriodInHistories}"/>
</DataTemplate> </DataTemplate>

View file

@ -29,6 +29,17 @@ namespace SourceGit.Views
public double Height { get; set; } = 0.0; public double Height { get; set; } = 0.0;
public int StartIdx { get; set; } = 0; public int StartIdx { get; set; } = 0;
public int EndIdx { get; set; } = 0; public int EndIdx { get; set; } = 0;
public bool ShouldReplace(TextViewHighlightChunk old)
{
if (old == null)
return true;
return Math.Abs(Y - old.Y) > 0.001 ||
Math.Abs(Height - old.Height) > 0.001 ||
StartIdx != old.StartIdx ||
EndIdx != old.EndIdx;
}
} }
public class ThemedTextDiffPresenter : TextEditor public class ThemedTextDiffPresenter : TextEditor
@ -158,11 +169,11 @@ namespace SourceGit.Views
return; return;
var color = (Color)this.FindResource("SystemAccentColor"); var color = (Color)this.FindResource("SystemAccentColor");
var brush = new SolidColorBrush(color, 0.5); var brush = new SolidColorBrush(color, 0.1);
var pen = new Pen(color.ToUInt32()); var pen = new Pen(color.ToUInt32());
var x = ((Point)view.TranslatePoint(new Point(0, 0), this)).X; var x = ((Point)view.TranslatePoint(new Point(0, 0), this)).X;
var rect = new Rect(x - 4, highlightChunk.Y, view.Bounds.Width + 8, highlightChunk.Height); var rect = new Rect(x - 4, highlightChunk.Y, view.Bounds.Width + 7, highlightChunk.Height);
context.DrawRectangle(brush, null, rect); context.DrawRectangle(brush, null, rect);
context.DrawLine(pen, rect.TopLeft, rect.TopRight); context.DrawLine(pen, rect.TopLeft, rect.TopRight);
@ -214,6 +225,21 @@ namespace SourceGit.Views
} }
} }
protected void TrySetHighlightChunk(TextViewHighlightChunk chunk)
{
var old = HighlightChunk;
if (chunk == null)
{
if (old != null)
SetCurrentValue(HighlightChunkProperty, null);
return;
}
if (chunk.ShouldReplace(old))
SetCurrentValue(HighlightChunkProperty, chunk);
}
protected (int, int) FindRangeByIndex(List<Models.TextDiffLine> lines, int lineIdx) protected (int, int) FindRangeByIndex(List<Models.TextDiffLine> lines, int lineIdx)
{ {
var startIdx = -1; var startIdx = -1;
@ -598,7 +624,7 @@ namespace SourceGit.Views
if (!string.IsNullOrEmpty(SelectedText)) if (!string.IsNullOrEmpty(SelectedText))
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
@ -622,14 +648,14 @@ namespace SourceGit.Views
if (lineIdx == -1) if (lineIdx == -1)
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
var (startIdx, endIdx) = FindRangeByIndex(DiffData.Lines, lineIdx); var (startIdx, endIdx) = FindRangeByIndex(DiffData.Lines, lineIdx);
if (startIdx == -1) if (startIdx == -1)
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
@ -643,14 +669,13 @@ namespace SourceGit.Views
endLine.GetTextLineVisualYPosition(endLine.TextLines[^1], VisualYPosition.TextBottom) - view.VerticalOffset: endLine.GetTextLineVisualYPosition(endLine.TextLines[^1], VisualYPosition.TextBottom) - view.VerticalOffset:
view.Bounds.Height; view.Bounds.Height;
var hightlight = new TextViewHighlightChunk() TrySetHighlightChunk(new TextViewHighlightChunk()
{ {
Y = rectStartY, Y = rectStartY,
Height = rectEndY - rectStartY, Height = rectEndY - rectStartY,
StartIdx = startIdx, StartIdx = startIdx,
EndIdx = endIdx, EndIdx = endIdx,
}; });
SetCurrentValue(HighlightChunkProperty, hightlight);
} }
} }
@ -982,14 +1007,14 @@ namespace SourceGit.Views
if (!string.IsNullOrEmpty(SelectedText)) if (!string.IsNullOrEmpty(SelectedText))
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
var parentView = this.FindAncestorOfType<TextDiffView>(); var parentView = this.FindAncestorOfType<TextDiffView>();
if (parentView == null || parentView.DataContext == null) if (parentView == null || parentView.DataContext == null)
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
@ -1015,14 +1040,14 @@ namespace SourceGit.Views
if (lineIdx == -1) if (lineIdx == -1)
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
var (startIdx, endIdx) = FindRangeByIndex(lines, lineIdx); var (startIdx, endIdx) = FindRangeByIndex(lines, lineIdx);
if (startIdx == -1) if (startIdx == -1)
{ {
SetCurrentValue(HighlightChunkProperty, null); TrySetHighlightChunk(null);
return; return;
} }
@ -1036,14 +1061,13 @@ namespace SourceGit.Views
endLine.GetTextLineVisualYPosition(endLine.TextLines[^1], VisualYPosition.TextBottom) - view.VerticalOffset : endLine.GetTextLineVisualYPosition(endLine.TextLines[^1], VisualYPosition.TextBottom) - view.VerticalOffset :
view.Bounds.Height; view.Bounds.Height;
var hightlight = new TextViewHighlightChunk() TrySetHighlightChunk(new TextViewHighlightChunk()
{ {
Y = rectStartY, Y = rectStartY,
Height = rectEndY - rectStartY, Height = rectEndY - rectStartY,
StartIdx = textDiff.Lines.IndexOf(lines[startIdx]), StartIdx = textDiff.Lines.IndexOf(lines[startIdx]),
EndIdx = textDiff.Lines.IndexOf(lines[endIdx]), EndIdx = endIdx == lines.Count - 1 ? textDiff.Lines.Count - 1 : textDiff.Lines.IndexOf(lines[endIdx]),
}; });
SetCurrentValue(HighlightChunkProperty, hightlight);
} }
} }
@ -1135,10 +1159,10 @@ namespace SourceGit.Views
if (startLine > endLine) if (startLine > endLine)
(startLine, endLine) = (endLine, startLine); (startLine, endLine) = (endLine, startLine);
if (UseSideBySideDiff) if (Editor.Content is ViewModels.TwoSideTextDiff twoSides)
(startLine, endLine) = GetUnifiedRange(diff, startLine, endLine, isOldSide); twoSides.ConvertsToCombinedRange(diff, ref startLine, ref endLine, isOldSide);
var selection = MakeSelection(diff, startLine, endLine, isOldSide); var selection = diff.MakeSelection(startLine, endLine, UseSideBySideDiff, isOldSide);
if (!selection.HasChanges) if (!selection.HasChanges)
return; return;
@ -1405,7 +1429,7 @@ namespace SourceGit.Views
if (change == null) if (change == null)
return; return;
var selection = MakeSelection(diff, chunk.StartIdx + 1, chunk.EndIdx + 1, false); var selection = diff.MakeSelection(chunk.StartIdx + 1, chunk.EndIdx + 1, false, false);
if (!selection.HasChanges) if (!selection.HasChanges)
return; return;
@ -1463,7 +1487,7 @@ namespace SourceGit.Views
if (change == null) if (change == null)
return; return;
var selection = MakeSelection(diff, chunk.StartIdx + 1, chunk.EndIdx + 1, false); var selection = diff.MakeSelection(chunk.StartIdx + 1, chunk.EndIdx + 1, false, false);
if (!selection.HasChanges) if (!selection.HasChanges)
return; return;
@ -1519,7 +1543,7 @@ namespace SourceGit.Views
if (change == null) if (change == null)
return; return;
var selection = MakeSelection(diff, chunk.StartIdx + 1, chunk.EndIdx + 1, false); var selection = diff.MakeSelection(chunk.StartIdx + 1, chunk.EndIdx + 1, false, false);
if (!selection.HasChanges) if (!selection.HasChanges)
return; return;
@ -1564,122 +1588,5 @@ namespace SourceGit.Views
repo.SetWatcherEnabled(true); repo.SetWatcherEnabled(true);
} }
} }
private (int, int) GetUnifiedRange(Models.TextDiff diff, int startLine, int endLine, bool isOldSide)
{
endLine = Math.Min(endLine, diff.Lines.Count);
if (Editor.Content is ViewModels.TwoSideTextDiff twoSides)
{
var target = isOldSide ? twoSides.Old : twoSides.New;
var firstContentLine = -1;
for (int i = startLine - 1; i < endLine; i++)
{
var line = target[i];
if (line.Type != Models.TextDiffLineType.None)
{
firstContentLine = i;
break;
}
}
if (firstContentLine < 0)
return (-1, -1);
var endContentLine = -1;
for (int i = Math.Min(endLine - 1, target.Count - 1); i >= startLine - 1; i--)
{
var line = target[i];
if (line.Type != Models.TextDiffLineType.None)
{
endContentLine = i;
break;
}
}
if (endContentLine < 0)
return (-1, -1);
var firstContent = target[firstContentLine];
var endContent = target[endContentLine];
startLine = diff.Lines.IndexOf(firstContent) + 1;
endLine = diff.Lines.IndexOf(endContent) + 1;
}
return (startLine, endLine);
}
private Models.TextDiffSelection MakeSelection(Models.TextDiff diff, int startLine, int endLine, bool isOldSide)
{
var rs = new Models.TextDiffSelection();
rs.StartLine = startLine;
rs.EndLine = endLine;
for (int i = 0; i < startLine - 1; i++)
{
var line = diff.Lines[i];
if (line.Type == Models.TextDiffLineType.Added)
{
rs.HasLeftChanges = true;
rs.IgnoredAdds++;
}
else if (line.Type == Models.TextDiffLineType.Deleted)
{
rs.HasLeftChanges = true;
rs.IgnoredDeletes++;
}
}
for (int i = startLine - 1; i < endLine; i++)
{
var line = diff.Lines[i];
if (line.Type == Models.TextDiffLineType.Added)
{
if (!UseSideBySideDiff)
{
rs.HasChanges = true;
break;
}
else if (isOldSide)
{
rs.HasLeftChanges = true;
}
else
{
rs.HasChanges = true;
}
}
else if (line.Type == Models.TextDiffLineType.Deleted)
{
if (!UseSideBySideDiff)
{
rs.HasChanges = true;
break;
}
else if (isOldSide)
{
rs.HasChanges = true;
}
else
{
rs.HasLeftChanges = true;
}
}
}
if (!rs.HasLeftChanges)
{
for (int i = endLine; i < diff.Lines.Count; i++)
{
var line = diff.Lines[i];
if (line.Type == Models.TextDiffLineType.Added || line.Type == Models.TextDiffLineType.Deleted)
{
rs.HasLeftChanges = true;
break;
}
}
}
return rs;
}
} }
} }