[Libreoffice-commits] .: Branch 'libreoffice-4-0' - configmgr/qa officecfg/registry sfx2/sdi sfx2/source svtools/AllLangResTarget_svt.mk svtools/inc svtools/Library_svt.mk svtools/Package_inc.mk svtools/source svtools/util sw/uiconfig

Libreoffice Gerrit user logerrit at kemper.freedesktop.org
Thu Dec 20 00:52:40 PST 2012


 configmgr/qa/unit/data.xcd                                           |    5 
 officecfg/registry/data/org/openoffice/Office/UI/GenericCommands.xcu |    5 
 sfx2/sdi/appslots.sdi                                                |    5 
 sfx2/sdi/sfx.sdi                                                     |   25 
 sfx2/source/appl/appserv.cxx                                         |    9 
 sfx2/source/doc/docvor.cxx                                           |   18 
 sfx2/source/doc/docvor.hrc                                           |    1 
 sfx2/source/doc/docvor.src                                           |    7 
 svtools/AllLangResTarget_svt.mk                                      |    1 
 svtools/Library_svt.mk                                               |    2 
 svtools/Package_inc.mk                                               |    1 
 svtools/inc/svtools/addresstemplate.hxx                              |  155 +
 svtools/inc/svtools/svtools.hrc                                      |    1 
 svtools/source/dialogs/addresstemplate.cxx                           | 1327 ++++++++++
 svtools/source/dialogs/addresstemplate.src                           |  313 ++
 svtools/source/uno/addrtempuno.cxx                                   |  228 +
 svtools/source/uno/miscservices.cxx                                  |   14 
 svtools/util/svt.component                                           |    3 
 sw/uiconfig/sglobal/menubar/menubar.xml                              |    1 
 sw/uiconfig/sweb/menubar/menubar.xml                                 |    1 
 sw/uiconfig/swform/menubar/menubar.xml                               |    1 
 sw/uiconfig/swreport/menubar/menubar.xml                             |    1 
 sw/uiconfig/swriter/menubar/menubar.xml                              |    1 
 sw/uiconfig/swxform/menubar/menubar.xml                              |    1 
 24 files changed, 2126 insertions(+)

New commits:
commit e0df39ae0456d6cc7ea150826c909447cbb44773
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Thu Dec 20 09:42:58 2012 +0100

    Partially reverted 786f15e605867668d88ab23d66cabb18f18bdcf9
    
    This dialog is still of some use with some Writer Wizards and templates.
    Re-added the dialog, but moved the menu entry to Tools menu in Writer.
    The menu entry has not been added back in the other applications.
    
    Change-Id: I1388d955752e99ab6d39dfc81bb41a97b33bdfcd

diff --git a/configmgr/qa/unit/data.xcd b/configmgr/qa/unit/data.xcd
index d22684e..d82baec 100644
--- a/configmgr/qa/unit/data.xcd
+++ b/configmgr/qa/unit/data.xcd
@@ -4042,6 +4042,11 @@
           <value xml:lang="x-no-translate"></value><value xml:lang="en-US">Do Not Mark Errors</value>
         </prop>
       </node>
+      <node oor:name=".uno:AddressBookSource" oor:op="replace">
+        <prop oor:name="Label" oor:type="xs:string">
+          <value xml:lang="x-no-translate"></value><value xml:lang="en-US">~Address Book Source...</value>
+        </prop>
+      </node>
       <node oor:name=".uno:RubyDialog" oor:op="replace">
         <prop oor:name="Label" oor:type="xs:string">
           <value xml:lang="x-no-translate"></value><value xml:lang="en-US">As~ian phonetic guide...</value>
diff --git a/officecfg/registry/data/org/openoffice/Office/UI/GenericCommands.xcu b/officecfg/registry/data/org/openoffice/Office/UI/GenericCommands.xcu
index 9ad65bd..aa55b28 100644
--- a/officecfg/registry/data/org/openoffice/Office/UI/GenericCommands.xcu
+++ b/officecfg/registry/data/org/openoffice/Office/UI/GenericCommands.xcu
@@ -4063,6 +4063,11 @@
                     <value xml:lang="en-US">Do Not Mark Errors</value>
                 </prop>
             </node>
+            <node oor:name=".uno:AddressBookSource" oor:op="replace">
+                <prop oor:name="Label" oor:type="xs:string">
+                    <value xml:lang="en-US">~Address Book Source...</value>
+                </prop>
+            </node>
             <node oor:name=".uno:RubyDialog" oor:op="replace">
                 <prop oor:name="Label" oor:type="xs:string">
                     <value xml:lang="en-US">As~ian phonetic guide...</value>
diff --git a/sfx2/sdi/appslots.sdi b/sfx2/sdi/appslots.sdi
index 73d37cf..9f7d6cc 100644
--- a/sfx2/sdi/appslots.sdi
+++ b/sfx2/sdi/appslots.sdi
@@ -127,6 +127,11 @@ interface Application
     [
         ExecMethod = MiscExec_Impl ;
     ]
+    SID_TEMPLATE_ADDRESSBOKSOURCE // ole(no) api(final/play/rec)
+    [
+        ExecMethod = MiscExec_Impl ;
+        StateMethod = MiscState_Impl ;
+    ]
     SID_ATTR_UNDO_COUNT // ole(no) api(final/play)
     [
         ExecMethod = PropExec_Impl ;
diff --git a/sfx2/sdi/sfx.sdi b/sfx2/sdi/sfx.sdi
index dac4893..7c19226 100644
--- a/sfx2/sdi/sfx.sdi
+++ b/sfx2/sdi/sfx.sdi
@@ -337,6 +337,31 @@ SfxObjectItem AddDirect SID_NEWDOCDIRECT
 ]
 
 //--------------------------------------------------------------------------
+SfxVoidItem AddressBookSource SID_TEMPLATE_ADDRESSBOKSOURCE
+()
+[
+    /* flags: */
+    AutoUpdate = FALSE,
+    Cachable = Cachable,
+    FastCall = FALSE,
+    HasCoreId = FALSE,
+    HasDialog = TRUE,
+    ReadOnlyDoc = TRUE,
+    Toggle = FALSE,
+    Container = TRUE,
+    RecordAbsolute = FALSE,
+    RecordPerSet;
+    Asynchron;
+
+    /* config: */
+    AccelConfig = TRUE,
+    MenuConfig = TRUE,
+    StatusBarConfig = FALSE,
+    ToolBoxConfig = TRUE,
+    GroupId = GID_TEMPLATE;
+]
+
+//--------------------------------------------------------------------------
 SfxVoidItem AddWatch SID_BASICIDE_ADDWATCH
 ()
 [
diff --git a/sfx2/source/appl/appserv.cxx b/sfx2/source/appl/appserv.cxx
index 38346f7..fd224a5 100644
--- a/sfx2/source/appl/appserv.cxx
+++ b/sfx2/source/appl/appserv.cxx
@@ -45,6 +45,7 @@
 #include <comphelper/storagehelper.hxx>
 #include "comphelper/configurationhelper.hxx"
 
+#include <svtools/addresstemplate.hxx>
 #include <svtools/miscopt.hxx>
 #include <svtools/restartdialog.hxx>
 #include <svl/visitem.hxx>
@@ -612,6 +613,14 @@ void SfxApplication::MiscExec_Impl( SfxRequest& rReq )
             break;
         }
 
+        case SID_TEMPLATE_ADDRESSBOKSOURCE:
+        {
+            svt::AddressBookSourceDialog aDialog(GetTopWindow(), ::comphelper::getProcessServiceFactory());
+            aDialog.Execute();
+            bDone = true;
+            break;
+        }
+
 #ifndef DISABLE_SCRIPTING
         case SID_BASICSTOP:
             StarBASIC::Stop();
diff --git a/sfx2/source/doc/docvor.cxx b/sfx2/source/doc/docvor.cxx
index 07cce42..4ad9a10 100644
--- a/sfx2/source/doc/docvor.cxx
+++ b/sfx2/source/doc/docvor.cxx
@@ -60,6 +60,7 @@
 #include <sfx2/filedlghelper.hxx>
 #include <sfx2/fcontnr.hxx>
 #include <svtools/localresaccess.hxx>
+#include <svtools/addresstemplate.hxx>
 #include "svtools/treelistentry.hxx"
 #include <comphelper/processfactory.hxx>
 
@@ -134,6 +135,7 @@ friend class SfxOrganizeListBox_Impl;
     OKButton                aOkBtn;
     MenuButton              aEditBtn;
     HelpButton              aHelpBtn;
+    PushButton              aAddressTemplateBtn;
     PushButton              aFilesBtn;
 
     Accelerator             aEditAcc;
@@ -157,6 +159,7 @@ friend class SfxOrganizeListBox_Impl;
     DECL_LINK( MenuSelect_Impl, Menu * );
     DECL_LINK( MenuActivate_Impl, Menu * );
     DECL_LINK( AddFiles_Impl, Button * );
+    DECL_LINK( OnAddressTemplateClicked, Button * );
 
     DECL_LINK(ImportHdl, void *);
     DECL_LINK(ExportHdl, void *);
