1*cdf0e10cSrcweir #include <vbalistcontrolhelper.hxx>
2*cdf0e10cSrcweir #include <vector>
3*cdf0e10cSrcweir 
4*cdf0e10cSrcweir using namespace com::sun::star;
5*cdf0e10cSrcweir using namespace ooo::vba;
6*cdf0e10cSrcweir 
7*cdf0e10cSrcweir const static rtl::OUString ITEMS( RTL_CONSTASCII_USTRINGPARAM("StringItemList") );
8*cdf0e10cSrcweir 
9*cdf0e10cSrcweir void SAL_CALL
10*cdf0e10cSrcweir ListControlHelper::AddItem( const uno::Any& pvargItem, const uno::Any& pvargIndex ) throw (uno::RuntimeException)
11*cdf0e10cSrcweir {
12*cdf0e10cSrcweir 	if ( pvargItem.hasValue()  )
13*cdf0e10cSrcweir 	{
14*cdf0e10cSrcweir 		uno::Sequence< rtl::OUString > sList;
15*cdf0e10cSrcweir 		m_xProps->getPropertyValue( ITEMS ) >>= sList;
16*cdf0e10cSrcweir 
17*cdf0e10cSrcweir 		sal_Int32 nIndex = sList.getLength();
18*cdf0e10cSrcweir 
19*cdf0e10cSrcweir 		if ( pvargIndex.hasValue() )
20*cdf0e10cSrcweir 			pvargIndex >>= nIndex;
21*cdf0e10cSrcweir 
22*cdf0e10cSrcweir 		rtl::OUString sString = getAnyAsString( pvargItem );
23*cdf0e10cSrcweir 
24*cdf0e10cSrcweir 		// if no index specified or item is to be appended to end of
25*cdf0e10cSrcweir 		// list just realloc the array and set the last item
26*cdf0e10cSrcweir 		if ( nIndex  == sList.getLength() )
27*cdf0e10cSrcweir 		{
28*cdf0e10cSrcweir 			sal_Int32 nOldSize = sList.getLength();
29*cdf0e10cSrcweir 			sList.realloc( nOldSize + 1 );
30*cdf0e10cSrcweir 			sList[ nOldSize ] = sString;
31*cdf0e10cSrcweir 		}
32*cdf0e10cSrcweir 		else
33*cdf0e10cSrcweir 		{
34*cdf0e10cSrcweir 			// just copy those elements above the one to be inserted
35*cdf0e10cSrcweir 			std::vector< rtl::OUString > sVec;
36*cdf0e10cSrcweir 			// reserve just the amount we need to copy
37*cdf0e10cSrcweir 			sVec.reserve( sList.getLength() - nIndex );
38*cdf0e10cSrcweir 
39*cdf0e10cSrcweir 			// point at first element to copy
40*cdf0e10cSrcweir 			rtl::OUString* pString = sList.getArray() + nIndex;
41*cdf0e10cSrcweir 			const rtl::OUString* pEndString = sList.getArray() + sList.getLength();
42*cdf0e10cSrcweir 			// insert the new element
43*cdf0e10cSrcweir 			sVec.push_back( sString );
44*cdf0e10cSrcweir 			// copy elements
45*cdf0e10cSrcweir 			for ( ; pString != pEndString; ++pString )
46*cdf0e10cSrcweir 				sVec.push_back( *pString );
47*cdf0e10cSrcweir 
48*cdf0e10cSrcweir 			sList.realloc(  sList.getLength() + 1 );
49*cdf0e10cSrcweir 
50*cdf0e10cSrcweir 			// point at first element to be overwritten
51*cdf0e10cSrcweir 			pString = sList.getArray() + nIndex;
52*cdf0e10cSrcweir 			pEndString = sList.getArray() + sList.getLength();
53*cdf0e10cSrcweir 			std::vector< rtl::OUString >::iterator it = sVec.begin();
54*cdf0e10cSrcweir 			for ( ; pString != pEndString; ++pString, ++it)
55*cdf0e10cSrcweir 				*pString = *it;
56*cdf0e10cSrcweir 			//
57*cdf0e10cSrcweir 		}
58*cdf0e10cSrcweir 
59*cdf0e10cSrcweir 		m_xProps->setPropertyValue( ITEMS, uno::makeAny( sList ) );
60*cdf0e10cSrcweir 
61*cdf0e10cSrcweir 	}
62*cdf0e10cSrcweir }
63*cdf0e10cSrcweir 
64*cdf0e10cSrcweir void SAL_CALL
65*cdf0e10cSrcweir ListControlHelper::removeItem( const uno::Any& index ) throw (uno::RuntimeException)
66*cdf0e10cSrcweir {
67*cdf0e10cSrcweir     sal_Int32 nIndex = 0;
68*cdf0e10cSrcweir     // for int index
69*cdf0e10cSrcweir 	if ( index >>= nIndex  )
70*cdf0e10cSrcweir 	{
71*cdf0e10cSrcweir 		uno::Sequence< rtl::OUString > sList;
72*cdf0e10cSrcweir 		m_xProps->getPropertyValue( ITEMS ) >>= sList;
73*cdf0e10cSrcweir         if( nIndex < 0 || nIndex > ( sList.getLength() - 1 ) )
74*cdf0e10cSrcweir             throw uno::RuntimeException( rtl::OUString::createFromAscii( "Invalid index" ), uno::Reference< uno::XInterface > () );
75*cdf0e10cSrcweir         if( sList.hasElements() )
76*cdf0e10cSrcweir         {
77*cdf0e10cSrcweir             if( sList.getLength() == 1 )
78*cdf0e10cSrcweir             {
79*cdf0e10cSrcweir                 Clear();
80*cdf0e10cSrcweir                 return;
81*cdf0e10cSrcweir             }
82*cdf0e10cSrcweir             for( sal_Int32 i = nIndex; i < ( sList.getLength()-1 ); i++ )
83*cdf0e10cSrcweir             {
84*cdf0e10cSrcweir                 sList[i] = sList[i+1];
85*cdf0e10cSrcweir             }
86*cdf0e10cSrcweir 			sList.realloc(  sList.getLength() - 1 );
87*cdf0e10cSrcweir 		}
88*cdf0e10cSrcweir 
89*cdf0e10cSrcweir 		m_xProps->setPropertyValue( ITEMS, uno::makeAny( sList ) );
90*cdf0e10cSrcweir 	}
91*cdf0e10cSrcweir }
92*cdf0e10cSrcweir 
93*cdf0e10cSrcweir void SAL_CALL
94*cdf0e10cSrcweir ListControlHelper::Clear(  ) throw (uno::RuntimeException)
95*cdf0e10cSrcweir {
96*cdf0e10cSrcweir 	// urk, setValue doesn't seem to work !!
97*cdf0e10cSrcweir 	//setValue( uno::makeAny( sal_Int16() ) );
98*cdf0e10cSrcweir 	m_xProps->setPropertyValue( ITEMS, uno::makeAny( uno::Sequence< rtl::OUString >() ) );
99*cdf0e10cSrcweir }
100*cdf0e10cSrcweir 
101*cdf0e10cSrcweir void SAL_CALL
102*cdf0e10cSrcweir ListControlHelper::setRowSource( const rtl::OUString& _rowsource ) throw (uno::RuntimeException)
103*cdf0e10cSrcweir {
104*cdf0e10cSrcweir 	if ( _rowsource.getLength() == 0 )
105*cdf0e10cSrcweir 		Clear();
106*cdf0e10cSrcweir }
107*cdf0e10cSrcweir 
108*cdf0e10cSrcweir sal_Int32 SAL_CALL
109*cdf0e10cSrcweir ListControlHelper::getListCount() throw (uno::RuntimeException)
110*cdf0e10cSrcweir {
111*cdf0e10cSrcweir     uno::Sequence< rtl::OUString > sList;
112*cdf0e10cSrcweir     m_xProps->getPropertyValue( ITEMS ) >>= sList;
113*cdf0e10cSrcweir     return sList.getLength();
114*cdf0e10cSrcweir }
115*cdf0e10cSrcweir 
116*cdf0e10cSrcweir uno::Any SAL_CALL
117*cdf0e10cSrcweir ListControlHelper::List( const ::uno::Any& pvargIndex, const uno::Any& pvarColumn ) throw (uno::RuntimeException)
118*cdf0e10cSrcweir {
119*cdf0e10cSrcweir     uno::Sequence< rtl::OUString > sList;
120*cdf0e10cSrcweir     m_xProps->getPropertyValue( ITEMS ) >>= sList;
121*cdf0e10cSrcweir     sal_Int16 nLength = static_cast< sal_Int16 >( sList.getLength() );
122*cdf0e10cSrcweir     uno::Any aRet;
123*cdf0e10cSrcweir     if ( pvargIndex.hasValue() )
124*cdf0e10cSrcweir     {
125*cdf0e10cSrcweir         sal_Int16 nIndex = -1;
126*cdf0e10cSrcweir         pvargIndex >>= nIndex;
127*cdf0e10cSrcweir         if( nIndex < 0 || nIndex >= nLength )
128*cdf0e10cSrcweir             throw uno::RuntimeException( rtl::OUString::createFromAscii(
129*cdf0e10cSrcweir                     "Bad row Index" ), uno::Reference< uno::XInterface >() );
130*cdf0e10cSrcweir         aRet <<= sList[ nIndex ];
131*cdf0e10cSrcweir     }
132*cdf0e10cSrcweir     else if ( pvarColumn.hasValue() ) // pvarColumn on its own would be bad
133*cdf0e10cSrcweir             throw uno::RuntimeException( rtl::OUString::createFromAscii(
134*cdf0e10cSrcweir                     "Bad column Index" ), uno::Reference< uno::XInterface >() );
135*cdf0e10cSrcweir     else // List() ( e.g. no args )
136*cdf0e10cSrcweir     {
137*cdf0e10cSrcweir         uno::Sequence< uno::Sequence< rtl::OUString > > sReturnArray( nLength );
138*cdf0e10cSrcweir         for ( sal_Int32 i = 0; i < nLength; ++i )
139*cdf0e10cSrcweir         {
140*cdf0e10cSrcweir             sReturnArray[ i ].realloc( 10 );
141*cdf0e10cSrcweir             sReturnArray[ i ][ 0 ] = sList[ i ];
142*cdf0e10cSrcweir         }
143*cdf0e10cSrcweir         aRet = uno::makeAny( sReturnArray );
144*cdf0e10cSrcweir     }
145*cdf0e10cSrcweir     return aRet;
146*cdf0e10cSrcweir }
147