Artículo original: Saving and restoring settings in VFP applications
http://www.sweetpotatosoftware.com/SPSBlog/PermaLink,guid,e5d49608-9752-42a5-b7f7-867df325a780.aspx
Autor: Craig Boyd
Traducido por: Ana María Bisbé York
El problema
Muchas veces, los desarrolladores Visual FoxPro van a encontrarse a si mismo guardando estados previos de alguna configuración para restaurarlo una vez que está ejecutando el código. Los más usuales son:
- comandos SET (tales como SET SAFETY, SET DELETED, etc.)
- comandos ON (ON ERROR, ON ESCAPE, etc.)
- posición del puntero de registro
- área de trabajo actual
La solución
En lugar de escribir las mismas líneas de código una y otra vez en sus programas, podríamos crear una clase que lo controle. Esto hace la siguiente clase SettingHandler, que he escrito y he preparado unos ejemplos de cómo utilizarla. Notará que cuando instancio la clase envío el comando que estoy por ejecutar (tales como SET SAFETY OFF) como un parámetro tipo cadena. La clase va a guardar la configuración actual del parámetro Safety y luego lo iguala a OFF. Cuando deseo restablecer la configuración anterior, libero la instancia de SettingHandler y la clase restablece el valor de Safety a lo que hubiera antes de que yo lo hubiera cambiado.
Inconvenientes y ventajas
El único inconveniente que encuentro en este proceder es que no trabaja IntelliSense cuando escribo el comando como parámetro de cadena. Y sobre las mejoras, puedo pensar en más de una, por ejemplo, operaciones sobre tablas. Se podría agregar que permita guardar la sesión actual de datos y que luego la restablezca (habrá probablemente otros parámetros que también se podrían proporcionar Captions, ForeColor, BackColor, Tag, etc) Además, se podría agregar alguna lógica para controlar si un desarrollador cambia las áreas de trabajo; pero no especifica un área de trabajo en el comando GOTO.
He aquí un ejemplo listo para correr y la definición de clase (copie y pegue el código que aparece a continuación en un prg y ejecútelo)
*************************
*!* EJEMPLO DE USO
*************************
CLEAR
LOCAL loSetting
? "SET COMMANDS:"
SET SAFETY ON
? SET("SAFETY")
** Guarda y cambia el valor de Safety
loSetting = CREATEOBJECT("SettingHandler", "SET SAFETY OFF")
? SET("SAFETY")
** Restaura el valor previo de Safety
RELEASE loSetting
? SET("SAFETY")
?
? "ON COMMANDS:"
ON ERROR ? "Controlador de error previo "
? ON("ERROR")
** Guarda y cambia el valor del controlador de error
loSetting = CREATEOBJECT("SettingHandler", "ON ERROR ?'New Error Handler'")
? ON("ERROR")
** Restaura el valor previo del controlador de error
RELEASE loSetting
? ON("ERROR")
?
? "RECORD NUMBER:"
IF !USED("customers")
USE (HOME(2) + "northwind\customers.dbf") IN 0 SHARED
ENDIF
GOTO 5 IN "customers"
? RECNO("customers")
** Guarda y cambia el valor de la posición del puntero de registro
loSetting = CREATEOBJECT("SettingHandler", "GO 12 in [customers]")
? RECNO("customers")
** Restaura el valor previo de la posición del puntero de registro
RELEASE loSetting
? RECNO("customers")
?
? "SELECT:"
IF !USED("orders")
USE (HOME(2) + "northwind\orders.dbf") IN 0 SHARED
ENDIF
SELECT "Orders"
? ALIAS()
** Guarda y cambia el valor del Alias actual
loSetting = CREATEOBJECT("SettingHandler", "Select Customers")
? ALIAS()
** Restaura el valor previo del Alias actual
RELEASE loSetting
? ALIAS()
USE IN SELECT("Customers")
USE IN SELECT("Orders")
*
******* Final de los ejemplos ******
*
************************************
*!* DEFINICIÓN DE CLASE
************************************
DEFINE CLASS SettingHandler as custom
PROTECTED PreviousValue
PreviousValue = .NULL.
PROTECTED SettingCommand
SettingCommand = ""
PROTECTED SettingType && 0 = SET/ON, 1 = RECNO
SettingType = -1
#DEFINE SETTINGDELIMITERS [('" ] + "[])"
PROCEDURE Init (tcCommand)
This.Setup(tcCommand)
ENDPROC
PROTECTED PROCEDURE Destroy
This.RevertSetting()
ENDPROC
PROCEDURE Setup (tcCommand)
This.SettingCommand = ALLTRIM(tcCommand)
This.SaveSetting()
This.UpdateSetting()
ENDPROC
PROTECTED PROCEDURE SaveSetting
LOCAL lcFirstPart, lcSecondPart, lnSecondPosition, lcCommand
lcFirstPart = UPPER(ALLTRIM(GETWORDNUM(this.SettingCommand, ;
1, SETTINGDELIMITERS)))
DO CASE
CASE INLIST(lcFirstPart, "SET", "ON")
lcSecondPart = UPPER(ALLTRIM(GETWORDNUM(this.SettingCommand, ;
2, SETTINGDELIMITERS)))
lcCommand = lcFirstPart + [("] + lcSecondPart + [")]
This.SettingType = 0
CASE INLIST(lcFirstPart, "GOTO", "GO")
lnSecondPosition = ATC(" IN ", this.SettingCommand)
IF lnSecondPosition > 0
lcSecondPart = SUBSTR(this.settingcommand, lnSecondPosition + 4)
ELSE
lcSecondPart = ""
ENDIF
lcCommand = [RECNO(] + lcSecondPart + [)]
This.SettingType = 1
CASE lcFirstPart = "SELECT"
lcSecondPart = UPPER(ALLTRIM(GETWORDNUM(this.SettingCommand, ;
2, SETTINGDELIMITERS)))
lcCommand = [ALIAS()]
This.SettingType = 2
ENDCASE
IF !EMPTY(lcCommand)
This.PreviousValue = EVALUATE(lcCommand)
ENDIF
ENDPROC
PROTECTED PROCEDURE UpdateSetting
EXECSCRIPT(This.SettingCommand) && Cambia los valores
ENDPROC
PROTECTED PROCEDURE RevertSetting
LOCAL lcCommand, lnStuffPosition, lnStuffLength, lcAliasWas
DO CASE
CASE This.SettingType = 0 && SET/ON
lnStuffPosition = AT(" ", this.Settingcommand, 2) + 1
lnStuffLength = LEN(this.settingcommand) - lnStuffPosition + 1
CASE This.SettingType = 1 && GOTO/GO
lnStuffPosition = AT(" RECORD ", UPPER(this.Settingcommand), 1) + 8
IF lnStuffPosition < 9
lnStuffPosition = AT(" ", this.Settingcommand, 1) + 1
lnStuffLength = AT(" ", this.Settingcommand, 2)
IF lnStuffLength > 0
lnStuffLength = lnStuffLength - lnStuffPosition + 1
ELSE
lnStuffLength = LEN(this.settingcommand) - lnStuffPosition + 1
ENDIF
ELSE
lnStuffLength = LEN(this.settingcommand) - lnStuffPosition + 1
ENDIF
CASE This.SettingType = 2 && SELECT
lnStuffPosition = AT(" ", this.Settingcommand, 1) + 1
lnStuffLength = LEN(this.settingcommand) - lnStuffPosition + 1
ENDCASE
IF !EMPTY(lnStuffPosition)
lcCommand = STUFF(This.SettingCommand, lnStuffPosition, ;
lnStuffLength, TRANSFORM(this.PreviousValue))
** Restablece el estado inicial antes de que fueran cambiado
EXECSCRIPT(lcCommand)
ENDIF
ENDPROC
ENDDEFINE
No hay comentarios. :
Publicar un comentario
Los comentarios son moderados, por lo que pueden demorar varias horas para su publicación.