Example #1
0
 /**
  * Generate the necessary DataUploadEvent for a given image and tags.
  */
 private function add_image($tmpname, $filename, $tags, $source, $rating, $thumbfile)
 {
     assert(file_exists($tmpname));
     $pathinfo = pathinfo($filename);
     if (!array_key_exists('extension', $pathinfo)) {
         throw new UploadException("File has no extension");
     }
     $metadata = array();
     $metadata['filename'] = $pathinfo['basename'];
     $metadata['extension'] = $pathinfo['extension'];
     $metadata['tags'] = $tags;
     $metadata['source'] = $source;
     $event = new DataUploadEvent($tmpname, $metadata);
     send_event($event);
     if ($event->image_id == -1) {
         throw new UploadException("File type not recognised");
     } else {
         if (class_exists("RatingSetEvent") && in_array($rating, array("s", "q", "e"))) {
             $ratingevent = new RatingSetEvent(Image::by_id($event->image_id), $rating);
             send_event($ratingevent);
         }
         if (file_exists($thumbfile)) {
             copy($thumbfile, warehouse_path("thumbs", $event->hash));
         }
     }
 }
Example #2
0
 /**
  * Generate the Thumbnail image for particular file.
  *
  * @param string $hash
  * @return bool Returns true on successful thumbnail creation.
  */
 protected function create_thumb($hash)
 {
     global $config;
     $ok = false;
     switch ($config->get_string("video_thumb_engine")) {
         default:
         case 'static':
             $outname = warehouse_path("thumbs", $hash);
             copy("ext/handle_video/thumb.jpg", $outname);
             $ok = true;
             break;
         case 'ffmpeg':
             $ffmpeg = escapeshellcmd($config->get_string("thumb_ffmpeg_path"));
             $w = (int) $config->get_int("thumb_width");
             $h = (int) $config->get_int("thumb_height");
             $inname = escapeshellarg(warehouse_path("images", $hash));
             $outname = escapeshellarg(warehouse_path("thumbs", $hash));
             if ($config->get_bool("video_thumb_ignore_aspect_ratio") == true) {
                 $cmd = escapeshellcmd("{$ffmpeg} -i {$inname} -ss 00:00:00.0 -f image2 -vframes 1 {$outname}");
             } else {
                 $scale = 'scale="' . escapeshellarg("if(gt(a,{$w}/{$h}),{$w},-1)") . ':' . escapeshellarg("if(gt(a,{$w}/{$h}),-1,{$h})") . '"';
                 $cmd = "{$ffmpeg} -i {$inname} -vf {$scale} -ss 00:00:00.0 -f image2 -vframes 1 {$outname}";
             }
             exec($cmd, $output, $returnValue);
             if ((int) $returnValue == (int) 1) {
                 $ok = true;
             }
             log_debug('handle_video', "Generating thumbnail with command `{$cmd}`, returns {$returnValue}");
             break;
     }
     return $ok;
 }
Example #3
0
 public function onPageRequest(PageRequestEvent $event)
 {
     global $config, $database, $page;
     if ($event->page_matches("get_svg")) {
         $id = int_escape($event->get_arg(0));
         $image = Image::by_id($id);
         $hash = $image->hash;
         $page->set_type("image/svg+xml");
         $page->set_mode("data");
         $page->set_data(file_get_contents(warehouse_path("images", $hash)));
     }
 }
Example #4
0
 public function onImageAddition(ImageAdditionEvent $event)
 {
     global $config;
     $access = $config->get_string("amazon_s3_access");
     $secret = $config->get_string("amazon_s3_secret");
     $bucket = $config->get_string("amazon_s3_bucket");
     if (!empty($bucket)) {
         log_debug("amazon_s3", "Mirroring Image #" . $event->image->id . " to S3 #{$bucket}");
         $s3 = new S3($access, $secret);
         $s3->putBucket($bucket, S3::ACL_PUBLIC_READ);
         $s3->putObjectFile(warehouse_path("thumbs", $event->image->hash), $bucket, 'thumbs/' . $event->image->hash, S3::ACL_PUBLIC_READ, array(), array("Content-Type" => "image/jpeg", "Content-Disposition" => "inline; filename=image-" . $event->image->id . ".jpg"));
         $s3->putObjectFile(warehouse_path("images", $event->image->hash), $bucket, 'images/' . $event->image->hash, S3::ACL_PUBLIC_READ, array(), array("Content-Type" => $event->image->get_mime_type(), "Content-Disposition" => "inline; filename=image-" . $event->image->id . "." . $event->image->ext));
     }
 }
