PBToolboxAI v5 ← Site

6. Fonctions transverses #

← Langue et RTL · Sommaire · FAQ →


Ce chapitre regroupe les services disponibles quel que soit le composant : info-bulles, hébergement de contrôles PowerBuilder, glisser-déposer depuis l'Explorateur, focus clavier, export image, et les objets utilitaires non visuels.


6.1 Info-bulles simples et enrichies #

Info-bulle du composant #

uo_button.is_tooltip = "Enregistrer le dossier (Ctrl+S)"

Le texte accepte le balisage riche : [b], [br], [color=…], [picture=…]…

Super info-bulle (titre + texte + image) #

Pour une aide contextuelle façon ruban Office :

uo_button.is_super_tooltip_title = "Enregistrer"
uo_button.is_super_tooltip_text  = "Écrit les modifications sur le serveur." &
                                   + "[br][br][size-=15]Raccourci : Ctrl+S[/size-=15]"
uo_button.is_super_tooltip_image = "img\help_save.png"

Les trois propriétés sont indépendantes : un titre seul, ou un titre + texte sans image, sont valides. Dès qu'une propriété is_super_tooltip_* est posée, elle prend le pas sur is_tooltip.

Info-bulle d'un item #

Toute classe d'item (n_pbt_item et ses descendants) porte les quatre mêmes propriétés :

uo_toolbar.of_item(/*keys*/ "main/save").is_tooltip = "Enregistrer"

uo_tab.of_page(/*key*/ "clients").is_super_tooltip_title = "Clients"
uo_tab.of_page(/*key*/ "clients").is_super_tooltip_text  = "128 fiches, dernière synchro à 09:12"

Comportement #


6.2 Héberger de vrais contrôles PowerBuilder #

Les composants conteneurs n'affichent pas du HTML à la place de vos écrans : ils accueillent de vrais contrôles PowerBuilder (userobjects, DataWindows, groupes de contrôles), reparentés comme fenêtres Win32 enfants. Vos écrans existants sont réutilisés tels quels.

// Onglets : chaque page est un userobject PB
uo_tab.of_add_page(/*key*/ "clients",   /*title*/ "Clients",   /*page*/ uo_page_clients)
uo_tab.of_add_page(/*key*/ "invoices",  /*title*/ "Factures",  /*page*/ uo_page_invoices, /*closable*/ true)

// Panneaux dockables : idem
uo_dock.is_main = "doc"                       // zone centrale
uo_dock.of_add_panel(/*key*/ "doc",      /*position*/ uo_dock.POSITION_STACK, /*relative_to*/ "", /*size*/ 0,   /*title*/ "Document",    /*content*/ uo_editor)
uo_dock.of_add_panel(/*key*/ "explorer", /*position*/ uo_dock.POSITION_START, /*relative_to*/ "", /*size*/ 240, /*title*/ "Explorateur", /*content*/ uo_tree)
uo_dock.of_add_panel(/*key*/ "props",    /*position*/ uo_dock.POSITION_END,   /*relative_to*/ "", /*size*/ 260, /*title*/ "Propriétés",  /*content*/ uo_props)

Ce qui est pris en charge pour vous :

⚠️ Un contrôle hébergé est une fenêtre native : il se dessine au-dessus de la couche web. C'est voulu (votre DataWindow reste nette et rapide), mais cela signifie qu'aucun effet web — ombre, transparence, animation — ne peut passer par-dessus lui.


6.3 Recevoir des fichiers depuis l'Explorateur Windows #

Un composant peut devenir cible de dépôt pour des fichiers glissés depuis l'Explorateur. La bibliothèque installe une cible de dépôt native : vous recevez les chemins complets, ce qu'un dépôt HTML ne permet pas.

uo_editor.ib_allow_drop = true
// event ue_drop_files de uo_editor : (string as_files[])
// Local variables
long ll_i

// Ouvrir chaque fichier depose
for ll_i = 1 to UpperBound(as_files)
    of_open_file(as_files[ll_i])
next
EventDéclenché quand
ue_drag_enter ( )Un glisser de fichiers entre dans le composant
ue_drag_leave ( )Il en sort sans déposer
ue_drop_files (string as_files[])Les fichiers sont déposés — chemins complets

