summaryrefslogtreecommitdiff
path: root/sc/source/filter/xml
diff options
context:
space:
mode:
authorArmin Le Grand (allotropia) <armin.le.grand.extern@allotropia.de>2024-01-10 20:07:47 +0100
committerArmin Le Grand <Armin.Le.Grand@me.com>2024-01-12 12:15:54 +0100
commitae7807c889c19145f89cec40afac82eee191837c (patch)
treee31e4a541555f3618e8173e24b79c5186d840607 /sc/source/filter/xml
parent8f215fab5593070556e903121cc195660e16105c (diff)
ITEM: No longer register Items at Pool
The issue is that the flag RegisteredAtPool at the SfxPoolItem is Pool-dependent: It marks that the Item is registeres at *one* Pool/Model. This makes it Pool-dependent. Due to this there is no way to share Items that need to be registered globally/ in multiple Pools/Models what is one of the goals for optimal sharing. We can also not live without having access to all Items associated with the Pool, due to mechanisms in place like the Surrogate stuff. This again is used for two purposes: (1) Access all Items associated with one Pool/Model, at least that is the assumption. This is not valid since it gets corrupted with a single ItemSet/Holder used that does not host model data, e.g. an open Dialog or the Sidebar (or...). But works in principle. (2) Access extra-Items that are held nowhere and are created using DirectPutItemInPool, e.g. infos for a Dialog. These would need a instance/place to host them, the Pool is (ab)used for that. Both are 'compromizes' (to not use a more bad word) and should not exist. (1) should iterate over the Model and do actions. There are even places that use (1) to *change* Items, by casting them to non-const, even RefCounted ones, so having no control over what all might be changed doing so. Since we talk about ca. 100+ places there is no way to get away from this - I can imagine how this happened: The 'poolable' attr traditionally needed for the old binary format was one day 'used' to not need to iterate over the Model, an API was added to access and this usage was copied. Sigh.. It is even used when ODF is loaded: E.g. the FillStyle is imported from XML, interpreted, and put into an ItemSet. Then it gets set at the XShape using UNO API and a *name* -> that name and the Surrogate mechanism is used to find and set the FillStyle at the Model Object. The FillStyle could probably just be set using UNO API and the data directly. The association between Model/Pool and Item is created by the object hosting the Item, these are ItemSets and ItemHolders. Thus it is possible to register these at the Pool. This allows to iterate and collect the Items associated with the Pool and keep the Surrogate mechanism alive. This is the main change done here. It limits the registrations to Items for which (at the Pool) the NeedsPoolRegistration is set, also Item-independent. Speed is okay, I saw no big changes in my tests here. The registration is just pointers, no ownership or RefCounting needed here. The advantage is that Items get closer to be shared office-wide, they can be referenced by multiple ItemSets (RefCnt) associated with different Pools/Models. NOTE: This is not true for SfxSetItems, these are and will stay Pool-dependent due to their need to a Pool in the contained ItemSet. Note that we have ca. six deivations of SfxSetItem, but ca. 500+ Item derivations, so not too bad. For the usages of Surrogates to change existing, RefCounted Items: These can now at least be changed - if they show up to be problematic - to iterate over the registered ItemSets and change Items there the correct way: Set a changed one at the ItemSet. That also allows Objects to *react* on ItemChanges, there is no way to do that with the existing 'compromize'... UnitTests show that this already works well for SC and SD, but SW has still some issues. I will put this to gerrit now, but there will be additional work. A involved problem is the current DefaultItem handling and the state the Pool implementation is in. E.g. StaticDefaults are not really static, Pools hard-delete the DefaultItems (forcing the RefCnt to zero to not have the destructor complain) and other quirks. Looking at that right now, hoping to get this change done without having to change that too much. I thought about adapting PoolItemTest to this, but it is only related to DirectPutItemInPool which is mostly gone and hopefully completely soon. Nonetheless I adapted that mechanism to use a list of SfxPoolItemHolder at the Pool. That makes it safe and abandons the need for indirect garbage collection removal at the Pool. Change-Id: Ib47f21dafa989202930919eace5f7e9c5632ce96 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/161896 Tested-by: Jenkins Reviewed-by: Armin Le Grand <Armin.Le.Grand@me.com>
Diffstat (limited to 'sc/source/filter/xml')
-rw-r--r--sc/source/filter/xml/xmlexprt.cxx4
-rw-r--r--sc/source/filter/xml/xmlfonte.cxx8
2 files changed, 9 insertions, 3 deletions
diff --git a/sc/source/filter/xml/xmlexprt.cxx b/sc/source/filter/xml/xmlexprt.cxx
index 9da5da65b7e6..4ec6ab6cdbb6 100644
--- a/sc/source/filter/xml/xmlexprt.cxx
+++ b/sc/source/filter/xml/xmlexprt.cxx
@@ -5329,7 +5329,9 @@ XMLNumberFormatAttributesExportHelper* ScXMLExport::GetNumberFormatAttributesExp
void ScXMLExport::CollectUserDefinedNamespaces(const SfxItemPool* pPool, sal_uInt16 nAttrib)
{
- for (const SfxPoolItem* pItem : pPool->GetItemSurrogates(nAttrib))
+ ItemSurrogates aSurrogates;
+ pPool->GetItemSurrogates(aSurrogates, nAttrib);
+ for (const SfxPoolItem* pItem : aSurrogates)
{
const SvXMLAttrContainerItem *pUnknown(static_cast<const SvXMLAttrContainerItem *>(pItem));
if( pUnknown->GetAttrCount() > 0 )
diff --git a/sc/source/filter/xml/xmlfonte.cxx b/sc/source/filter/xml/xmlfonte.cxx
index ab8e42f4ce60..f6951eddb0b8 100644
--- a/sc/source/filter/xml/xmlfonte.cxx
+++ b/sc/source/filter/xml/xmlfonte.cxx
@@ -59,7 +59,9 @@ void ScXMLFontAutoStylePool_Impl::AddFontItems(const sal_uInt16* pWhichIds, sal_
pFont->GetFamily(), pFont->GetPitch(),
pFont->GetCharSet() );
}
- for (const SfxPoolItem* pItem : pItemPool->GetItemSurrogates( nWhichId ))
+ ItemSurrogates aSurrogates;
+ pItemPool->GetItemSurrogates( aSurrogates, nWhichId );
+ for (const SfxPoolItem* pItem : aSurrogates)
{
const SvxFontItem *pFont(static_cast<const SvxFontItem *>(pItem));
Add( pFont->GetFamilyName(), pFont->GetStyleName(),
@@ -111,7 +113,9 @@ ScXMLFontAutoStylePool_Impl::ScXMLFontAutoStylePool_Impl(ScXMLExport& rExportP,
for (sal_uInt16 nPageWhichId : aPageWhichIds)
{
- for (const SfxPoolItem* pItem : rPagePool.GetItemSurrogates( nPageWhichId ))
+ ItemSurrogates aSurrogates;
+ rPagePool.GetItemSurrogates( aSurrogates, nPageWhichId );
+ for (const SfxPoolItem* pItem : aSurrogates)
{
const ScPageHFItem* pPageItem = static_cast<const ScPageHFItem*>(pItem);
const EditTextObject* pLeftArea(pPageItem->GetLeftArea());