sw/source/uibase/inc/content.hxx               |    5 +
 sw/source/uibase/utlui/content.cxx             |   76 +++++++++++++++++++------
 sw/uiconfig/swriter/ui/navigatorcontextmenu.ui |   36 +++++++----
 3 files changed, 87 insertions(+), 30 deletions(-)

New commits:
commit b802cecbc0f57d0ba0d70434cf619a7e91c7393f
Author:     Jim Raykowski <rayk...@gmail.com>
AuthorDate: Sat Mar 12 02:07:46 2022 -0900
Commit:     Jim Raykowski <rayk...@gmail.com>
CommitDate: Wed Mar 16 08:42:34 2022 +0100

    tdf#86395 tdf#104253 tdf#147658 tdf#135043 SwNavigator sort enhancement
    
    Provides for sorting content members by order in document or
    alphabetically. The option to sort comment and footnote content types
    members alphabetically is not done by this patch.
    
    Change-Id: If68c08bb0f1035b32cd1dad1d5bd08a340834b49
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/131448
    Tested-by: Jenkins
    Reviewed-by: Jim Raykowski <rayk...@gmail.com>

diff --git a/sw/source/uibase/inc/content.hxx b/sw/source/uibase/inc/content.hxx
index 0a4e18013be4..2d6ac1a7d925 100644
--- a/sw/source/uibase/inc/content.hxx
+++ b/sw/source/uibase/inc/content.hxx
@@ -183,6 +183,8 @@ class SwContentType final : public SwTypeNumber
     bool                m_bEdit:          1;  // can this type be edited?
     bool                m_bDelete:        1;  // can this type be deleted?
 
+    bool m_bAlphabeticSort = false;
+
         static OUString     RemoveNewline(const OUString&);
 public:
         SwContentType(SwWrtShell* pParent, ContentTypeId nType, sal_uInt8 
nLevel );
@@ -206,6 +208,9 @@ public:
                                 Invalidate();
                             }
 
+        bool GetSortType() const {return m_bAlphabeticSort;}
+        void SetSortType(bool bAlphabetic) {m_bAlphabeticSort = bAlphabetic;}
+
         void                Invalidate(); // only nMemberCount is read again
 
         bool                IsEditable() const {return m_bEdit;}
diff --git a/sw/source/uibase/utlui/content.cxx 
b/sw/source/uibase/utlui/content.cxx
index 6a4bf1d9456d..7e186232512b 100644
--- a/sw/source/uibase/utlui/content.cxx
+++ b/sw/source/uibase/utlui/content.cxx
@@ -438,7 +438,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                 if (nLevel >= m_nOutlineLevel || 
!m_pWrtShell->getIDocumentOutlineNodesAccess()->
                         isOutlineInLayout(i, *m_pWrtShell->GetLayout()))
                     continue;