Example #5
0
 public function receive_event(Event $event)
 {
     if (is_null($this->theme)) {
         $this->theme = get_theme_object($this);
     }
     if ($event instanceof DataUploadEvent && $this->supported_ext($event->type) && $this->check_contents($event->tmpname)) {
         $hash = $event->hash;
         $ha = substr($hash, 0, 2);
         if (!move_upload_to_archive($event)) {
             return;
         }
         send_event(new ThumbnailGenerationEvent($event->hash, $event->type));
         $image = $this->create_image_from_data(warehouse_path("images", $hash), $event->metadata);
         if (is_null($image)) {
             throw new UploadException("SVG handler failed to create image object from data");
         }
         $iae = new ImageAdditionEvent($event->user, $image);
         send_event($iae);
         $event->image_id = $iae->image->id;
     }
     if ($event instanceof ThumbnailGenerationEvent && $this->supported_ext($event->type)) {
         $hash = $event->hash;
         $ha = substr($hash, 0, 2);
         global $config;
         //			if($config->get_string("thumb_engine") == "convert") {
         //				$w = $config->get_int("thumb_width");
         //				$h = $config->get_int("thumb_height");
         //				$q = $config->get_int("thumb_quality");
         //				$mem = $config->get_int("thumb_max_memory") / 1024 / 1024; // IM takes memory in MB
         //
         //				exec("convert images/{$ha}/{$hash}[0] -geometry {$w}x{$h} -quality {$q} jpg:thumbs/{$ha}/{$hash}");
         //			}
         //			else {
         copy("ext/handle_svg/thumb.jpg", warehouse_path("thumbs", $hash));
         //			}
     }
     if ($event instanceof DisplayingImageEvent && $this->supported_ext($event->image->ext)) {
         global $page;
         $this->theme->display_image($page, $event->image);
     }
     if ($event instanceof PageRequestEvent && $event->page_matches("get_svg")) {
         global $config, $database, $page;
         $id = int_escape($event->get_arg(0));
         $image = Image::by_id($id);
         $hash = $image->hash;
         $page->set_type("image/svg+xml");
         $page->set_mode("data");
         $page->set_data(file_get_contents(warehouse_path("images", $hash)));
     }
 }
Example #6
0
 protected function create_thumb($hash)
 {
     $inname = warehouse_path("images", $hash);
     $outname = warehouse_path("thumbs", $hash);
     global $config;
     $ok = false;
     switch ($config->get_string("thumb_engine")) {
         default:
         case 'gd':
             $ok = $this->make_thumb_gd($inname, $outname);
             break;
         case 'convert':
             $ok = $this->make_thumb_convert($inname, $outname);
             break;
     }
     return $ok;
 }
Example #7
0
 /**
  * @param string $hash
  * @return bool
  */
 protected function create_thumb($hash)
 {
     copy("ext/handle_mp3/thumb.jpg", warehouse_path("thumbs", $hash));
     return true;
 }
Example #8
0
 private function create_thumb($hash)
 {
     global $config;
     $inname = warehouse_path("images", $hash);
     $outname = warehouse_path("thumbs", $hash);
     $w = $config->get_int("thumb_width");
     $h = $config->get_int("thumb_height");
     $q = $config->get_int("thumb_quality");
     $mem = $config->get_int("thumb_max_memory") / 1024 / 1024;
     // IM takes memory in MB
     if ($config->get_bool("ico_convert")) {
         // "-limit memory $mem" broken?
         exec("convert {$inname}[0] -geometry {$w}x{$h} -quality {$q} jpg:{$outname}");
     } else {
         copy($inname, $outname);
     }
     return true;
 }
Example #9
0
 public function receive_event(Event $event)
 {
     if (is_null($this->theme)) {
         $this->theme = get_theme_object($this);
     }
     if ($event instanceof DataUploadEvent && $this->supported_ext($event->type) && $this->check_contents($event->tmpname)) {
         if (!move_upload_to_archive($event)) {
             return;
         }
         send_event(new ThumbnailGenerationEvent($event->hash, $event->type));
         /* Check if we are replacing an image */
         if (array_key_exists('replace', $event->metadata) && isset($event->metadata['replace'])) {
             /* hax: This seems like such a dirty way to do this.. */
             /* Validate things */
             $image_id = int_escape($event->metadata['replace']);
             /* Check to make sure the image exists. */
             $existing = Image::by_id($image_id);
             if (is_null($existing)) {
                 throw new UploadException("Image to replace does not exist!");
             }
             if ($existing->hash === $event->metadata['hash']) {
                 throw new UploadException("The uploaded image is the same as the one to replace.");
             }
             // even more hax..
             $event->metadata['tags'] = $existing->get_tag_list();
             $image = $this->create_image_from_data(warehouse_path("images", $event->metadata['hash']), $event->metadata);
             if (is_null($image)) {
                 throw new UploadException("Data handler failed to create image object from data");
             }
             $ire = new ImageReplaceEvent($image_id, $image);
             send_event($ire);
             $event->image_id = $image_id;
         } else {
             $image = $this->create_image_from_data(warehouse_path("images", $event->hash), $event->metadata);
             if (is_null($image)) {
                 throw new UploadException("Data handler failed to create image object from data");
             }
             $iae = new ImageAdditionEvent($event->user, $image);
             send_event($iae);
             $event->image_id = $iae->image->id;
             // Rating Stuff.
             if (!empty($event->metadata['rating'])) {
                 global $user;
                 $rating = $event->metadata['rating'];
                 send_event(new RatingSetEvent($image, $user, $rating));
             }
             // Locked Stuff.
             if (!empty($event->metadata['locked'])) {
                 $locked = $event->metadata['locked'];
                 send_event(new LockSetEvent($image, !empty($locked)));
             }
         }
     }
     if ($event instanceof ThumbnailGenerationEvent && $this->supported_ext($event->type)) {
         $this->create_thumb($event->hash);
     }
     if ($event instanceof DisplayingImageEvent && $this->supported_ext($event->image->ext)) {
         global $page;
         $this->theme->display_image($page, $event->image);
     }
     if ($event instanceof SetupBuildingEvent) {
         $sb = $this->setup();
         if ($sb) {
             $event->panel->add_block($sb);
         }
     }
 }
