Location: PHPKode > projects > Dev's CMS > devscms/includes/class.gallery.php
<?php

system::includeLib('filehandling');

class galleryAlbums
{
	/**
	 * @var mysqliConnection
	 */
	private $_db;
	private $_tableName;
	private $_tagsTableName;
	
	public function __construct(&$db)
	{
		$this->_db = &$db;
		$this->_tableName = config::get('gallery', 'tablePrefix') . 'albums';
		$this->_tagsTableName = config::get('gallery', 'tablePrefix') . 'album_tags';
		
		$db->checkTable($this->_tableName, "
			`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
			`name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			`description` text COLLATE utf8_unicode_ci NOT NULL,
			`link` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			PRIMARY KEY (`id`)
		");
		
		$db->checkTable($this->_tagsTableName, "
			`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
			`album_id` int(10) unsigned NOT NULL,
			`name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			PRIMARY KEY (`id`)
		");
	}
	
	public function add($name, $description, $tags)
	{
		$id = $this->_db->insert($this->_tableName, array('name' => $name, 'description' => $description, 'link' => $this->_makeLink($name)));
		return $this->addTags($id, $tags);
	}
	
	public function get($id)
	{
		$sql_query = "SELECT a.id AS id, a.name AS aname, a.description AS adescription, a.link, at.name AS tname FROM {$this->_tableName} AS a LEFT JOIN {$this->_tagsTableName} AS at ON (a.id = at.album_id) WHERE a.id = " . $this->_db->quote($id);
		$result = $this->_db->query($sql_query);
		
		if ($result->num_rows == 0) {
			return false;
		}
		
		while ($row = $result->fetch_assoc()) {
			$name = $row['aname'];
			$description = $row['adescription'];
			$link = $row['link'];
			$tags[] = $row['tname'];
		}
		
		return array('id' => $id, 'name' => $name, 'description' => $description, 'link' => $link, 'tags' => $tags);
	}
	
	public function getByLink($link)
	{
		$sql_query = "SELECT a.id AS id, a.name AS aname, a.description AS adescription, a.link, at.name AS tname FROM {$this->_tableName} AS a LEFT JOIN {$this->_tagsTableName} AS at ON (a.id = at.album_id) WHERE a.link = " . $this->_db->quote($link);
		$result = $this->_db->query($sql_query);
		
		if ($result->num_rows == 0) {
			return false;
		}
		
		while ($row = $result->fetch_assoc()) {
			$id = $row['id'];
			$name = $row['aname'];
			$description = $row['adescription'];
			$link = $row['link'];
			$tags[] = $row['tname'];
		}
		
		return array('id' => $id, 'name' => $name, 'description' => $description, 'link' => $link, 'tags' => $tags);
	}
	
	public function getInfo($id)
	{
		return $this->_db->getRow($this->_tableName, '*', 'id', $id);
	}
	
	public function editName($id, $name)
	{
		$this->_db->update($this->_tableName, array('name' => $name/*, 'link' => $this->_makeLink($name)*/), 'id = ' . $this->_db->quote($id));
		return true;
	}
	
	public function editDescription($id, $description)
	{
		$this->_db->update($this->_tableName, array('description' => $description), 'id = ' . $this->_db->quote($id));
		return true;
	}
	
	public function getAll($filters = array(), $invertedFilters = array())
	{
		$where = array();
		foreach ($filters as $column => $value) {
			if (is_array($value)) {
				foreach ($value as &$v) {
					$v = $this->_db->quote($v);
				}
				$where[] = "a.$column IN (" . implode(',', $value) . ')';
			} else {
				$where[] = "a.$column = " . $this->_db->quote($value);
			}
		}
		
		foreach ($invertedFilters as $column => $value) {
			if (is_array($value)) {
				foreach ($value as &$v) {
					$v = $this->_db->quote($v);
				}
				$where[] = "a.$column NOT IN (" . implode(',', $value) . ')';
			} else {
				$where[] = "a.$column != " . $this->_db->quote($value);
			}
		}
		
		$sql_query = "SELECT a.id AS id, a.name AS aname, a.description AS adescription, a.link, at.name AS tname FROM {$this->_tableName} AS a LEFT JOIN {$this->_tagsTableName} AS at ON (a.id = at.album_id) %where ORDER BY id DESC";
		$sql_query = empty($where) ? str_replace('%where', '', $sql_query) : str_replace('%where', 'WHERE ' . implode(' AND ', $where), $sql_query);
		
		$result = $this->_db->query($sql_query);
		
		$id = 0;
		$albums = array();
		$name = "";
		$description = "";
		$link = "";
		$tags = array();
		
		while ($row = $result->fetch_assoc()) {
			// If next album id
			if ($id != $row['id'] && $id != 0) {
				$albums[] = array('id' => $id, 'name' => $name, 'description' => $description, 'link' => $link, 'tags' => $tags);
				$tags = array();
			}
			
			$id = $row['id'];
			$name = $row['aname'];
			$description = $row['adescription'];
			$link = $row['link'];
			$tags[] = $row['tname'];
		}
		
		if ($id != 0) {
			$albums[] = array('id' => $id, 'name' => $name, 'description' => $description, 'link' => $link, 'tags' => $tags);
		}
		
		return $albums;
	}
	
	public function remove($id)
	{
		$this->_db->delete($this->_tableName, 'id = ' . $this->_db->quote($id));
		return $this->editTags($id, array());
	}
	
	
	public function addTags($album_id, $tags)
	{
		if (empty($tags)) {
			return true;
		}
		
		foreach ($tags as $tag) {
			$quoted_tags[] = $this->_db->quote($tag);
		}
		
		$sql_query = "INSERT INTO {$this->_tagsTableName} (album_id, name) VALUE (" . $this->_db->quote($album_id) .
						', ' . implode('), (' . $this->_db->quote($album_id) . ', ', $quoted_tags) . ")";
		
		$this->_db->query($sql_query);
		
		return true;
	}
	
	public function editTags($album_id, $tags)
	{
		$to_add = array();
		$to_remove = array();
		
		$current_tags = $this->getTags($album_id);
		
		foreach ($tags as $tag) {
			if (!in_array($tag, $current_tags)) {
				$to_add[] = $tag;
			}
		}
		
		foreach ($current_tags as $current_tag) {
			if (!in_array($current_tag, $tags)) {
				$to_remove[] = $current_tag;
			}
		}
		
		$this->addTags($album_id, $to_add);
		$this->removeTags($album_id, $to_remove);
		
		return true;
	}
	
	public function getTags($album_id)
	{
		$sql_query = "SELECT name FROM {$this->_tagsTableName} WHERE album_id = " . $this->_db->quote($album_id);
		$result = $this->_db->query($sql_query);
		
		$tags = array();
		
		while ($row = $result->fetch_assoc()) {
			$tags[] = $row['name'];
		}
		
		return $tags;
	}
	
	public function removeTags($album_id, $tags)
	{
		if (empty($tags)) {
			return true;
		}
		
		foreach ($tags as $tag) {
			$quoted_tags[] = $this->_db->quote($tag);
		}
		
		$this->_db->delete($this->_tagsTableName, "album_id = $album_id AND (name = " . implode(' OR name = ', $quoted_tags) . ')');
		return true;
	}
	
	private function _makeLink($text)
	{
		$linkUnique = $link = $this->_linkify($text);
		
		$i = 1;
		while ($this->getByLink($linkUnique) !== false) {
			$linkUnique = $link . '-' . $i++;
		}
		
		return $linkUnique;
	}
	
	private function _linkify($filename, $additionalCharacters = '')
	{
		if (mb_detect_encoding($filename, 'UTF-8, ISO-8859-1') == 'UTF-8') {
			$filename = utf8_decode($filename);
		}
		if (mb_detect_encoding($additionalCharacters, 'UTF-8, ISO-8859-1') == 'UTF-8') {
			$additionalCharacters = utf8_decode($additionalCharacters);
		}
		
		return utf8_encode(preg_replace("/[^a-z0-9{$additionalCharacters}_.!~*')(-]/", '',
			preg_replace('/\s+/', '-',
				strtolower($filename)
			)
		));
	}
}

class galleryPictures
{
	/**
	 * @var mysqliConnection
	 */
	private $_db;
	private $_tableName;
	private $_tagsTableName;
	private $_tags;
	
	public function __construct(&$db)
	{
		$this->_db = &$db;
		$this->_tableName = config::get('gallery', 'tablePrefix') . 'pictures';
		$this->_tags = new galleryTags($db);
		$this->_tagsTableName = $this->_tags->getTableName();
		filehandling::folderHasToExist(config::get('gallery', 'path'));
		filehandling::folderHasToExist(config::get('gallery', 'uploadPath'));
		
		$db->checkTable($this->_tableName, "
			`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
			`filename` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			`name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			PRIMARY KEY (`id`)
		");
	}
	
	/**
	 * Add picture from upload directory
	 *
	 * @param string $filename
	 */
	public function add($filename)
	{
		$uploadPath = config::get('gallery', 'uploadPath');
		$path = config::get('gallery', 'path');
		$size = config::get('gallery', 'size');
		
		if (!is_file($uploadPath . $filename)) {
			system::error("Couldn't find file $filename");
		}
		
		$id = $this->_db->insert($this->_tableName, array('name' => str_ireplace('.jpg', '', $filename)));
		$newFilename = $id . '.jpg';
		
		if (galleryPictures::resize($uploadPath . $filename, $path . $newFilename, $size, 'scale', 95)) {
			unlink($uploadPath . $filename);
			$this->_db->update($this->_tableName, array('filename' => $newFilename), 'id = ' . $this->_db->quote($id));
			
			galleryPictures::resize($path . $newFilename, galleryPictures::getThumbnailFilename($path . $newFilename), config::get('gallery', 'thumbSize'), 'crop');
			galleryPictures::resize($path . $newFilename, galleryPictures::getThumbnailFilename($path . $newFilename, 'mini'), config::get('gallery', 'thumbMiniSize'), 'scale');
			galleryPictures::resize($path . $newFilename, galleryPictures::getThumbnailFilename($path . $newFilename, 'medium'), config::get('gallery', 'thumbMediumSize'), 'scale');
			
			return $id;
		}
		return false;
	}
	
	public function edit($id, $name, $tags)
	{
		$this->editName($id, $name);
		return $this->_tags->edit($id, $tags);
	}
	
	public function editName($id, $name)
	{
		$this->_db->update($this->_tableName, array('name' => $name), 'id = ' . $this->_db->quote($id));
		return true;
	}
	
	public function get($id)
	{
		$sqlQuery = "SELECT p.id,p.name AS pname,p.filename AS filename,pt.name AS tname FROM {$this->_tableName} AS p LEFT JOIN {$this->_tagsTableName} AS pt ON (p.id = pt.picture_id) WHERE p.id = " . $this->_db->quote($id); // . " ORDER BY tname ASC";
		$result = $this->_db->query($sqlQuery);
		
		$tags = array();
		while ($row = $result->fetch_assoc()) {
			$id = $row['id'];
			$name = $row['pname'];
			$filename = config::get('gallery', 'path') . $row['filename'];
			if ($row['tname'] != null) {
				$tags[] = $row['tname'];
			}
		}
		
		if (isset($name)) {
			return array('id' => $id, 'name' => $name, 'filename' => $filename, 'thumbnail' => galleryPictures::getThumbnailFilename($filename), 'tags' => $tags);
		} else {
			return null;
		}
	}
	
	/*public function getInfo()
	{
		$sql_query = "SELECT * FROM gallery_pictures WHERE id = " . $this->_db->quote($this->id);
		$result = mysql_query($sql_query);
		
		$row = mysql_fetch_assoc($result);
		
		return array('id' => $this->id,
					'name' => utf8_decode($row['name']),
					'filename' => PICTURE_DIR.$row['filename'],
					'thumbnail' => picture::getThumbnailFilename(PICTURE_DIR.$row['filename']));
	}*/
	
	public function getAll()
	{
		$sqlQuery = "SELECT p.id AS id, p.name AS pname, p.filename AS filename, pt.name AS tname FROM {$this->_tableName} AS p LEFT JOIN {$this->_tagsTableName} AS pt ON (p.id = pt.picture_id) ORDER BY id DESC"; //, tname ASC";
		$result = $this->_db->query($sqlQuery);
		
		$id = 0;
		$pictures = array();
		$name = "";
		$filename = "";
		$tags = array();
		
		while ($row = $result->fetch_assoc()) {
			// If next picture id
			if ($id != $row['id'] && $id != 0) {
				$pictures[] = array('id' => $id, 'name' => $name, 'filename' => $filename, 'thumbnail' => galleryPictures::getThumbnailFilename($filename), 'tags' => $tags);
				$tags = array();
			}
			
			$id = $row['id'];
			$name = $row['pname'];
			$filename = config::get('gallery', 'path') . $row['filename'];
			if ($row['tname'] != null) {
				$tags[] = $row['tname'];
			}
		}
		
		if ($id != 0) {
			$pictures[] = array('id' => $id, 'name' => $name, 'filename' => $filename, 'thumbnail' => galleryPictures::getThumbnailFilename($filename), 'tags' => $tags);
		}
		
		return $pictures;
	}
	
	public function getMany($tags, $limit = 0, $orderByRandom = false)
	{
		if (empty($tags)) {
			$sql_query = "SELECT id AS picture_id,0 AS c FROM {$this->_tableName} ORDER BY " . ($orderByRandom?'rand()':'name') . ($limit!=0?" LIMIT $limit":'');
		} else {
			foreach ($tags as $tag) {
				$quoted_tags[] = $this->_db->quote("%" . $tag . "%");
			}
			
			$sql_query = "SELECT picture_id,count(*) AS c FROM {$this->_tagsTableName} WHERE name LIKE " .
				implode(' OR name LIKE ', $quoted_tags) .
				" GROUP BY picture_id ORDER BY c DESC, " . ($orderByRandom?'rand()':'picture_id DESC') . ($limit!=0?" LIMIT $limit":'');
		}
		
		$result = $this->_db->query($sql_query);
		
		$pictures = array();
		while ($row = $result->fetch_assoc()) {
			$picture_id = $row['picture_id'];
			$count = $row['c'];
			
			if ($count == count($tags)) {
				$pictures[] = $this->get($picture_id);
			} else {
				break;
			}
		}
		
		return $pictures;
	}
	
	public static function getThumbnailFilename($filename, $size = null)
	{
		if (isset($size)) {
			return str_ireplace('.jpg', "-thumb-$size.jpg", $filename);
		} else {
			return str_ireplace('.jpg', '-thumb.jpg', $filename);
		}
	}
	
	public static function resize($filename, $newFilename, $maxSize, $method = 'crop', $jpegQuality = 85)
	{
		ini_set('memory_limit','64M');
		
		if (!file_exists($filename)) {
			system::error("File $filename doesn't exist");
		}
		
		list($width, $height) = getimagesize($filename);
		
		if ($method == 'scale') {
			// Calc new dimensions
			if (max($maxSize, $width) == $maxSize && max($maxSize,$height) == $maxSize) {
				$new_width = $width;
				$new_height = $height;
			} else {
				$percent = min($maxSize / $width, $maxSize / $height);
				$new_width = round($width * $percent);
				$new_height = round($height * $percent);
			}
	
			// Resample
			$image_p = imagecreatetruecolor($new_width, $new_height);
			
			switch (filehandling::getExtension($filename)) {
				case 'jpg':
				case 'jpeg':
					$image = imagecreatefromjpeg($filename);
					break;
					
				case 'png':
					$image = imagecreatefrompng($filename);
					break;
			}
			
			imagecopyresampled($image_p, $image, 0, 0, 0, 0, $new_width, $new_height, $width, $height);
	
		} elseif ($method == 'crop') {
			// Calc crop size
			/*$crop_width = $width * 0.3;
			$crop_height = $height * 0.3;*/
			$crop_width = min($width, $height);
			$crop_height = min($width, $height);
	
			// Create images
			$image_tmp = imagecreatetruecolor($crop_width, $crop_height) or die("$crop_width, $crop_height, $filename");    //Crop
			$image = imagecreatefromjpeg($filename);    //Org image
	
			// Crop
			if ($width < $crop_width || $height < $crop_height) {
				imagecopy ($image_tmp, $image, 0, 0, 0, 0, $crop_width, $crop_height);
			} else {
				//imagecopy ($image_tmp, $image, 0, 0, rand(0,$width-$crop_width), rand(0,$height-$crop_height), $crop_width, $crop_height);
				imagecopy ($image_tmp, $image, 0, 0, $width/2-$crop_width/2, $height/2-$crop_height/2, $crop_width, $crop_height);
			}
	
			// Calc new dimensions
			$percent = min($maxSize / $crop_width, $maxSize / $crop_height);
			$new_width = round($crop_width * $percent);
			$new_height = round($crop_height * $percent);
	
			// Create final image
			$image_p = imagecreatetruecolor($new_width, $new_height);    //Final image
	
			// Resample
			imagecopyresampled($image_p, $image_tmp, 0, 0, 0, 0, $new_width, $new_height, $crop_width, $crop_height);
	
			// Destroy tmp image
			imagedestroy($image_tmp);
	
		}
	
		// Output
		//$newFilename = picture::getThumbnailFilename($filename);
		imagejpeg($image_p, $newFilename, $jpegQuality);
		ImageDestroy ($image_p);
		ImageDestroy ($image);
		return true;
	}
	
	public function remove($id)
	{
		$picture = $this->get($id);
		$this->_db->delete($this->_tableName, 'id = ' . $this->_db->quote($id));
		
		$filename = $picture['filename'];
		
		@unlink($filename);
		@unlink(galleryPictures::getThumbnailFilename($filename));
		@unlink(galleryPictures::getThumbnailFilename($filename, 'mini'));
		@unlink(galleryPictures::getThumbnailFilename($filename, 'medium'));
		
		return $this->_tags->edit($id, array());
	}
}

class galleryTags
{
	/**
	 * @var mysqliConnection
	 */
	private $_db;
	private $_tableName;
	
	public function __construct(&$db)
	{
		$this->_db = &$db;
		$this->_tableName = config::get('gallery', 'tablePrefix') . 'picture_tags';
		
		$db->checkTable($this->_tableName, "
			`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
			`picture_id` int(10) unsigned NOT NULL,
			`name` varchar(255) COLLATE utf8_unicode_ci NOT NULL,
			PRIMARY KEY (`id`)
		");
	}
	
	public function add($picture_id, $tags)
	{
		if (empty($tags)) {
			return true;
		}
		
		foreach ($tags as $tag) {
			$quoted_tags[] = $this->_db->quote($tag);
		}
		
		$sql_query = "INSERT INTO {$this->_tableName} (picture_id, name) VALUE (" . $this->_db->quote($picture_id) .
			', ' . implode('), (' . $this->_db->quote($picture_id) . ', ', $quoted_tags) . ")";
		
		$this->_db->query($sql_query);
		
		return true;
	}
	
	public function edit($picture_id, $tags)
	{
		$to_add = array();
		$to_remove = array();
		
		$current_tags = $this->get($picture_id, false);
		
		foreach ($tags as $tag) {
			if (!in_array($tag, $current_tags)) {
				$to_add[] = $tag;
			}
		}
		
		foreach ($current_tags as $current_tag) {
			if (!in_array($current_tag, $tags)) {
				$to_remove[] = $current_tag;
			}
		}

		$this->add($picture_id, $to_add);
		$this->remove($picture_id, $to_remove);
		
		return true;
	}
	
	public static function explodeTags($str_tags)
	{
		$tags = explode(',', $str_tags);
		//$tags = array_map('trim', $tags);
		for ($i=0; $i<count($tags); $i++)
		{
			$tags[$i] = trim($tags[$i]);
			if (empty($tags[$i])) {
				array_splice($tags, $i, 1);
			}
		}
		return $tags;
	}
	
	public function get($picture_id)
	{
		$sql_query = "SELECT name FROM {$this->_tableName} WHERE picture_id = " . $this->_db->quote($picture_id) . " ORDER BY name DESC";
		$result = $this->_db->query($sql_query);
		
		$tags = array();
		
		while ($row = $result->fetch_assoc()) {
			$tags[] = $row['name'];
		}
		
		return $tags;
	}
	
	public function getTableName()
	{
		return $this->_tableName;
	}
	
	public function remove($picture_id, $tags)
	{
		if (empty($tags)) {
			return true;
		}
		
		foreach ($tags as $tag) {
			$quoted_tags[] = $this->_db->quote($tag);
		}
		
		$sql_query = "DELETE FROM {$this->_tableName} WHERE picture_id = $picture_id AND (name = " . implode(' OR name = ', $quoted_tags) . ")";
		$this->_db->query($sql_query);

		return true;
	}
}
Return current item: Dev's CMS