diff options
author | Justin Luth <justin.luth@collabora.com> | 2018-09-29 14:38:31 +0300 |
---|---|---|
committer | Miklos Vajna <vmiklos@collabora.co.uk> | 2018-10-11 09:48:03 +0200 |
commit | 048b8e45813f6a19a4ff56e1d676fe9450325cd2 (patch) | |
tree | 473a10bbf7f559afae949060a131046dc1c4ce6a | |
parent | 0f26c6ddda31221364b011a0b89286ecea303d89 (diff) |
tdf#111980 oox optionbutton autoGroup inside GroupBox
The area of a GroupBox indicates which radio buttons
are considered to be part of the same group. The
button needs to be fully inside of the groupbox
in order to participate. This patch resolves the last
worry of commit 9f969799629fe6bdf8b922d8cb922846aa646ece
Change-Id: Ie6057337c63bf9eb173a0615e30c8d4e4d0c7a19
Reviewed-on: https://gerrit.libreoffice.org/61131
Tested-by: Jenkins
Reviewed-by: Justin Luth <justin_luth@sil.org>
Reviewed-by: Miklos Vajna <vmiklos@collabora.co.uk>
-rw-r--r-- | oox/source/ole/axcontrol.cxx | 9 | ||||
-rw-r--r-- | oox/source/vml/vmldrawing.cxx | 55 | ||||
-rw-r--r-- | sc/qa/unit/subsequent_filters-test.cxx | 27 | ||||
-rw-r--r-- | sc/source/filter/oox/drawingfragment.cxx | 3 |
4 files changed, 86 insertions, 8 deletions
diff --git a/oox/source/ole/axcontrol.cxx b/oox/source/ole/axcontrol.cxx index 350fe0e315f9..563cf06e5a54 100644 --- a/oox/source/ole/axcontrol.cxx +++ b/oox/source/ole/axcontrol.cxx @@ -1555,13 +1555,8 @@ void AxMorphDataModelBase::convertProperties( PropertyMap& rPropMap, const Contr rConv.convertColor( rPropMap, PROP_TextColor, mnTextColor ); if ( mnDisplayStyle == AX_DISPLAYSTYLE_OPTBUTTON ) { - // Form Radio Controls (non-ActiveX) have no group name, but autoGroup - // with their group box, or frame, or sheet, or document. - // So ensure that SOME name is given for a group name - // TODO: ActiveX controls without a Group name shouldn't autogroup - // with non-ActiveX option buttons. - // TODO: each application should test if control's area is fully inside - // a GroupBox, and give those a separate group name. + // If unspecified, radio buttons autoGroup in the same document/sheet + // NOTE: form controls should not autoGroup with ActiveX controls - see drawingfragment.cxx OUString sGroupName = !maGroupName.isEmpty() ? maGroupName : "autoGroup_"; rPropMap.setProperty( PROP_GroupName, sGroupName ); } diff --git a/oox/source/vml/vmldrawing.cxx b/oox/source/vml/vmldrawing.cxx index ab2a9f8a42d5..0d5698eab0c9 100644 --- a/oox/source/vml/vmldrawing.cxx +++ b/oox/source/vml/vmldrawing.cxx @@ -35,6 +35,8 @@ #include <oox/ole/axcontrol.hxx> #include <oox/vml/vmlshape.hxx> #include <oox/vml/vmlshapecontainer.hxx> +#include <tools/diagnose_ex.h> +#include <tools/gen.hxx> namespace oox { namespace vml { @@ -146,6 +148,59 @@ void Drawing::convertAndInsert() const { Reference< XShapes > xShapes( mxDrawPage, UNO_QUERY ); mxShapes->convertAndInsert( xShapes ); + + // Group together form control radio buttons that are in the same groupBox + std::map<OUString, tools::Rectangle> GroupBoxMap; + std::map<Reference< XPropertySet >, tools::Rectangle> RadioButtonMap; + for ( sal_Int32 i = 0; i < xShapes->getCount(); ++i ) + { + try + { + Reference< XControlShape > xCtrlShape( xShapes->getByIndex(i), UNO_QUERY_THROW ); + Reference< XControlModel > xCtrlModel( xCtrlShape->getControl(), UNO_SET_THROW ); + Reference< XServiceInfo > xModelSI (xCtrlModel, UNO_QUERY_THROW ); + Reference< XPropertySet > aProps( xCtrlModel, UNO_QUERY_THROW ); + + OUString sName; + aProps->getPropertyValue("Name") >>= sName; + const ::Point aPoint( xCtrlShape->getPosition().X, xCtrlShape->getPosition().Y ); + const ::Size aSize( xCtrlShape->getSize().Width, xCtrlShape->getSize().Height ); + const tools::Rectangle aRect( aPoint, aSize ); + if ( !sName.isEmpty() + && xModelSI->supportsService("com.sun.star.awt.UnoControlGroupBoxModel") ) + { + GroupBoxMap[sName] = aRect; + } + else if ( xModelSI->supportsService("com.sun.star.awt.UnoControlRadioButtonModel") ) + { + OUString sGroupName; + aProps->getPropertyValue("GroupName") >>= sGroupName; + // only Form Controls are affected by Group Boxes - see drawingfragment.cxx + if ( sGroupName == "autoGroup_formControl" ) + RadioButtonMap[aProps] = aRect; + } + } + catch (uno::Exception&) + { + DBG_UNHANDLED_EXCEPTION("oox.vml"); + } + } + for ( auto& BoxItr : GroupBoxMap ) + { + const uno::Any aGroup( OUString("autoGroup_").concat(BoxItr.first) ); + for ( auto RadioItr = RadioButtonMap.begin(); RadioItr != RadioButtonMap.end(); ) + { + if ( BoxItr.second.IsInside(RadioItr->second) ) + { + RadioItr->first->setPropertyValue("GroupName", aGroup ); + // If conflict, first created GroupBox wins + RadioButtonMap.erase( RadioItr++ ); + } + else + RadioItr++; + } + } + } sal_Int32 Drawing::getLocalShapeIndex( const OUString& rShapeId ) const diff --git a/sc/qa/unit/subsequent_filters-test.cxx b/sc/qa/unit/subsequent_filters-test.cxx index 188a957f5440..f06aca38ecf5 100644 --- a/sc/qa/unit/subsequent_filters-test.cxx +++ b/sc/qa/unit/subsequent_filters-test.cxx @@ -1724,6 +1724,33 @@ void ScFiltersTest::testActiveXOptionButtonGroup() CPPUNIT_ASSERT_EQUAL( sGroupName4, sGroupName5 ); CPPUNIT_ASSERT( sGroupName2 != sGroupName5 ); CPPUNIT_ASSERT( sGroupName != sGroupName5 ); + + OUString sGroupName7; //Form radiobutton autogrouped by GroupBox + xControlShape.set(xIA_DrawPage->getByIndex(7), uno::UNO_QUERY_THROW); + xPropertySet.set(xControlShape->getControl(), uno::UNO_QUERY_THROW); + xPropertySet->getPropertyValue("GroupName") >>= sGroupName7; + CPPUNIT_ASSERT_EQUAL( OUString("autoGroup_Group Box 7"), sGroupName7 ); + + OUString sGroupName8; + xControlShape.set(xIA_DrawPage->getByIndex(8), uno::UNO_QUERY_THROW); + xPropertySet.set(xControlShape->getControl(), uno::UNO_QUERY_THROW); + xPropertySet->getPropertyValue("GroupName") >>= sGroupName8; + CPPUNIT_ASSERT_EQUAL( sGroupName7, sGroupName8 ); + CPPUNIT_ASSERT( sGroupName4 != sGroupName8 ); + CPPUNIT_ASSERT( sGroupName2 != sGroupName8 ); + CPPUNIT_ASSERT( sGroupName != sGroupName8 ); + + OUString sGroupName9; //Form radiobutton not fully inside GroupBox + xControlShape.set(xIA_DrawPage->getByIndex(9), uno::UNO_QUERY_THROW); + xPropertySet.set(xControlShape->getControl(), uno::UNO_QUERY_THROW); + xPropertySet->getPropertyValue("GroupName") >>= sGroupName9; + CPPUNIT_ASSERT_EQUAL( sGroupName4, sGroupName9 ); + + OUString sGroupName10; //ActiveX unaffected by GroupBox + xControlShape.set(xIA_DrawPage->getByIndex(10), uno::UNO_QUERY_THROW); + xPropertySet.set(xControlShape->getControl(), uno::UNO_QUERY_THROW); + xPropertySet->getPropertyValue("GroupName") >>= sGroupName10; + CPPUNIT_ASSERT_EQUAL( sGroupName, sGroupName10 ); } void ScFiltersTest::testChartImportODS() diff --git a/sc/source/filter/oox/drawingfragment.cxx b/sc/source/filter/oox/drawingfragment.cxx index 47346ca81191..b091318bed45 100644 --- a/sc/source/filter/oox/drawingfragment.cxx +++ b/sc/source/filter/oox/drawingfragment.cxx @@ -536,7 +536,8 @@ Reference< XShape > VmlDrawing::createAndInsertClientXShape( const ::oox::vml::S case XML_Radio: { AxOptionButtonModel& rAxModel = aControl.createModel< AxOptionButtonModel >(); - // unique name to prevent autoGrouping with ActiveX controls. + + // unique name to prevent autoGrouping with ActiveX controls and which a GroupBox may override - see vmldrawing.cxx. rAxModel.maGroupName = "autoGroup_formControl"; convertControlText( rAxModel.maFontData, rAxModel.mnTextColor, rAxModel.maCaption, pTextBox, pClientData->mnTextHAlign ); convertControlBackground( rAxModel, rShape ); |