Le composant fournit lui-même le retour visuel de survol (surbrillance de la zone de dépôt). Publié par les composants où le dépôt a du sens : statictext, codeeditor.


6.4 Clavier et focus #

Un composant PBToolboxAI participe à la navigation clavier de votre fenêtre comme un contrôle natif :

Une touche que le composant traite lui-même reste à lui : Entrée sur un élément qu'il dessine comme un bouton (une étape, un segment) l'active — et ne presse pas en plus le bouton par défaut ; Échap qui abandonne un glisser ou quitte un mode ne ferme pas la fenêtre. Une frappe ne produit jamais deux effets. Une frappe AltGr qui produit un caractère (l'euro d'un clavier français) est de la saisie, jamais un raccourci.

Pour donner explicitement le focus au contenu d'un composant (par exemple après avoir ouvert un panneau de recherche) :

uo_editor.of_focus_webview()

6.5 Exporter le rendu en image #

Rappel du socle commun : tout composant s'exporte tel qu'affiché.

uo_tiles.of_save_as_png(/*path*/ "C:\temp\accueil.png")
uo_tiles.of_save_as_jpg(/*path*/ "C:\temp\accueil.jpg")

Utile pour joindre un écran à un e-mail, alimenter un état, ou tracer un incident utilisateur.


6.6 Boîtes de dialogue et notifications #

Deux services sans contrôle à poser dans la fenêtre :

// Local variables
n_pbt_messagebox lnv_mb

// Boite de dialogue modale themee (retour synchrone)
lnv_mb = create n_pbt_messagebox
lnv_mb.is_title   = "Suppression"
lnv_mb.is_message = "Supprimer définitivement [b]12 dossiers[/b] ?"
lnv_mb.is_icon    = lnv_mb.ICON_QUESTION
lnv_mb.of_add_button(/*text*/ "Supprimer", /*default*/ false, /*cancel*/ false)
lnv_mb.of_add_button(/*text*/ "Annuler",   /*default*/ true,  /*cancel*/ true)

if lnv_mb.of_show(/*hwnd*/ Handle(this)) = 1 then of_delete()
destroy lnv_mb
// Local variables
n_pbt_toaster lnv_toast

// Notification "toast" en coin d'ecran, non bloquante
lnv_toast = create n_pbt_toaster
lnv_toast.is_title = "Import terminé"
lnv_toast.is_text  = "1 240 lignes intégrées."
lnv_toast.is_kind  = lnv_toast.KIND_SUCCESS
lnv_toast.of_show()
destroy lnv_toast

Détails complets : messagebox et toaster.


6.7 Objets utilitaires non visuels #

Livrés dans la même PBL, sans webview ni rendu : ce sont de simples enveloppes autour de la DLL. Créez-les, utilisez-les, détruisez-les.

Base64, empreintes, identifiants — n_pbt_crypto #

Le base64 (texte ou fichier), les empreintes SHA et les identifiants uniques vivent dans le composant crypto : of_base64_encode, of_base64_encode_file, of_sha256, of_hash_file, of_uuid… Une seule page pour tout ce qui se calcule sans rien afficher.

Expressions régulières — u_pbt_regex #

Syntaxe ECMAScript, absente de PowerScript.

Sans clé qui la couvre, u_pbt_regex est en mode démo : le texte fouillé fait 2048 caractères au plus, au-delà l'appel échoue et of_get_last_error() le dit. Pour que la clé qui couvre votre application s'applique, posez ipo_owner sur l'objet qui l'utilise (lnv_re.ipo_owner = this), comme pour crypto.

// Local variables
u_pbt_regex lnv_re
string ls_found[], ls_email, ls_date, ls_input, ls_text, ls_year, ls_clean
long ll_nb

// Un objet pour toutes les recherches : le creer, s'en servir, le detruire
lnv_re = create u_pbt_regex

if lnv_re.of_is_match(/*pattern*/ "^[\w.]+@[\w.]+\.\w{2,}$", /*input*/ ls_email) then …

