New: Add feature to crop/resize image file on product photos

This commit is contained in:
Laurent Destailleur 2010-02-21 03:09:45 +00:00
parent 1c2728547b
commit e1e57f52ad
9 changed files with 292 additions and 54 deletions

View File

@ -34,7 +34,7 @@ if (isset($_GET["id"]))
$result=restrictedArea($user,'produit|service',$id,'product','','',$fieldid);
$original_file = isset($_GET["file"])?urldecode($_GET["file"]):'';
$original_file = isset($_REQUEST["file"])?urldecode($_REQUEST["file"]):'';
$langs->load("products");
@ -46,32 +46,28 @@ if (!$user->rights->produit->lire) accessforbidden();
* Actions
*/
if ($_POST["action"] == 'confirm_resize' && (isset($_POST["file"]) != "") && (isset($_POST["sizex"]) != "") &&(isset($_POST["sizey"]) != ""))
if ($_POST["action"] == 'confirm_resize' && (isset($_POST["file"]) != "") && (isset($_POST["sizex"]) != "") && (isset($_POST["sizey"]) != ""))
{
/* $thumb = new Imagick($conf->produit->dir_output."/".$_POST["file"]);
$height=$thumb->getImageHeight(); // dimensions de l'image actuelle
$width=$thumb->getImageWidth(); // dimensions de l'image actuelle
$fullpath=$conf->produit->dir_output."/".$_POST["file"];
$result=dol_imageResize($fullpath,$_POST['sizex'],$_POST['sizey']);
if($_POST["sizex"] != "")
if ($result == $fullpath)
{
if ($width > $_POST['sizex'])
$thumb->scaleImage(intval($_POST['sizex']), 0);
header("Location: ".DOL_URL_ROOT."/product/photos.php?id=".$_POST["product"].'&action=addthumb&file='.urldecode($_POST["file"]));
exit;
}
if($_POST["sizey"] != "")
else
{
if ($height > $_POST['sizey'])
$thumb->scaleImage(0, intval($_POST['sizey']));
$mesg=$result;
$_GET['file']=$_POST["file"];
$_GET['id']=$_POST["id"];
}
$thumb->writeImage($conf->produit->dir_output."/".$_POST["file"]);
$thumb->destroy();
*/
header("Location: ".DOL_URL_ROOT."/product/photos.php?id=".$_POST["product"].'&action=addthumb&file='.urldecode($_POST["file"]));
exit;
}
// Crop d'une image
if ($_POST["action"] == 'confirm_crop' && $_POST["file"])
{
// TODO Add function to crop image in images.lib.php
/* $thumb = new Imagick($conf->produit->dir_output."/".urldecode($_POST["file"]));
$thumb->cropImage($_POST['w'], $_POST['h'], $_POST['x'], $_POST['y']);
$thumb->writeImage($conf->produit->dir_output."/".urldecode($_POST["file"]));
@ -86,31 +82,35 @@ if ($_POST["action"] == 'confirm_crop' && $_POST["file"])
* View
*/
llxHeader($head, $langs->trans("Resize"), '', '', 0, 0, array('includes/jcrop/js/jquery.min.js','includes/jcrop/js/jquery.Jcrop.min.js','lib/lib_photosresize.js'), array(DOL_URL_ROOT.'/includes/jcrop/css/jquery.Jcrop.css'));
llxHeader($head, $langs->trans("Image"), '', '', 0, 0, array('includes/jcrop/js/jquery.min.js','includes/jcrop/js/jquery.Jcrop.min.js','lib/lib_photosresize.js'), array(DOL_URL_ROOT.'/includes/jcrop/css/jquery.Jcrop.css'));
print_fiche_titre($langs->trans("Current"));
print_fiche_titre($langs->trans("Image"));
if ($mesg) print '<div class="error">'.$mesg.'</div>';
$infoarray=dol_getImageSize($conf->produit->dir_output."/".urldecode($_GET["file"]));
$height=$infoarray['height'];
$width=$infoarray['width'];
print $langs->trans("Size").': </p>
<ul>
<li>'.$langs->trans("Length").': '.$width.' px</li>
<li>'.$langs->trans("Width").': '.$height.' px</li>
<li>'.$langs->trans("Width").': '.$width.' px</li>
<li>'.$langs->trans("Height").': '.$height.' px</li>
</ul>';
print '<br>';
print_fiche_titre($langs->trans("Resize"),'','');
print '<form name="redim_file" action="'.DOL_URL_ROOT.'/product/photos_resize.php?id='.$_GET['id'].'" method="post">';
print 'Entrer la nouvelle largeur <strong>OU</strong> la nouvelle hauteur. Le ratio est conservé lors du redimensionnement...<br>';
print 'Nouvelle largeur : <input class="flat" name="sizex" size="10" type="text" > px <br /> ';
print 'Nouvelle hauteur : <input class="flat" name="sizey" size="10" type="text" > px &nbsp; <br />';
print '<form name="redim_file" action="'.$_SERVER["PHP_SELF"].'?id='.$_GET['id'].'" method="POST">';
print $langs->trans("ResizeDesc").'<br>';
print $langs->trans("NewLength").': <input class="flat" name="sizex" size="10" type="text" > px <br /> ';
print $langs->trans("NewHeight").': <input class="flat" name="sizey" size="10" type="text" > px &nbsp; <br />';
print '<input type="hidden" name="file" value="'.$_GET['file'].'" />';
print '<input type="hidden" name="action" value="confirm_resize" />';
print '<input type="hidden" name="product" value="'.$_GET['id'].'" />';
print '<br><input class="button" name="sendit" value="Redimensionner" type="submit" />';
print '<input type="hidden" name="id" value="'.$_GET['id'].'" />';
print '<br><input class="button" name="sendit" value="'.dol_escape_htmltag($langs->trans("Resize")).'" type="submit" />';
print '<br></form>';
print '<br>';
@ -121,14 +121,16 @@ print '<br>';
print '<br>';
print_fiche_titre($langs->trans("Recenter"),'','');
print 'Define new area to keep...<br>';
print '<img src="'.DOL_URL_ROOT.'/viewimage.php?modulepart=product&file='.$original_file.'" alt="Taille origine" id="cropbox" />';
print $langs->trans("DefineNewAreaToPick").'...<br>';
print '<br>';
print '<img style="border: 1px solid #888888;" src="'.DOL_URL_ROOT.'/viewimage.php?modulepart=product&file='.$original_file.'" alt="Taille origine" id="cropbox" />';
print '<br>';
$infoarray=dol_getImageSize($conf->produit->dir_output."/".urldecode($_GET["file"]));
$height=$infoarray['height'];
$width=$infoarray['width'];
print '<form action="photos_resize.php" method="post" onsubmit="return checkCoords();">
print '<form action="'.$_SERVER["PHP_SELF"].'?id='.$_GET['id'].'" method="post" onsubmit="return checkCoords();">
<div class="jc_coords">
<div class="titre">Nouvelles dimensions après recadrage</div>
'.$langs->trans("NewSizeAfterCropping").':
<label>X1 <input type="text" size="4" id="x" name="x" /></label>
<label>Y1 <input type="text" size="4" id="y" name="y" /></label>
<label>X2 <input type="text" size="4" id="x2" name="x2" /></label>
@ -140,7 +142,8 @@ print '<form action="photos_resize.php" method="post" onsubmit="return checkCoor
<input type="hidden" id="file" name="file" value="'.urlencode($original_file).'" />
<input type="hidden" id="action" name="action" value="confirm_crop" />
<input type="hidden" id="product" name="product" value="'.$_GET['id'].'" />
<br><input type="submit" class="button" value="Recadrer" />
<input type="hidden" name="id" value="'.$_GET['id'].'" />
<br><input type="submit" class="button" value="'.dol_escape_htmltag($langs->trans("Recenter")).'" />
</form>';
llxFooter('$Date$ - $Revision$');

41
htdocs/core/pre.inc.php Normal file
View File

@ -0,0 +1,41 @@
<?php
/* Copyright (C) 2001-2007 Rodolphe Quiedeville <rodolphe@quiedeville.org>
* Copyright (C) 2004-2010 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2007 Auguria SARL <info@auguria.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
/**
* \file htdocs/core/pre.inc.php
* \ingroup core
* \brief Menu file
* \version $Id$
*/
require("../main.inc.php");
function llxHeader($head = '',$help_url='', $title='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='')
{
global $user, $conf, $langs;
top_menu($head, $title, $target, $disablejs, $disablehead, $arrayofjs, $arrayofcss);
$menu = new Menu();
left_menu($menu->liste, $help_url);
}
?>

View File

@ -153,7 +153,7 @@ class FormBarCode
print '<form method="post" action="'.$page.'">';
print '<input type="hidden" name="token" value="'.$_SESSION['newtoken'].'">';
print '<input type="hidden" name="action" value="setbarcodetype">';
print '<table class="noborder" cellpadding="0" cellspacing="0">';
print '<table class="nobordernopadding" cellpadding="0" cellspacing="0">';
print '<tr><td>';
$this->select_barcode_type($selected, $htmlname, 1);
print '</td>';

View File

@ -115,6 +115,11 @@ EMailTextOrderRefused=The order %s has been refused.
EMailTextOrderRefusedBy=The order %s has been refused by %s.
ImportedWithSet=Importation data set
DolibarrNotification=Automatic notification
ResizeDesc=Enter new width <b>OR</b> new height. Ratio will be kept during resizing...
NewLength=New width
NewHeight=New height
NewSizeAfterCropping=New size after cropping
DefineNewAreaToPick=Define new area on image to pick (left click on image then drag until you reach the opposite corner)
##### Bookmark #####
Bookmark=Bookmark

View File

@ -115,6 +115,11 @@ EMailTextOrderRefused=La commande %s a été réfusée.
EMailTextOrderRefusedBy=La commande %s a été réfusée par %s.
ImportedWithSet=Lot d'importation (Import key)
DolibarrNotification=Notification automatique
ResizeDesc=Entrer la nouvelle largeur <b>OU</b> la nouvelle hauteur. Le ratio est conservé lors du redimensionnement...
NewLength=Nouvelle largeur
NewHeight=Nouvelle hauteur
NewSizeAfterCropping=Nouvelles dimensions après recadrage
DefineNewAreaToPick=Définissez la zone d'image à conserver (clic gauche sur l'image puis drag vers les coin opposé)
##### Bookmark #####
Bookmark=Marque page

View File

@ -1,5 +1,5 @@
<?php
/* Copyright (C) 2004-2008 Laurent Destailleur <eldy@users.sourceforge.net>
/* Copyright (C) 2004-2010 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2005-2007 Regis Houssin <regis@dolibarr.fr>
*
* This program is free software; you can redistribute it and/or modify
@ -49,6 +49,195 @@ function dol_getImageSize($file)
}
/**
* \brief Resize an image file
* \brief Supported extensions are jpg and png
* \param file Chemin du fichier image a redimensionner
* \param newWidth Largeur maximum que dois faire la miniature (-1=unchanged)
* \param newHeight Hauteur maximum que dois faire l'image (-1=unchanged)
* \return int File name if OK, error message if KO
* \remarks With file=myfile.jpg -> myfile_small.jpg
*/
function dol_imageResize($file, $newWidth, $newHeight)
{
require_once(DOL_DOCUMENT_ROOT."/lib/functions2.lib.php");
global $conf,$langs;
dol_syslog("dol_imageResize file=".$file." newWidth=".$newWidth." newHeight=".$newHeight);
// Clean parameters
$file=trim($file);
// Check parameters
if (! $file)
{
// Si le fichier n'a pas ete indique
return 'Bad parameter file';
}
elseif (! file_exists($file))
{
// Si le fichier passe en parametre n'existe pas
return $langs->trans("ErrorFileNotFound",$file);
}
elseif(image_format_supported($file) < 0)
{
return 'This file '.$file.' does not seem to be an image format file name.';
}
elseif(!is_numeric($newWidth) && !is_numeric($newHeight)){
return 'Wrong value for parameter newWidth or newHeight';
}
elseif ($newWidth <= 0 && $newHeight <= 0)
{
return 'At least newHeight or newWidth must be defined';
}
$fichier = realpath($file); // Chemin canonique absolu de l'image
$dir = dirname($file); // Chemin du dossier contenant l'image
$infoImg = getimagesize($fichier); // Recuperation des infos de l'image
$imgWidth = $infoImg[0]; // Largeur de l'image
$imgHeight = $infoImg[1]; // Hauteur de l'image
if ($newWidth <= 0)
{
$newWidth=intval(($newHeight / $imgHeight) * $imgWidth); // Keep ratio
}
if ($newHeight <= 0)
{
$newHeight=intval(($newWidth / $imgWidth) * $imgHeight); // Keep ratio
}
$imgfonction='';
switch($infoImg[2])
{
case 1: // IMG_GIF
$imgfonction = 'imagecreatefromgif';
break;
case 2: // IMG_JPG
$imgfonction = 'imagecreatefromjpeg';
break;
case 3: // IMG_PNG
$imgfonction = 'imagecreatefrompng';
break;
case 4: // IMG_WBMP
$imgfonction = 'imagecreatefromwbmp';
break;
}
if ($imgfonction)
{
if (! function_exists($imgfonction))
{
// Fonctions de conversion non presente dans ce PHP
return 'Resize not possible. This PHP does not support GD functions '.$imgfonction;
}
}
// Initialisation des variables selon l'extension de l'image
switch($infoImg[2])
{
case 1: // Gif
$img = imagecreatefromgif($fichier);
$extImg = '.gif'; // Extension de l'image
$newquality='NU';
break;
case 2: // Jpg
$img = imagecreatefromjpeg($fichier);
$extImg = '.jpg'; // Extension de l'image
$newquality=100;
break;
case 3: // Png
$img = imagecreatefrompng($fichier);
$extImg = '.png';
$newquality=10;
break;
case 4: // Bmp
$img = imagecreatefromwbmp($fichier);
$extImg = '.bmp';
$newquality='NU';
break;
}
// Create empty image
if ($infoImg[2] == 1)
{
// Compatibilite image GIF
$imgThumb = imagecreate($newWidth, $newHeight);
}
else
{
$imgThumb = imagecreatetruecolor($newWidth, $newHeight);
}
// Activate antialiasing for better quality
if (function_exists('imageantialias'))
{
imageantialias($imgThumb, true);
}
// This is to keep transparent alpha channel if exists (PHP >= 4.2)
if (function_exists('imagesavealpha'))
{
imagesavealpha($imgThumb, true);
}
// Initialisation des variables selon l'extension de l'image
switch($infoImg[2])
{
case 1: // Gif
$trans_colour = imagecolorallocate($imgThumb, 255, 255, 255); // On procede autrement pour le format GIF
imagecolortransparent($imgThumb,$trans_colour);
break;
case 2: // Jpg
$trans_colour = imagecolorallocatealpha($imgThumb, 255, 255, 255, 0);
break;
case 3: // Png
imagealphablending($imgThumb,false); // Pour compatibilite sur certain systeme
$trans_colour = imagecolorallocatealpha($imgThumb, 255, 255, 255, 127); // Keep transparent channel
break;
case 4: // Bmp
$trans_colour = imagecolorallocatealpha($imgThumb, 255, 255, 255, 0);
break;
}
if (function_exists("imagefill")) imagefill($imgThumb, 0, 0, $trans_colour);
dol_syslog("dol_imageResize: convert image from ($imgWidth x $imgHeight) to ($newWidth x $newHeight) as $extImg, newquality=$newquality");
//imagecopyresized($imgThumb, $img, 0, 0, 0, 0, $thumbWidth, $thumbHeight, $imgWidth, $imgHeight); // Insere l'image de base redimensionnee
imagecopyresampled($imgThumb, $img, 0, 0, 0, 0, $newWidth, $newHeight, $imgWidth, $imgHeight); // Insere l'image de base redimensionnee
$imgThumbName = $file;
// Check if permission are ok
//$fp = fopen($imgThumbName, "w");
//fclose($fp);
// Create image on disk
switch($infoImg[2])
{
case 1: // Gif
imagegif($imgThumb, $imgThumbName);
break;
case 2: // Jpg
imagejpeg($imgThumb, $imgThumbName, $newquality);
break;
case 3: // Png
imagepng($imgThumb, $imgThumbName, $newquality);
break;
case 4: // Bmp
image2wmp($imgThumb, $imgThumbName);
break;
}
// Set permissions on file
if (! empty($conf->global->MAIN_UMASK)) @chmod($imgThumbName, octdec($conf->global->MAIN_UMASK));
// Free memory
imagedestroy($imgThumb);
return $imgThumbName;
}
/**
* \brief Create a thumbnail from an image file (une small et un mini)
* \brief Les extensions prises en compte sont jpg et png
@ -66,7 +255,7 @@ function vignette($file, $maxWidth = 160, $maxHeight = 120, $extName='_small', $
global $conf,$langs;
dol_syslog("functions.inc::vignette file=".$file." extName=".$extName." maxWidth=".$maxWidth." maxHeight=".$maxHeight." quality=".$quality);
dol_syslog("vignette file=".$file." extName=".$extName." maxWidth=".$maxWidth." maxHeight=".$maxHeight." quality=".$quality);
// Clean parameters
$file=trim($file);
@ -88,11 +277,11 @@ function vignette($file, $maxWidth = 160, $maxHeight = 120, $extName='_small', $
}
elseif(!is_numeric($maxWidth) || empty($maxWidth) || $maxWidth < -1){
// Si la largeur max est incorrecte (n'est pas numerique, est vide, ou est inferieure a 0)
return 'Valeur de la largeur incorrecte.';
return 'Wrong value for parameter maxWidth';
}
elseif(!is_numeric($maxHeight) || empty($maxHeight) || $maxHeight < -1){
// Si la hauteur max est incorrecte (n'est pas numerique, est vide, ou est inferieure a 0)
return 'Valeur de la hauteur incorrecte.';
return 'Wrong value for parameter maxHeight';
}
$fichier = realpath($file); // Chemin canonique absolu de l'image
@ -271,15 +460,11 @@ function vignette($file, $maxWidth = 160, $maxHeight = 120, $extName='_small', $
/**
\brief permet d'afficher un thermometre monetaire.
\param actualValue
\param pendingValue
\param intentValue
\return thermometer htmlLegenda
This function returns the html for the moneymeter.
cachedValue: amount of actual money
pendingValue: amount of money of pending memberships
intentValue: amount of intended money (that's without the amount of actual money)
* \brief This function returns the html for the moneymeter.
* \param actualValue: amount of actual money
* \param pendingValue: amount of money of pending memberships
* \param intentValue: amount of intended money (that's without the amount of actual money)
* \return thermometer htmlLegenda
*/
function moneyMeter($actualValue=0, $pendingValue=0, $intentValue=0)
{

View File

@ -2404,7 +2404,7 @@ class Product extends CommonObject
*/
function show_photos($sdir,$size=0,$nbmax=0,$nbbyrow=5,$showfilename=0,$showaction=0)
{
global $user,$langs;
global $conf,$user,$langs;
include_once(DOL_DOCUMENT_ROOT ."/lib/files.lib.php");
@ -2468,12 +2468,10 @@ class Product extends CommonObject
}
if ($user->rights->produit->creer || $user->rights->service->creer)
{
if ($conf->global->MAIN_FEATURES_LEVEL > 0)
{
// Link to resize
print '<a href="'.DOL_URL_ROOT.'/product/photos_resize.php?id='.$_GET["id"].'&amp;file='.urlencode($pdir.$viewfilename).'" title="'.dol_escape_htmltag($langs->trans("Resize")).'">'.img_picto($langs->trans("Resize"),DOL_URL_ROOT.'/theme/common/transform-crop-and-resize','',1).'</a>';
}
// Link to delete
// Link to resize
print '<a href="'.DOL_URL_ROOT.'/core/photos_resize.php?id='.$_GET["id"].'&amp;file='.urlencode($pdir.$viewfilename).'" title="'.dol_escape_htmltag($langs->trans("Resize")).'">'.img_picto($langs->trans("Resize"),DOL_URL_ROOT.'/theme/common/transform-crop-and-resize','',1).'</a> &nbsp; ';
// Link to delete
print '<a href="'.$_SERVER["PHP_SELF"].'?id='.$_GET["id"].'&amp;action=delete&amp;file='.urlencode($pdir.$viewfilename).'">';
print img_delete().'</a>';
}

View File

@ -1,6 +1,6 @@
<?php
/* Copyright (C) 2001-2007 Rodolphe Quiedeville <rodolphe@quiedeville.org>
* Copyright (C) 2004-2009 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2004-2010 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2005-2010 Regis Houssin <regis@dolibarr.fr>
*
* This program is free software; you can redistribute it and/or modify
@ -42,6 +42,7 @@ $fieldid = isset($_GET["ref"])?'ref':'rowid';
if ($user->societe_id) $socid=$user->societe_id;
$result=restrictedArea($user,'produit|service&barcode',$id,'product','','',$fieldid);
/*
* Actions
*/
@ -70,7 +71,7 @@ if ($_POST['action'] == 'setbarcode' && $user->rights->barcode->creer)
/*
* Mode vue et edition
* View
*/
llxHeader("","",$langs->trans("BarCode"));

View File

@ -1,6 +1,6 @@
<?php
/* Copyright (C) 2001-2007 Rodolphe Quiedeville <rodolphe@quiedeville.org>
* Copyright (C) 2004-2009 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2004-2010 Laurent Destailleur <eldy@users.sourceforge.net>
* Copyright (C) 2007 Auguria SARL <info@auguria.org>
*
* This program is free software; you can redistribute it and/or modify