首页 / 应用软件 / 详细指南,在WordPress中开发集成在线简易图片批量处理与格式转换工具

详细指南,在WordPress中开发集成在线简易图片批量处理与格式转换工具

详细指南:在WordPress中开发集成在线简易图片批量处理与格式转换工具

摘要

随着互联网内容的日益丰富,图片处理已成为网站运营中不可或缺的环节。对于WordPress网站管理员和内容创作者而言,拥有一个集成的图片批量处理与格式转换工具可以极大提高工作效率。本文将详细介绍如何在WordPress中通过代码二次开发,实现一个功能完善的在线简易图片批量处理与格式转换工具,涵盖从需求分析、技术选型到具体实现的完整流程。

目录

  1. 引言:为什么WordPress需要集成图片处理工具
  2. 需求分析与功能规划
  3. 技术选型与环境准备
  4. 创建WordPress插件基础结构
  5. 实现图片上传与批量选择功能
  6. 开发图片批量处理核心功能
  7. 集成图片格式转换模块
  8. 优化用户界面与用户体验
  9. 安全性与性能优化
  10. 测试与部署
  11. 扩展功能与未来展望
  12. 结论

1. 引言:为什么WordPress需要集成图片处理工具

WordPress作为全球最流行的内容管理系统,拥有超过40%的网站市场份额。尽管其内置了基础的图片上传和编辑功能,但在实际运营中,用户常常面临以下痛点:

  • 需要批量调整图片尺寸以适应不同展示场景
  • 需要将图片转换为不同格式(如PNG转JPG、WebP转换)
  • 缺乏对图片进行批量压缩以优化网站加载速度的工具
  • 依赖外部图片处理软件,工作流程不连贯

通过开发一个集成在WordPress后台的图片批量处理工具,管理员可以直接在熟悉的环境中完成这些操作,无需切换不同应用程序,大大提高了内容管理效率。本文将指导您通过WordPress代码二次开发,实现这样一个实用工具。

2. 需求分析与功能规划

2.1 核心功能需求

  1. 批量图片上传:支持多文件同时上传
  2. 图片预览:上传后显示缩略图预览
  3. 批量处理选项

    • 尺寸调整(按比例、固定尺寸)
    • 质量压缩
    • 格式转换(JPG、PNG、GIF、WebP之间转换)
  4. 处理进度显示:实时显示处理进度
  5. 结果下载:打包下载处理后的图片

2.2 技术需求

  1. 前端使用React或Vue.js实现交互界面
  2. 后端使用PHP配合WordPress钩子机制
  3. 图片处理使用GD库或ImageMagick
  4. 支持AJAX异步处理,避免超时问题

2.3 用户界面规划

  • WordPress后台独立菜单页
  • 拖拽上传区域
  • 图片预览网格
  • 处理选项侧边栏
  • 进度指示器
  • 结果操作按钮

3. 技术选型与环境准备

3.1 开发环境要求

  • WordPress 5.0+
  • PHP 7.4+(支持GD库或ImageMagick扩展)
  • MySQL 5.6+
  • 现代浏览器支持(Chrome、Firefox、Edge等)

3.2 关键技术选择

图片处理库选择:

  • GD库:PHP内置,无需额外安装,基础功能齐全
  • ImageMagick:功能更强大,支持更多格式,需要服务器安装

考虑到通用性,本指南将使用GD库作为主要图片处理引擎,同时提供ImageMagick备选方案。

前端框架选择:
考虑到与WordPress的兼容性和开发效率,我们选择使用原生JavaScript配合少量jQuery,避免框架冲突。

3.3 开发工具准备

  1. 本地WordPress开发环境(如Local by Flywheel、XAMPP)
  2. 代码编辑器(VS Code、PHPStorm等)
  3. 版本控制系统(Git)
  4. 浏览器开发者工具

4. 创建WordPress插件基础结构

4.1 插件目录结构

wp-content/plugins/bulk-image-processor/
├── bulk-image-processor.php          # 主插件文件
├── includes/
│   ├── class-image-processor.php     # 图片处理核心类
│   ├── class-ajax-handler.php        # AJAX处理类
│   └── class-format-converter.php    # 格式转换类
├── admin/
│   ├── css/
│   │   └── admin-style.css           # 后台样式
│   ├── js/
│   │   └── admin-script.js           # 后台脚本
│   └── partials/
│       └── admin-display.php         # 后台界面
├── assets/
│   ├── images/                       # 插件图片资源
│   └── fonts/                        # 字体文件
└── languages/                        # 国际化文件