ls_year = lnv_re.of_match(/*pattern*/ "(\d{4})-(\d{2})-(\d{2})", /*input*/ ls_date, /*group*/ 1)
ls_clean = lnv_re.of_replace(/*pattern*/ "\s+", /*input*/ ls_input, /*replacement*/ " ")
ll_nb = lnv_re.of_match_all(/*pattern*/ "[A-Z]{2}\d{6}", /*input*/ ls_text, /*matches*/ ls_found)

destroy lnv_re
MéthodeRôle
of_is_match (motif, texte [, ab_ignore_case | al_flags])Le texte correspond-il ?
of_match (motif, texte, ai_groupe [, al_flags])Première correspondance (0 = tout, 1.. = groupe capturant)
of_match_all (motif, texte [, ai_groupe, al_flags], ref as_res[])Toutes les correspondances ; renvoie le nombre
of_replace (motif, texte, remplacement)Remplace toutes les occurrences ($1… autorisés)

Options combinables : FLAG_IGNORE_CASE (1), FLAG_SINGLELINE (2, le . traverse les sauts de ligne).

Archives ZIP — u_pbt_zip #

// Local variables
u_pbt_zip lnv_zip

// Compresser un dossier, puis extraire l'archive ailleurs
lnv_zip = create u_pbt_zip
lnv_zip.of_compress(/*zip*/ "C:\temp\livraison.zip", /*src*/ "C:\appli\export")   // fichier OU dossier
lnv_zip.of_extract(/*zip*/ "C:\temp\livraison.zip",  /*dest*/ "C:\appli\import")   // dossier cree si absent
destroy lnv_zip

Les deux méthodes renvoient un boolean.

Sans clé qui la couvre, u_pbt_zip est en mode démo : ce qu'il compresse (fichier ou dossier, au total) et l'archive qu'il extrait font 2048 octets au plus ; au-delà la méthode rend false et of_get_last_error() le dit. Posez ipo_owner sur l'objet qui l'utilise (lnv_zip.ipo_owner = this) pour que la clé de votre application s'applique.


6.8 Informations sur la bibliothèque #

// Local variables
long ll_version

// Version de la DLL : un long, majeure x 10000 + mineure x 100 + correctif
ll_version = PBT_GetVersion()   // 40000 = 4.00.00
Fonction globaleRôle
PBT_GetVersion ( ) → longVersion de la bibliothèque : 40000 = 4.00.00 (majeure × 10000 + mineure × 100 + correctif)
PBT_CheckRuntime (ref string, long)Version du runtime WebView2 installé (≤ 0 = absent)
PBT_GetLastErrorMessage (ref string, long)Dernier message d'erreur du processus
PBT_LicenseStatus ( )État de la licence — voir Licence

6.9 Imprimer #

Tout composant sait s'imprimer, tel qu'affiché, sans DataWindow intermédiaire.

// Silencieux : un PDF sur disque, rien à cliquer
uo_grid.of_print_to_pdf(/*path*/ "C:\etats\ventes.pdf")

// Paysage, pour une grille large
uo_grid.of_print_to_pdf(/*path*/ "C:\etats\ventes.pdf", /*landscape*/ true)

// Avec dialogue : l'utilisateur choisit son imprimante et voit l'aperçu
uo_grid.of_print()

// Directement le dialogue système d'impression
uo_grid.of_print(/*system_dialog*/ /*dialogue systeme*/ true)
MéthodeRôle
of_print_to_pdf (string as_path) · of_print_to_pdf (string, boolean ab_paysage)Écrit un PDF sans rien afficher. Ne rend la main qu'une fois le fichier écrit (0 = fait)
of_print ( ) · of_print (boolean ab_dialogue_systeme)Ouvre le dialogue d'impression. Rend la main dès que le dialogue est ouvert : ce que l'utilisateur en fait ensuite lui appartient

⚠️ Ce qui est imprimé est ce qui est RENDU. Une grille virtualisée n'imprime que les lignes qu'elle détient : pour un état complet, passez d'abord par une mise en page qui les affiche toutes (pagination), ou exportez les données plutôt que le rendu.

Le code retour -6 signale un runtime WebView2 trop ancien pour imprimer (1.0.1108 pour le PDF, 1.0.1587 pour le dialogue). Tout le reste suit les codes retour communs.



← Langue et RTL · Sommaire · FAQ →