This topic is locked

Guide 17 - Improve Video Viewing

6/3/2021 11:34:14 AM
PHPRunner Tips and Tricks
fhumanes author

This example arises from the need to improve the standard solution that facilitates Phprunner for video viewing.

According to the example, I evaluated that it could also be very interesting for Phprunner users to learn to manage and visualize the possibility of uploading different files and storing these in File System of the server, maintaining the reference to the files in a field From the database in JSON format (standard format that Phprunner uses). I have made a set of very useful functions for users who use this type of storage.

Objective

Use a video viewing plugin that is more modern and better features, than the product is standard. Also, teach and facilitate a series of functions that improves the management of this type of fields.

DEMO: https://fhumanes.com/videos

All explanation, an example project, you can get it on my portal:

https://fhumanes.com/blog/guias-desarrollo/guia-17-phprunner-mejorar-la-visualizacion-de-videos/

fhumanes author 6/3/2021

Technical solution

To show the possibilities I have use a single table with 3 fields.

SELECT
id_videos,
title,
videos,
videos videos2,
videos videos3
FROM videos

As you can see, the "videos" field is 3 times, because we are going to use 3 ways to represent the same data.

img alt

We already see on the LIST page that we can offer 3 ways to represent the content:

  • Report textually from the content of files that the field has
  • Facilitate the miniatures of the images (only images) in the field
  • Facilitate the first of the images, blurred, and above the summary of the content of the field.

img alt
This is the aspect that Phprunner has to visualize 2 files in MP4 format, which have been uploaded to a field.

As you can appreciate it is quite outdated and impractical, hence a user has requested a plugin that improves the representation and is more functional.

To produce this improvement I have used the VideoJS plugin, which has this URL for documentation and unloading.
Video.js - Make Your Player Yours

The aspects resulting from using this plugin and the functions made are:
img alt

Like on the LIST page, on this page view there are 3 formats other than the information.

In the videos3 field it is where we can see the plugin whose most important features are:

  • A viewing area with a cover image of the content of the video.
  • A menu (on the left) with all the videos, each with its cover.
  • The name of each video, which takes it from the name of the file.

The example associates cover image to the video by having the same file name.
img alt

In this case, having only a video appears this and the menu of the videos is deleted.

How has it been done?

In the example project, which will be at the end of the article to be able to download, in the section of Custom File I have put:

  • videojs directory, which are the sources of the plugin.
  • The analysis_of_files.php file, which are the set of functions to treat the contents of the data storage fields of the files.
  • The custom_image_style.css file, which I use it for the viewing of content on LIST pages.
  • The custom_video.css file, which describes the customization of the presentation of the videos on VIEW pages.

analysis_of_files.php

<?php
// Funcines para reconocer los ficheros contenidos en un campo de almacenamiento de ficheros
// Functions to recognize the files contained in a field

function countFiles($field){
$fileArray = my_json_decode($field);
return count($fileArray);
}

function countImagesVideos($field) {
$fileArray = my_json_decode($field);
$countImage = 0;
$countVideo = 0;
foreach ($fileArray as &$file) {
$type = $file['type'];
$parts = explode("/", $type);
switch ($parts[0]) {
case "video":
$countVideo += 1;
break;
case "image":
$countImage += 1;
break;
}
}
return array($countImage, $countVideo);
}

function arrayImages($field) {
$return = [];
$fileArray = my_json_decode($field);
foreach ($fileArray as &$file) {
$type = $file['type'];
$parts = explode("/", $type);
if ( $parts[0] == 'image' ) {
$return[] = $file['usrName'];
}
}
return $return;
}

function onlyImages($field) {
$numDelete = 0;
$fileArray = my_json_decode($field);
$return = $fileArray;
for ($i = 0; $i < count($fileArray); $i++) {
$type = $fileArray[$i]['type'];
$parts = explode("/", $type);
if ( $parts[0] <> 'image' ) {
unset($return[$i]);
$numDelete += 1;
}
}
$return = my_json_encode($return);
return $return;
}

function arrayVideos($field) {
$return = [];
$fileArray = my_json_decode($field);
foreach ($fileArray as &$file) {
$type = $file['type'];
$parts = explode("/", $type);
if ( $parts[0] == 'video' ) {
$return[] = $file['usrName'];
}
}
return $return;
}

function searchImageOfVideo($field,$nameVideo) {
$fileArray = my_json_decode($field);
$parts = explode(".", $nameVideo);
$name = $parts[0]; // name without extension

foreach ($fileArray as &$file) {
$type = $file['type'];
$parts = explode("/", $type);
if($parts[0] == 'image') {
$parts2 = explode(".", $file['usrName']);
if ( $parts2[0] == $name ) { // Found File image equal name to the video file
return array(true, $file['usrName']);
}
}
}
return array(false, NULL);
}

function searchMimeType($field,$nameFile) {
$fileArray = my_json_decode($field);

foreach ($fileArray as &$file) {

if($file['usrName'] == $nameFile) {
return $file['type'];
}
}
return '';
}

To include the code (LIST page) I have used the event list page:Before record processed:

include_once "MyCode/analysis_of_files.php";

