CalcFunctionsList/it

Tutte le modifiche apportate al codice sorgente originale di OpenOffice.org elencate in questa pagina sono:


 * '''Sotto Licenza LGPL V3 ( and you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation)
 * Copyright Eric Bachard 3 Settembre 2009

Modulo : sc
sc/source/ui/scfuncs.src :  E' il contenitore della lista completa delle funzioni esistenti. E'presente anche una ExtraData field (0 per visible, 1 per nascosto), L'ho utilizzitao finora per nascondere le funzioni che non voglio appaiano nella lista.

Ma non è semplice implementare un meccanismo che crei la differenza tra chi è alle prime armi e via su di livello.. così ho preferito chiedere ad Eike Rathke (uno dei principali sviluppatori di Calc) quale fosse il miglior metodo per ottenere questo risultato. Eike con estrema cortesia mi ha risposto di cambiare il tipo d'approccio e vedere il problema sotto altra prospettiva.

The enumeration, is RID_SC_FUNCTION_DESCRIPTIONS1, and it is called at runtime in global.cxx, more precisely in sc/source/core/data/global.cxx ScFunctionList::ScFunctionList if (bSuppressed) ...

The choice who has been made is :

re-use the static getUserLevel

If expert -> do nothing

If Beginner -> for every ressource, compare the Id with the one in the list "Beginner". If not listed-> delete If Average -> for every ressource, compare the Id with the one in the list "Average". If not listed-> delete

The idea is: in the !bSuppressed case, check for the prefs, to know whether the function currently checked is visible or not

TODO : define a list of the functions we'll have in the 3 levels.

First, include the right headers, for retrieving the value in the Common.xcu

Index: sc/source/core/data/global.cxx

=
====================================================== --- sc/source/core/data/global.cxx	(revision 275641) +++ sc/source/core/data/global.cxx	(working copy) @@ -70,6 +70,7 @@ + @@ -91,13 +92,27 @@ +#ifdef OOo4Kids +#include "vcl/unohelp.hxx" +#include  +#include  +#include  +#include  +#include  + // ---
 * 1) include 
 * 2) include 
 * 1) include "global.hxx"
 * 2) include "scresid.hxx"
 * 3) include "autoform.hxx"
 * 1) include "scmod.hxx"
 * 2) include "appoptio.hxx"

Define the constants, to improve the readability

+#define SC_USER_LEVEL_BEGINNER     1 +#define SC_USER_LEVEL_AVERAGE      2 +#define SC_USER_LEVEL_EXPERT       3 +#endif + + ScDocShellRef*	ScGlobal::pDrawClipDocShellRef = NULL; SvxSearchItem*	ScGlobal::pSearchItem = NULL; ScAutoFormat*	ScGlobal::pAutoFormat = NULL;
 * 1) define CLIPST_AVAILABLE	0
 * 2) define CLIPST_CAPTURED		1
 * 3) define CLIPST_DELETE		2
 * 4) define CLIPST_DRAW			3

'''Use the right namespace. Comments below give what is concerned.'''

@@ -147,6 +162,75 @@ static USHORT nPPTZoom = 0;		// ScreenZoom used to determine nScreenPPTX/Y +#ifdef OOo4Kids +using namespace ::com::sun::star::uno; // Reference +using namespace ::com::sun::star::lang; // XMultiServiceFactory +using namespace ::com::sun::star::beans; // PropertyValue +using namespace ::com::sun::star::container; // XNameAccess +using ::rtl::OUString;

Below, some helpers ( for readability )

+ +static const OUString sULConfigSrvc( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.configuration.ConfigurationProvider" ) ); +static const OUString sULAccessSrvc( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.configuration.ConfigurationUpdateAccess" ) );

The getUserLevel (the same as the one used in the svx part

+ +static short getUserLevel +{ +   short dUserLevel = 1; // default is beginner +   try +   { +	// get service provider +       Reference< XMultiServiceFactory > xSMgr( vcl::unohelper::GetMultiServiceFactory ); +       // create configuration hierachical access name +       if( xSMgr.is ) +	{ +	   try +           { +                Reference< XMultiServiceFactory > xConfigProvider( +                    Reference< XMultiServiceFactory >( +                       xSMgr->createInstance( sULConfigSrvc ), +                       UNO_QUERY ) +                    ); +               if( xConfigProvider.is ) +               { +                    Sequence< Any > aArgs(1); +                   PropertyValue aVal; +                   aVal.Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "nodepath" ) ); +                   aVal.Value <<= OUString( RTL_CONSTASCII_USTRINGPARAM( "/org.openoffice.Office.Common/Misc" ) ); +                   aArgs.getArray[0] <<= aVal; +                   Reference< XNameAccess > xConfigAccess( +                        Reference< XNameAccess >( +                           xConfigProvider->createInstanceWithArguments( sULAccessSrvc, aArgs ), UNO_QUERY ) +                        ); +                   if( xConfigAccess.is ) +                   { +                        try +                       { +                            short bValue = 1; +                           Any aAny = xConfigAccess->getByName( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "UserLevel" ) ) ); +                           if( aAny >>= bValue ) +                               dUserLevel = bValue; +                       } +                        catch( NoSuchElementException& ) +                       { +                        } +                        catch( WrappedTargetException& ) +                       { +                        } +                    } +                } +            } +            catch( Exception& ) +           { +            } +        } +    } +    catch( WrappedTargetException& ) +   { +    } +    return dUserLevel; +} +#endif +

Then we add our code in ScFuncUtil constructor 

+ // ... oder so? BOOL bOderSo; @@ -1250,6 +1334,9 @@ 	ScFuncDesc*		pDesc	= NULL; xub_StrLen		nStrLen = 0; FuncCollection*	pFuncColl; +#ifdef OOo4Kids +   short   nLevel = getUserLevel; +#endif USHORT i,j; USHORT nDescBlock[] = {

'''As announced, the algorithm is :
 * If expert -> do nothing
 * If Beginner -> for every ressource, compare the Id with the one in the list "Beginner". If not listed-> delete
 * If Average -> for every ressource, compare the Id with the one in the list "Average". If not listed-> delete '''

@@ -1277,10 +1364,71 @@ 				pDesc = new ScFuncDesc; bool bSuppressed = false; ScFuncRes aSubRes( aRes, pDesc, bSuppressed); +#ifdef OOo4Kids +               bool bIsNotForThisLevel = false; + +               if ( nLevel != SC_USER_LEVEL_EXPERT ) +               { +                    if ( SC_USER_LEVEL_BEGINNER == nLevel ) +                   { +                        switch ( aRes.GetId ) +                       { +                            // FIXME : define the right list for Beginner +                           case SC_OPCODE_RANDOM: +                           case SC_OPCODE_MAX: +                           case SC_OPCODE_MIN: +                           case SC_OPCODE_AVERAGE: +                           case SC_OPCODE_PI: +                           case SC_OPCODE_MOD: +                           case SC_OPCODE_SUM: +                           case SC_OPCODE_PRODUCT: +                               break; +                           default: +                               bIsNotForThisLevel = true; +                               break; +                       } +                    } +                    else if (  SC_USER_LEVEL_AVERAGE == nLevel ) +                   { +                        switch ( aRes.GetId ) +                       { +                            // FIXME : define the right list for Average +                           case SC_OPCODE_RANDOM: +                           case SC_OPCODE_MAX: +                           case SC_OPCODE_MIN: +                           case SC_OPCODE_AVERAGE: +                           case SC_OPCODE_PI: +                           case SC_OPCODE_MOD: +                           case SC_OPCODE_SUM: +                           case SC_OPCODE_PRODUCT: +                           case SC_OPCODE_SIN: +                           case SC_OPCODE_COS: +                           case SC_OPCODE_DEG: +                           case SC_OPCODE_RAD: +                           case SC_OPCODE_ABS: +                           case SC_OPCODE_SQRT: +                           case SC_OPCODE_NOT: +                           case SC_OPCODE_AND: +                           case SC_OPCODE_OR: +                           case SC_OPCODE_PLUS_MINUS: +                           case SC_OPCODE_GGT: +                           case SC_OPCODE_KGV: +                           case SC_OPCODE_POWER: +                               break; +                           default: +                               bIsNotForThisLevel = true; +                               break; +                       } +                    } +                } +                 // Instead of dealing with this exceptional case at 1001 places // we simply don't add an entirely suppressed function to the // list and delete it. -               if (bSuppressed) +               if ( bSuppressed || bIsNotForThisLevel ) +#else +               if ( bSuppressed ) +#endif delete pDesc; else {

Important : do not forget to remove sc addins, excepted in export mode

@@ -1387,10 +1538,14 @@ 	//	StarOne AddIns -	ScUnoAddInCollection* pUnoAddIns = ScGlobal::GetAddInCollection; -	long nUnoCount = pUnoAddIns->GetFuncCount; -	for (long nFunc=0; nFuncGetFuncCount; +	   for (long nFunc=0; nFuncnFIndex = nNextId++; @@ -1403,7 +1558,10 @@ 		} 		else delete pDesc; +	   } +#ifdef OOo4Kids } +#endif }

FIXED, see below : cannot be changed without restart OOo, probably because the list is cached and not deleted (even when closing the doc ?)

The trick was to reset the function list when the box is closed. The next time it will be used, the UserLevel is read, and if it is different, a new function list is filled. Tested working OK

ScFunctionList* ScGlobal::GetStarCalcFunctionList {       ResetFunctionList; if ( !pStarCalcFunctionList ) pStarCalcFunctionList = new	ScFunctionList;
 * 1) ifdef OOo4Kids
 * 1) else
 * 1) endif

return pStarCalcFunctionList; }