@@ -193,6 +196,7 @@ SfxOrganizeDlg_Impl::SfxOrganizeDlg_Impl( SfxTemplateOrganizeDlg* pParent,
     aOkBtn              ( pParent, SfxResId( BTN_OK ) ),
     aEditBtn            ( pParent, SfxResId( BTN_EDIT ) ),
     aHelpBtn            ( pParent, SfxResId( BTN_HELP ) ),
+    aAddressTemplateBtn ( pParent, SfxResId( BTN_ADDRESSTEMPLATE ) ),
     aFilesBtn           ( pParent, SfxResId( BTN_FILES ) ),
 
     aEditAcc    ( SfxResId( ACC_EDIT ) ),
@@ -246,6 +250,8 @@ SfxOrganizeDlg_Impl::SfxOrganizeDlg_Impl( SfxTemplateOrganizeDlg* pParent,
 
     aFilesBtn.SetClickHdl(
         LINK(this,SfxOrganizeDlg_Impl, AddFiles_Impl));
+    aAddressTemplateBtn.SetClickHdl(
+        LINK(this,SfxOrganizeDlg_Impl, OnAddressTemplateClicked));
     aLeftTypLb.SetSelectHdl(
         LINK(this, SfxOrganizeDlg_Impl, LeftListBoxSelect_Impl));
     aRightTypLb.SetSelectHdl(
@@ -259,6 +265,8 @@ SfxOrganizeDlg_Impl::SfxOrganizeDlg_Impl( SfxTemplateOrganizeDlg* pParent,
     aRightLb.SetPosSizePixel(pParent->LogicToPixel(Point(103, 6), MAP_APPFONT),
                              pParent->LogicToPixel(Size(94, 132), MAP_APPFONT));
 
+    if ( !SvtModuleOptions().IsModuleInstalled(SvtModuleOptions::E_SDATABASE) )
+        aAddressTemplateBtn.Hide();
     Font aFont(aLeftLb.GetFont());
     aFont.SetWeight(WEIGHT_NORMAL);
     aLeftLb.SetFont(aFont);
@@ -2158,6 +2166,16 @@ IMPL_LINK( SfxOrganizeDlg_Impl, RightListBoxSelect_Impl, ListBox *, pBox )
 
 //-------------------------------------------------------------------------
 
+IMPL_LINK( SfxOrganizeDlg_Impl, OnAddressTemplateClicked, Button *, pButton )
+{
+    (void)pButton; //unused
+    svt::AddressBookSourceDialog aDialog(pDialog, ::comphelper::getProcessServiceFactory());
+    aDialog.Execute();
+    return 0L;
+}
+
+//-------------------------------------------------------------------------
+
 IMPL_LINK( SfxOrganizeDlg_Impl, AddFiles_Impl, Button *, pButton )
 
 /*  [Description]
diff --git a/sfx2/source/doc/docvor.hrc b/sfx2/source/doc/docvor.hrc
index 2196210..f191ddd 100644
--- a/sfx2/source/doc/docvor.hrc
+++ b/sfx2/source/doc/docvor.hrc
@@ -43,6 +43,7 @@
 #define LB_LEFT_TYP 2
 #define BTN_EDIT 105
 #define BTN_FILES 3
+#define BTN_ADDRESSTEMPLATE 4
 #define LB_LEFT 1
 #define BTN_HELP 100
 
diff --git a/sfx2/source/doc/docvor.src b/sfx2/source/doc/docvor.src
index 22da0c3..95a6aca 100644
--- a/sfx2/source/doc/docvor.src
+++ b/sfx2/source/doc/docvor.src
@@ -55,6 +55,13 @@ ModalDialog DLG_ORGANIZE
         Text [ en-US ] = "~File..." ;
         TabStop = TRUE ;
     };
+    PushButton BTN_ADDRESSTEMPLATE
+    {
+        HelpID = "sfx2:PushButton:DLG_ORGANIZE:BTN_ADDRESSTEMPLATE";
+        Pos = MAP_APPFONT ( 205 , 124 ) ;
+        Size = MAP_APPFONT ( 60 , 14 ) ;
+        Text [ en-US ] = "~Address Book..." ;
+    };
     ListBox LB_LEFT_TYP
     {
         HelpID = "sfx2:ListBox:DLG_ORGANIZE:LB_LEFT_TYP";
diff --git a/svtools/AllLangResTarget_svt.mk b/svtools/AllLangResTarget_svt.mk
index 3b59e5d..7be5ae9 100644
--- a/svtools/AllLangResTarget_svt.mk
+++ b/svtools/AllLangResTarget_svt.mk
@@ -49,6 +49,7 @@ $(eval $(call gb_SrsTarget_add_files,svt/res,\
     svtools/source/control/ctrlbox.src \
     svtools/source/control/ctrltool.src \
     svtools/source/control/filectrl.src \
+    svtools/source/dialogs/addresstemplate.src \
     svtools/source/dialogs/filedlg2.src \
     svtools/source/dialogs/formats.src \
     svtools/source/dialogs/prnsetup.src \
diff --git a/svtools/Library_svt.mk b/svtools/Library_svt.mk
index 9fb3a42..97b7e2e 100644
--- a/svtools/Library_svt.mk
+++ b/svtools/Library_svt.mk
@@ -123,6 +123,7 @@ $(eval $(call gb_Library_add_exception_objects,svt,\
     svtools/source/control/urlcontrol \
     svtools/source/control/valueacc \
     svtools/source/control/valueset \
+    svtools/source/dialogs/addresstemplate \
     svtools/source/dialogs/colrdlg \
     svtools/source/dialogs/filedlg \
     svtools/source/dialogs/filedlg2 \
@@ -230,6 +231,7 @@ $(eval $(call gb_Library_add_exception_objects,svt,\
     svtools/source/toolpanel/toolpaneldeckpeer \
     svtools/source/toolpanel/toolpaneldrawer \
     svtools/source/toolpanel/toolpaneldrawerpeer \
+    svtools/source/uno/addrtempuno \
     svtools/source/uno/contextmenuhelper \
     svtools/source/uno/framestatuslistener \
     svtools/source/uno/generictoolboxcontroller \
diff --git a/svtools/Package_inc.mk b/svtools/Package_inc.mk
index beca57f..85afa18 100644
--- a/svtools/Package_inc.mk
+++ b/svtools/Package_inc.mk
@@ -27,6 +27,7 @@ $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/accessibilityoptions.h
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/accessiblefactory.hxx,svtools/accessiblefactory.hxx))
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/accessibletable.hxx,svtools/accessibletable.hxx))
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/accessibletableprovider.hxx,svtools/accessibletableprovider.hxx))
+$(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/addresstemplate.hxx,svtools/addresstemplate.hxx))
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/apearcfg.hxx,svtools/apearcfg.hxx))
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/asynclink.hxx,svtools/asynclink.hxx))
 $(eval $(call gb_Package_add_file,svtools_inc,inc/svtools/bindablecontrolhelper.hxx,svtools/bindablecontrolhelper.hxx))
diff --git a/svtools/inc/svtools/addresstemplate.hxx b/svtools/inc/svtools/addresstemplate.hxx
new file mode 100644
index 0000000..7d716f6
--- /dev/null
+++ b/svtools/inc/svtools/addresstemplate.hxx
@@ -0,0 +1,155 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#ifndef _SVT_ADDRESSTEMPLATE_HXX_
+#define _SVT_ADDRESSTEMPLATE_HXX_
+
+#include "svtools/svtdllapi.h"
+#include <vcl/dialog.hxx>
+#include <vcl/group.hxx>
+#include <vcl/fixed.hxx>
+#include <vcl/combobox.hxx>
+#include <vcl/button.hxx>
+#include <vcl/lstbox.hxx>
+#include <vcl/scrbar.hxx>
+#include <com/sun/star/container/XNameAccess.hpp>
+#include <com/sun/star/lang/XMultiServiceFactory.hpp>
+#include <com/sun/star/util/AliasProgrammaticPair.hpp>
+#include <com/sun/star/sdb/XDatabaseContext.hpp>
+#include <com/sun/star/sdbc/XDataSource.hpp>
+#include <unotools/configitem.hxx>
+
+// .......................................................................
+namespace svt
+{
+// .......................................................................
+
+    // ===================================================================
+    // = AddressBookSourceDialog
+    // ===================================================================
+    struct AddressBookSourceDialogData;
+    class SVT_DLLPUBLIC AddressBookSourceDialog : public ModalDialog
+    {
+    protected:
+        // Controls
+        FixedLine       m_aDatasourceFrame;
+        FixedText       m_aDatasourceLabel;
+        ComboBox        m_aDatasource;
+        PushButton      m_aAdministrateDatasources;
+        FixedText       m_aTableLabel;
+        ComboBox        m_aTable;
+
+        FixedText       m_aFieldsTitle;
+        Window          m_aFieldsFrame;
+
+        ScrollBar       m_aFieldScroller;
+        OKButton        m_aOK;
+        CancelButton    m_aCancel;
+        HelpButton      m_aHelp;
+
+        // string to display for "no selection"
+        const String    m_sNoFieldSelection;
+
+        /// the DatabaseContext for selecting data sources
+        ::com::sun::star::uno::Reference< ::com::sun::star::sdb::XDatabaseContext >
+                        m_xDatabaseContext;
+        // the ORB for creating objects
+        ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >
+                        m_xORB;
+        ::com::sun::star::uno::Reference< ::com::sun::star::container::XNameAccess >
+                        m_xCurrentDatasourceTables;
+
+        AddressBookSourceDialogData*
+                        m_pImpl;
+
+    public:
+        AddressBookSourceDialog( Window* _pParent,
+            const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >& _rxORB );
+
+        /** if you use this ctor, the dialog
+            <ul><li>will not store it's data in the configuration (nor initially retrieve it from there)</li>
+                <li>will not allow to change the data source name</li>
+                <li>will not allow to change the table name</li>
+                <li>will not allow to call the data source administration dialog</li>
+            </ul>
+
+            @param _rxORB
+                a service factory to use for various UNO related needs
+            @param _rxTransientDS
+                the data source to obtain connections from
+            @param _rDataSourceName
+                the to-be name of _rxTransientDS. This is only for displaying this
+                name to the user, since the dialog completely works on _rxTransientDS,
+                and doesn't allow to change this.
+            @param _rTable
+                the table name to display. It must refer to a valid table, relative to a connection
+                obtained from <arg>_rxTransientDS</arg>
+        */
+        AddressBookSourceDialog( Window* _pParent,
+            const ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory >& _rxORB,
+            const ::com::sun::star::uno::Reference< ::com::sun::star::sdbc::XDataSource >& _rxTransientDS,
+            const ::rtl::OUString& _rDataSourceName,
+            const ::rtl::OUString& _rTable,
+            const ::com::sun::star::uno::Sequence< ::com::sun::star::util::AliasProgrammaticPair >& _rMapping
+        );
+
+        ~AddressBookSourceDialog();
+
+        // to be used if the object was constructed for editing a field mapping only
+        void        getFieldMapping(
+            ::com::sun::star::uno::Sequence< ::com::sun::star::util::AliasProgrammaticPair >& _rMapping) const;
+
+    protected:
+        void    implConstruct();
+
+        // Window overridables
+        virtual long        PreNotify( NotifyEvent& _rNEvt );
+
+        // implementations
+        void    implScrollFields(sal_Int32 _nPos, sal_Bool _bAdjustFocus, sal_Bool _bAdjustScrollbar);
+        void    implSelectField(ListBox* _pBox, const String& _rText);
+
+        void    initalizeListBox(ListBox* _pList);
+        void    resetTables();
+        void    resetFields();
+
+        // fill in the data sources listbox
+        void    initializeDatasources();
+
+        // initialize the dialog from the configuration data
+        void    loadConfiguration();
+
+        DECL_LINK(OnFieldScroll, ScrollBar*);
+        DECL_LINK(OnFieldSelect, ListBox*);
+        DECL_LINK(OnAdministrateDatasources, void*);
+        DECL_LINK(OnComboGetFocus, ComboBox*);
+        DECL_LINK(OnComboLoseFocus, ComboBox*);
+        DECL_LINK(OnComboSelect, ComboBox*);
+        DECL_LINK(OnOkClicked, void*);
+        DECL_LINK(OnDelayedInitialize, void*);
+    };
+
+
+// .......................................................................
+}   // namespace svt
+// .......................................................................
+
+#endif // _SVT_ADDRESSTEMPLATE_HXX_
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/svtools/inc/svtools/svtools.hrc b/svtools/inc/svtools/svtools.hrc
index 11a3592..01ee8a8 100644
--- a/svtools/inc/svtools/svtools.hrc
+++ b/svtools/inc/svtools/svtools.hrc
@@ -219,6 +219,7 @@
 // dialogs
 
 #define DLG_LOGIN                       (RID_SVTOOLS_START+113)
+#define DLG_ADDRESSBOOKSOURCE           (RID_SVTOOLS_START+114)
 
 //.............................................................................
 // bitmaps
diff --git a/svtools/source/dialogs/addresstemplate.cxx b/svtools/source/dialogs/addresstemplate.cxx
new file mode 100644
index 0000000..2106538
--- /dev/null
+++ b/svtools/source/dialogs/addresstemplate.cxx
@@ -0,0 +1,1327 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+
+#include <stdio.h>
+#include <svtools/addresstemplate.hxx>
+#include "addresstemplate.hrc"
+#include <svtools/svtools.hrc>
+#include <svtools/helpid.hrc>
+#include <svtools/svtresid.hxx>
+#include <tools/debug.hxx>
+#include <comphelper/extract.hxx>
+#include <comphelper/interaction.hxx>
+#include <comphelper/processfactory.hxx>
+#include <comphelper/stl_types.hxx>
+#include <comphelper/string.hxx>
+#include <vcl/stdtext.hxx>
+#include <vcl/waitobj.hxx>
+#include <vcl/msgbox.hxx>
+#include <toolkit/helper/vclunohelper.hxx>
+#include <com/sun/star/ui/dialogs/XExecutableDialog.hpp>
+#include <com/sun/star/awt/XWindow.hpp>
+#include <com/sun/star/beans/PropertyValue.hpp>
+#include <com/sun/star/beans/XPropertySet.hpp>
+#include <com/sun/star/sdb/DatabaseContext.hpp>
+#include <com/sun/star/sdb/XCompletedConnection.hpp>
+#include <com/sun/star/sdb/SQLContext.hpp>
+#include <com/sun/star/sdbc/SQLWarning.hpp>
+#include <com/sun/star/sdbc/XConnection.hpp>
+#include <com/sun/star/task/InteractionHandler.hpp>
+#include <com/sun/star/sdbcx/XTablesSupplier.hpp>
+#include <com/sun/star/sdbcx/XColumnsSupplier.hpp>
+#include <com/sun/star/sdb/CommandType.hpp>
+#include <svtools/localresaccess.hxx>
+#include "svl/filenotation.hxx"
+#include <tools/urlobj.hxx>
+#include <algorithm>
+
+// .......................................................................
+namespace svt
+{
+// .......................................................................
+
+    using namespace ::com::sun::star::uno;
+    using namespace ::com::sun::star::lang;
+    using namespace ::com::sun::star::container;
+    using namespace ::com::sun::star::ui::dialogs;
+    using namespace ::com::sun::star::util;
+    using namespace ::com::sun::star::beans;
+    using namespace ::com::sun::star::sdb;
+    using namespace ::com::sun::star::sdbc;
+    using namespace ::com::sun::star::sdbcx;
+    using namespace ::com::sun::star::task;
+    using namespace ::comphelper;
+    using namespace ::utl;
+
+    DECLARE_STL_VECTOR( String, StringArray );
+    DECLARE_STL_STDKEY_SET( ::rtl::OUString, StringBag );
+    DECLARE_STL_USTRINGACCESS_MAP( ::rtl::OUString, MapString2String );
+
+    namespace
+    {
+        String lcl_getSelectedDataSource( const ComboBox& _dataSourceCombo )
+        {
+            String selectedDataSource = _dataSourceCombo.GetText();
+            if ( _dataSourceCombo.GetEntryPos( selectedDataSource ) == LISTBOX_ENTRY_NOTFOUND )
+            {
+                // none of the pre-selected entries -> assume a path to a database document
+                OFileNotation aFileNotation( selectedDataSource, OFileNotation::N_SYSTEM );
+                selectedDataSource = aFileNotation.get( OFileNotation::N_URL );
+            }
+            return selectedDataSource;
+        }
+    }
+
+    // ===================================================================
+    // = IAssigmentData
+    // ===================================================================
+    class IAssigmentData
+    {
+    public:
+        virtual ~IAssigmentData();
+
+        /// the data source to use for the address book
+        virtual ::rtl::OUString getDatasourceName() const = 0;
+
+        /// the command to use for the address book
+        virtual ::rtl::OUString getCommand() const = 0;
+
+        /** the command type to use for the address book
+            @return
+                a <type scope="com.sun.star.sdb">CommandType</type> value
+        */
+        virtual sal_Int32       getCommandType() const = 0;
+
+        /// checks whether or not there is an assignment for a given logical field
+        virtual sal_Bool        hasFieldAssignment(const ::rtl::OUString& _rLogicalName) = 0;
+        /// retrieves the assignment for a given logical field
+        virtual ::rtl::OUString getFieldAssignment(const ::rtl::OUString& _rLogicalName) = 0;
+
+        /// set the assignment for a given logical field
+        virtual void            setFieldAssignment(const ::rtl::OUString& _rLogicalName, const ::rtl::OUString& _rAssignment) = 0;
+        /// clear the assignment for a given logical field
+        virtual void            clearFieldAssignment(const ::rtl::OUString& _rLogicalName) = 0;
+
+        virtual void    setDatasourceName(const ::rtl::OUString& _rName) = 0;
+        virtual void    setCommand(const ::rtl::OUString& _rCommand) = 0;
+    };
+
+    // -------------------------------------------------------------------
+    IAssigmentData::~IAssigmentData()
+    {
+    }
+
+    // ===================================================================
+    // = AssigmentTransientData
+    // ===================================================================
+    class AssigmentTransientData : public IAssigmentData
+    {
+    protected:
+        Reference< XDataSource >    m_xDataSource;
+        ::rtl::OUString             m_sDSName;
+        ::rtl::OUString             m_sTableName;
+        MapString2String            m_aAliases;
+
+public:
+        AssigmentTransientData(
+            const Reference< XDataSource >& _rxDataSource,
+            const ::rtl::OUString& _rDataSourceName,
+            const ::rtl::OUString& _rTableName,
+            const Sequence< AliasProgrammaticPair >& _rFields
+        );
+
+        // IAssigmentData overridables
+        virtual ::rtl::OUString getDatasourceName() const;
+        virtual ::rtl::OUString getCommand() const;
+        virtual sal_Int32       getCommandType() const;
+
+        virtual sal_Bool        hasFieldAssignment(const ::rtl::OUString& _rLogicalName);
+        virtual ::rtl::OUString getFieldAssignment(const ::rtl::OUString& _rLogicalName);
+        virtual void            setFieldAssignment(const ::rtl::OUString& _rLogicalName, const ::rtl::OUString& _rAssignment);
+        virtual void            clearFieldAssignment(const ::rtl::OUString& _rLogicalName);
+
+        virtual void    setDatasourceName(const ::rtl::OUString& _rName);
+        virtual void    setCommand(const ::rtl::OUString& _rCommand);
+    };
+
+    // -------------------------------------------------------------------
+    AssigmentTransientData::AssigmentTransientData( const Reference< XDataSource >& _rxDataSource,
+            const ::rtl::OUString& _rDataSourceName, const ::rtl::OUString& _rTableName,
+            const Sequence< AliasProgrammaticPair >& _rFields )
+        :m_xDataSource( _rxDataSource )
+        ,m_sDSName( _rDataSourceName )
+        ,m_sTableName( _rTableName )
+    {
+        // fill our aliaes structure
+        // first collect all known programmatic names
+        StringBag aKnownNames;
+
+        rtl::OUString sLogicalFieldNames(SVT_RESSTR(STR_LOGICAL_FIELD_NAMES));
+        sal_Int32 nIndex = 0;
+        do
+        {
+            rtl::OUString aToken = sLogicalFieldNames.getToken(0, ';', nIndex);
+            aKnownNames.insert(aToken);
+        }
+        while ( nIndex >= 0);
+
+        // loop throuzh the given names
+        const AliasProgrammaticPair* pFields = _rFields.getConstArray();
+        const AliasProgrammaticPair* pFieldsEnd = pFields + _rFields.getLength();
+        for (;pFields != pFieldsEnd; ++pFields)
+        {
+            StringBagIterator aKnownPos = aKnownNames.find( pFields->ProgrammaticName );
+            if ( aKnownNames.end() != aKnownPos )
+            {
+                m_aAliases[ pFields->ProgrammaticName ] = pFields->Alias;
+            }
+            else
+            {
+                OSL_FAIL(   (   ::rtl::OString("AssigmentTransientData::AssigmentTransientData: unknown programmatic name (")
+                                +=  ::rtl::OString(pFields->ProgrammaticName.getStr(), pFields->ProgrammaticName.getLength(), RTL_TEXTENCODING_ASCII_US)
+                                +=  ::rtl::OString(")!")
+                                ).getStr()
+                            );
+            }
+        }
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssigmentTransientData::getDatasourceName() const
+    {
+        return m_sDSName;
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssigmentTransientData::getCommand() const
+    {
+        return m_sTableName;
+    }
+
+    // -------------------------------------------------------------------
+    sal_Int32 AssigmentTransientData::getCommandType() const
+    {
+        return CommandType::TABLE;
+    }
+
+    // -------------------------------------------------------------------
+    sal_Bool AssigmentTransientData::hasFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        ConstMapString2StringIterator aPos = m_aAliases.find( _rLogicalName );
+        return  ( m_aAliases.end() != aPos )
+            &&  ( !aPos->second.isEmpty() );
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssigmentTransientData::getFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        ::rtl::OUString sReturn;
+        ConstMapString2StringIterator aPos = m_aAliases.find( _rLogicalName );
+        if ( m_aAliases.end() != aPos )
+            sReturn = aPos->second;
+
+        return sReturn;
+    }
+
+    // -------------------------------------------------------------------
+    void AssigmentTransientData::setFieldAssignment(const ::rtl::OUString& _rLogicalName, const ::rtl::OUString& _rAssignment)
+    {
+        m_aAliases[ _rLogicalName ] = _rAssignment;
+    }
+
+    // -------------------------------------------------------------------
+    void AssigmentTransientData::clearFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        MapString2StringIterator aPos = m_aAliases.find( _rLogicalName );
+        if ( m_aAliases.end() != aPos )
+            m_aAliases.erase( aPos );
+    }
+
+    // -------------------------------------------------------------------
+    void AssigmentTransientData::setDatasourceName(const ::rtl::OUString&)
+    {
+        OSL_FAIL( "AssigmentTransientData::setDatasourceName: cannot be implemented for transient data!" );
+    }
+
+    // -------------------------------------------------------------------
+    void AssigmentTransientData::setCommand(const ::rtl::OUString&)
+    {
+        OSL_FAIL( "AssigmentTransientData::setCommand: cannot be implemented for transient data!" );
+    }
+
+    // ===================================================================
+    // = AssignmentPersistentData
+    // ===================================================================
+    class AssignmentPersistentData
+            :public ::utl::ConfigItem
+            ,public IAssigmentData
+    {
+    protected:
+        StringBag       m_aStoredFields;
+
+    protected:
+        ::com::sun::star::uno::Any
+                        getProperty(const ::rtl::OUString& _rLocalName) const;
+        ::com::sun::star::uno::Any
+                        getProperty(const sal_Char* _pLocalName) const;
+
+        ::rtl::OUString getStringProperty(const sal_Char* _pLocalName) const;
+        sal_Int32       getInt32Property(const sal_Char* _pLocalName) const;
+
+        ::rtl::OUString getStringProperty(const ::rtl::OUString& _rLocalName) const;
+
+        void            setStringProperty(const sal_Char* _pLocalName, const ::rtl::OUString& _rValue);
+
+    public:
+        AssignmentPersistentData();
+        ~AssignmentPersistentData();
+
+        // IAssigmentData overridables
+        virtual ::rtl::OUString getDatasourceName() const;
+        virtual ::rtl::OUString getCommand() const;
+        virtual sal_Int32       getCommandType() const;
+
+        virtual sal_Bool        hasFieldAssignment(const ::rtl::OUString& _rLogicalName);
+        virtual ::rtl::OUString getFieldAssignment(const ::rtl::OUString& _rLogicalName);
+        virtual void            setFieldAssignment(const ::rtl::OUString& _rLogicalName, const ::rtl::OUString& _rAssignment);
+        virtual void            clearFieldAssignment(const ::rtl::OUString& _rLogicalName);
+
+        virtual void    setDatasourceName(const ::rtl::OUString& _rName);
+        virtual void    setCommand(const ::rtl::OUString& _rCommand);
+
+        virtual void    Notify( const com::sun::star::uno::Sequence<rtl::OUString>& aPropertyNames);
+        virtual void    Commit();
+    };
+
+
+void AssignmentPersistentData::Notify( const com::sun::star::uno::Sequence<rtl::OUString>& )
+{
+}
+
+void AssignmentPersistentData::Commit()
+{
+}
+
+    // -------------------------------------------------------------------
+    AssignmentPersistentData::AssignmentPersistentData()
+        :ConfigItem( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Office.DataAccess/AddressBook" )))
+    {
+        Sequence< ::rtl::OUString > aStoredNames = GetNodeNames(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Fields")));
+        const ::rtl::OUString* pStoredNames = aStoredNames.getConstArray();
+        for (sal_Int32 i=0; i<aStoredNames.getLength(); ++i, ++pStoredNames)
+            m_aStoredFields.insert(*pStoredNames);
+    }
+
+    // -------------------------------------------------------------------
+    AssignmentPersistentData::~AssignmentPersistentData()
+    {
+    }
+
+    // -------------------------------------------------------------------
+    sal_Bool AssignmentPersistentData::hasFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        return (m_aStoredFields.end() != m_aStoredFields.find(_rLogicalName));
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssignmentPersistentData::getFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        ::rtl::OUString sAssignment;
+        if (hasFieldAssignment(_rLogicalName))
+        {
+            ::rtl::OUString sFieldPath(RTL_CONSTASCII_USTRINGPARAM("Fields/"));
+            sFieldPath += _rLogicalName;
+            sFieldPath += ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/AssignedFieldName"));
+            sAssignment = getStringProperty(sFieldPath);
+        }
+        return sAssignment;
+    }
+
+    // -------------------------------------------------------------------
+    Any AssignmentPersistentData::getProperty(const sal_Char* _pLocalName) const
+    {
+        return getProperty(::rtl::OUString::createFromAscii(_pLocalName));
+    }
+
+    // -------------------------------------------------------------------
+    Any AssignmentPersistentData::getProperty(const ::rtl::OUString& _rLocalName) const
+    {
+        Sequence< ::rtl::OUString > aProperties(&_rLocalName, 1);
+        Sequence< Any > aValues = const_cast<AssignmentPersistentData*>(this)->GetProperties(aProperties);
+        DBG_ASSERT(aValues.getLength() == 1, "AssignmentPersistentData::getProperty: invalid sequence length!");
+        return aValues[0];
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssignmentPersistentData::getStringProperty(const ::rtl::OUString& _rLocalName) const
+    {
+        ::rtl::OUString sReturn;
+        getProperty( _rLocalName ) >>= sReturn;
+        return sReturn;
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssignmentPersistentData::getStringProperty(const sal_Char* _pLocalName) const
+    {
+        ::rtl::OUString sReturn;
+        getProperty( _pLocalName ) >>= sReturn;
+        return sReturn;
+    }
+
+    // -------------------------------------------------------------------
+    sal_Int32 AssignmentPersistentData::getInt32Property(const sal_Char* _pLocalName) const
+    {
+        sal_Int32 nReturn = 0;
+        getProperty( _pLocalName ) >>= nReturn;
+        return nReturn;
+    }
+
+    // -------------------------------------------------------------------
+    void AssignmentPersistentData::setStringProperty(const sal_Char* _pLocalName, const ::rtl::OUString& _rValue)
+    {
+        Sequence< ::rtl::OUString > aNames(1);
+        Sequence< Any > aValues(1);
+        aNames[0] = ::rtl::OUString::createFromAscii(_pLocalName);
+        aValues[0] <<= _rValue;
+        PutProperties(aNames, aValues);
+    }
+
+    // -------------------------------------------------------------------
+    void AssignmentPersistentData::setFieldAssignment(const ::rtl::OUString& _rLogicalName, const ::rtl::OUString& _rAssignment)
+    {
+        if (_rAssignment.isEmpty())
+        {
+            if (hasFieldAssignment(_rLogicalName))
+                // the assignment exists but it should be reset
+                clearFieldAssignment(_rLogicalName);
+                return;
+        }
+
+        // Fields
+        ::rtl::OUString sDescriptionNodePath(RTL_CONSTASCII_USTRINGPARAM("Fields"));
+
+        // Fields/<field>
+        ::rtl::OUString sFieldElementNodePath(sDescriptionNodePath);
+        sFieldElementNodePath += ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/"));
+        sFieldElementNodePath += _rLogicalName;
+
+        Sequence< PropertyValue > aNewFieldDescription(2);
+        // Fields/<field>/ProgrammaticFieldName
+        aNewFieldDescription[0].Name = sFieldElementNodePath;
+        aNewFieldDescription[0].Name += ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/ProgrammaticFieldName"));
+        aNewFieldDescription[0].Value <<= _rLogicalName;
+        // Fields/<field>/AssignedFieldName
+        aNewFieldDescription[1].Name = sFieldElementNodePath;
+        aNewFieldDescription[1].Name += ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("/AssignedFieldName"));
+        aNewFieldDescription[1].Value <<= _rAssignment;
+
+        // just set the new value
+#ifdef DBG_UTIL
+        sal_Bool bSuccess =
+#endif
+        SetSetProperties(sDescriptionNodePath, aNewFieldDescription);
+        DBG_ASSERT(bSuccess, "AssignmentPersistentData::setFieldAssignment: could not commit the changes a field!");
+    }
+
+    // -------------------------------------------------------------------
+    void AssignmentPersistentData::clearFieldAssignment(const ::rtl::OUString& _rLogicalName)
+    {
+        if (!hasFieldAssignment(_rLogicalName))
+            // nothing to do
+            return;
+
+        ::rtl::OUString sDescriptionNodePath(RTL_CONSTASCII_USTRINGPARAM("Fields"));
+        Sequence< ::rtl::OUString > aNames(&_rLogicalName, 1);
+        ClearNodeElements(sDescriptionNodePath, aNames);
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssignmentPersistentData::getDatasourceName() const
+    {
+        return getStringProperty( "DataSourceName" );
+    }
+
+    // -------------------------------------------------------------------
+    ::rtl::OUString AssignmentPersistentData::getCommand() const
+    {
+        return getStringProperty( "Command" );
+    }
+
+    // -------------------------------------------------------------------
+    void AssignmentPersistentData::setDatasourceName(const ::rtl::OUString& _rName)
+    {
+        setStringProperty( "DataSourceName", _rName );
+    }
+
+    // -------------------------------------------------------------------
+    void AssignmentPersistentData::setCommand(const ::rtl::OUString& _rCommand)
+    {
+        setStringProperty( "Command", _rCommand );
+    }
+
+    // -------------------------------------------------------------------
+    sal_Int32 AssignmentPersistentData::getCommandType() const
+    {
+        return getInt32Property( "CommandType" );
+    }
+
+    // ===================================================================
+    // = AddressBookSourceDialogData
+    // ===================================================================
+    struct AddressBookSourceDialogData
+    {
+        FixedText*      pFieldLabels[FIELD_PAIRS_VISIBLE * 2];
+        ListBox*        pFields[FIELD_PAIRS_VISIBLE * 2];
+
+        /// when working transient, we need the data source
+        Reference< XDataSource >
+                        m_xTransientDataSource;
+        /// current scroll pos in the field list
+        sal_Int32       nFieldScrollPos;
+        /// the index within m_pFields of the last visible list box. This is redundant, it could be extracted from other members
+        sal_Int32       nLastVisibleListIndex;
+        /// indicates that we've an odd field number. This member is for efficiency only, it's redundant.
+        sal_Bool        bOddFieldNumber : 1;
+        /// indicates that we're working with the real persistent configuration
+        sal_Bool        bWorkingPersistent : 1;
+
+        /// the strings to use as labels for the field selection listboxes
+        StringArray     aFieldLabels;
+        // the current field assignment
+        StringArray     aFieldAssignments;
+        /// the logical field names
+        StringArray     aLogicalFieldNames;
+
+        IAssigmentData* pConfigData;
+
+        // ................................................................
+        AddressBookSourceDialogData( )
+            :nFieldScrollPos(0)
+            ,nLastVisibleListIndex(0)
+            ,bOddFieldNumber(sal_False)
+            ,bWorkingPersistent( sal_True )
+            ,pConfigData( new AssignmentPersistentData )
+        {
+        }
+
+        // ................................................................
+        AddressBookSourceDialogData( const Reference< XDataSource >& _rxTransientDS, const ::rtl::OUString& _rDataSourceName,
+            const ::rtl::OUString& _rTableName, const Sequence< AliasProgrammaticPair >& _rFields )
+            :m_xTransientDataSource( _rxTransientDS )
+            ,nFieldScrollPos(0)
+            ,nLastVisibleListIndex(0)
+            ,bOddFieldNumber(sal_False)
+            ,bWorkingPersistent( sal_False )
+            ,pConfigData( new AssigmentTransientData( m_xTransientDataSource, _rDataSourceName, _rTableName, _rFields ) )
+        {
+        }
+
+        ~AddressBookSourceDialogData()
+        {
+            delete pConfigData;
+        }
+
+    };
+
+    // ===================================================================
+    // = AddressBookSourceDialog
+    // ===================================================================
+#define INIT_FIELDS()   \
+         ModalDialog(_pParent, SvtResId( DLG_ADDRESSBOOKSOURCE ))\
+        ,m_aDatasourceFrame         (this, SvtResId(FL_DATASOURCEFRAME))\
+        ,m_aDatasourceLabel         (this, SvtResId(FT_DATASOURCE))\
+        ,m_aDatasource              (this, SvtResId(CB_DATASOURCE))\
+        ,m_aAdministrateDatasources (this, SvtResId(PB_ADMINISTATE_DATASOURCES))\
+        ,m_aTableLabel              (this, SvtResId(FT_TABLE))\
+        ,m_aTable                   (this, SvtResId(CB_TABLE))\
+        ,m_aFieldsTitle             (this, SvtResId(FT_FIELDS))\
+        ,m_aFieldsFrame             (this, SvtResId(CT_BORDER))\
+        ,m_aFieldScroller           (&m_aFieldsFrame, SvtResId(SB_FIELDSCROLLER))\
+        ,m_aOK                      (this, SvtResId(PB_OK))\
+        ,m_aCancel                  (this, SvtResId(PB_CANCEL))\
+        ,m_aHelp                    (this, SvtResId(PB_HELP))\
+        ,m_sNoFieldSelection(SVT_RESSTR(STR_NO_FIELD_SELECTION))\
+        ,m_xORB(_rxORB)
+
+    // -------------------------------------------------------------------
+    AddressBookSourceDialog::AddressBookSourceDialog(Window* _pParent,
+            const Reference< XMultiServiceFactory >& _rxORB )
+        :INIT_FIELDS()
+        ,m_pImpl( new AddressBookSourceDialogData )
+    {
+        implConstruct();
+    }
+
+    // -------------------------------------------------------------------
+    AddressBookSourceDialog::AddressBookSourceDialog( Window* _pParent, const Reference< XMultiServiceFactory >& _rxORB,
+        const Reference< XDataSource >& _rxTransientDS, const ::rtl::OUString& _rDataSourceName,
+        const ::rtl::OUString& _rTable, const Sequence< AliasProgrammaticPair >& _rMapping )
+        :INIT_FIELDS()
+        ,m_pImpl( new AddressBookSourceDialogData( _rxTransientDS, _rDataSourceName, _rTable, _rMapping ) )
+    {
+        implConstruct();
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::implConstruct()
+    {
+        for (sal_Int32 row=0; row<FIELD_PAIRS_VISIBLE; ++row)
+        {
+            for (sal_Int32 column=0; column<2; ++column)
+            {
+                // the label
+                m_pImpl->pFieldLabels[row * 2 + column] = new FixedText(&m_aFieldsFrame, SvtResId((sal_uInt16)(FT_FIELD_BASE + row * 2 + column)));
+                // the listbox
+                m_pImpl->pFields[row * 2 + column] = new ListBox(&m_aFieldsFrame, SvtResId((sal_uInt16)(LB_FIELD_BASE + row * 2 + column)));
+                m_pImpl->pFields[row * 2 + column]->SetDropDownLineCount(15);
+                m_pImpl->pFields[row * 2 + column]->SetSelectHdl(LINK(this, AddressBookSourceDialog, OnFieldSelect));
+
+                m_pImpl->pFields[row * 2 + column]->SetHelpId(HID_ADDRTEMPL_FIELD_ASSIGNMENT);
+            }
+        }
+
+        m_aFieldsFrame.SetStyle((m_aFieldsFrame.GetStyle() | WB_TABSTOP | WB_DIALOGCONTROL) & ~WB_NODIALOGCONTROL);
+
+        // correct the z-order
+        m_aFieldScroller.SetZOrder(m_pImpl->pFields[FIELD_CONTROLS_VISIBLE - 1], WINDOW_ZORDER_BEHIND);
+        m_aOK.SetZOrder(&m_aFieldsFrame, WINDOW_ZORDER_BEHIND);
+        m_aCancel.SetZOrder(&m_aOK, WINDOW_ZORDER_BEHIND);
+
+        initializeDatasources();
+
+        // for the moment, we have a hard coded list of all known fields.
+        // A better solution would be to store all known field translations in the configuration, which could be
+        // extensible by the user in an arbitrary way.
+        // But for the moment we need a quick solution ...
+        // (the main thing would be to store the translations to use here in the user interface, besides that, the code
+        // should be adjustable with a rather small effort.)
+
+        // initialize the strings for the field labels
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_FIRSTNAME ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_LASTNAME ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_COMPANY));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_DEPARTMENT ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_STREET ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_ZIPCODE ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_CITY ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_STATE));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_COUNTRY ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_HOMETEL ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_WORKTEL ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_OFFICETEL));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_MOBILE));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_TELOTHER));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_PAGER));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_FAX ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_EMAIL ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_URL ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_TITLE ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_POSITION ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_INITIALS ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_ADDRFORM ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_SALUTATION ));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_ID));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_CALENDAR));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_INVITE));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_NOTE));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_USER1));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_USER2));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_USER3));
+        m_pImpl->aFieldLabels.push_back( SVT_RESSTR( STR_FIELD_USER4));
+
+        // force a even number of known fields
+        m_pImpl->bOddFieldNumber = (m_pImpl->aFieldLabels.size() % 2) != 0;
+        if (m_pImpl->bOddFieldNumber)
+            m_pImpl->aFieldLabels.push_back( String() );
+
+        // limit the scrollbar range accordingly
+        sal_Int32 nOverallFieldPairs = m_pImpl->aFieldLabels.size() / 2;
+        m_aFieldScroller.SetRange( Range(0, nOverallFieldPairs - FIELD_PAIRS_VISIBLE) );
+        m_aFieldScroller.SetLineSize(1);
+        m_aFieldScroller.SetPageSize(FIELD_PAIRS_VISIBLE);
+
+        // reset the current field assignments
+        m_pImpl->aFieldAssignments.resize(m_pImpl->aFieldLabels.size());
+            // (empty strings mean "no assignment")
+
+        // some knittings
+        m_aFieldScroller.SetScrollHdl(LINK(this, AddressBookSourceDialog, OnFieldScroll));
+        m_aAdministrateDatasources.SetClickHdl(LINK(this, AddressBookSourceDialog, OnAdministrateDatasources));
+        m_aDatasource.EnableAutocomplete(sal_True);
+        m_aTable.EnableAutocomplete(sal_True);
+        m_aTable.SetGetFocusHdl(LINK(this, AddressBookSourceDialog, OnComboGetFocus));
+        m_aDatasource.SetGetFocusHdl(LINK(this, AddressBookSourceDialog, OnComboGetFocus));
+        m_aTable.SetLoseFocusHdl(LINK(this, AddressBookSourceDialog, OnComboLoseFocus));
+        m_aDatasource.SetLoseFocusHdl(LINK(this, AddressBookSourceDialog, OnComboLoseFocus));
+        m_aTable.SetSelectHdl(LINK(this, AddressBookSourceDialog, OnComboSelect));
+        m_aDatasource.SetSelectHdl(LINK(this, AddressBookSourceDialog, OnComboSelect));
+        m_aOK.SetClickHdl(LINK(this, AddressBookSourceDialog, OnOkClicked));
+
+        m_aDatasource.SetDropDownLineCount(15);
+
+        // initialize the field controls
+        resetFields();
+        m_aFieldScroller.SetThumbPos(0);
+        m_pImpl->nFieldScrollPos = -1;
+        implScrollFields(0, sal_False, sal_False);
+
+        // the logical names
+        rtl::OUString sLogicalFieldNames(SVT_RESSTR(STR_LOGICAL_FIELD_NAMES));
+        sal_Int32 nAdjustedTokenCount = comphelper::string::getTokenCount(sLogicalFieldNames, ';') + (m_pImpl->bOddFieldNumber ? 1 : 0);
+        DBG_ASSERT(nAdjustedTokenCount == (sal_Int32)m_pImpl->aFieldLabels.size(),
+            "AddressBookSourceDialog::AddressBookSourceDialog: inconsistence between logical and UI field names!");
+        m_pImpl->aLogicalFieldNames.reserve(nAdjustedTokenCount);
+        for (sal_Int32 i = 0; i<nAdjustedTokenCount; ++i)
+            m_pImpl->aLogicalFieldNames.push_back(comphelper::string::getToken(sLogicalFieldNames, i, ';'));
+
+        PostUserEvent(LINK(this, AddressBookSourceDialog, OnDelayedInitialize));
+            // so the dialog will at least show up before we do the loading of the
+            // configuration data and the (maybe time consuming) analysis of the data source/table to select
+
+        FreeResource();
+
+        if ( !m_pImpl->bWorkingPersistent )
+        {
+            StyleSettings aSystemStyle = GetSettings().GetStyleSettings();
+            const Color& rNewColor = aSystemStyle.GetDialogColor();
+
+            m_aDatasource.SetReadOnly( sal_True );
+            m_aDatasource.SetBackground( Wallpaper( rNewColor ) );
+            m_aDatasource.SetControlBackground( rNewColor );
+
+            m_aTable.SetReadOnly( sal_True );
+            m_aTable.SetBackground( Wallpaper( rNewColor ) );
+            m_aTable.SetControlBackground( rNewColor );
+
+            m_aAdministrateDatasources.Hide( );
+        }
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::getFieldMapping(Sequence< AliasProgrammaticPair >& _rMapping) const
+    {
+        _rMapping.realloc( m_pImpl->aLogicalFieldNames.size() );
+        AliasProgrammaticPair* pPair = _rMapping.getArray();
+
+        ::rtl::OUString sCurrent;
+        for (   ConstStringArrayIterator aProgrammatic = m_pImpl->aLogicalFieldNames.begin();
+                aProgrammatic != m_pImpl->aLogicalFieldNames.end();
+                ++aProgrammatic
+            )
+        {
+            sCurrent = *aProgrammatic;
+            if ( m_pImpl->pConfigData->hasFieldAssignment( sCurrent ) )
+            {
+                // the user gave us an assignment for this field
+                pPair->ProgrammaticName = *aProgrammatic;
+                pPair->Alias = m_pImpl->pConfigData->getFieldAssignment( *aProgrammatic );
+                ++pPair;
+            }
+        }
+
+        _rMapping.realloc( pPair - _rMapping.getArray() );
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::loadConfiguration()
+    {
+        ::rtl::OUString sName = m_pImpl->pConfigData->getDatasourceName();
+        INetURLObject aURL( sName );
+        if( aURL.GetProtocol() != INET_PROT_NOT_VALID )
+        {
+            OFileNotation aFileNotation( aURL.GetMainURL( INetURLObject::NO_DECODE ) );
+            sName = aFileNotation.get(OFileNotation::N_SYSTEM);
+        }
+
+        m_aDatasource.SetText(sName);
+        m_aTable.SetText(m_pImpl->pConfigData->getCommand());
+        // we ignore the CommandType: only tables are supported
+
+        // the logical names for the fields
+        DBG_ASSERT(m_pImpl->aLogicalFieldNames.size() == m_pImpl->aFieldAssignments.size(),
+            "AddressBookSourceDialog::loadConfiguration: inconsistence between field names and field assignments!");
+
+        ConstStringArrayIterator aLogical = m_pImpl->aLogicalFieldNames.begin();
+        StringArrayIterator aAssignment = m_pImpl->aFieldAssignments.begin();
+        for (   ;
+                aLogical < m_pImpl->aLogicalFieldNames.end();
+                ++aLogical, ++aAssignment
+            )
+            *aAssignment = m_pImpl->pConfigData->getFieldAssignment(*aLogical);
+    }
+
+    // -------------------------------------------------------------------
+    AddressBookSourceDialog::~AddressBookSourceDialog()
+    {
+        sal_Int32 i;
+        for (i=0; i<FIELD_CONTROLS_VISIBLE; ++i)
+        {
+            delete m_pImpl->pFieldLabels[i];
+            delete m_pImpl->pFields[i];
+        }
+
+        delete m_pImpl;
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::initializeDatasources()
+    {
+        if (!m_xDatabaseContext.is())
+        {
+            DBG_ASSERT(m_xORB.is(), "AddressBookSourceDialog::initializeDatasources: no service factory!");
+            if (!m_xORB.is())
+                return;
+
+            try
+            {
+                m_xDatabaseContext = DatabaseContext::create(comphelper::getComponentContext(m_xORB));
+            }
+            catch(Exception&) { }
+            if (!m_xDatabaseContext.is())
+            {
+                const rtl::OUString sContextServiceName("com.sun.star.sdb.DatabaseContext");
+                ShowServiceNotAvailableError( this, sContextServiceName, sal_False);
+                return;
+            }
+        }
+        m_aDatasource.Clear();
+
+        // fill the datasources listbox
+        Sequence< ::rtl::OUString > aDatasourceNames;
+        try
+        {
+            aDatasourceNames = m_xDatabaseContext->getElementNames();
+        }
+        catch(Exception&)
+        {
+            OSL_FAIL("AddressBookSourceDialog::initializeDatasources: caught an exception while asking for the data source names!");
+        }
+        const ::rtl::OUString* pDatasourceNames = aDatasourceNames.getConstArray();
+        const ::rtl::OUString* pEnd = pDatasourceNames + aDatasourceNames.getLength();
+        for (; pDatasourceNames < pEnd; ++pDatasourceNames)
+            m_aDatasource.InsertEntry(*pDatasourceNames);
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK(AddressBookSourceDialog, OnFieldScroll, ScrollBar*, _pScrollBar)
+    {
+        implScrollFields( _pScrollBar->GetThumbPos(), sal_True, sal_True );
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::resetTables()
+    {
+        if (!m_xDatabaseContext.is())
+            return;
+
+        WaitObject aWaitCursor(this);
+
+        // no matter what we do here, we handled the currently selected data source (no matter if successfull or not)
+        m_aDatasource.SaveValue();
+
+        // create an interaction handler (may be needed for connecting)
+        Reference< XInteractionHandler > xHandler;
+        try
+        {
+            xHandler.set(
+                InteractionHandler::createWithParent(comphelper::getComponentContext(m_xORB), 0),
+                UNO_QUERY_THROW );
+        }
+        catch(Exception&) { }
+        if (!xHandler.is())
+        {
+            const rtl::OUString sInteractionHandlerServiceName("com.sun.star.task.InteractionHandler");
+            ShowServiceNotAvailableError(this, sInteractionHandlerServiceName, sal_True);
+            return;
+        }
+
+        // the currently selected table
+        ::rtl::OUString sOldTable = m_aTable.GetText();
+
+        m_aTable.Clear();
+
+        m_xCurrentDatasourceTables= NULL;
+
+        // get the tables of the connection
+        Sequence< ::rtl::OUString > aTableNames;
+        Any aException;
+        try
+        {
+            Reference< XCompletedConnection > xDS;
+            if ( m_pImpl->bWorkingPersistent )
+            {
+                String sSelectedDS = lcl_getSelectedDataSource(  m_aDatasource );
+
+                // get the data source the user has chosen and let it build a connection
+                INetURLObject aURL( sSelectedDS );
+                if ( aURL.GetProtocol() != INET_PROT_NOT_VALID || m_xDatabaseContext->hasByName(sSelectedDS) )
+                    m_xDatabaseContext->getByName( sSelectedDS ) >>= xDS;
+            }
+            else
+            {
+                xDS = xDS.query( m_pImpl->m_xTransientDataSource );
+            }
+
+            // build the connection
+            Reference< XConnection > xConn;
+            if (xDS.is())
+                xConn = xDS->connectWithCompletion(xHandler);
+
+            // get the table names
+            Reference< XTablesSupplier > xSupplTables(xConn, UNO_QUERY);
+            if (xSupplTables.is())
+            {
+                m_xCurrentDatasourceTables = Reference< XNameAccess >(xSupplTables->getTables(), UNO_QUERY);
+                if (m_xCurrentDatasourceTables.is())
+                    aTableNames = m_xCurrentDatasourceTables->getElementNames();
+            }
+        }
+        catch(const SQLContext& e) { aException <<= e; }
+        catch(const SQLWarning& e) { aException <<= e; }
+        catch(const SQLException& e) { aException <<= e; }
+        catch(Exception&)
+        {
+            OSL_FAIL("AddressBookSourceDialog::resetTables: could not retrieve the table!");
+        }
+
+        if (aException.hasValue())
+        {
+            Reference< XInteractionRequest > xRequest = new OInteractionRequest(aException);
+            try
+            {
+                xHandler->handle(xRequest);
+            }
+            catch(Exception&) { }
+            return;
+        }
+
+        sal_Bool bKnowOldTable = sal_False;
+        // fill the table list
+        const ::rtl::OUString* pTableNames = aTableNames.getConstArray();
+        const ::rtl::OUString* pEnd = pTableNames + aTableNames.getLength();
+        for (;pTableNames != pEnd; ++pTableNames)
+        {
+            m_aTable.InsertEntry(*pTableNames);
+            if (0 == pTableNames->compareTo(sOldTable))
+                bKnowOldTable = sal_True;
+        }
+
+        // set the old table, if the new data source knows a table with this name, too. Else reset the tables edit field.
+        if (!bKnowOldTable)
+            sOldTable = ::rtl::OUString();
+        m_aTable.SetText(sOldTable);
+
+        resetFields();
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::resetFields()
+    {
+        WaitObject aWaitCursor(this);
+
+        // no matter what we do here, we handled the currently selected table (no matter if successfull or not)
+        m_aDatasource.SaveValue();
+
+        String sSelectedTable = m_aTable.GetText();
+        Sequence< ::rtl::OUString > aColumnNames;
+        try
+        {
+            if (m_xCurrentDatasourceTables.is())
+            {
+                // get the table and the columns
+                Reference< XColumnsSupplier > xSuppTableCols;
+                if (m_xCurrentDatasourceTables->hasByName(sSelectedTable))
+                    ::cppu::extractInterface(xSuppTableCols, m_xCurrentDatasourceTables->getByName(sSelectedTable));
+                Reference< XNameAccess > xColumns;
+                if (xSuppTableCols.is())
+                    xColumns = xSuppTableCols->getColumns();
+                if (xColumns.is())
+                    aColumnNames = xColumns->getElementNames();
+            }
+        }
+        catch(Exception&)
+        {
+            OSL_FAIL("AddressBookSourceDialog::resetFields: could not retrieve the table columns!");
+        }
+
+
+        const ::rtl::OUString* pColumnNames = aColumnNames.getConstArray();
+        const ::rtl::OUString* pEnd = pColumnNames + aColumnNames.getLength();
+
+        // for quicker access
+        ::std::set< String > aColumnNameSet;
+        for (pColumnNames = aColumnNames.getConstArray(); pColumnNames != pEnd; ++pColumnNames)
+            aColumnNameSet.insert(*pColumnNames);
+
+        std::vector<String>::iterator aInitialSelection = m_pImpl->aFieldAssignments.begin() + m_pImpl->nFieldScrollPos;
+
+        ListBox** pListbox = m_pImpl->pFields;
+        String sSaveSelection;
+        for (sal_Int32 i=0; i<FIELD_CONTROLS_VISIBLE; ++i, ++pListbox, ++aInitialSelection)
+        {
+            sSaveSelection = (*pListbox)->GetSelectEntry();
+
+            (*pListbox)->Clear();
+
+            // the one entry for "no selection"
+            (*pListbox)->InsertEntry(m_sNoFieldSelection, 0);
+            // as it's entry data, set the index of the list box in our array
+            (*pListbox)->SetEntryData(0, reinterpret_cast<void*>(i));
+
+            // the field names
+            for (pColumnNames = aColumnNames.getConstArray(); pColumnNames != pEnd; ++pColumnNames)
+                (*pListbox)->InsertEntry(*pColumnNames);
+
+            if (aInitialSelection->Len() && (aColumnNameSet.end() != aColumnNameSet.find(*aInitialSelection)))
+                // we can select the entry as specified in our field assignment array
+                (*pListbox)->SelectEntry(*aInitialSelection);
+            else
+                // try to restore the selection
+                if (aColumnNameSet.end() != aColumnNameSet.find(sSaveSelection))
+                    // the old selection is a valid column name
+                    (*pListbox)->SelectEntry(sSaveSelection);
+                else
+                    // select the <none> entry
+                    (*pListbox)->SelectEntryPos(0);
+        }
+
+        // adjust m_pImpl->aFieldAssignments
+        for (   StringArrayIterator aAdjust = m_pImpl->aFieldAssignments.begin();
+                aAdjust != m_pImpl->aFieldAssignments.end();
+                ++aAdjust
+            )
+            if (aAdjust->Len())
+                if (aColumnNameSet.end() == aColumnNameSet.find(*aAdjust))
+                    aAdjust->Erase();
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK(AddressBookSourceDialog, OnFieldSelect, ListBox*, _pListbox)
+    {
+        // the index of the affected list box in our array
+        sal_IntPtr nListBoxIndex = reinterpret_cast<sal_IntPtr>(_pListbox->GetEntryData(0));
+        DBG_ASSERT(nListBoxIndex >= 0 && nListBoxIndex < FIELD_CONTROLS_VISIBLE,
+            "AddressBookSourceDialog::OnFieldScroll: invalid list box entry!");
+
+        // update the array where we remember the field selections
+        if (0 == _pListbox->GetSelectEntryPos())
+            // it's the "no field selection" entry
+            m_pImpl->aFieldAssignments[m_pImpl->nFieldScrollPos * 2 + nListBoxIndex] = String();
+        else
+            // it's a regular field entry
+            m_pImpl->aFieldAssignments[m_pImpl->nFieldScrollPos * 2 + nListBoxIndex] = _pListbox->GetSelectEntry();
+
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::implScrollFields(sal_Int32 _nPos, sal_Bool _bAdjustFocus, sal_Bool _bAdjustScrollbar)
+    {
+        if (_nPos == m_pImpl->nFieldScrollPos)
+            // nothing to do
+            return;
+
+        // loop through our field control rows and do some adjustments
+        // for the new texts
+        FixedText** pLeftLabelControl = m_pImpl->pFieldLabels;
+        FixedText** pRightLabelControl = pLeftLabelControl + 1;
+        ConstStringArrayIterator pLeftColumnLabel = m_pImpl->aFieldLabels.begin() + 2 * _nPos;
+        ConstStringArrayIterator pRightColumnLabel = pLeftColumnLabel + 1;
+
+        // for the focus movement and the selection scroll
+        ListBox** pLeftListControl = m_pImpl->pFields;
+        ListBox** pRightListControl = pLeftListControl + 1;
+
+        // for the focus movement
+        sal_Int32 nOldFocusRow = -1;
+        sal_Int32 nOldFocusColumn = 0;
+
+        // for the selection scroll
+        ConstStringArrayIterator pLeftAssignment = m_pImpl->aFieldAssignments.begin() + 2 * _nPos;
+        ConstStringArrayIterator pRightAssignment = pLeftAssignment + 1;
+
+        m_pImpl->nLastVisibleListIndex = -1;
+        // loop
+        for (sal_Int32 i=0; i<FIELD_PAIRS_VISIBLE; ++i)
+        {
+            if ((*pLeftListControl)->HasChildPathFocus())
+            {
+                nOldFocusRow = i;
+                nOldFocusColumn = 0;
+            }
+            else if ((*pRightListControl)->HasChildPathFocus())
+            {
+                nOldFocusRow = i;
+                nOldFocusColumn = 1;
+            }
+
+            // the new texts of the label controls
+            (*pLeftLabelControl)->SetText(*pLeftColumnLabel);
+            (*pRightLabelControl)->SetText(*pRightColumnLabel);
+
+            // we may have to hide the controls in the right column, if we have no label text for it
+            // (which means we have an odd number of fields, though we forced our internal arrays to
+            // be even-sized for easier handling)
+            // (If sometimes we support an arbitrary number of field assignments, we would have to care for
+            // an invisible left hand side column, too. But right now, the left hand side controls are always
+            // visible)
+            sal_Bool bHideRightColumn = (0 == pRightColumnLabel->Len());
+            (*pRightLabelControl)->Show(!bHideRightColumn);
+            (*pRightListControl)->Show(!bHideRightColumn);
+            // the new selections of the listboxes
+            implSelectField(*pLeftListControl, *pLeftAssignment);
+            implSelectField(*pRightListControl, *pRightAssignment);
+
+            // the index of the last visible list box
+            ++m_pImpl->nLastVisibleListIndex;   // the left hand side box is always visible
+            if (!bHideRightColumn)
+                ++m_pImpl->nLastVisibleListIndex;
+
+            // increment ...
+            if ( i < FIELD_PAIRS_VISIBLE - 1 )
+            {   // (not in the very last round, here the +=2 could result in an invalid
+                // iterator position, which causes an abort in a non-product version
+                pLeftLabelControl += 2;
+                pRightLabelControl += 2;
+                pLeftColumnLabel += 2;
+                pRightColumnLabel += 2;
+
+                pLeftListControl += 2;
+                pRightListControl += 2;
+                pLeftAssignment += 2;
+                pRightAssignment += 2;
+            }
+        }
+
+        if (_bAdjustFocus && (nOldFocusRow >= 0))
+        {   // we have to adjust the focus and one of the list boxes has the focus
+            sal_Int32 nDelta = m_pImpl->nFieldScrollPos - _nPos;
+            // the new row for the focus
+            sal_Int32 nNewFocusRow = nOldFocusRow + nDelta;
+            // normalize
+            nNewFocusRow = std::min(nNewFocusRow, (sal_Int32)(FIELD_PAIRS_VISIBLE - 1), ::std::less< sal_Int32 >());
+            nNewFocusRow = std::max(nNewFocusRow, (sal_Int32)0, ::std::less< sal_Int32 >());
+            // set the new focus (in the same column)
+            m_pImpl->pFields[nNewFocusRow * 2 + nOldFocusColumn]->GrabFocus();
+        }
+
+        m_pImpl->nFieldScrollPos = _nPos;
+
+        if (_bAdjustScrollbar)
+            m_aFieldScroller.SetThumbPos(m_pImpl->nFieldScrollPos);
+    }
+
+    // -------------------------------------------------------------------
+    void AddressBookSourceDialog::implSelectField(ListBox* _pBox, const String& _rText)
+    {
+        if (_rText.Len())
+            // a valid field name
+            _pBox->SelectEntry(_rText);
+        else
+            // no selection for this item
+            _pBox->SelectEntryPos(0);
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK_NOARG(AddressBookSourceDialog, OnDelayedInitialize)
+    {
+        // load the initial data from the configuration
+        loadConfiguration();
+        resetTables();
+            // will reset the tables/fields implicitly
+
+        if ( !m_pImpl->bWorkingPersistent )
+            if ( m_pImpl->pFields[0] )
+                m_pImpl->pFields[0]->GrabFocus();
+
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK(AddressBookSourceDialog, OnComboSelect, ComboBox*, _pBox)
+    {
+        if (_pBox == &m_aDatasource)
+            resetTables();
+        else
+            resetFields();
+        return 0;
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK(AddressBookSourceDialog, OnComboGetFocus, ComboBox*, _pBox)
+    {
+        _pBox->SaveValue();
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK(AddressBookSourceDialog, OnComboLoseFocus, ComboBox*, _pBox)
+    {
+        if (_pBox->GetSavedValue() != _pBox->GetText())
+        {
+            if (_pBox == &m_aDatasource)
+                resetTables();
+            else
+                resetFields();
+        }
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK_NOARG(AddressBookSourceDialog, OnOkClicked)
+    {
+        String sSelectedDS = lcl_getSelectedDataSource(  m_aDatasource );
+        if ( m_pImpl->bWorkingPersistent )
+        {
+            m_pImpl->pConfigData->setDatasourceName(sSelectedDS);
+            m_pImpl->pConfigData->setCommand(m_aTable.GetText());
+        }
+
+        // set the field assignments
+        ConstStringArrayIterator aLogical = m_pImpl->aLogicalFieldNames.begin();
+        ConstStringArrayIterator aAssignment = m_pImpl->aFieldAssignments.begin();
+        for (   ;
+                aLogical < m_pImpl->aLogicalFieldNames.end();
+                ++aLogical, ++aAssignment
+            )
+            m_pImpl->pConfigData->setFieldAssignment(*aLogical, *aAssignment);
+
+
+        EndDialog(RET_OK);
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    IMPL_LINK_NOARG(AddressBookSourceDialog, OnAdministrateDatasources)
+    {
+        // collect some initial arguments for the dialog
+        Sequence< Any > aArgs(1);
+        aArgs[0] <<= PropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("ParentWindow")), 0, makeAny(VCLUnoHelper::GetInterface(this)), PropertyState_DIRECT_VALUE);
+
+        // create the dialog object
+        const rtl::OUString sDialogServiceName("com.sun.star.ui.dialogs.AddressBookSourcePilot");
+        Reference< XExecutableDialog > xAdminDialog;
+        try
+        {
+            xAdminDialog = Reference< XExecutableDialog >(m_xORB->createInstanceWithArguments(sDialogServiceName, aArgs), UNO_QUERY);
+        }
+        catch(Exception&) { }
+        if (!xAdminDialog.is())
+        {
+            ShowServiceNotAvailableError(this, sDialogServiceName, sal_True);
+            return 1L;
+        }
+
+        // excute the dialog
+        try
+        {
+            if ( xAdminDialog->execute() == RET_OK )
+            {
+                Reference<XPropertySet> xProp(xAdminDialog,UNO_QUERY);
+                if ( xProp.is() )
+                {
+                    ::rtl::OUString sName;
+                    xProp->getPropertyValue(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("DataSourceName"))) >>= sName;
+
+                    INetURLObject aURL( sName );
+                    if( aURL.GetProtocol() != INET_PROT_NOT_VALID )
+                    {
+                        OFileNotation aFileNotation( aURL.GetMainURL( INetURLObject::NO_DECODE ) );
+                        sName = aFileNotation.get(OFileNotation::N_SYSTEM);
+                    }
+                    m_aDatasource.InsertEntry(sName);
+                    delete m_pImpl->pConfigData;
+                    m_pImpl->pConfigData = new AssignmentPersistentData();
+                    loadConfiguration();
+                    resetTables();
+                    // will reset the fields implicitly
+                }
+            }
+        }
+        catch(Exception&)
+        {
+            OSL_FAIL("AddressBookSourceDialog::OnAdministrateDatasources: an error occurred while executing the administration dialog!");
+        }
+
+        // re-fill the data source list
+        // try to preserve the current selection
+
+//      initializeDatasources();
+
+        return 0L;
+    }
+
+    // -------------------------------------------------------------------
+    long AddressBookSourceDialog::PreNotify( NotifyEvent& _rNEvt )
+    {
+        switch (_rNEvt.GetType())
+        {
+            case EVENT_KEYINPUT:
+            {
+                const KeyEvent* pKeyEvent = _rNEvt.GetKeyEvent();
+                sal_uInt16 nCode  = pKeyEvent->GetKeyCode().GetCode();
+                sal_Bool   bShift = pKeyEvent->GetKeyCode().IsShift();
+                sal_Bool   bCtrl  = pKeyEvent->GetKeyCode().IsMod1();
+                sal_Bool   bAlt =   pKeyEvent->GetKeyCode().IsMod2();
+
+                if (KEY_TAB == nCode)
+                {   // somebody pressed the tab key
+                    if (!bAlt && !bCtrl && !bShift)
+                    {   // it's really the only the key (no modifiers)
+                        if (m_pImpl->pFields[m_pImpl->nLastVisibleListIndex]->HasChildPathFocus())
+                            // the last of our visible list boxes has the focus
+                            if (m_pImpl->nFieldScrollPos < m_aFieldScroller.GetRangeMax())
+                            {   // we can still scroll down
+                                sal_Int32 nNextFocusList = m_pImpl->nLastVisibleListIndex + 1 - 2;
+                                // -> scroll down
+                                implScrollFields(m_pImpl->nFieldScrollPos + 1, sal_False, sal_True);
+                                // give the left control in the "next" line the focus
+                                m_pImpl->pFields[nNextFocusList]->GrabFocus();
+                                // return saying "have handled this"
+                                return 1;
+                            }
+                    }
+                    else if (!bAlt && !bCtrl && bShift)
+                    {   // it's shift-tab
+                        if (m_pImpl->pFields[0]->HasChildPathFocus())
+                            // our first list box has the focus
+                            if (m_pImpl->nFieldScrollPos > 0)
+                            {   // we can still scroll up
+                                // -> scroll up
+                                implScrollFields(m_pImpl->nFieldScrollPos - 1, sal_False, sal_True);
+                                // give the right control in the "prebious" line the focus
+                                m_pImpl->pFields[0 - 1 + 2]->GrabFocus();
+                                // return saying "have handled this"
+                                return 1;
+                            }
+                    }
+                }
+            }
+            break;
+        }
+        return ModalDialog::PreNotify(_rNEvt);
+    }
+
+// .......................................................................
+}   // namespace svt
+// .......................................................................
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/svtools/source/dialogs/addresstemplate.src b/svtools/source/dialogs/addresstemplate.src
new file mode 100644
index 0000000..95dcea1
--- /dev/null
+++ b/svtools/source/dialogs/addresstemplate.src
@@ -0,0 +1,313 @@
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#include <svtools/svtools.hrc>
+#include "addresstemplate.hrc"
+#include <svtools/controldims.hrc>
+
+#define FIELD_ROW_HEIGHT    17
+
+ModalDialog DLG_ADDRESSBOOKSOURCE
+{
+    HelpID = "svtools:ModalDialog:DLG_ADDRESSBOOKSOURCE";
+    SVLook = TRUE ;
+    OutputSize = TRUE ;
+    Size = MAP_APPFONT ( 300 , 88 + FIELD_ROW_HEIGHT * FIELD_PAIRS_VISIBLE ) ;
+    Hide = TRUE ;
+    Moveable = TRUE ;
+    Text [ en-US ] = "Templates: Address Book Assignment";
+
+    FixedLine FL_DATASOURCEFRAME
+    {
+        Text [ en-US ] = "Address Book Source";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 6 , 2 ) ;
+        Size = MAP_APPFONT ( 288 , RSC_CD_FIXEDLINE_HEIGHT ) ;
+    };
+    FixedText FT_DATASOURCE
+    {
+        Text [ en-US ] = "Data source";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 12 , 15 ) ;
+        Size = MAP_APPFONT ( 90 , 10 ) ;
+
+        Group = TRUE;
+    };
+    ComboBox CB_DATASOURCE
+    {
+        HelpID = "svtools:ComboBox:DLG_ADDRESSBOOKSOURCE:CB_DATASOURCE";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 105, 13 ) ;
+        Size = MAP_APPFONT ( 96, 55 ) ;
+
+        DropDown = TRUE;
+        TabStop = TRUE;
+    };
+    PushButton PB_ADMINISTATE_DATASOURCES
+    {
+        HelpID = "svtools:PushButton:DLG_ADDRESSBOOKSOURCE:PB_ADMINISTATE_DATASOURCES";
+        Text [ en-US ] = "~Address Data Source...";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 204, 13 ) ;
+        Size = MAP_APPFONT ( 90, 14 ) ;
+        TabStop = TRUE;
+    };
+    FixedText FT_TABLE
+    {
+        Text [ en-US ] = "Table";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 12 , 32 ) ;
+        Size = MAP_APPFONT ( 90 , 10 ) ;
+
+        Group = TRUE;
+    };
+    ComboBox CB_TABLE
+    {
+        HelpID = "svtools:ComboBox:DLG_ADDRESSBOOKSOURCE:CB_TABLE";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 105, 30 ) ;
+        Size = MAP_APPFONT ( 96, 55 ) ;
+
+        DropDown = TRUE;
+        TabStop = TRUE;
+    };
+    FixedText FT_FIELDS
+    {
+        Text [ en-US ] = "Field assignment";
+        SVLook = TRUE ;
+        Pos = MAP_APPFONT ( 6, 30 + RSC_CD_DROPDOWN_HEIGHT + RSC_SP_CTRL_Y  ) ;
+        Size = MAP_APPFONT ( 248 , RSC_CD_FIXEDTEXT_HEIGHT ) ;
+    };
+    Window CT_BORDER
+    {
+        Border = TRUE ;
+        Pos = MAP_APPFONT ( 6, 30 + RSC_CD_DROPDOWN_HEIGHT + RSC_SP_CTRL_Y + RSC_CD_FIXEDTEXT_HEIGHT + RSC_SP_CTRL_DESC_Y ) ;
+        Size = MAP_APPFONT ( 288 , 5 + FIELD_ROW_HEIGHT * FIELD_PAIRS_VISIBLE ) ;
+    };
+
+#define DECLARE_FIELD( row, column )    \
+        FixedText FT_FIELD_BASE + row * 2 + column  \
+        {   \
+            SVLook = TRUE ; \
+            Pos = MAP_APPFONT ( 3 + column * 134, RSC_SP_CTRL_GROUP_Y + 2 + row * FIELD_ROW_HEIGHT ) ;   \
+            Size = MAP_APPFONT ( 79 , 10 ) ; \
+            Group = TRUE;   \
+        };  \
+        ListBox LB_FIELD_BASE + row * 2 + column    \
+        {   \
+            SVLook = TRUE;  \
+            Pos = MAP_APPFONT ( 89 + column * 134, RSC_SP_CTRL_GROUP_Y + row * FIELD_ROW_HEIGHT ) ;  \
+            Size = MAP_APPFONT ( 42 , 14 ) ;    \
+            Border = TRUE;  \
+            DropDown = TRUE;    \
+            TabStop = TRUE;  \
+        }
+
+#if FIELD_PAIRS_VISIBLE > 0
+    DECLARE_FIELD( 0, 0 );
+    DECLARE_FIELD( 0, 1 );
+#endif
+#if FIELD_PAIRS_VISIBLE > 1
+    DECLARE_FIELD( 1, 0 );
+    DECLARE_FIELD( 1, 1 );
+#endif
+#if FIELD_PAIRS_VISIBLE > 2
+    DECLARE_FIELD( 3, 0 );
+    DECLARE_FIELD( 3, 1 );
+#endif
+#if FIELD_PAIRS_VISIBLE > 3
+    DECLARE_FIELD( 2, 0 );
+    DECLARE_FIELD( 2, 1 );
+#endif
+#if FIELD_PAIRS_VISIBLE > 4
+    DECLARE_FIELD( 4, 0 );
+    DECLARE_FIELD( 4, 1 );
+#endif
+#if FIELD_PAIRS_VISIBLE > 5
+    DECLARE_FIELD( 5, 0 );
+    DECLARE_FIELD( 5, 1 );
+#endif
+
+    ScrollBar SB_FIELDSCROLLER
+    {
+        SVLook = TRUE;
+        Pos = MAP_APPFONT ( 275, RSC_SP_CTRL_GROUP_Y ) ;
+        Size = MAP_APPFONT ( 8 , 16 - RSC_SP_CTRL_GROUP_Y + FIELD_ROW_HEIGHT * (FIELD_PAIRS_VISIBLE - 1) ) ;
+    };
+
+    OKButton PB_OK
+    {
+        SVLook = TRUE;
+        DefButton = TRUE;
+        Pos = MAP_APPFONT ( 137, 70 + FIELD_ROW_HEIGHT * FIELD_PAIRS_VISIBLE ) ;
+        Size = MAP_APPFONT ( 50 , 14 ) ;
+    };
+
+    CancelButton PB_CANCEL
+    {
+        SVLook = TRUE;
+        Pos = MAP_APPFONT ( 190, 70 + FIELD_ROW_HEIGHT * FIELD_PAIRS_VISIBLE ) ;
+        Size = MAP_APPFONT ( 50 , 14 ) ;
+    };
+
+    HelpButton PB_HELP
+    {
+        SVLook = TRUE;
+        Pos = MAP_APPFONT ( 244, 70 + FIELD_ROW_HEIGHT * FIELD_PAIRS_VISIBLE ) ;
+        Size = MAP_APPFONT ( 50 , 14 ) ;
+    };
+
+    String STR_LOGICAL_FIELD_NAMES
+    {
+        Text = "FirstName;LastName;Company;Department;Street;Zip;City;State;Country;PhonePriv;PhoneComp;PhoneOffice;PhoneCell;PhoneOther;Pager;Fax;EMail;URL;Title;Position;Code;AddrForm;AddrFormMail;Id;CalendarURL;InviteParticipant;Note;Altfield1;Altfield2;Altfield3;Altfield4";
+        // no need to translate this
+        // the items in this string have to be in the same order as the STR_FIELD_* strings are added to the
+        // field label list of the dialog
+    };
+
+    String STR_NO_FIELD_SELECTION
+    {
+        Text [ en-US ] = "<none>";
+        };
+
+    String STR_FIELD_COMPANY
+    {
+        Text [ en-US ] = "Company";
+        };
+    String STR_FIELD_DEPARTMENT
+    {
+        Text [ en-US ] = "Department";
+        };
+    String STR_FIELD_FIRSTNAME
+    {
+        Text [ en-US ] = "First name";
+        };
+    String STR_FIELD_LASTNAME
+    {
+        Text [ en-US ] = "Last name";
+        };
+    String STR_FIELD_STREET
+    {
+        Text [ en-US ] = "Street";
+        };
+    String STR_FIELD_COUNTRY
+    {
+        Text [ en-US ] = "Country";
+        };
+    String STR_FIELD_ZIPCODE
+    {
+        Text [ en-US ] = "ZIP Code";
+        };
+    String STR_FIELD_CITY
+    {
+        Text [ en-US ] = "City";
+        };
+    String STR_FIELD_TITLE
+    {
+        Text [ en-US ] = "Title";
+        };
+    String STR_FIELD_POSITION
+    {
+        Text [ en-US ] = "Position";
+        };
+    String STR_FIELD_ADDRFORM
+    {
+        Text [ en-US ] = "Addr. Form";
+        };
+    String STR_FIELD_INITIALS
+    {
+        Text [ en-US ] = "Initials";
+        };
+    String STR_FIELD_SALUTATION
+    {
+        Text [ en-US ] = "Complimentary close";
+        };
+    String STR_FIELD_HOMETEL
+    {
+        Text [ en-US ] = "Tel: Home";
+        };
+    String STR_FIELD_WORKTEL
+    {
+        Text [ en-US ] = "Tel: Work";
+        };
+    String STR_FIELD_FAX
+    {
+        Text [ en-US ] = "FAX";
+        };
+    String STR_FIELD_EMAIL
+    {
+        Text [ en-US ] = "E-mail";
+        };
+    String STR_FIELD_URL
+    {
+        Text [ en-US ] = "URL";
+        };
+    String STR_FIELD_NOTE
+    {
+        Text [ en-US ] = "Note";
+        };
+    String STR_FIELD_USER1
+    {
+        Text [ en-US ] = "User 1";
+        };
+    String STR_FIELD_USER2
+    {
+        Text [ en-US ] = "User 2";
+        };
+    String STR_FIELD_USER3
+    {
+        Text [ en-US ] = "User 3";
+        };
+    String STR_FIELD_USER4
+    {
+        Text [ en-US ] = "User 4";
+        };
+
+    String STR_FIELD_ID
+    {
+        Text [ en-US ] = "ID";
+        };
+    String STR_FIELD_STATE
+    {
+        Text [ en-US ] = "State";
+        };
+    String STR_FIELD_OFFICETEL
+    {
+        Text [ en-US ] = "Tel: Office";
+        };
+    String STR_FIELD_PAGER
+    {
+        Text [ en-US ] = "Pager";
+        };
+    String STR_FIELD_MOBILE
+    {
+        Text [ en-US ] = "Mobile";
+        };
+    String STR_FIELD_TELOTHER
+    {
+        Text [ en-US ] = "Tel: Other";
+        };
+    String STR_FIELD_CALENDAR
+    {
+        Text [ en-US ] = "Calendar";
+        };
+    String STR_FIELD_INVITE
+    {
+        Text [ en-US ] = "Invite";
+        };
+};
diff --git a/svtools/source/uno/addrtempuno.cxx b/svtools/source/uno/addrtempuno.cxx
new file mode 100644
index 0000000..2287b12
--- /dev/null
+++ b/svtools/source/uno/addrtempuno.cxx
@@ -0,0 +1,228 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#include "svtools/genericunodialog.hxx"
+#include <svtools/addresstemplate.hxx>
+#include <comphelper/extract.hxx>
+#include <cppuhelper/typeprovider.hxx>
+#include <comphelper/property.hxx>
+#include <com/sun/star/sdbc/XDataSource.hpp>
+
+// .......................................................................
+namespace svt
+{
+// .......................................................................
+
+#define UNODIALOG_PROPERTY_ID_ALIASES       100
+#define UNODIALOG_PROPERTY_ALIASES          "FieldMapping"
+
+    using namespace com::sun::star::uno;
+    using namespace com::sun::star::lang;
+    using namespace com::sun::star::util;
+    using namespace com::sun::star::beans;
+    using namespace com::sun::star::sdbc;
+
+    //=========================================================================
+    //= OAddressBookSourceDialogUno
+    //=========================================================================
+    typedef OGenericUnoDialog OAddressBookSourceDialogUnoBase;
+    class OAddressBookSourceDialogUno
+            :public OAddressBookSourceDialogUnoBase
+            ,public ::comphelper::OPropertyArrayUsageHelper< OAddressBookSourceDialogUno >
+    {
+    protected:
+        Sequence< AliasProgrammaticPair >   m_aAliases;
+        Reference< XDataSource >            m_xDataSource;
+        ::rtl::OUString                     m_sDataSourceName;
+        ::rtl::OUString                     m_sTable;
+
+    protected:
+        OAddressBookSourceDialogUno(const Reference< XMultiServiceFactory >& _rxORB);
+
+    public:
+        // XTypeProvider
+        virtual Sequence<sal_Int8> SAL_CALL getImplementationId(  ) throw(RuntimeException);
+
+        // XServiceInfo
+        virtual ::rtl::OUString SAL_CALL getImplementationName() throw(RuntimeException);
+        virtual ::comphelper::StringSequence SAL_CALL getSupportedServiceNames() throw(RuntimeException);
+
+        // XServiceInfo - static methods
+        static Sequence< ::rtl::OUString > getSupportedServiceNames_Static(void) throw( RuntimeException );
+        static ::rtl::OUString getImplementationName_Static(void) throw( RuntimeException );
+        static Reference< XInterface >
+                SAL_CALL Create(const Reference< com::sun::star::lang::XMultiServiceFactory >&);
+
+        // XPropertySet
+        virtual Reference< XPropertySetInfo>  SAL_CALL getPropertySetInfo() throw(RuntimeException);
+        virtual ::cppu::IPropertyArrayHelper& SAL_CALL getInfoHelper();
+
+        // OPropertyArrayUsageHelper
+        virtual ::cppu::IPropertyArrayHelper* createArrayHelper( ) const;
+
+    protected:
+    // OGenericUnoDialog overridables
+        virtual Dialog* createDialog(Window* _pParent);
+
+        virtual void implInitialize(const com::sun::star::uno::Any& _rValue);
+
+        virtual void executedDialog(sal_Int16 _nExecutionResult);
+    };
+
+
+    //=========================================================================
+    //= OAddressBookSourceDialogUno
+    //=========================================================================
+    Reference< XInterface > SAL_CALL OAddressBookSourceDialogUno_CreateInstance( const Reference< XMultiServiceFactory >& _rxFactory)
+    {
+        return OAddressBookSourceDialogUno::Create(_rxFactory);
+    }
+
+    //-------------------------------------------------------------------------
+    OAddressBookSourceDialogUno::OAddressBookSourceDialogUno(const Reference< XMultiServiceFactory >& _rxORB)
+        :OGenericUnoDialog(_rxORB)
+    {
+        registerProperty(::rtl::OUString(UNODIALOG_PROPERTY_ALIASES), UNODIALOG_PROPERTY_ID_ALIASES, PropertyAttribute::READONLY,
+            &m_aAliases, getCppuType(&m_aAliases));
+    }
+
+    //-------------------------------------------------------------------------
+    Sequence<sal_Int8> SAL_CALL OAddressBookSourceDialogUno::getImplementationId(  ) throw(RuntimeException)
+    {
+        static ::cppu::OImplementationId aId;
+        return aId.getImplementationId();
+    }
+
+    //-------------------------------------------------------------------------
+    Reference< XInterface > SAL_CALL OAddressBookSourceDialogUno::Create(const Reference< XMultiServiceFactory >& _rxFactory)
+    {
+        return *(new OAddressBookSourceDialogUno(_rxFactory));
+    }
+
+    //-------------------------------------------------------------------------
+    ::rtl::OUString SAL_CALL OAddressBookSourceDialogUno::getImplementationName() throw(RuntimeException)
+    {
+        return getImplementationName_Static();
+    }
+
+    //-------------------------------------------------------------------------
+    ::rtl::OUString OAddressBookSourceDialogUno::getImplementationName_Static() throw(RuntimeException)
+    {
+        return ::rtl::OUString( "com.sun.star.comp.svtools.OAddressBookSourceDialogUno" );
+    }
+
+    //-------------------------------------------------------------------------
+    ::comphelper::StringSequence SAL_CALL OAddressBookSourceDialogUno::getSupportedServiceNames() throw(RuntimeException)
+    {
+        return getSupportedServiceNames_Static();
+    }
+
+    //-------------------------------------------------------------------------
+    ::comphelper::StringSequence OAddressBookSourceDialogUno::getSupportedServiceNames_Static() throw(RuntimeException)
+    {
+        ::comphelper::StringSequence aSupported(1);
+        aSupported.getArray()[0] = ::rtl::OUString( "com.sun.star.ui.AddressBookSourceDialog" );
+        return aSupported;
+    }
+
+    //-------------------------------------------------------------------------
+    Reference<XPropertySetInfo>  SAL_CALL OAddressBookSourceDialogUno::getPropertySetInfo() throw(RuntimeException)
+    {
+        Reference<XPropertySetInfo>  xInfo( createPropertySetInfo( getInfoHelper() ) );
+        return xInfo;
+    }
+
+    //-------------------------------------------------------------------------
+    ::cppu::IPropertyArrayHelper& OAddressBookSourceDialogUno::getInfoHelper()
+    {
+        return *const_cast<OAddressBookSourceDialogUno*>(this)->getArrayHelper();
+    }
+
+    //------------------------------------------------------------------------------
+    ::cppu::IPropertyArrayHelper* OAddressBookSourceDialogUno::createArrayHelper( ) const
+    {
+        Sequence< Property > aProps;
+        describeProperties(aProps);
+        return new ::cppu::OPropertyArrayHelper(aProps);
+    }
+
+    //------------------------------------------------------------------------------
+    void OAddressBookSourceDialogUno::executedDialog(sal_Int16 _nExecutionResult)
+    {
+        OAddressBookSourceDialogUnoBase::executedDialog(_nExecutionResult);
+
+        if ( _nExecutionResult )
+            if ( m_pDialog )
+                static_cast< AddressBookSourceDialog* >( m_pDialog )->getFieldMapping( m_aAliases );
+    }
+
+    //------------------------------------------------------------------------------
+    void OAddressBookSourceDialogUno::implInitialize(const com::sun::star::uno::Any& _rValue)
+    {
+        PropertyValue aVal;
+        if (_rValue >>= aVal)
+        {
+            if (0 == aVal.Name.compareToAscii("DataSource"))
+            {
+#if OSL_DEBUG_LEVEL > 0
+                sal_Bool bSuccess =
+#endif
+                aVal.Value >>= m_xDataSource;
+                OSL_ENSURE( bSuccess, "OAddressBookSourceDialogUno::implInitialize: invalid type for DataSource!" );
+                return;
+            }
+
+            if (0 == aVal.Name.compareToAscii("DataSourceName"))
+            {
+#if OSL_DEBUG_LEVEL > 0
+                sal_Bool bSuccess =
+#endif
+                aVal.Value >>= m_sDataSourceName;
+                OSL_ENSURE( bSuccess, "OAddressBookSourceDialogUno::implInitialize: invalid type for DataSourceName!" );
+                return;
+            }
+
+            if (0 == aVal.Name.compareToAscii("Command"))
+            {
+#if OSL_DEBUG_LEVEL > 0
+                sal_Bool bSuccess =
+#endif
+                aVal.Value >>= m_sTable;
+                OSL_ENSURE( bSuccess, "OAddressBookSourceDialogUno::implInitialize: invalid type for Command!" );
+                return;
+            }
+        }
+
+        OAddressBookSourceDialogUnoBase::implInitialize( _rValue );
+    }
+
+    //------------------------------------------------------------------------------
+    Dialog* OAddressBookSourceDialogUno::createDialog(Window* _pParent)
+    {
+        if ( m_xDataSource.is() && !m_sTable.isEmpty() )
+            return new AddressBookSourceDialog(_pParent, m_aContext.getLegacyServiceFactory(), m_xDataSource, m_sDataSourceName, m_sTable, m_aAliases );
+        else
+            return new AddressBookSourceDialog( _pParent, m_aContext.getLegacyServiceFactory() );
+    }
+
+// .......................................................................
+}   // namespace svt
+// .......................................................................
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/svtools/source/uno/miscservices.cxx b/svtools/source/uno/miscservices.cxx
index 64095fa..f40f964 100644
--- a/svtools/source/uno/miscservices.cxx
+++ b/svtools/source/uno/miscservices.cxx
@@ -75,6 +75,7 @@ namespace
 
 // -------------------------------------------------------------------------------------
 
+DECLARE_CREATEINSTANCE_NAMESPACE( svt, OAddressBookSourceDialogUno )
 DECLARE_CREATEINSTANCE( SvFilterOptionsDialog )
 DECLARE_CREATEINSTANCE_NAMESPACE( unographic, GraphicProvider )
 DECLARE_CREATEINSTANCE_NAMESPACE( unographic, GraphicRendererVCL )
@@ -91,6 +92,19 @@ SAL_DLLPUBLIC_EXPORT void * SAL_CALL svt_component_getFactory (
     {
         Reference< XSingleServiceFactory > xFactory;
         if (rtl_str_compare (
+                pImplementationName, "com.sun.star.comp.svtools.OAddressBookSourceDialogUno") == 0)
+        {
+            Sequence< OUString > aServiceNames(1);
+            aServiceNames.getArray()[0] =
+                OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.ui.AddressBookSourceDialog" ));
+
+            xFactory = ::cppu::createSingleFactory (
+                reinterpret_cast< XMultiServiceFactory* >( _pServiceManager ),
+                OUString::createFromAscii( pImplementationName ),
+                svt::OAddressBookSourceDialogUno_CreateInstance,
+                aServiceNames);
+        }
+        else if (rtl_str_compare (
                      pImplementationName, "com.sun.star.svtools.SvFilterOptionsDialog") == 0)
         {
             Sequence< OUString > aServiceNames(1);
diff --git a/svtools/util/svt.component b/svtools/util/svt.component
index 16b0c40..4670a13 100644
--- a/svtools/util/svt.component
+++ b/svtools/util/svt.component
@@ -25,6 +25,9 @@
   <implementation name="com.sun.star.comp.graphic.GraphicRendererVCL">
     <service name="com.sun.star.graphic.GraphicRendererVCL"/>
   </implementation>
+  <implementation name="com.sun.star.comp.svtools.OAddressBookSourceDialogUno">
+    <service name="com.sun.star.ui.AddressBookSourceDialog"/>
+  </implementation>
   <implementation name="com.sun.star.comp.svtools.uno.Wizard">
     <service name="com.sun.star.ui.dialogs.Wizard"/>
   </implementation>
diff --git a/sw/uiconfig/sglobal/menubar/menubar.xml b/sw/uiconfig/sglobal/menubar/menubar.xml
index e27f19a..191eb7c 100644
--- a/sw/uiconfig/sglobal/menubar/menubar.xml
+++ b/sw/uiconfig/sglobal/menubar/menubar.xml
@@ -434,6 +434,7 @@
       <menu:menuitem menu:id=".uno:Gallery"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:BibliographyComponent"/>
+      <menu:menuitem menu:id=".uno:AddressBookSource"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:MergeDocuments"/>
       <menu:menuseparator/>
diff --git a/sw/uiconfig/sweb/menubar/menubar.xml b/sw/uiconfig/sweb/menubar/menubar.xml
index 1bfb39b..90b4a5c 100644
--- a/sw/uiconfig/sweb/menubar/menubar.xml
+++ b/sw/uiconfig/sweb/menubar/menubar.xml
@@ -376,6 +376,7 @@
       <menu:menuitem menu:id=".uno:AVMediaPlayer"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:BibliographyComponent"/>
+      <menu:menuitem menu:id=".uno:AddressBookSource"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:SortDialog"/>
       <menu:menuitem menu:id=".uno:CalculateSel"/>
diff --git a/sw/uiconfig/swform/menubar/menubar.xml b/sw/uiconfig/swform/menubar/menubar.xml
index a50afdd..6d25a44 100644
--- a/sw/uiconfig/swform/menubar/menubar.xml
+++ b/sw/uiconfig/swform/menubar/menubar.xml
@@ -430,6 +430,7 @@
       <menu:menuitem menu:id=".uno:Gallery"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:BibliographyComponent"/>
+      <menu:menuitem menu:id=".uno:AddressBookSource"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:MailMergeWizard"/>
       <menu:menuseparator/>
diff --git a/sw/uiconfig/swreport/menubar/menubar.xml b/sw/uiconfig/swreport/menubar/menubar.xml
index d4f4c0c..74f8684 100644
--- a/sw/uiconfig/swreport/menubar/menubar.xml
+++ b/sw/uiconfig/swreport/menubar/menubar.xml
@@ -430,6 +430,7 @@
       <menu:menuitem menu:id=".uno:Gallery"/>
       <menu:menuseparator/>
       <menu:menuitem menu:id=".uno:BibliographyComponent"/>
+      <menu:menuitem menu:id=".uno:AddressBookSource"/>

... etc. - the rest is truncated


More information about the Libreoffice-commits mailing list