4.2 主插件文件配置

<?php
/**
 * Plugin Name: 批量图片处理器
 * Plugin URI:  https://yourwebsite.com/bulk-image-processor
 * Description: WordPress在线简易图片批量处理与格式转换工具
 * Version:     1.0.0
 * Author:      您的名称
 * License:     GPL v2 or later
 * Text Domain: bulk-image-processor
 */

// 防止直接访问
if (!defined('ABSPATH')) {
    exit;
}

// 定义插件常量
define('BIP_VERSION', '1.0.0');
define('BIP_PLUGIN_DIR', plugin_dir_path(__FILE__));
define('BIP_PLUGIN_URL', plugin_dir_url(__FILE__));
define('BIP_UPLOAD_DIR', wp_upload_dir()['basedir'] . '/bip-temp/');
define('BIP_UPLOAD_URL', wp_upload_dir()['baseurl'] . '/bip-temp/');

// 创建临时目录
if (!file_exists(BIP_UPLOAD_DIR)) {
    wp_mkdir_p(BIP_UPLOAD_DIR);
}

// 包含必要文件
require_once BIP_PLUGIN_DIR . 'includes/class-image-processor.php';
require_once BIP_PLUGIN_DIR . 'includes/class-ajax-handler.php';
require_once BIP_PLUGIN_DIR . 'includes/class-format-converter.php';

// 初始化插件
class Bulk_Image_Processor {
    
    private static $instance = null;
    
    public static function get_instance() {
        if (null === self::$instance) {
            self::$instance = new self();
        }
        return self::$instance;
    }
    
    private function __construct() {
        $this->init_hooks();
    }
    
    private function init_hooks() {
        // 后台菜单
        add_action('admin_menu', array($this, 'add_admin_menu'));
        
        // 加载脚本和样式
        add_action('admin_enqueue_scripts', array($this, 'enqueue_admin_assets'));
        
        // 初始化AJAX处理
        $ajax_handler = new BIP_Ajax_Handler();
        $ajax_handler->init();
        
        // 插件激活/停用钩子
        register_activation_hook(__FILE__, array($this, 'activate'));
        register_deactivation_hook(__FILE__, array($this, 'deactivate'));
    }
    
    public function add_admin_menu() {
        add_menu_page(
            '批量图片处理器',
            '图片批量处理',
            'manage_options',
            'bulk-image-processor',
            array($this, 'display_admin_page'),
            'dashicons-images-alt2',
            30
        );
    }
    
    public function display_admin_page() {
        include BIP_PLUGIN_DIR . 'admin/partials/admin-display.php';
    }
    
    public function enqueue_admin_assets($hook) {
        if ('toplevel_page_bulk-image-processor' !== $hook) {
            return;
        }
        
        // 加载CSS
        wp_enqueue_style(
            'bip-admin-style',
            BIP_PLUGIN_URL . 'admin/css/admin-style.css',
            array(),
            BIP_VERSION
        );
        
        // 加载JavaScript
        wp_enqueue_script(
            'bip-admin-script',
            BIP_PLUGIN_URL . 'admin/js/admin-script.js',
            array('jquery'),
            BIP_VERSION,
            true
        );
        
        // 本地化脚本,传递数据到JS
        wp_localize_script('bip-admin-script', 'bip_ajax', array(
            'ajax_url' => admin_url('admin-ajax.php'),
            'nonce' => wp_create_nonce('bip_ajax_nonce'),
            'max_file_size' => wp_max_upload_size(),
            'supported_formats' => array('jpg', 'jpeg', 'png', 'gif', 'webp')
        ));
    }
    
    public function activate() {
        // 创建数据库表(如果需要)
        // 设置默认选项
    }
    
    public function deactivate() {
        // 清理临时文件
        $this->cleanup_temp_files();
    }
    
    private function cleanup_temp_files() {
        // 删除临时目录中的所有文件
        $files = glob(BIP_UPLOAD_DIR . '*');
        foreach ($files as $file) {
            if (is_file($file)) {
                unlink($file);
            }
        }
    }
}

// 启动插件
Bulk_Image_Processor::get_instance();

5. 实现图片上传与批量选择功能

5.1 创建后台界面

