我是python和编写GIMP插件的新手。我正在尝试编写一个简单的插件来执行层名称的搜索/替换。我已经设法使它与"平面"gimp图像一起工作,但不知道如何使它在组中迭代工作。这是我的"平面"结构代码:
import math
import string
import re
from gimpfu import *
from array import array
def python_search_replace_layer_names(image, layer, searchterm, replaceterm, applyvisible, casesensative) :
pdb.gimp_image_undo_group_start(image)
pdb.gimp_context_push()
applylayers = []
for layer in image.layers[::-1]:
if (applyvisible == 0) or (layer.visible != 0): #user didn't check Only apply visible or if layer is visible.
applylayers.append([layer,counter])
for applylayer in applylayers:
if casesensative == 0:
searchtermRegEx = re.compile(re.escape(searchterm),re.IGNORECASE)
else:
searchtermRegEx = re.compile(re.escape(searchterm))
layername = searchtermRegEx.sub(replaceterm, str(applylayer[0].name))
applylayer[0].name = layername
pdb.gimp_context_pop()
pdb.gimp_image_undo_group_end(image)
pdb.gimp_displays_flush()
register(
"python_fu_search_replace_layer_names",
"Search/Replace in Layer Names",
"Search/Replace in Layer Names...",
"stigzler",
"stigzler",
"2020",
"<Image>/Edit/Search and Replace/Replace Layer Names...",
"RGB*, GRAY*",
[
(PF_STRING, "searchterm", "Search for Term:", "SearchTerm"),
(PF_STRING, "replaceterm", "Replace With:", "ReplaceWith"),
(PF_TOGGLE, "applyvisible", "Only Apply to visible layers:", 0),
(PF_TOGGLE, "casesensative", "Case sensative:", 0)
],
[],
python_search_replace_layer_names)
main()
我猜这将涉及一些迭代的、自引用的函数,但我只掌握了三点知识:
- 相关插件结构操作
- 不知道python的语法/结构(通常是.net,尽管我确信有很多相似之处(
- 不知道访问组结构的gimpapi
希望有人能帮忙!
更新:
多亏了xenoid的回答,解决了这个问题。如果你在这里寻找一个层重命名插件,你可以在这里找到完成的
其实很简单。我写了一些代码来转储图像的层次结构:
def dump(parent,level,dumpList):
prefix=' '*level
for pos,layerOrGroup in enumerate(parent.layers):
dumpList.append(prefix+layerOrGroup.name)
if isinstance(layerOrGroup,gimp.GroupLayer):
dump(layerOrGroup,level+1,dumpList)
def dumpLayerHierarchy(image):
dumpList=[]
dump(image,0,dumpList)
gimp.message('n'.join(dumpList))
需要知道的两件事:
- 层组是
gimp.GroupLayer
的实例(规则层是gimp.Layer
( - 在最佳情况下,
gimp.Image
和gimp.GroupLayer
都有layers
属性中的子级,因此您甚至不需要对从图像本身开始的第一级进行特殊处理
PS:更好的注册:
register(
"search-replace-layer-names",
"Search/Replace in Layer Names",
"Search/Replace in Layer Names...",
"stigzler",
"stigzler",
"2020",
"Replace Layer Names...",
"*",
[
(PF_IMAGE,"image", "Image:", None),
(PF_DRAWABLE, "drawable", "Drawable:", None),
(PF_STRING, "searchterm", "Search for Term:", "SearchTerm"),
(PF_STRING, "replaceterm", "Replace With:", "ReplaceWith"),
(PF_TOGGLE, "applyvisible", "Only Apply to visible layers:", 0),
(PF_TOGGLE, "casesensative", "Case sensative:", 0)
],
[],
python_search_replace_layer_names
menu="<Image>/Edit/Search and Replace/"
)
更改:
- 化妆品:让"原子"更标准。Gimp添加的"python fu">
- 将菜单声明更改为不推荐使用的类型,具有单独的菜单项和菜单位置
- 使图像类型
"*"
支持所有图像类型(您的代码不适用于索引图像( - 明确"图像"one_answers"可绘制"参数。这有时很有用。由于您可能无论如何都不使用layer/drawable,因此可以将其从参数列表(以及从函数原型(中删除
其他:
- 您不需要上下文推送/弹出,因为您不更改上下文
- 你不需要复制图像层(
image.layers[::-1]
(,甚至不需要反转它们,因为你只需要更新属性(如果你删除层,那就另当别论了( - 撤消组是好的,但您可以在try/except中将代码括起来,这样在出现问题时,撤消组将正确关闭,您仍然可以轻松地撤消部分更改:
import traceback # To still get source code location
def the_plugin(image,layer):
image.undo_group_start()
try:
# Your code goes here
except Exception as e:
trace(e.args[0])
gimp.message(e.args[0]+':'+traceback.format_exc())
image.undo_group_end()
您的代码,已修复:
import re,traceback
from gimpfu import *
def python_search_replace_layer_names(image,searchterm, replaceterm, applyvisible, casesensitive) :
image.undo_group_start()
try:
searchtermRegEx = re.compile(re.escape(searchterm),0 if casesensitive else re.IGNORECASE)
renameLayers(image,searchtermRegEx,replaceterm,applyvisible)
except Exception as e:
gimp.message(e.args[0]+':'+traceback.format_exc())
image.undo_group_end()
def renameLayers(parent,searchtermRegEx,replaceterm,applyvisible):
for pos,layerOrGroup in enumerate(parent.layers):
if not applyvisible or layerOrGroup.visible:
layerName = searchtermRegEx.sub(replaceterm, layerOrGroup.name)
layerOrGroup.name = layerName
if isinstance(layerOrGroup,gimp.GroupLayer):
renameLayers(layerOrGroup,searchtermRegEx,replaceterm,applyvisible)
register(
"search-replace-layer-names",
"Search/Replace in Layer Names",
"Search/Replace in Layer Names...",
"stigzler",
"stigzler",
"2020",
"Replace Layer Names...",
"*",
[
(PF_IMAGE,"image", "Image:", None),
(PF_STRING, "searchterm", "Search for Term:", "SearchTerm"),
(PF_STRING, "replaceterm", "Replace With:", "ReplaceWith"),
(PF_TOGGLE, "applyvisible", "Only Apply to visible layers:", 0),
(PF_TOGGLE, "casesensitive", "Case sensative:", 0)
],
[],
python_search_replace_layer_names,
menu="<Image>/Edit/Search and Replace/")
main()
修复:
- 在注册中的
python_search_replace_layer_names
末尾添加缺少的逗号 - 已添加
traceback
导入 - 删除了对
trace
函数的调用(仅在我自己的代码中( - 取消了许多不必要的进口
- 已将
layer
参数删除到插件函数 - 将
level
参数删除到递归函数 - 一些代码变得更像蟒蛇
此外,组中的层可能是不可见的,因为它本身是不可见(layer.visible
为false(,或者因为组是不可见。您当前的代码没有考虑组诱导的不可见性。
最后,可以在这里找到一些调试Gimp-python脚本的提示(重点是Windows(。