Example #10
0
 protected function create_thumb($hash)
 {
     copy("ext/handle_flash/thumb.jpg", warehouse_path("thumbs", $hash));
 }
 /**
  * Figure out where the thumbnail is on disk.
  *
  * @return string
  */
 public function get_thumb_filename()
 {
     return warehouse_path("thumbs", $this->hash);
 }
Example #12
0
 private function download_all_images()
 {
     global $database, $page;
     $images = $database->get_all("SELECT hash, ext FROM images");
     $filename = data_path('imgdump-' . date('Ymd') . '.zip');
     $zip = new ZipArchive();
     if ($zip->open($filename, ZIPARCHIVE::CREATE | ZIPARCHIVE::OVERWRITE) === TRUE) {
         foreach ($images as $img) {
             $img_loc = warehouse_path("images", $img["hash"], FALSE);
             $zip->addFile($img_loc, $img["hash"] . "." . $img["ext"]);
         }
         $zip->close();
     }
     $page->set_mode("redirect");
     $page->set_redirect(make_link($filename));
     //TODO: Delete file after downloaded?
     return false;
     // we do want a redirect, but a manual one
 }
Example #13
0
 private function resize_image($image_id, $width, $height)
 {
     global $config;
     global $user;
     global $page;
     global $database;
     if ($height <= 0 && $width <= 0) {
         throw new ImageResizeException("Invalid options for height and width. ({$width} x {$height})");
     }
     $image_obj = Image::by_id($image_id);
     $hash = $image_obj->hash;
     if (is_null($hash)) {
         throw new ImageResizeException("Image does not have a hash associated with it.");
     }
     $image_filename = warehouse_path("images", $hash);
     $info = getimagesize($image_filename);
     /* Get the image file type */
     $pathinfo = pathinfo($image_obj->filename);
     $filetype = strtolower($pathinfo['extension']);
     if ($image_obj->width != $info[0] || $image_obj->height != $info[1]) {
         throw new ImageResizeException("The image size does not match what is in the database! - Aborting Resize.");
     }
     /* Check memory usage limits */
     $memory_use = filesize($image_filename) * 2 + $width * $height * 4 + 4 * 1024 * 1024;
     $memory_limit = get_memory_limit();
     if ($memory_use > $memory_limit) {
         throw new ImageResizeException("The image is too large to resize given the memory limits. ({$memory_use} > {$memory_limit})");
     }
     /* Calculate the new size of the image */
     if ($height > 0 && $width > 0) {
         $new_height = $height;
         $new_width = $width;
     } else {
         // Scale the new image
         if ($width == 0) {
             $factor = $height / $image_obj->height;
         } elseif ($height == 0) {
             $factor = $width / $image_obj->width;
         } else {
             $factor = min($width / $image_obj->width, $height / $image_obj->height);
         }
         $new_width = round($image_obj->width * $factor);
         $new_height = round($image_obj->height * $factor);
     }
     /* Attempt to load the image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             $image = imagecreatefromgif($image_filename);
             break;
         case IMAGETYPE_JPEG:
             $image = imagecreatefromjpeg($image_filename);
             break;
         case IMAGETYPE_PNG:
             $image = imagecreatefrompng($image_filename);
             break;
         default:
             throw new ImageResizeException("Unsupported image type.");
     }
     /* Resize and resample the image */
     $image_resized = imagecreatetruecolor($new_width, $new_height);
     if ($info[2] == IMAGETYPE_GIF || $info[2] == IMAGETYPE_PNG) {
         $transparency = imagecolortransparent($image);
         if ($transparency >= 0) {
             $transparent_color = imagecolorsforindex($image, $trnprt_indx);
             $transparency = imagecolorallocate($image_resized, $trnprt_color['red'], $trnprt_color['green'], $trnprt_color['blue']);
             imagefill($image_resized, 0, 0, $transparency);
             imagecolortransparent($image_resized, $transparency);
         } elseif ($info[2] == IMAGETYPE_PNG) {
             imagealphablending($image_resized, false);
             $color = imagecolorallocatealpha($image_resized, 0, 0, 0, 127);
             imagefill($image_resized, 0, 0, $color);
             imagesavealpha($image_resized, true);
         }
     }
     imagecopyresampled($image_resized, $image, 0, 0, 0, 0, $new_width, $new_height, $image_obj->width, $image_obj->height);
     /* Temp storage while we resize */
     $tmp_filename = tempnam("/tmp", 'shimmie_resize');
     if (empty($tmp_filename)) {
         throw new ImageResizeException("Unable to save temporary image file.");
     }
     /* Output to the same format as the original image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             imagegif($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_JPEG:
             imagejpeg($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_PNG:
             imagepng($image_resized, $tmp_filename);
             break;
         default:
             throw new ImageResizeException("Unsupported image type.");
     }
     /* Move the new image into the main storage location */
     $new_hash = md5_file($tmp_filename);
     $new_size = filesize($tmp_filename);
     $target = warehouse_path("images", $new_hash);
     if (!file_exists(dirname($target))) {
         mkdir(dirname($target), 0755, true);
     }
     if (!@copy($tmp_filename, $target)) {
         throw new ImageResizeException("Failed to copy new image file from temporary location ({$tmp_filename}) to archive ({$target})");
     }
     $new_filename = 'resized-' . $image_obj->filename;
     /* Remove temporary file */
     @unlink($tmp_filename);
     /* Delete original image and thumbnail */
     log_debug("image", "Removing image with hash " . $hash);
     $image_obj->remove_image_only();
     /* Generate new thumbnail */
     send_event(new ThumbnailGenerationEvent($new_hash, $filetype));
     /* Update the database */
     $database->Execute("UPDATE images SET \n\t\t\t\t\tfilename = :filename, filesize = :filesize,\thash = :hash, width = :width, height = :height\n\t\t\t\tWHERE \n\t\t\t\t\tid = :id\n\t\t\t\t", array("filename" => $new_filename, "filesize" => $new_size, "hash" => $new_hash, "width" => $new_width, "height" => $new_height, "id" => $image_id));
     log_info("resize", "Resized Image #{$image_id} - New hash: {$new_hash}");
 }
