Commit 77ea773e4a41e0aef904591b6ec16ee14640e356

Authored by Charl Joseph Mert
1 parent cefd354b

Brand server without requiring access to FS

PT: 1243391

Added default crop selection handle size now matches image if the image is smaller than the logo dimentions.

Updated by: Charl Joseph Mert
plugins/ktcore/KTWidgets.php
... ... @@ -1047,15 +1047,8 @@ class KTCoreImageCropWidget extends KTWidget {
1047 1047 return $res;
1048 1048 }
1049 1049  
1050   - // FIXME make required *either* per-action property
1051   - // FIXME or a global pref.
1052   - $global_required_default = true;
1053   - $this->bRequired = (KTUtil::arrayGet($aOptions, 'required', $global_required_default, false) == true);
1054   -
1055   - $this->src = $aOptions['src'];
1056   - $this->alt = $aOptions['alt'];
1057   - $this->title = $aOptions['title'];
1058   -
  1050 + $this->aOptions['init_width'] = KTUtil::arrayGet($aOptions, 'init_width', '313');
  1051 + $this->aOptions['init_height'] = KTUtil::arrayGet($aOptions, 'init_height', '50');
1059 1052 }
1060 1053  
1061 1054 function render() {
... ... @@ -1069,7 +1062,7 @@ class KTCoreImageCropWidget extends KTWidget {
1069 1062  
1070 1063 $this->aJavascript[] = 'thirdpartyjs/jquery/jquery-1.3.2.js';
1071 1064 $this->aJavascript[] = 'thirdpartyjs/jquery/plugins/imageareaselect/scripts/jquery.imgareaselect.pack.js';
1072   - $this->aJavascript[] = 'resources/js/kt_image_crop.js';
  1065 + //$this->aJavascript[] = 'resources/js/kt_image_crop.js';
1073 1066  
1074 1067 if (!empty($this->aJavascript)) {
1075 1068 // grab our inner page.
... ...
plugins/ktcore/admin/manageBranding.php
1   -<?php
2   -/**
3   - * $Id$
4   - *
5   - * KnowledgeTree Community Edition
6   - * Document Management Made Simple
7   - * Copyright (C) 2008, 2009 KnowledgeTree Inc.
8   - *
9   - *
10   - * This program is free software; you can redistribute it and/or modify it under
11   - * the terms of the GNU General Public License version 3 as published by the
12   - * Free Software Foundation.
13   - *
14   - * This program is distributed in the hope that it will be useful, but WITHOUT
15   - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
16   - * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
17   - * details.
18   - *
19   - * You should have received a copy of the GNU General Public License
20   - * along with this program. If not, see <http://www.gnu.org/licenses/>.
21   - *
22   - * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco,
23   - * California 94120-7775, or email info@knowledgetree.com.
24   - *
25   - * The interactive user interfaces in modified source and object code versions
26   - * of this program must display Appropriate Legal Notices, as required under
27   - * Section 5 of the GNU General Public License version 3.
28   - *
29   - * In accordance with Section 7(b) of the GNU General Public License version 3,
30   - * these Appropriate Legal Notices must retain the display of the "Powered by
31   - * KnowledgeTree" logo and retain the original copyright notice. If the display of the
32   - * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices
33   - * must display the words "Powered by KnowledgeTree" and retain the original
34   - * copyright notice.
35   - * Contributor( s): ______________________________________
36   - */
37   -
38   -require_once(KT_LIB_DIR . '/dispatcher.inc.php');
39   -require_once(KT_LIB_DIR . '/templating/templating.inc.php');
40   -require_once(KT_LIB_DIR . '/browse/columnregistry.inc.php');
41   -require_once(KT_LIB_DIR . '/widgets/reorderdisplay.inc.php');
42   -require_once(KT_LIB_DIR . '/widgets/fieldWidgets.php');
43   -require_once(KT_LIB_DIR . "/widgets/FieldsetDisplayRegistry.inc.php");
44   -require_once(KT_LIB_DIR . "/widgets/fieldsetDisplay.inc.php");
45   -require_once(KT_LIB_DIR . "/widgets/widgetfactory.inc.php");
46   -require_once(KT_LIB_DIR . "/validation/dispatchervalidation.inc.php");
47   -require_once(KT_LIB_DIR . "/metadata/fieldsetregistry.inc.php");
48   -require_once(KT_LIB_DIR . "/validation/validatorfactory.inc.php");
49   -
50   -
51   -class ManageBrandDispatcher extends KTAdminDispatcher {
52   -
53   - private $maxLogoWidth = 313;
54   - private $maxLogoHeight = 50;
55   - public $supportedTypes = array('gif', 'png', 'pjpeg', 'jpe', 'jpeg', 'jpg', 'jfif', 'jfif-tbnl');
56   -
57   - function check() {
58   -
59   - $this->aBreadcrumbs[] = array('url' => $_SERVER['PHP_SELF'], 'name' => _kt('Manage Branding'));
60   - return parent::check();
61   - }
62   -
63   - function do_main() {
64   - $uploadLogoForm = $this->getUploadLogoForm();
65   - return $uploadLogoForm->render();
66   - }
67   -
68   -
69   - /**
70   - * Returns the upload logo form
71   - * @return KTForm
72   - *
73   - */
74   -
75   - function getUploadLogoForm() {
76   - $this->oPage->setBreadcrumbDetails(_kt("Upload Logo"));
77   -
78   - $oForm = new KTForm;
79   - $oForm->setOptions(array(
80   - 'identifier' => 'ktcore.folder.branding',
81   - 'label' => _kt('Upload Logo'),
82   - 'submit_label' => _kt('Upload'),
83   - 'action' => 'upload',
84   - 'fail_action' => 'main',
85   - 'encoding' => 'multipart/form-data',
86   - 'context' => &$this,
87   - 'extraargs' => $this->meldPersistQuery("","",true),
88   - 'description' => _kt('You can upload a logo to brand your KnowledgeTree site.')
89   - ));
90   -
91   - $oWF =& KTWidgetFactory::getSingleton();
92   -
93   - $widgets = array();
94   - $validators = array();
95   -
96   - // Adding the File Upload Widget
97   - $widgets[] = $oWF->get('ktcore.widgets.file', array(
98   - 'label' => _kt('Logo File'),
99   - 'required' => true,
100   - 'name' => 'file',
101   - 'id' => 'file',
102   - 'value' => '',
103   - 'description' => _kt("The logo's dimensions should be 313px width by 50px height. If your logo doesn't fit these dimensions, you can choose to crop or scale it."),
104   - ));
105   -
106   - $aVocab['crop'] = 'Crop - Cut out a selection';
107   - $aVocab['scale'] = 'Scale - Stretch or Shrink to fit';
108   - $aVocab['nothing'] = 'Don\'t do anything <span class="descriptiveText">(My image has the correct dimensions)</span>';
109   -
110   - //Adding document type lookup widget
111   - $widgets[] = $oWF->get('ktcore.widgets.selection',array(
112   - 'label' => _kt('Fitting Image'),
113   - 'id' => 'logo_action',
114   - 'description' => _kt('How would you like to resize the image?'),
115   - 'name' => 'resize_method',
116   - 'vocab' => $aVocab,
117   - 'selected' => 'crop',
118   - 'label_method' => 'getName',
119   - 'simple_select' => true,
120   - ));
121   -
122   - $oForm->setWidgets($widgets);
123   - $oForm->setValidators($validators);
124   -
125   - // TODO: Should electronic signature be implemented for this?
126   - // Implement an electronic signature for accessing the admin section, it will appear every 10 minutes
127   - /* //Have to instanciate the oFolder
128   - global $default;
129   - $iFolderId = $this->oFolder->getId();
130   - if($default->enableESignatures){
131   - $sUrl = KTPluginUtil::getPluginPath('electronic.signatures.plugin', true);
132   - $heading = _kt('You are attempting to perform a bulk upload');
133   - $submit['type'] = 'button';
134   - $submit['onclick'] = "javascript: showSignatureForm('{$sUrl}', '{$heading}', 'ktcore.transactions.bulk_upload', 'bulk', 'bulk_upload_form', 'submit', {$iFolderId});";
135   - }else{
136   - $submit['type'] = 'submit';
137   - $submit['onclick'] = '';
138   - }
139   - */
140   -
141   - return $oForm;
142   - }
143   -
144   -
145   - /**
146   - * Returns the scale logo form
147   - *
148   - * This form will display a preview of all the possible sclaled combinations.
149   - * This includes:
150   - *
151   - * Stretched, Top Left Cropped, Proportional Stretch, Proportional Top Left Cropped
152   - *
153   - * @return KTForm
154   - *
155   - */
156   -
157   - function getScaleLogoForm($logoItems = array()) {
158   - $this->oPage->setBreadcrumbDetails(_kt("Scale Logo"));
159   -
160   - $oForm = new KTForm;
161   - $oForm->setOptions(array(
162   - 'identifier' => 'ktcore.folder.branding',
163   - 'label' => _kt('Choose Logo'),
164   - 'submit_label' => _kt('Select'),
165   - 'action' => 'selectLogo',
166   - 'fail_action' => 'main',
167   - 'encoding' => 'multipart/form-data',
168   - 'context' => &$this,
169   - 'extraargs' => $this->meldPersistQuery("","",true),
170   - 'description' => _kt('Choose a logo by clicking on one of the images')
171   - ));
172   -
173   - $oWF =& KTWidgetFactory::getSingleton();
174   -
175   - $widgets = array();
176   - $validators = array();
177   -
178   - $logoFileName = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
179   -
180   - // Adding the image select widget (User will select the best image)
181   - $widgets[] = $oWF->get('ktcore.widgets.imageselect', array(
182   - 'label' => _kt('Logo Preview'),
183   - 'name' => $logoFileName,
184   - 'value' => $logoItems,
185   - ));
186   -
187   - // Adding the Hidden FileName Input String
188   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
189   - 'name' => 'kt_imageselect',
190   - 'value' => $logoItems[0],
191   - ));
192   -
193   - $oForm->setWidgets($widgets);
194   - $oForm->setValidators($validators);
195   -
196   - return $oForm;
197   - }
198   -
199   -
200   - /**
201   - * Returns the crop logo form
202   - *
203   - * This form will assist the user in selecting an area of the image to use as the logo
204   - * within predefined dimensions required for the logo to fit properly into the page header.
205   - *
206   - * @return KTForm
207   - *
208   - */
209   -
210   - function getCropLogoForm($logoFileName = '') {
211   - $this->oPage->setBreadcrumbDetails(_kt("Crop Logo"));
212   -
213   - $oForm = new KTForm;
214   - $oForm->setOptions(array(
215   - 'identifier' => 'ktcore.folder.branding',
216   - 'name' => 'crop_form',
217   - 'label' => _kt('Crop Logo'),
218   - 'submit_label' => _kt('Crop'),
219   - 'action' => 'crop',
220   - 'fail_action' => 'main',
221   - 'encoding' => 'multipart/form-data',
222   - 'context' => &$this,
223   - 'extraargs' => $this->meldPersistQuery("","",true),
224   - 'description' => _kt('Use this facility to ensure that the logo meets the required dimensions for the header.')
225   - ));
226   -
227   - $oWF =& KTWidgetFactory::getSingleton();
228   -
229   - $widgets = array();
230   - $validators = array();
231   -
232   - $logoFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
233   -
234   - // Adding the Image Crop Widget
235   - $widgets[] = $oWF->get('ktcore.widgets.imagecrop', array(
236   - 'label' => _kt('Crop Logo'),
237   - //'name' => 'Logo',
238   - 'value' => $logoFile,
239   - 'description' => _kt('To crop an area of the logo, click and drag the resizable rectangle over the image.'),
240   - ));
241   -
242   - // Adding the Hidden FileName Input String
243   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
244   - 'name' => 'logo_file_name',
245   - 'value' => $logoFileName,
246   - ));
247   -
248   - // Adding the Hidden Coordinates X1
249   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
250   - 'name' => 'crop_x1',
251   - 'value' => 'x1test',
252   - ));
253   -
254   - // Adding the Hidden Coordinates Y1
255   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
256   - 'name' => 'crop_y1',
257   - 'value' => '',
258   - ));
259   -
260   - // Adding the Hidden Coordinates X2
261   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
262   - 'name' => 'crop_x2',
263   - 'value' => '',
264   - ));
265   -
266   - // Adding the Hidden Coordinates Y2
267   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
268   - 'name' => 'crop_y2',
269   - 'value' => '',
270   - ));
271   -
272   - $oForm->setWidgets($widgets);
273   - $oForm->setValidators($validators);
274   -
275   - return $oForm;
276   - }
277   -
278   - /**
279   - * Returns the apply logo form
280   - *
281   - * This form will display a preview of the correctly sized logo and prompt the user to apply it.
282   - *
283   - * @return KTForm
284   - *
285   - */
286   -
287   - function getApplyLogoForm($logoFileName = '') {
288   - $this->oPage->setBreadcrumbDetails(_kt("Apply Logo"));
289   -
290   - $oForm = new KTForm;
291   - $oForm->setOptions(array(
292   - 'identifier' => 'ktcore.folder.branding',
293   - 'label' => _kt('Apply Logo'),
294   - 'submit_label' => _kt('Apply'),
295   - 'action' => 'apply',
296   - 'fail_action' => 'main',
297   - 'encoding' => 'multipart/form-data',
298   - 'context' => &$this,
299   - 'extraargs' => $this->meldPersistQuery("","",true),
300   - 'description' => _kt('Applying the logo will activate it in the header making it visible to all who access this site.')
301   - ));
302   -
303   - $oWF =& KTWidgetFactory::getSingleton();
304   -
305   - $widgets = array();
306   - $validators = array();
307   -
308   - $logoFileName = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
309   -
310   - // Adding the Image Widget
311   - $widgets[] = $oWF->get('ktcore.widgets.image', array(
312   - 'label' => _kt('Logo Preview'),
313   - 'name' => $logoFileName, // title and alt attributes get set to this.
314   - 'value' => $logoFileName,
315   - 'width' => $this->maxLogoWidth,
316   - 'height' => $this->maxLogoHeight,
317   - 'widgetwidth' => 20
318   - ));
319   -
320   - // Adding the Hidden FileName Input String
321   - $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
322   - 'name' => 'logo_file_name',
323   - 'value' => $logoFileName,
324   - ));
325   -
326   - $oForm->setWidgets($widgets);
327   - $oForm->setValidators($validators);
328   -
329   - return $oForm;
330   - }
331   -
332   -
333   - /*
334   - * Action responsible for uploading the logo
335   - *
336   - */
337   -
338   - function do_upload(){
339   - global $default;
340   -
341   - $oForm = $this->getUploadLogoForm();
342   - $res = $oForm->validate();
343   - if (!empty($res['errors'])) {
344   - return $oForm->handleError();
345   - }
346   -
347   - // Setting up the branding directory, logos will be stored in var/branding/
348   - $brandDir = $default->varDirectory.DIRECTORY_SEPARATOR.'branding';
349   -
350   - if (stristr(PHP_OS,'WIN')) {
351   - $brandDir = str_replace('/', '\\', $brandDir);
352   - }
353   -
354   - //if branding dir does not exist, generate one and add an index file to block access
355   - if (!file_exists($brandDir)) {
356   - mkdir($brandDir, 0755);
357   - touch($brandDir.DIRECTORY_SEPARATOR.'index.html');
358   - file_put_contents($brandDir.DIRECTORY_SEPARATOR.'index.html', 'You do not have permission to access this directory.');
359   - }
360   -
361   - $logoDir = $brandDir.DIRECTORY_SEPARATOR."logo";
362   - //if branding dir does not exist, generate one and add an index file to block access
363   - if (!file_exists($logoDir)) {
364   - mkdir($logoDir, 0755);
365   - touch($logoDir.DIRECTORY_SEPARATOR.'index.html');
366   - file_put_contents($logoDir.DIRECTORY_SEPARATOR.'index.html', 'You do not have permission to access this directory.');
367   - }
368   -
369   - $logoFileName = $_FILES['_kt_attempt_unique_file']['name'];
370   -
371   - //Changing to logo.jpg (Need to preserve extention as GD requires the exact image type to work)
372   - $ext = end(explode('.', $logoFileName));
373   -
374   - $type = $_FILES['_kt_attempt_unique_file']['type'];
375   -
376   - //Stage 1 filename based ext check:
377   - if (!$this->isSupportedExtension($ext)) {
378   - //If filename based extension isn't supported will try and guess based on mime type
379   - $default->log->error("Stage 1: Unsupported file type: '".$type."' for file: ':".$_FILES['_kt_attempt_unique_file']['name']."'");
380   - $ext = $this->getExtension($type);
381   -
382   - if (!$this->isSupportedExtension($ext)) {
383   - $default->log->error("Unsupported file type: '".$type."' for file: ':".$_FILES['_kt_attempt_unique_file']['name']."'");
384   - $this->errorRedirectToMain("The file you tried to upload is not supported.");
385   - }
386   - }
387   -
388   - $logoFileName = 'logo_tmp_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
389   - $logoFile = $logoDir.DIRECTORY_SEPARATOR.$logoFileName;
390   -
391   - // deleting old tmp file
392   - if (file_exists($logoFile)) {
393   - @unlink($logoFile);
394   - }
395   -
396   - //TODO: Test Upload Failure by setting the $logoFile to ''
397   -
398   - if(!move_uploaded_file($_FILES['_kt_attempt_unique_file']['tmp_name'], $logoFile)) {
399   - $default->log->error("Couldn't upload file from '".$_FILES['_kt_attempt_unique_file']['tmp_name']."' to '$logoFile'");
400   - $this->errorRedirectToMain("Couldn't upload file");
401   - exit(0);
402   - }
403   -
404   - $resizeMethod = $_REQUEST['data']['resize_method'];
405   -
406   - $relDir = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR;
407   -
408   - switch ($resizeMethod) {
409   - case 'crop':
410   -
411   - if ($this->isImageCroppable($logoFile, $this->maxLogoWith, $this->maxLogoHeight, $type)) {
412   -
413   - $retForm = $this->getCropLogoForm($logoFileName);
414   - } else {
415   - $_SESSION['KTErrorMessage'][] = _kt("The image was too small to be cropped.");
416   - $retForm = $this->getApplyLogoForm($logoFileName);
417   - }
418   -
419   - return $retForm->render();
420   -
421   - case 'scale':
422   -
423   - $logoFileNameStretched = 'logo_tmp_stretched_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
424   - $logoFileStretched = $logoDir.DIRECTORY_SEPARATOR.$logoFileNameStretched;
425   -
426   - $logoFileNameCropped = 'logo_tmp_cropped_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
427   - $logoFileCropped = $logoDir.DIRECTORY_SEPARATOR.$logoFileNameCropped;
428   -
429   - //Creating stretched image
430   - $res = $this->scaleImage($logoFile, $logoFileStretched, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, false);
431   -
432   - //Creating top-left cropped image
433   - $res = $this->scaleImage($logoFile, $logoFileCropped, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, true);
434   - $res = $this->cropImage($logoFileCropped, $logoFileCropped, 0, 0, $this->maxLogoWidth, $this->maxLogoHeight, $type);
435   -
436   - $logoItem[] = $relDir.$logoFileNameStretched;
437   - $logoItem[] = $relDir.$logoFileNameCropped;
438   -
439   - $form = $this->getScaleLogoForm($logoItem);
440   - return $form->render();
441   -
442   - default:
443   - $form = $this->getApplyLogoForm($logoFileName);
444   - return $form->render();
445   - }
446   -
447   - }
448   -
449   -
450   - /**
451   - * Returns the MIME of the filename, deducted from its extension
452   - * If the extension is unknown, returns "image/jpeg"
453   - */
454   - function getMime($filename)
455   - {
456   - $pos = strrpos($filename, '.');
457   - $extension = "";
458   - if ($pos !== false) {
459   - $extension = strtolower(substr($filename, $pos+1));
460   - }
461   -
462   - switch($extension) {
463   - case 'gif':
464   - return 'image/gif';
465   - case 'jfif':
466   - return 'image/jpeg';
467   - case 'jfif-tbnl':
468   - return 'image/jpeg';
469   - case 'png':
470   - return 'image/png';
471   - case 'jpe':
472   - return 'image/jpeg';
473   - case 'jpeg':
474   - return 'image/jpeg';
475   - case 'jpg':
476   - return 'image/jpeg';
477   - default:
478   - return 'image/jpeg';
479   - }
480   - }
481   -
482   -
483   - /**
484   - * Returns the MIME of the filename, deducted from its extension
485   - * If the extension is unknown, returns "image/jpeg"
486   - */
487   - function getExtension($type)
488   - {
489   -
490   - switch($type) {
491   - case 'image/gif':
492   - return 'gif';
493   - case 'image/jpeg':
494   - return 'jfif';
495   - case 'image/jpeg':
496   - return 'jfif-tbnl';
497   - case 'image/png':
498   - return 'png';
499   - case 'image/jpeg':
500   - return 'jpe';
501   - case 'image/jpeg':
502   - return 'jpeg';
503   - case 'image/jpeg':
504   - return 'jpg';
505   - case 'image/pjpeg':
506   - return 'jpg';
507   - default:
508   - return 'image/jpeg';
509   - }
510   - }
511   -
512   -
513   - /**
514   - * Returns TRUE of the extension is supported
515   - */
516   - function isSupportedExtension($extension)
517   - {
518   - if (in_array($extension, $this->supportedTypes)) {
519   - return TRUE;
520   - }
  1 +<?php
  2 +/**
  3 + * $Id$
  4 + *
  5 + * KnowledgeTree Community Edition
  6 + * Document Management Made Simple
  7 + * Copyright (C) 2008, 2009 KnowledgeTree Inc.
  8 + *
  9 + *
  10 + * This program is free software; you can redistribute it and/or modify it under
  11 + * the terms of the GNU General Public License version 3 as published by the
  12 + * Free Software Foundation.
  13 + *
  14 + * This program is distributed in the hope that it will be useful, but WITHOUT
  15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
  16 + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
  17 + * details.
  18 + *
  19 + * You should have received a copy of the GNU General Public License
  20 + * along with this program. If not, see <http://www.gnu.org/licenses/>.
  21 + *
  22 + * You can contact KnowledgeTree Inc., PO Box 7775 #87847, San Francisco,
  23 + * California 94120-7775, or email info@knowledgetree.com.
  24 + *
  25 + * The interactive user interfaces in modified source and object code versions
  26 + * of this program must display Appropriate Legal Notices, as required under
  27 + * Section 5 of the GNU General Public License version 3.
  28 + *
  29 + * In accordance with Section 7(b) of the GNU General Public License version 3,
  30 + * these Appropriate Legal Notices must retain the display of the "Powered by
  31 + * KnowledgeTree" logo and retain the original copyright notice. If the display of the
  32 + * logo is not reasonably feasible for technical reasons, the Appropriate Legal Notices
  33 + * must display the words "Powered by KnowledgeTree" and retain the original
  34 + * copyright notice.
  35 + * Contributor( s): ______________________________________
  36 + */
  37 +
  38 +require_once(KT_LIB_DIR . '/dispatcher.inc.php');
  39 +require_once(KT_LIB_DIR . '/templating/templating.inc.php');
  40 +require_once(KT_LIB_DIR . '/browse/columnregistry.inc.php');
  41 +require_once(KT_LIB_DIR . '/widgets/reorderdisplay.inc.php');
  42 +require_once(KT_LIB_DIR . '/widgets/fieldWidgets.php');
  43 +require_once(KT_LIB_DIR . "/widgets/FieldsetDisplayRegistry.inc.php");
  44 +require_once(KT_LIB_DIR . "/widgets/fieldsetDisplay.inc.php");
  45 +require_once(KT_LIB_DIR . "/widgets/widgetfactory.inc.php");
  46 +require_once(KT_LIB_DIR . "/validation/dispatchervalidation.inc.php");
  47 +require_once(KT_LIB_DIR . "/metadata/fieldsetregistry.inc.php");
  48 +require_once(KT_LIB_DIR . "/validation/validatorfactory.inc.php");
  49 +
  50 +
  51 +class ManageBrandDispatcher extends KTAdminDispatcher {
  52 +
  53 + private $maxLogoWidth = 313;
  54 + private $maxLogoHeight = 50;
  55 + public $supportedTypes = array('gif', 'png', 'pjpeg', 'jpe', 'jpeg', 'jpg', 'jfif', 'jfif-tbnl');
  56 +
  57 + function check() {
  58 +
  59 + $this->aBreadcrumbs[] = array('url' => $_SERVER['PHP_SELF'], 'name' => _kt('Manage Branding'));
  60 + return parent::check();
  61 + }
  62 +
  63 + function do_main() {
  64 + $uploadLogoForm = $this->getUploadLogoForm();
  65 + return $uploadLogoForm->render();
  66 + }
  67 +
  68 +
  69 + /**
  70 + * Returns the upload logo form
  71 + * @return KTForm
  72 + *
  73 + */
  74 +
  75 + function getUploadLogoForm() {
  76 + $this->oPage->setBreadcrumbDetails(_kt("Upload Logo"));
  77 +
  78 + $oForm = new KTForm;
  79 + $oForm->setOptions(array(
  80 + 'identifier' => 'ktcore.folder.branding',
  81 + 'label' => _kt('Upload Logo'),
  82 + 'submit_label' => _kt('Upload'),
  83 + 'action' => 'upload',
  84 + 'fail_action' => 'main',
  85 + 'encoding' => 'multipart/form-data',
  86 + 'context' => &$this,
  87 + 'extraargs' => $this->meldPersistQuery("","",true),
  88 + 'description' => _kt('You can upload a logo to brand your KnowledgeTree site.')
  89 + ));
  90 +
  91 + $oWF =& KTWidgetFactory::getSingleton();
  92 +
  93 + $widgets = array();
  94 + $validators = array();
  95 +
  96 + // Adding the File Upload Widget
  97 + $widgets[] = $oWF->get('ktcore.widgets.file', array(
  98 + 'label' => _kt('Logo File'),
  99 + 'required' => true,
  100 + 'name' => 'file',
  101 + 'id' => 'file',
  102 + 'value' => '',
  103 + 'description' => _kt("The logo's dimensions should be 313px width by 50px height. If your logo doesn't fit these dimensions, you can choose to crop or scale it."),
  104 + ));
  105 +
  106 + $aVocab['crop'] = 'Crop - Cut out a selection';
  107 + $aVocab['scale'] = 'Scale - Stretch or Shrink to fit';
  108 + $aVocab['nothing'] = 'Don\'t do anything <span class="descriptiveText">(My image has the correct dimensions)</span>';
  109 +
  110 + //Adding document type lookup widget
  111 + $widgets[] = $oWF->get('ktcore.widgets.selection',array(
  112 + 'label' => _kt('Fitting Image'),
  113 + 'id' => 'logo_action',
  114 + 'description' => _kt('How would you like to resize the image?'),
  115 + 'name' => 'resize_method',
  116 + 'vocab' => $aVocab,
  117 + 'selected' => 'crop',
  118 + 'label_method' => 'getName',
  119 + 'simple_select' => true,
  120 + ));
  121 +
  122 + $oForm->setWidgets($widgets);
  123 + $oForm->setValidators($validators);
  124 +
  125 + // TODO: Should electronic signature be implemented for this?
  126 + // Implement an electronic signature for accessing the admin section, it will appear every 10 minutes
  127 + /* //Have to instanciate the oFolder
  128 + global $default;
  129 + $iFolderId = $this->oFolder->getId();
  130 + if($default->enableESignatures){
  131 + $sUrl = KTPluginUtil::getPluginPath('electronic.signatures.plugin', true);
  132 + $heading = _kt('You are attempting to perform a bulk upload');
  133 + $submit['type'] = 'button';
  134 + $submit['onclick'] = "javascript: showSignatureForm('{$sUrl}', '{$heading}', 'ktcore.transactions.bulk_upload', 'bulk', 'bulk_upload_form', 'submit', {$iFolderId});";
  135 + }else{
  136 + $submit['type'] = 'submit';
  137 + $submit['onclick'] = '';
  138 + }
  139 + */
  140 +
  141 + return $oForm;
  142 + }
  143 +
  144 +
  145 + /**
  146 + * Returns the scale logo form
  147 + *
  148 + * This form will display a preview of all the possible sclaled combinations.
  149 + * This includes:
  150 + *
  151 + * Stretched, Top Left Cropped, Proportional Stretch, Proportional Top Left Cropped
  152 + *
  153 + * @return KTForm
  154 + *
  155 + */
  156 +
  157 + function getScaleLogoForm($logoItems = array()) {
  158 + $this->oPage->setBreadcrumbDetails(_kt("Scale Logo"));
  159 +
  160 + $oForm = new KTForm;
  161 + $oForm->setOptions(array(
  162 + 'identifier' => 'ktcore.folder.branding',
  163 + 'label' => _kt('Choose Logo'),
  164 + 'submit_label' => _kt('Select'),
  165 + 'action' => 'selectLogo',
  166 + 'fail_action' => 'main',
  167 + 'encoding' => 'multipart/form-data',
  168 + 'context' => &$this,
  169 + 'extraargs' => $this->meldPersistQuery("","",true),
  170 + 'description' => _kt('Choose a logo by clicking on one of the images')
  171 + ));
  172 +
  173 + $oWF =& KTWidgetFactory::getSingleton();
  174 +
  175 + $widgets = array();
  176 + $validators = array();
  177 +
  178 + $logoFileName = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  179 +
  180 + // Adding the image select widget (User will select the best image)
  181 + $widgets[] = $oWF->get('ktcore.widgets.imageselect', array(
  182 + 'label' => _kt('Logo Preview'),
  183 + 'name' => $logoFileName,
  184 + 'value' => $logoItems,
  185 + ));
  186 +
  187 + // Adding the Hidden FileName Input String
  188 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  189 + 'name' => 'kt_imageselect',
  190 + 'value' => $logoItems[0],
  191 + ));
  192 +
  193 + $oForm->setWidgets($widgets);
  194 + $oForm->setValidators($validators);
  195 +
  196 + return $oForm;
  197 + }
  198 +
  199 +
  200 + /**
  201 + * Returns the crop logo form
  202 + *
  203 + * This form will assist the user in selecting an area of the image to use as the logo
  204 + * within predefined dimensions required for the logo to fit properly into the page header.
  205 + *
  206 + * @return KTForm
  207 + *
  208 + */
  209 +
  210 + function getCropLogoForm($logoFileName = '') {
  211 + $this->oPage->setBreadcrumbDetails(_kt("Crop Logo"));
  212 +
  213 + $oForm = new KTForm;
  214 + $oForm->setOptions(array(
  215 + 'identifier' => 'ktcore.folder.branding',
  216 + 'name' => 'crop_form',
  217 + 'label' => _kt('Crop Logo'),
  218 + 'submit_label' => _kt('Crop'),
  219 + 'action' => 'crop',
  220 + 'fail_action' => 'main',
  221 + 'encoding' => 'multipart/form-data',
  222 + 'context' => &$this,
  223 + 'extraargs' => $this->meldPersistQuery("","",true),
  224 + 'description' => _kt('Use this facility to ensure that the logo meets the required dimensions for the header.')
  225 + ));
  226 +
  227 + $oWF =& KTWidgetFactory::getSingleton();
  228 +
  229 + $widgets = array();
  230 + $validators = array();
  231 +
  232 + $logoFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  233 + $ext = end(explode('.', end(explode(DIRECTORY_SEPARATOR, $logoFile))));
  234 + $type = $this->getMime($ext);
521 235  
522   - return FALSE;
523   - }
  236 + $imageWidth = $this->getImageWidth($logoFile, $type);
  237 + $imageHeight = $this->getImageHeight($logoFile, $type);
