Programando o OO.o com Python

Propaganda
Programando o OO.o com Python
Introdução
Python é uma linguagem de programação de propósito geral, interpretada, multiplataforma e de fácil
aprendizagem. Ela é orientada a objetos, mas pode ser usada na programação estruturada. Além disso, ela
é livre, muito bem documentada e conta com uma comunidade bastante ativa.
Desde o OO.o 1.1.0, o núcleo da linguagem de programação Python versão 2.2.2 é instalado, por padrão,
juntamente com o OpenOffice.org. Deste modo, programadores Python podem escrever aplicativos para o
Openoffice.org.
O componente PyUNO é o responsável pela intermediação entre o interpretador Python e o OO.o. Ele
coloca à disposição do desenvolvedor todos os objetos da API do OO.o.
Aqui, você não encontrará explicações sobre a API do OO.o. Para conhecê-la, consulte a minha apostila _
Introdução ao OpenOffice.org Basic _ ou consulte o item Mais Informações no final deste documento.
Usando Python para OO.o ( PyUNO )
Para usar Python, você só precisa instalar o OO.o versão 1.1.x ou superior. É recomendado o uso da
versão distribuida e instalada com o OO.o e não as versões oficiais do Python (apesar da substituição ser
possível).
Python é instalada, por padrão, no diretório <OO.o_Install>\program\python-core-2.2.2. Para iniciar o
ambiente Python, alterne para o diretório <OO.o_Install>\program e execute o script python.bat
(ambiente Windows).
Os programas Python para o OO.o podem ser escritos para serem usados de duas maneiras diferentes: (1)
a partir de um processo Python ou (2) de dentro de um processo do OO.o.
No primeiro modo, o OO.o precisa ser inicializado para reconhecer conexões remotas. No segundo, o
programa Python precisa ser instalado como um componente UNO e ser ativado a partir de um evento
definido pelo programador (seleção de uma opção de menu, clique sobre um ícone, chamado a partir de
uma macro OOoBasic, etc).
Num processo Python
Este método de execução é lento, principalmente pela sobrecarga da comunicação entre os processos
Python e OO.o.
Ele deve ser usado quando você: (1) estiver aprendendo PyUNO ou desejar o menor tempo entre
codificação e execução, e (2) for usar o seu programa num processo separado (p.ex: como parte de um
script).
Digite o exemplo abaixo no seu editor preferido e salve-o (formato UNIX, sem CR) como
ex_py_calc.py:
## #####################################################
## ex_py_calc.py
## Exemplo de programa Python para o OO.o.
##
##
##
##
##
##
##
##
##
##
##
##
##
##
- Usa o processo Python para rodar o programa ( modo 1)
- Abre um novo documento do calc e preenche algumas células com dados
- Salva e fecha o novo documento
ATENCAO -> antes de usar este exemplo voce precisa:
1. encerrar todo OOo (inclusive o inicio rápido)
2. iniciar o OOo para aceitar conexão remota, com o comando:
<oooInstall>\program\soffice "-accept=socket,host=localhost,port=2002;urp;"
Uso: <oooInstall>\program\python ex_py_calc.py
............. OU ...............
<oooInstall>\program\python
>> import ex_py_calc.py
#####################################################
import uno
# cria o contexto do componente UNO
localContext = uno.getComponentContext()
# cria o UnoUrlResolver
resolver = localContext.ServiceManager.createInstanceWithContext
("com.sun.star.bridge.UnoUrlResolver",localContext)
# conecta ao processo OO.o (você iniciou o OO.o para aceitar conexões remotas)
ctx = resolver.resolve
("uno:socket,host=localhost,port=2002;urp;StarOffice.ComponentContext")
smgr = ctx.ServiceManager
# de agora em diante, o uso da API do OO.o é bastante semelhante ao
# da linguagem OOoBasic, portanto você pode consultar a apostila
# <Introdução ao OOoBasic> (ou outra documentação) para aprender
# como programar com os objetos da API do OO.o.
#
# cria o objeto Desktop
desktop = smgr.createInstanceWithContext ("com.sun.star.frame.Desktop", ctx)
# cria um novo documento (planilha) do Calc
oDoc = desktop.loadComponentFromURL ("private:factory/scalc","_blank",0,())
# obtem a folha de planilha 1
oPlan = oDoc.getSheets().getByIndex(0)
# dados para as celulas
lin = [ ['Gênero','Quant','Preço'],
['Banana','1 dz',1.50],
['Arroz','5 kg',7.50],
['Feijão','3 kg',4.50] ]
# obtem as células e preenche com dados
for i in range(4):
for j in range(3):
oCel = oPlan.getCellByPosition(j, i)
oCel.setFormula(lin[i][j])
# salva o arquivo, altere o caminho para o seu sistema
sURL = uno.systemPathToFileUrl ('C:\Documents and Settings\user1\My
Documents\ex_py_calc.sxc')
oDoc.storeToURL(sURL, ())
# fecha o arquivo
oDoc.close(True)
#
# para evitar problemas com metodos <oneway>
# ctx.ServiceManager
Vejamos os passos preparatórios para rodar programas neste modo: (1) iniciar o processo OO.o, e (2)
iniciar o processo Python.
No passo (1) devemos iniciar o OO.o para aceitar conexões remotas. Certifique-se de encerrar todos os
processos do OO.o, inclusive o Início Rápido e no “prompt” digite o comando abaixo e tecle <Enter>:
<oooInstall>\program\soffice "-accept=socket,host=localhost,port=2002;urp;"
No passo (2) iniciamos o processo Python. O OO.o traz o “script” python.bat que se encarrega desta
tarefa. No “prompt” digite o comando abaixo e tecle <Enter>:
<oooInstall>\program\python ex_py_calc.py
................ OU ...................
<oooInstall>\program\python <Enter>
>> import ex_py_calc.py
Agora, teste o nosso exemplo. Em caso de erros, revise o programa (testado com OO.o 1.1.3 + XPp).
Num processo OO.o
Este modo deve ser usado quando você desejar: (1) rapidez na execução do seu programa; (2) distribuir
seu programa por várias instalações do OO.o, e (3) executar o seu programa pela interface gráfica do
OO.o.
Neste modo, o programa Python deve ser escrito como um componente UNO e deve ser parte de uma
classe Python. Adicionalmente, precisamos de um arquivo para configurar o OO.o de modo que ele saiba
qual evento dispara a execução do programa.
O exemplo abaixo (ex_comp_py_calc.py) tem a mesma funcionalidade do anterior:
########################################################################
## ex_comp_py_calc.py
## Exemplo de programa Python para o OO.o.
## - Usa o processo OO.o para rodar o programa ( modo 2)
## - Abre um novo documento do calc e preenche algumas células com dados
## - Salva e fecha o novo documento
########################################################################
import uno
import unohelper
from com.sun.star.task import XJobExecutor
# implementa um componente UNO, derivando da classe padrão
# unohelper.Base e das interfaces que você vai implementar.
class PyCalcJob( unohelper.Base, XJobExecutor ):
def __init__( self, ctx ):
# o construtor recebe o contexto (ctx) como argumento.
# armazena o contexto para uso posterior.
self.ctx = ctx
def trigger( self, args ):
# nota: args[0] == "DespesaAlimentar", veja config. abaixo
# cria o objeto Desktop
desktop = self.ctx.ServiceManager.createInstanceWithContext(
"com.sun.star.frame.Desktop", self.ctx )
# cria um novo documento (planilha) do Calc
oDoc = desktop.loadComponentFromURL ("private:factory/scalc","_blank",0,())
# obtem a folha de planilha 1
oPlan = oDoc.getSheets().getByIndex(0)
# dados para as celulas
lin = [ ['Gênero','Quant','Preço'],
['Banana','1 dz',1.50],
['Arroz','5 kg',7.50],
['Feijão','3 kg',4.50] ]
# obtem as células e preenche com dados
for i in range(4):
for j in range(3):
oCel = oPlan.getCellByPosition(j, i)
oCel.setFormula(lin[i][j])
# salva o arquivo, altere o caminho para o seu sistema
sURL = uno.systemPathToFileUrl ('C:\Documents and Settings\Anadsec\My
Documents\ex_py_calc.sxc')
oDoc.storeToURL(sURL, ())
# fecha o arquivo
oDoc.close(True)
# o loader python busca uma variável estática g_ImplementationHelper
g_ImplementationHelper = unohelper.ImplementationHelper()
# adiciona a classe ao container de implementação, que é
# usado pelo loader para registrar/instanciar o componente
g_ImplementationHelper.addImplementation( \
PyCalcJob,
# classe de objeto UNO
"org.openoffice.comp.pyuno.nad.DespesaAlimentar", # nome da implementação
# mude este nome para o seu script
("com.sun.star.task.Job",),)
# lista dos serviços implementados
# (apenas um serviço)
Apesar das semelhanças, algumas diferenças são notórias, por exemplo: toda a etapa de conexão com o
OO.o foi removida.
Vamos agora preparar o arquivo de configuração abaixo, que cuida da configuração do OO.o para
executar o componente python. Digite o código xml no seu editor de texto favorito e salve como
addons.xcu:
<?xml version="1.0" encoding="UTF-8"?>
<oor:node xmlns:oor="http://openoffice.org/2001/registry"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
oor:name="Addons" oor:package="org.openoffice.Office">
<node oor:name="AddonUI">
<node oor:name="AddonMenu">
<node oor:name="org.openoffice.comp.pyuno.nad.DespesaAlimentar" oor:op="replace">
<prop oor:name="URL" oor:type="xs:string">
<value>service:org.openoffice.comp.pyuno.nad.DespesaAlimentar?insert</value>
</prop>
<prop oor:name="ImageIdentifier" oor:type="xs:string">
<value>private:image/3216</value>
</prop>
<prop oor:name="Title" oor:type="xs:string">
<value>Food Expense</value>
<value xml:lang="pt-BR">Despesa Alimentar</value>
</prop>
</node>
</node>
</node>
</oor:node>
Já temos os arquivos necessários para cirar o pacote UNO (um arquivo zip). Então crie um arquivo
ex_comp_py_calc.zip contendo os arquivos ex_comp_py_calc.py e addons.xcu.
O próximo passo é a instalação do pacote ex_comp_py_calc.zip. Para isto, mova o pacote para o diretório
<OOoUserInstall>\user\uno_packages e em seguida execute o programa pkgchk com o comando
(ATENÇÃO: feche todos os processos do OO.o, inclusive o Início Rápido):
<OOoInstall>\program\pkgchk
Agora, ao iniciar o OO.o uma nova opção de menu estará disponível em (Ferramentas => Suplementos
=> Despesa Alimentar). Ao selecioná-la o nosso exemplo será executado. Se ocorrer algum erro, revise
os arquivos ( testado com OO.o 1.1.3 e XPp ).
Podemos, ainda, escrever componentes Python para serem utilizados por outros programas (por exemplo,
implementar uma interface UNO e chamar seus métodos de uma macro OOoBasic). Nestes casos,
precisamos apenas registrar o componente Python no OO.o. Não é necessário escrever o arquivo de
configuração e nem criar um pacote UNO, basta copiar o componente para o diretório uno_packages e
executar o programa pkgchk, como explicado.
Usando tipos UNO com o Python
A API do OO.o define diversos tipos de dados, que são usados como valores para propriedades de objetos
ou como argumentos para os métodos, a seguir veremos como usar alguns destes tipos em nossos
programas:
Os tipos de dados simples são, de modo geral, convertidos para tipos similares do Python. Por exemplo,
você pode usar True/False quando um objeto UNO lidar com um tipo boolean. Existem objetos no
módulo uno.py (importado nos programas PyUNO) representando vários tipos de dados (uno.Bool –
uno.Char, etc):
oCursor.gotoEnd ( uno.Bool ( 1 ) )
um_char = uno.Char ( u'A' ) # uno.Char('A') <= errado
Constantes ( Constant Groups ) e Enumerações ( Enums ) devem ser importadas como abaixo:
from com.sun.star.text.ControlCharacter import PARAGRAPH_BREAK
from com.sun.star.text.TextContentAnchorType import AS_CHARACTER
A seguir a constante PARAGRAPH_BREAK e o valor Enum AS_CHARACTER podem ser usados no
código Python:
oText.insertControlCharacter( oCursor, PARAGRAPH_BREAK, 0 )
Estruturas ( Structs ) também devem ser importadas:
from com.sun.star.awt import Size
# ....
oRetangulo.setSize ( Size ( 2000, 1000 ) )
Seqüências UNO são mapeadas para o tipo Python tupla (listas não funcionam).
Muitos métodos da API recebem como argumento uma seqüência de estruturas. Por exemplo, o último
argumento do método loadComponentFromURL é um vetor da estrutura
com.sun.star.beans.PropertyValue:
# importa a estrutura
from com.sun.star.beans import PropertyValue
#
# para sequencia vazia (não precisa importar)
oDoc = oDT.loadComponentFromURL( sUrl , "_blank", 0, () )
#
# sequencia com um elemento, note a vírgula final
aProp = PropertyValue( "Hidden" , 0 , True, 0 ),
oDoc = oDT.loadComponentFromURL( sUrl , "_blank", 0, aProp )
#
# sequencia com mais de um elemento
aProps = (
PropertyValue( "FilterName" , 0, filtro , 0 ),
PropertyValue( "FilterOptions",0, opcoes ,0))
oDoc = oDT.loadComponentFromURL( sUrl , "_blank", 0, aProps )
Você está pronto para prosseguir sozinho, seguem alguns vínculos contendo documentos/código sobre
programação para o OO.o.
Mais Informações
PyUNO Bridge => Documentação oficial com exemplos de programas para os dois modos e vínculos
para aplicações desenvolvidas com Python.
OOo SDK => Tudo que você precisa, principalmente documentação (The Developer's Guide e IDL
Reference) além de exemplos.
Apostila de Introdução ao OOoBasic => Apesar de orientada para o OOoBasic, contém inúmeros
exemplos de uso da API com uma descrição dos objetos, métodos e propriedades utilizadas.
Addons1_1 => Documento detalhando o arquivo de configuração addons.xcu. Contém uma macro para
criar automaticamente este arquivo.
OOoForum => Fórum de discussão (em inglês) sobre o OOo. Faça uma busca com a palavra-chave
Python.
Danny's Python modules => Da seção de código do OOoForum, um exemplo de componente UNO.
Modeless window with controls in Python => Da seção de código do OOoForum, um exemplo sobre a
criação de janelas contendo controles.
Autor
Tradução resumida do documento PyUNO Bridge, por Noelson Alves Duarte, em 23/02/2005.
Download