-                tools::Long nYPos = getYPos(
+                tools::Long nYPos = m_bAlphabeticSort ? 0 : getYPos(
                             
*m_pWrtShell->getIDocumentOutlineNodesAccess()->getOutlineNode(i));
                 OUString aEntry(comphelper::string::stripStart(
                                     
m_pWrtShell->getIDocumentOutlineNodesAccess()->getOutlineText(
@@ -486,8 +486,11 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                     continue;
                 }
                 tools::Long nYPos = 0;
-                if (SwTable* pTable = SwTable::FindTable(&rTableFormat))
-                    nYPos = getYPos(*pTable->GetTableNode());
+                if (!m_bAlphabeticSort)
+                {
+                    if (SwTable* pTable = SwTable::FindTable(&rTableFormat))
+                        nYPos = getYPos(*pTable->GetTableNode());
+                }
                 auto pCnt = make_unique<SwContent>(this, 
rTableFormat.GetName(), nYPos);
                 if( !rTableFormat.GetInfo( aAskItem ) &&
                         !aAskItem.pObject )     // not visible
@@ -527,19 +530,18 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                 const OUString sFrameName = pFrameFormat->GetName();
 
                 SwContent* pCnt;
+                tools::Long nYPos =
+                        m_bAlphabeticSort ? 0 : 
pFrameFormat->FindLayoutRect(false, &aNullPt).Top();
                 if(ContentTypeId::GRAPHIC == m_nContentType)
                 {
                     OUString sLink;
                     m_pWrtShell->GetGrfNms( &sLink, nullptr, static_cast<const 
SwFlyFrameFormat*>( pFrameFormat));
-                    pCnt = new SwGraphicContent(this, sFrameName,
-                                INetURLObject::decode( sLink,
-                                           
INetURLObject::DecodeMechanism::Unambiguous ),
-                                pFrameFormat->FindLayoutRect(false, 
&aNullPt).Top());
+                    pCnt = new SwGraphicContent(this, sFrameName, 
INetURLObject::decode(sLink,
+                                           
INetURLObject::DecodeMechanism::Unambiguous), nYPos);
                 }
                 else
                 {
-                    pCnt = new SwContent(this, sFrameName,
-                            pFrameFormat->FindLayoutRect(false, 
&aNullPt).Top() );
+                    pCnt = new SwContent(this, sFrameName, nYPos);
                 }
                 if( !pFrameFormat->GetInfo( aAskItem ) &&
                     !aAskItem.pObject )     // not visible
@@ -562,6 +564,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
         break;
         case ContentTypeId::BOOKMARK:
         {
+            tools::Long nYPos = 0;
             IDocumentMarkAccess* const pMarkAccess = 
m_pWrtShell->getIDocumentMarkAccess();
             for(IDocumentMarkAccess::const_iterator_t ppBookmark = 
pMarkAccess->getBookmarksBegin();
                 ppBookmark != pMarkAccess->getBookmarksEnd();
@@ -571,7 +574,8 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                 {
                     const OUString& rBkmName = (*ppBookmark)->GetName();
                     //nYPos from 0 -> text::Bookmarks will be sorted 
alphabetically
-                    std::unique_ptr<SwContent> pCnt(new SwContent(this, 
rBkmName, 0));
+                    auto pCnt(std::make_unique<SwContent>(this, rBkmName,
+                                                          m_bAlphabeticSort ? 
0 : nYPos++));
                     m_pMember->insert(std::move(pCnt));
                 }
             }
@@ -617,7 +621,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                                     + sSubType + sExpandField;
                         }
                         auto pCnt(std::make_unique<SwTextFieldContent>(this, 
sText, pFormatField,
-                                      
pTextField->GetTextNode().GetIndex().get()));
+                            m_bAlphabeticSort ? 0 : 
pTextField->GetTextNode().GetIndex().get()));
                         if 
(!pTextField->GetTextNode().getLayoutFrame(m_pWrtShell->GetLayout()))
                             pCnt->SetInvisible();
                         m_pMember->insert(std::move(pCnt));
@@ -681,7 +685,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                     }
 
                     std::unique_ptr<SwContent> pCnt(new SwRegionContent(this, 
sSectionName,
-                            nLevel, getYPos(*pNodeIndex)));
+                            nLevel, m_bAlphabeticSort ? 0 : 
getYPos(*pNodeIndex)));
                     if( !pFormat->GetInfo( aAskItem ) &&
                         !aAskItem.pObject )     // not visible
                         pCnt->SetInvisible();
@@ -707,10 +711,11 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
             std::vector<OUString> aRefMarks;
             m_pWrtShell->GetRefMarks( &aRefMarks );
 
+            tools::Long nYPos = 0;
             for (const auto& rRefMark : aRefMarks)
             {
-                // References sorted alphabetically
-                m_pMember->insert(std::make_unique<SwContent>(this, rRefMark, 
0));
+                m_pMember->insert(std::make_unique<SwContent>(this, rRefMark,
+                                                              
m_bAlphabeticSort ? 0 : nYPos++));
             }
         }
         break;
@@ -719,6 +724,19 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
             SwGetINetAttrs aArr;
             m_pWrtShell->GetINetAttrs(aArr);
 
+            if (m_bAlphabeticSort)
+            {
+                for (auto& r : aArr)
+                {
+                    auto pCnt(make_unique<SwURLFieldContent>(this, r.sText, 
INetURLObject::decode(
+                                                    
r.rINetAttr.GetINetFormat().GetValue(),
+                                                    
INetURLObject::DecodeMechanism::Unambiguous),
+                                                             &r.rINetAttr, 0));
+                    m_pMember->insert(std::move(pCnt));
+                }
+                break;
+            }
+
             // use stable sort array to list hyperlinks in document order
             std::vector<SwGetINetAttr*> aStableSortINetAttrsArray;
             for (SwGetINetAttr& r : aArr)
@@ -752,7 +770,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                 OUString sTOXNm( pBase->GetTOXName() );
 
                 SwContent* pCnt = new SwTOXBaseContent(
-                        this, sTOXNm, nTox, *pBase);
+                        this, sTOXNm, m_bAlphabeticSort ? 0 : nTox, *pBase);
 
                 if(pBase && !pBase->IsVisible())
                     pCnt->SetInvisible();
@@ -824,7 +842,7 @@ void SwContentType::FillMemberList(bool* pbContentChanged)
                         tools::Long nYPos = LONG_MIN;
                         const bool bIsVisible = 
rIDDMA.IsVisibleLayerId(pTemp->GetLayer());
                         if (bIsVisible)
-                            nYPos = pTemp->GetLogicRect().Top();
+                            nYPos = m_bAlphabeticSort ? 0 : 
pTemp->GetLogicRect().Top();
                         auto pCnt(std::make_unique<SwContent>(this, 
pTemp->GetName(), nYPos));
                         if (!bIsVisible)
                             pCnt->SetInvisible();
