Add "Multiple Languages" option for OCR

This commit is contained in:
Ben Olden-Cooligan 2024-02-17 10:47:15 -08:00
parent 5001d4278a
commit f128f8fbcc
6 changed files with 138 additions and 7 deletions

View File

@ -120,6 +120,9 @@ public class CommonConfig
[Common]
public string? OcrLanguageCode { get; set; }
[Common]
public string? LastOcrMultiLangCode { get; set; }
[Common]
public LocalizedOcrMode OcrMode { get; set; }
@ -188,5 +191,4 @@ public class CommonConfig
[Common]
public bool DisableScannerSharing { get; set; }
}

View File

@ -48,6 +48,7 @@ public static class InternalDefaults
OcrTimeoutInSeconds = 10 * 60, // 10 minutes
EnableOcr = false,
OcrLanguageCode = "",
LastOcrMultiLangCode = "",
OcrMode = LocalizedOcrMode.Fast,
OcrAfterScanning = true,
LastImageExt = "",

View File

@ -0,0 +1,48 @@
using Eto.Drawing;
using NAPS2.EtoForms.Layout;
using NAPS2.EtoForms.Widgets;
using NAPS2.Ocr;
namespace NAPS2.EtoForms.Ui;
public class OcrMultiLangForm : EtoDialogBase
{
private readonly IListView<Language> _languageList;
public OcrMultiLangForm(Naps2Config config, TesseractLanguageManager tesseractLanguageManager,
OcrLanguagesListViewBehavior ocrLanguagesListViewBehavior) : base(config)
{
_languageList = EtoPlatform.Current.CreateListView(ocrLanguagesListViewBehavior);
_languageList.SetItems(tesseractLanguageManager.InstalledLanguages.OrderBy(x => x.Name));
}
public string? Code { get; private set; }
protected override void BuildLayout()
{
Title = UiStrings.OcrMultiLangFormTitle;
Icon = new Icon(1f, Icons.text_small.ToEtoImage());
FormStateController.RestoreFormState = false;
FormStateController.DefaultExtraLayoutSize = new Size(150, 20);
LayoutController.Content = L.Column(
_languageList.Control.Scale(),
C.Spacer(),
L.Row(
C.Filler(),
L.OkCancel(
C.OkButton(this, Save),
C.CancelButton(this))
)
);
}
private void Save()
{
if (_languageList.Selection.Count > 0)
{
Code = string.Join("+", _languageList.Selection.OrderBy(x => x.Name).Select(lang => lang.Code));
}
}
}

View File

