Skip to content

Commit

Permalink
Check for Duplicates In Mining Mode (#109)
Browse files Browse the repository at this point in the history
* Check for Duplicates In Mining Mode

* Remove alert for Dupe detection

* Do Duplicate Check After the fact

* Remove unused import

* PR Review Changes

Moved Icon to the end of the row so we can actually toggle visibility of the icon instead of uncollapse it
PR review changes like return types, array instead of List, etc.
Changed to Textblock instead of button
Made method to get first mining param instead of getting everything and then only getting the first.

* remove unused import

* PR Review Changes #3

Fill out GetMiningParameter Method
Move duplicateIcons List out of Fields
More small Object/List Related Changes

* remove debug

* PR Review Changes

Add braces to case
refactor frequencies to inline conditional
get rid of unused var in Preferred Frequency
move unused and default cases to top
moved ankiconfigcheck
downmerged from upstream
changed to array instead of list per upstream change
other small pr related changes

* Suggested primarySpellingandFirstReading change

Co-authored-by: rampaa <[email protected]>

---------

Co-authored-by: rampaa <[email protected]>
  • Loading branch information
bpwhelan and rampaa authored Dec 12, 2024
1 parent d8a3cb9 commit b80e5f0
Show file tree
Hide file tree
Showing 7 changed files with 400 additions and 8 deletions.
2 changes: 2 additions & 0 deletions JL.Core/Config/CoreConfigManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ public sealed class CoreConfigManager
public bool AnkiIntegration { get; set; } // = false;
public bool ForceSyncAnki { get; private set; } // = false;
public bool AllowDuplicateCards { get; private set; } // = false;
public bool CheckForDuplicateCards { get; private set; } // = false;
public double LookupRate { get; private set; } // = 0;
public bool CaptureTextFromClipboard { get; set; } = true;
public bool CaptureTextFromWebSocket { get; set; } // = false;
Expand Down Expand Up @@ -95,6 +96,7 @@ public void ApplyPreferences(SqliteConnection connection)
AnkiIntegration = ConfigDBManager.GetValueFromConfig(connection, AnkiIntegration, nameof(AnkiIntegration), bool.TryParse);
ForceSyncAnki = ConfigDBManager.GetValueFromConfig(connection, ForceSyncAnki, nameof(ForceSyncAnki), bool.TryParse);
AllowDuplicateCards = ConfigDBManager.GetValueFromConfig(connection, AllowDuplicateCards, nameof(AllowDuplicateCards), bool.TryParse);
CheckForDuplicateCards = ConfigDBManager.GetValueFromConfig(connection, CheckForDuplicateCards, nameof(CheckForDuplicateCards), bool.TryParse);
LookupRate = ConfigDBManager.GetNumberWithDecimalPointFromConfig(connection, LookupRate, nameof(LookupRate), double.TryParse);
TextBoxTrimWhiteSpaceCharacters = ConfigDBManager.GetValueFromConfig(connection, TextBoxTrimWhiteSpaceCharacters, nameof(TextBoxTrimWhiteSpaceCharacters), bool.TryParse);
TextBoxRemoveNewlines = ConfigDBManager.GetValueFromConfig(connection, TextBoxRemoveNewlines, nameof(TextBoxRemoveNewlines), bool.TryParse);
Expand Down
7 changes: 2 additions & 5 deletions JL.Core/Mining/Anki/AnkiConnect.cs
Original file line number Diff line number Diff line change
Expand Up @@ -42,15 +42,12 @@ internal static class AnkiConnect
return Send(req);
}

