Verzeichnisstruktur phpBB-3.2.0


Veröffentlicht
06.01.2017

So funktioniert es


Auf das letzte Element klicken. Dies geht jeweils ein Schritt zurück

Auf das Icon klicken, dies öffnet das Verzeichnis. Nochmal klicken schließt das Verzeichnis.
Auf den Verzeichnisnamen klicken, dies zeigt nur das Verzeichnis mit Inhalt an

(Beispiel Datei-Icons)

Auf das Icon klicken um den Quellcode anzuzeigen

TypeJpeg.php

Zuletzt modifiziert: 09.10.2024, 12:57 - Dateigröße: 5.04 KiB


001  <?php
002   
003  /**
004   * fast-image-size image type jpeg
005   * @package fast-image-size
006   * @copyright (c) Marc Alexander <admin@m-a-styles.de>
007   *
008   * For the full copyright and license information, please view the LICENSE
009   * file that was distributed with this source code.
010   */
011   
012  namespace FastImageSize\Type;
013   
014  class TypeJpeg extends TypeBase
015  {
016      /** @var int JPEG max header size. Headers can be bigger, but we'll abort
017       *            going through the header after this */
018      const JPEG_MAX_HEADER_SIZE = 124576;
019   
020      /** @var string JPEG header */
021      const JPEG_HEADER = "\xFF\xD8";
022   
023      /** @var string Start of frame marker */
024      const SOF_START_MARKER = "\xFF";
025   
026      /** @var array JPEG SOF markers */
027      protected $sofMarkers = array(
028          "\xC0",
029          "\xC1",
030          "\xC2",
031          "\xC3",
032          "\xC5",
033          "\xC6",
034          "\xC7",
035          "\xC8",
036          "\xC9",
037          "\xCA",
038          "\xCB",
039          "\xCD",
040          "\xCE",
041          "\xCF"
042      );
043   
044      /** @var array JPEG APP markers */
045      protected $appMarkers = array(
046          "\xE0",
047          "\xE1",
048          "\xE2",
049          "\xE3",
050          "\xEC",
051          "\xED",
052          "\xEE",
053      );
054   
055      /** @var string|bool $data JPEG data stream */
056      protected $data = '';
057   
058      /** @var bool Flag whether exif was found */
059      protected $foundExif = false;
060   
061      /** @var bool Flag whether xmp was found */
062      protected $foundXmp = false;
063   
064      /**
065       * {@inheritdoc}
066       */
067      public function getSize($filename)
068      {
069          // Do not force the data length
070          $this->data = $this->fastImageSize->getImage($filename, 0, self::JPEG_MAX_HEADER_SIZE, false);
071   
072          // Check if file is jpeg
073          if ($this->data === false || substr($this->data, 0, self::SHORT_SIZE) !== self::JPEG_HEADER)
074          {
075              return;
076          }
077   
078          // Look through file for SOF marker
079          $size = $this->getSizeInfo();
080   
081          $this->fastImageSize->setSize($size);
082          $this->fastImageSize->setImageType(IMAGETYPE_JPEG);
083      }
084   
085      /**
086       * Return if current data point is an SOF marker
087       *
088       * @param string $firstByte First byte to check
089       * @param string $secondByte Second byte to check
090       *
091       * @return bool True if current data point is SOF marker, false if not
092       */
093      protected function isSofMarker($firstByte, $secondByte)
094      {
095          return $firstByte === self::SOF_START_MARKER && in_array($secondByte, $this->sofMarkers);
096      }
097   
098      /**
099       * Return if current data point is an APP marker
100       *
101       * @param string $firstByte First byte to check
102       * @param string $secondByte Second byte to check
103       *
104       * @return bool True if current data point is APP marker, false if not
105       */
106      protected function isAppMarker($firstByte, $secondByte)
107      {
108          return $firstByte === self::SOF_START_MARKER && in_array($secondByte, $this->appMarkers);
109      }
110   
111      /**
112       * Return if current data point is a valid APP1 marker (EXIF or XMP)
113       *
114       * @param string $firstByte First byte to check
115       * @param string $secondByte Second byte to check
116       *
117       * @return bool True if current data point is valid APP1 marker, false if not
118       */
119      protected function isApp1Marker($firstByte, $secondByte)
120      {
121          return (!$this->foundExif || !$this->foundXmp) && $firstByte === self::SOF_START_MARKER && $secondByte === $this->appMarkers[1];
122      }
123   
124      /**
125       * Get size info from image data
126       *
127       * @return array An array with the image's size info or an empty array if
128       *        size info couldn't be found
129       */
130      protected function getSizeInfo()
131      {
132          $size = array();
133          // since we check $i + 1 we need to stop one step earlier
134          $dataLength = strlen($this->data) - 1;
135          $this->foundExif = $this->foundXmp = false;
136   
137          // Look through file for SOF marker
138          for ($i = 0; $i < $dataLength; $i++)
139          {
140              // Only look for EXIF and XMP app marker once, other types more often
141              if (!$this->checkForAppMarker($dataLength, $i))
142              {
143                  break;
144              }
145   
146              if ($this->isSofMarker($this->data[$i], $this->data[$i + 1]))
147              {
148                  // Extract size info from SOF marker
149                  list(, $unpacked) = unpack("H*", substr($this->data, $i + self::LONG_SIZE + 1, self::LONG_SIZE));
150   
151                  // Get width and height from unpacked size info
152                  $size = array(
153                      'width'        => hexdec(substr($unpacked, 4, 4)),
154                      'height'    => hexdec(substr($unpacked, 0, 4)),
155                  );
156   
157                  break;
158              }
159          }
160   
161          return $size;
162      }
163   
164      /**
165       * Check for APP marker in data
166       *
167       * @param int $dataLength Length of input data
168       * @param int $index Current data index
169       *
170       * @return bool True if searching through data should be continued, false if not
171       */
172      protected function checkForAppMarker($dataLength, &$index)
173      {
174          if ($this->isApp1Marker($this->data[$index], $this->data[$index + 1]) || $this->isAppMarker($this->data[$index], $this->data[$index + 1]))
175          {
176              // Extract length from APP marker
177              list(, $unpacked) = unpack("H*", substr($this->data, $index + self::SHORT_SIZE, 2));
178   
179              $length = hexdec(substr($unpacked, 0, 4));
180   
181              $this->setApp1Flags($this->data[$index + 1]);
182   
183              // Skip over length of APP header
184              $index += (int) $length;
185   
186              // Make sure we don't exceed the data length
187              if ($index >= $dataLength)
188              {
189                  return false;
190              }
191          }
192   
193          return true;
194      }
195   
196      /**
197       * Set APP1 flags for specified data point
198       *
199       * @param string $data Data point
200       */
201      protected function setApp1Flags($data)
202      {
203          if (!$this->foundExif)
204          {
205              $this->foundExif = $data === $this->appMarkers[1];
206          }
207          else if (!$this->foundXmp)
208          {
209              $this->foundXmp = $data === $this->appMarkers[1];
210          }
211      }
212  }
213