返回列表 发帖

[文本处理] 有偿求批量圆形图片变方形!!!!

各位大佬,
求一个能批量把如下图圆形图片无损变方形,方形无损变圆形的批处理,不要那种简单裁切,要不损失图片内容的变形。谢谢!
[img][/img]

先看看版规,然后最好能给出几个测试原文件。

TOP

啊 ,反过来还好说
这圆形变方形 ,涉及图像复原技术 ,建议直接网上搜索图形修复 ,看看有啥现成的东西

TOP

圆形变方形
读取第一个透明度不为0的像素的颜色为背景色
新建个方形,把圆形粘贴上去

QQ 20147578

TOP

回复 4# czjt1234


    是用PS吗?有没有简单一些的软件或者批处理?

TOP

回复 3# Five66


    应该不涉及修复,PS中的变形就可以做到,但比较麻烦

TOP

1. 把当前目录的矩形图片变圆形图片,"矩形变圆形.ps1.bat"
<#*,:
@echo off&cd /d "%~dp0"&set "batchfile=%~f0"
powershell -ExecutionPolicy Bypass -C "Set-Location -LiteralPath ([Environment]::CurrentDirectory);. ([ScriptBlock]::Create([IO.File]::ReadAllText($env:batchfile,[Text.Encoding]::GetEncoding(0) )) )"
pause
exit /b
#>
# convert rectangle to ellipse
Add-Type -AssemblyName System.Drawing
Get-ChildItem -Filter *.png | Where-Object { $_ -is [IO.FileInfo] } | ForEach-Object {
  try {
    $_.Name
    $bytes = [IO.File]::ReadAllBytes($_.FullName)
    $memstream = New-Object System.IO.MemoryStream -ArgumentList (, $bytes)
    $bmp = New-Object System.Drawing.Bitmap -ArgumentList ($memstream)
    $width = $bmp.Width
    $height = $bmp.Height
    $a = $width / 2
    $b = $height / 2
    $centerX = $width / 2
    $centerY = $height / 2
    foreach ($x in 0..($width - 1)) {
      foreach ($y in 0..($height - 1)) {
        # // 椭圆公式: (x - centerX)^2 / a^2 + (y - centerY)^2 / b^2 > 1
        $equation = [Math]::Pow($x - $centerX, 2) / [Math]::Pow($a, 2) + [Math]::Pow($y - $centerY, 2) / [Math]::Pow($b, 2)
        if ($equation -gt 1) {
          $color = $bmp.GetPixel($x, $y)
          # NOTE:Both System.Drawing and imagemagick will set RGB channel to 0 when alpha channel is 0.
          $transparent_color = [System.Drawing.Color]::FromArgb(1, $color.R, $color.G, $color.B)
          $bmp.SetPixel($x, $y, $transparent_color)
        }
      }
    }
    $bmp.Save($_.FullName)
  } finally {
    if ($memstream) { $memstream.Close() }
    if ($bmp) { $bmp.Dispose() }
  }
}COPY
2.把当前目录的圆形图片变矩形图片,"圆形变矩形.ps1.bat"
<#*,:
@echo off&cd /d "%~dp0"&set "batchfile=%~f0"
powershell -ExecutionPolicy Bypass -C "Set-Location -LiteralPath ([Environment]::CurrentDirectory);. ([ScriptBlock]::Create([IO.File]::ReadAllText($env:batchfile,[Text.Encoding]::GetEncoding(0) )) )"
pause
exit /b
#>
# convert ellipse to rectangle
Add-Type -AssemblyName System.Drawing
Get-ChildItem -Filter *.png | Where-Object { $_ -is [IO.FileInfo] } | ForEach-Object {
  try {
    $_.Name
    $bytes = [IO.File]::ReadAllBytes($_.FullName)
    $memstream = New-Object System.IO.MemoryStream -ArgumentList (, $bytes)
    $bmp = New-Object System.Drawing.Bitmap -ArgumentList ($memstream)
    $width = $bmp.Width
    $height = $bmp.Height
    $a = $width / 2
    $b = $height / 2
    $centerX = $width / 2
    $centerY = $height / 2
    foreach ($x in 0..($width - 1)) {
      foreach ($y in 0..($height - 1)) {
        $equation = [Math]::Pow($x - $centerX, 2) / [Math]::Pow($a, 2) + [Math]::Pow($y - $centerY, 2) / [Math]::Pow($b, 2)
        if ($equation -gt 1) {
          $color = $bmp.GetPixel($x, $y)
          # NOTE:Both System.Drawing and imagemagick will set RGB channel to 0 when alpha channel is 0.
          $transparent_color = [System.Drawing.Color]::FromArgb(255, $color.R, $color.G, $color.B)
          $bmp.SetPixel($x, $y, $transparent_color)
        }
      }
    }
    $bmp.Save($_.FullName)
  } finally {
    if ($memstream) { $memstream.Close() }
    if ($bmp) { $bmp.Dispose() }
  }
}COPY
3

评分人数

微信:flashercs
QQ:49908356

TOP

回复 7# flashercs
感谢大佬出手帮忙!我反馈一下结果,圆变方,实验了三张均没有成功。方变圆,实验两张,有一张成功了。
请大佬麻烦再帮忙看看,非常感谢您!敬礼!!

    [img][/img]