<!-- admin/partials/admin-display.php -->
<div class="wrap bip-container">
    <h1><?php echo esc_html(get_admin_page_title()); ?></h1>
    
    <div class="bip-upload-area" id="bip-dropzone">
        <div class="bip-upload-icon">
            <span class="dashicons dashicons-upload"></span>
        </div>
        <h3>拖放图片到这里,或点击选择文件</h3>
        <p>支持格式:JPG、PNG、GIF、WebP,最大文件大小:<?php echo size_format(wp_max_upload_size()); ?></p>
        <input type="file" id="bip-file-input" multiple accept="image/*" style="display: none;">
        <button type="button" id="bip-select-files" class="button button-primary">选择图片</button>
    </div>
    
    <div class="bip-preview-container" id="bip-preview-container" style="display: none;">
        <h3>已选择图片 (<span id="bip-selected-count">0</span>)</h3>
        <div class="bip-preview-grid" id="bip-preview-grid">
            <!-- 图片预览将动态插入这里 -->
        </div>
        <div class="bip-preview-actions">
            <button type="button" id="bip-remove-all" class="button">清除全部</button>
            <button type="button" id="bip-select-all" class="button">全选</button>
        </div>
    </div>
    
    <div class="bip-processing-options" id="bip-options-panel" style="display: none;">
        <h3>处理选项</h3>
        
        <div class="bip-option-section">
            <h4>尺寸调整</h4>
            <div class="bip-option-row">
                <label>
                    <input type="checkbox" id="bip-resize-enable"> 启用尺寸调整
                </label>
            </div>
            <div class="bip-option-row bip-resize-options" style="display: none;">
                <div class="bip-option-group">
                    <label>宽度:</label>
                    <input type="number" id="bip-resize-width" min="1" placeholder="像素">
                    <label>高度:</label>
                    <input type="number" id="bip-resize-height" min="1" placeholder="像素">
                </div>
                <div class="bip-option-group">
                    <label>保持比例:</label>
                    <input type="checkbox" id="bip-keep-aspect" checked>
                </div>
            </div>
        </div>
        
        <div class="bip-option-section">
            <h4>格式转换</h4>
            <div class="bip-option-row">
                <label>输出格式:</label>
                <select id="bip-output-format">
                    <option value="original">保持原格式</option>
                    <option value="jpg">JPG</option>
                    <option value="png">PNG</option>
                    <option value="webp">WebP</option>
                    <option value="gif">GIF</option>
                </select>
            </div>
            <div class="bip-option-row bip-jpg-quality" style="display: none;">
                <label>JPG质量 (1-100):</label>
                <input type="range" id="bip-jpg-quality" min="1" max="100" value="85">
                <span id="bip-quality-value">85</span>
            </div>
        </div>
        
        <div class="bip-option-section">
            <h4>压缩选项</h4>
            <div class="bip-option-row">
                <label>
                    <input type="checkbox" id="bip-compress-enable"> 启用压缩优化
                </label>
            </div>
        </div>
        
        <div class="bip-process-actions">
            <button type="button" id="bip-start-process" class="button button-primary button-large">开始处理</button>
        </div>
    </div>
    
    <div class="bip-progress-container" id="bip-progress-container" style="display: none;">
        <h3>处理进度</h3>
        <div class="bip-progress-bar">
            <div class="bip-progress-fill" id="bip-progress-fill"></div>
        </div>
        <div class="bip-progress-text">
            正在处理:<span id="bip-current-file">-</span>
        </div>
        <div class="bip-progress-stats">
            已完成:<span id="bip-processed-count">0</span> / 
            总计:<span id="bip-total-count">0</span>
        </div>
    </div>
    
    <div class="bip-results-container" id="bip-results-container" style="display: none;">
        <h3>处理完成</h3>
        <div class="bip-results-info">
            <p>成功处理 <span id="bip-success-count">0</span> 张图片,失败 <span id="bip-failed-count">0</span> 张。</p>
        </div>
        <div class="bip-results-actions">
            <button type="button" id="bip-download-all" class="button button-primary">下载全部</button>
            <button type="button" id="bip-process-again" class="button">再次处理</button>
        </div>
    </div>
</div>

5.2 实现前端JavaScript功能

