domingo, 14 de julio de 2024

Procedimientos. Datos

Mostar y ocultar hojas mediante OOo Basic

Ya vimos como trabajar con macros para mostrar, ocultar y posicionarse en una hoja determinada. Ahora tenemos que aprender a realizar estas mismas operaciones usando OOo Basic, esto es: sin recurrir a Grabar macro.


Empiezo por exponer el código Mostar vs. Ocultar hojas por su mayor simplicidad y por ser ambos expresiones de una misma instrucción. Aunque podemos diferenciar formas alternativas de hacer lo mismo, en realidad todo forma parte de una unidad de programación.

Empecemos por ocultar la hoja activa:

Sub OcultarHoja1 'Hoja activa

Dim oHojaActiva As Object

oHojaActiva = ThisComponent.getCurrentController.getActiveSheet()

oHojaActiva.isVisible = False

End Sub

Una vez que asignamos el objeto HojaActiva a la variable objeto declarada a tal fin (oHojaActiva = ThisComponent.getCurrentController.getActiveSheet()), simplemente tendremos que declarar su atributo isVisble como False (oHojaActiva.isVisible = False)

Esta última acción es la define lo nuclear del código OOo Basic que nos permite definir una hoja como visible u oculta. Podemos crear código que parta de otras consideraciones respecto a la hoja de referencia, pero lo fundamental está ya expresado en el script anterior. 

Por ejemplo, Ocultar/Mostar una determinada hoja identificada por su índice:

Sub OcultarHoja2  'Ocultar hoja

Dim oHoja As Object

oHoja = ThisComponent.getSheets.getByIndex(1)

oHoja.isVisible = False

End Sub

 Sub MostrarHoja2 'Mostar hoja

Dim oHoja As Object

oHoja = ThisComponent.getSheets.getByIndex(1)

oHoja.isVisible = True

End Sub

En ambos casos se asigna a la variable el objeto Hoja 1 (1) (oHoja = ThisComponent.getSheets.getByIndex(1)) y después se atribuye valor True/False a su atributo isVisible

Es posible, pues, crear una subrutina que asuma la ejecución de la operación (mostrar vs. ocultar) con tan sólo pasarle como valor del parámetro True/False, además del identificador de la hoja sobre la que actuar. Te muestro el código de este conjunto:

Sub MostrarH  ' Script para mostrar una hoja

operaMO (True,0)

End Sub

Sub OcultarH  ' Script para ocultar una hoja

operaMO (False,0)

End Sub


Sub operaMO (vb As Boolean, nh As Integer)  'Subrutina

Dim oHoja As Object

oHoja = ThisComponent.getSheets.getByIndex(nh)

oHoja.isVisible = vb

End Sub

No es ahora necesario complicar los script, así que me limito a formularlos de la forma más simple. La subrutina es prácticamente idéntica al script mostrado anteriormente, sustituyendo los valores por los identificadores de los parámetros que, como se puede ver, son dos (operaMO (vb As Boolean, nh As Integer)

Para finalizar esta entrada me ha parecido de interés explicar cómo mostrar u ocultar todas las hojas del libro de una sala vez (2). 

El script es muy simple, ya que me limito a hacer la llamada a la subrutina. Además el parámetro que se pasa debe ajustarse al objetivo cambiando su valor (True vs. False):

Sub TodasOM                 'Script

TodasH(True)

End Sub


Sub TodasH (vb As Boolean) 'Subrutina

Dim oHojaActiva As Object
Dim oHojas As Object
Dim co1 As Long

oHojaActiva = ThisComponent.getCurrentController.getActiveSheet()

oHojas = ThisComponent.getSheets()

For co1 = 0 To oHojas.getCount() - 1

If oHojas.getByIndex(co1).getName <> oHojaActiva.getName() Then
oHojas.getByIndex(co1).isVisible = vb
End If

Next

End Sub

La subrutina tiene un único parámetro (TodasH (vb As Boolean)puesto que no es necesario especificar las hojas sobre las que se actuará, lo que sí es necesario es diferenciar los objetos Hojas (oHojas) y HojaActiva (oHojaActiva), de ahí que se declaren dos variables.

Después asignamos los objetos a las variables...

oHojaActiva = ThisComponent.getCurrentController.getActiveSheet()
oHojas = ThisComponent.getSheets()

 ... para recorrer después el conjunto de las hojas mediante un bucle For, (3) actuando sobre ellas (4). El condicional anidado If permite diferenciar la hoja activa del resto (5), ya que sobre ésta no deseamos que se realice la operación Mostrar/Ocultar (6).

Documento. En [este libro Calc] puedes encontrar el código explicado en la entrada.

NOTAS

(1) Según su índice, en este caso la hoja 1, esto es: la que ocupa la segunda posición.
(2) Al menos una hoja debe quedar visible, así que la idea es ocultar vs. mostrar todas las hojas menos la activa.
(3) Utilizamos el método getCount() del objeto oHojas para identificar el número de hojas del libro. Restamos 1 al valor que devuelve getCount() porque, como sabemos, la matriz que contiene las hojas del libro se inicia en 0. 
(4) Esto es: ocultándolas o mostrándolas en función del valor del parámetro vb. Esta operación se realiza sobre cada una de las hojas del libro (oHojas) mediante la instrucción (oHojas.getByIndex(co1).isVisible = vb), que identifica a cada uno de ellas por su índice, el cual se asocia al valor del contador (co1). Dicha instrucción está situada dentro del condicional If, ya que queda condicionada al cumplimiento del criterio que se establece en ella, y que constituye el objetivo de la subrutina.
(5) El condicional If tiene como condición True que no sean iguales (<>)el nombre de cada una de las hojas que recorre el bucle y el de la hoja activa (oHojas.getByIndex(co1).getName <> oHojaActiva.getName()). El nombre de la hoja se obtiene mediante el método getName aplicado tanto a la colección de hojas (en realidad matriz de objetos asignada a oHojas) como a la hoja activa (objeto asignado a oHojaActiva).
(6) Si prescindimos del condicional anidado en el bucle, el script funcionaría igual (no daría error) pero invariablemente, a la hora de ocultar las hojas mostraría como hoja activa la última de la colección de hojas del libro, ya que es en ella donde se posiciona el bucle en su recorrido (For co1 = 0 To oHojas.getCount() - 1)