public static ValueTask<Response?> GetCanAddNotesResponse(Note note)
public static ValueTask<Response?> GetCanAddNotesResponse(List<Note> notes)
{
Request req = new("canAddNotes", 6, new Dictionary<string, object>(1, StringComparer.Ordinal)
{
{
"notes", new[]
{
note
}
"notes", notes
}
});

Expand Down
12 changes: 11 additions & 1 deletion JL.Core/Mining/Anki/AnkiUtils.cs
Original file line number Diff line number Diff line change
Expand Up @@ -37,11 +37,21 @@ public static class AnkiUtils

internal static async Task<bool?> CanAddNote(Note note)
{
Response? response = await AnkiConnect.GetCanAddNotesResponse(note).ConfigureAwait(false);
Response? response = await AnkiConnect.GetCanAddNotesResponse([note]).ConfigureAwait(false);
string? resultString = response?.Result?.ToString() ?? null;

return resultString is not null
? JsonSerializer.Deserialize<List<bool>>(resultString)![0]
: null;
}

internal static async ValueTask<List<bool>?> CanAddNotes(List<Note> notes)
{
Response? response = await AnkiConnect.GetCanAddNotesResponse(notes).ConfigureAwait(false);
string? resultString = response?.Result?.ToString() ?? null;

return resultString is not null
? JsonSerializer.Deserialize<List<bool>>(resultString)
: null;
}
}
318 changes: 318 additions & 0 deletions JL.Core/Mining/MiningUtils.cs

Large diffs are not rendered by default.

4 changes: 4 additions & 0 deletions JL.Windows/ConfigManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -836,6 +836,7 @@ public void LoadPreferenceWindow(PreferencesWindow preferenceWindow)
preferenceWindow.WebSocketUriTextBox.Text = coreConfigManager.WebSocketUri.OriginalString;
preferenceWindow.ForceSyncAnkiCheckBox.IsChecked = coreConfigManager.ForceSyncAnki;
preferenceWindow.AllowDuplicateCardsCheckBox.IsChecked = coreConfigManager.AllowDuplicateCards;
preferenceWindow.CheckForDuplicateCardsCheckBox.IsChecked = coreConfigManager.CheckForDuplicateCards;
preferenceWindow.LookupRateNumericUpDown.Value = coreConfigManager.LookupRate;
preferenceWindow.KanjiModeCheckBox.IsChecked = coreConfigManager.KanjiMode;
preferenceWindow.AutoAdjustFontSizesOnResolutionChangeCheckBox.IsChecked = AutoAdjustFontSizesOnResolutionChange;
Expand Down Expand Up @@ -1205,6 +1206,9 @@ public async Task SavePreferences(PreferencesWindow preferenceWindow)
ConfigDBManager.UpdateSetting(connection, nameof(CoreConfigManager.AllowDuplicateCards),
preferenceWindow.AllowDuplicateCardsCheckBox.IsChecked.ToString()!);

ConfigDBManager.UpdateSetting(connection, nameof(CoreConfigManager.CheckForDuplicateCards),
preferenceWindow.CheckForDuplicateCardsCheckBox.IsChecked.ToString()!);

ConfigDBManager.UpdateSetting(connection, nameof(CoreConfigManager.LookupRate),
preferenceWindow.LookupRateNumericUpDown.Value.ToString(CultureInfo.InvariantCulture));

Expand Down
58 changes: 56 additions & 2 deletions JL.Windows/GUI/PopupWindow.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -477,6 +477,8 @@ private void UpdatePosition(double x, double y)

public void DisplayResults(bool generateAllResults)
{
ConfigManager configManager = ConfigManager.Instance;
CoreConfigManager coreConfigManager = CoreConfigManager.Instance;
_dictsWithResults.Clear();

PopupListView.Items.Filter = PopupWindowUtils.NoAllDictFilter;
Expand All @@ -497,6 +499,15 @@ public void DisplayResults(bool generateAllResults)
? LastLookupResults.Length
: Math.Min(LastLookupResults.Length, ConfigManager.Instance.MaxNumResultsNotInMiningMode);

bool checkForDuplicateCards = MiningMode
&& coreConfigManager.CheckForDuplicateCards
&& !configManager.MineToFileInsteadOfAnki
&& coreConfigManager.AnkiIntegration;

TextBlock[]? duplicateIcons = checkForDuplicateCards
? new TextBlock[LastLookupResults.Length]
: null;

StackPanel[] popupItemSource = new StackPanel[resultCount];

for (int i = 0; i < resultCount; i++)
Expand All @@ -508,10 +519,14 @@ public void DisplayResults(bool generateAllResults)
_dictsWithResults.Add(lookupResult.Dict);
}

