/** * Handle the creation of a new photo. * @todo Get tags from the XMP and/or IPTC data in the image * * @param Item_Model $photo */ static function item_created($photo) { $tags = array(); if ($photo->is_photo()) { $path = $photo->file_path(); $size = getimagesize($photo->file_path(), $info); if (is_array($info) && !empty($info["APP13"])) { $iptc = iptcparse($info["APP13"]); if (!empty($iptc["2#025"])) { foreach ($iptc["2#025"] as $tag) { $tag = str_replace("", "", $tag); foreach (explode(",", $tag) as $word) { $word = trim($word); if (function_exists("mb_detect_encoding") && mb_detect_encoding($word) != "UTF-8") { $word = utf8_encode($word); } $tags[$word] = 1; } } } } } // @todo figure out how to read the keywords from xmp foreach (array_keys($tags) as $tag) { try { tag::add($photo, $tag); } catch (Exception $e) { Kohana_Log::add("error", "Error adding tag: {$tag}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); } } return; }
/** * Handle the creation of a new photo. * @todo Get tags from the XMP and/or IPTC data in the image * * @param Item_Model $photo */ static function item_created($photo) { $tags = array(); if ($photo->is_photo()) { $path = $photo->file_path(); $size = getimagesize($photo->file_path(), $info); if (is_array($info) && !empty($info["APP13"])) { $iptc = iptcparse($info["APP13"]); if (!empty($iptc["2#025"])) { foreach ($iptc["2#025"] as $tag) { $tag = str_replace("", "", $tag); if (function_exists("mb_detect_encoding") && mb_detect_encoding($tag) != "UTF-8") { $tag = utf8_encode($tag); } $tags[$tag] = 1; } } } } // @todo figure out how to read the keywords from xmp foreach (array_keys($tags) as $tag) { tag::add($photo, $tag); } return; }
/** * Handle the creation of a new photo. * @todo Get tags from the XMP and/or IPTC data in the image * * @param Item_Model $photo */ static function item_created($photo) { if ($photo->is_photo()) { $path = $photo->file_path(); $tags = array(); $size = getimagesize($photo->file_path(), $info); if (is_array($info) && !empty($info["APP13"])) { $iptc = iptcparse($info["APP13"]); if (!empty($iptc["2#025"])) { foreach ($iptc["2#025"] as $tag) { $tags[$tag] = 1; } } } } // @todo figure out how to read the keywords from xmp foreach (array_keys($tags) as $tag) { tag::add($photo, $tag); } return; }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item */ static function generate($item) { if ($item->type == "album") { $cover = $item->album_cover(); if (!$cover) { return; } $input_file = $cover->file_path(); } else { $input_file = $item->file_path(); } $ops = array(); if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && $item->type != "album") { $ops["resize"] = $item->resize_path(); } if (!$ops) { return; } foreach (array("thumb" => $item->thumb_path(), "resize" => $item->resize_path()) as $target => $output_file) { $working_file = $input_file; foreach (ORM::factory("graphics_rule")->where("target", $target)->orderby("priority", "asc")->find_all() as $rule) { $args = array($working_file, $output_file, unserialize($rule->args)); call_user_func_array(array("graphics", $rule->operation), $args); $working_file = $output_file; } } if (!empty($ops["thumb"])) { $dims = getimagesize($item->thumb_path()); $item->thumb_width = $dims[0]; $item->thumb_height = $dims[1]; $item->thumb_dirty = 0; } if (!empty($ops["resize"])) { $dims = getimagesize($item->resize_path()); $item->resize_width = $dims[0]; $item->resize_height = $dims[1]; $item->resize_dirty = 0; } $item->save(); }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item * @return true on successful generation */ static function generate($item) { if ($item->is_album()) { if (!($cover = $item->album_cover())) { return false; } $input_file = $cover->file_path(); $input_item = $cover; } else { $input_file = $item->file_path(); $input_item = $item; } if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && !$item->is_album() && !$item->is_movie()) { $ops["resize"] = $item->resize_path(); } if (empty($ops)) { $item->thumb_dirty = 0; $item->resize_dirty = 0; $item->save(); return true; } try { foreach ($ops as $target => $output_file) { if ($input_item->is_movie()) { // Convert the movie to a JPG first $output_file = preg_replace("/...\$/", "jpg", $output_file); try { movie::extract_frame($input_file, $output_file); } catch (Exception $e) { // Assuming this is MISSING_FFMPEG for now copy(MODPATH . "gallery/images/missing_movie.png", $output_file); } $working_file = $output_file; } else { $working_file = $input_file; } foreach (ORM::factory("graphics_rule")->where("target", $target)->where("active", true)->orderby("priority", "asc")->find_all() as $rule) { $args = array($working_file, $output_file, unserialize($rule->args)); call_user_func_array(array("graphics", $rule->operation), $args); $working_file = $output_file; } } if (!empty($ops["thumb"])) { $dims = getimagesize($item->thumb_path()); $item->thumb_width = $dims[0]; $item->thumb_height = $dims[1]; $item->thumb_dirty = 0; } if (!empty($ops["resize"])) { $dims = getimagesize($item->resize_path()); $item->resize_width = $dims[0]; $item->resize_height = $dims[1]; $item->resize_dirty = 0; } $item->save(); } catch (Exception $e) { // Something went wrong rebuilding the image. Leave it dirty and move on. // @todo we should handle this better. Kohana::log("error", "Caught exception rebuilding image: {$item->title}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); return false; } return true; }
/** * Move this item to the specified target. * @chainable * @param Item_Model $target Target item (must be an album) * @return ORM_MPTT */ function move_to($target) { if (!$target->is_album()) { throw new Exception("@todo INVALID_MOVE_TYPE {$target->type}"); } if (file_exists($target_file = "{$target->file_path()}/{$this->name}")) { throw new Exception("@todo INVALID_MOVE_TARGET_EXISTS: {$target_file}"); } if ($this->id == 1) { throw new Exception("@todo INVALID_SOURCE root album"); } $original_path = $this->file_path(); $original_resize_path = $this->resize_path(); $original_thumb_path = $this->thumb_path(); $original_parent = $this->parent(); parent::move_to($target, true); model_cache::clear(); $this->relative_path_cache = null; rename($original_path, $this->file_path()); if ($this->is_album()) { @rename(dirname($original_resize_path), dirname($this->resize_path())); @rename(dirname($original_thumb_path), dirname($this->thumb_path())); Database::instance()->update("items", array("relative_path_cache" => null, "relative_url_cache" => null), array("left_ptr >" => $this->left_ptr, "right_ptr <" => $this->right_ptr)); } else { @rename($original_resize_path, $this->resize_path()); @rename($original_thumb_path, $this->thumb_path()); } module::event("item_moved", $this, $original_parent); return $this; }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item */ static function generate($item) { if ($item->is_album()) { if (!($cover = $item->album_cover())) { // This album has no cover; there's nothing to generate. Because of an old bug, it's // possible that there's an album cover item id that points to an invalid item. In that // case, just null out the album cover item id. It's not optimal to do that at this low // level, but it's not trivial to find these cases quickly in an upgrade script and if we // don't do this, the album may be permanently marked as "needs rebuilding" // // ref: http://sourceforge.net/apps/trac/gallery/ticket/1172 // http://gallery.menalto.com/node/96926 if ($item->album_cover_item_id) { $item->album_cover_item_id = null; $item->save(); } return; } $input_file = $cover->file_path(); $input_item = $cover; } else { $input_file = $item->file_path(); $input_item = $item; } if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && !$item->is_album() && !$item->is_movie()) { $ops["resize"] = $item->resize_path(); } if (empty($ops)) { $item->thumb_dirty = 0; $item->resize_dirty = 0; $item->save(); return; } try { foreach ($ops as $target => $output_file) { if ($input_item->is_movie()) { // Convert the movie filename to a JPG first, delete anything that might already be there $output_file = legal_file::change_extension($output_file, "jpg"); unlink($output_file); // Run movie_extract_frame events, which can either: // - generate an output file, bypassing the ffmpeg-based movie::extract_frame // - add to the options sent to movie::extract_frame (e.g. change frame extract time, // add de-interlacing arguments to ffmpeg... see movie helper for more info) // Note that the args are similar to those of the events in gallery_graphics $movie_options_wrapper = new stdClass(); $movie_options_wrapper->movie_options = array(); module::event("movie_extract_frame", $input_file, $output_file, $movie_options_wrapper, $input_item); // If no output_file generated by events, run movie::extract_frame with movie_options clearstatcache(); if (@filesize($output_file) == 0) { try { movie::extract_frame($input_file, $output_file, $movie_options_wrapper->movie_options); } catch (Exception $e) { // Didn't work, likely because of MISSING_FFMPEG - copy missing_movie instead copy(MODPATH . "gallery/images/missing_movie.jpg", $output_file); } } $working_file = $output_file; } else { $working_file = $input_file; } foreach (self::_get_rules($target) as $rule) { $args = array($working_file, $output_file, unserialize($rule->args), $item); call_user_func_array($rule->operation, $args); $working_file = $output_file; } } if (!empty($ops["thumb"])) { if (file_exists($item->thumb_path())) { $item->thumb_dirty = 0; } else { copy(MODPATH . "gallery/images/missing_photo.png", $item->thumb_path()); } $dims = getimagesize($item->thumb_path()); $item->thumb_width = $dims[0]; $item->thumb_height = $dims[1]; } if (!empty($ops["resize"])) { if (file_exists($item->resize_path())) { $item->resize_dirty = 0; } else { copy(MODPATH . "gallery/images/missing_photo.png", $item->resize_path()); } $dims = getimagesize($item->resize_path()); $item->resize_width = $dims[0]; $item->resize_height = $dims[1]; } $item->save(); } catch (Exception $e) { // Something went wrong rebuilding the image. Leave it dirty and move on. // @todo we should handle this better. Kohana_Log::add("error", "Caught exception rebuilding image: {$item->title}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); throw $e; } }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item */ static function generate($item) { if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && $item->is_photo()) { $ops["resize"] = $item->resize_path(); } try { foreach ($ops as $target => $output_file) { $working_file = $item->file_path(); // Delete anything that might already be there @unlink($output_file); switch ($item->type) { case "movie": // Run movie_extract_frame events, which can either: // - generate an output file, bypassing the ffmpeg-based movie::extract_frame // - add to the options sent to movie::extract_frame (e.g. change frame extract time, // add de-interlacing arguments to ffmpeg... see movie helper for more info) // Note that the args are similar to those of the events in gallery_graphics $movie_options_wrapper = new stdClass(); $movie_options_wrapper->movie_options = array(); module::event("movie_extract_frame", $working_file, $output_file, $movie_options_wrapper, $item); // If no output_file generated by events, run movie::extract_frame with movie_options clearstatcache(); if (@filesize($output_file) == 0) { try { movie::extract_frame($working_file, $output_file, $movie_options_wrapper->movie_options); // If we're here, we know ffmpeg is installed and the movie is valid. Because the // user may not always have had ffmpeg installed, the movie's width, height, and // mime type may need updating. Let's use this opportunity to make sure they're // correct. It's not optimal to do it at this low level, but it's not trivial to find // these cases quickly in an upgrade script. list($width, $height, $mime_type) = movie::get_file_metadata($working_file); // Only set them if they need updating to avoid marking them as "changed" if ($item->width != $width || $item->height != $height || $item->mime_type != $mime_type) { $item->width = $width; $item->height = $height; $item->mime_type = $mime_type; } } catch (Exception $e) { // Didn't work, likely because of MISSING_FFMPEG - use placeholder graphics::_replace_image_with_placeholder($item, $target); break; } } $working_file = $output_file; case "photo": // Run the graphics rules (for both movies and photos) foreach (self::_get_rules($target) as $rule) { $args = array($working_file, $output_file, unserialize($rule->args), $item); call_user_func_array($rule->operation, $args); $working_file = $output_file; } break; case "album": if (!($cover = $item->album_cover())) { // This album has no cover; copy its placeholder image. Because of an old bug, it's // possible that there's an album cover item id that points to an invalid item. In that // case, just null out the album cover item id. It's not optimal to do that at this low // level, but it's not trivial to find these cases quickly in an upgrade script and if we // don't do this, the album may be permanently marked as "needs rebuilding" // // ref: http://sourceforge.net/apps/trac/gallery/ticket/1172 // http://galleryproject.org/node/96926 if ($item->album_cover_item_id) { $item->album_cover_item_id = null; $item->save(); } graphics::_replace_image_with_placeholder($item, $target); break; } if ($cover->thumb_dirty) { graphics::generate($cover); } if (!$cover->thumb_dirty) { // Make the album cover from the cover item's thumb. Run gallery_graphics::resize with // null options and it will figure out if this is a direct copy or conversion to jpg. $working_file = $cover->thumb_path(); gallery_graphics::resize($working_file, $output_file, null, $item); } break; } } if (!empty($ops["thumb"])) { if (file_exists($item->thumb_path())) { $item->thumb_dirty = 0; } else { Kohana_Log::add("error", "Failed to rebuild thumb image: {$item->title}"); graphics::_replace_image_with_placeholder($item, "thumb"); } } if (!empty($ops["resize"])) { if (file_exists($item->resize_path())) { $item->resize_dirty = 0; } else { Kohana_Log::add("error", "Failed to rebuild resize image: {$item->title}"); graphics::_replace_image_with_placeholder($item, "resize"); } } graphics::_update_item_dimensions($item); $item->save(); } catch (Exception $e) { // Something went wrong rebuilding the image. Replace with the placeholder images, // leave it dirty and move on. Kohana_Log::add("error", "Caught exception rebuilding images: {$item->title}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); if ($item->is_photo()) { graphics::_replace_image_with_placeholder($item, "resize"); } graphics::_replace_image_with_placeholder($item, "thumb"); try { graphics::_update_item_dimensions($item); } catch (Exception $e) { // Looks like get_file_metadata couldn't identify our placeholders. We should never get // here, but in the odd case we do, we need to do something. Let's put in hardcoded values. if ($item->is_photo()) { list($item->resize_width, $item->resize_height) = array(200, 200); } list($item->thumb_width, $item->thumb_height) = array(200, 200); } $item->save(); throw $e; } }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item */ static function generate($item) { if ($item->is_album()) { if (!($cover = $item->album_cover())) { // This album has no cover; there's nothing to generate. return; } $input_file = $cover->file_path(); $input_item = $cover; } else { $input_file = $item->file_path(); $input_item = $item; } if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && !$item->is_album() && !$item->is_movie()) { $ops["resize"] = $item->resize_path(); } if (empty($ops)) { $item->thumb_dirty = 0; $item->resize_dirty = 0; $item->save(); return; } try { foreach ($ops as $target => $output_file) { if ($input_item->is_movie()) { // Convert the movie to a JPG first $output_file = preg_replace("/...\$/", "jpg", $output_file); try { movie::extract_frame($input_file, $output_file); } catch (Exception $e) { // Assuming this is MISSING_FFMPEG for now copy(MODPATH . "gallery/images/missing_movie.png", $output_file); } $working_file = $output_file; } else { $working_file = $input_file; } foreach (self::_get_rules($target) as $rule) { $args = array($working_file, $output_file, unserialize($rule->args)); call_user_func_array($rule->operation, $args); $working_file = $output_file; } } if (!empty($ops["thumb"])) { $dims = getimagesize($item->thumb_path()); $item->thumb_width = $dims[0]; $item->thumb_height = $dims[1]; $item->thumb_dirty = 0; } if (!empty($ops["resize"])) { $dims = getimagesize($item->resize_path()); $item->resize_width = $dims[0]; $item->resize_height = $dims[1]; $item->resize_dirty = 0; } $item->save(); } catch (Exception $e) { // Something went wrong rebuilding the image. Leave it dirty and move on. // @todo we should handle this better. Kohana_Log::add("error", "Caught exception rebuilding image: {$item->title}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); throw $e; } }
/** * Rebuild the thumb and resize for the given item. * @param Item_Model $item */ static function generate($item) { if ($item->is_album()) { if (!($cover = $item->album_cover())) { // This album has no cover; there's nothing to generate. Because of an old bug, it's // possible that there's an album cover item id that points to an invalid item. In that // case, just null out the album cover item id. It's not optimal to do that at this low // level, but it's not trivial to find these cases quickly in an upgrade script and if we // don't do this, the album may be permanently marked as "needs rebuilding" // // ref: http://sourceforge.net/apps/trac/gallery/ticket/1172 // http://gallery.menalto.com/node/96926 if ($item->album_cover_item_id) { $item->album_cover_item_id = null; $item->save(); } return; } $input_file = $cover->file_path(); $input_item = $cover; } else { $input_file = $item->file_path(); $input_item = $item; } if ($item->thumb_dirty) { $ops["thumb"] = $item->thumb_path(); } if ($item->resize_dirty && !$item->is_album() && !$item->is_movie()) { $ops["resize"] = $item->resize_path(); } if (empty($ops)) { $item->thumb_dirty = 0; $item->resize_dirty = 0; $item->save(); return; } try { foreach ($ops as $target => $output_file) { if ($input_item->is_movie()) { // Convert the movie to a JPG first $output_file = legal_file::change_extension($output_file, "jpg"); try { movie::extract_frame($input_file, $output_file); } catch (Exception $e) { // Assuming this is MISSING_FFMPEG for now copy(MODPATH . "gallery/images/missing_movie.jpg", $output_file); } $working_file = $output_file; } else { $working_file = $input_file; } foreach (self::_get_rules($target) as $rule) { $args = array($working_file, $output_file, unserialize($rule->args), $item); call_user_func_array($rule->operation, $args); $working_file = $output_file; } } if (!empty($ops["thumb"])) { if (file_exists($item->thumb_path())) { $item->thumb_dirty = 0; } else { copy(MODPATH . "gallery/images/missing_photo.png", $item->thumb_path()); } $dims = getimagesize($item->thumb_path()); $item->thumb_width = $dims[0]; $item->thumb_height = $dims[1]; } if (!empty($ops["resize"])) { if (file_exists($item->resize_path())) { $item->resize_dirty = 0; } else { copy(MODPATH . "gallery/images/missing_photo.png", $item->resize_path()); } $dims = getimagesize($item->resize_path()); $item->resize_width = $dims[0]; $item->resize_height = $dims[1]; } $item->save(); } catch (Exception $e) { // Something went wrong rebuilding the image. Leave it dirty and move on. // @todo we should handle this better. Kohana_Log::add("error", "Caught exception rebuilding image: {$item->title}\n" . $e->getMessage() . "\n" . $e->getTraceAsString()); throw $e; } }