SubtitleEdit/libse/Forms/FixCommonErrors/FixEmptyLines.cs
2019-08-16 22:55:32 +02:00

157 lines
6.1 KiB
C#

using System;
using Nikse.SubtitleEdit.Core.Interfaces;
namespace Nikse.SubtitleEdit.Core.Forms.FixCommonErrors
{
public class FixEmptyLines : IFixCommonError
{
public void Fix(Subtitle subtitle, IFixCallbacks callbacks)
{
var language = Configuration.Settings.Language.FixCommonErrors;
string fixAction0 = language.RemovedEmptyLine;
string fixAction1 = language.RemovedEmptyLineAtTop;
string fixAction2 = language.RemovedEmptyLineAtBottom;
string fixAction3 = language.RemovedEmptyLineInMiddle;
if (subtitle.Paragraphs.Count == 0)
{
return;
}
int emptyLinesRemoved = 0;
for (int i = subtitle.Paragraphs.Count - 1; i >= 0; i--)
{
Paragraph p = subtitle.Paragraphs[i];
if (!string.IsNullOrEmpty(p.Text))
{
string text = p.Text.Trim(' ');
var oldText = text;
var pre = string.Empty;
var post = string.Empty;
// Ssa Tags
if (text.StartsWith("{\\", StringComparison.Ordinal))
{
var endIdx = text.IndexOf('}', 2);
if (endIdx > 2)
{
pre = text.Substring(0, endIdx + 1);
text = text.Remove(0, endIdx + 1);
}
}
while (text.LineStartsWithHtmlTag(true, true))
{
// Three length tag
if (text[2] == '>')
{
pre += text.Substring(0, 3);
text = text.Remove(0, 3);
}
else // <font ...>
{
var closeIdx = text.IndexOf('>');
if (closeIdx <= 2)
{
break;
}
pre += text.Substring(0, closeIdx + 1);
text = text.Remove(0, closeIdx + 1);
}
}
while (text.LineEndsWithHtmlTag(true, true))
{
var len = text.Length;
// Three length tag
if (text[len - 4] == '<')
{
post = text.Substring(text.Length - 4) + post;
text = text.Remove(text.Length - 4);
}
else // </font>
{
post = text.Substring(text.Length - 7) + post;
text = text.Remove(text.Length - 7);
}
}
if (callbacks.AllowFix(p, fixAction1) && text.StartsWith(Environment.NewLine, StringComparison.Ordinal))
{
if (pre.Length > 0)
{
text = pre + text.TrimStart(Utilities.NewLineChars);
}
else
{
text = text.TrimStart(Utilities.NewLineChars);
}
p.Text = text;
emptyLinesRemoved++;
callbacks.AddFixToListView(p, fixAction1, oldText, p.Text);
}
else
{
text = pre + text;
}
if (callbacks.AllowFix(p, fixAction2) && text.EndsWith(Environment.NewLine, StringComparison.Ordinal))
{
if (post.Length > 0)
{
text = text.TrimEnd(Utilities.NewLineChars) + post;
}
else
{
text = text.TrimEnd(Utilities.NewLineChars);
}
p.Text = text;
emptyLinesRemoved++;
callbacks.AddFixToListView(p, fixAction2, oldText, p.Text);
}
if (Configuration.Settings.Tools.RemoveEmptyLinesBetweenText &&
callbacks.AllowFix(p, fixAction3) && text.Contains(Environment.NewLine + Environment.NewLine))
{
int beforeLength = text.Length;
while (text.Contains(Environment.NewLine + Environment.NewLine))
{
text = text.Replace(Environment.NewLine + Environment.NewLine, Environment.NewLine);
}
p.Text = text;
emptyLinesRemoved += (beforeLength - text.Length) / Environment.NewLine.Length;
callbacks.AddFixToListView(p, fixAction3, oldText, p.Text);
}
}
}
// this must be the very last action done, or line numbers will be messed up!!!
for (int i = subtitle.Paragraphs.Count - 1; i >= 0; i--)
{
Paragraph p = subtitle.Paragraphs[i];
var text = HtmlUtil.RemoveHtmlTags(p.Text, true).Trim();
if (callbacks.AllowFix(p, fixAction0) && string.IsNullOrEmpty(text.RemoveControlCharacters()))
{
subtitle.Paragraphs.RemoveAt(i);
emptyLinesRemoved++;
callbacks.AddFixToListView(p, fixAction0, p.Text, $"[{language.RemovedEmptyLine}]");
callbacks.AddToDeleteIndices(i);
}
}
if (emptyLinesRemoved > 0)
{
callbacks.UpdateFixStatus(emptyLinesRemoved, language.RemovedEmptyLinesUnsedLineBreaks, string.Format(language.EmptyLinesRemovedX, emptyLinesRemoved));
subtitle.Renumber();
}
}
}
}