You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现非中心式图像Bloat效果?求Python/Node.js/PHP解决方案

实现非中心原点的图像Bloat效果

当然可以实现!这种效果的核心逻辑是基于自定义原点计算像素距离,再根据距离调整像素的偏移/放大程度,而非固定使用图像中心。下面给你三个语言的可行解决方案:

Python 方案(使用PIL库)

先确保安装依赖:pip install pillow
原理:遍历每个像素,计算其到自定义原点的距离,根据距离缩放像素偏移量,模拟膨胀效果。

from PIL import Image
import math

def bloat_image_custom_origin(input_path, output_path, origin=(100, 150), strength=0.1):
    img = Image.open(input_path)
    width, height = img.size
    pixels = img.load()
    new_img = Image.new(img.mode, (width, height))
    new_pixels = new_img.load()

    for x in range(width):
        for y in range(height):
            # 计算当前像素到自定义原点的距离
            dx = x - origin[0]
            dy = y - origin[1]
            distance = math.hypot(dx, dy)
            
            # 根据距离计算偏移量,距离越远偏移越大(膨胀效果)
            offset_x = dx * strength * (distance / max(width, height))
            offset_y = dy * strength * (distance / max(width, height))
            
            # 确保新位置不超出图像范围
            new_x = int(x + offset_x)
            new_y = int(y + offset_y)
            new_x = max(0, min(new_x, width-1))
            new_y = max(0, min(new_y, height-1))
            
            new_pixels[x, y] = pixels[new_x, new_y]
    
    new_img.save(output_path)

# 使用示例
bloat_image_custom_origin("input.jpg", "output_python.jpg", origin=(200, 200), strength=0.2)

Node.js 方案(使用sharp库)

先安装依赖:npm install sharp
sharp是高性能图像处理库,这里通过操作像素缓冲区实现效果:

const sharp = require('sharp');

async function bloatImageCustomOrigin(inputPath, outputPath, origin = {x: 100, y: 150}, strength = 0.1) {
    const img = await sharp(inputPath).raw().toBuffer({resolveWithObject: true});
    const {data, info} = img;
    const {width, height, channels} = info;
    const newData = Buffer.alloc(data.length);

    for (let y = 0; y < height; y++) {
        for (let x = 0; x < width; x++) {
            const dx = x - origin.x;
            const dy = y - origin.y;
            const distance = Math.hypot(dx, dy);
            
            const offsetX = dx * strength * (distance / Math.max(width, height));
            const offsetY = dy * strength * (distance / Math.max(width, height));
            
            let newX = Math.round(x + offsetX);
            let newY = Math.round(y + offsetY);
            newX = Math.max(0, Math.min(newX, width - 1));
            newY = Math.max(0, Math.min(newY, height - 1));
            
            // 复制像素数据到新位置
            const srcIdx = (newY * width + newX) * channels;
            const destIdx = (y * width + x) * channels;
            for (let c = 0; c < channels; c++) {
                newData[destIdx + c] = data[srcIdx + c];
            }
        }
    }

    await sharp(newData, {raw: {width, height, channels}}).toFile(outputPath);
}

// 使用示例
bloatImageCustomOrigin('input.jpg', 'output_node.jpg', {x: 200, y: 200}, 0.2)
    .then(() => console.log('处理完成'))
    .catch(err => console.error(err));

PHP 方案(使用GD库)

确保PHP已启用GD扩展(大部分环境默认开启):

function bloatImageCustomOrigin($inputPath, $outputPath, $origin = [100, 150], $strength = 0.1) {
    $img = imagecreatefromjpeg($inputPath);
    $width = imagesx($img);
    $height = imagesy($img);
    $newImg = imagecreatetruecolor($width, $height);

    for ($x = 0; $x < $width; $x++) {
        for ($y = 0; $y < $height; $y++) {
            $dx = $x - $origin[0];
            $dy = $y - $origin[1];
            $distance = hypot($dx, $dy);
            
            $offsetX = $dx * $strength * ($distance / max($width, $height));
            $offsetY = $dy * $strength * ($distance / max($width, $height));
            
            $newX = (int)($x + $offsetX);
            $newY = (int)($y + $offsetY);
            $newX = max(0, min($newX, $width - 1));
            $newY = max(0, min($newY, $height - 1));
            
            $color = imagecolorat($img, $newX, $newY);
            imagesetpixel($newImg, $x, $y, $color);
        }
    }

    imagejpeg($newImg, $outputPath);
    imagedestroy($img);
    imagedestroy($newImg);
}

// 使用示例
bloatImageCustomOrigin('input.jpg', 'output_php.jpg', [200, 200], 0.2);

效果调整小技巧

  • 修改origin参数可设置任意非中心的膨胀原点
  • 调整strength参数控制膨胀强度,值越大效果越明显
  • 如果需要更细腻的效果,可以优化距离计算的权重公式,比如加入非线性的距离映射

内容的提问来源于stack exchange,提问作者Алекс Кирсанов

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 11:13:39