PBToolboxAI v4 ← Site

video — u_pbt_video #

← Référence des composants · Sommaire du guide

Lecteur vidéo : un fichier du poste — servi en flux par la DLL, un long film démarre tout de suite — ou une URL, avec la barre de transport du composant, qui suit le thème : lecture, recherche, temps, muet, volume. Sous-titres WebVTT, affiche avant lecture, boucle, vitesse, cadrage, capture de l'image courante en PNG ou JPEG. Tout ce que l'utilisateur fait sur la barre, votre application le sait.

▶ Le voir en vrai — Application de démonstration, tuile Video player : le film, le code qui le pilote et cette page, côte à côte (connexion Internet requise pour le film d'exemple).


En bref #

Userobjectu_pbt_video
Classe d'items— (composant sans items)
Sert àUn film de formation dans l'application, la vidéo d'un produit, la relecture d'un enregistrement, une boucle de présentation sur un stand
PrincipeUn <video> du moteur WebView2 : tous les formats qu'il décode (mp4, webm, m4v, mov, mkv). La barre est celle du composant ; ses gestes passent par les mêmes verbes que vos appels, donc les mêmes événements
DépendanceLe runtime WebView2, déjà requis par la bibliothèque — rien d'autre

Démarrage rapide #

// A film of the workstation, streamed by the DLL : starts at once
uo_video.is_poster = "img\packimages.dll:PNG/COVER"   // shown until the film starts
uo_video.is_subtitles = "films\training.vtt"
uo_video.of_play(/*source*/ "films\training.mp4")

// A URL plays the same way
uo_video.of_play(/*source*/ "https://www.w3schools.com/html/mov_bbb.mp4")

// The user pauses from the bar, or your code does : either way ue_paused fires
uo_video.of_pause()
uo_video.of_seek(/*ms*/ 90000)          // to 1:30, in milliseconds

Tout ce qui se règle est une propriété (is_source, ii_volume, ib_loop…), lue en direct sur le composant ; ce qui se fait est une méthode (of_play, of_pause, of_stop, of_seek, of_capture) ; ce qui arrive est un événement (ue_started, ue_ended, ue_progress…). Un fichier absent n'est pas une exception : ue_failed le dit, et le message s'affiche sur l'image.


Propriétés #

PropriétéTypeDéfautRôle
is_sourcestring""Le film : un fichier du poste (n'importe quel chemin, servi en flux) ou une URL https. Une adresse http:// est refusée (ue_failed, REASON_INSECURE) : le moteur la promeut en https et échoue — téléchargez le film d'abord (restclient, of_download). Formats : mp4, webm, m4v, mov (un film d'iPhone ou de caméra en H.264), mkv, et les formats audio ; avi, wmv et flv sont refusés par leur nom (REASON_FORMAT). Le poser arrête ce qui jouait ; ib_autoplay décide si le nouveau démarre seul. Un film de n'importe quelle taille, en 32 bits aussi : la DLL le sert par tranches, jamais le fichier entier d'un coup ; un film que le moteur ne décode pas est signalé par ue_failed. Un NOUVEAU film laisse derrière lui ce qui appartenait à l'ancien : son segment, ses sous-titres, ses marqueurs et ses chapitres (posés avant tout film, ils attendent le premier) ; un film de la liste de lecture garde ses propres sous-titres
ib_autoplaybooleanfalseDémarre le film dès que is_source est posé ; sinon il attend of_play, la barre ou le clavier, et montre is_poster
ib_mutedbooleanfalseCoupe le son, volume conservé ; le bouton de la barre et la touche M le posent aussi
ii_volumeinteger100Volume en pour cent, 0 à 100 ; le curseur de la barre et les flèches haut/bas aussi
ib_loopbooleanfalseRejoue le film en boucle jusqu'à of_stop ; un film en boucle ne lève jamais ue_ended
ii_rateinteger100Vitesse en pour cent, 25 à 400 : 50 = moitié, 200 = double, le son suit
is_stretchstring"uniform"Cadrage : STRETCH_NONE, STRETCH_FILL, STRETCH_UNIFORM, STRETCH_UNIFORMTOFILL — les quatre modes d'une image
ib_controlsbooleantrueLa barre de transport du composant, au thème. false la masque : votre fenêtre pilote le film
is_posterstring""L'affiche montrée avant le film : fichier, URL ou pack.dll:NOM, comme la source d'une image. Un préfixe mono:/tint:/white:/black: recolore une image monochrome au thème
is_subtitlesstring""Un fichier de sous-titres, local ou URL https : WebVTT (.vtt) ou SubRip (.srt, converti — UTF-8, UTF-16 ou la page de code ANSI du poste). Une URL est TÉLÉCHARGÉE par le composant : son serveur doit autoriser CORS (GitHub, un CDN le font) ; un refus, ou une URL http://, est dit par ue_subtitles_failed et le film continue. Une piste ; of_add_subtitles en empile plusieurs. Il appartient au film : un nouvel is_source le retire
is_subtitle_langstring""La piste de sous-titres affichée (langue d'of_add_subtitles) ; vide = aucune
ii_fpsinteger25Images par seconde du film, pour of_step_frames
ib_remember_positionbooleanfalseRetient où chaque film est laissé et y reprend au prochain of_play de la même source
is_theme_stylestring""Style visuel du composant (constantes THEME_STYLE_*) ; vide = celui de l'application, suivi à chaque changement
is_theme_modestring""Variante claire ou sombre (constantes THEME_MODE_*) ; vide = celle de l'application, suivie à chaque changement
il_theme_accentlong-1Couleur d'accent de ce composant (-1 = l'accent de l'application, ou celui du thème)
is_tooltipstring""Info-bulle simple affichée au survol du composant
is_super_tooltip_titlestring""Titre de l'info-bulle enrichie (prend le pas sur is_tooltip)
is_super_tooltip_textstring""Texte de l'info-bulle enrichie (balisage riche accepté)
is_super_tooltip_imagestring""Image de l'info-bulle enrichie
ib_enabledbooleantruefalse : image assombrie, barre et clavier inertes — sauf Échap en plein écran : on peut toujours en sortir ; votre code commande toujours
ib_scrub_previewbooleantrueUne bulle de temps suit le curseur sur la barre de défilement (true, par défaut), avec le chapitre s'il y en a. false la masque
ib_pause_when_hiddenbooleantrueMet le film en pause quand le composant est MASQUÉ (une autre page d'un tab ou d'un dock PBToolboxAI, PBT_SetVisible) : ue_paused suit, et le film attend of_play, il ne reprend jamais seul. false le laisse jouer (un mur d'écrans). Un Tab NATIF de PowerBuilder ne prévient pas le composant : appelez of_pause dans son SelectionChanged

Un clic sur l'image met en pause, un second reprend. Clavier, quand le film a le focus : Espace ou K lecture/pause, ←/→ cinq secondes, ↑/↓ volume, M muet, Début/Fin.


Méthodes #

MéthodeRôle
of_play ( ) → longJoue is_source d'où il est : du début la première fois, de la pause ensuite (ue_resumed). Rend 0 une fois envoyé, -2 si le composant n'est pas créé
of_play (string as_source) → longPose is_source et le joue : le même appel que celui du lecteur de sons. Rend 0 une fois envoyé, -1 sans composant
of_pause ( ) → longSuspend le film où il est ; of_play le reprend. Rend 0 une fois envoyé, -1 sans composant
of_stop ( )Arrête le film et revient à son début ; ue_stopped suit
of_seek (long al_ms) → longSe place à une position du film, en millisecondes, en lecture ou non ; un fichier local cherche tout de suite. ue_seeked suit, comme pour la barre. Rend 0 une fois envoyé, -2 si le composant n'est pas créé
of_is_playing ( ) → booleanVrai tant qu'un film est en cours — en pause compris, il n'est pas fini
of_is_paused ( ) → booleanVrai tant que le film est suspendu — par of_pause, la barre ou le clavier
of_is_buffering ( ) → booleanVrai tant que le film TOURNE mais attend ses données — le temps que ue_buffering a annoncé. Lu dans le composant, jamais dans une copie
of_duration ( ) → longRend le nombre de millisecondes que dure le film, 0 tant qu'il est inconnu
of_position ( ) → longRend le nombre de millisecondes lues depuis le début ; ue_progress l'apporte aussi chaque seconde
of_capture (string as_path) → longEnregistre l'image montrée maintenant, à la taille du film : of_capture(as_path, 0). L'EXTENSION choisit le format : .jpg ou .jpeg écrit un JPEG, tout le reste un PNG ; attend la première image décodée (10 s au plus), donc peut suivre of_play directement. Rend 0 une fois écrite, -4 sans film, avec un film qui n'a pas pu se charger, sans image à temps, quand un film d'un autre site refuse ses pixels ou quand le fichier ne peut pas être écrit, -5 sur un chemin vide ou qui dépend du dossier courant (\x, C:x), -2 si le composant n'est pas créé ; après un retour négatif, of_get_last_error dit pourquoi. Un chemin relatif s'écrit dans le dossier où l'application a démarré (le dossier courant au chargement de la bibliothèque, le même dans l'IDE et compilé)
of_capture (string as_path, long al_max_width) → longLa même capture, RÉDUITE à al_max_width pixels de large (hauteur en proportion) : la vignette d'un film 4K n'est pas une image 4K. 0 garde la taille du film. Mêmes retours qu'of_capture(as_path)
of_fullscreen (boolean ab_on) → longLe film sur TOUT le moniteur (la DLL déplace le contrôle dans une fenêtre à elle ; votre fenêtre n'est pas touchée), ou de retour. Au-dessus de tout tant qu'il est la fenêtre active : Alt+Tab vers une autre application la fait passer devant, et revenir à votre application ramène le film au-dessus de tout. Double-clic, le bouton de la barre, Échap, Alt+F4. Échap sort même quand ib_enabled est faux. Ces gestes et cet appel lèvent ue_fullscreen_changed (of_is_fullscreen le lit). Rend 0, -2 si le composant n'est pas créé
of_is_fullscreen ( ) → booleanVrai tant que le film couvre le moniteur
of_add_marker (long al_ms, string as_label) → longUn MARQUEUR sur la barre : un repère cliquable, et ue_marker_reached quand le film le passe. Rend 0, -5 sur une position négative, -2 si le composant n'est pas créé
of_clear_markers ( ) → longRetire tous les marqueurs. Rend 0, -2 si le composant n'est pas créé
of_marker_count ( ) → longRend le nombre de marqueurs
of_play_range (long al_from_ms, long al_to_ms) → longJoue UN segment : à la fin, ue_ended, ou avec ib_loop le segment reprend. Rend 0, -5 sur des bornes sans sens, -2 si le composant n'est pas créé
of_clear_range ( ) → longLibère le film de son segment. Rend 0, -2 si le composant n'est pas créé
of_step_frames (long al_frames) → longAvance ou recule d'al_frames images (ii_fps) et met en pause ; touches . et , sur l'image. ue_seeked suit, comme pour les touches. Rend 0, -2 si le composant n'est pas créé
of_add_source (string as_source) → longAjoute un film à la LISTE DE LECTURE : le premier devient is_source (par-dessus un film posé avant, sauf s'il JOUE : la liste le suit alors à sa fin), les suivants s'enchaînent d'eux-mêmes (ue_source_changed pour chaque film qui suit, et pour le premier quand cet appel le charge). Rend 0, -5 sur une source vide, -2 si le composant n'est pas créé
of_add_source (string as_source, string as_subtitles) → longAjoute un film AVEC son fichier de sous-titres (.vtt ou .srt, converti par la DLL) : le sous-titre appartient à ce film et s'affiche seulement quand il passe. La façon simple et sans ambiguïté de sous-titrer une liste. Rend 0, -5 sur une source vide
of_clear_playlist ( ) → longVide la liste ; le film en cours continue. Rend 0, -2 si le composant n'est pas créé
of_next ( ) / of_previous ( ) → longLe film suivant ou précédent de la liste ; of_playlist_index dit où elle en est, et ue_source_changed suit. Rend 0, -2 si le composant n'est pas créé
of_playlist_count ( ) → longRend le nombre de films de la liste
of_playlist_index ( ) → longRend l'indice (depuis 1) du film de la liste en cours, 0 hors liste
of_add_subtitles (string as_lang, string as_source) → longUne piste de sous-titres par langue : .vtt, ou .srt converti, du poste ou d'une URL https (téléchargée : CORS requis, voir ue_subtitles_failed). Le bouton CC de la barre les fait défiler. Rend 0, -5 sur une source vide, une langue déjà posée sur le film (of_remove_subtitles d'abord) ou qui contient / ou `, -2` si le composant n'est pas créé
of_remove_subtitles (string as_lang) → longRetire la piste d'une langue du film à l'écran (et du film de la liste qui joue : elle ne revient pas sur of_previous). La piste d'is_subtitles s'appelle default. Rend 0, -5 pour une langue que le film ne porte pas, -2 si le composant n'est pas créé
of_subtitle_count ( ) → longRend le nombre de pistes de sous-titres
of_remembered_position ( ) → longRend le nombre de millisecondes où is_source a été laissé (ib_remember_position), 0 sinon
of_has_output ( ) → booleanVrai si le poste a une sortie audio
of_add_chapter (long al_ms, string as_title) → longUn CHAPITRE (table des matières) : ue_chapter_changed quand la lecture y entre. of_go_chapter y saute (à partir de 1), of_next_chapter / of_previous_chapter les parcourent (chaque saut lève ue_seeked et ue_chapter_changed), of_chapter_count / of_chapter_index / of_chapters les lisent, of_clear_chapters les vide. Rend 0, -5 si négatif (numéros à partir de 1)
of_clear_chapters ( ) → longRetire tous les chapitres ; la barre et la bulle de survol les oublient. Rend 0, -2 si le composant n'est pas créé
of_go_chapter (long al_index) → longSaute au chapitre al_index (à partir de 1, dans l'ordre de of_add_chapter) ; of_chapter_index le lit aussitôt, et ue_seeked puis ue_chapter_changed suivent, comme pour un clic sur la barre. Rend 0, -5 pour un numéro inférieur à 1 ou supérieur à of_chapter_count(), -2 si le composant n'est pas créé
of_next_chapter ( ) → longSaute au chapitre qui suit la position courante; of_chapter_index le lit aussitôt, et ue_seeked puis ue_chapter_changed suivent. Rien ne bouge depuis le dernier chapitre. Rend 0, -2 si le composant n'est pas créé
of_previous_chapter ( ) → longSaute au chapitre qui précède celui où se trouve la lecture; of_chapter_index le lit aussitôt, et ue_seeked puis ue_chapter_changed suivent. Rien ne bouge depuis le premier chapitre. Rend 0, -2 si le composant n'est pas créé
of_chapter_count ( ) → longRend le nombre de chapitres du film (of_add_chapter), 0 sans
of_chapter_index ( ) → longRend le numéro (à partir de 1) du chapitre où se trouve la lecture, 0 avant le premier ou sans chapitre. Lu en direct
of_chapters (ref long al_ms[], ref string as_titles[]) → longRemplit les chapitres dans l'ordre — la position de chacun en ms dans al_ms, son titre dans as_titles — pour bâtir un menu à vous ; un titre peut contenir n'importe quel caractère. Rend le nombre de chapitres, 0 sans
of_picture_in_picture (boolean ab_on) → longLe film dans une fenêtre flottante à lui (true) ou de retour (false) ; ue_pip_changed suit, comme quand l'utilisateur ferme la petite fenêtre. of_is_pip dit s'il flotte, of_pip_available si le poste l'autorise. Rend 0, -2 si le composant n'est pas créé
of_is_pip ( ) → booleanVrai tant que le film flotte dans sa fenêtre Picture-in-Picture ; faux de nouveau quand l'utilisateur la ferme
of_pip_available ( ) → booleanVrai si le moteur et le poste autorisent le Picture-in-Picture : à demander avant d'offrir le bouton

Événements #

ÉvénementQuand
ue_started (long al_duration_ms)Le film démarre vraiment ; la longueur quand le fichier la dit, 0 sinon
ue_ended (boolean ab_truncated)Le film est fini de lui-même ; ab_truncated vrai quand la limite démo l'a coupé
ue_failed (string as_message, string as_reason)Le film n'a pas pu jouer. as_reason le dit en un mot que votre code teste : REASON_INSECURE (source http://), REASON_FORMAT (avi, wmv, flv, ou un format que le moteur déclare illisible), REASON_UNSUPPORTED (fichier absent ou conteneur non décodable), REASON_DECODE, REASON_NETWORK, REASON_NO_SOURCE, REASON_FAILED ; as_message est le texte affiché sur l'image
ue_stopped ( )of_stop a coupé un film en cours
ue_paused ( ) / ue_resumed ( )Le film est suspendu, puis reprend — par votre code, la barre ou le clavier, indifféremment ; aussi quand le composant est masqué (ib_pause_when_hidden)
ue_progress (long al_position_ms, long al_duration_ms)Une fois par seconde pendant la lecture : ce qu'une barre de progression à vous attend, sans timer
ue_seeked (long al_position_ms)La position a bougé : l'utilisateur (barre, flèches, marqueur) ou votre code — of_seek, of_step_frames et les fonctions de chapitre le lèvent aussi, comme le geste
ue_volume_changed (long al_percent)L'utilisateur a tourné le volume ; jamais ii_volume
ue_rate_changed (long al_percent)L'utilisateur a choisi une vitesse sur la barre ; jamais ii_rate
ue_subtitles_changed (string as_lang)L'utilisateur a fait défiler les sous-titres (CC) ; vide = aucun
ue_muted_changed (boolean ab_on)L'utilisateur a coupé (true) ou rendu (false) le son — le haut-parleur de la barre, la touche M ; jamais ib_muted
ue_fullscreen_changed (boolean ab_on)Le film est passé plein écran, ou en est revenu : double-clic, le bouton, Échap, Alt+F4, ou of_fullscreen. of_reset ne le lève jamais
ue_marker_reached (long al_ms, string as_label)Le film passe un marqueur
ue_source_changed (long al_index, string as_source)La liste de lecture passe à un autre film : d'elle-même, le précédent ayant fini, ou par of_next, of_previous et le premier of_add_source
ue_chapter_changed (long al_index, string as_title)La lecture entre dans un autre chapitre (of_add_chapter) : son numéro (à partir de 1, 0 avant le premier) et son titre ; aussi quand l'utilisateur ou votre code (of_go_chapter, of_next_chapter, of_previous_chapter) y saute
ue_pip_changed (boolean ab_on)Le film est entré (true) dans la fenêtre Picture-in-Picture ou en est sorti (false) : l'utilisateur l'a fermée, le moteur y a mis le film de lui-même, ou of_picture_in_picture l'a demandé (of_is_pip le lit)
ue_subtitles_failed (string as_lang, string as_reason)Un fichier de sous-titres n'a pas pu se charger : une URL https dont le serveur refuse CORS ou répond une erreur (REASON_NETWORK, REASON_NOT_FOUND), une URL http:// (REASON_INSECURE). La piste est retirée, le film continue
ue_buffering (boolean ab_on)Le film TOURNE mais doit attendre ses données plus d'un quart de seconde (true) — un réseau lent, un saut loin dans un film d'une URL : un anneau à l'accent du thème tourne sur l'image — puis l'attente prend fin (false) : le film repart, ou a été mis en pause, arrêté, remplacé, ou a échoué. of_reset ne le lève jamais

Plein écran, marqueurs, segment, image par image #

// Chapters on the bar, then one extract in a loop
uo_video.of_add_marker(/*ms*/ 2000, /*label*/ "Intro")
uo_video.of_add_marker(/*ms*/ 5000, /*label*/ "The bunny")
uo_video.ib_loop = true
uo_video.of_play_range(/*from_ms*/ 2000, /*to_ms*/ 8000)

// Surveillance : back one picture at a time
uo_video.ii_fps = 30
uo_video.of_step_frames(/*frames*/ -1)

Liste de lecture, sous-titres, reprise, formats #

// A playlist, each film WITH its subtitles, the position remembered
uo_video.ib_remember_position = true
uo_video.of_add_source(/*source*/ "intro.mp4", /*subtitles*/ "intro.en.vtt")
uo_video.of_add_source(/*source*/ "lesson-1.mp4", /*subtitles*/ "lesson-1.en.srt")   // .srt : converted by the DLL
uo_video.of_play()

// A second language for the film on screen : it stays with that film
uo_video.of_add_subtitles(/*lang*/ "fr", /*source*/ "intro.fr.vtt")
uo_video.is_subtitle_lang = "fr"

Exemples #

Une boucle de présentation, silencieuse, sans barre #

// A silent showcase film, in a loop, without its bar
uo_video.ib_controls = false
uo_video.ib_muted = true
uo_video.ib_loop = true
uo_video.is_stretch = u_pbt_video.STRETCH_UNIFORMTOFILL
uo_video.of_play(/*source*/ "films\showcase.mp4")

Vos propres boutons et une barre de progression #

// cb_play.clicked
if uo_video.of_is_paused() or not uo_video.of_is_playing() then uo_video.of_play() else uo_video.of_pause()

// uo_video.ue_progress : once a second, no timer needed
hpb_progress.Position = al_position_ms * 100 / Max(al_duration_ms, 1)

Une vignette du film pour un rapport #

// Stop the film on the picture to keep
uo_video.of_play(/*source*/ "films\training.mp4")
uo_video.of_pause()
uo_video.of_seek(/*ms*/ 15000)                 // the frame at 0:15

// of_capture waits for the picture itself (10 s at most) : no timer to write.
// A .jpg path writes a JPEG ; 320 : a thumbnail 320 pixels wide.
// A relative path goes to the folder the application started in.
if uo_video.of_capture(/*path*/ "C:\Reports\training.jpg", /*max_width*/ 320) < 0 then MessageBox("Capture", uo_video.of_get_last_error())

Bonnes pratiques #

Hérité du socle commun #

Ces membres existent sur tous les composants visuels — ils ne sont pas propres à celui-ci. Ils sont détaillés une seule fois, dans les chapitres transverses ; cette table dit seulement où les lire.

MembresRôleDétaillé dans
of_resetRemettre le composant à zéro3.6 Remettre un composant à zéro : of_reset()
of_register_shortcut · of_clear_shortcutsRaccourcis clavier du composant3.5 Les raccourcis clavier
of_is_created · of_is_ready · of_get_last_errorS'il est né, s'il est prêt, ce qui a échoué3.7 Diagnostic
of_save_as_png · of_save_as_jpgExporter le rendu en image3.8 Exporter le rendu en image
of_set_redrawGrouper les modifications en un seul repaint3.10 Bonnes pratiques
of_preload_iconsIcônes affichées sans délaiAffichage instantané : of_icon
of_set_translationTraduire un libellé du composant5.2 Adapter un libellé : of_set_translation
of_focus_webviewDonner le focus au composant6.4 Clavier et focus
of_print · of_print_to_pdfImprimer, ou écrire un PDF6.9 Imprimer
of_set_property · of_get_property · of_component_namePiloter une propriété par son nom3.1 Le moteur de propriétés

← Référence des composants · Sommaire du guide