@ -1,3 +1,4 @@
using System.Globalization;
using Eto.Drawing;
using Eto.Forms;
using NAPS2.EtoForms.Layout;
@ -15,6 +16,10 @@ public class OcrSetupForm : EtoDialogBase
private readonly CheckBox _ocrAfterScanning = C.CheckBox(UiStrings.RunOcrAfterScanning);
private readonly LinkButton _moreLanguages = C.Link(UiStrings.GetMoreLanguages);
private string? _code;
private string? _multiLangCode;
private bool _suppressLangChangeEvent;
public OcrSetupForm(Naps2Config config, TesseractLanguageManager tesseractLanguageManager) : base(config)
{
_tesseractLanguageManager = tesseractLanguageManager;
@ -22,8 +27,6 @@ public class OcrSetupForm : EtoDialogBase
_enableOcr.CheckedChanged += EnableOcr_CheckedChanged;
_moreLanguages.Click += MoreLanguages_Click;
LoadLanguages();
var configOcrMode = Config.Get(c => c.OcrMode);
if (configOcrMode == LocalizedOcrMode.Legacy)
{
@ -31,13 +34,16 @@ public class OcrSetupForm : EtoDialogBase
configOcrMode = LocalizedOcrMode.Fast;
}
_code = Config.Get(c => c.OcrLanguageCode);
_multiLangCode = Config.Get(c => c.LastOcrMultiLangCode);
_enableOcr.Checked = Config.Get(c => c.EnableOcr);
_ocrLang.SelectedKey = Config.Get(c => c.OcrLanguageCode) ?? "";
if (_ocrLang.SelectedIndex == -1) _ocrLang.SelectedIndex = 0;
_ocrLang.SelectedIndexChanged += OcrLang_SelectedIndexChanged;
_ocrMode.SelectedIndex = (int) configOcrMode;
if (_ocrMode.SelectedIndex == -1) _ocrMode.SelectedIndex = 0;
_ocrAfterScanning.Checked = Config.Get(c => c.OcrAfterScanning);
LoadLanguages();
UpdateView();
}
@ -73,17 +79,43 @@ public class OcrSetupForm : EtoDialogBase
private void LoadLanguages()
{
_suppressLangChangeEvent = true;
var languages = _tesseractLanguageManager.InstalledLanguages
.OrderBy(x => x.Name)
.ToList();
var selectedKey = _ocrLang.SelectedKey;
_ocrLang.Items.Clear();
_ocrLang.Items.AddRange(languages.Select(lang => new ListItem
{
Key = lang.Code,
Text = lang.Name
}));
_ocrLang.SelectedKey = selectedKey;
if (languages.Count > 1)
{
if (_multiLangCode?.Contains("+") == true)
{
_ocrLang.Items.Add(new ListItem
{
Key = _multiLangCode,
Text = string.Join($"{CultureInfo.CurrentCulture.TextInfo.ListSeparator} ",
_multiLangCode.Split('+')
.Select(code => languages.SingleOrDefault(lang => lang.Code == code)?.Name))
});
}
_ocrLang.Items.Add(new ListItem
{
Key = "",
Text = UiStrings.MultipleLanguages
});
}
if (!string.IsNullOrEmpty(_code))
{
_ocrLang.SelectedKey = _code;
}
if (_ocrLang.SelectedIndex == -1)
{
_ocrLang.SelectedIndex = 0;
}
_suppressLangChangeEvent = false;
}
private void UpdateView()
@ -107,6 +139,26 @@ public class OcrSetupForm : EtoDialogBase
LoadLanguages();
}
private void OcrLang_SelectedIndexChanged(object sender, EventArgs e)
{
if (_suppressLangChangeEvent) return;
if (_ocrLang.SelectedIndex == _ocrLang.Items.Count - 1)
{
var multiLangForm = FormFactory.Create<OcrMultiLangForm>();
multiLangForm.ShowModal();
if (multiLangForm.Code != null)
{
_code = multiLangForm.Code;
}
if (multiLangForm.Code?.Contains("+") == true)
{
_multiLangCode = multiLangForm.Code;
}
LoadLanguages();
}
_code = _ocrLang.SelectedKey;
}
private void Save()
{
if (!Config.AppLocked.Has(c => c.EnableOcr))
@ -114,6 +166,10 @@ public class OcrSetupForm : EtoDialogBase
var transact = Config.User.BeginTransaction();
transact.Set(c => c.EnableOcr, _enableOcr.IsChecked());
transact.Set(c => c.OcrLanguageCode, _ocrLang.SelectedKey);
if (_multiLangCode?.Contains("+") == true)
{
Config.User.Set(c => c.LastOcrMultiLangCode, _multiLangCode);
}
transact.Set(c => c.OcrMode, (LocalizedOcrMode) _ocrMode.SelectedIndex);
transact.Set(c => c.OcrAfterScanning, _ocrAfterScanning.IsChecked());
transact.Commit();

View File

@ -1130,6 +1130,15 @@ namespace NAPS2.Lang.Resources {
}
}
/// <summary>
/// Looks up a localized string similar to Multiple Languages....
/// </summary>
internal static string MultipleLanguages {
get {
return ResourceManager.GetString("MultipleLanguages", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Multiple scans (fixed delay between scans).
/// </summary>
@ -1274,6 +1283,15 @@ namespace NAPS2.Lang.Resources {
}
}
/// <summary>
/// Looks up a localized string similar to Multiple Languages.
/// </summary>
internal static string OcrMultiLangFormTitle {
get {
return ResourceManager.GetString("OcrMultiLangFormTitle", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to Select one or more languages:.
/// </summary>

View File

@ -864,4 +864,10 @@
<data name="ShareAsService" xml:space="preserve">
<value>Share even when NAPS2 is closed</value>
</data>
<data name="MultipleLanguages" xml:space="preserve">
<value>Multiple Languages...</value>
</data>
<data name="OcrMultiLangFormTitle" xml:space="preserve">
<value>Multiple Languages</value>
</data>
</root>