// admin/js/admin-script.js
jQuery(document).ready(function($) {
    
    let selectedFiles = [];
    let processedFiles = [];
    
    // 初始化拖放上传
    initDropzone();
    
    // 文件选择按钮点击事件
    $('#bip-select-files').on('click', function() {
        $('#bip-file-input').click();
    });
    
    // 文件输入变化事件
    $('#bip-file-input').on('change', function(e) {
        handleFiles(e.target.files);
    });
    
    // 初始化拖放区域
    function initDropzone() {
        const dropzone = $('#bip-dropzone')[0];
        
        dropzone.addEventListener('dragover', function(e) {
            e.preventDefault();
            e.stopPropagation();
            $(this).addClass('dragover');
        });
        
        dropzone.addEventListener('dragleave', function(e) {
            e.preventDefault();
            e.stopPropagation();
            $(this).removeClass('dragover');
        });
        
        dropzone.addEventListener('drop', function(e) {
            e.preventDefault();
            e.stopPropagation();
            $(this).removeClass('dragover');
            
            const files = e.dataTransfer.files;
            handleFiles(files);
        });
    }
    
    // 处理选择的文件
    function handleFiles(files) {
        const supportedFormats = bip_ajax.supported_formats;
        
        for (let i = 0; i < files.length; i++) {
            const file = files[i];
            const fileExt = file.name.split('.').pop().toLowerCase();
            
            // 检查文件格式
            if (!supportedFormats.includes(fileExt)) {
                alert(`文件 ${file.name} 格式不支持,已跳过。`);
                continue;
            }
            
            // 检查文件大小
            if (file.size > bip_ajax.max_file_size) {
                alert(`文件 ${file.name} 太大,已跳过。`);
                continue;
            }
            
            // 添加到选择列表
            if (!selectedFiles.some(f => f.name === file.name && f.size === file.size)) {
                selectedFiles.push(file);
            }
        }
        
        updatePreview();
    }
    
    // 更新预览区域
    function updatePreview() {
        const previewGrid = $('#bip-preview-grid');
        previewGrid.empty();
        
        if (selectedFiles.length === 0) {
            $('#bip-preview-container').hide();
            $('#bip-options-panel').hide();
            return;
        }
        
        $('#bip-preview-container').show();
        $('#bip-options-panel').show();
        $('#bip-selected-count').text(selectedFiles.length);
        
        selectedFiles.forEach((file, index) => {
            const reader = new FileReader();
            
            reader.onload = function(e) {
                const previewItem = $(`
                    <div class="bip-preview-item" data-index="${index}">
                        <div class="bip-preview-checkbox">
                            <input type="checkbox" class="bip-file-checkbox" checked data-index="${index}">
                        </div>
                        <div class="bip-preview-image">
                            <img src="${e.target.result}" alt="${file.name}">
                        </div>
                        <div class="bip-preview-info">

file.name}</div>

                        <div class="bip-filesize">${formatFileSize(file.size)}</div>
                    </div>
                    <button type="button" class="bip-remove-file" data-index="${index}">
                        <span class="dashicons dashicons-no"></span>
                    </button>
                </div>
            `);
            
            previewGrid.append(previewItem);
        };
        
        reader.readAsDataURL(file);
    });
    
    // 绑定移除按钮事件
    $('.bip-remove-file').on('click', function() {
        const index = parseInt($(this).data('index'));
        selectedFiles.splice(index, 1);
        updatePreview();
    });
    
    // 绑定复选框事件
    $('.bip-file-checkbox').on('change', function() {
        const index = parseInt($(this).data('index'));
        $(this).closest('.bip-preview-item').toggleClass('unselected', !this.checked);
    });
}

// 全选/取消全选
$('#bip-select-all').on('click', function() {
    const allChecked = $('.bip-file-checkbox:checked').length === selectedFiles.length;
    $('.bip-file-checkbox').prop('checked', !allChecked).trigger('change');
});

// 清除全部
$('#bip-remove-all').on('click', function() {
    if (confirm('确定要清除所有已选择的图片吗?')) {
        selectedFiles = [];
        updatePreview();
    }
});

// 格式转换选项变化
$('#bip-output-format').on('change', function() {
    if ($(this).val() === 'jpg') {
        $('.bip-jpg-quality').show();
    } else {
        $('.bip-jpg-quality').hide();
    }
});

// JPG质量滑块
$('#bip-jpg-quality').on('input', function() {
    $('#bip-quality-value').text($(this).val());
});

// 尺寸调整选项切换
$('#bip-resize-enable').on('change', function() {
    $('.bip-resize-options').toggle(this.checked);
});

// 开始处理按钮
$('#bip-start-process').on('click', function() {
    startProcessing();
});

// 开始处理函数
function startProcessing() {
    // 获取选中的文件
    const filesToProcess = [];
    $('.bip-file-checkbox:checked').each(function() {
        const index = parseInt($(this).data('index'));
        filesToProcess.push(selectedFiles[index]);
    });
    
    if (filesToProcess.length === 0) {
        alert('请至少选择一张图片进行处理。');
        return;
    }
    
    // 收集处理选项
    const options = {
        resize: {
            enabled: $('#bip-resize-enable').is(':checked'),
            width: parseInt($('#bip-resize-width').val()) || 0,
            height: parseInt($('#bip-resize-height').val()) || 0,
            keepAspect: $('#bip-keep-aspect').is(':checked')
        },
        format: $('#bip-output-format').val(),
        quality: parseInt($('#bip-jpg-quality').val()) || 85,
        compress: $('#bip-compress-enable').is(':checked')
    };
    
    // 验证尺寸参数
    if (options.resize.enabled) {
        if (options.resize.width <= 0 && options.resize.height <= 0) {
            alert('请至少指定宽度或高度中的一个值。');
            return;
        }
    }
    
    // 显示进度条
    $('#bip-options-panel').hide();
    $('#bip-progress-container').show();
    $('#bip-progress-fill').css('width', '0%');
    $('#bip-total-count').text(filesToProcess.length);
    $('#bip-processed-count').text('0');
    
    // 开始处理
    processFiles(filesToProcess, options);
}

// 处理文件队列
async function processFiles(files, options) {
    processedFiles = [];
    
    for (let i = 0; i < files.length; i++) {
        const file = files[i];
        
        // 更新进度显示
        $('#bip-current-file').text(file.name);
        $('#bip-processed-count').text(i);
        const progress = ((i + 1) / files.length) * 100;
        $('#bip-progress-fill').css('width', progress + '%');
        
        // 上传并处理文件
        try {
            const result = await uploadAndProcessFile(file, options);
            processedFiles.push(result);
        } catch (error) {
            console.error('处理失败:', error);
            processedFiles.push({
                success: false,
                filename: file.name,
                error: error.message
            });
        }
    }
    
    // 处理完成
    showResults();
}

// 上传并处理单个文件
function uploadAndProcessFile(file, options) {
    return new Promise((resolve, reject) => {
        const formData = new FormData();
        formData.append('action', 'bip_process_image');
        formData.append('nonce', bip_ajax.nonce);
        formData.append('file', file);
        formData.append('options', JSON.stringify(options));
        
        $.ajax({
            url: bip_ajax.ajax_url,
            type: 'POST',
            data: formData,
            processData: false,
            contentType: false,
            dataType: 'json',
            success: function(response) {
                if (response.success) {
                    resolve(response.data);
                } else {
                    reject(new Error(response.data || '处理失败'));
                }
            },
            error: function(xhr, status, error) {
                reject(new Error('上传失败: ' + error));
            }
        });
    });
}

// 显示处理结果
function showResults() {
    const successCount = processedFiles.filter(f => f.success).length;
    const failedCount = processedFiles.length - successCount;
    
    $('#bip-success-count').text(successCount);
    $('#bip-failed-count').text(failedCount);
    
    $('#bip-progress-container').hide();
    $('#bip-results-container').show();
}

// 下载全部结果
$('#bip-download-all').on('click', function() {
    if (processedFiles.length === 0) return;
    
    // 创建ZIP文件
    const zip = new JSZip();
    
    processedFiles.forEach(file => {
        if (file.success && file.data) {
            // 将base64数据转换为二进制
            const binaryData = atob(file.data.split(',')[1]);
            const array = [];
            for (let i = 0; i < binaryData.length; i++) {
                array.push(binaryData.charCodeAt(i));
            }
            const blob = new Uint8Array(array);
            
            zip.file(file.filename, blob);
        }
    });
    
    // 生成并下载ZIP
    zip.generateAsync({type: "blob"})
        .then(function(content) {
            const link = document.createElement('a');
            link.href = URL.createObjectURL(content);
            link.download = 'processed-images.zip';
            link.click();
        });
});

// 再次处理
$('#bip-process-again').on('click', function() {
    $('#bip-results-container').hide();
    $('#bip-options-panel').show();
});

// 辅助函数:格式化文件大小
function formatFileSize(bytes) {
    if (bytes === 0) return '0 Bytes';
    const k = 1024;
    const sizes = ['Bytes', 'KB', 'MB', 'GB'];
    const i = Math.floor(Math.log(bytes) / Math.log(k));
    return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + sizes[i];
}

});