Example #14
0
 protected function create_thumb($hash)
 {
     // FIXME: scale image, as not all boards use 192x192
     copy("ext/handle_flash/thumb.jpg", warehouse_path("thumbs", $hash));
 }
Example #15
0
 /**
  * This function could be made much smaller by using the ImageReplaceEvent
  * ie: Pretend that we are replacing the image with a resized copy.
  *
  * @param Image $image_obj
  * @param int $width
  * @param int $height
  * @throws ImageResizeException
  */
 private function resize_image(Image $image_obj, $width, $height)
 {
     global $config, $user, $page, $database;
     if ($height <= 0 && $width <= 0) {
         throw new ImageResizeException("Invalid options for height and width. ({$width} x {$height})");
     }
     $hash = $image_obj->hash;
     $image_filename = warehouse_path("images", $hash);
     $info = getimagesize($image_filename);
     /* Get the image file type */
     $pathinfo = pathinfo($image_obj->filename);
     $filetype = strtolower($pathinfo['extension']);
     if ($image_obj->width != $info[0] || $image_obj->height != $info[1]) {
         throw new ImageResizeException("The current image size does not match what is set in the database! - Aborting Resize.");
     }
     /*
     	Check Memory usage limits
     
     	Old check:   $memory_use = (filesize($image_filename)*2) + ($width*$height*4) + (4*1024*1024);
     	New check:    memory_use = width * height * (bits per channel) * channels * 2.5
     	
     	It didn't make sense to compute the memory usage based on the NEW size for the image. ($width*$height*4)
     	We need to consider the size that we are GOING TO instead.
     	
     	The factor of 2.5 is simply a rough guideline.
     	http://stackoverflow.com/questions/527532/reasonable-php-memory-limit-for-image-resize
     */
     if (isset($info['bits']) && isset($info['channels'])) {
         $memory_use = $info[0] * $info[1] * ($info['bits'] / 8) * $info['channels'] * 2.5 / 1024;
     } else {
         //
         // If we don't have bits and channel info from the image then assume default values
         // of 8 bits per color and 4 channels (R,G,B,A) -- ie: regular 24-bit color
         //
         $memory_use = $info[0] * $info[1] * 1 * 4 * 2.5 / 1024;
     }
     $memory_limit = get_memory_limit();
     if ($memory_use > $memory_limit) {
         throw new ImageResizeException("The image is too large to resize given the memory limits. ({$memory_use} > {$memory_limit})");
     }
     /* Calculate the new size of the image */
     if ($height > 0 && $width > 0) {
         $new_height = $height;
         $new_width = $width;
     } else {
         // Scale the new image
         if ($width == 0) {
             $factor = $height / $image_obj->height;
         } elseif ($height == 0) {
             $factor = $width / $image_obj->width;
         } else {
             $factor = min($width / $image_obj->width, $height / $image_obj->height);
         }
         $new_width = round($image_obj->width * $factor);
         $new_height = round($image_obj->height * $factor);
     }
     /* Attempt to load the image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             $image = imagecreatefromgif($image_filename);
             break;
         case IMAGETYPE_JPEG:
             $image = imagecreatefromjpeg($image_filename);
             break;
         case IMAGETYPE_PNG:
             $image = imagecreatefrompng($image_filename);
             break;
         default:
             throw new ImageResizeException("Unsupported image type (Only GIF, JPEG, and PNG are supported).");
     }
     // Handle transparent images
     $image_resized = imagecreatetruecolor($new_width, $new_height);
     if ($info[2] == IMAGETYPE_GIF) {
         $transparency = imagecolortransparent($image);
         // If we have a specific transparent color
         if ($transparency >= 0) {
             // Get the original image's transparent color's RGB values
             $transparent_color = imagecolorsforindex($image, $transparency);
             // Allocate the same color in the new image resource
             $transparency = imagecolorallocate($image_resized, $transparent_color['red'], $transparent_color['green'], $transparent_color['blue']);
             // Completely fill the background of the new image with allocated color.
             imagefill($image_resized, 0, 0, $transparency);
             // Set the background color for new image to transparent
             imagecolortransparent($image_resized, $transparency);
         }
     } elseif ($info[2] == IMAGETYPE_PNG) {
         //
         // More info here:  http://stackoverflow.com/questions/279236/how-do-i-resize-pngs-with-transparency-in-php
         //
         imagealphablending($image_resized, false);
         imagesavealpha($image_resized, true);
         $transparent_color = imagecolorallocatealpha($image_resized, 255, 255, 255, 127);
         imagefilledrectangle($image_resized, 0, 0, $new_width, $new_height, $transparent_color);
     }
     // Actually resize the image.
     imagecopyresampled($image_resized, $image, 0, 0, 0, 0, $new_width, $new_height, $image_obj->width, $image_obj->height);
     /* Temp storage while we resize */
     $tmp_filename = tempnam("/tmp", 'shimmie_resize');
     if (empty($tmp_filename)) {
         throw new ImageResizeException("Unable to save temporary image file.");
     }
     /* Output to the same format as the original image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             imagegif($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_JPEG:
             imagejpeg($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_PNG:
             imagepng($image_resized, $tmp_filename);
             break;
         default:
             throw new ImageResizeException("Failed to save the new image - Unsupported image type.");
     }
     /* Move the new image into the main storage location */
     $new_hash = md5_file($tmp_filename);
     $new_size = filesize($tmp_filename);
     $target = warehouse_path("images", $new_hash);
     if (!@copy($tmp_filename, $target)) {
         throw new ImageResizeException("Failed to copy new image file from temporary location ({$tmp_filename}) to archive ({$target})");
     }
     $new_filename = 'resized-' . $image_obj->filename;
     /* Remove temporary file */
     @unlink($tmp_filename);
     /* Delete original image and thumbnail */
     log_debug("image", "Removing image with hash " . $hash);
     $image_obj->remove_image_only();
     /* Generate new thumbnail */
     send_event(new ThumbnailGenerationEvent($new_hash, $filetype));
     /* Update the database */
     $database->Execute("UPDATE images SET \n\t\t\t\t\tfilename = :filename, filesize = :filesize,\thash = :hash, width = :width, height = :height\n\t\t\t\tWHERE \n\t\t\t\t\tid = :id\n\t\t\t\t", array("filename" => $new_filename, "filesize" => $new_size, "hash" => $new_hash, "width" => $new_width, "height" => $new_height, "id" => $image_obj->id));
     log_info("resize", "Resized Image #{$image_obj->id} - New hash: {$new_hash}");
 }
