summaryrefslogtreecommitdiffstats
path: root/cui/source/dialogs/SpellDialog.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'cui/source/dialogs/SpellDialog.cxx')
-rw-r--r--cui/source/dialogs/SpellDialog.cxx201
1 files changed, 145 insertions, 56 deletions
diff --git a/cui/source/dialogs/SpellDialog.cxx b/cui/source/dialogs/SpellDialog.cxx
index dae7b92c9155..dfdad984ec41 100644
--- a/cui/source/dialogs/SpellDialog.cxx
+++ b/cui/source/dialogs/SpellDialog.cxx
@@ -26,6 +26,7 @@
#include <svl/undo.hxx>
#include <tools/debug.hxx>
#include <unotools/lingucfg.hxx>
+#include <editeng/editund2.hxx>
#include <editeng/colritem.hxx>
#include <editeng/eeitem.hxx>
#include <editeng/langitem.hxx>
@@ -50,6 +51,7 @@
#include <SpellDialog.hxx>
#include <optlingu.hxx>
#include <treeopt.hxx>
+#include <svtools/colorcfg.hxx>
#include <svtools/langtab.hxx>
#include <sal/log.hxx>
#include <i18nlangtag/languagetag.hxx>
@@ -160,6 +162,7 @@ SpellDialog::SpellDialog(SpellDialogChildWindow* pChildWindow,
: SfxModelessDialogController (_pBindings, pChildWindow,
pParent, "cui/ui/spellingdialog.ui", "SpellingDialog")
, aDialogUndoLink(LINK (this, SpellDialog, DialogUndoHdl))
+ , m_pInitHdlEvent(nullptr)
, bFocusLocked(true)
, rParent(*pChildWindow)
, pImpl( new SpellDialog_Impl )
@@ -171,7 +174,7 @@ SpellDialog::SpellDialog(SpellDialogChildWindow* pChildWindow,
, m_xExplainFT(m_xBuilder->weld_label("explain"))
, m_xExplainLink(m_xBuilder->weld_link_button("explainlink"))
, m_xNotInDictFT(m_xBuilder->weld_label("notindictft"))
- , m_xSentenceED(new SentenceEditWindow_Impl)
+ , m_xSentenceED(new SentenceEditWindow_Impl(m_xBuilder->weld_scrolled_window("scrolledwindow", true)))
, m_xSuggestionFT(m_xBuilder->weld_label("suggestionsft"))
, m_xSuggestionLB(m_xBuilder->weld_tree_view("suggestionslb"))
, m_xIgnorePB(m_xBuilder->weld_button("ignore"))
@@ -218,11 +221,19 @@ SpellDialog::SpellDialog(SpellDialogChildWindow* pChildWindow,
//InitHdl wants to use virtual methods, so it
//can't be called during the ctor, so init
//it on next event cycle post-ctor
- Application::PostUserEvent(LINK(this, SpellDialog, InitHdl));
+ m_pInitHdlEvent = Application::PostUserEvent(LINK(this, SpellDialog, InitHdl));
}
SpellDialog::~SpellDialog()
{
+ if (m_xOptionsDlg)
+ {
+ m_xOptionsDlg->response(RET_CANCEL);
+ m_xOptionsDlg.reset();
+ }
+
+ if (m_pInitHdlEvent)
+ Application::RemoveUserEvent(m_pInitHdlEvent);
if (pImpl)
{
// save possibly modified user-dictionaries
@@ -351,6 +362,11 @@ void SpellDialog::SpellContinue_Impl(std::unique_ptr<UndoChangeGroupGuard>* pGua
//then GetNextSentence() has to be called followed again by MarkNextError()
//MarkNextError is not initially called if the UndoEdit mode is active
bool bNextSentence = false;
+ if (!m_xSentenceED)
+ {
+ return;
+ }
+
if(!((!m_xSentenceED->IsUndoEditMode() && m_xSentenceED->MarkNextError( bIgnoreCurrentError, xSpell )) ||
( bNextSentence = GetNextSentence_Impl(pGuard, bUseSavedSentence, m_xSentenceED->IsUndoEditMode()) && m_xSentenceED->MarkNextError( false, xSpell ))))
return;
@@ -364,16 +380,10 @@ void SpellDialog::SpellContinue_Impl(std::unique_ptr<UndoChangeGroupGuard>* pGua
{
m_xNotInDictFT.get(),
m_xSentenceED->GetDrawingArea(),
- m_xLanguageFT.get(),
- nullptr
+ m_xLanguageFT.get()
};
- sal_Int32 nIdx = 0;
- do
- {
- aControls[nIdx]->set_sensitive(true);
- }
- while(aControls[++nIdx]);
-
+ for (weld::Widget* pWidget : aControls)
+ pWidget->set_sensitive(true);
}
if( bNextSentence )
{
@@ -387,6 +397,7 @@ void SpellDialog::SpellContinue_Impl(std::unique_ptr<UndoChangeGroupGuard>* pGua
*/
IMPL_LINK_NOARG( SpellDialog, InitHdl, void*, void)
{
+ m_pInitHdlEvent = nullptr;
m_xDialog->freeze();
//show or hide AutoCorrect depending on the modules abilities
m_xAutoCorrPB->set_visible(rParent.HasAutoCorrection());
@@ -401,7 +412,9 @@ IMPL_LINK_NOARG( SpellDialog, InitHdl, void*, void)
InitUserDicts();
LockFocusChanges(true);
- if( m_xChangePB->get_sensitive() )
+ if(m_xSentenceED->IsEnabled())
+ m_xSentenceED->GrabFocus();
+ else if( m_xChangePB->get_sensitive() )
m_xChangePB->grab_focus();
else if( m_xIgnorePB->get_sensitive() )
m_xIgnorePB->grab_focus();
@@ -456,19 +469,22 @@ IMPL_LINK_NOARG(SpellDialog, CheckGrammarHdl, weld::Toggleable&, void)
void SpellDialog::StartSpellOptDlg_Impl()
{
- SfxItemSetFixed<SID_AUTOSPELL_CHECK,SID_AUTOSPELL_CHECK> aSet( SfxGetpApp()->GetPool() );
- SfxSingleTabDialogController aDlg(m_xDialog.get(), &aSet, "cui/ui/spelloptionsdialog.ui", "SpellOptionsDialog");
+ auto xSet = std::make_shared<SfxItemSetFixed<SID_AUTOSPELL_CHECK,SID_AUTOSPELL_CHECK>>( SfxGetpApp()->GetPool() );
+ m_xOptionsDlg = std::make_shared<SfxSingleTabDialogController>(
+ m_xDialog.get(), xSet.get(), "content", "cui/ui/spelloptionsdialog.ui", "SpellOptionsDialog");
- std::unique_ptr<SfxTabPage> xPage = SvxLinguTabPage::Create(aDlg.get_content_area(), &aDlg, &aSet);
+ std::unique_ptr<SfxTabPage> xPage = SvxLinguTabPage::Create(m_xOptionsDlg->get_content_area(), m_xOptionsDlg.get(), xSet.get());
static_cast<SvxLinguTabPage*>(xPage.get())->HideGroups( GROUP_MODULES );
- aDlg.SetTabPage(std::move(xPage));
- if (RET_OK == aDlg.run())
- {
- InitUserDicts();
- const SfxItemSet* pOutSet = aDlg.GetOutputItemSet();
- if(pOutSet)
- OfaTreeOptionsDialog::ApplyLanguageOptions(*pOutSet);
- }
+ m_xOptionsDlg->SetTabPage(std::move(xPage));
+ weld::GenericDialogController::runAsync(m_xOptionsDlg, [this, xSet] (sal_uInt32 nResult) {
+ if (RET_OK == nResult)
+ {
+ InitUserDicts();
+ const SfxItemSet* pOutSet = m_xOptionsDlg->GetOutputItemSet();
+ if(pOutSet)
+ OfaTreeOptionsDialog::ApplyLanguageOptions(*pOutSet);
+ }
+ });
}
namespace
@@ -713,8 +729,7 @@ void SpellDialog::Close()
// section - in that case, the cursor can move from the editable field to
// the protected area, and the slots get disabled because of
// SfxDisableFlags::SwOnProtectedCursor (see FN_SPELL_GRAMMAR_DIALOG in .sdi).
- SfxViewFrame* pViewFrame = SfxViewFrame::Current();
- if (pViewFrame)
+ if (SfxViewFrame* pViewFrame = SfxViewFrame::Current())
pViewFrame->ToggleChildWindow(rParent.GetType());
}
@@ -828,15 +843,15 @@ int SpellDialog::InitUserDicts()
IMPL_LINK_NOARG(SpellDialog, AddToDictClickHdl, weld::Button&, void)
{
- AddToDictionaryExecute(OString::number(1));
+ AddToDictionaryExecute(OUString::number(1));
}
-IMPL_LINK(SpellDialog, AddToDictSelectHdl, const OString&, rIdent, void)
+IMPL_LINK(SpellDialog, AddToDictSelectHdl, const OUString&, rIdent, void)
{
AddToDictionaryExecute(rIdent);
}
-void SpellDialog::AddToDictionaryExecute(const OString& rItemId)
+void SpellDialog::AddToDictionaryExecute(const OUString& rItemId)
{
auto xGuard(std::make_unique<UndoChangeGroupGuard>(*m_xSentenceED));
@@ -945,7 +960,7 @@ void SpellDialog::Activate()
void SpellDialog::Deactivate()
{
- SfxModelessDialogController::Activate();
+ SfxModelessDialogController::Deactivate();
ToplevelFocusChanged();
}
@@ -969,15 +984,11 @@ void SpellDialog::InvalidateDialog()
m_xChangePB.get(),
m_xChangeAllPB.get(),
m_xAutoCorrPB.get(),
- m_xUndoPB.get(),
- nullptr
+ m_xUndoPB.get()
};
- sal_Int16 i = 0;
- while(aDisableArr[i])
- {
- aDisableArr[i]->set_sensitive(false);
- i++;
- }
+ for (weld::Widget* pWidget : aDisableArr)
+ pWidget->set_sensitive(false);
+
SfxModelessDialogController::Deactivate();
}
@@ -1119,13 +1130,15 @@ bool SpellDialog::ApplyChangeAllList_Impl(SpellPortions& rSentence, bool &bHasRe
return bRet;
}
-SentenceEditWindow_Impl::SentenceEditWindow_Impl()
- : m_pSpellDialog(nullptr)
+SentenceEditWindow_Impl::SentenceEditWindow_Impl(std::unique_ptr<weld::ScrolledWindow> xScrolledWindow)
+ : m_xScrolledWindow(std::move(xScrolledWindow))
+ , m_pSpellDialog(nullptr)
, m_pToolbar(nullptr)
, m_nErrorStart(0)
, m_nErrorEnd(0)
, m_bIsUndoEditMode(false)
{
+ m_xScrolledWindow->connect_vadjustment_changed(LINK(this, SentenceEditWindow_Impl, ScrollHdl));
}
void SentenceEditWindow_Impl::SetDrawingArea(weld::DrawingArea* pDrawingArea)
@@ -1136,6 +1149,77 @@ void SentenceEditWindow_Impl::SetDrawingArea(weld::DrawingArea* pDrawingArea)
WeldEditView::SetDrawingArea(pDrawingArea);
// tdf#132288 don't merge equal adjacent attributes
m_xEditEngine->DisableAttributeExpanding();
+
+ m_xEditEngine->SetStatusEventHdl(LINK(this, SentenceEditWindow_Impl, EditStatusHdl));
+
+ // tdf#142631 use document background color in this widget
+ Color aBgColor = svtools::ColorConfig().GetColorValue(svtools::DOCCOLOR).nColor;
+ OutputDevice& rDevice = pDrawingArea->get_ref_device();
+ rDevice.SetBackground(aBgColor);
+ m_xEditView->SetBackgroundColor(aBgColor);
+ m_xEditEngine->SetBackgroundColor(aBgColor);
+}
+
+IMPL_LINK_NOARG(SentenceEditWindow_Impl, EditStatusHdl, EditStatus&, void)
+{
+ SetScrollBarRange();
+ DoScroll();
+}
+
+IMPL_LINK_NOARG(SentenceEditWindow_Impl, ScrollHdl, weld::ScrolledWindow&, void)
+{
+ DoScroll();
+}
+
+void SentenceEditWindow_Impl::DoScroll()
+{
+ if (m_xEditView)
+ {
+ auto currentDocPos = m_xEditView->GetVisArea().Top();
+ auto nDiff = currentDocPos - m_xScrolledWindow->vadjustment_get_value();
+ // we expect SetScrollBarRange callback to be triggered by Scroll
+ // to set where we ended up
+ m_xEditView->Scroll(0, nDiff);
+ }
+}
+
+void SentenceEditWindow_Impl::EditViewScrollStateChange()
+{
+ // editengine height has changed or editview scroll pos has changed
+ SetScrollBarRange();
+}
+
+void SentenceEditWindow_Impl::SetScrollBarRange()
+{
+ EditEngine *pEditEngine = GetEditEngine();
+ if (!pEditEngine)
+ return;
+ if (!m_xScrolledWindow)
+ return;
+ EditView* pEditView = GetEditView();
+ if (!pEditView)
+ return;
+
+ int nVUpper = pEditEngine->GetTextHeight();
+ int nVCurrentDocPos = pEditView->GetVisArea().Top();
+ const Size aOut(pEditView->GetOutputArea().GetSize());
+ int nVStepIncrement = aOut.Height() * 2 / 10;
+ int nVPageIncrement = aOut.Height() * 8 / 10;
+ int nVPageSize = aOut.Height();
+
+ /* limit the page size to below nUpper because gtk's gtk_scrolled_window_start_deceleration has
+ effectively...
+
+ lower = gtk_adjustment_get_lower
+ upper = gtk_adjustment_get_upper - gtk_adjustment_get_page_size
+
+ and requires that upper > lower or the deceleration animation never ends
+ */
+ nVPageSize = std::min(nVPageSize, nVUpper);
+
+ m_xScrolledWindow->vadjustment_configure(nVCurrentDocPos, 0, nVUpper,
+ nVStepIncrement, nVPageIncrement, nVPageSize);
+ m_xScrolledWindow->set_vpolicy(nVUpper > nVPageSize ? VclPolicyType::ALWAYS : VclPolicyType::NEVER);
}
SentenceEditWindow_Impl::~SentenceEditWindow_Impl()
@@ -1163,7 +1247,10 @@ namespace
void ExtractErrorDescription(const EECharAttrib& rEECharAttrib, SpellErrorDescription& rSpellErrorDescription)
{
css::uno::Sequence<css::uno::Any> aSequence;
- static_cast<const SfxGrabBagItem*>(rEECharAttrib.pAttr)->GetGrabBag().find("SpellErrorDescription")->second >>= aSequence;
+ const auto pGrabBag = static_cast<const SfxGrabBagItem*>(rEECharAttrib.pAttr)->GetGrabBag();
+ const auto iter = pGrabBag.find("SpellErrorDescription");
+ assert(iter != pGrabBag.end());
+ iter->second >>= aSequence;
rSpellErrorDescription.fromSequence(aSequence);
}
}
@@ -1487,6 +1574,8 @@ bool SentenceEditWindow_Impl::KeyInput(const KeyEvent& rKeyEvt)
//start position
if (!IsUndoEditMode() && bIsErrorActive)
{
+ aAttribList.clear();
+ m_xEditEngine->GetCharAttribs(0, aAttribList);
const EECharAttrib* pFontColor = FindCharAttrib(nCursor, EE_CHAR_COLOR, aAttribList);
const EECharAttrib* pErrorAttrib = FindCharAttrib(m_nErrorStart, EE_CHAR_GRABBAG, aAttribList);
if (pFontColor && pErrorAttrib)
@@ -1518,7 +1607,7 @@ void SentenceEditWindow_Impl::Init(weld::Toolbar* pToolbar)
m_pToolbar->connect_clicked(LINK(this,SentenceEditWindow_Impl,ToolbarHdl));
}
-IMPL_LINK(SentenceEditWindow_Impl, ToolbarHdl, const OString&, rCurItemId, void)
+IMPL_LINK(SentenceEditWindow_Impl, ToolbarHdl, const OUString&, rCurItemId, void)
{
if (rCurItemId == "paste")
{
@@ -1667,8 +1756,12 @@ void SentenceEditWindow_Impl::MoveErrorMarkTo(sal_Int32 nStart, sal_Int32 nEnd,
m_xEditEngine->RemoveAttribs(aAll, false, EE_CHAR_WEIGHT_CJK);
m_xEditEngine->RemoveAttribs(aAll, false, EE_CHAR_WEIGHT_CTL);
+ // tdf#116566 Use color defined in the current Color Scheme
+ Color aSpellErrorCollor = svtools::ColorConfig().GetColorValue(svtools::SPELL).nColor;
+ Color aGrammarErrorCollor = svtools::ColorConfig().GetColorValue(svtools::GRAMMAR).nColor;
+
SfxItemSet aSet(m_xEditEngine->GetEmptyItemSet());
- aSet.Put(SvxColorItem(bGrammarError ? COL_LIGHTBLUE : COL_LIGHTRED, EE_CHAR_COLOR));
+ aSet.Put(SvxColorItem(bGrammarError ? aGrammarErrorCollor : aSpellErrorCollor, EE_CHAR_COLOR));
aSet.Put(SvxWeightItem(WEIGHT_BOLD, EE_CHAR_WEIGHT));
aSet.Put(SvxWeightItem(WEIGHT_BOLD, EE_CHAR_WEIGHT_CJK));
aSet.Put(SvxWeightItem(WEIGHT_BOLD, EE_CHAR_WEIGHT_CTL));
@@ -1683,6 +1776,8 @@ void SentenceEditWindow_Impl::MoveErrorMarkTo(sal_Int32 nStart, sal_Int32 nEnd,
if (!bCurrentSelectionInRange)
{
m_xEditView->SetSelection(ESelection(0, nStart));
+ // tdf#157148 ensure current location is auto-scrolled to be visible
+ m_xEditView->ShowCursor();
}
Invalidate();
@@ -1816,7 +1911,7 @@ void SentenceEditWindow_Impl::SetAlternatives( const Reference< XSpellAlternativ
aLocale = xAlt->getLocale();
aAlts = xAlt->getAlternatives();
}
- SpellErrorDescription aDesc( false, aWord, aLocale, aAlts, nullptr);
+ SpellErrorDescription aDesc( false, aWord, std::move(aLocale), aAlts, nullptr);
SfxGrabBagItem aSpellErrorDescription(EE_CHAR_GRABBAG);
aSpellErrorDescription.GetGrabBag()["SpellErrorDescription"] <<= aDesc.toSequence();
SetAttrib(aSpellErrorDescription, m_nErrorStart, m_nErrorEnd);
@@ -1945,7 +2040,6 @@ svx::SpellPortions SentenceEditWindow_Impl::CreateSpellPortions() const
aPortion1.eLanguage = eLang;
aPortion1.sText = m_xEditEngine->GetText(ESelection(0, nStart, 0, aStart->nPosition));
-
bool bIsIgnoreError = m_aIgnoreErrorsAt.find( nStart ) != m_aIgnoreErrorsAt.end();
if( bIsIgnoreError )
{
@@ -1977,7 +2071,7 @@ svx::SpellPortions SentenceEditWindow_Impl::CreateSpellPortions() const
aPortion2.sText = aLeftOverText.makeStringAndClear();
aRet.push_back( aPortion2 );
}
- else
+ else if (!aLeftOverText.isEmpty() && !aRet.empty())
{ // we just need to append the left-over text to the last portion (which had no errors)
aRet[ aRet.size() - 1 ].sText += aLeftOverText;
}
@@ -1989,7 +2083,7 @@ svx::SpellPortions SentenceEditWindow_Impl::CreateSpellPortions() const
void SentenceEditWindow_Impl::Undo()
{
- SfxUndoManager& rUndoMgr = m_xEditEngine->GetUndoManager();
+ EditUndoManager& rUndoMgr = m_xEditEngine->GetUndoManager();
DBG_ASSERT(GetUndoActionCount(), "no undo actions available" );
if(!GetUndoActionCount())
return;
@@ -2008,13 +2102,13 @@ void SentenceEditWindow_Impl::Undo()
void SentenceEditWindow_Impl::ResetUndo()
{
- SfxUndoManager& rUndo = m_xEditEngine->GetUndoManager();
+ EditUndoManager& rUndo = m_xEditEngine->GetUndoManager();
rUndo.Clear();
}
void SentenceEditWindow_Impl::AddUndoAction( std::unique_ptr<SfxUndoAction> pAction )
{
- SfxUndoManager& rUndoMgr = m_xEditEngine->GetUndoManager();
+ EditUndoManager& rUndoMgr = m_xEditEngine->GetUndoManager();
rUndoMgr.AddUndoAction(std::move(pAction));
GetSpellDialog()->m_xUndoPB->set_sensitive(true);
}
@@ -2063,15 +2157,10 @@ void SentenceEditWindow_Impl::SetUndoEditMode(bool bSet)
pSpellDialog->m_xLanguageLB->get_widget(),
pSpellDialog->m_xAddToDictMB.get(),
pSpellDialog->m_xAddToDictPB.get(),
- pSpellDialog->m_xAutoCorrPB.get(),
- nullptr
+ pSpellDialog->m_xAutoCorrPB.get()
};
- sal_Int32 nIdx = 0;
- do
- {
- aControls[nIdx]->set_sensitive(false);
- }
- while(aControls[++nIdx]);
+ for (weld::Widget* pWidget : aControls)
+ pWidget->set_sensitive(false);
//remove error marks
ESelection aAll(0, 0, 0, EE_TEXTPOS_ALL);