source: trunk/include/derivative_params.inc.php @ 19703

Last change on this file since 19703 was 19703, checked in by plg, 11 years ago

update Piwigo headers to 2013 (the end of the world didn't occur as expected on r12922)

File size: 7.5 KB
Line 
1<?php
2// +-----------------------------------------------------------------------+
3// | Piwigo - a PHP based photo gallery                                    |
4// +-----------------------------------------------------------------------+
5// | Copyright(C) 2008-2013 Piwigo Team                  http://piwigo.org |
6// +-----------------------------------------------------------------------+
7// | This program is free software; you can redistribute it and/or modify  |
8// | it under the terms of the GNU General Public License as published by  |
9// | the Free Software Foundation                                          |
10// |                                                                       |
11// | This program is distributed in the hope that it will be useful, but   |
12// | WITHOUT ANY WARRANTY; without even the implied warranty of            |
13// | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU      |
14// | General Public License for more details.                              |
15// |                                                                       |
16// | You should have received a copy of the GNU General Public License     |
17// | along with this program; if not, write to the Free Software           |
18// | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, |
19// | USA.                                                                  |
20// +-----------------------------------------------------------------------+
21
22function derivative_to_url($t)
23{
24  return substr($t, 0, 2);
25}
26
27function size_to_url($s)
28{
29  if ($s[0]==$s[1])
30  {
31    return $s[0];
32  }
33  return $s[0].'x'.$s[1];
34}
35
36function size_equals($s1, $s2)
37{
38  return ($s1[0]==$s2[0] && $s1[1]==$s2[1]);
39}
40
41function char_to_fraction($c)
42{
43        return (ord($c) - ord('a'))/25;
44}
45
46function fraction_to_char($f)
47{
48        return chr(ord('a') + round($f*25));
49}
50
51/** small utility to manipulate a 'rectangle'*/
52final class ImageRect
53{
54  public $l,$t,$r,$b;
55
56  function __construct($l)
57  {
58    $this->l = $this->t = 0;
59    $this->r = $l[0];
60    $this->b = $l[1];
61  }
62
63  function width()
64  {
65    return $this->r - $this->l;
66  }
67
68  function height()
69  {
70    return $this->b - $this->t;
71  }
72
73  function crop_h($pixels, $coi)
74  {
75    if ($this->width() <= $pixels)
76      return;
77    $tlcrop = floor($pixels/2);
78
79    if (!empty($coi))
80    {
81      $coil = floor($this->r * char_to_fraction($coi[0]));
82      $coir = ceil($this->r * char_to_fraction($coi[2]));
83      $availableL = $coil > $this->l ? $coil - $this->l : 0;
84      $availableR = $coir < $this->r ? $this->r - $coir : 0;
85      if ($availableL + $availableR >= $pixels)
86      {
87        if ($availableL < $tlcrop)
88        {
89          $tlcrop = $availableL;
90        }
91        elseif ($availableR < $tlcrop)
92        {
93          $tlcrop = $pixels - $availableR;
94        }
95      }
96    }
97    $this->l += $tlcrop;
98    $this->r -= $pixels - $tlcrop;
99  }
100
101  function crop_v($pixels, $coi)
102  {
103    if ($this->height() <= $pixels)
104      return;
105    $tlcrop = floor($pixels/2);
106
107    if (!empty($coi))
108    {
109      $coit = floor($this->b * char_to_fraction($coi[1]));
110      $coib = ceil($this->b * char_to_fraction($coi[3]));
111      $availableT = $coit > $this->t ? $coit - $this->t : 0;
112      $availableB = $coib < $this->b ? $this->b - $coib : 0;
113      if ($availableT + $availableB >= $pixels)
114      {
115        if ($availableT < $tlcrop)
116        {
117          $tlcrop = $availableT;
118        }
119        elseif ($availableB < $tlcrop)
120        {
121          $tlcrop = $pixels - $availableB;
122        }
123      }
124    }
125    $this->t += $tlcrop;
126    $this->b -= $pixels - $tlcrop;
127  }
128
129}
130
131
132/*how we crop and/or resize an image*/
133final class SizingParams
134{
135  function __construct($ideal_size, $max_crop = 0, $min_size = null)
136  {
137    $this->ideal_size = $ideal_size;
138    $this->max_crop = $max_crop;
139    $this->min_size = $min_size;
140  }
141
142  static function classic($w, $h)
143  {
144    return new SizingParams( array($w,$h) );
145  }
146
147  static function square($w)
148  {
149    return new SizingParams( array($w,$w), 1, array($w,$w) );
150  }
151
152  function add_url_tokens(&$tokens)
153  {
154      if ($this->max_crop == 0)
155      {
156        $tokens[] = 's'.size_to_url($this->ideal_size);
157      }
158      elseif ($this->max_crop == 1 && size_equals($this->ideal_size, $this->min_size) )
159      {
160        $tokens[] = 'e'.size_to_url($this->ideal_size);
161      }
162      else
163      {
164        $tokens[] = size_to_url($this->ideal_size);
165        $tokens[] = fraction_to_char($this->max_crop);
166        $tokens[] = size_to_url($this->min_size);
167      }
168  }
169
170  function compute($in_size, $coi, &$crop_rect, &$scale_size)
171  {
172    $destCrop = new ImageRect($in_size);
173
174    if ($this->max_crop > 0)
175    {
176      $ratio_w = $destCrop->width() / $this->ideal_size[0];
177      $ratio_h = $destCrop->height() / $this->ideal_size[1];
178      if ($ratio_w>1 || $ratio_h>1)
179      {
180        if ($ratio_w > $ratio_h)
181        {
182          $h = $destCrop->height() / $ratio_w;
183          if ($h < $this->min_size[1])
184          {
185            $idealCropPx = $destCrop->width() - floor($destCrop->height() * $this->ideal_size[0] / $this->min_size[1]);
186            $maxCropPx = round($this->max_crop * $destCrop->width());
187            $destCrop->crop_h( min($idealCropPx, $maxCropPx), $coi);
188          }
189        }
190        else
191        {
192          $w = $destCrop->width() / $ratio_h;
193          if ($w < $this->min_size[0])
194          {
195            $idealCropPx = $destCrop->height() - floor($destCrop->width() * $this->ideal_size[1] / $this->min_size[0]);
196            $maxCropPx = round($this->max_crop * $destCrop->height());
197            $destCrop->crop_v( min($idealCropPx, $maxCropPx), $coi);
198          }
199        }
200      }
201    }
202
203    $scale_size = array($destCrop->width(), $destCrop->height());
204
205    $ratio_w = $destCrop->width() / $this->ideal_size[0];
206    $ratio_h = $destCrop->height() / $this->ideal_size[1];
207    if ($ratio_w>1 || $ratio_h>1)
208    {
209      if ($ratio_w > $ratio_h)
210      {
211        $scale_size[0] = $this->ideal_size[0];
212        $scale_size[1] = floor(1e-6 + $scale_size[1] / $ratio_w);
213      }
214      else
215      {
216        $scale_size[0] = floor(1e-6 + $scale_size[0] / $ratio_h);
217        $scale_size[1] = $this->ideal_size[1];
218      }
219    }
220    else
221    {
222      $scale_size = null;
223    }
224
225    $crop_rect = null;
226    if ($destCrop->width()!=$in_size[0] || $destCrop->height()!=$in_size[1] )
227    {
228      $crop_rect = $destCrop;
229    }
230  }
231
232}
233
234
235/*how we generate a derivative image*/
236final class DerivativeParams
237{
238  public $type = IMG_CUSTOM;
239  public $last_mod_time = 0; // used for non-custom images to regenerate the cached files
240  public $use_watermark = false;
241  public $sizing;
242  public $sharpen = 0;
243
244  function __construct($sizing)
245  {
246    $this->sizing = $sizing;
247  }
248
249  public function __sleep()
250  {
251      return array('last_mod_time', 'sizing', 'sharpen');
252  }
253
254  function add_url_tokens(&$tokens)
255  {
256    $this->sizing->add_url_tokens($tokens);
257  }
258
259  function compute_final_size($in_size)
260  {
261    $this->sizing->compute( $in_size, null, $crop_rect, $scale_size );
262    return $scale_size != null ? $scale_size : $in_size;
263  }
264
265  function max_width()
266  {
267    return $this->sizing->ideal_size[0];
268  }
269
270  function max_height()
271  {
272    return $this->sizing->ideal_size[1];
273  }
274
275  function is_identity($in_size)
276  {
277    if ($in_size[0] > $this->sizing->ideal_size[0] or
278        $in_size[1] > $this->sizing->ideal_size[1] )
279    {
280      return false;
281    }
282    return true;
283  }
284 
285  function will_watermark($out_size)
286  {
287    if ($this->use_watermark)
288    {
289      $min_size = ImageStdParams::get_watermark()->min_size;
290      return $min_size[0]<=$out_size[0]
291        || $min_size[1]<=$out_size[1];
292    }
293    return false;
294  }
295}
296?>
Note: See TracBrowser for help on using the repository browser.