I’m building a plugin for Krita that allows editing text layers in an external application. Currently, my workflow for updating vector layer text is:
- Extract text - Read SVG content from the
.krafile (which is a ZIP archive) by accessinglayers/[layer].shapelayer/content.svg - Parse and modify - Parse the SVG XML, find
<text>and<tspan>elements, and replace their text content using regex-based replacement to preserve Krita’s specific XML formatting - Update the .kra file:
- Modify the SVG files
- Close the document (
doc.close()) - Reopen the document (
openDocument(kra_path)) - Add it back to the active window (
addView(new_doc))
The Problem:
- It requires closing and reopening the document
- User loses their current view/zoom position
- Maybe slow for multiple documents update
Questions:
- Is there a proper way to use Krita API to live-update vector layer content without document reload?
Update:
- Does following workaround works?(have not tested yet)
- Get all shapes:
shapes = layer.shapes() - Get SVG for each shape:
svg_content = shape.toSvg() - Modify the SVG: Parse and update the text content
- Remove old shape:
shape.remove() - Add modified shape:
layer.addShapesFromSvg(modified_svg)
- Get all shapes:
import sys
from krita import *
doc = Application.activeDocument()
root = doc.rootNode()
for layer in root.childNodes():
if (str(layer.type())=="vectorlayer"):
for shape in layer.shapes():
print(shape.name())
print(shape.toSvg())
shape0
<text fill="#000000" stroke-opacity="0" stroke="#000000" stroke-width="0" stroke-linecap="square" stroke-linejoin="bevel" paint-order="stroke fill markers" style="inline-size: 391.69;font-size: 20;white-space: pre-wrap;">Second Text
Test2
NewLine
NewLine2</text>
shape1
<text fill="#000000" stroke-opacity="0" stroke="#000000" stroke-width="0" stroke-linecap="square" stroke-linejoin="bevel" paint-order="stroke fill markers" style="inline-size: 292.429614181439;font-size: 20;white-space: pre-wrap;"><tspan>Second Text
</tspan><tspan style="font-size: 24;">Test2</tspan></text>
shape0
<text fill="#000000" stroke-opacity="0" stroke="#000000" stroke-width="0" stroke-linecap="square" stroke-linejoin="bevel" paint-order="stroke fill markers" style="inline-size: 277.451511991658;font-size: 22;white-space: pre-wrap;">Second Layer123
Test1
Test2 234
123</text>

