From 591b00e538052543376e937a220aa6ef024ed10b Mon Sep 17 00:00:00 2001 From: Alan Kilborn Date: Fri, 22 Sep 2023 08:22:07 -0400 Subject: [PATCH] Make auto-checking of Find InSelection configurable (OFF or resizable) Set value to 0 to disable auto-checking "In Selection" checkbox in Find dialog. Set any value to define the length of selected characters to auto-check "In Selection" checkbox in Find dialog. The default and maximum value is 1024. Fix #14108, fix #13677, fix #12639, close #14175 --- PowerEditor/installer/nativeLang/english.xml | 2 + PowerEditor/src/NppCommands.cpp | 10 ++-- PowerEditor/src/Parameters.cpp | 14 +++++- PowerEditor/src/Parameters.h | 3 ++ .../src/ScintillaComponent/FindReplaceDlg.cpp | 36 +++++++++----- .../src/ScintillaComponent/FindReplaceDlg.h | 1 - .../src/WinControls/Preference/preference.rc | 18 ++++--- .../WinControls/Preference/preferenceDlg.cpp | 49 ++++++++++++++++++- .../WinControls/Preference/preferenceDlg.h | 8 +++ .../WinControls/Preference/preference_rc.h | 2 + 10 files changed, 117 insertions(+), 26 deletions(-) diff --git a/PowerEditor/installer/nativeLang/english.xml b/PowerEditor/installer/nativeLang/english.xml index ac8c32a76..1a5b7cf32 100644 --- a/PowerEditor/installer/nativeLang/english.xml +++ b/PowerEditor/installer/nativeLang/english.xml @@ -1146,6 +1146,7 @@ You can define several column markers by using white space to separate the diffe + @@ -1742,6 +1743,7 @@ Click on "?" button on right to open website with User Manual."/> + diff --git a/PowerEditor/src/NppCommands.cpp b/PowerEditor/src/NppCommands.cpp index 1215ba066..c4bd07fb6 100644 --- a/PowerEditor/src/NppCommands.cpp +++ b/PowerEditor/src/NppCommands.cpp @@ -1237,6 +1237,12 @@ void Notepad_plus::command(int id) const int strSize = FINDREPLACE_MAXLENGTH; TCHAR str[strSize] = { '\0' }; + const NppGUI& nppGui = (NppParameters::getInstance()).getNppGUI(); + if (nppGui._fillFindFieldWithSelected) + { + _pEditView->getGenericSelectedText(str, strSize, nppGui._fillFindFieldSelectCaret); + } + bool isFirstTime = !_findReplaceDlg.isCreated(); DIALOG_TYPE dlgID = FIND_DLG; @@ -1246,11 +1252,9 @@ void Notepad_plus::command(int id) dlgID = MARK_DLG; _findReplaceDlg.doDialog(dlgID, _nativeLangSpeaker.isRTL()); - const NppGUI & nppGui = (NppParameters::getInstance()).getNppGUI(); if (nppGui._fillFindFieldWithSelected) { - _pEditView->getGenericSelectedText(str, strSize, nppGui._fillFindFieldSelectCaret); - if (lstrlen(str) <= FINDREPLACE_INSEL_TEXTSIZE_THRESHOLD) + if (lstrlen(str) <= FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT) { _findReplaceDlg.setSearchText(str); } diff --git a/PowerEditor/src/Parameters.cpp b/PowerEditor/src/Parameters.cpp index 7ce306ac7..7630424ec 100644 --- a/PowerEditor/src/Parameters.cpp +++ b/PowerEditor/src/Parameters.cpp @@ -5946,6 +5946,17 @@ void NppParameters::feedGUIParameters(TiXmlNode *node) const TCHAR* optReplaceStopsWithoutFindingNext = element->Attribute(TEXT("replaceStopsWithoutFindingNext")); if (optReplaceStopsWithoutFindingNext) _nppGUI._replaceStopsWithoutFindingNext = (lstrcmp(optReplaceStopsWithoutFindingNext, TEXT("yes")) == 0); + + int inSelThresh; + if (element->Attribute(TEXT("inSelectionAutocheckThreshold"), &inSelThresh) && + (inSelThresh >= 0 && inSelThresh <= FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT)) + { + _nppGUI._inSelectionAutocheckThreshold = inSelThresh; + } + else + { + _nppGUI._inSelectionAutocheckThreshold = FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT; + } } else if (!lstrcmp(nm, TEXT("MISC"))) { @@ -7305,7 +7316,7 @@ void NppParameters::createXmlTreeFromGUIParams() GUIConfigElement->SetAttribute(TEXT("hideMenuRightShortcuts"), _nppGUI._hideMenuRightShortcuts ? TEXT("yes") : TEXT("no")); } - // + // { TiXmlElement* GUIConfigElement = (newGUIRoot->InsertEndChild(TiXmlElement(TEXT("GUIConfig"))))->ToElement(); GUIConfigElement->SetAttribute(TEXT("name"), TEXT("Searching")); @@ -7316,6 +7327,7 @@ void NppParameters::createXmlTreeFromGUIParams() GUIConfigElement->SetAttribute(TEXT("findDlgAlwaysVisible"), _nppGUI._findDlgAlwaysVisible ? TEXT("yes") : TEXT("no")); GUIConfigElement->SetAttribute(TEXT("confirmReplaceInAllOpenDocs"), _nppGUI._confirmReplaceInAllOpenDocs ? TEXT("yes") : TEXT("no")); GUIConfigElement->SetAttribute(TEXT("replaceStopsWithoutFindingNext"), _nppGUI._replaceStopsWithoutFindingNext ? TEXT("yes") : TEXT("no")); + GUIConfigElement->SetAttribute(TEXT("inSelectionAutocheckThreshold"), _nppGUI._inSelectionAutocheckThreshold); } // diff --git a/PowerEditor/src/Parameters.h b/PowerEditor/src/Parameters.h index 15195ea27..09a3e57c1 100644 --- a/PowerEditor/src/Parameters.h +++ b/PowerEditor/src/Parameters.h @@ -137,6 +137,8 @@ const int COPYDATA_FULL_CMDLINE = 3; #define NPP_STYLING_FILESIZE_LIMIT_DEFAULT (200 * 1024 * 1024) // 200MB+ file won't be styled +const int FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT = 1024; + const TCHAR fontSizeStrs[][3] = {TEXT(""), TEXT("5"), TEXT("6"), TEXT("7"), TEXT("8"), TEXT("9"), TEXT("10"), TEXT("11"), TEXT("12"), TEXT("14"), TEXT("16"), TEXT("18"), TEXT("20"), TEXT("22"), TEXT("24"), TEXT("26"), TEXT("28")}; const TCHAR localConfFile[] = TEXT("doLocalConf.xml"); @@ -814,6 +816,7 @@ struct NppGUI final bool _findDlgAlwaysVisible = false; bool _confirmReplaceInAllOpenDocs = true; bool _replaceStopsWithoutFindingNext = false; + int _inSelectionAutocheckThreshold = FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT; bool _muteSounds = false; bool _enableFoldCmdToggable = false; bool _hideMenuRightShortcuts = false; diff --git a/PowerEditor/src/ScintillaComponent/FindReplaceDlg.cpp b/PowerEditor/src/ScintillaComponent/FindReplaceDlg.cpp index f5377efd3..6036c9b7c 100644 --- a/PowerEditor/src/ScintillaComponent/FindReplaceDlg.cpp +++ b/PowerEditor/src/ScintillaComponent/FindReplaceDlg.cpp @@ -1495,23 +1495,30 @@ intptr_t CALLBACK FindReplaceDlg::run_dlgProc(UINT message, WPARAM wParam, LPARA Sci_CharacterRangeFull cr = (*_ppEditView)->getSelection(); intptr_t nbSelected = cr.cpMax - cr.cpMin; - _options._isInSelection = nbSelected >= FINDREPLACE_INSEL_TEXTSIZE_THRESHOLD; + bool inSelEnabled = nbSelected != 0; // Searching/replacing in multiple selections or column selection is not allowed - if (((*_ppEditView)->execute(SCI_GETSELECTIONMODE) == SC_SEL_RECTANGLE) || ((*_ppEditView)->execute(SCI_GETSELECTIONS) > 1)) + if (((*_ppEditView)->execute(SCI_GETSELECTIONMODE) == SC_SEL_RECTANGLE) || + ((*_ppEditView)->execute(SCI_GETSELECTIONS) > 1)) { - _options._isInSelection = false; - nbSelected = 0; + inSelEnabled = false; } - enableFindDlgItem(IDC_IN_SELECTION_CHECK, nbSelected != 0); + enableFindDlgItem(IDC_IN_SELECTION_CHECK, inSelEnabled); - // uncheck if the control is disable - if (!nbSelected) + bool inSelChecked = isCheckedOrNot(IDC_IN_SELECTION_CHECK); + + const NppGUI& nppGui = (NppParameters::getInstance()).getNppGUI(); + if (nppGui._inSelectionAutocheckThreshold != 0) { - _options._isInSelection = false; + // code is allowed to change checkmark status of In-selection checkbox + + inSelChecked = inSelEnabled && (nbSelected >= nppGui._inSelectionAutocheckThreshold); + + setChecked(IDC_IN_SELECTION_CHECK, inSelChecked); } - ::SendDlgItemMessage(_hSelf, IDC_IN_SELECTION_CHECK, BM_SETCHECK, _options._isInSelection ? BST_CHECKED : BST_UNCHECKED, 0); + + _options._isInSelection = inSelEnabled && inSelChecked; } if (isCheckedOrNot(IDC_TRANSPARENT_LOSSFOCUS_RADIO)) @@ -2176,7 +2183,10 @@ intptr_t CALLBACK FindReplaceDlg::run_dlgProc(UINT message, WPARAM wParam, LPARA case IDC_IN_SELECTION_CHECK : { if ((_currentStatus == FIND_DLG) || (_currentStatus == REPLACE_DLG) || (_currentStatus == MARK_DLG)) - _options._isInSelection = isCheckedOrNot(IDC_IN_SELECTION_CHECK); + { + _options._isInSelection = ::IsWindowEnabled(::GetDlgItem(_hSelf, IDC_IN_SELECTION_CHECK)) && + isCheckedOrNot(IDC_IN_SELECTION_CHECK); + } } return TRUE; @@ -2738,7 +2748,11 @@ int FindReplaceDlg::processAll(ProcessOperation op, const FindOption *opt, bool (*_ppEditView)->execute(SCI_SCROLLRANGE, startPosition, endPosition); if (startPosition == endPosition) { - setChecked(IDC_IN_SELECTION_CHECK, false); + const NppGUI& nppGui = (NppParameters::getInstance()).getNppGUI(); + if (nppGui._inSelectionAutocheckThreshold != 0) + { + setChecked(IDC_IN_SELECTION_CHECK, false); + } enableFindDlgItem(IDC_IN_SELECTION_CHECK, false); } } diff --git a/PowerEditor/src/ScintillaComponent/FindReplaceDlg.h b/PowerEditor/src/ScintillaComponent/FindReplaceDlg.h index 8220a3095..83a508b46 100644 --- a/PowerEditor/src/ScintillaComponent/FindReplaceDlg.h +++ b/PowerEditor/src/ScintillaComponent/FindReplaceDlg.h @@ -30,7 +30,6 @@ #define FIND_INVALID_REGULAR_EXPRESSION -2 #define FINDREPLACE_MAXLENGTH 2048 -#define FINDREPLACE_INSEL_TEXTSIZE_THRESHOLD 1024 #define FINDTEMPSTRING_MAXSIZE 1024*1024 diff --git a/PowerEditor/src/WinControls/Preference/preference.rc b/PowerEditor/src/WinControls/Preference/preference.rc index 9263aa983..119d490b7 100644 --- a/PowerEditor/src/WinControls/Preference/preference.rc +++ b/PowerEditor/src/WinControls/Preference/preference.rc @@ -354,14 +354,16 @@ IDD_PREFERENCE_SUB_SEARCHING DIALOGEX 115, 10, 460, 205 STYLE DS_SETFONT | DS_FIXEDSYS | DS_CONTROL | WS_CHILD FONT 8, "MS Shell Dlg", 0, 0, 0x1 BEGIN - GROUPBOX "When Find Dialog is Invoked", IDD_FILL_FIND_FIELD_GRP_STATIC, 31, 4, 323, 43, BS_CENTER - CONTROL "Fill Find Field with Selected Text", IDC_CHECK_FILL_FIND_FIELD_WITH_SELECTED, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 16, 275, 10 - CONTROL "Select Word Under Caret when Nothing Selected", IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 52, 31, 275, 10 - CONTROL "Use Monospaced font in Find dialog (Need to restart Notepad++)", IDC_CHECK_MONOSPACEDFONT_FINDDLG, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 52, 350, 10 - CONTROL "Find dialog remains open after search that outputs to results window", IDC_CHECK_FINDDLG_ALWAYS_VISIBLE, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 67, 350, 10 - CONTROL "Confirm Replace All in All Opened Documents", IDC_CHECK_CONFIRMREPLOPENDOCS, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 82, 350, 10 - CONTROL "Replace: Don't move to the following occurrence", IDC_CHECK_REPLACEANDSTOP, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 97, 350, 10 - CONTROL "Search Result window: show only one entry per found line", IDC_CHECK_SHOWONCEPERFOUNDLINE, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 112, 350, 10 + GROUPBOX "When Find Dialog is Invoked", IDD_FILL_FIND_FIELD_GRP_STATIC, 31, 4, 323, 65, BS_CENTER + RTEXT "Minimum Size for Auto-Checking 'In selection'", IDC_INSELECTION_THRESHOLD_STATIC, 37, 16, 202, 8 + EDITTEXT IDC_INSELECTION_THRESHOLD_EDIT, 250, 15, 27, 12, ES_CENTER | ES_NUMBER | WS_TABSTOP + CONTROL "Fill Find Field with Selected Text", IDC_CHECK_FILL_FIND_FIELD_WITH_SELECTED, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 38, 275, 10 + CONTROL "Select Word Under Caret when Nothing Selected", IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 52, 53, 275, 10 + CONTROL "Use Monospaced font in Find dialog (Need to restart Notepad++)", IDC_CHECK_MONOSPACEDFONT_FINDDLG, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 74, 350, 10 + CONTROL "Find dialog remains open after search that outputs to results window", IDC_CHECK_FINDDLG_ALWAYS_VISIBLE, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 89, 350, 10 + CONTROL "Confirm Replace All in All Opened Documents", IDC_CHECK_CONFIRMREPLOPENDOCS, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 104, 350, 10 + CONTROL "Replace: Don't move to the following occurrence", IDC_CHECK_REPLACEANDSTOP, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 119, 350, 10 + CONTROL "Search Result window: show only one entry per found line", IDC_CHECK_SHOWONCEPERFOUNDLINE, "Button", BS_AUTOCHECKBOX | WS_TABSTOP, 37, 134, 350, 10 END diff --git a/PowerEditor/src/WinControls/Preference/preferenceDlg.cpp b/PowerEditor/src/WinControls/Preference/preferenceDlg.cpp index 020763575..e9c415569 100644 --- a/PowerEditor/src/WinControls/Preference/preferenceDlg.cpp +++ b/PowerEditor/src/WinControls/Preference/preferenceDlg.cpp @@ -5575,6 +5575,20 @@ intptr_t CALLBACK SearchingSubDlg::run_dlgProc(UINT message, WPARAM wParam, LPAR ::SendDlgItemMessage(_hSelf, IDC_CHECK_CONFIRMREPLOPENDOCS, BM_SETCHECK, nppGUI._confirmReplaceInAllOpenDocs, 0); ::SendDlgItemMessage(_hSelf, IDC_CHECK_REPLACEANDSTOP, BM_SETCHECK, nppGUI._replaceStopsWithoutFindingNext, 0); ::SendDlgItemMessage(_hSelf, IDC_CHECK_SHOWONCEPERFOUNDLINE, BM_SETCHECK, nppGUI._finderShowOnlyOneEntryPerFoundLine, 0); + ::SetDlgItemInt(_hSelf, IDC_INSELECTION_THRESHOLD_EDIT, nppGUI._inSelectionAutocheckThreshold, 0); + + NativeLangSpeaker* pNativeSpeaker = (NppParameters::getInstance()).getNativeLangSpeaker(); + generic_string tipText = pNativeSpeaker->getLocalizedStrFromID("searchingInSelThresh-tip", L"Number of selected characters in edit zone to automatically check the 'In selection' checkbox when the Find dialog is activated. The maximum value is 1024. Set the value to 0 to disable auto-checking."); + + _tipInSelThresh = CreateToolTip(IDC_INSELECTION_THRESHOLD_EDIT, _hSelf, _hInst, const_cast(tipText.c_str()), pNativeSpeaker->isRTL()); + + if (_tipInSelThresh != nullptr) + { + ::SendMessage(_tipInSelThresh, TTM_SETMAXTIPWIDTH, 0, 260); + + // Make tip stay 30 seconds + ::SendMessage(_tipInSelThresh, TTM_SETDELAYTIME, TTDT_AUTOPOP, MAKELPARAM((30000), (0))); + } return TRUE; } @@ -5596,13 +5610,44 @@ intptr_t CALLBACK SearchingSubDlg::run_dlgProc(UINT message, WPARAM wParam, LPAR case WM_COMMAND: { + if ((LOWORD(wParam) == IDC_INSELECTION_THRESHOLD_EDIT) && + (HIWORD(wParam) == EN_CHANGE)) + { + constexpr int stringSize = 5; + wchar_t str[stringSize]{}; + ::GetDlgItemText(_hSelf, IDC_INSELECTION_THRESHOLD_EDIT, str, stringSize); + + if (lstrcmp(str, L"") == 0) + { + ::SetDlgItemInt(_hSelf, IDC_INSELECTION_THRESHOLD_EDIT, nppGUI._inSelectionAutocheckThreshold, FALSE); + return FALSE; + } + + UINT newValue = ::GetDlgItemInt(_hSelf, IDC_INSELECTION_THRESHOLD_EDIT, nullptr, FALSE); + + if (static_cast(newValue) == nppGUI._inSelectionAutocheckThreshold) + { + return FALSE; + } + + if (newValue > FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT) + { + ::SetDlgItemInt(_hSelf, IDC_INSELECTION_THRESHOLD_EDIT, FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT, FALSE); + newValue = FINDREPLACE_INSELECTION_THRESHOLD_DEFAULT; + } + + nppGUI._inSelectionAutocheckThreshold = newValue; + + return TRUE; + } + switch (wParam) { case IDC_CHECK_FILL_FIND_FIELD_WITH_SELECTED: { nppGUI._fillFindFieldWithSelected = isCheckedOrNot(IDC_CHECK_FILL_FIND_FIELD_WITH_SELECTED); - ::EnableWindow(::GetDlgItem(_hSelf, IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET), nppGUI._fillFindFieldWithSelected ? TRUE :FALSE); - if (!nppGUI._fillFindFieldWithSelected) + ::EnableWindow(::GetDlgItem(_hSelf, IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET), nppGUI._fillFindFieldWithSelected ? TRUE : FALSE); + if (!nppGUI._fillFindFieldWithSelected) { ::SendDlgItemMessage(_hSelf, IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET, BM_SETCHECK, BST_UNCHECKED, 0); nppGUI._fillFindFieldSelectCaret = false; diff --git a/PowerEditor/src/WinControls/Preference/preferenceDlg.h b/PowerEditor/src/WinControls/Preference/preferenceDlg.h index f795df3c2..54c6c675a 100644 --- a/PowerEditor/src/WinControls/Preference/preferenceDlg.h +++ b/PowerEditor/src/WinControls/Preference/preferenceDlg.h @@ -178,8 +178,16 @@ class SearchingSubDlg : public StaticDialog { public: SearchingSubDlg() = default; + ~SearchingSubDlg() { + if (_tipInSelThresh != nullptr) + { + ::DestroyWindow(_tipInSelThresh); + _tipInSelThresh = nullptr; + } + }; private: + HWND _tipInSelThresh = nullptr; intptr_t CALLBACK run_dlgProc(UINT message, WPARAM wParam, LPARAM lParam) override; }; diff --git a/PowerEditor/src/WinControls/Preference/preference_rc.h b/PowerEditor/src/WinControls/Preference/preference_rc.h index 36d7f6fbf..4bd4cb3aa 100644 --- a/PowerEditor/src/WinControls/Preference/preference_rc.h +++ b/PowerEditor/src/WinControls/Preference/preference_rc.h @@ -438,6 +438,8 @@ #define IDD_FILL_FIND_FIELD_GRP_STATIC (IDD_PREFERENCE_SUB_SEARCHING + 7) #define IDC_CHECK_FILL_FIND_FIELD_WITH_SELECTED (IDD_PREFERENCE_SUB_SEARCHING + 8) #define IDC_CHECK_FILL_FIND_FIELD_SELECT_CARET (IDD_PREFERENCE_SUB_SEARCHING + 9) + #define IDC_INSELECTION_THRESHOLD_STATIC (IDD_PREFERENCE_SUB_SEARCHING + 10) + #define IDC_INSELECTION_THRESHOLD_EDIT (IDD_PREFERENCE_SUB_SEARCHING + 11) #define IDD_PREFERENCE_SUB_DARKMODE 7100 //(IDD_PREFERENCE_BOX + 1100) //#define IDC_CHECK_DARKMODE_ENABLE (IDD_PREFERENCE_SUB_DARKMODE + 1)