par , 20/11/2020 à 15h15 (405 Affichages)
Suite à la demande d’Ézéchias sur le forum Windev, je vous livre ma version d'un gestionnaire d'évènements personnalisés afin de pallier ce manque dans l'AGL de PC Soft.
Envoyé par
denouezechias
Bonjour,
Je suis en train de convertir un script qui a été ecrit en Visual basic et j'ai besoin d'aide pour ce genre d'instruction ci dessous:
AddHandler event, AddressOf eventhandler
Merci d'avance
La solution est, somme toute, triviale. Une classe va se charger de répertorier une procédure à exécuter pour chaque évènement dont le nom pourra être défini.
C'est parti :
tout d'abord, la déclaration de la classe cEventHandler, avec ces membres et sa méthode d'instanciation globale afin de n'instancier qu'un seul gestionnaire d'évènements.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
|
cEventHandler is Class
PRIVATE
// Enregistre la liste des écouteurs
_events is associative array of Procédures
GLOBAL
_instance is cEventHandler dynamic
END
PROCÉDURE PRIVATE Constructor()
// Rien ici
PROCÉDURE PUBLIC GLOBAL getInstance()
IF _instance = Null THEN
_instance <- new cEventHandler
END
RESULT _instance |
Une fois le gestionnaire d'évènements instancié, nous voulons pouvoir inscrire un évènement personnel avec le traitement qui lui sera associé :
1 2 3
|
PROCÉDURE onEventDo(pEvent is personalEvent, pCallable is Procédure)
_events[pEvent..Name] = pCallable |
Ici, le paramètre pEvent est une énumération afin de s'assurer que le nom de l'évènement est sans équivoque.
Maintenant que l'évènement est enregistré, il suffit de déclencher un appel vers ce dernier afin d'exécuter la procédure associée :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
|
PROCÉDURE emit(pEvent is personalEvent, *)
returnedProcess is Procédure <- _getProcess(pEvent)
IF returnedProcess <> Null THEN
SWITCH MyParameters..Count
CASE > 1
WHEN EXCEPTION IN
returnedProcess(MyParameters[2 TO])
RESULT True
DO
RESULT returnedProcess(MyParameters[2 TO])
END
OTHER CASE
WHEN EXCEPTION IN
returnedProcess()
RESULT True
DO
RESULT returnedProcess()
END
END
END
RESULT Null |
Que fait cette méthode :
- Si l'évènement personnalisé existe dans la liste des évènements enregistrés :
1 2 3
|
PROCÉDURE PRIVATE _hasEvent(pEvent is personalEvent) : boolean
RESULT _events[pEvent..Name]..Exist |
- il est récupéré pour être exécuté
1 2 3 4 5 6 7 8
|
PROCÉDURE PRIVATE _getProcess(pEvent is personalEvent) : Procédure
pProc is Procédure = Null
IF _hasEvent(pEvent) THEN
pProc = _events[pEvent..Name]
END
RESULT pProc |
Enfin, une méthode permettant de supprimer un évènement déjà enregistré dans la liste :
1 2 3 4 5
|
PROCÉDURE deleteEvent(pEvent is personalEvent)
IF _hasEvent(pEvent) THEN
_events.delete(pEvent)
END |
L'utilisation de ce gestionnaire est alors simple :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
|
// Énumération des évènements
personalEvent est énumération
dire_bonjour
dire_autre_chose
FIN
// Instanciation du gestionnaire d'évènements
MonGestionnaireDevenementsPersos est un cEventHandler dynamique <- cEventHandler.getInstance()
// Définition des procédures associées aux évènements
// Sans paramètres
PROCEDURE INTERNE hello()
trace("Hello world !")
FIN
// Avec paramètres
PROCEDURE INTERNE tell(*)
POUR indexParam = 1 _A_ MesParamètres..occurence
trace(MesParamètres[indexParam])
FIN
FIN
// Inscrire les évènements auprès du gestionnaire
MonGestionnaireDevenementsPersos.onEventDo(dire_bonjour, hello)
MonGestionnaireDevenementsPersos.onEventDo(dire_autre_chose, tell)
// Déclencher l'évènement
MonGestionnaireDevenementsPersos.emit(dire_bonjour)
// La trace vaut
// Hello world !
MonGestionnaireDevenementsPersos.emit(dire_autre_chose, "Hello", "world", "!")
// La trace vaut
// Hello
// world
// ! |
Voilà, il peut sans doute être amélioré mais est déjà bien fonctionnel en l'état.
J'espère qu'il pourra être utile à certains d'entre vous.