Example #16
0
 /**
  * This function could be made much smaller by using the ImageReplaceEvent
  * ie: Pretend that we are replacing the image with a resized copy.
  *
  * @param Image $image_obj
  * @param int $width
  * @param int $height
  * @throws ImageResizeException
  */
 private function resize_image(Image $image_obj, $width, $height)
 {
     global $database;
     if ($height <= 0 && $width <= 0) {
         throw new ImageResizeException("Invalid options for height and width. ({$width} x {$height})");
     }
     $hash = $image_obj->hash;
     $image_filename = warehouse_path("images", $hash);
     $info = getimagesize($image_filename);
     /* Get the image file type */
     $pathinfo = pathinfo($image_obj->filename);
     $filetype = strtolower($pathinfo['extension']);
     if ($image_obj->width != $info[0] || $image_obj->height != $info[1]) {
         throw new ImageResizeException("The current image size does not match what is set in the database! - Aborting Resize.");
     }
     $memory_use = $this->calc_memory_use($info);
     $memory_limit = get_memory_limit();
     if ($memory_use > $memory_limit) {
         throw new ImageResizeException("The image is too large to resize given the memory limits. ({$memory_use} > {$memory_limit})");
     }
     list($new_height, $new_width) = $this->calc_new_size($image_obj, $width, $height);
     /* Attempt to load the image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             $image = imagecreatefromgif($image_filename);
             break;
         case IMAGETYPE_JPEG:
             $image = imagecreatefromjpeg($image_filename);
             break;
         case IMAGETYPE_PNG:
             $image = imagecreatefrompng($image_filename);
             break;
         default:
             throw new ImageResizeException("Unsupported image type (Only GIF, JPEG, and PNG are supported).");
     }
     // Handle transparent images
     $image_resized = imagecreatetruecolor($new_width, $new_height);
     if ($info[2] == IMAGETYPE_GIF) {
         $transparency = imagecolortransparent($image);
         // If we have a specific transparent color
         if ($transparency >= 0) {
             // Get the original image's transparent color's RGB values
             $transparent_color = imagecolorsforindex($image, $transparency);
             // Allocate the same color in the new image resource
             $transparency = imagecolorallocate($image_resized, $transparent_color['red'], $transparent_color['green'], $transparent_color['blue']);
             // Completely fill the background of the new image with allocated color.
             imagefill($image_resized, 0, 0, $transparency);
             // Set the background color for new image to transparent
             imagecolortransparent($image_resized, $transparency);
         }
     } elseif ($info[2] == IMAGETYPE_PNG) {
         //
         // More info here:  http://stackoverflow.com/questions/279236/how-do-i-resize-pngs-with-transparency-in-php
         //
         imagealphablending($image_resized, false);
         imagesavealpha($image_resized, true);
         $transparent_color = imagecolorallocatealpha($image_resized, 255, 255, 255, 127);
         imagefilledrectangle($image_resized, 0, 0, $new_width, $new_height, $transparent_color);
     }
     // Actually resize the image.
     imagecopyresampled($image_resized, $image, 0, 0, 0, 0, $new_width, $new_height, $image_obj->width, $image_obj->height);
     /* Temp storage while we resize */
     $tmp_filename = tempnam("/tmp", 'shimmie_resize');
     if (empty($tmp_filename)) {
         throw new ImageResizeException("Unable to save temporary image file.");
     }
     /* Output to the same format as the original image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             imagegif($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_JPEG:
             imagejpeg($image_resized, $tmp_filename);
             break;
         case IMAGETYPE_PNG:
             imagepng($image_resized, $tmp_filename);
             break;
         default:
             throw new ImageResizeException("Failed to save the new image - Unsupported image type.");
     }
     /* Move the new image into the main storage location */
     $new_hash = md5_file($tmp_filename);
     $new_size = filesize($tmp_filename);
     $target = warehouse_path("images", $new_hash);
     if (!@copy($tmp_filename, $target)) {
         throw new ImageResizeException("Failed to copy new image file from temporary location ({$tmp_filename}) to archive ({$target})");
     }
     $new_filename = 'resized-' . $image_obj->filename;
     /* Remove temporary file */
     @unlink($tmp_filename);
     /* Delete original image and thumbnail */
     log_debug("image", "Removing image with hash " . $hash);
     $image_obj->remove_image_only();
     /* Generate new thumbnail */
     send_event(new ThumbnailGenerationEvent($new_hash, $filetype));
     /* Update the database */
     $database->Execute("\n\t\t\tUPDATE images SET filename = :filename, filesize = :filesize, hash = :hash, width = :width, height = :height\n\t\t\tWHERE id = :id\n\t\t", array("filename" => $new_filename, "filesize" => $new_size, "hash" => $new_hash, "width" => $new_width, "height" => $new_height, "id" => $image_obj->id));
     log_info("resize", "Resized Image #{$image_obj->id} - New hash: {$new_hash}");
 }
