tdf#154179: fix pre-selection of the current outline level

This seems to always be the intention, and never worked. The pre-selection
made in SwOutlineSettingsTabPage::SetWrtShell was overridden later in the
SwOutlineSettingsTabPage::ActivatePage, because SwOutlineTabDialog::s_nNumLevel
wasn't updated to the wanted value. Additionally, it only could potentially
work when the dialog opened the SwOutlineSettingsTabPage, not the other
page (which would happen when it was active the last time when the dialog
closed).

And the active document level value must be sanitized.

Change-Id: Iefefcdcde9da0e54e3acaffb981e057367a27197
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/148837
Tested-by: Jenkins
Reviewed-by: Mike Kaganski <mike.kaganski@collabora.com>
diff --git a/sw/source/ui/misc/outline.cxx b/sw/source/ui/misc/outline.cxx
index 5903fd5..f98603c 100644
--- a/sw/source/ui/misc/outline.cxx
+++ b/sw/source/ui/misc/outline.cxx
@@ -129,7 +129,9 @@ SwNumNamesDlg::SwNumNamesDlg(weld::Window *pParent)

static sal_uInt16 lcl_BitToLevel(sal_uInt16 nActLevel)
{
    sal_uInt16 nTmp = nActLevel;
    constexpr sal_uInt16 MAXLEVEL_MASK = USHRT_MAX >> (sizeof(sal_uInt16) * CHAR_BIT - MAXLEVEL);
    assert((nActLevel & MAXLEVEL_MASK) == nActLevel);
    sal_uInt16 nTmp = nActLevel & MAXLEVEL_MASK; // a safety measure
    sal_uInt16 nTmpLevel = 0;
    while( 0 != (nTmp >>= 1) )
        nTmpLevel++;
@@ -152,6 +154,13 @@ SwOutlineTabDialog::SwOutlineTabDialog(weld::Window* pParent, const SfxItemSet* 
    m_xNumRule.reset(new SwNumRule(*rSh.GetOutlineNumRule()));
    GetCancelButton().connect_clicked(LINK(this, SwOutlineTabDialog, CancelHdl));

    if (auto nOutlinePos = m_rWrtSh.GetOutlinePos(MAXLEVEL); nOutlinePos != SwOutlineNodes::npos)
    {
        int nTmp = m_rWrtSh.getIDocumentOutlineNodesAccess()->getOutlineLevel(nOutlinePos);
        assert(nTmp < MAXLEVEL);
        SetActNumLevel(nTmp < 0 ? USHRT_MAX : (1 << nTmp));
    }

    AddTabPage("position", &SwNumPositionTabPage::Create, nullptr);
    AddTabPage("numbering", &SwOutlineSettingsTabPage::Create, nullptr);

@@ -528,21 +537,15 @@ void    SwOutlineSettingsTabPage::Update()

IMPL_LINK( SwOutlineSettingsTabPage, LevelHdl, weld::TreeView&, rBox, void )
{
    m_nActLevel = 0;
    auto aRows = rBox.get_selected_rows();
    if (std::find(aRows.begin(), aRows.end(), MAXLEVEL) != aRows.end())
    assert(aRows.empty() || aRows.size() == 1); // Single selection only
    if (aRows.empty() || aRows[0] == MAXLEVEL)
    {
        m_nActLevel = 0xFFFF;
        m_nActLevel = USHRT_MAX;
    }
    else
    {
        sal_uInt16 nMask = 1;
        for( sal_uInt16 i = 0; i < MAXLEVEL; i++ )
        {
            if (std::find(aRows.begin(), aRows.end(), i) != aRows.end())
                m_nActLevel |= nMask;
            nMask <<= 1;
        }
        m_nActLevel = 1 << aRows[0];
    }
    Update();
}
@@ -754,13 +757,6 @@ void SwOutlineSettingsTabPage::SetWrtShell(SwWrtShell* pShell)
    }

    m_xNumberBox->SelectNumberingType(rNumFormat.GetNumberingType());
    SwOutlineNodes::size_type nOutlinePos = m_pSh->GetOutlinePos(MAXLEVEL);
    int nTmp = 0;
    if(nOutlinePos != SwOutlineNodes::npos)
    {
        nTmp = o3tl::narrowing<sal_uInt16>(m_pSh->getIDocumentOutlineNodesAccess()->getOutlineLevel(nOutlinePos));
    }
    m_xLevelLB->select(nTmp-1);

    // collect char styles
    m_xCharFormatLB->clear();
diff --git a/sw/source/uibase/inc/outline.hxx b/sw/source/uibase/inc/outline.hxx
index cf96ee6..2b5e6f0 100644
--- a/sw/source/uibase/inc/outline.hxx
+++ b/sw/source/uibase/inc/outline.hxx
@@ -33,6 +33,7 @@ class SwChapterNumRules;
class SwOutlineTabDialog final : public SfxTabDialogController
{
    static     sal_uInt16    s_nNumLevel;
    static_assert(sizeof(s_nNumLevel) * CHAR_BIT >= MAXLEVEL);

    OUString            m_aCollNames[MAXLEVEL];