mikuli.cz

:)
git clone https://git.sr.ht/~ashymad/mikuli.cz
Log | Files | Refs

commit 24140d62eabc2accc3f78f432cb7e9fcb07add81
parent b681142bda77dae209615ed24c34e0f655b61c8e
Author: markseu <mark2011@mayberg.se>
Date:   Tue, 25 May 2021 09:39:30 +0200

Updated extensions, no longer needs external exif extension

Diffstat:
Msystem/extensions/core.php | 71++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-------
Msystem/extensions/image.php | 54+++++++++++++++++++++++++++++-------------------------
2 files changed, 93 insertions(+), 32 deletions(-)

diff --git a/system/extensions/core.php b/system/extensions/core.php @@ -2,7 +2,7 @@ // Core extension, https://github.com/datenstrom/yellow-extensions/tree/master/source/core class YellowCore { - const VERSION = "0.8.43"; + const VERSION = "0.8.44"; const RELEASE = "0.8.17"; public $page; // current page public $content; // content files @@ -78,7 +78,6 @@ class YellowCore { $troubleshooting = PHP_SAPI!="cli" ? "<a href=\"".$this->getTroubleshootingUrl()."\">See troubleshooting</a>." : ""; version_compare(PHP_VERSION, "5.6", ">=") || die("Datenstrom Yellow requires PHP 5.6 or higher! $troubleshooting\n"); extension_loaded("curl") || die("Datenstrom Yellow requires PHP curl extension! $troubleshooting\n"); - extension_loaded("exif") || die("Datenstrom Yellow requires PHP exif extension! $troubleshooting\n"); extension_loaded("gd") || die("Datenstrom Yellow requires PHP gd extension! $troubleshooting\n"); extension_loaded("mbstring") || die("Datenstrom Yellow requires PHP mbstring extension! $troubleshooting\n"); extension_loaded("zip") || die("Datenstrom Yellow requires PHP zip extension! $troubleshooting\n"); @@ -3226,7 +3225,7 @@ class YellowToolbox { } if (PHP_OS=="Darwin") { $os = "Mac"; - } else if (strtoupperu(substru(PHP_OS, 0, 3))=="WIN") { + } elseif (strtoupperu(substru(PHP_OS, 0, 3))=="WIN") { $os = "Windows"; } else { $os = PHP_OS; @@ -3247,9 +3246,9 @@ class YellowToolbox { return $languageFound; } - // Detect image dimensions and type for gif/jpg/png/svg + // Detect image width, height, orientation and type for gif/jpg/png/svg public function detectImageInformation($fileName, $fileType = "") { - $width = $height = 0; + $width = $height = $orientation = 0; $type = ""; $fileHandle = @fopen($fileName, "rb"); if ($fileHandle) { @@ -3270,7 +3269,11 @@ class YellowToolbox { if (!feof($fileHandle) && ($dataSignature=="\xff\xd8\xff\xe0" || $dataSignature=="\xff\xd8\xff\xe1")) { for ($pos=2; $pos+8<$dataBufferSize; $pos+=$length) { if ($dataBuffer[$pos]!="\xff") break; - if ($dataBuffer[$pos+1]=="\xc0" || $dataBuffer[$pos+1]=="\xc2") { + $dataMarker = $dataBuffer[$pos+1]; + if ($dataMarker=="\xe1") { + $orientation = $this->getImageOrientationFromBuffer($dataBuffer, $pos+4, $dataBufferSize); + } + if ($dataMarker>="\xc0" && $dataMarker<="\xcf") { $width = (ord($dataBuffer[$pos+7])<<8) + ord($dataBuffer[$pos+8]); $height = (ord($dataBuffer[$pos+5])<<8) + ord($dataBuffer[$pos+6]); $type = $fileType; @@ -3310,7 +3313,61 @@ class YellowToolbox { } fclose($fileHandle); } - return array($width, $height, $type); + return array($width, $height, $orientation, $type); + } + + // Return image orientation from Exif + public function getImageOrientationFromBuffer($dataBuffer, $pos, $size) { + $orientation = 0; + $dataSignature = substrb($dataBuffer, $pos, 6); + if ($dataSignature=="\x45\x78\x69\x66\x00\x00" && $pos+14<=$size) { + $startPos = $pos+6; + $bigEndian = $dataBuffer[$startPos]=="M"; + $ifdOffset = $this->getLongFromBuffer($dataBuffer, $startPos+4, $bigEndian); + $ifdStartPos = $startPos+$ifdOffset; + $ifdCount = $ifdStartPos+2<=$size ? $this->getShortFromBuffer($dataBuffer, $ifdStartPos, $bigEndian) : 0; + $pos = $ifdStartPos+2; + while ($ifdCount && $pos+12<=$size) { + $ifdTag = $this->getShortFromBuffer($dataBuffer, $pos, $bigEndian); + $ifdFormat = $this->getShortFromBuffer($dataBuffer, $pos+2, $bigEndian); + if ($ifdTag==0x8769 && $ifdFormat==4) { + $ifdOffset = $this->getLongFromBuffer($dataBuffer, $pos+8, $bigEndian); + $ifdStartPos = $startPos+$ifdOffset; + $ifdCount = $ifdStartPos+2<=$size ? $this->getShortFromBuffer($dataBuffer, $ifdStartPos, $bigEndian) : 0; + $pos = $ifdStartPos+2; + continue; + } + if ($ifdTag==0x0112 && $ifdFormat==3) { + $orientation = $this->getShortFromBuffer($dataBuffer, $pos+8, $bigEndian); + break; + } + --$ifdCount; + $pos += 12; + } + } + return $orientation; + } + + // Return unsigned short value from buffer + public function getShortFromBuffer($dataBuffer, $pos, $bigEndian) { + if ($bigEndian) { + $value = (ord($dataBuffer[$pos])<<8) + ord($dataBuffer[$pos+1]); + } else { + $value = (ord($dataBuffer[$pos+1])<<8) + ord($dataBuffer[$pos]); + } + return $value; + } + + // Return unsigned long value from buffer + public function getLongFromBuffer($dataBuffer, $pos, $bigEndian) { + if ($bigEndian) { + $value = (ord($dataBuffer[$pos])<<24) + (ord($dataBuffer[$pos+1])<<16) + + (ord($dataBuffer[$pos+2])<<8) + ord($dataBuffer[$pos+3]); + } else { + $value = (ord($dataBuffer[$pos+3])<<24) + (ord($dataBuffer[$pos+2])<<16) + + (ord($dataBuffer[$pos+1])<<8) + ord($dataBuffer[$pos]); + } + return $value; } // Normalise location arguments diff --git a/system/extensions/image.php b/system/extensions/image.php @@ -2,7 +2,7 @@ // Image extension, https://github.com/datenstrom/yellow-extensions/tree/master/source/image class YellowImage { - const VERSION = "0.8.12"; + const VERSION = "0.8.13"; public $yellow; // access to API // Handle initialisation @@ -57,16 +57,25 @@ class YellowImage { public function onEditMediaFile($file, $action, $email) { if ($action=="upload") { $fileName = $file->fileName; - list($widthInput, $heightInput, $type) = $this->yellow->toolbox->detectImageInformation($fileName, $file->get("type")); + list($widthInput, $heightInput, $orientation, $type) = + $this->yellow->toolbox->detectImageInformation($fileName, $file->get("type")); $widthMax = $this->yellow->system->get("imageUploadWidthMax"); $heightMax = $this->yellow->system->get("imageUploadHeightMax"); - if (($widthInput>$widthMax || $heightInput>$heightMax) && ($type=="gif" || $type=="jpg" || $type=="png")) { - list($widthOutput, $heightOutput) = $this->getImageDimensionsFit($widthInput, $heightInput, $widthMax, $heightMax); - $image = $this->loadImage($fileName, $type); - $image = $this->resizeImage($image, $widthInput, $heightInput, $widthOutput, $heightOutput); - $image = $this->orientImage($image, $fileName, $type); - if (!$this->saveImage($image, $fileName, $type, $this->yellow->system->get("imageUploadJpgQuality"))) { - $file->error(500, "Can't write file '$fileName'!"); + if ($type=="gif" || $type=="jpg" || $type=="png") { + if ($widthInput>$widthMax || $heightInput>$heightMax) { + list($widthOutput, $heightOutput) = $this->getImageDimensionsFit($widthInput, $heightInput, $widthMax, $heightMax); + $image = $this->loadImage($fileName, $type); + $image = $this->resizeImage($image, $widthInput, $heightInput, $widthOutput, $heightOutput); + $image = $this->orientImage($image, $orientation); + if (!$this->saveImage($image, $fileName, $type, $this->yellow->system->get("imageUploadJpgQuality"))) { + $file->error(500, "Can't write file '$fileName'!"); + } + } elseif ($orientation>1) { + $image = $this->loadImage($fileName, $type); + $image = $this->orientImage($image, $orientation); + if (!$this->saveImage($image, $fileName, $type, $this->yellow->system->get("imageUploadJpgQuality"))) { + $file->error(500, "Can't write file '$fileName'!"); + } } } } @@ -75,7 +84,7 @@ class YellowImage { // Return image information, create thumbnail on demand public function getImageInformation($fileName, $widthOutput, $heightOutput) { $fileNameShort = substru($fileName, strlenu($this->yellow->system->get("coreImageDirectory"))); - list($widthInput, $heightInput, $type) = $this->yellow->toolbox->detectImageInformation($fileName); + list($widthInput, $heightInput, $orientation, $type) = $this->yellow->toolbox->detectImageInformation($fileName); $widthOutput = $this->convertValueAndUnit($widthOutput, $widthInput); $heightOutput = $this->convertValueAndUnit($heightOutput, $heightInput); if (($widthInput==$widthOutput && $heightInput==$heightOutput) || $type=="svg" || $type=="") { @@ -90,7 +99,7 @@ class YellowImage { if ($this->isFileNotUpdated($fileName, $fileNameOutput)) { $image = $this->loadImage($fileName, $type); $image = $this->resizeImage($image, $widthInput, $heightInput, $widthOutput, $heightOutput); - $image = $this->orientImage($image, $fileName, $type); + $image = $this->orientImage($image, $orientation); if (is_file($fileNameOutput)) $this->yellow->toolbox->deleteFile($fileNameOutput); if (!$this->saveImage($image, $fileNameOutput, $type, $this->yellow->system->get("imageThumbnailJpgQuality")) || !$this->yellow->toolbox->modifyFile($fileNameOutput, $this->yellow->toolbox->getFileModified($fileName))) { @@ -160,20 +169,15 @@ class YellowImage { } // Orient image automatically - public function orientImage($image, $fileName, $type) { - if ($type=="jpg") { - $exif = @exif_read_data($fileName); - if ($exif && isset($exif["Orientation"])) { - switch ($exif["Orientation"]) { - case 2: imageflip($image, IMG_FLIP_HORIZONTAL); break; - case 3: $image = imagerotate($image, 180, 0); break; - case 4: imageflip($image, IMG_FLIP_VERTICAL); break; - case 5: $image = imagerotate($image, 90, 0); imageflip($image, IMG_FLIP_VERTICAL); break; - case 6: $image = imagerotate($image, -90, 0); break; - case 7: $image = imagerotate($image, 90, 0); imageflip($image, IMG_FLIP_HORIZONTAL); break; - case 8: $image = imagerotate($image, 90, 0); break; - } - } + public function orientImage($image, $orientation) { + switch ($orientation) { + case 2: imageflip($image, IMG_FLIP_HORIZONTAL); break; + case 3: $image = imagerotate($image, 180, 0); break; + case 4: imageflip($image, IMG_FLIP_VERTICAL); break; + case 5: $image = imagerotate($image, 90, 0); imageflip($image, IMG_FLIP_VERTICAL); break; + case 6: $image = imagerotate($image, -90, 0); break; + case 7: $image = imagerotate($image, 90, 0); imageflip($image, IMG_FLIP_HORIZONTAL); break; + case 8: $image = imagerotate($image, 90, 0); break; } return $image; }