From 854d8c418904bbb9370ca6ee0aad6bde5deb426e Mon Sep 17 00:00:00 2001 From: Caolán McNamara Date: Fri, 6 Apr 2018 16:06:49 +0100 Subject: weld SfxNewStyleDlg MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit set some parents and replace VclComboBoxText with an entry and a treeview Change-Id: Ied75176355f23c986eac4d5de8654472a15dbbbf Reviewed-on: https://gerrit.libreoffice.org/52517 Tested-by: Jenkins Reviewed-by: Caolán McNamara Tested-by: Caolán McNamara --- include/sfx2/newstyle.hxx | 27 +++++-------- include/vcl/weld.hxx | 31 ++++++++++++++ sc/source/ui/view/formatsh.cxx | 6 +-- sfx2/source/dialog/newstyle.cxx | 67 ++++++++++++++----------------- sfx2/source/dialog/templdlg.cxx | 6 +-- sfx2/uiconfig/ui/newstyle.ui | 89 +++++++++++++++++++++++++++++++++++------ solenv/sanitizers/ui/sfx.suppr | 1 + sw/source/uibase/app/docst.cxx | 6 +-- vcl/source/app/salvtables.cxx | 56 ++++++++++++++++++++++++++ vcl/source/window/builder.cxx | 50 +++++++++++++++++++++++ vcl/unx/gtk3/gtk3gtkinst.cxx | 5 +++ 11 files changed, 269 insertions(+), 75 deletions(-) diff --git a/include/sfx2/newstyle.hxx b/include/sfx2/newstyle.hxx index dceeeec2e7ec..6fecb3378f4d 100644 --- a/include/sfx2/newstyle.hxx +++ b/include/sfx2/newstyle.hxx @@ -22,34 +22,29 @@ #include #include #include -#include -#include -#include -#include -#include #include class SfxStyleSheetBasePool; -class SFX2_DLLPUBLIC SfxNewStyleDlg : public ModalDialog +class SFX2_DLLPUBLIC SfxNewStyleDlg : public weld::GenericDialogController { private: - VclPtr m_pColBox; - VclPtr m_pOKBtn; + SfxStyleSheetBasePool& m_rPool; - std::unique_ptr xQueryOverwriteBox; - SfxStyleSheetBasePool& rPool; + std::unique_ptr m_xColBox; + std::unique_ptr m_xOKBtn; - DECL_DLLPRIVATE_LINK( OKHdl, ComboBox&, void ); - DECL_DLLPRIVATE_LINK( OKClickHdl, Button *, void ); - DECL_DLLPRIVATE_LINK( ModifyHdl, Edit&, void ); + std::unique_ptr m_xQueryOverwriteBox; + + DECL_DLLPRIVATE_LINK(OKHdl, weld::TreeView&, void); + DECL_DLLPRIVATE_LINK(OKClickHdl, weld::Button&, void); + DECL_DLLPRIVATE_LINK(ModifyHdl, weld::Entry&, void); public: - SfxNewStyleDlg( vcl::Window* pParent, SfxStyleSheetBasePool& ); + SfxNewStyleDlg(weld::Window* pParent, SfxStyleSheetBasePool&); virtual ~SfxNewStyleDlg() override; - virtual void dispose() override; - OUString GetName() const { return comphelper::string::stripStart(m_pColBox->GetText(), ' '); } + OUString GetName() const { return comphelper::string::stripStart(m_xColBox->get_text(), ' '); } }; #endif diff --git a/include/vcl/weld.hxx b/include/vcl/weld.hxx index 9c0fa76468b8..6f6776f38b57 100644 --- a/include/vcl/weld.hxx +++ b/include/vcl/weld.hxx @@ -901,6 +901,33 @@ public: virtual Point get_accessible_location() = 0; }; +// an entry + treeview pair, where the entry autocompletes from the +// treeview list, and selecting something in the list sets the +// entry to that text +class VCL_DLLPUBLIC EntryTreeView +{ +private: + DECL_DLLPRIVATE_LINK(ClickHdl, weld::TreeView&, void); + DECL_DLLPRIVATE_LINK(ModifyHdl, weld::Entry&, void); + void EntryModifyHdl(weld::Entry& rEntry); + +protected: + Link m_aChangeHdl; + std::unique_ptr m_xEntry; + std::unique_ptr m_xTreeView; + +public: + EntryTreeView(std::unique_ptr xEntry, std::unique_ptr xTreeView); + OUString get_text() const { return m_xEntry->get_text(); } + void append_text(const OUString& rText) { m_xTreeView->append_text(rText); } + void connect_row_activated(const Link& rLink) + { + m_xTreeView->connect_row_activated(rLink); + } + void connect_changed(const Link& rLink) { m_aChangeHdl = rLink; } + void set_size_request_by_digits_rows(int nDigits, int nRows); +}; + class VCL_DLLPUBLIC Menu { public: @@ -992,6 +1019,10 @@ public: FactoryFunction pUITestFactoryFunction = nullptr, void* pUserData = nullptr, bool bTakeOwnership = false) = 0; + virtual std::unique_ptr weld_entry_tree_view(const OString& entryid, + const OString& treeviewid, + bool bTakeOwnership = false) + = 0; virtual std::unique_ptr weld_menu(const OString& id, bool bTakeOwnership = true) = 0; virtual std::unique_ptr create_size_group() = 0; virtual ~Builder() {} diff --git a/sc/source/ui/view/formatsh.cxx b/sc/source/ui/view/formatsh.cxx index 7622c978683c..9213b39042d8 100644 --- a/sc/source/ui/view/formatsh.cxx +++ b/sc/source/ui/view/formatsh.cxx @@ -434,10 +434,10 @@ void ScFormatShell::ExecuteStyle( SfxRequest& rReq ) aStyleName = static_cast(pNameItem)->GetValue(); else if ( nSlotId == SID_STYLE_NEW_BY_EXAMPLE ) { - ScopedVclPtrInstance pDlg( nullptr, *pStylePool ); - if ( RET_OK != pDlg->Execute() ) + SfxNewStyleDlg aDlg(pTabViewShell->GetFrameWeld(), *pStylePool); + if (aDlg.run() != RET_OK) return; - aStyleName = pDlg->GetName(); + aStyleName = aDlg.GetName(); } pStyleSheet = pStylePool->Find( aStyleName, eFamily ); diff --git a/sfx2/source/dialog/newstyle.cxx b/sfx2/source/dialog/newstyle.cxx index f4feb1f3f959..38cd472c4d65 100644 --- a/sfx2/source/dialog/newstyle.cxx +++ b/sfx2/source/dialog/newstyle.cxx @@ -27,71 +27,62 @@ // Private methods ------------------------------------------------------ -IMPL_LINK_NOARG( SfxNewStyleDlg, OKClickHdl, Button*, void ) +IMPL_LINK_NOARG(SfxNewStyleDlg, OKClickHdl, weld::Button&, void) { - OKHdl(*m_pColBox); -} -IMPL_LINK_NOARG( SfxNewStyleDlg, OKHdl, ComboBox&, void ) -{ - const OUString aName( m_pColBox->GetText() ); - SfxStyleSheetBase* pStyle = rPool.Find( aName, rPool.GetSearchFamily() ); + const OUString aName(m_xColBox->get_text()); + SfxStyleSheetBase* pStyle = m_rPool.Find(aName, m_rPool.GetSearchFamily()); if ( pStyle ) { if ( !pStyle->IsUserDefined() ) { - std::unique_ptr xBox(Application::CreateMessageDialog(GetFrameWeld(), + std::unique_ptr xBox(Application::CreateMessageDialog(m_xDialog.get(), VclMessageType::Info, VclButtonsType::Ok, SfxResId(STR_POOL_STYLE_NAME))); xBox->run(); return; } - if (RET_YES == xQueryOverwriteBox->run()) - EndDialog( RET_OK ); + if (RET_YES == m_xQueryOverwriteBox->run()) + m_xDialog->response(RET_OK); } else - EndDialog( RET_OK ); + m_xDialog->response(RET_OK); +} + +IMPL_LINK_NOARG(SfxNewStyleDlg, OKHdl, weld::TreeView&, void) +{ + OKClickHdl(*m_xOKBtn); } -IMPL_LINK( SfxNewStyleDlg, ModifyHdl, Edit&, rBox, void ) +IMPL_LINK(SfxNewStyleDlg, ModifyHdl, weld::Entry&, rBox, void) { - m_pOKBtn->Enable( !rBox.GetText().replaceAll(" ", "").isEmpty() ); + m_xOKBtn->set_sensitive(!rBox.get_text().replaceAll(" ", "").isEmpty()); } -SfxNewStyleDlg::SfxNewStyleDlg( vcl::Window* pParent, SfxStyleSheetBasePool& rInPool ) - : ModalDialog(pParent, "CreateStyleDialog", "sfx/ui/newstyle.ui") - , xQueryOverwriteBox(Application::CreateMessageDialog(GetFrameWeld(), VclMessageType::Question, VclButtonsType::YesNo, - SfxResId(STR_QUERY_OVERWRITE))) - , rPool(rInPool) +SfxNewStyleDlg::SfxNewStyleDlg(weld::Window* pParent, SfxStyleSheetBasePool& rInPool) + : GenericDialogController(pParent, "sfx/ui/newstyle.ui", "CreateStyleDialog") + , m_rPool(rInPool) + , m_xColBox(m_xBuilder->weld_entry_tree_view("stylename", "styles")) + , m_xOKBtn(m_xBuilder->weld_button("ok")) + , m_xQueryOverwriteBox(Application::CreateMessageDialog(m_xDialog.get(), VclMessageType::Question, VclButtonsType::YesNo, + SfxResId(STR_QUERY_OVERWRITE))) { - get(m_pColBox, "stylename"); - m_pColBox->set_width_request(m_pColBox->approximate_char_width() * 25); - m_pColBox->set_height_request(m_pColBox->GetTextHeight() * 10); - get(m_pOKBtn, "ok"); + m_xColBox->set_size_request_by_digits_rows(20, 8); - m_pOKBtn->SetClickHdl(LINK(this, SfxNewStyleDlg, OKClickHdl)); - m_pColBox->SetModifyHdl(LINK(this, SfxNewStyleDlg, ModifyHdl)); - m_pColBox->SetDoubleClickHdl(LINK(this, SfxNewStyleDlg, OKHdl)); + m_xOKBtn->connect_clicked(LINK(this, SfxNewStyleDlg, OKClickHdl)); + m_xColBox->connect_changed(LINK(this, SfxNewStyleDlg, ModifyHdl)); + m_xColBox->connect_row_activated(LINK(this, SfxNewStyleDlg, OKHdl)); - SfxStyleSheetBase *pStyle = rPool.First(); - while ( pStyle ) + SfxStyleSheetBase *pStyle = m_rPool.First(); + while (pStyle) { - m_pColBox->InsertEntry(pStyle->GetName()); - pStyle = rPool.Next(); + m_xColBox->append_text(pStyle->GetName()); + pStyle = m_rPool.Next(); } } SfxNewStyleDlg::~SfxNewStyleDlg() { - disposeOnce(); -} - -void SfxNewStyleDlg::dispose() -{ - xQueryOverwriteBox.reset(); - m_pColBox.clear(); - m_pOKBtn.clear(); - ModalDialog::dispose(); } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sfx2/source/dialog/templdlg.cxx b/sfx2/source/dialog/templdlg.cxx index e72d920bd8c0..3bec0c87479b 100644 --- a/sfx2/source/dialog/templdlg.cxx +++ b/sfx2/source/dialog/templdlg.cxx @@ -1696,12 +1696,12 @@ void SfxCommonTemplateDialog_Impl::ActionSelect(sal_uInt16 nEntry) nFilter=pStyleSheetPool->GetSearchMask(); pStyleSheetPool->SetSearchMask( eFam, SfxStyleSearchBits::UserDefined ); - ScopedVclPtrInstance< SfxNewStyleDlg > pDlg(pWindow, *pStyleSheetPool); // why? : FloatingWindow must not be parent of a modal dialog - if(RET_OK == pDlg->Execute()) + SfxNewStyleDlg aDlg(pWindow ? pWindow->GetFrameWeld() : nullptr, *pStyleSheetPool); + if (aDlg.run() == RET_OK) { pStyleSheetPool->SetSearchMask(eFam, nFilter); - const OUString aTemplName(pDlg->GetName()); + const OUString aTemplName(aDlg.GetName()); Execute_Impl(SID_STYLE_NEW_BY_EXAMPLE, aTemplName, "", static_cast(GetFamilyItem_Impl()->GetFamily()), diff --git a/sfx2/uiconfig/ui/newstyle.ui b/sfx2/uiconfig/ui/newstyle.ui index e9fa34ca4909..86ad1f114d92 100644 --- a/sfx2/uiconfig/ui/newstyle.ui +++ b/sfx2/uiconfig/ui/newstyle.ui @@ -1,13 +1,34 @@ - + - + + + + + + + + + + liststore1 + 0 + True + False + False + False + False 6 Create Style + True + 0 + 0 dialog + + + False @@ -90,23 +111,67 @@ 6 12 - + True False True True - True - False - 60 - - - False + 3 + + + True + True + True + True + in + + + True + True + True + True + liststore1 + False + False + 0 + False + + + + + + + + + 0 + + + + + + + + 0 + 1 + - - - Style Name + + + True + True + True + entrycompletion1 + + + Style Name + + + + 0 + 0 + diff --git a/solenv/sanitizers/ui/sfx.suppr b/solenv/sanitizers/ui/sfx.suppr index 55c74c2684fd..66b8d3725202 100644 --- a/solenv/sanitizers/ui/sfx.suppr +++ b/solenv/sanitizers/ui/sfx.suppr @@ -63,6 +63,7 @@ sfx2/uiconfig/ui/licensedialog.ui://GtkLabel[@id='label'] orphan-label sfx2/uiconfig/ui/loadtemplatedialog.ui://GtkLabel[@id='alttitle'] orphan-label sfx2/uiconfig/ui/loadtemplatedialog.ui://GtkDrawingArea[@id='image'] no-labelled-by sfx2/uiconfig/ui/managestylepage.ui://GtkLabel[@id='desc'] orphan-label +sfx2/uiconfig/ui/newstyle.ui://GtkEntry[@id='entry'] no-labelled-by sfx2/uiconfig/ui/optprintpage.ui://GtkSpinButton[@id='reducegradstep'] no-labelled-by sfx2/uiconfig/ui/password.ui://GtkLabel[@id='minlenft'] orphan-label sfx2/uiconfig/ui/startcenter.ui://GtkLabel[@id='create_label'] orphan-label diff --git a/sw/source/uibase/app/docst.cxx b/sw/source/uibase/app/docst.cxx index 6c748709b94e..534f96f4fadd 100644 --- a/sw/source/uibase/app/docst.cxx +++ b/sw/source/uibase/app/docst.cxx @@ -382,10 +382,10 @@ void SwDocShell::ExecStyleSheet( SfxRequest& rReq ) { case SID_STYLE_NEW_BY_EXAMPLE: { - VclPtrInstance pDlg( nullptr, *GetStyleSheetPool()); - if(RET_OK == pDlg->Execute()) + SfxNewStyleDlg aDlg(GetView()->GetViewFrame()->GetWindow().GetFrameWeld(), *GetStyleSheetPool()); + if (aDlg.run() == RET_OK) { - aParam = pDlg->GetName(); + aParam = aDlg.GetName(); rReq.AppendItem(SfxStringItem(nSlot, aParam)); } } diff --git a/vcl/source/app/salvtables.cxx b/vcl/source/app/salvtables.cxx index dfac4c9f9aca..f32c36af335d 100644 --- a/vcl/source/app/salvtables.cxx +++ b/vcl/source/app/salvtables.cxx @@ -1472,6 +1472,11 @@ public: weld::Entry::connect_cursor_position(rLink); } + void SetAutocompleteHdl(const Link& rLink) + { + m_xEntry->SetAutocompleteHdl(rLink); + } + virtual ~SalInstanceEntry() override { if (m_aCursorPositionHdl.IsSet()) @@ -2308,6 +2313,51 @@ IMPL_LINK_NOARG(SalInstanceComboBoxTextWithEdit, EntryActivateHdl, Edit&, void) m_aEntryActivateHdl.Call(*this); } +class SalInstanceEntryTreeView : public weld::EntryTreeView +{ +private: + DECL_LINK(AutocompleteHdl, Edit&, void); + SalInstanceEntry* m_pEntry; +public: + SalInstanceEntryTreeView(std::unique_ptr xEntry, std::unique_ptr xTreeView) + : EntryTreeView(std::move(xEntry), std::move(xTreeView)) + , m_pEntry(dynamic_cast(m_xEntry.get())) + { + assert(m_pEntry); + m_pEntry->SetAutocompleteHdl(LINK(this, SalInstanceEntryTreeView, AutocompleteHdl)); + } + ~SalInstanceEntryTreeView() + { + m_pEntry->SetAutocompleteHdl(Link()); + } +}; + +IMPL_LINK(SalInstanceEntryTreeView, AutocompleteHdl, Edit&, rEdit, void) +{ + Selection aSel = rEdit.GetSelection(); + + OUString aFullText = rEdit.GetText(); + OUString aStartText = aFullText.copy(0, static_cast(aSel.Max())); + + int nPos = -1; + int nCount = m_xTreeView->n_children(); + for (int i = 0; i < nCount; ++i) + { + if (m_xTreeView->get_text(i).startsWithIgnoreAsciiCase(aStartText)) + { + nPos = i; + break; + } + } + + if (nPos != -1) + { + OUString aText = m_xTreeView->get_text(nPos); + Selection aSelection(aText.getLength(), aStartText.getLength()); + rEdit.SetText(aText, aSelection); + } +} + class SalInstanceBuilder : public weld::Builder { private: @@ -2462,6 +2512,12 @@ public: return pListBox ? o3tl::make_unique(pListBox, bTakeOwnership) : nullptr; } + virtual std::unique_ptr weld_entry_tree_view(const OString& entryid, const OString& treeviewid, bool bTakeOwnership) override + { + return o3tl::make_unique(weld_entry(entryid, bTakeOwnership), + weld_tree_view(treeviewid, bTakeOwnership)); + } + virtual std::unique_ptr weld_tree_view(const OString &id, bool bTakeOwnership) override { ListBox* pTreeView = m_xBuilder->get(id); diff --git a/vcl/source/window/builder.cxx b/vcl/source/window/builder.cxx index 6fd77952f24f..2ca29761b473 100644 --- a/vcl/source/window/builder.cxx +++ b/vcl/source/window/builder.cxx @@ -332,6 +332,56 @@ namespace weld const LocaleDataWrapper& rLocaleData = aSysLocale.GetLocaleData(); return TimeFormatter::FormatTime(ConvertValue(nValue), m_eFormat, TimeFormat::Hour24, true, rLocaleData); } + + EntryTreeView::EntryTreeView(std::unique_ptr xEntry, std::unique_ptr xTreeView) + : m_xEntry(std::move(xEntry)) + , m_xTreeView(std::move(xTreeView)) + { + m_xTreeView->connect_changed(LINK(this, EntryTreeView, ClickHdl)); + m_xEntry->connect_changed(LINK(this, EntryTreeView, ModifyHdl)); + } + + IMPL_LINK(EntryTreeView, ClickHdl, weld::TreeView&, rView, void) + { + m_xEntry->set_text(rView.get_selected_text()); + } + + void EntryTreeView::EntryModifyHdl(weld::Entry& rBox) + { + OUString sText(rBox.get_text()); + int nExists = m_xTreeView->find_text(sText); + if (nExists != -1) + { + m_xTreeView->select(nExists); + return; + } + + m_xTreeView->select(-1); + if (sText.isEmpty()) + return; + + int nCount = m_xTreeView->n_children(); + for (int i = 0; i < nCount; ++i) + { + if (m_xTreeView->get_text(i).startsWith(sText)) + { + m_xTreeView->select(i); + break; + } + } + } + + IMPL_LINK(EntryTreeView, ModifyHdl, weld::Entry&, rBox, void) + { + EntryModifyHdl(rBox); + m_aChangeHdl.Call(rBox); + } + + void EntryTreeView::set_size_request_by_digits_rows(int nDigits, int nRows) + { + m_xTreeView->set_size_request(m_xTreeView->get_approximate_digit_width() * nDigits, + m_xTreeView->get_height_rows(nRows)); + } } VclBuilder::VclBuilder(vcl::Window *pParent, const OUString& sUIDir, const OUString& sUIFile, const OString& sID, diff --git a/vcl/unx/gtk3/gtk3gtkinst.cxx b/vcl/unx/gtk3/gtk3gtkinst.cxx index 3d8a8a03b8f0..34d7d75ca954 100644 --- a/vcl/unx/gtk3/gtk3gtkinst.cxx +++ b/vcl/unx/gtk3/gtk3gtkinst.cxx @@ -5352,6 +5352,11 @@ public: return o3tl::make_unique(pTreeView, bTakeOwnership); } + virtual std::unique_ptr weld_entry_tree_view(const OString& entryid, const OString& treeviewid, bool bTakeOwnership) override + { + return o3tl::make_unique(weld_entry(entryid, bTakeOwnership), weld_tree_view(treeviewid, bTakeOwnership)); + } + virtual std::unique_ptr weld_label(const OString &id, bool bTakeOwnership) override { GtkLabel* pLabel = GTK_LABEL(gtk_builder_get_object(m_pBuilder, id.getStr())); -- cgit