weld SwChangeDBDlg
Change-Id: Ie0fc6a6346f9c777b7172a0b641a2783cf633c1d
Reviewed-on: https://gerrit.libreoffice.org/68544
Tested-by: Jenkins
Reviewed-by: Caolán McNamara <caolanm@redhat.com>
Tested-by: Caolán McNamara <caolanm@redhat.com>
diff --git a/include/vcl/weld.hxx b/include/vcl/weld.hxx
index 4802713..6000bb5 100644
--- a/include/vcl/weld.hxx
+++ b/include/vcl/weld.hxx
@@ -552,6 +552,10 @@ public:
{
insert(pParent, -1, &rStr, &rId, &rImage, nullptr, nullptr, false, nullptr);
}
void append(weld::TreeIter* pParent, const OUString& rStr)
{
insert(pParent, -1, &rStr, nullptr, nullptr, nullptr, nullptr, false, nullptr);
}
void append(const OUString& rId, const OUString& rStr, VirtualDevice& rImage)
{
insert(nullptr, -1, &rStr, &rId, nullptr, &rImage, nullptr, false, nullptr);
diff --git a/sw/qa/uitest/writer_tests2/exchangeDatabase.py b/sw/qa/uitest/writer_tests2/exchangeDatabase.py
index 1697a16..d255bd1 100644
--- a/sw/qa/uitest/writer_tests2/exchangeDatabase.py
+++ b/sw/qa/uitest/writer_tests2/exchangeDatabase.py
@@ -42,7 +42,7 @@ class exchangeDB(UITestCase):
xTreeEntry2 = xTreeEntry.getChild('0') #Available Databases
xTreeEntry2.executeAction("SELECT", tuple()) #Click on the biblio
xDefineBtn = xExDBDlg.getChild("define")
xDefineBtn = xExDBDlg.getChild("ok")
xDefineBtn.executeAction("CLICK", tuple())
self.ui_test.execute_dialog_through_command(".uno:ChangeDatabaseField")
@@ -55,4 +55,4 @@ class exchangeDB(UITestCase):
self.ui_test.close_doc()
# vim: set shiftwidth=4 softtabstop=4 expandtab:
\ No newline at end of file
# vim: set shiftwidth=4 softtabstop=4 expandtab:
diff --git a/sw/source/ui/dialog/swdlgfact.cxx b/sw/source/ui/dialog/swdlgfact.cxx
index 656a670..b60c775 100644
--- a/sw/source/ui/dialog/swdlgfact.cxx
+++ b/sw/source/ui/dialog/swdlgfact.cxx
@@ -789,8 +789,7 @@ VclPtr<AbstractSwBreakDlg> SwAbstractDialogFactory_Impl::CreateSwBreakDlg(weld::
VclPtr<VclAbstractDialog> SwAbstractDialogFactory_Impl::CreateSwChangeDBDlg(SwView& rVw)
{
#if HAVE_FEATURE_DBCONNECTIVITY
VclPtr<Dialog> pDlg = VclPtr<SwChangeDBDlg>::Create(rVw);
return VclPtr<VclAbstractDialog_Impl>::Create(pDlg);
return VclPtr<AbstractGenericDialog_Impl>::Create(std::make_unique<SwChangeDBDlg>(rVw));
#else
(void) rVw;
return nullptr;
diff --git a/sw/source/ui/fldui/changedb.cxx b/sw/source/ui/fldui/changedb.cxx
index 54854cd..4ddfff3 100644
--- a/sw/source/ui/fldui/changedb.cxx
+++ b/sw/source/ui/fldui/changedb.cxx
@@ -50,35 +50,35 @@ using namespace ::com::sun::star::uno;
// edit insert-field
SwChangeDBDlg::SwChangeDBDlg(SwView const & rVw)
: SvxStandardDialog(&rVw.GetViewFrame()->GetWindow(), "ExchangeDatabasesDialog",
"modules/swriter/ui/exchangedatabases.ui")
: SfxDialogController(rVw.GetViewFrame()->GetWindow().GetFrameWeld(), "modules/swriter/ui/exchangedatabases.ui",
"ExchangeDatabasesDialog")
, pSh(rVw.GetWrtShellPtr())
, m_xUsedDBTLB(m_xBuilder->weld_tree_view("inuselb"))
, m_xAvailDBTLB(new DBTreeList(m_xBuilder->weld_tree_view("availablelb")))
, m_xAddDBPB(m_xBuilder->weld_button("browse"))
, m_xDocDBNameFT(m_xBuilder->weld_label("dbnameft"))
, m_xDefineBT(m_xBuilder->weld_button("ok"))
{
get(m_pUsedDBTLB, "inuselb");
get(m_pAvailDBTLB, "availablelb");
get(m_pAddDBPB, "browse");
get(m_pDocDBNameFT, "dbnameft");
get(m_pDefineBT, "define");
m_pAvailDBTLB->SetWrtShell(*pSh);
int nWidth = m_xUsedDBTLB->get_approximate_digit_width() * 25;
int nHeight = m_xUsedDBTLB->get_height_rows(8);
m_xUsedDBTLB->set_size_request(nWidth, nHeight);
m_xAvailDBTLB->set_size_request(nWidth, nHeight);
m_xAvailDBTLB->SetWrtShell(*pSh);
FillDBPopup();
ShowDBName(pSh->GetDBData());
m_pDefineBT->SetClickHdl(LINK(this, SwChangeDBDlg, ButtonHdl));
m_pAddDBPB->SetClickHdl(LINK(this, SwChangeDBDlg, AddDBHdl));
m_xDefineBT->connect_clicked(LINK(this, SwChangeDBDlg, ButtonHdl));
m_xAddDBPB->connect_clicked(LINK(this, SwChangeDBDlg, AddDBHdl));
m_pUsedDBTLB->SetSelectionMode(SelectionMode::Multiple);
m_pUsedDBTLB->SetStyle(m_pUsedDBTLB->GetStyle()|WB_HASLINES|WB_CLIPCHILDREN|WB_SORT|WB_HASBUTTONS|WB_HASBUTTONSATROOT|WB_HSCROLL);
m_pUsedDBTLB->SetSpaceBetweenEntries(0);
m_pUsedDBTLB->SetNodeBitmaps(Image(StockImage::Yes, RID_BMP_COLLAPSE),
Image(StockImage::Yes, RID_BMP_EXPAND));
m_xUsedDBTLB->set_selection_mode(SelectionMode::Multiple);
m_xUsedDBTLB->make_sorted();
Link<SvTreeListBox*,void> aLink = LINK(this, SwChangeDBDlg, TreeSelectHdl);
Link<weld::TreeView&,void> aLink = LINK(this, SwChangeDBDlg, TreeSelectHdl);
m_pUsedDBTLB->SetSelectHdl(aLink);
m_pUsedDBTLB->SetDeselectHdl(aLink);
m_pAvailDBTLB->SetSelectHdl(aLink);
m_pAvailDBTLB->SetSelectHdl(aLink);
TreeSelectHdl(nullptr);
m_xUsedDBTLB->connect_changed(aLink);
m_xAvailDBTLB->connect_changed(aLink);
TreeSelect();
}
// initialise database listboxes
@@ -87,7 +87,8 @@ void SwChangeDBDlg::FillDBPopup()
Reference< XComponentContext > xContext( ::comphelper::getProcessComponentContext() );
Reference<XDatabaseContext> xDBContext = DatabaseContext::create(xContext);
const SwDBData& rDBData = pSh->GetDBData();
m_pAvailDBTLB->Select(rDBData.sDataSource, rDBData.sCommand, OUString());
m_xAvailDBTLB->Select(rDBData.sDataSource, rDBData.sCommand, OUString());
TreeSelect();
std::vector<OUString> aAllDBNames;
@@ -104,106 +105,101 @@ void SwChangeDBDlg::FillDBPopup()
pSh->GetAllUsedDB( aDBNameList, &aAllDBNames );
size_t nCount = aDBNameList.size();
m_pUsedDBTLB->Clear();
SvTreeListEntry *pFirst = nullptr;
SvTreeListEntry *pLast = nullptr;
m_xUsedDBTLB->clear();
std::unique_ptr<weld::TreeIter> xFirst;
for(size_t k = 0; k < nCount; k++)
{
pLast = Insert(aDBNameList[k].getToken(0, ';'));
if (!pFirst)
pFirst = pLast;
std::unique_ptr<weld::TreeIter> xLast = Insert(aDBNameList[k].getToken(0, ';'));
if (!xFirst)
xFirst = std::move(xLast);
}
if (pFirst)
if (xFirst)
{
m_pUsedDBTLB->MakeVisible(pFirst);
m_pUsedDBTLB->Select(pFirst);
m_xUsedDBTLB->expand_row(*xFirst);
m_xUsedDBTLB->scroll_to_row(*xFirst);
m_xUsedDBTLB->select(*xFirst);
}
}
SvTreeListEntry* SwChangeDBDlg::Insert(const OUString& rDBName)
std::unique_ptr<weld::TreeIter> SwChangeDBDlg::Insert(const OUString& rDBName)
{
sal_Int32 nIdx{ 0 };
const OUString sDBName(rDBName.getToken(0, DB_DELIM, nIdx));
const OUString sTableName(rDBName.getToken(0, DB_DELIM, nIdx));
sal_IntPtr nCommandType = rDBName.getToken(0, DB_DELIM, nIdx).toInt32();
SvTreeListEntry* pParent;
SvTreeListEntry* pChild;
OUString sUserData = rDBName.getToken(0, DB_DELIM, nIdx);
sal_Int32 nCommandType = sUserData.toInt32();
sal_uLong nParent = 0;
sal_uLong nChild = 0;
OUString aTableImg(RID_BMP_DBTABLE);
OUString aDBImg(RID_BMP_DB);
OUString aQueryImg(RID_BMP_DBQUERY);
OUString& rToInsert = nCommandType ? aQueryImg : aTableImg;
Image aTableImg(StockImage::Yes, RID_BMP_DBTABLE);
Image aDBImg(StockImage::Yes, RID_BMP_DB);
Image aQueryImg(StockImage::Yes, RID_BMP_DBQUERY);
Image& rToInsert = nCommandType ? aQueryImg : aTableImg;
while ((pParent = m_pUsedDBTLB->GetEntry(nParent++)) != nullptr)
std::unique_ptr<weld::TreeIter> xIter(m_xUsedDBTLB->make_iterator());
if (m_xUsedDBTLB->get_iter_first(*xIter))
{
if (sDBName == m_pUsedDBTLB->GetEntryText(pParent))
do
{
while ((pChild = m_pUsedDBTLB->GetEntry(pParent, nChild++)) != nullptr)
if (sDBName == m_xUsedDBTLB->get_text(*xIter))
{
if (sTableName == m_pUsedDBTLB->GetEntryText(pChild))
return pChild;
if (m_xUsedDBTLB->iter_children(*xIter))
{
do
{
if (sTableName == m_xUsedDBTLB->get_text(*xIter))
return xIter;
} while (m_xUsedDBTLB->iter_next_sibling(*xIter));
m_xUsedDBTLB->iter_parent(*xIter);
}
m_xUsedDBTLB->insert(xIter.get(), -1, &sTableName, &sUserData, nullptr, nullptr,
&rToInsert, false, xIter.get());
return xIter;
}
SvTreeListEntry* pRet = m_pUsedDBTLB->InsertEntry(sTableName, rToInsert, rToInsert, pParent);
pRet->SetUserData(reinterpret_cast<void*>(nCommandType));
return pRet;
}
} while (m_xUsedDBTLB->iter_next_sibling(*xIter));
}
pParent = m_pUsedDBTLB->InsertEntry(sDBName, aDBImg, aDBImg);
SvTreeListEntry* pRet = m_pUsedDBTLB->InsertEntry(sTableName, rToInsert, rToInsert, pParent);
pRet->SetUserData(reinterpret_cast<void*>(nCommandType));
return pRet;
m_xUsedDBTLB->insert(nullptr, -1, &sDBName, nullptr, nullptr, nullptr,
&aDBImg, false, xIter.get());
m_xUsedDBTLB->insert(xIter.get(), -1, &sTableName, &sUserData, nullptr, nullptr,
&rToInsert, false, xIter.get());
return xIter;
}
// destroy dialog
SwChangeDBDlg::~SwChangeDBDlg()
{
disposeOnce();
}
void SwChangeDBDlg::dispose()
short SwChangeDBDlg::run()
{
m_pUsedDBTLB.clear();
m_pAvailDBTLB.clear();
m_pAddDBPB.clear();
m_pDocDBNameFT.clear();
m_pDefineBT.clear();
SvxStandardDialog::dispose();
short nRet = SfxDialogController::run();
if (nRet == RET_OK)
UpdateFields();
return nRet;
}
// close
void SwChangeDBDlg::Apply()
{
UpdateFields();
}
void SwChangeDBDlg::UpdateFields()
{
std::vector<OUString> aDBNames;
aDBNames.reserve(m_pUsedDBTLB->GetSelectionCount());
SvTreeListEntry* pEntry = m_pUsedDBTLB->FirstSelected();
while( pEntry )
{
if( m_pUsedDBTLB->GetParent( pEntry ))
m_xUsedDBTLB->selected_foreach([this, &aDBNames](weld::TreeIter& rEntry){
if (m_xUsedDBTLB->get_iter_depth(rEntry))
{
OUString sTmp(m_pUsedDBTLB->GetEntryText( m_pUsedDBTLB->GetParent( pEntry )) +
OUStringLiteral1(DB_DELIM) + m_pUsedDBTLB->GetEntryText( pEntry ) + OUStringLiteral1(DB_DELIM) +
OUString::number(static_cast<int>(reinterpret_cast<sal_uLong>(pEntry->GetUserData()))));
std::unique_ptr<weld::TreeIter> xIter(m_xUsedDBTLB->make_iterator(&rEntry));
m_xUsedDBTLB->iter_parent(*xIter);
OUString sTmp(m_xUsedDBTLB->get_text(*xIter) +
OUStringLiteral1(DB_DELIM) + m_xUsedDBTLB->get_text(rEntry) + OUStringLiteral1(DB_DELIM) +
m_xUsedDBTLB->get_id(rEntry));
aDBNames.push_back(sTmp);
}
pEntry = m_pUsedDBTLB->NextSelected(pEntry);
}
});
pSh->StartAllAction();
OUString sTableName;
OUString sColumnName;
sal_Bool bIsTable = false;
const OUString DBName(m_pAvailDBTLB->GetDBName(sTableName, sColumnName, &bIsTable));
const OUString DBName(m_xAvailDBTLB->GetDBName(sTableName, sColumnName, &bIsTable));
const OUString sTemp = DBName
+ OUStringLiteral1(DB_DELIM)
+ sTableName
@@ -215,52 +211,60 @@ void SwChangeDBDlg::UpdateFields()
pSh->EndAllAction();
}
IMPL_LINK_NOARG(SwChangeDBDlg, ButtonHdl, Button*, void)
IMPL_LINK_NOARG(SwChangeDBDlg, ButtonHdl, weld::Button&, void)
{
OUString sTableName;
OUString sColumnName;
SwDBData aData;
sal_Bool bIsTable = false;
aData.sDataSource = m_pAvailDBTLB->GetDBName(sTableName, sColumnName, &bIsTable);
aData.sDataSource = m_xAvailDBTLB->GetDBName(sTableName, sColumnName, &bIsTable);
aData.sCommand = sTableName;
aData.nCommandType = bIsTable ? 0 : 1;
pSh->ChgDBData(aData);
ShowDBName(pSh->GetDBData());
EndDialog(RET_OK);
m_xDialog->response(RET_OK);
}
IMPL_LINK_NOARG(SwChangeDBDlg, TreeSelectHdl, SvTreeListBox*, void)
IMPL_LINK_NOARG(SwChangeDBDlg, TreeSelectHdl, weld::TreeView&, void)
{
SvTreeListEntry* pEntry = m_pAvailDBTLB->GetCurEntry();
if (pEntry)
{
bool bEnable = false;
if (m_pAvailDBTLB->GetParent(pEntry))
bEnable = true;
m_pDefineBT->Enable( bEnable );
}
TreeSelect();
}
void SwChangeDBDlg::TreeSelect()
{
bool bEnable = false;
std::unique_ptr<weld::TreeIter> xIter(m_xAvailDBTLB->make_iterator());
if (m_xAvailDBTLB->get_selected(xIter.get()))
{
if (m_xAvailDBTLB->get_iter_depth(*xIter))
bEnable = true;
}
m_xDefineBT->set_sensitive(bEnable);
}
// convert database name for display
void SwChangeDBDlg::ShowDBName(const SwDBData& rDBData)
{
if (rDBData.sDataSource.isEmpty() && rDBData.sCommand.isEmpty())
{
m_pDocDBNameFT->SetText(SwResId(SW_STR_NONE));
m_xDocDBNameFT->set_label(SwResId(SW_STR_NONE));
}
else
{
const OUString sName(rDBData.sDataSource + "." + rDBData.sCommand);
m_pDocDBNameFT->SetText(sName.replaceAll("~", "~~"));
m_xDocDBNameFT->set_label(sName.replaceAll("~", "~~"));
}
}
IMPL_LINK_NOARG(SwChangeDBDlg, AddDBHdl, Button*, void)
IMPL_LINK_NOARG(SwChangeDBDlg, AddDBHdl, weld::Button&, void)
{
const OUString sNewDB = SwDBManager::LoadAndRegisterDataSource(GetFrameWeld());
const OUString sNewDB = SwDBManager::LoadAndRegisterDataSource(m_xDialog.get());
if (!sNewDB.isEmpty())
m_pAvailDBTLB->AddDataSource(sNewDB);
{
m_xAvailDBTLB->AddDataSource(sNewDB);
TreeSelect();
}
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sw/source/uibase/dbui/dbtree.cxx b/sw/source/uibase/dbui/dbtree.cxx
index 8daa167..34840d8 100644
--- a/sw/source/uibase/dbui/dbtree.cxx
+++ b/sw/source/uibase/dbui/dbtree.cxx
@@ -486,4 +486,290 @@ void SwDBTreeList::SetWrtShell(SwWrtShell& rSh)
InitTreeList();
}
DBTreeList::DBTreeList(std::unique_ptr<weld::TreeView> xTreeView)
: bInitialized(false)
, bShowColumns(false)
, pImpl(new SwDBTreeList_Impl)
, m_xTreeView(std::move(xTreeView))
{
m_xTreeView->connect_expanding(LINK(this, DBTreeList, RequestingChildrenHdl));
#if 0
if (m_xTreeView->get_visible())
InitTreeList();
#endif
}
DBTreeList::~DBTreeList()
{
}
void DBTreeList::InitTreeList()
{
if (!pImpl->HasContext() && pImpl->GetWrtShell())
return;
//TODO SetDragDropMode(DragDropMode::APP_COPY);
//TODO GetModel()->SetCompareHdl(LINK(this, DBTreeList, DBCompare));
Sequence< OUString > aDBNames = pImpl->GetContext()->getElementNames();
auto const sort = comphelper::string::NaturalStringSorter(
comphelper::getProcessComponentContext(),
Application::GetSettings().GetUILanguageTag().getLocale());
std::sort(
aDBNames.begin(), aDBNames.end(),
[&sort](OUString const & x, OUString const & y)
{ return sort.compare(x, y) < 0; });
const OUString* pDBNames = aDBNames.getConstArray();
sal_Int32 nCount = aDBNames.getLength();
OUString aImg(RID_BMP_DB);
for (sal_Int32 i = 0; i < nCount; ++i)
{
OUString sDBName(pDBNames[i]);
Reference<XConnection> xConnection = pImpl->GetConnection(sDBName);
if (xConnection.is())
{
m_xTreeView->insert(nullptr, -1, &sDBName, nullptr, nullptr, nullptr, &aImg, true, nullptr);
}
}
Select(OUString(), OUString(), OUString());
bInitialized = true;
}
void DBTreeList::AddDataSource(const OUString& rSource)
{
OUString aImg(RID_BMP_DB);
std::unique_ptr<weld::TreeIter> xIter(m_xTreeView->make_iterator());
m_xTreeView->insert(nullptr, -1, &rSource, nullptr, nullptr, nullptr, &aImg, true, xIter.get());
m_xTreeView->select(*xIter);
}
IMPL_LINK(DBTreeList, RequestingChildrenHdl, weld::TreeIter&, rParent, bool)
{
if (!m_xTreeView->iter_has_child(rParent))
{
if (m_xTreeView->get_iter_depth(rParent)) // column names
{
try
{
std::unique_ptr<weld::TreeIter> xGrandParent(m_xTreeView->make_iterator(&rParent));
m_xTreeView->iter_parent(*xGrandParent);
OUString sSourceName = m_xTreeView->get_text(*xGrandParent);
OUString sTableName = m_xTreeView->get_text(rParent);
if(!pImpl->GetContext()->hasByName(sSourceName))
return true;
Reference<XConnection> xConnection = pImpl->GetConnection(sSourceName);
bool bTable = m_xTreeView->get_id(rParent).isEmpty();
Reference<XColumnsSupplier> xColsSupplier;
if(bTable)
{
Reference<XTablesSupplier> xTSupplier(xConnection, UNO_QUERY);
if(xTSupplier.is())
{
Reference<XNameAccess> xTables = xTSupplier->getTables();
OSL_ENSURE(xTables->hasByName(sTableName), "table not available anymore?");
try
{
Any aTable = xTables->getByName(sTableName);
Reference<XPropertySet> xPropSet;
aTable >>= xPropSet;
xColsSupplier.set(xPropSet, UNO_QUERY);
}
catch (const Exception&)
{
}
}
}
else
{
Reference<XQueriesSupplier> xQSupplier(xConnection, UNO_QUERY);
if(xQSupplier.is())
{
Reference<XNameAccess> xQueries = xQSupplier->getQueries();
OSL_ENSURE(xQueries->hasByName(sTableName), "table not available anymore?");
try
{
Any aQuery = xQueries->getByName(sTableName);
Reference<XPropertySet> xPropSet;
aQuery >>= xPropSet;
xColsSupplier.set(xPropSet, UNO_QUERY);
}
catch (const Exception&)
{
}
}
}
if(xColsSupplier.is())
{
Reference <XNameAccess> xCols = xColsSupplier->getColumns();
Sequence< OUString> aColNames = xCols->getElementNames();
const OUString* pColNames = aColNames.getConstArray();
long nCount = aColNames.getLength();
for (long i = 0; i < nCount; i++)
{
OUString sName = pColNames[i];
m_xTreeView->append(&rParent, sName);
}
}
}
catch (const Exception&)
{
}
}
else // table names
{
try
{
OUString sSourceName = m_xTreeView->get_text(rParent);
if (!pImpl->GetContext()->hasByName(sSourceName))
return true;
Reference<XConnection> xConnection = pImpl->GetConnection(sSourceName);
if (xConnection.is())
{
Reference<XTablesSupplier> xTSupplier(xConnection, UNO_QUERY);
if(xTSupplier.is())
{
Reference<XNameAccess> xTables = xTSupplier->getTables();
Sequence< OUString> aTableNames = xTables->getElementNames();
OUString sTableName;
long nCount = aTableNames.getLength();
const OUString* pTableNames = aTableNames.getConstArray();
OUString aImg(RID_BMP_DBTABLE);
for (long i = 0; i < nCount; i++)
{
sTableName = pTableNames[i];
m_xTreeView->insert(&rParent, -1, &sTableName, nullptr,
nullptr, nullptr, &aImg, bShowColumns, nullptr);
}
}
Reference<XQueriesSupplier> xQSupplier(xConnection, UNO_QUERY);
if(xQSupplier.is())
{
Reference<XNameAccess> xQueries = xQSupplier->getQueries();
Sequence< OUString> aQueryNames = xQueries->getElementNames();
OUString sQueryName;
long nCount = aQueryNames.getLength();
const OUString* pQueryNames = aQueryNames.getConstArray();
OUString aImg(RID_BMP_DBQUERY);
for (long i = 0; i < nCount; i++)
{
sQueryName = pQueryNames[i];
//to discriminate between queries and tables the user data of query entries is set
OUString sId(OUString::number(1));
m_xTreeView->insert(&rParent, -1, &sQueryName, &sId,
nullptr, nullptr, &aImg, bShowColumns, nullptr);
}
}
}
}
catch (const Exception&)
{
}
}
}
return true;
}
#if 0
IMPL_LINK( DBTreeList, DBCompare, const SvSortData&, rData, sal_Int32 )
{
SvTreeListEntry* pRight = const_cast<SvTreeListEntry*>(rData.pRight);
if (GetParent(pRight) && GetParent(GetParent(pRight)))
return 1; // don't sort column names
return DefaultCompare(rData); // otherwise call base class
}
#endif
OUString DBTreeList::GetDBName(OUString& rTableName, OUString& rColumnName, sal_Bool* pbIsTable)
{
OUString sDBName;
std::unique_ptr<weld::TreeIter> xIter(m_xTreeView->make_iterator());
if (m_xTreeView->get_selected(xIter.get()) && m_xTreeView->get_iter_depth(*xIter))
{
if (m_xTreeView->get_iter_depth(*xIter) > 2)
{
rColumnName = m_xTreeView->get_text(*xIter);
m_xTreeView->iter_parent(*xIter); // column name was selected
}
if (pbIsTable)
{
*pbIsTable = m_xTreeView->get_id(*xIter).isEmpty();
}
rTableName = m_xTreeView->get_text(*xIter);
m_xTreeView->iter_parent(*xIter);
sDBName = m_xTreeView->get_text(*xIter);
}
return sDBName;
}
// Format: database.table
void DBTreeList::Select(const OUString& rDBName, const OUString& rTableName, const OUString& rColumnName)
{
std::unique_ptr<weld::TreeIter> xParent(m_xTreeView->make_iterator());
if (!m_xTreeView->get_iter_first(*xParent))
return;
do
{
if (rDBName == m_xTreeView->get_text(*xParent))
{
if (!m_xTreeView->iter_has_child(*xParent))
m_xTreeView->expand_row(*xParent);
std::unique_ptr<weld::TreeIter> xChild(m_xTreeView->make_iterator(xParent.get()));
if (!m_xTreeView->iter_children(*xChild))
continue;
do
{
if (rTableName == m_xTreeView->get_text(*xChild))
{
m_xTreeView->copy_iterator(*xChild, *xParent);
bool bNoChild = false;
if (bShowColumns && !rColumnName.isEmpty())
{
if (!m_xTreeView->iter_has_child(*xParent))
m_xTreeView->expand_row(*xParent);
bNoChild = true;
if (m_xTreeView->iter_children(*xChild))
{
do
{
if (rColumnName == m_xTreeView->get_text(*xChild))
{
bNoChild = false;
break;
}
}
while (m_xTreeView->iter_next_sibling(*xChild));
}
}
if (bNoChild)
m_xTreeView->copy_iterator(*xParent, *xChild);
m_xTreeView->scroll_to_row(*xChild);
m_xTreeView->select(*xChild);
return;
}
}
while (m_xTreeView->iter_next_sibling(*xChild));
}
} while (m_xTreeView->iter_next_sibling(*xParent));
}
void DBTreeList::SetWrtShell(SwWrtShell& rSh)
{
pImpl->SetWrtShell(rSh);
if (m_xTreeView->get_visible() && !bInitialized)
InitTreeList();
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sw/source/uibase/inc/changedb.hxx b/sw/source/uibase/inc/changedb.hxx
index b2563f0..9beae0b 100644
--- a/sw/source/uibase/inc/changedb.hxx
+++ b/sw/source/uibase/inc/changedb.hxx
@@ -19,11 +19,8 @@
#ifndef INCLUDED_SW_SOURCE_UIBASE_INC_CHANGEDB_HXX
#define INCLUDED_SW_SOURCE_UIBASE_INC_CHANGEDB_HXX
#include <vcl/bitmap.hxx>
#include <vcl/button.hxx>
#include <vcl/fixed.hxx>
#include <vcl/treelistbox.hxx>
#include <svx/stddlg.hxx>
#include <vcl/weld.hxx>
#include "dbtree.hxx"
class SwFieldMgr;
@@ -32,30 +29,31 @@ class SwWrtShell;
struct SwDBData;
// exchange database at fields
class SwChangeDBDlg: public SvxStandardDialog
class SwChangeDBDlg : public SfxDialogController
{
VclPtr<SvTreeListBox> m_pUsedDBTLB;
VclPtr<SwDBTreeList> m_pAvailDBTLB;
VclPtr<PushButton> m_pAddDBPB;
VclPtr<FixedText> m_pDocDBNameFT;
VclPtr<PushButton> m_pDefineBT;
SwWrtShell *pSh;
DECL_LINK(TreeSelectHdl, SvTreeListBox*, void);
DECL_LINK(ButtonHdl, Button*, void);
DECL_LINK(AddDBHdl, Button*, void);
std::unique_ptr<weld::TreeView> m_xUsedDBTLB;
std::unique_ptr<DBTreeList> m_xAvailDBTLB;
std::unique_ptr<weld::Button> m_xAddDBPB;
std::unique_ptr<weld::Label> m_xDocDBNameFT;
std::unique_ptr<weld::Button> m_xDefineBT;
virtual void Apply() override;
void TreeSelect();
DECL_LINK(TreeSelectHdl, weld::TreeView&, void);
DECL_LINK(ButtonHdl, weld::Button&, void);
DECL_LINK(AddDBHdl, weld::Button&, void);
void UpdateFields();
void FillDBPopup();
SvTreeListEntry* Insert(const OUString& rDBName);
std::unique_ptr<weld::TreeIter> Insert(const OUString& rDBName);
void ShowDBName(const SwDBData& rDBData);
public:
SwChangeDBDlg(SwView const & rVw);
virtual short run() override;
virtual ~SwChangeDBDlg() override;
virtual void dispose() override;
};
#endif
diff --git a/sw/source/uibase/inc/dbtree.hxx b/sw/source/uibase/inc/dbtree.hxx
index 333f850..c9634b6 100644
--- a/sw/source/uibase/inc/dbtree.hxx
+++ b/sw/source/uibase/inc/dbtree.hxx
@@ -21,6 +21,7 @@
#include <memory>
#include <vcl/treelistbox.hxx>
#include <vcl/weld.hxx>
#include <swdllapi.h>
#include <swtypes.hxx>
@@ -62,6 +63,40 @@ public:
void AddDataSource(const OUString& rSource);
};
class SW_DLLPUBLIC DBTreeList
{
bool bInitialized;
bool bShowColumns;
rtl::Reference<SwDBTreeList_Impl> pImpl;
std::unique_ptr<weld::TreeView> m_xTreeView;
#if 0
DECL_DLLPRIVATE_LINK( DBCompare, const SvSortData&, sal_Int32 );
#endif
DECL_DLLPRIVATE_LINK(RequestingChildrenHdl, weld::TreeIter&, bool);
SAL_DLLPRIVATE void InitTreeList();
public:
DBTreeList(std::unique_ptr<weld::TreeView> xTreeView);
~DBTreeList();
OUString GetDBName(OUString& rTableName, OUString& rColumnName, sal_Bool* pbIsTable = nullptr);
void Select( const OUString& rDBName, const OUString& rTableName,
const OUString& rColumnName );
void SetWrtShell(SwWrtShell& rSh);
void AddDataSource(const OUString& rSource);
void connect_changed(const Link<weld::TreeView&, void>& rLink) { m_xTreeView->connect_changed(rLink); }
std::unique_ptr<weld::TreeIter> make_iterator(const weld::TreeIter* pOrig = nullptr) const { return m_xTreeView->make_iterator(pOrig); }
bool get_selected(weld::TreeIter* pIter) const { return m_xTreeView->get_selected(pIter); }
int get_iter_depth(const weld::TreeIter& rIter) const { return m_xTreeView->get_iter_depth(rIter); }
void set_size_request(int nWidth, int nHeight) { m_xTreeView->set_size_request(nWidth, nHeight); }
};
#endif
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sw/uiconfig/swriter/ui/exchangedatabases.ui b/sw/uiconfig/swriter/ui/exchangedatabases.ui
index d2a4486..44f3285c 100644
--- a/sw/uiconfig/swriter/ui/exchangedatabases.ui
+++ b/sw/uiconfig/swriter/ui/exchangedatabases.ui
@@ -1,12 +1,35 @@
<?xml version="1.0" encoding="UTF-8"?>
<!-- Generated with glade 3.16.0 -->
<!-- Generated with glade 3.22.1 -->
<interface domain="sw">
<requires lib="gtk+" version="3.18"/>
<object class="GtkTreeStore" id="liststore1">
<columns>
<!-- column-name expander -->
<column type="GdkPixbuf"/>
<!-- column-name text -->
<column type="gchararray"/>
<!-- column-name id -->
<column type="gchararray"/>
</columns>
</object>
<object class="GtkTreeStore" id="liststore2">
<columns>
<!-- column-name expander -->
<column type="GdkPixbuf"/>
<!-- column-name text -->
<column type="gchararray"/>
<!-- column-name id -->
<column type="gchararray"/>
</columns>
</object>
<object class="GtkDialog" id="ExchangeDatabasesDialog">
<property name="can_focus">False</property>
<property name="border_width">6</property>
<property name="title" translatable="yes" context="exchangedatabases|ExchangeDatabasesDialog">Exchange Databases</property>
<property name="type_hint">dialog</property>
<child>
<placeholder/>
</child>
<child internal-child="vbox">
<object class="GtkBox" id="dialog-vbox1">
<property name="can_focus">False</property>
@@ -17,7 +40,7 @@
<property name="can_focus">False</property>
<property name="layout_style">end</property>
<child>
<object class="GtkButton" id="define">
<object class="GtkButton" id="ok">
<property name="label" translatable="yes" context="exchangedatabases|define">Define</property>
<property name="visible">True</property>
<property name="can_focus">True</property>
@@ -57,6 +80,7 @@
<property name="expand">False</property>
<property name="fill">True</property>
<property name="position">2</property>
<property name="secondary">True</property>
</packing>
</child>
</object>
@@ -102,32 +126,28 @@
<object class="GtkLabel" id="label5">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="xalign">0</property>
<property name="label" translatable="yes" context="exchangedatabases|label5">Databases in Use</property>
<property name="use_underline">True</property>
<property name="mnemonic_widget">inuselb:border</property>
<property name="mnemonic_widget">inuselb</property>
<property name="xalign">0</property>
</object>
<packing>
<property name="left_attach">0</property>
<property name="top_attach">0</property>
<property name="width">1</property>
<property name="height">1</property>
</packing>
</child>
<child>
<object class="GtkLabel" id="label6">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="xalign">0</property>
<property name="label" translatable="yes" context="exchangedatabases|label6">_Available Databases</property>
<property name="use_underline">True</property>
<property name="mnemonic_widget">availablelb:border</property>
<property name="mnemonic_widget">availablelb</property>
<property name="xalign">0</property>
</object>
<packing>
<property name="left_attach">1</property>
<property name="top_attach">0</property>
<property name="width">1</property>
<property name="height">1</property>
</packing>
</child>
<child>
@@ -142,8 +162,6 @@
<packing>
<property name="left_attach">1</property>
<property name="top_attach">2</property>
<property name="width">1</property>
<property name="height">1</property>
</packing>
</child>
<child>
@@ -152,45 +170,113 @@
<property name="can_focus">False</property>
<property name="margin_top">12</property>
<property name="margin_bottom">12</property>
<property name="xalign">0</property>
<property name="label" translatable="yes" context="exchangedatabases|label7">Use this dialog to replace the databases you access in your document via database fields, with other databases. You can only make one change at a time. Multiple selection is possible in the list on the left.
Use the browse button to select a database file.</property>
<property name="wrap">True</property>
<property name="width_chars">72</property>
<property name="max_width_chars">72</property>
<property name="xalign">0</property>
</object>
<packing>
<property name="left_attach">0</property>
<property name="top_attach">3</property>
<property name="width">2</property>
<property name="height">1</property>
</packing>
</child>
<child>
<object class="vcllo-SvTreeListBox" id="inuselb:border">
<object class="GtkScrolledWindow">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="can_focus">True</property>
<property name="hexpand">True</property>
<property name="vexpand">True</property>
<property name="shadow_type">in</property>
<child>
<object class="GtkTreeView" id="inuselb">
<property name="width_request">-1</property>
<property name="visible">True</property>
<property name="can_focus">True</property>
<property name="receives_default">True</property>
<property name="hexpand">True</property>
<property name="vexpand">True</property>
<property name="model">liststore1</property>
<property name="headers_visible">False</property>
<property name="show_expanders">True</property>
<property name="search_column">1</property>
<property name="enable_tree_lines">True</property>
<child internal-child="selection">
<object class="GtkTreeSelection" id="Macro Library List-selection1"/>
</child>
<child>
<object class="GtkTreeViewColumn" id="treeviewcolumn2">
<property name="spacing">6</property>
<child>
<object class="GtkCellRendererPixbuf" id="cellrenderertext4"/>
<attributes>
<attribute name="pixbuf">0</attribute>
</attributes>
</child>
<child>
<object class="GtkCellRendererText" id="cellrenderertext2"/>
<attributes>
<attribute name="text">1</attribute>
</attributes>
</child>
</object>
</child>
</object>
</child>
</object>
<packing>
<property name="left_attach">0</property>
<property name="top_attach">1</property>
<property name="width">1</property>
<property name="height">1</property>
</packing>
</child>
<child>
<object class="swlo-SwDBTreeList" id="availablelb:border">
<object class="GtkScrolledWindow">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="can_focus">True</property>
<property name="hexpand">True</property>
<property name="vexpand">True</property>
<property name="shadow_type">in</property>
<child>
<object class="GtkTreeView" id="availablelb">
<property name="width_request">-1</property>
<property name="visible">True</property>
<property name="can_focus">True</property>
<property name="receives_default">True</property>
<property name="hexpand">True</property>
<property name="vexpand">True</property>
<property name="model">liststore2</property>
<property name="headers_visible">False</property>
<property name="show_expanders">True</property>
<property name="search_column">1</property>
<property name="enable_tree_lines">True</property>
<child internal-child="selection">
<object class="GtkTreeSelection" id="Macro Library List-selection2"/>
</child>
<child>
<object class="GtkTreeViewColumn" id="treeviewcolumn8">
<property name="spacing">6</property>
<child>
<object class="GtkCellRendererPixbuf" id="cellrenderertext5"/>
<attributes>
<attribute name="pixbuf">0</attribute>
</attributes>
</child>
<child>
<object class="GtkCellRendererText" id="cellrenderertext6"/>
<attributes>
<attribute name="text">1</attribute>
</attributes>
</child>
</object>
</child>
</object>
</child>
</object>
<packing>
<property name="left_attach">1</property>
<property name="top_attach">1</property>
<property name="width">1</property>
<property name="height">1</property>
</packing>
</child>
<child>
@@ -238,7 +324,7 @@ Use the browse button to select a database file.</property>
<object class="GtkLabel" id="dbnameft">
<property name="visible">True</property>
<property name="can_focus">False</property>
<property name="label" translatable="no">DataSource.Command</property>
<property name="label">DataSource.Command</property>
</object>
<packing>
<property name="expand">False</property>
@@ -263,7 +349,7 @@ Use the browse button to select a database file.</property>
</object>
</child>
<action-widgets>
<action-widget response="0">define</action-widget>
<action-widget response="-5">ok</action-widget>
<action-widget response="-7">close</action-widget>
<action-widget response="-11">help</action-widget>
</action-widgets>