= 90) { return $sourcePath; } outFileLog($sourcePath,'upload_img','$sourcePath2'); // 计算新尺寸 $newSize = self::calculateNewSize($width, $height, $maxWidth, $maxHeight); $newWidth = $newSize['width']; $newHeight = $newSize['height']; outFileLog($newWidth,'upload_img','$newWidth'); outFileLog($newHeight,'upload_img','$newHeight'); // 创建源图片资源 $sourceImage = self::createImageFromType($sourcePath, $type); if (!$sourceImage) { throw new Exception('不支持的图片格式'); } outFileLog($sourceImage,'upload_img','$sourceImage'); // 创建新图片资源 $newImage = imagecreatetruecolor($newWidth, $newHeight); outFileLog($newImage,'upload_img','$newImage'); // 处理透明背景(PNG/GIF) if ($type == IMAGETYPE_PNG || $type == IMAGETYPE_GIF) { imagealphablending($newImage, false); imagesavealpha($newImage, true); $transparent = imagecolorallocatealpha($newImage, 255, 255, 255, 127); imagefill($newImage, 0, 0, $transparent); } // 重新采样 imagecopyresampled($newImage, $sourceImage, 0, 0, 0, 0, $newWidth, $newHeight, $width, $height); // 生成压缩后的文件路径 $compressedPath = self::generateCompressedPath($sourcePath); outFileLog($compressedPath,'upload_img','$compressedPath'); // 保存压缩后的图片 $result = self::saveImageByType($newImage, $compressedPath, $type, $quality); utFileLog($result,'upload_img','$result'); // $imageInfo = getimagesize($result); // 释放内存 imagedestroy($sourceImage); imagedestroy($newImage); return $result ? $compressedPath : false; } catch (Exception $e) { return false; } } /** * 计算新尺寸(保持宽高比) */ private static function calculateNewSize($width, $height, $maxWidth, $maxHeight) { $ratio = min($maxWidth / $width, $maxHeight / $height, 1); return [ 'width' => intval($width * $ratio), 'height' => intval($height * $ratio) ]; } /** * 根据图片类型创建图片资源 */ private static function createImageFromType($path, $type) { // 检查文件是否存在 if (!file_exists($path)) { throw new Exception('图片文件不存在: ' . $path); } outFileLog(file_exists($path),'upload_img','createImageFromType-$path1'); // 检查文件是否可读 if (!is_readable($path)) { throw new Exception('图片文件无法读取: ' . $path); } outFileLog(is_readable($path),'upload_img','createImageFromType-$path2'); // 检查GD扩展 if (!extension_loaded('gd')) { throw new Exception('GD扩展未安装'); } outFileLog(extension_loaded('gd'),'upload_img','createImageFromType-gd'); outFileLog($type,'upload_img','createImageFromType-$type'); outFileLog($path,'upload_img','createImageFromType-$path'); try { switch ($type) { case IMAGETYPE_JPEG: // PNG特殊处理 outFileLog('开始处理PNG图片: ' . $path, 'upload_img', 'png_process_start'); // 检查文件大小 $fileSize = filesize($path); outFileLog('PNG文件大小: ' . $fileSize . ' bytes', 'upload_img', 'png_file_size'); // 检查内存限制 $memoryLimit = ini_get('memory_limit'); $currentMemory = memory_get_usage(true); outFileLog('内存限制: ' . $memoryLimit . ', 当前使用: ' . $currentMemory, 'upload_img', 'memory_info'); $image = imagecreatefromjpeg($path); outFileLog($image, 'upload_img', '$image112'); $error = error_get_last(); outFileLog('PNG创建失败,错误信息: ' . json_encode($error), 'upload_img', 'png_create_error'); if ($image === false) { // 获取详细错误信息 $error = error_get_last(); outFileLog('PNG创建失败,错误信息: ' . json_encode($error), 'upload_img', 'png_create_error'); // 尝试使用getimagesize验证 $imageInfo = @getimagesize($path); if ($imageInfo === false) { throw new Exception('PNG文件无法被识别,可能已损坏'); } outFileLog('PNG图片信息: ' . json_encode($imageInfo), 'upload_img', 'png_image_info'); } break; case IMAGETYPE_PNG: // PNG特殊处理 outFileLog('开始处理PNG图片: ' . $path, 'upload_img', 'png_process_start'); // 检查文件大小 $fileSize = filesize($path); outFileLog('PNG文件大小: ' . $fileSize . ' bytes', 'upload_img', 'png_file_size'); // 检查内存限制 $memoryLimit = ini_get('memory_limit'); $currentMemory = memory_get_usage(true); outFileLog('内存限制: ' . $memoryLimit . ', 当前使用: ' . $currentMemory, 'upload_img', 'memory_info'); // 尝试创建PNG图片资源 $image = @imagecreatefrompng($path); // $image = imagecreatefrompng($path); if ($image === false) { // 获取详细错误信息 $error = error_get_last(); outFileLog('PNG创建失败,错误信息: ' . json_encode($error), 'upload_img', 'png_create_error'); // 尝试验证PNG文件头 $handle = fopen($path, 'rb'); $header = fread($handle, 8); fclose($handle); $pngSignature = "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A"; if ($header !== $pngSignature) { throw new Exception('PNG文件头不正确,文件可能损坏'); } // 尝试使用getimagesize验证 $imageInfo = @getimagesize($path); if ($imageInfo === false) { throw new Exception('PNG文件无法被识别,可能已损坏'); } outFileLog('PNG图片信息: ' . json_encode($imageInfo), 'upload_img', 'png_image_info'); } break; case IMAGETYPE_GIF: $image = imagecreatefromgif($path); break; case IMAGETYPE_WEBP: if (!function_exists('imagecreatefromwebp')) { throw new Exception('WebP格式不支持'); } $image = imagecreatefromwebp($path); break; default: throw new Exception('不支持的图片格式: ' . $type); } if (!$image) { throw new Exception('创建图片资源失败,可能是内存不足或文件损坏'); } outFileLog($image ? 'success' : 'failed', 'upload_img', 'createImageFromType-result'); return $image; } catch (Exception $e) { outFileLog('图片处理异常: ' . $e->getMessage(), 'upload_img', 'createImageFromType-exception'); throw new Exception('图片处理失败: ' . $e->getMessage()); } } /** * 根据图片类型保存图片 */ private static function saveImageByType($image, $path, $type, $quality) { switch ($type) { case IMAGETYPE_JPEG: return imagejpeg($image, $path, $quality); case IMAGETYPE_PNG: // PNG压缩级别 0-9,质量参数需要转换 $pngQuality = intval((100 - $quality) / 10); return imagepng($image, $path, $pngQuality); case IMAGETYPE_GIF: return imagegif($image, $path); case IMAGETYPE_WEBP: return imagewebp($image, $path, $quality); default: return false; } } /** * 生成压缩后的文件路径 */ private static function generateCompressedPath($originalPath) { $pathInfo = pathinfo($originalPath); return $pathInfo['dirname'] . '/' . $pathInfo['filename'] . '_compressed.' . $pathInfo['extension']; } }