Example #17
0
 /**
  * @param DataUploadEvent $event
  * @throws UploadException
  */
 public function onDataUpload(DataUploadEvent $event)
 {
     $supported_ext = $this->supported_ext($event->type);
     $check_contents = $this->check_contents($event->tmpname);
     if ($supported_ext && $check_contents) {
         if (!move_upload_to_archive($event)) {
             return;
         }
         send_event(new ThumbnailGenerationEvent($event->hash, $event->type));
         /* Check if we are replacing an image */
         if (array_key_exists('replace', $event->metadata) && isset($event->metadata['replace'])) {
             /* hax: This seems like such a dirty way to do this.. */
             /* Validate things */
             $image_id = int_escape($event->metadata['replace']);
             /* Check to make sure the image exists. */
             $existing = Image::by_id($image_id);
             if (is_null($existing)) {
                 throw new UploadException("Image to replace does not exist!");
             }
             if ($existing->hash === $event->metadata['hash']) {
                 throw new UploadException("The uploaded image is the same as the one to replace.");
             }
             // even more hax..
             $event->metadata['tags'] = $existing->get_tag_list();
             $image = $this->create_image_from_data(warehouse_path("images", $event->metadata['hash']), $event->metadata);
             if (is_null($image)) {
                 throw new UploadException("Data handler failed to create image object from data");
             }
             $ire = new ImageReplaceEvent($image_id, $image);
             send_event($ire);
             $event->image_id = $image_id;
         } else {
             $image = $this->create_image_from_data(warehouse_path("images", $event->hash), $event->metadata);
             if (is_null($image)) {
                 throw new UploadException("Data handler failed to create image object from data");
             }
             $iae = new ImageAdditionEvent($image);
             send_event($iae);
             $event->image_id = $iae->image->id;
             // Rating Stuff.
             if (!empty($event->metadata['rating'])) {
                 $rating = $event->metadata['rating'];
                 send_event(new RatingSetEvent($image, $rating));
             }
             // Locked Stuff.
             if (!empty($event->metadata['locked'])) {
                 $locked = $event->metadata['locked'];
                 send_event(new LockSetEvent($image, !empty($locked)));
             }
         }
     } elseif ($supported_ext && !$check_contents) {
         throw new UploadException("Invalid or corrupted file");
     }
 }