$countFiles = countFiles($data['videos']);
$countTypes = countImagesVideos($data['videos']);
$countImage = $countTypes[0];
$countVideo = $countTypes[1];
$data['videos'] = 'Files: **'.$countFiles.'**<BR> Images: **'.$countImage.'**<BR> Videos: **'.$countVideo.'**';

$data['videos2'] = onlyImages($data['videos2']);
// List Video3 ---------------------------------------------
$arrayImages = arrayImages($data['videos3']);
$countFiles = countFiles($data['videos3']);
$countTypes = countImagesVideos($data['videos3']);
$countImage = $countTypes[0];
$countVideo = $countTypes[1];

if ( $countImage <> 0 ) { // There are images

$img = '<img src="mfhandler.php?file='.$arrayImages[0].
'&table=videos&field=videos3&'.
'pageType=list&page=list&key1='.$data['id_videos'].
'" class="img-thumbnail" alt="'.$arrayImages[0].'" width="150" height="100">';

$textCount = 'Files: **'.$countFiles.'**<BR> Images: **'.$countImage.'**<BR> Videos: **'.$countVideo.'**';
$data['videos3'] = <<<EOT
<link REL="stylesheet" href="MyCode/custom_image_style.css" type="text/css">
<div class="custom_image_container">
$img
<div class="custom_image_top-left">$textCount</div>
</div>
EOT;

} else {
$data['videos3'] = 'Files: **'.$countFiles.'**<BR> Images: **'.$countImage.'**<BR> Videos: **'.$countVideo.'**';
}
return true;

To include the code (page VIEW) I have used the event Process record values:

include_once "MyCode/analysis_of_files.php";

$values['videos2'] = onlyImages($values['videos2']);
// ---------------- For field "video3" ------------------
$arrayVideos = arrayVideos($values['videos3']);
$countVideos = count($arrayVideos);
if ( $countVideos <> 0 ) { // There are videos
$part = searchImageOfVideo($values['videos3'],$arrayVideos[0]);
$nameVideo = '';
$img = '';
if ($part[0] == true ) { // There is a video image file
$nameVideo = $part[1];
$img0 .= 'poster="mfhandler.php?file='.$nameVideo.
'&table=videos&field=videos3&'.
'pageType=view&page=view&key1='.$values['id_videos'].
'" ';
}
$src0 = 'src="mfhandler.php?file='.$arrayVideos[0].
'&table=videos&field=videos3&'.
'pageType=view&page=view&key1='.$values['id_videos'].'"'.
' type="'.searchMimeType($values['videos3'],$arrayVideos[0]).'" '; // First video

// ---- More of 1 video ---------------------
$div_playList = '';
$playList = '';
if ($countVideos > 1 ) {
$div_playList = <<<EOT
<div class="vjs-playlist">
<!--
The contents of this element will be filled based on the
currently loaded playlist
-->
</div>
EOT;

$playList = ' player.playlist([';
foreach ($arrayVideos as &$file) {
$parts = explode(".", $file);
$name = $parts[0];
$src = 'src: "mfhandler.php?file='.$file.
'&table=videos&field=videos3&'.
'pageType=view&page=view&key1='.$values['id_videos'].'"'.
', type: "'.searchMimeType($values['videos3'],$file).'" ';

$parts = searchImageOfVideo($values['videos3'],$file);
$img = '';
if ($parts[0] == true ) { // There is a video image file
$nameVideo = $parts[1];
$img = 'src: "mfhandler.php?file='.$nameVideo.
'&table=videos&field=videos3&'.
'pageType=view&page=view&key1='.$values['id_videos'].
'" ';
}

$playList .= <<<EOT
{
name: '$name',
sources: [
{ $src },
],
thumbnail: [
{
$img
}
]
},
EOT;
}
$playList .=<<<EOT
]);

// Initialize the playlist-ui plugin with no option (i.e. the defaults).
player.playlistUi();
EOT;
}

$values['videos3'] = <<<EOT
<link href="MyCode/videojs/video-js.css" rel="stylesheet">
<link href="MyCode/custom_video.css" rel="stylesheet">
<link href="MyCode/videojs/plugin/videojs-playlist-ui.css" rel="stylesheet">

<div class="player-container">
<video
id="custom_video"
class="video-js"
height="200"
width="400"
$img0
controls>
<source $src0 >
</video>
$div_playList
</div>

<script src="MyCode/videojs/video.js"></script>
<script src="MyCode/videojs/plugin/videojs-playlist.js"></script>
<script src="MyCode/videojs/plugin/videojs-playlist-ui.js"></script>
<script>
var player = videojs('custom_video');

player.ready(function() {
var promise = player.play();
if (promise !== undefined) {
promise.then(function() {
console.log('AutoPlay yes');
}).catch(function(error) {
console.log('AutoPlay no');
});
}
});

$playList
</script>
EOT;
}

I hope and I want you to be of interest to you shown in the example and for any question you can contact me through my email fernandohumanes@gmail.com.

The example is made in PHPRunner 10.5 and the downloadable zip is the project, the backup of the table used and the file directory that contains the files that refers in the contents of the table.

fhumanes author 6/5/2021

Hello:

I have corrected an error on the LIST page and it was when there was no image with the videos.

Sorry.

Greetings,
fernando

C
Corrie 6/7/2021

Very nice. Thank you for sharing.
There is a lot here that I will use.