[img][/img]

TOP

回复 6# duoduo200


    方形变圆形 ,图片内容就丢失了 ,要变回方形 ,不用图像复原技术怎么把丢失的弄回来???  
复原的话 ,简单点的还好 ,可以自己弄 ,但是复杂点的 ,要保持效果 ,还得用上深度学习
photoshop能弄是因为人家有对应的复原算法将图片修复
另外photoshop有自动化对象 ,叫photoshop.application ,可用vbs ,jscript ,powershell之类进行自动化操作 ,可以网上搜搜看看能不能使用photoshop的自动化对象用vbs ,jscript ,powershell之类自动修复

TOP

传几张图片到网盘给人家测试

QQ 20147578

TOP

回复 7# flashercs


    大佬,这是测试圆形和方形图片样张,谢谢。

链接: https://pan.baidu.com/s/16hkeqbYC8qWt44RDCucvFg?pwd=8mkx 提取码: 8mkx

TOP

回复 10# czjt1234


    感谢指导,谢谢!

TOP

回复 9# Five66


    感谢您的指导!非常感谢&#128591;

TOP

参考7楼的简单写了一下,不过发现你的原图有灰边,处理灰边System.Drawing可能力有未逮。
填充透明像素为矩形:
<#*,:
@echo off&cd /d "%~dp0"&set "batchfile=%~f0"
powershell -ExecutionPolicy Bypass -C "Set-Location -LiteralPath ([Environment]::CurrentDirectory);. ([ScriptBlock]::Create([IO.File]::ReadAllText($env:batchfile,[Text.Encoding]::GetEncoding(0) )) )"
pause
exit /b
#>
Add-Type -AssemblyName System.Drawing
Get-ChildItem -Path . -Filter *.png -File | ForEach-Object {
    try {
        Write-Host "处理文件: $($_.Name)" -ForegroundColor Cyan
        $bytes = [IO.File]::ReadAllBytes($_.FullName)
        $memstream = New-Object System.IO.MemoryStream -ArgumentList (, $bytes)
        $bitmap = New-Object System.Drawing.Bitmap -ArgumentList ($memstream)
        $grayTolerance = 10
        $colorCount = @{}
        for ($y = 0; $y -lt $bitmap.Height; $y++) {
            for ($x = 0; $x -lt $bitmap.Width; $x++) {
                $color = $bitmap.GetPixel($x, $y)
                if ($color.A -gt 0) {
                    if ($colorCount.ContainsKey($color)) {
                        $colorCount[$color]++
                    } else {
                        $colorCount[$color] = 1
                    }
                }
            }
        }
        if ($colorCount.Count -eq 0) {
            Write-Warning "警告:$($_.Name) 中无图像,跳过处理"
            continue
        }
        $mostColor = $colorCount.GetEnumerator() | Sort-Object -Property Value -Descending | Select-Object -First 1 -ExpandProperty Key
        $centerX = $bitmap.Width / 2
        $centerY = $bitmap.Height / 2
        $shortestRadius = 0
        for ($y = 0; $y -lt $bitmap.Height; $y++) {
            for ($x = 0; $x -lt $bitmap.Width; $x++) {
                $color = $bitmap.GetPixel($x, $y)
                if ($color.A -gt 0 -and $color -ne $mostColor) {
                    $isGray = [Math]::Abs($color.R - $color.G) -le $grayTolerance -and [Math]::Abs($color.G - $color.B) -le $grayTolerance -and [Math]::Abs($color.R - $color.B) -le $grayTolerance
                    if (-not $isGray) {
                        $distance = [Math]::Sqrt([Math]::Pow($x - $centerX, 2) + [Math]::Pow($y - $centerY, 2))
                        if ($distance -gt $shortestRadius) {
                            $shortestRadius = $distance
                        }
                    }
                }
            }
        }
        $newBitmap = New-Object System.Drawing.Bitmap $bitmap.Width, $bitmap.Height
        for ($y = 0; $y -lt $bitmap.Height; $y++) {
            for ($x = 0; $x -lt $bitmap.Width; $x++) {
                $originalColor = $bitmap.GetPixel($x, $y)
                $distance = [Math]::Sqrt([Math]::Pow($x - $centerX, 2) + [Math]::Pow($y - $centerY, 2))
                if ($originalColor.A -eq 0 -or $distance -gt $shortestRadius) {
                    $newColor = [System.Drawing.Color]::FromArgb(255, $mostColor.R, $mostColor.G, $mostColor.B)
                    $newBitmap.SetPixel($x, $y, $newColor)
                } else {
                    $newBitmap.SetPixel($x, $y, $originalColor)
                }
            }
        }
        $newFileName = [IO.Path]::ChangeExtension($_.Name, "_filled.png")
        $newBitmap.Save($newFileName, [System.Drawing.Imaging.ImageFormat]::Png)
        Write-Host "保存为: $newFileName" -ForegroundColor Green
    } finally {
        if ($memstream) { $memstream.Close() }
        if ($bitmap) { $bitmap.Dispose() }
        if ($newBitmap) { $newBitmap.Dispose() }
    }
}
Write-Host "处理完成!" -ForegroundColor GreenCOPY

TOP

感觉难点在于处理圆形的灰边,和方形的四角的边框

QQ 20147578

TOP

返回列表