@@ -1431,6 +1449,8 @@ IMPL_LINK(SwContentTree, CommandHdl, const CommandEvent&, 
rCEvt, bool)
     bool bRemoveFieldTracking = true;
     bool bRemoveFootnoteTracking = true;
 
+    bool bRemoveSortEntry = true;
+
     if (xEntry)
     {
         const SwContentType* pType;
@@ -1440,6 +1460,13 @@ IMPL_LINK(SwContentTree, CommandHdl, const 
CommandEvent&, rCEvt, bool)
             pType = weld::fromId<SwContent*>(
                         m_xTreeView->get_id(*xEntry))->GetParent();
         const ContentTypeId nContentType = pType->GetType();
+
+        if (nContentType != ContentTypeId::FOOTNOTE && nContentType != 
ContentTypeId::POSTIT)
+        {
+            bRemoveSortEntry = false;
+            xPop->set_active("sort", pType->GetSortType());
+        }
+
         OString aIdent;
         switch (nContentType)
         {
@@ -1734,6 +1761,9 @@ IMPL_LINK(SwContentTree, CommandHdl, const CommandEvent&, 
rCEvt, bool)
     if (bRemoveFootnoteTracking)
         xPop->remove("footnotetracking");
 
+    if (bRemoveSortEntry)
+        xPop->remove("sort");
+
     bool bSetSensitiveCollapseAllCategories = false;
     if (!m_bIsRoot)
     {
@@ -4180,6 +4210,20 @@ void SwContentTree::ExecuteContextMenuAction(const 
OString& rSelectedPopupEntry)
     if (!m_xTreeView->get_selected(xFirst.get()))
         return; // this shouldn't happen, but better to be safe than ...
 
+    if (rSelectedPopupEntry == "sort")
+    {
+        SwContentType* pCntType;
+        const OUString& rId(m_xTreeView->get_id(*xFirst));
+        if (lcl_IsContentType(*xFirst, *m_xTreeView))
+            pCntType = weld::fromId<SwContentType*>(rId);
+        else
+            pCntType = 
const_cast<SwContentType*>(weld::fromId<SwContent*>(rId)->GetParent());
+        pCntType->SetSortType(!pCntType->GetSortType());
+        pCntType->FillMemberList();
+        Display(true);
+        return;
+    }
+
     auto nSelectedPopupEntry = rSelectedPopupEntry.toUInt32();
     switch (nSelectedPopupEntry)
     {
diff --git a/sw/uiconfig/swriter/ui/navigatorcontextmenu.ui 
b/sw/uiconfig/swriter/ui/navigatorcontextmenu.ui
index 5cda6038e110..e39368556fed 100644
--- a/sw/uiconfig/swriter/ui/navigatorcontextmenu.ui
+++ b/sw/uiconfig/swriter/ui/navigatorcontextmenu.ui
@@ -196,20 +196,6 @@
         <property name="can-focus">False</property>
       </object>
     </child>
-    <child>
-      <object class="GtkMenuItem" id="1">
-        <property name="visible">True</property>
-        <property name="can-focus">False</property>
-        <property name="label" translatable="yes" 
context="navigatorcontextmenu|STR_OUTLINE_LEVEL">Outline Level</property>
-        <property name="use-underline">True</property>
-        <child type="submenu">
-          <object class="GtkMenu" id="outlinelevel">
-            <property name="visible">True</property>
-            <property name="can-focus">False</property>
-          </object>
-        </child>
-      </object>
-    </child>
     <child>
       <object class="GtkMenuItem" id="4">
         <property name="visible">True</property>
@@ -328,12 +314,34 @@
         <property name="use-underline">True</property>
       </object>
     </child>
+    <child>
+      <object class="GtkCheckMenuItem" id="sort">
+        <property name="visible">True</property>
+        <property name="can-focus">False</property>
+        <property name="label" translatable="yes" 
context="navigatorcontextmenu|STR_SORT_ALPHABETICALLY">Sort 
Alphabetically</property>
+        <property name="use-underline">True</property>
+      </object>
+    </child>
     <child>
       <object class="GtkSeparatorMenuItem">
         <property name="visible">True</property>
         <property name="can-focus">False</property>
       </object>
     </child>
+    <child>
+      <object class="GtkMenuItem" id="1">
+        <property name="visible">True</property>
+        <property name="can-focus">False</property>
+        <property name="label" translatable="yes" 
context="navigatorcontextmenu|STR_OUTLINE_LEVEL">Outline Level</property>
+        <property name="use-underline">True</property>
+        <child type="submenu">
+          <object class="GtkMenu" id="outlinelevel">
+            <property name="visible">True</property>
+            <property name="can-focus">False</property>
+          </object>
+        </child>
+      </object>
+    </child>
     <child>
       <object class="GtkMenuItem" id="2">
         <property name="visible">True</property>

Reply via email to