OpenOffice.org Forum at OOoForum.orgThe OpenOffice.org Forum
 
 [Home]   [FAQ]   [Search]   [Memberlist]   [Usergroups]   [Register
 [Profile]   [Log in to check your private messages]   [Log in

Addin with GUI

 
Post new topic   Reply to topic    OOoForum.org Forum Index -> OpenOffice.org Calc
View previous topic :: View next topic  
Author Message
beiwen
Guest





PostPosted: Mon Apr 05, 2004 12:02 am    Post subject: Addin with GUI Reply with quote

Hi,

I am trying to implement an add-in that adds functions to Calc and additionally adds a menu to the office bar, that can be used to call dialogs on the add-in. So far I was able to create a uno component that dows the GUI-stuff and an add-in to create the functions. However I don't know how to bring those two solutions together.

Any help is very much appreciated

Kind Regards
Back to top
DannyB
Moderator
Moderator


Joined: 02 Apr 2003
Posts: 4021
Location: Lawrence, Kansas, USA

PostPosted: Mon Apr 05, 2004 7:13 am    Post subject: Reply with quote

If you've done that much, then you've done a lot already!

I'm not exactly sure what you're asking. Maybe you could provide additional information.

What language did you write your new Calc functions in?

Are you adding menus by altering the configuration manager via. the API?

What I would recommend is packaging your entire solution into a package that is deployed with pkgchk.

At first I didn't like pkgchk. But now I have changed my mind. Here is how an end user deploys a package....
1. Make sure OOo is not running.
2. Copy package file into the OOo\user\uno_packages folder.
3. Run the command... OOo\program\pkgchk.exe

An administrator can install the package for all users by....
1. Make sure OOo is not running.
2. Copy package file into the OOo\share\uno_packages folder.
3. Run the command... OOo\program\pkgchk -s

Uninstalling the component is similarly easy. Just remove your package from the folder in step 2, and then do step 3. Package is removed from OOo.

Step 3 can be done by simply double clicking on the pkgchk program, even though it is a command line tool. It does the right thing. If anything goes wrong, you can always look at the
OOo\user-or-share\uno_packages\cache\log.txt
file to see what went wrong.

Maybe I misunderstand your question?

The OOo developers really need to provide a simple GUI-fied version of pkgchk which can be double clicked by a user, which runs pkgchk, and then confirms to the user that it was installed/removed successfully -- or displays the OOo\user-or-share\uno_packages\cache\log.txt to show what went wrong. Such a gui front end to pkgchk would be analogous to the gui program OOo\program\jvmsetup that is already part of OOo.
_________________
Want to make OOo Drawings like the colored flower design to the left?
Back to top
View user's profile Send private message
beiwen
Guest





PostPosted: Mon Apr 05, 2004 11:01 am    Post subject: Addin with GUI Reply with quote

Thank you for the message. I have seen a lot of postings from you already and I think you have a very profound knowledge of OO.

I try to be more specific what my problem is:

I have written an addin in java. It adds a function to Calc. I can test that function in Calc and it behaves as expected. The addin is a package. I do deploy it with pkgchk - it gets unzipped into the cache directory and everything is just fine.

However, I can only use the function in Calc, when I type it into a cell. I so see some GUI when I use the function pilot. There I can see explanations of my parameters. All very neat but I need a way to call up a dialog, where I can adjust properties/preferences for my addin (i.e global properties, like defaults). I would like to have a menu item in the officebar, where I can call up a dialog to adjust these values for my addin. I haven't found a way to let my addin respond to menuitem-commands. I can add the menu and menuitems using xcu files. I have also implemented the interfaces XDispatchProvider and XDispatch. However, my dispatch-method gets never called.

I hope it's somewhat clearer what I try to achive.

Kind regards
Benno
Back to top
DannyB
Moderator
Moderator


Joined: 02 Apr 2003
Posts: 4021
Location: Lawrence, Kansas, USA

PostPosted: Mon Apr 05, 2004 1:23 pm    Post subject: Reply with quote

beiwen wrote:
I have seen a lot of postings from you already and I think you have a very profound knowledge of OO.


Thanks. But don't be fooled. I don't have any magic insight. It helps that I have been programming for 25 years. It helps that I have spent more than a year now studying the OOo API and conducting countless experiments using simple Basic programs.

Other people have been doing the same thing. Some even longer than I. Andrew Pitonyak's macro document for example, demonstrates a significant effort to study OOo programming for a long period of time. Andrew's macro document existed in some form in my early days of learning OOo last year.

Others here, like dfrench, are more expert than I in particular modules of OOo, such as Calc or Writer. My interest is Draw (and Impress).

If you've written a java component with calc add in functions, then you've jumped numerous hurdles, the same ones I've learned in the last year. You may just be impressed because I spend a lot of time answering questions and posting example code. That's probably just because I am passionate about OOo and seeing it succeed.

Mostly, I spend a lot of time playing with OOo. I have no commercial interest or motive. To me, OOo is a really cool toy that I have not yet become bored with.


beiwen wrote:
I have written an addin in java. ....


Here is how I read your more elaborate description.

Your addin does describe all aspects of the function, its parameters, help strings, etc. Therefore, the function seems to truly fit into Calc, including the function autopilot.

You want your function to have some additional "configuration parameters" which are not parameters to the function.

For instance, if the function were called....

AddMyConstant( x )

then if I passed 5 for x, some magic configurable constant would be added to x (i.e. 5) and the result returned. You want to be able to go to the menu, bring up a dialog box, and tweak the constant that AddMyConstant adds to its parameter. If I go to the menu, bring up the custom dialog, and change the constant to 3, then AddMyConstant( x ) behaves as if it were "AddThree( x )".

If this is the correct interpretation, then here is what I would do....

Think of your add in as three distinct parts.
1. Some new configuration data, using your own custom schema.
2. The calc function addin, which accesses your custom configuration data and uses it in evaluating the function.
3. A component that brings up a dialog box and edits the custom configuration data. A menu command is added to the office which displays this dialog component.

Do you know how to access the Configuration Manager API?

The Configuration Manager edits the XCU files in OOo.

What is allowed into the XCU files is defined by the XCS files.

Simply put an XCU and an XCS file into your package, and pkgchk will property install it.

Here is an example custom configuration schema that I use.
DannyExample.xcs
Code:
<?xml version='1.0' encoding='UTF-8'?>

<oor:component-schema oor:name="DannyExample" oor:package="nom.DannyBrewer.Example" xml:lang="en-US" xmlns:oor="http://openoffice.org/2001/registry" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
   <templates>
      <group oor:name="DannysSetting">
         <prop oor:name="Setting" oor:type="xs:string"/>
         <set oor:name="SubSettings" oor:node-type="DannysSetting"/>
      </group>
   </templates>
   <component>
      <group oor:name="DannysConfig">
         <set oor:name="Settings" oor:node-type="DannysSetting"/>
      </group>
   </component>
</oor:component-schema>


Here is an example XCU file that stores data according to the above specification.
DannyExample.xcu
Code:
<?xml version="1.0" encoding="UTF-8"?>
<oor:component-data xmlns:oor="http://openoffice.org/2001/registry" xmlns:xs="http://www.w3.org/2001/XMLSchema" oor:name="DannyExample" oor:package="nom.DannyBrewer.Example">
 <node oor:name="DannysConfig">
  <node oor:name="Settings">

   <node oor:name="my.location" oor:op="replace">
    <prop oor:name="Setting" oor:type="xs:string">
     <value>%origin%</value>
    </prop>
   </node>

   <node oor:name="my.thing1" oor:op="replace">
    <prop oor:name="Setting" oor:type="xs:string">
     <value>Thing1</value>
    </prop>
   </node>
   <node oor:name="my.thing2" oor:op="replace">
    <prop oor:name="Setting" oor:type="xs:string">
     <value>Thing2</value>
    </prop>
    <node oor:name="SubSettings">
     <node oor:name="sub1" oor:op="replace">
      <prop oor:name="Setting" oor:type="xs:string">
       <value>sub setting 1</value>
      </prop>
     </node>
     <node oor:name="sub2" oor:op="replace">
      <prop oor:name="Setting" oor:type="xs:string">
       <value>sub setting 2</value>
      </prop>
     </node>
    </node>
   </node>
  </node>
 </node>
</oor:component-data>


PkgChk will install both of these files. Because of the oor:package property, pkgchk will create a folder called "nom" containing a folder called "DannyBrewer" containing a folder called "Example" containing a file called "DannyExample.xcs" and "DannyExample.xcu".

Now using the Configuration Manager API, you can access the DannysConfig node like this....

Code:
Function GetMyLocation()
   oConfigAccess = GetConfigAccess( "/nom.DannyBrewer.Example.DannyExample/DannysConfig" )

   oElement = oConfigAccess.getByName( "Settings" )
   
   if Not oElement.hasByName( "my.thing1" ) Then
      MsgBox "my.thing1 not defined"
   EndIf

   if Not oElement.hasByName( "my.location" ) Then
      MsgBox "my.location not defined"
      Exit Function
   EndIf
   
   oLocation = oElement.getByName( "my.location" )
   cMyLocation = oLocation.Setting
   GetMyLocation() = cMyLocation
End Function



Function GetConfigAccess( ByVal cNodePath As String,_
                     ByVal bWriteAccess As Boolean,_
                     Optional bEnableSync,_
                     Optional bLazyWrite ) As Object
   If IsMissing( bEnableSync ) Then
      bEnableSync = True
   EndIf
   If IsMissing( bLazyWrite ) Then
      bLazyWrite = False
   EndIf

'   If bWriteAccess  And  bEnableSync Then
      oConfigProvider = GetProcessServiceManager().createInstanceWithArguments(_
                     "com.sun.star.configuration.ConfigurationProvider",_
                     Array( MakePropertyValue( "enableasync", bEnableSync ) ) )
'   Else
'      oConfigProvider = createUnoService( "com.sun.star.configuration.ConfigurationProvider" )
'   EndIf
   
   If bWriteAccess Then
      cServiceName = "com.sun.star.configuration.ConfigurationUpdateAccess"
   Else
      cServiceName = "com.sun.star.configuration.ConfigurationAccess"
   EndIf
   
   oConfigAccess = oConfigProvider.createInstanceWithArguments( cServiceName,_
      Array( MakePropertyValue( "nodepath", cNodePath ),_
            MakePropertyValue( "lazywrite", bLazyWrite ) ) )
   
   GetConfigAccess() = oConfigAccess
End Function

Function MakePropertyValue( Optional cName As String, Optional uValue ) As com.sun.star.beans.PropertyValue
   Dim oPropertyValue As New com.sun.star.beans.PropertyValue
   If Not IsMissing( cName ) Then
      oPropertyValue.Name = cName
   EndIf
   If Not IsMissing( uValue ) Then
      oPropertyValue.Value = uValue
   EndIf
   MakePropertyValue() = oPropertyValue
End Function




Each node, such as "my.thing1" and "my.thing2" has two properties....
1. Setting
2. SubSettings

Setting is a value of type string.

SubSettings is another node that contains named sets the above two items. So a node named "my.thing3" can have one Setting, and then have a named set of SubSettings, each SubSetting having a name, such as "Fred", "Joe", "John", and each of Fred, Joe and John are identically structured to the above, having both a Setting property, and a SubSettings property that has more named sub-sub-settings.

Since each node has a name, like "my.thing1" and "my.thing2", I can access a node by name, and get its setting. But that node can have SubSettings which have more nodes by name, accessed using hasByName(), getByName(), etc.


This is just one flexible configuration schema that I use. You can make up your own. I wanted to make my custom configuration schema recursive so that I could reuse the same xcu and xcs files in every component I create, yet store arbitrary tree structures of data.

Basically you store configuration data into an XCU file. Define the structure of it by an XCS file. Pkgchk installs both of those.

Your code must use the configuration manager, as I demonstrated above in Basic, to access your configuration settings. Your dialog box will get / display / edit / save the setting. Your add in function will get the setting and use its values.

Don't name your configuration schema "nom.DannyBrewer.Example.DannyExample". This may conflict with components that I develop. The developer's guide uses example schema names like "org.openoffice.example" and such. You can use any name that fits into the hierarchical name structure.

Off topic. In the above, you'll notice I have a location node in my configuration data. In that, I store the value "%origin%". Pkgchk will replace "%origin%" with a string that is the URL of the folder where the component was installed to. You first have to macro expand that string. But effectively, the GetMyLocation() function returns something that when macro expanded (beyond the scope of this thread) returns the pathname of other files, such as bitmaps and other files that were installed with my component. Therefore, when I create a dialog box, the dialog can have image controls whose properties are edited at runtime so that the dialog box displays pictures which are part of my component.

Hope this helps.

Danny
_________________
Want to make OOo Drawings like the colored flower design to the left?
Back to top
View user's profile Send private message
beiwen
Guest





PostPosted: Mon Apr 05, 2004 1:56 pm    Post subject: Reply with quote

Thank you so much for the extensive answer and the sample code. I have now a clear picture how to implement the addin!

Kind regards
Benno
Back to top
DannyB
Moderator
Moderator


Joined: 02 Apr 2003
Posts: 4021
Location: Lawrence, Kansas, USA

PostPosted: Wed Apr 07, 2004 5:22 am    Post subject: Reply with quote

Just adding a cross reference.....

http://www.oooforum.org/forum/viewtopic.php?t=7525
_________________
Want to make OOo Drawings like the colored flower design to the left?
Back to top
View user's profile Send private message
cbosdonnat
Power User
Power User


Joined: 14 Nov 2004
Posts: 61
Location: France - Lyon

PostPosted: Tue Oct 31, 2006 7:07 am    Post subject: Reply with quote

Thank you Danny for your method: it's really useful.

I needed to create a new node from scratch in the configuration from a macro, and here is the way I did. It might help others.

Code:
Function AddConfigNode( xAccess as Variant, sName as String, optional bForce as Boolean)
   
   If IsMissing( bEnableSync ) Then
      bEnableSync = False
   EndIf
   
   if xAccess.supportsService("com.sun.star.configuration.ConfigurationUpdateAccess") AND NOT isEmpty(sName) then
      
      if NOT (xAccess.hasByName(sName) AND bForce) then
         oNewNode = xAccess.createInstance()
         xAccess.insertByName(sName, oNewNode)
      
         AddConfigNode() = oNewNode
      end if
   end if
   
End Function


Here is a sample of use of this method:

Code:
oConfigAccess = GetConfigAccess( "/nom.DannyBrewer.Example.DannyExample/DannysConfig/Settings" )

oInsertedNode = AddConfigNode(oConfigAccess, "my.newSetting")
oInsertedNode.Setting = "New Setting"


Now we have a new node named my.NewSetting, with the Setting value set to "New Setting".

Cedric
_________________
Perso: http://cedric.bosdonnat.free.fr
Back to top
View user's profile Send private message Visit poster's website
SergeM
Super User
Super User


Joined: 09 Sep 2003
Posts: 3208
Location: Troyes France

PostPosted: Tue Oct 31, 2006 7:54 am    Post subject: Reply with quote

If you have a little time you can write a little article in the code snippets forum on the subject.
Thank you for this example.
_________________
Linux & Windows OOo3.0
UNO & C++ : WIKI
http://wiki.services.openoffice.org/wiki/Using_Cpp_with_the_OOo_SDK
In French
http://wiki.services.openoffice.org/wiki/Documentation/FR/Cpp_Guide
Back to top
View user's profile Send private message Visit poster's website
9point9
Moderator
Moderator


Joined: 31 Aug 2004
Posts: 3904
Location: UK

PostPosted: Thu Feb 01, 2007 11:59 am    Post subject: Reply with quote

Are their any addons/extensions which store settings in this way. I'd like to have a look at a working example as I can't get anything out of DannyB's code so far. Confused
_________________
Arch Linux
OOo 3.2.0

OOoSVN, change control for OOo documents:
http://sourceforge.net/projects/ooosvn/
Back to top
View user's profile Send private message Visit poster's website
cbosdonnat
Power User
Power User


Joined: 14 Nov 2004
Posts: 61
Location: France - Lyon

PostPosted: Mon Feb 05, 2007 12:33 pm    Post subject: Reply with quote

yes there are some addons doing it: just have a look at this one: http://starxpert.fr/outils/OOoMultiDiff

Cedric
Back to top
View user's profile Send private message Visit poster's website
9point9
Moderator
Moderator


Joined: 31 Aug 2004
Posts: 3904
Location: UK

PostPosted: Wed Aug 08, 2007 2:05 pm    Post subject: Reply with quote

I've had a few problems with the code to add a node:
cbosdonnat wrote:

Here is a sample of use of this method:

Code:
oConfigAccess = GetConfigAccess( "/nom.DannyBrewer.Example.DannyExample/DannysConfig/Settings" )

oInsertedNode = AddConfigNode(oConfigAccess, "my.newSetting")
oInsertedNode.Setting = "New Setting"

I have found that this will fail on the first line for me, however changing it to:
Code:
oConfigAccess = GetConfigAccess( "/nom.DannyBrewer.Example.DannyExample/DannysConfig/Settings", true)

fixes that error for me.

The next error I get is on:
Code:
oNewNode = xAccess.createInstance()

where I'm told that the Property or Method is not found. I've tried many alternatives and always fall down at this line.
_________________
Arch Linux
OOo 3.2.0

OOoSVN, change control for OOo documents:
http://sourceforge.net/projects/ooosvn/
Back to top
View user's profile Send private message Visit poster's website
Display posts from previous:   
Post new topic   Reply to topic    OOoForum.org Forum Index -> OpenOffice.org Calc All times are GMT - 8 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group