popupItemSource[i] = PrepareResultStackPanel(lookupResult, i, resultCount, pitchDict, pitchDictIsActive, showPOrthographyInfo, showROrthographyInfo, showAOrthographyInfo, pOrthographyInfoFontSize);
popupItemSource[i] = PrepareResultStackPanel(lookupResult, i, resultCount, pitchDict, pitchDictIsActive, showPOrthographyInfo, showROrthographyInfo, showAOrthographyInfo, pOrthographyInfoFontSize, duplicateIcons);
}

PopupListView.ItemsSource = popupItemSource;
if (duplicateIcons is not null)
{
_ = CheckResultForDuplicates(duplicateIcons);
}
GenerateDictTypeButtons();
UpdateLayout();
}
Expand All @@ -536,7 +551,7 @@ private void AddEventHandlersToDefinitionsTextBox(TextBox textBox)
textBox.PreviewMouseLeftButtonDown += DefinitionsTextBox_PreviewMouseLeftButtonDown;
}

private StackPanel PrepareResultStackPanel(LookupResult result, int index, int resultCount, Dict? pitchDict, bool pitchDictIsActive, bool showPOrthographyInfo, bool showROrthographyInfo, bool showAOrthographyInfo, double pOrthographyInfoFontSize)
private StackPanel PrepareResultStackPanel(LookupResult result, int index, int resultCount, Dict? pitchDict, bool pitchDictIsActive, bool showPOrthographyInfo, bool showROrthographyInfo, bool showAOrthographyInfo, double pOrthographyInfoFontSize, TextBlock[]? duplicateIcons)
{
// top
WrapPanel top = new()
Expand Down Expand Up @@ -797,6 +812,29 @@ private StackPanel PrepareResultStackPanel(LookupResult result, int index, int r
_ = top.Children.Add(dictTypeTextBlock);
}

// Keep this at the bottom
if (duplicateIcons is not null)
{
TextBlock duplicate = new()
{
Text = "⚠",
Name = nameof(duplicate),
FontSize = configManager.DictTypeFontSize,
Foreground = configManager.DefinitionsColor,
VerticalAlignment = VerticalAlignment.Top,
Margin = new Thickness(7, 0, 0, 0),
HorizontalAlignment = HorizontalAlignment.Left,
Background = Brushes.Transparent,
Cursor = Cursors.Arrow,
Padding = new Thickness(0),
ToolTip = $"{result.PrimarySpelling} is already in the Anki deck.",
Visibility = Visibility.Hidden
};

_ = top.Children.Add(duplicate);
duplicateIcons[index] = duplicate;
}

// bottom
StackPanel bottom = new();

Expand Down Expand Up @@ -1071,6 +1109,22 @@ private StackPanel PrepareResultStackPanel(LookupResult result, int index, int r
return stackPanel;
}

private async Task CheckResultForDuplicates(TextBlock[] duplicateIcons)
{
bool[]? duplicateCard = await MiningUtils.CheckDuplicates(LastLookupResults, _currentText, _currentCharPosition).ConfigureAwait(false);

if (duplicateCard is not null)
{
for (int i = 0; i < duplicateCard.Length; i++)
{
if (duplicateCard[i])
{
await MainWindow.Instance.Dispatcher.InvokeAsync(() => { duplicateIcons[i].Visibility = Visibility.Visible; });
}
}
}
}

private int GetFirstVisibleListViewItemIndex()
{
StackPanel? firstVisibleStackPanel = PopupListView.Items.Cast<StackPanel>()
Expand Down
7 changes: 7 additions & 0 deletions JL.Windows/GUI/PreferencesWindow.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -1032,6 +1032,13 @@
<CheckBox x:Name="AllowDuplicateCardsCheckBox" HorizontalAlignment="Right" />
</DockPanel>

<DockPanel Margin="0,10,0,0">
<TextBlock HorizontalAlignment="Left" Text="Check for duplicate cards"
Style="{StaticResource TextBlockDefault}" VerticalAlignment="Center" TextWrapping="Wrap"
ToolTip="Checks Anki for Duplicate Expressions when entering Mining Mode" Cursor="Help"/>
<CheckBox x:Name="CheckForDuplicateCardsCheckBox" HorizontalAlignment="Right" />
</DockPanel>

<TabControl Margin="0,10,0,0">
<TabControl.Resources>
<Style TargetType="{x:Type TabPanel}">
Expand Down

0 comments on commit b80e5f0

Please sign in to comment.