Example #18
0
 /**
  * This function could be made much smaller by using the ImageReplaceEvent
  * ie: Pretend that we are replacing the image with a rotated copy.
  *
  * @param int $image_id
  * @param int $deg
  * @throws ImageRotateException
  */
 private function rotate_image($image_id, $deg)
 {
     global $config, $user, $page, $database;
     if ($deg <= -360 || $deg >= 360) {
         throw new ImageRotateException("Invalid options for rotation angle. ({$deg})");
     }
     $image_obj = Image::by_id($image_id);
     $hash = $image_obj->hash;
     if (is_null($hash)) {
         throw new ImageRotateException("Image does not have a hash associated with it.");
     }
     $image_filename = warehouse_path("images", $hash);
     if (file_exists($image_filename) == false) {
         throw new ImageRotateException("{$image_filename} does not exist.");
     }
     $info = getimagesize($image_filename);
     /* Get the image file type */
     $pathinfo = pathinfo($image_obj->filename);
     $filetype = strtolower($pathinfo['extension']);
     /*
     	Check Memory usage limits
     
     	Old check:   $memory_use = (filesize($image_filename)*2) + ($width*$height*4) + (4*1024*1024);
     	New check:    memory_use = width * height * (bits per channel) * channels * 2.5
     	
     	It didn't make sense to compute the memory usage based on the NEW size for the image. ($width*$height*4)
     	We need to consider the size that we are GOING TO instead.
     	
     	The factor of 2.5 is simply a rough guideline.
     	http://stackoverflow.com/questions/527532/reasonable-php-memory-limit-for-image-resize
     */
     $memory_use = $info[0] * $info[1] * ($info['bits'] / 8) * $info['channels'] * 2.5 / 1024;
     $memory_limit = get_memory_limit();
     if ($memory_use > $memory_limit) {
         throw new ImageRotateException("The image is too large to rotate given the memory limits. ({$memory_use} > {$memory_limit})");
     }
     /* Attempt to load the image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             $image = imagecreatefromgif($image_filename);
             break;
         case IMAGETYPE_JPEG:
             $image = imagecreatefromjpeg($image_filename);
             break;
         case IMAGETYPE_PNG:
             $image = imagecreatefrompng($image_filename);
             break;
         default:
             throw new ImageRotateException("Unsupported image type or ");
     }
     /* Rotate and resample the image */
     /*
     $image_rotated = imagecreatetruecolor( $new_width, $new_height );
     
     if ( ($info[2] == IMAGETYPE_GIF) || ($info[2] == IMAGETYPE_PNG) ) {
       $transparency = imagecolortransparent($image);
     
       if ($transparency >= 0) {
     	$transparent_color  = imagecolorsforindex($image, $trnprt_indx);
     	$transparency       = imagecolorallocate($image_rotated, $trnprt_color['red'], $trnprt_color['green'], $trnprt_color['blue']);
     	imagefill($image_rotated, 0, 0, $transparency);
     	imagecolortransparent($image_rotated, $transparency);
       }
       elseif ($info[2] == IMAGETYPE_PNG) {
     	imagealphablending($image_rotated, false);
     	$color = imagecolorallocatealpha($image_rotated, 0, 0, 0, 127);
     	imagefill($image_rotated, 0, 0, $color);
     	imagesavealpha($image_rotated, true);
       }
     }
     */
     $image_rotated = imagerotate($image, $deg, 0);
     /* Temp storage while we rotate */
     $tmp_filename = tempnam(ini_get('upload_tmp_dir'), 'shimmie_rotate');
     if (empty($tmp_filename)) {
         throw new ImageRotateException("Unable to save temporary image file.");
     }
     /* Output to the same format as the original image */
     switch ($info[2]) {
         case IMAGETYPE_GIF:
             imagegif($image_rotated, $tmp_filename);
             break;
         case IMAGETYPE_JPEG:
             imagejpeg($image_rotated, $tmp_filename);
             break;
         case IMAGETYPE_PNG:
             imagepng($image_rotated, $tmp_filename);
             break;
         default:
             throw new ImageRotateException("Unsupported image type.");
     }
     /* Move the new image into the main storage location */
     $new_hash = md5_file($tmp_filename);
     $new_size = filesize($tmp_filename);
     $target = warehouse_path("images", $new_hash);
     if (!@copy($tmp_filename, $target)) {
         throw new ImageRotateException("Failed to copy new image file from temporary location ({$tmp_filename}) to archive ({$target})");
     }
     $new_filename = 'rotated-' . $image_obj->filename;
     list($new_width, $new_height) = getimagesize($target);
     /* Remove temporary file */
     @unlink($tmp_filename);
     /* Delete original image and thumbnail */
     log_debug("image", "Removing image with hash " . $hash);
     $image_obj->remove_image_only();
     /* Generate new thumbnail */
     send_event(new ThumbnailGenerationEvent($new_hash, $filetype));
     /* Update the database */
     $database->Execute("UPDATE images SET \n\t\t\t\t\tfilename = :filename, filesize = :filesize,\thash = :hash, width = :width, height = :height\n\t\t\t\tWHERE \n\t\t\t\t\tid = :id\n\t\t\t\t", array("filename" => $new_filename, "filesize" => $new_size, "hash" => $new_hash, "width" => $new_width, "height" => $new_height, "id" => $image_id));
     log_info("rotate", "Rotated Image #{$image_id} - New hash: {$new_hash}");
 }