524 238  
525   -
526   - /*
527   - * This method uses the GD library to scale an image.
528   - * - Supported images are jpeg, png and gif
529   - *
530   - */
531   - public function scaleImage( $origFile, $destFile, $width, $height, $type = 'image/jpeg', $scaleUp = false, $keepProportion = true) {
532   - global $default;
533   -
534   - //Requires the GD library if not exit gracefully
535   - if (!extension_loaded('gd')) {
536   - $default->log->error("The GD library isn't loaded");
537   - return false;
538   - }
539   -
540   - switch($type) {
541   - case 'image/jpeg':
542   - $orig = imagecreatefromjpeg($origFile);
543   - break;
544   - case 'image/pjpeg':
545   - $orig = imagecreatefromjpeg($origFile);
546   - break;
547   - case 'image/png':
548   - $orig = imagecreatefrompng($origFile);
549   - break;
550   - case 'image/gif':
551   - $orig = imagecreatefromgif($origFile);
552   - break;
553   - default:
554   - //Handle Error
555   - $default->log->error("Tried to scale an unsupported file type: $type");
556   - return false;
  239 + if ($imageWidth > $this->maxLogoWidth) {
  240 + $imageWidth = $this->maxLogoWidth;
557 241 }
558 242  
559   - if($orig) {
560   - /*
561   - * calculate the size of the new image.
562   - */
563   - $orig_x = imagesx($orig);
564   - $orig_y = imagesy($orig);
565   -
566   - if (($orig_x < $width) && ($orig_y < $height)) {
567   - //Image Qualifies for Upscaling
568   - //If we're not going to scale up then exit here.
569   - if (!$scaleUp) {
570   - return true;
571   - }
572   - }
573   -
574   - $image_x = $width;
575   - $image_y = $height;
576   -
577   - //Constraining proportion
578   - if ($keepProportion) {
579   - $image_y = round(($orig_y * $image_x) / $orig_x); //Preserve proportion
580   - }
581   -
582   - /*
583   - * create the new image, and scale the original into it.
584   - */
585   - $image = imagecreatetruecolor($image_x, $image_y);
586   - imagecopyresampled($image, $orig, 0, 0, 0, 0, $image_x, $image_y, $orig_x, $orig_y);
587   -
588   - switch($type) {
589   - case 'image/jpeg':
590   - imagejpeg($image, $destFile);
591   - break;
592   - case 'image/pjpeg':
593   - imagejpeg($image, $destFile);
594   - break;
595   - case 'image/png':
596   - imagepng($image, $destFile);
597   - break;
598   - case 'image/gif':
599   - imagegif($image, $destFile);
600   - break;
601   - default:
602   - //Handle Error
603   - $default->log->error("Tried to scale an unsupported file type: $type");
604   - return false;
605   - }
606   -
607   - } else {
608   - //Handle Error
609   - $default->log->error("Couldn't obtain a valid GD resource");
610   - $default->log->error($sourceFile);
611   - $default->log->error($destFile);
612   - return false;
613   - }
614   -
615   - return true;
616   - }
617   -
618   -
619   - /*
620   - * Action responsible for cropping the logo
621   - *
622   - */
623   - function do_crop(){
624   - global $default;
625   -
626   - $logoFileName = $_REQUEST['data']['logo_file_name'];
627   - $logoFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
628   -
629   - $ext = end(explode('.', $logoFileName));
630   - $destFileName = 'logo_tmp_'.md5(Date('ymd-hms')).'.'.$ext;
631   - $destFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$destFileName;
632   -
633   - $x1 = $_REQUEST['data']['crop_x1'];
634   - $y1 = $_REQUEST['data']['crop_y1'];
635   -
636   - $x2 = $_REQUEST['data']['crop_x2'];
637   - $y2 = $_REQUEST['data']['crop_y2'];
638   -
639   - $type = $this->getMime($logoFileName);
640   -
641   - //GD Crop
642   - $res = $this->cropImage($logoFile, $destFile, $x1, $y1, $x2, $y2, $type);
643   -
644   - //If dimensions don't conform then will scale it further
645   - $width = $x2 - $x1;
646   - $height = $y2 - $y1;
647   -
648   - if (($width > $this->maxLogoWidth) || ($height > $this->maxLogoHeight)) {
649   - $default->log->info('SCALING IMAGE AFTER CROP');
650   - $res = $this->scaleImage($destFile, $destFile, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, false);
651   - }
652   -
653   - // ImageMagick Crop
654   - /*
655   - // do generation
656   - $pathConvert = (!empty($default->convertPath)) ? $default->convertPath : 'convert';
657   -
658   - // windows path may contain spaces
659   - if (stristr(PHP_OS,'WIN')) {
660   - $cmd = "\"{$pathConvert}\" \"{$logoFileName}" . $pageNumber . "\" -crop 313x50+110+110 \"$logoFileName\"";
661   - }
662   - else {
663   - $cmd = "{$pathConvert} {$logoFileName}" . $pageNumber . " -resize 313x50 $logoFileName";
664   - }
665   -
666   - $result = KTUtil::pexec($cmd);
667   - */
668   -
669   - $applyLogoForm = $this->getApplyLogoForm($destFileName);
670   - return $applyLogoForm->render();
671   -
672   - }
673   -
674   - /*
675   - * This method is used to determine if the image actually can be cropped
676   - * - Supported images are jpeg, png and gif
677   - *
678   - */
679   - public function isImageCroppable( $origFile, $width, $height, $type) {
680   - global $default;
681   -
682   - //Requires the GD library if not exit gracefully
683   - if (!extension_loaded('gd')) {
684   - $default->log->error("The GD library isn't loaded");
685   - return false;
686   - }
687   -
688   - switch($type) {
689   - case 'image/jpeg':
690   - $orig = imagecreatefromjpeg($origFile);
691   - break;
692   - case 'image/pjpeg':
693   - $orig = imagecreatefromjpeg($origFile);
694   - break;
695   - case 'image/png':
696   - $orig = imagecreatefrompng($origFile);
697   - break;
698   - case 'image/gif':
699   - $orig = imagecreatefromgif($origFile);
700   - break;
701   - default:
702   - //Handle Error
703   - $default->log->error("Tried to determine crop for an unsupported file type: $type");
704   - return false;
  243 + if ($imageHeight > $this->maxLogoHeight) {
  244 + $imageHeight = $this->maxLogoHeight;
705 245 }
706 246  
707   - if($orig) {
708   - /*
709   - * calculate the size of the new image.
710   - */
  247 + // Adding the Image Crop Widget
  248 + $widgets[] = $oWF->get('ktcore.widgets.imagecrop', array(
  249 + 'label' => _kt('Crop Logo'),
  250 + //'name' => 'Logo',
  251 + 'value' => $logoFile,
  252 + 'init_width' => $imageWidth,
  253 + 'init_height' => $imageHeight,
  254 + 'description' => _kt('To crop an area of the logo, click and drag the resizable rectangle over the image.'),
  255 + ));
  256 +
  257 + // Adding the Hidden FileName Input String
  258 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  259 + 'name' => 'logo_file_name',
  260 + 'value' => $logoFileName,
  261 + ));
  262 +
  263 + // Adding the Hidden Coordinates X1
  264 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  265 + 'name' => 'crop_x1',
  266 + 'value' => 'x1test',
  267 + ));
  268 +
  269 + // Adding the Hidden Coordinates Y1
  270 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  271 + 'name' => 'crop_y1',
  272 + 'value' => '',
  273 + ));
  274 +
  275 + // Adding the Hidden Coordinates X2
  276 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  277 + 'name' => 'crop_x2',
  278 + 'value' => '',
  279 + ));
  280 +
  281 + // Adding the Hidden Coordinates Y2
  282 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  283 + 'name' => 'crop_y2',
  284 + 'value' => '',
  285 + ));
  286 +
  287 + $oForm->setWidgets($widgets);
  288 + $oForm->setValidators($validators);
  289 +
  290 + return $oForm;
  291 + }
  292 +
  293 + /**
  294 + * Returns the apply logo form
  295 + *
  296 + * This form will display a preview of the correctly sized logo and prompt the user to apply it.
  297 + *
  298 + * @return KTForm
  299 + *
  300 + */
  301 +
  302 + function getApplyLogoForm($logoFileName = '') {
  303 + $this->oPage->setBreadcrumbDetails(_kt("Apply Logo"));
  304 +
  305 + $oForm = new KTForm;
  306 + $oForm->setOptions(array(
  307 + 'identifier' => 'ktcore.folder.branding',
  308 + 'label' => _kt('Apply Logo'),
  309 + 'submit_label' => _kt('Apply'),
  310 + 'action' => 'apply',
  311 + 'fail_action' => 'main',
  312 + 'encoding' => 'multipart/form-data',
  313 + 'context' => &$this,
  314 + 'extraargs' => $this->meldPersistQuery("","",true),
  315 + 'description' => _kt('Applying the logo will activate it in the header making it visible to all who access this site.')
  316 + ));
  317 +
  318 + $oWF =& KTWidgetFactory::getSingleton();
  319 +
  320 + $widgets = array();
  321 + $validators = array();
  322 +
  323 + $logoFileName = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  324 +
  325 + // Adding the Image Widget
  326 + $widgets[] = $oWF->get('ktcore.widgets.image', array(
  327 + 'label' => _kt('Logo Preview'),
  328 + 'name' => $logoFileName, // title and alt attributes get set to this.
  329 + 'value' => $logoFileName,
  330 + 'width' => $this->maxLogoWidth,
  331 + 'height' => $this->maxLogoHeight,
  332 + 'widgetwidth' => 20
  333 + ));
  334 +
  335 + // Adding the Hidden FileName Input String
  336 + $widgets[] = $oWF->get('ktcore.widgets.hidden', array(
  337 + 'name' => 'logo_file_name',
  338 + 'value' => $logoFileName,
  339 + ));
  340 +
  341 + $oForm->setWidgets($widgets);
  342 + $oForm->setValidators($validators);
  343 +
  344 + return $oForm;
  345 + }
  346 +
  347 + /*
  348 + * Action responsible for uploading the logo
  349 + *
  350 + */
  351 +
  352 + function do_upload(){
  353 + global $default;
  354 +
  355 + $oForm = $this->getUploadLogoForm();
  356 + $res = $oForm->validate();
  357 + if (!empty($res['errors'])) {
  358 + return $oForm->handleError();
  359 + }
  360 +
  361 + // Setting up the branding directory, logos will be stored in var/branding/
  362 + $brandDir = $default->varDirectory.DIRECTORY_SEPARATOR.'branding';
  363 +
  364 + if (stristr(PHP_OS,'WIN')) {
  365 + $brandDir = str_replace('/', '\\', $brandDir);
  366 + }
  367 +
  368 + //if branding dir does not exist, generate one and add an index file to block access
  369 + if (!file_exists($brandDir)) {
  370 + mkdir($brandDir, 0755);
  371 + touch($brandDir.DIRECTORY_SEPARATOR.'index.html');
  372 + file_put_contents($brandDir.DIRECTORY_SEPARATOR.'index.html', 'You do not have permission to access this directory.');
  373 + }
  374 +
  375 + $logoDir = $brandDir.DIRECTORY_SEPARATOR."logo";
  376 + //if branding dir does not exist, generate one and add an index file to block access
  377 + if (!file_exists($logoDir)) {
  378 + mkdir($logoDir, 0755);
  379 + touch($logoDir.DIRECTORY_SEPARATOR.'index.html');
  380 + file_put_contents($logoDir.DIRECTORY_SEPARATOR.'index.html', 'You do not have permission to access this directory.');
  381 + }
  382 +
  383 + $logoFileName = $_FILES['_kt_attempt_unique_file']['name'];
  384 +
  385 + //Changing to logo.jpg (Need to preserve extention as GD requires the exact image type to work)
  386 + $ext = end(explode('.', $logoFileName));
  387 +
  388 + $type = $_FILES['_kt_attempt_unique_file']['type'];
  389 +
  390 + //Stage 1 filename based ext check:
  391 + if (!$this->isSupportedExtension($ext)) {
  392 + //If filename based extension isn't supported will try and guess based on mime type
  393 + $default->log->error("Stage 1: Unsupported file type: '".$type."' for file: ':".$_FILES['_kt_attempt_unique_file']['name']."'");
  394 + $ext = $this->getExtension($type);
  395 +
  396 + if (!$this->isSupportedExtension($ext)) {
  397 + $default->log->error("Unsupported file type: '".$type."' for file: ':".$_FILES['_kt_attempt_unique_file']['name']."'");
  398 + $this->errorRedirectToMain("The file you tried to upload is not supported.");
  399 + }
  400 + }
  401 +
  402 + $logoFileName = 'logo_tmp_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
  403 + $logoFile = $logoDir.DIRECTORY_SEPARATOR.$logoFileName;
  404 +
  405 + // deleting old tmp file
  406 + if (file_exists($logoFile)) {
  407 + @unlink($logoFile);
  408 + }
  409 +
  410 + //TODO: Test Upload Failure by setting the $logoFile to ''
  411 +
  412 + if(!move_uploaded_file($_FILES['_kt_attempt_unique_file']['tmp_name'], $logoFile)) {
  413 + $default->log->error("Couldn't upload file from '".$_FILES['_kt_attempt_unique_file']['tmp_name']."' to '$logoFile'");
  414 + $this->errorRedirectToMain("Couldn't upload file");
  415 + exit(0);
  416 + }
  417 +
  418 + $resizeMethod = $_REQUEST['data']['resize_method'];
  419 +
  420 + $relDir = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR;
  421 +
  422 + switch ($resizeMethod) {
  423 + case 'crop':
  424 +
  425 + if ($this->isImageCroppable($logoFile, $this->maxLogoWith, $this->maxLogoHeight, $type)) {
  426 +
  427 + $retForm = $this->getCropLogoForm($logoFileName);
  428 + } else {
  429 + $_SESSION['KTErrorMessage'][] = _kt("The image was too small to be cropped.");
  430 + $retForm = $this->getApplyLogoForm($logoFileName);
  431 + }
  432 +
  433 + return $retForm->render();
  434 +
  435 + case 'scale':
  436 +
  437 + $logoFileNameStretched = 'logo_tmp_stretched_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
  438 + $logoFileStretched = $logoDir.DIRECTORY_SEPARATOR.$logoFileNameStretched;
  439 +
  440 + $logoFileNameCropped = 'logo_tmp_cropped_'.md5(Date('ymd-hms')).'.'.$ext; //Fighting the browser cache here
  441 + $logoFileCropped = $logoDir.DIRECTORY_SEPARATOR.$logoFileNameCropped;
  442 +
  443 + //Creating stretched image
  444 + $res = $this->scaleImage($logoFile, $logoFileStretched, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, false);
  445 +
  446 + //Creating top-left cropped image
  447 + $res = $this->scaleImage($logoFile, $logoFileCropped, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, true);
  448 + $res = $this->cropImage($logoFileCropped, $logoFileCropped, 0, 0, $this->maxLogoWidth, $this->maxLogoHeight, $type);
  449 +
  450 + $logoItem[] = $relDir.$logoFileNameStretched;
  451 + $logoItem[] = $relDir.$logoFileNameCropped;
  452 +
  453 + $form = $this->getScaleLogoForm($logoItem);
  454 + return $form->render();
  455 +
  456 + default:
  457 + $form = $this->getApplyLogoForm($logoFileName);
  458 + return $form->render();
  459 + }
  460 +
  461 + }
  462 +
  463 +
  464 + /**
  465 + * Returns the MIME of the filename, deducted from its extension
  466 + * If the extension is unknown, returns "image/jpeg"
  467 + */
  468 + function getMime($filename)
  469 + {
  470 + $pos = strrpos($filename, '.');
  471 + $extension = "";
  472 + if ($pos !== false) {
  473 + $extension = strtolower(substr($filename, $pos+1));
  474 + }
  475 +
  476 + switch($extension) {
  477 + case 'gif':
  478 + return 'image/gif';
  479 + case 'jfif':
  480 + return 'image/jpeg';
  481 + case 'jfif-tbnl':
  482 + return 'image/jpeg';
  483 + case 'png':
  484 + return 'image/png';
  485 + case 'jpe':
  486 + return 'image/jpeg';
  487 + case 'jpeg':
  488 + return 'image/jpeg';
  489 + case 'jpg':
  490 + return 'image/jpeg';
  491 + default:
  492 + return 'image/jpeg';
  493 + }
  494 + }
  495 +
  496 +
  497 + /**
  498 + * Returns the MIME of the filename, deducted from its extension
  499 + * If the extension is unknown, returns "image/jpeg"
  500 + */
  501 + function getExtension($type)
  502 + {
  503 +
  504 + switch(strtolower($type)) {
  505 + case 'image/gif':
  506 + return 'gif';
  507 + case 'image/jpeg':
  508 + return 'jfif';
  509 + case 'image/jpeg':
  510 + return 'jfif-tbnl';
  511 + case 'image/png':
  512 + return 'png';
  513 + case 'image/jpeg':
  514 + return 'jpe';
  515 + case 'image/jpeg':
  516 + return 'jpeg';
  517 + case 'image/jpeg':
  518 + return 'jpg';
  519 + case 'image/pjpeg':
  520 + return 'jpg';
  521 + default:
  522 + return 'image/jpeg';
  523 + }
  524 + }
  525 +
  526 +
  527 + /**
  528 + * Returns TRUE of the extension is supported
  529 + */
  530 + function isSupportedExtension($extension)
  531 + {
  532 + if (in_array(strtolower($extension), $this->supportedTypes)) {
  533 + return TRUE;
  534 + }
  535 +
  536 + return FALSE;
  537 + }
  538 +
  539 +
  540 + /*
  541 + * This method uses the GD library to scale an image.
  542 + * - Supported images are jpeg, png and gif
  543 + *
  544 + */
  545 + public function scaleImage( $origFile, $destFile, $width, $height, $type = 'image/jpeg', $scaleUp = false, $keepProportion = true) {
  546 + global $default;
  547 +
  548 + //Requires the GD library if not exit gracefully
  549 + if (!extension_loaded('gd')) {
  550 + $default->log->error("The GD library isn't loaded");
  551 + return false;
  552 + }
  553 +
  554 + switch($type) {
  555 + case 'image/jpeg':
  556 + $orig = imagecreatefromjpeg($origFile);
  557 + break;
  558 + case 'image/pjpeg':
  559 + $orig = imagecreatefromjpeg($origFile);
  560 + break;
  561 + case 'image/png':
  562 + $orig = imagecreatefrompng($origFile);
  563 + break;
  564 + case 'image/gif':
  565 + $orig = imagecreatefromgif($origFile);
  566 + break;
  567 + default:
  568 + //Handle Error
  569 + $default->log->error("Tried to scale an unsupported file type: $type");
  570 + return false;
  571 + }
  572 +
  573 + if($orig) {
  574 + /*
  575 + * calculate the size of the new image.
  576 + */
  577 + $orig_x = imagesx($orig);
  578 + $orig_y = imagesy($orig);
  579 +
  580 + if (($orig_x < $width) && ($orig_y < $height)) {
  581 + //Image Qualifies for Upscaling
  582 + //If we're not going to scale up then exit here.
  583 + if (!$scaleUp) {
  584 + return true;
  585 + }
  586 + }
  587 +
  588 + $image_x = $width;
  589 + $image_y = $height;
  590 +
  591 + //Constraining proportion
  592 + if ($keepProportion) {
  593 + $image_y = round(($orig_y * $image_x) / $orig_x); //Preserve proportion
  594 + }
  595 +
  596 + /*
  597 + * create the new image, and scale the original into it.
  598 + */
  599 + $image = imagecreatetruecolor($image_x, $image_y);
  600 + imagecopyresampled($image, $orig, 0, 0, 0, 0, $image_x, $image_y, $orig_x, $orig_y);
  601 +
  602 + switch($type) {
  603 + case 'image/jpeg':
  604 + imagejpeg($image, $destFile);
  605 + break;
  606 + case 'image/pjpeg':
  607 + imagejpeg($image, $destFile);
  608 + break;
  609 + case 'image/png':
  610 + imagepng($image, $destFile);
  611 + break;
  612 + case 'image/gif':
  613 + imagegif($image, $destFile);
  614 + break;
  615 + default:
  616 + //Handle Error
  617 + $default->log->error("Tried to scale an unsupported file type: $type");
  618 + return false;
  619 + }
  620 +
  621 + } else {
  622 + //Handle Error
  623 + $default->log->error("Couldn't obtain a valid GD resource");
  624 + $default->log->error($sourceFile);
  625 + $default->log->error($destFile);
  626 + return false;
  627 + }
  628 +
  629 + return true;
  630 + }
  631 +
  632 +
  633 + /*
  634 + * Action responsible for cropping the logo
  635 + *
  636 + */
  637 + function do_crop(){
  638 + global $default;
  639 +
  640 + $logoFileName = $_REQUEST['data']['logo_file_name'];
  641 + $logoFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  642 +
  643 + $ext = end(explode('.', $logoFileName));
  644 + $destFileName = 'logo_tmp_'.md5(Date('ymd-hms')).'.'.$ext;
  645 + $destFile = 'var'.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$destFileName;
  646 +
  647 + $x1 = $_REQUEST['data']['crop_x1'];
  648 + $y1 = $_REQUEST['data']['crop_y1'];
  649 +
  650 + $x2 = $_REQUEST['data']['crop_x2'];
  651 + $y2 = $_REQUEST['data']['crop_y2'];
  652 +
  653 + $type = $this->getMime($logoFileName);
  654 +
  655 + //GD Crop
  656 + $res = $this->cropImage($logoFile, $destFile, $x1, $y1, $x2, $y2, $type);
  657 +
  658 + //If dimensions don't conform then will scale it further
  659 + $width = $x2 - $x1;
  660 + $height = $y2 - $y1;
  661 +
  662 + if (($width > $this->maxLogoWidth) || ($height > $this->maxLogoHeight)) {
  663 + $default->log->info('SCALING IMAGE AFTER CROP');
  664 + $res = $this->scaleImage($destFile, $destFile, $this->maxLogoWidth, $this->maxLogoHeight, $type, false, false);
  665 + }
  666 +
  667 + // ImageMagick Crop
  668 + /*
  669 + // do generation
  670 + $pathConvert = (!empty($default->convertPath)) ? $default->convertPath : 'convert';
  671 +
  672 + // windows path may contain spaces
  673 + if (stristr(PHP_OS,'WIN')) {
  674 + $cmd = "\"{$pathConvert}\" \"{$logoFileName}" . $pageNumber . "\" -crop 313x50+110+110 \"$logoFileName\"";
  675 + }
  676 + else {
  677 + $cmd = "{$pathConvert} {$logoFileName}" . $pageNumber . " -resize 313x50 $logoFileName";
  678 + }
  679 +
  680 + $result = KTUtil::pexec($cmd);
  681 + */
  682 +
  683 + $applyLogoForm = $this->getApplyLogoForm($destFileName);
  684 + return $applyLogoForm->render();
  685 +
  686 + }
  687 +
  688 + /*
  689 + * This method is used to determine if the image actually can be cropped
  690 + * - Supported images are jpeg, png and gif
  691 + *
  692 + */
  693 + public function isImageCroppable( $origFile, $width, $height, $type) {
  694 + global $default;
  695 +
  696 + //Requires the GD library if not exit gracefully
  697 + if (!extension_loaded('gd')) {
  698 + $default->log->error("The GD library isn't loaded");
  699 + return false;
  700 + }
  701 +
  702 + switch($type) {
  703 + case 'image/jpeg':
  704 + $orig = imagecreatefromjpeg($origFile);
  705 + break;
  706 + case 'image/pjpeg':
  707 + $orig = imagecreatefromjpeg($origFile);
  708 + break;
  709 + case 'image/png':
  710 + $orig = imagecreatefrompng($origFile);
  711 + break;
  712 + case 'image/gif':
  713 + $orig = imagecreatefromgif($origFile);
  714 + break;
  715 + default:
  716 + //Handle Error
  717 + $default->log->error("Tried to determine crop for an unsupported file type: $type");
  718 + return false;
  719 + }
  720 +
  721 + if($orig) {
  722 + /*
  723 + * calculate the size of the new image.
  724 + */
  725 + $orig_x = imagesx($orig);
  726 + $orig_y = imagesy($orig);
  727 +
  728 + if (($orig_x > $width) || ($orig_y > $height)) {
  729 + return true;
  730 + }
  731 +
  732 + } else {
  733 + //Handle Error
  734 + $default->log->error("Couldn't obtain a valid GD resource $origFile");
  735 + return false;
  736 + }
  737 +
  738 + return true;
  739 + }
  740 +
  741 +
  742 + /*
  743 + * This method uses GD library to return the image width
  744 + * - Supported images are jpeg, png and gif *
  745 + */
  746 + public function getImageWidth( $origFile, $type) {
  747 + global $default;
  748 +
  749 + //Requires the GD library if not exit gracefully
  750 + if (!extension_loaded('gd')) {
  751 + $default->log->error("The GD library isn't loaded");
  752 + return false;
  753 + }
  754 +
  755 + switch($type) {
  756 + case 'image/jpeg':
  757 + $orig = imagecreatefromjpeg($origFile);
  758 + break;
  759 + case 'image/pjpeg':
  760 + $orig = imagecreatefromjpeg($origFile);
  761 + break;
  762 + case 'image/png':
  763 + $orig = imagecreatefrompng($origFile);
  764 + break;
  765 + case 'image/gif':
  766 + $orig = imagecreatefromgif($origFile);
  767 + break;
  768 + default:
  769 + //Handle Error
  770 + $default->log->error("Tried to determine crop for an unsupported file type: $type");
  771 + return false;
  772 + }
  773 +
  774 + if($orig) {
  775 + /*
  776 + * calculate the size of the new image. */
  777 +
711 778 $orig_x = imagesx($orig);
  779 + return $orig_x;
  780 +
  781 + } else {
  782 + //Handle Error
  783 + $default->log->error("Couldn't obtain a valid GD resource $origFile");
  784 + return false;
  785 + }
  786 +
  787 + return false;
  788 + }
  789 +
  790 +
  791 + /*
  792 + * This method uses GD library to return the image height
  793 + * - Supported images are jpeg, png and gif *
  794 + */
  795 + public function getImageHeight( $origFile, $type) {
  796 + global $default;
  797 +
  798 + //Requires the GD library if not exit gracefully
  799 + if (!extension_loaded('gd')) {
  800 + $default->log->error("The GD library isn't loaded");
  801 + return false;
  802 + }
  803 +
  804 + switch($type) {
  805 + case 'image/jpeg':
  806 + $orig = imagecreatefromjpeg($origFile);
  807 + break;
  808 + case 'image/pjpeg':
  809 + $orig = imagecreatefromjpeg($origFile);
  810 + break;
  811 + case 'image/png':
  812 + $orig = imagecreatefrompng($origFile);
  813 + break;
  814 + case 'image/gif':
  815 + $orig = imagecreatefromgif($origFile);
  816 + break;
  817 + default:
  818 + //Handle Error
  819 + $default->log->error("Tried to determine crop for an unsupported file type: $type");
  820 + return false;
  821 + }
  822 +
  823 + if($orig) {
  824 + /*
  825 + * calculate the size of the new image. */
  826 +
712 827 $orig_y = imagesy($orig);
713   -
714   - $default->log->info("ORIG_X : $orig_x");
715   - $default->log->info("ORIG_Y : $orig_y");
716   -
717   - if (($orig_x > $width) || ($orig_y > $height)) {
718   - return true;
719   - }
720   -
721   - } else {
722   - //Handle Error
723   - $default->log->error("Couldn't obtain a valid GD resource $origFile");
724   - return false;
725   - }
726   -
727   - return true;
728   - }
729   -
730   -
731   - /*
732   - * This method uses the GD library to crop an image.
733   - * - Supported images are jpeg, png and gif
734   - *
735   - */
736   - public function cropImage( $origFile, $destFile, $x1, $y1, $x2, $y2, $type = 'image/jpeg', $scaleUp = true) {
737   - global $default;
738   -
739   - $width = $x2 - $x1;
740   - $height = $y2 - $y1;
741   -
742   - //Requires the GD library if not exit gracefully
743   - if (!extension_loaded('gd')) {
744   - $default->log->error("The GD library isn't loaded");
745   - return false;
746   - }
747   -
748   - switch($type) {
749   - case 'image/jpeg':
750   - $orig = imagecreatefromjpeg($origFile);
751   - break;
752   - case 'image/pjpeg':
753   - $orig = imagecreatefromjpeg($origFile);
754   - break;
755   - case 'image/png':
756   - $orig = imagecreatefrompng($origFile);
757   - break;
758   - case 'image/gif':
759   - $orig = imagecreatefromgif($origFile);
760   - break;
761   - default:
762   - //Handle Error
763   - $default->log->error("Tried to crop an unsupported file type: $type");
764   - return false;
765   - }
766   -
767   - if($orig) {
768   - /*
769   - * create the new image, and crop it.
770   - */
771   - $image = imagecreatetruecolor($width, $height);
772   - //imagecopyresampled($image, $orig, 0, 0, 0, 0, $image_x, $image_y, $orig_x, $orig_y);
773   -
774   - // Generate the cropped image
775   - imagecopyresampled($image, $orig, 0, 0, $x1, $y1, $width, $height, $width, $height);
776   - //imagecopyresized($canvas, $piece, 0,0, $cropLeft, $cropHeight,$newwidth, $newheight, $width, $height);
777   -
778   - switch($type) {
779   - case 'image/jpeg':
780   - imagejpeg($image, $destFile);
781   - break;
782   - case 'image/pjpeg':
783   - imagejpeg($image, $destFile);
784   - break;
785   - case 'image/png':
786   - imagepng($image, $destFile);
787   - break;
788   - case 'image/gif':
789   - imagegif($image, $destFile);
790   - break;
791   - default:
792   - //Handle Error
793   - $default->log->error("Tried to crop an unsupported file type: $type");
794   - return false;
795   - }
796   -
797   -
798   - } else {
799   - //Handle Error
800   - $default->log->error("Couldn't obtain a valid GD resource $sourceFile $destFile");
801   - return false;
802   - }
803   -
804   - return true;
805   - }
806   -
807   -
808   - /*
809   - * Action responsible for selecting the logo after it has been scaled.
810   - *
811   - */
812   - function do_selectLogo(){
813   - global $default;
814   -
815   - $tmpLogoFileName = end(explode(DIRECTORY_SEPARATOR, $_REQUEST['kt_imageselect']));
816   -
817   - $form = $this->getApplyLogoForm($tmpLogoFileName);
818   - return $form->render();
819   -
820   - }
821   -
822   -
823   -
824   - /*
825   - * Action responsible for applying the logo
826   - *
827   - */
828   - function do_apply(){
829   - global $default;
830   -
831   - $rootPath = $default->varDirectory . '/';
832   -
833   - $tmpLogoFileName = $_REQUEST['data']['logo_file_name'];
834   - $tmpLogoFileName = end(explode(DIRECTORY_SEPARATOR, $tmpLogoFileName));
835   - $tmpLogoFile = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$tmpLogoFileName;
836   -
837   - $ext = end(explode('.', $tmpLogoFileName));
838   - $logoFileName = 'logo_'.md5(Date('ymd-hms')).'.'.$ext;
839   - $logoFile = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
840   -
841   - $logoFileRel = end(explode(DIRECTORY_SEPARATOR, $default->varDirectory)).DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
842   -
843   - // Applying the new logo
844   - if(!@copy($tmpLogoFile, $logoFile)){
845   - $default->log->info("Couldn't copy logo ".$tmpLogoFile." to ".$logoFile);
846   - } else {
847   - //Cleaning stale files
848   - $brandDir = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR;
849   - $handle = opendir($brandDir);
850   - while (false !== ($file = readdir($handle))) {
851   - if (!is_dir($file) && $file != $tmpLogoFileName && $file != $logoFileName) {
852   - if (!@unlink($brandDir.$file)) {
853   - $default->log->error("Couldn't delete '".$brandDir.$file."'");
854   - } else {
855   - $default->log->error("Cleaning Brand Logo Dir: Deleted '".$brandDir.$file."'");
856   - }
857   - }
858   - }
859   - }
860   -
861   - //
862   - // Updating Config Settings with the new Logo Location
863   - //
864   -
865   - $sql = "SELECT id from config_settings WHERE item = 'companyLogo'";
866   - $companyLogoId = DBUtil::getOneResultKey($sql,'id');
867   - if (PEAR::isError($companyLogoId))
868   - {
869   - if (PEAR::isError($res)) {
870   - $default->log->error(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
871   - $this->errorRedirectToMain(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
872   - exit();
873   - }
874   - }
875   -
876   - $res = DBUtil::autoUpdate('config_settings', array('value' => $logoFileRel), $companyLogoId);
877   - if (PEAR::isError($res)) {
878   - $default->log->error(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
879   - $this->errorRedirectToMain(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
880   - exit();
881   - }
882   -
883   - // Clear the cached settings
884   - $oKTConfig = new KTConfig();
885   - $oKTConfig->clearCache();
886   -
887   - $this->successRedirectTo('', _kt("Logo succesfully applied."));
888   - }
889   -
890   -}
891   -
892   -?>
  828 + return $orig_y;
  829 +
  830 + } else {
  831 + //Handle Error
  832 + $default->log->error("Couldn't obtain a valid GD resource $origFile");
  833 + return false;
  834 + }
  835 +
  836 + return false;
  837 + }
  838 +
  839 +
  840 + /*
  841 + * This method uses the GD library to crop an image.
  842 + * - Supported images are jpeg, png and gif
  843 + *
  844 + */
  845 + public function cropImage( $origFile, $destFile, $x1, $y1, $x2, $y2, $type = 'image/jpeg', $scaleUp = true) {
  846 + global $default;
  847 +
  848 + $width = $x2 - $x1;
  849 + $height = $y2 - $y1;
  850 +
  851 + //Requires the GD library if not exit gracefully
  852 + if (!extension_loaded('gd')) {
  853 + $default->log->error("The GD library isn't loaded");
  854 + return false;
  855 + }
  856 +
  857 + switch($type) {
  858 + case 'image/jpeg':
  859 + $orig = imagecreatefromjpeg($origFile);
  860 + break;
  861 + case 'image/pjpeg':
  862 + $orig = imagecreatefromjpeg($origFile);
  863 + break;
  864 + case 'image/png':
  865 + $orig = imagecreatefrompng($origFile);
  866 + break;
  867 + case 'image/gif':
  868 + $orig = imagecreatefromgif($origFile);
  869 + break;
  870 + default:
  871 + //Handle Error
  872 + $default->log->error("Tried to crop an unsupported file type: $type");
  873 + return false;
  874 + }
  875 +
  876 + if($orig) {
  877 + /*
  878 + * create the new image, and crop it.
  879 + */
  880 + $image = imagecreatetruecolor($width, $height);
  881 + //imagecopyresampled($image, $orig, 0, 0, 0, 0, $image_x, $image_y, $orig_x, $orig_y);
  882 +
  883 + // Generate the cropped image
  884 + imagecopyresampled($image, $orig, 0, 0, $x1, $y1, $width, $height, $width, $height);
  885 + //imagecopyresized($canvas, $piece, 0,0, $cropLeft, $cropHeight,$newwidth, $newheight, $width, $height);
  886 +
  887 + switch($type) {
  888 + case 'image/jpeg':
  889 + imagejpeg($image, $destFile);
  890 + break;
  891 + case 'image/pjpeg':
  892 + imagejpeg($image, $destFile);
  893 + break;
  894 + case 'image/png':
  895 + imagepng($image, $destFile);
  896 + break;
  897 + case 'image/gif':
  898 + imagegif($image, $destFile);
  899 + break;
  900 + default:
  901 + //Handle Error
  902 + $default->log->error("Tried to crop an unsupported file type: $type");
  903 + return false;
  904 + }
  905 +
  906 +
  907 + } else {
  908 + //Handle Error
  909 + $default->log->error("Couldn't obtain a valid GD resource $sourceFile $destFile");
  910 + return false;
  911 + }
  912 +
  913 + return true;
  914 + }
  915 +
  916 +
  917 + /*
  918 + * Action responsible for selecting the logo after it has been scaled.
  919 + *
  920 + */
  921 + function do_selectLogo(){
  922 + global $default;
  923 +
  924 + $tmpLogoFileName = end(explode(DIRECTORY_SEPARATOR, $_REQUEST['kt_imageselect']));
  925 +
  926 + $form = $this->getApplyLogoForm($tmpLogoFileName);
  927 + return $form->render();
  928 +
  929 + }
  930 +
  931 +
  932 +
  933 + /*
  934 + * Action responsible for applying the logo
  935 + *
  936 + */
  937 + function do_apply(){
  938 + global $default;
  939 +
  940 + $rootPath = $default->varDirectory . '/';
  941 +
  942 + $tmpLogoFileName = $_REQUEST['data']['logo_file_name'];
  943 + $tmpLogoFileName = end(explode(DIRECTORY_SEPARATOR, $tmpLogoFileName));
  944 + $tmpLogoFile = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$tmpLogoFileName;
  945 +
  946 + $ext = end(explode('.', $tmpLogoFileName));
  947 + $logoFileName = 'logo_'.md5(Date('ymd-hms')).'.'.$ext;
  948 + $logoFile = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  949 +
  950 + $logoFileRel = end(explode(DIRECTORY_SEPARATOR, $default->varDirectory)).DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR.$logoFileName;
  951 +
  952 + // Applying the new logo
  953 + if(!@copy($tmpLogoFile, $logoFile)){
  954 + $default->log->info("Couldn't copy logo ".$tmpLogoFile." to ".$logoFile);
  955 + } else {
  956 + //Cleaning stale files
  957 + $brandDir = $default->varDirectory.DIRECTORY_SEPARATOR.'branding'.DIRECTORY_SEPARATOR.'logo'.DIRECTORY_SEPARATOR;
  958 + $handle = opendir($brandDir);
  959 + while (false !== ($file = readdir($handle))) {
  960 + if (!is_dir($file) && $file != $tmpLogoFileName && $file != $logoFileName) {
  961 + if (!@unlink($brandDir.$file)) {
  962 + $default->log->error("Couldn't delete '".$brandDir.$file."'");
  963 + } else {
  964 + $default->log->error("Cleaning Brand Logo Dir: Deleted '".$brandDir.$file."'");
  965 + }
  966 + }
  967 + }
  968 + }
  969 +
  970 + //
  971 + // Updating Config Settings with the new Logo Location
  972 + //
  973 +
  974 + $sql = "SELECT id from config_settings WHERE item = 'companyLogo'";
  975 + $companyLogoId = DBUtil::getOneResultKey($sql,'id');
  976 + if (PEAR::isError($companyLogoId))
  977 + {
  978 + if (PEAR::isError($res)) {
  979 + $default->log->error(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
  980 + $this->errorRedirectToMain(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
  981 + exit();
  982 + }
  983 + }
  984 +
  985 + $res = DBUtil::autoUpdate('config_settings', array('value' => $logoFileRel), $companyLogoId);
  986 + if (PEAR::isError($res)) {
  987 + $default->log->error(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
  988 + $this->errorRedirectToMain(sprintf(_kt("Failed to apply logo: %s"), $res->getMessage()));
  989 + exit();
  990 + }
  991 +
  992 + // Clear the cached settings
  993 + $oKTConfig = new KTConfig();
  994 + $oKTConfig->clearCache();
  995 +
  996 + $this->successRedirectTo('', _kt("Logo succesfully applied."));
  997 + }
  998 +
  999 +}
  1000 +
  1001 +?>
... ...
templates/ktcore/forms/widgets/imagecrop.smarty
1   - <img id="kt_image_to_crop" {if $has_value} src="{$value}"{/if} alt="{$name}" title="{$name}" />
  1 +<img id="kt_image_to_crop" src="{$value}" alt="{$name}" title="{$name}" />
  2 +{$options.init_width}
  3 +{$options.init_height}
  4 +<script type="text/javascript">
  5 +jQuery(function () {ldelim}
  6 + //TODO: Draw attributes and config options from widget attributes
  7 + //jQuery('#kt_image_to_crop').imgAreaSelect({ldelim} maxWidth: 200, maxHeight: 150, handles: true {rdelim});
  8 + //jQuery('#kt_image_to_crop').imgAreaSelect({ldelim} aspectRatio: '4:3', handles: true {rdelim});
  9 + jQuery('#kt_image_to_crop').imgAreaSelect({ldelim}
  10 + x1: 0,
  11 + y1: 0,
  12 + x2: {$options.init_width},
  13 + y2: {$options.init_height},
  14 + handles: true
  15 + {rdelim});
  16 +{rdelim});
  17 +
  18 +jQuery('#kt_image_to_crop').imgAreaSelect({ldelim}
  19 + onSelectEnd: function (img, selection) {ldelim}
  20 + jQuery('input[name="data[crop_x1]"]').val(selection.x1);
  21 + jQuery('input[name="data[crop_y1]"]').val(selection.y1);
  22 + jQuery('input[name="data[crop_x2]"]').val(selection.x2);
  23 + jQuery('input[name="data[crop_y2]"]').val(selection.y2);
  24 + {rdelim}
  25 +{rdelim})
  26 +</script>
... ...