## 6. 开发图片批量处理核心功能

### 6.1 创建图片处理类

<?php
// includes/class-image-processor.php

class BIP_Image_Processor {


private $image_resource = null;
private $image_info = null;
private $error = null;

/**
 * 加载图片
 */
public function load($file_path) {
    if (!file_exists($file_path)) {
        $this->error = '文件不存在: ' . $file_path;
        return false;
    }
    
    $this->image_info = getimagesize($file_path);
    if (!$this->image_info) {
        $this->error = '无法读取图片信息';
        return false;
    }
    
    $mime_type = $this->image_info['mime'];
    
    switch ($mime_type) {
        case 'image/jpeg':
        case 'image/jpg':
            $this->image_resource = imagecreatefromjpeg($file_path);
            break;
        case 'image/png':
            $this->image_resource = imagecreatefrompng($file_path);
            break;
        case 'image/gif':
            $this->image_resource = imagecreatefromgif($file_path);
            break;
        case 'image/webp':
            if (function_exists('imagecreatefromwebp')) {
                $this->image_resource = imagecreatefromwebp($file_path);
            } else {
                $this->error = '服务器不支持WebP格式';
                return false;
            }
            break;
        default:
            $this->error = '不支持的图片格式: ' . $mime_type;
            return false;
    }
    
    if (!$this->image_resource) {
        $this->error = '无法创建图片资源';
        return false;
    }
    
    return true;
}

/**
 * 调整图片尺寸
 */
public function resize($width, $height, $keep_aspect = true) {
    if (!$this->image_resource) {
        $this->error = '未加载图片';
        return false;
    }
    
    $original_width = $this->image_info[0];
    $original_height = $this->image_info[1];
    
    // 计算新尺寸
    if ($keep_aspect) {
        if ($width > 0 && $height > 0) {
            // 按最大边缩放
            $width_ratio = $width / $original_width;
            $height_ratio = $height / $original_height;
            $ratio = min($width_ratio, $height_ratio);
            
            $new_width = round($original_width * $ratio);
            $new_height = round($original_height * $ratio);
        } elseif ($width > 0) {
            // 按宽度缩放
            $ratio = $width / $original_width;
            $new_width = $width;
            $new_height = round($original_height * $ratio);
        } elseif ($height > 0) {
            // 按高度缩放
            $ratio = $height / $original_height;
            $new_width = round($original_width * $ratio);
            $new_height = $height;
        } else {
            // 保持原尺寸
            $new_width = $original_width;
            $new_height = $original_height;
        }
    } else {
        $new_width = $width > 0 ? $width : $original_width;
        $new_height = $height > 0 ? $height : $original_height;
    }
    
    // 创建新图片资源
    $new_image = imagecreatetruecolor($new_width, $new_height);
    
    // 处理PNG和WebP的透明度
    if ($this->image_info['mime'] == 'image/png' || $this->image_info['mime'] == 'image/webp') {
        imagealphablending($new_image, false);
        imagesavealpha($new_image, true);
        $transparent = imagecolorallocatealpha($new_image, 255, 255, 255, 127);
        imagefilledrectangle($new_image, 0, 0, $new_width, $new_height, $transparent);
    }
    
    // 调整尺寸
    $result = imagecopyresampled(
        $new_image,
        $this->image_resource,
        0, 0, 0, 0,
        $new_width,
        $new_height,
        $original_width,
        $original_height
    );
    
    if (!$result) {
        $this->error = '调整尺寸失败';
        return false;
    }
    
    // 替换原图片资源
    imagedestroy($this->image_resource);
    $this->image_resource = $new_image;
    $this->image_info[0] = $new_width;
    $this->image_info[1] = $new_height;
    
    return true;
}

/**
 * 压缩图片
 */
public function compress($quality = 85) {
    if (!$this->image_resource) {
        $this->error = '未加载图片';
        return false;
    }
    
    // 对于JPG,使用指定的质量参数
    // 对于PNG,使用压缩级别(0-9)
    // 这里主要针对JPG优化
    return true;
}

/**
 * 保存图片到指定格式
 */
public function save($file_path, $format = 'jpg', $quality = 85) {
    if (!$this->image_resource) {
        $this->error = '未加载图片';
        return false;
    }
    
    $result = false;
    
    switch (strtolower($format)) {
        case 'jpg':
        case 'jpeg':
            $result = imagejpeg($this->image_resource, $file_path, $quality);
            break;
        case 'png':
            // PNG质量参数是压缩级别(0-9)
            $png_quality = 9 - round(($quality / 100) * 9);
            $result = imagepng($this->image_resource, $file_path, $png_quality);
            break;
        case 'gif':
            $result = imagegif($this->image_resource, $file_path);
            break;
        case 'webp':
            if (function_exists('imagewebp')) {
                $result = imagewebp($this->image_resource, $file_path, $quality);
            } else {
                $this->error = '服务器不支持WebP格式';
                return false;
            }
            break;
        default:
            $this->error = '不支持的输出格式: ' . $format;
            return false;
    }
    
    if (!$result) {
        $this->error = '保存图片失败';
        return false;
    }
    
    return true;
}

/**
 * 获取图片的base64编码
 */
public function get_base64($format = 'jpg', $quality = 85) {
    if (!$this->image_resource) {
        $this->error = '未加载图片';
        return false;
    }
    
    // 创建临时文件
    $temp_file = tempnam(sys_get_temp_dir(), 'bip_');
    
    if (!$this->save($temp_file, $format, $quality)) {
        unlink($temp_file);
        return false;
    }
    
    // 读取文件内容并转换为base64
    $file_content = file_get_contents($temp_file);
    $base64 = 'data:image/' . $format . ';base64,' . base64_encode($file_content);
    
    // 清理临时文件
    unlink($temp_file);
    
    return $base64;
}

/**
 * 获取错误信息
 */
public function get_error() {
    return $this->error;
}

/**
 * 清理资源
 */
public function cleanup() {
    if ($this->image_resource) {
        imagedestroy($this->image_resource);
        $this->image_resource = null;
    }
}

/**
 * 获取支持的图片格式
 */
public static function get_supported_formats() {
    $formats = array('jpg', 'jpeg', 'png', 'gif');
    
    if (function_exists('imagewebp')) {
        $formats[] = 'webp';
    }
    
    return $formats;
}

/**
 * 批量处理图片
 */
public static function batch_process($files, $options) {
    $results = array();
    
    foreach ($files as $index => $file) {
        $processor = new self();
        
        // 加载图片
        if (!$processor->load($file['tmp_name'])) {
            $results[] = array(
                'success' => false,
                'filename' => $file['name'],
                'error' => $processor->get_error()
            );
            continue;
        }
        
        // 调整尺寸
        if ($options['resize']['enabled']) {
            $width = $options['resize']['width'];
            $height = $options['resize']['height'];
            $keep_aspect = $options['resize']['keepAspect'];
            
            if (!$processor->resize($width, $height, $keep_aspect)) {
                $results[] = array(
                    'success' => false,
                    'filename' => $file['name'],
                    'error' => $processor->get_error()
                );
                $processor->cleanup();
                continue;
            }
        }
        
        // 压缩
        if ($options['compress']) {
            $processor->compress($options['quality']);
        }
        
        // 获取处理后的图片
        $output_format = $options['format'] == 'original' ? 
            pathinfo($file['name'], PATHINFO_EXTENSION) : 
            $options['format'];
        
        $base64_data = $processor->get_base64($output_format, $options['quality']);
        
        if ($base64_data) {
            $new_filename = pathinfo($file['name'], PATHINFO_FILENAME) . 
                           '_processed.' . $output_format;
            
            $results[] = array(
                'success' => true,
                'filename' => $new_filename,
                'data' => $base64_data,
                'format' => $output_format,
                'size' => strlen(base64_decode(explode(',', $base64_data)[1]))
            );
        } else {
            $results[] = array(
                'success' => false,
                'filename' => $file['name'],
                'error' => $processor->get_error()
            );
        }
        
        $processor->cleanup();
    }
    
    return $results;
}

}


## 7. 集成图片格式转换模块
本文来自网络,不代表柔性供应链服务中心立场,转载请注明出处:https://mall.org.cn/5343.html

EXCHANGES®作者

上一篇
下一篇

为您推荐

发表回复

联系我们

联系我们

18559313275

在线咨询: QQ交谈

邮箱: vip@exchanges.center

工作时间:周一至周五,9:00-17:30,节假日休息
返回顶部