Example #19
0
 public function receive_event(Event $event)
 {
     if (is_null($this->theme)) {
         $this->theme = get_theme_object($this);
     }
     if ($event instanceof DataUploadEvent && $this->supported_ext($event->type) && $this->check_contents($event->tmpname)) {
         if (!move_upload_to_archive($event)) {
             return;
         }
         send_event(new ThumbnailGenerationEvent($event->hash, $event->type));
         $image = $this->create_image_from_data(warehouse_path("images", $event->hash), $event->metadata);
         if (is_null($image)) {
             throw new UploadException("Data handler failed to create image object from data");
         }
         $iae = new ImageAdditionEvent($event->user, $image);
         send_event($iae);
         $event->image_id = $iae->image->id;
     }
     if ($event instanceof ThumbnailGenerationEvent && $this->supported_ext($event->type)) {
         $this->create_thumb($event->hash);
     }
     if ($event instanceof DisplayingImageEvent && $this->supported_ext($event->image->ext)) {
         global $page;
         $this->theme->display_image($page, $event->image);
     }
 }
Example #20
0
<?php

// custom routing for stand-alone mode
if (PHP_SAPI !== 'cli-server') {
    die('cli only');
}
// warehouse files
$matches = array();
if (preg_match('/\\/_(images|thumbs)\\/([0-9a-f]{32}).*$/', $_SERVER["REQUEST_URI"], $matches)) {
    header('Content-Type: image/jpeg');
    print file_get_contents(warehouse_path($matches[1], $matches[2]));
    return true;
}
unset($matches);
// use the default handler (serve static files, interpret php files)
if (preg_match('/\\.(?:png|jpg|jpeg|gif|css|js|php)(\\?.*)?$/', $_SERVER["REQUEST_URI"])) {
    return false;
}
// all other requests (use shimmie routing based on URL)
$_SERVER["PHP_SELF"] = '/';
$_GET['q'] = $_SERVER["REQUEST_URI"];
require_once "index.php";