Added support for MP4 uploads and gif to mp4 conversions

This commit is contained in:
Christian Haschek
2015-11-23 19:56:54 +01:00
parent bfbc107d7e
commit c42679b3ac
4 changed files with 97 additions and 11 deletions

View File

@@ -6,6 +6,7 @@ PictShare is an multi lingual, open source image hosting service with a simple r
UPDATES
========
- Nov. 23: Added support for MP4 uploads and conversion from gif to mp4
- Nov. 12: Created new git project: [Pictshare stats](https://github.com/chrisiaut/pictshare_stats)
- Nov. 07: Added 9 new (instagram-like) filters
- Nov. 06: Master delete code. One code to delete them all
@@ -48,6 +49,8 @@ If there is some option that's not recognized by PictShare it's simply ignored,
**Resizing** | | |
<width>**x**<height> | -none- | https://pictshare.net/20x20/b260e36b60.jpg | ![Resized](https://pictshare.net/20x20/b260e36b60.jpg)
forcesize | -none- | https://pictshare.net/100x400/forcesize/b260e36b60.jpg | ![Forced size](https://pictshare.net/100x400/forcesize/b260e36b60.jpg)
**GIF to mp4** | | |
mp4 | -none- | https://www.pictshare.net/mp4/102687fe65.gif | Converts gif to mp4 and displays as that. Note that you can't include that mp4 in an img tag
**Rotating** | | |
left | -none- | https://pictshare.net/left/b260e36b60.jpg | ![Rotated left](https://pictshare.net/200/left/b260e36b60.jpg)
right | -none- | https://pictshare.net/right/b260e36b60.jpg | ![Rotated right](https://pictshare.net/200/right/b260e36b60.jpg)
@@ -137,6 +140,7 @@ If you access the image with the code like this: ```https://www.pictshare.net/ch
- Make sure you have PHP5 GD libraries installed: ```apt-get install php5-gd```
- Unpack the [PictShare zip](https://github.com/chrisiaut/pictshare/archive/master.zip)
- Rename /inc/example.config.inc.php to /inc/config.inc.php
- ```chmod +x bin/ffmpeg``` if you want to be able to use mp4 uploads
- (optional) You can and should put a [nginx](https://www.nginx.com/) proxy before the Apache server. That thing is just insanely fast with static content like images.
- (optional) To secure your traffic I'd highly recommend getting an [SSL Cert](https://letsencrypt.org/) for your server if you don't already have one.
@@ -166,7 +170,7 @@ server {
fastcgi_param PATH_INFO $fastcgi_script_name;
}
location ~ /(upload|tmp) {
location ~ /(upload|tmp|bin) {
deny all;
return 404;
}

BIN
bin/ffmpeg Normal file

Binary file not shown.

View File

@@ -150,8 +150,22 @@ function renderImage($data)
imagepng($im);
break;
case 'gif':
if($data['mp4'])
{
header("Content-Type: video/mp4");
readfile($pm->gifToMP4($path));
}
else
{
header ("Content-type: image/gif");
$im = imagecreatefromgif($path);
readfile($path);
}
break;
case 'mp4':
header("Content-Type: video/mp4");
readfile($path);
break;
}

View File

@@ -44,6 +44,8 @@ class PictshareModel extends Model
if($this->isImage($el))
$data['hash']=$el;
else if($el=='mp4')
$data['mp4'] = 1;
else if($this->isSize($el))
$data['size'] = $el;
else if($this->isRotation($el))
@@ -68,6 +70,12 @@ class PictshareModel extends Model
return false;
}
if($data['mp4'])
{
$hash = $data['hash'];
if(!$hash || $this->getTypeOfHash($hash)!='gif')
unset($data['mp4']);
}
return $data;
}
@@ -257,10 +265,20 @@ class PictshareModel extends Model
if(count($arr)>1)
{
$a2 = explode('/', $arr[0]);
return $a2[1];
$type = $a2[1];
}
else
{
$a2 = explode('/', $type);
return $a2[1];
$type = $a2[1];
}
if($type=='mp4' && !$this->isProperMP4($url))
return false;
return $type;
}
function isTypeAllowed($type)
@@ -278,19 +296,19 @@ class PictshareModel extends Model
case 'image/gif': return 'gif';
case 'gif': return 'gif';
case 'mp4': return 'mp4';
default: return false;
}
}
function uploadImageFromURL($url)
{
$type = $this->getTypeOfFile($url);
$type = $this->isTypeAllowed($type);
$dup_id = $this->isDuplicate($url);
if($dup_id)
{
$hash = $dup_id;
@@ -400,6 +418,9 @@ class PictshareModel extends Model
if($data['status']=='OK')
{
if($data['type']=='mp4')
$o.= '<h2>'.$this->translate(4).' '.++$i.'</h2><a target="_blank" href="'.DOMAINPATH.$data['hash'].'">'.$data['hash'].'</a><br/>';
else
$o.= '<h2>'.$this->translate(4).' '.++$i.'</h2><a target="_blank" href="'.DOMAINPATH.$data['hash'].'"><img src="'.DOMAINPATH.'300/'.$data['hash'].'" /></a><br/>';
}
}
@@ -571,4 +592,51 @@ class PictshareModel extends Model
return $type;
}
function getTypeOfHash($hash)
{
$base_path = ROOT.DS.'upload'.DS.$hash.DS;
$path = $base_path.$hash;
$type = $this->isTypeAllowed($this->getTypeOfFile($path));
return $type;
}
function isProperMP4($filename)
{
$filename = '/var/www/outfile.mp4';
$file = escapeshellarg($filename);
$tmp = ROOT.DS.'tmp'.DS.md5(time()+rand(1,10000)).'.'.rand(1,10000).'.log';
$bin = escapeshellcmd(ROOT.DS.'bin'.DS.'ffmpeg');
$cmd = "$bin -i $file > $tmp 2>> $tmp";
system($cmd);
$answer = file($tmp);
unlink($tmp);
$ismp4 = false;
if(is_array($answer))
foreach($answer as $line)
{
$line = trim($line);
if(strpos($line,'Duration: 00:00:00')) return false;
if(strpos($line, 'Video: h264'))
$ismp4 = true;
}
return $ismp4;
}
function gifToMP4($gifpath)
{
$bin = escapeshellcmd(ROOT.DS.'bin'.DS.'ffmpeg');
$file = escapeshellarg($gifpath);
$mp4file = $gifpath.'.mp4';
$cmd = "$bin -f gif -i $file $file.mp4";
system($cmd);
return $mp4file;
}
}