Salta fins al contingut

Aprofundim en el connector «Neteja ràpida de l'esbós» per a Krita

Publicació anterior | Divendres, 20 de desembre de 2024 | Temps de lectura: 13 minuts |

Connector «Neteja ràpida de l'esbós»

Introducció

Vam començar este projecte amb la intenció de proporcionar als usuaris una eina útil per a entintar els esbossos. Es basa en un article de recerca de Simo & Sierra publicat el 2016 i utilitza les xarxes neuronals (ara anomenades senzillament IA) per a funcionar. L'eina s'ha desenvolupat en associació amb Intel i encara es considera experimental, però ja es pot utilitzar i veure els resultats.

En la secció següent, hi ha alguns exemples de casos d'ús reals i els resultats del connector. Els resultats varien, però es pot utilitzar per a extraure esbossos febles de llapis des de fotografies, netejar línies i entintar còmics.

Pel que fa al model utilitzat a l'eina, l'entrenem nosaltres mateixos. Totes les dades del conjunt de dades són donades per persones que ens han enviat les seues imatges i han sigut d'acord amb este cas d'ús específic. No hem utilitzat cap altra dada. A més, quan utilitzeu el connector, este processa localment a la vostra màquina, no requerix cap connexió amb Internet, no es connecta amb cap servidor i tampoc es requerix cap compte. Actualment només funciona a Windows i Linux, però treballarem perquè també estiga disponible a MacOS.

Casos d'ús

Fa una mitjana de les línies en una de sola línia i crea línies negres fortes, però el resultat final pot ser difuminat o desigual. No obstant açò, en molts casos, seguix funcionant millor que utilitzar un filtre de «Nivells» (per exemple, quan s'extrau l'esbós a llapis). Pot ser una bona idea utilitzar el filtre de «Nivells» després d'utilitzar el connector per a reduir el difuminat. Atés que el connector funciona millor amb un llenç en blanc i línies de color gris fosc, en el cas d'esbossos a llapis fotografiats o de línies d'esbós molt clares, pot ser una bona idea utilitzar també «Nivells» abans d'utilitzar el connector.

Extracció d'un esbós a llapis fotografiat

Este és el resultat del procediment estàndard d'utilitzar el filtre de «Nivells» sobre un esbós per a extraure les línies (el qual resulta en que una part de la imatge rebrà ombra):

Comparació del procediment amb l'esbós original d'una xica

Comparació del procediment amb l'esbós original d'una xica a 1843×1209 165 KB

L'esbós l'ha realitzat en Tiar (enllaç cap al perfil de KA).

Este és el procediment que se seguix amb el connector SketchyModel (Nivells → «connector» → Nivells):

Comparació del procediment amb l'esbós nou d'una xica

Comparació del procediment amb l'esbós nou d'una xica a 1843×2419 267 KB

Comparació (per a les línies negres):

Comparació del procediment amb l'esbós d'una xica

Comparació del procediment amb l'esbós d'una xica a 1920×1260 215 KB

Un altre resultat possible és senzillament parar al connector sense forçar les línies negres utilitzant «Nivells», el qual resultarà en una aparença més agradable i pareixent a un llapis mentre encara es manté la part inferior de la pàgina en blanc:

Esbós d'una xica després del connector

Esbós d'una xica després del connector a 1536×2016 161 KB

Entintat pareixent a un llibre de còmic


Imatge d'un home feta per en BeARToys

A les imatges de dalt es pot veure l'entintat a l'estil dels còmics. El resultat, el qual està una mica difuminat en comparació amb l'original, es pot millorar encara més utilitzant un filtre d'«Agudització». El drac l'ha esbossat en David Revoy (CC-BY 4.0).

Neteja de les línies

Exemples d'esbossos que he fet i el resultat del connector, mostren els punts forts i febles. Totes les imatges de davall s'han realitzar utilitzant l'SketchyModel.

flower_001

flower_0011209×739 46.5 KB

flower_001_detail

flower_001_detail681×456 22.1 KB

portrait_man_portrait_2_comparison_2_small

portrait_man_portrait_2_comparison_2_small1305×505 139 KB

portrait_man_portrait_2_detail

portrait_man_portrait_2_detail646×1023 26.6 KB

Totes les imatges de dalt les ha realitzat en Tiar (enllaç cap al perfil de KA).

A les imatges que apareixen a continuació, a les escates dels peixos, es pot veure com el model discrimina les línies més fines i realça les més fortes, fent que les escates estiguen més pronunciades. En teoria, açò es podria fer utilitzant el filtre «Nivells», però a la pràctica els resultats serien pitjors, perquè el model té en compte la força local de la línia.


fish_square_sketchy_comparison_small1920×968 156 KB

Imatge del peix realitzada per na Christine Garner (enllaç amb la cartera).

Com utilitzar-lo a Krita

Per a utilitzar el connector «Neteja ràpida de l'esbós» a Krita, feu el següent:

  1. Prepareu Krita:
    1. En Windows:
      1. En un sol paquet: baixeu Krita 5.3.0-prealpha amb el connector «Neteja ràpida de l'esbós» ja inclòs: https://download.kde.org/unstable/krita/5.3.0-prealpha-fast-sketch/krita-x64-5.3.0-prealpha-cdac9c31.zip
      2. O per separat:
        1. Baixeu la versió portable de Krita 5.2.6 (o una versió similar -hauria de seguir funcionant-).
        2. Baixeu ací per separat el connector «Neteja ràpida de l'esbós»: https://download.kde.org/stable/krita/FastSketchPlugin-1.0.2/FastSketchPlugin1.0.2.zip
        3. Descomprimiu el fitxer a dins de la carpeta krita-5.2.6/ (mantenint l'estructura de les carpetes).
        4. Després, aneu fins a «Configuració → Configura Krita → Gestor de connectors en Python», activeu el connector «Neteja ràpida de l'esbós» i reinicieu Krita.
    2. En Linux:
      1. Baixeu l'AppImage: https://download.kde.org/unstable/krita/5.3.0-prealpha-fast-sketch/krita-5.3.0-prealpha-cdac9c31c9-x86_64.AppImage
  2. (Opcional) Instal·leu els controladors de NPU si teniu una NPU al vostre dispositiu (pràcticament només és necessari a Linux, si teniu una CPU d'Intel molt nova): Configuracions per a les NPU d'Intel® amb OpenVINO™ -Documentació d'OpenVINO™ (nota: encara podreu executar el connector a la CPU o GPU, no es requerix una NPU).
  3. Execució del connector:
    1. Obriu o creeu un llenç en blanc amb els traços en gris i blanc (cal tindre en compte que el connector prendrà la projecció actual del llenç, no la capa actual).
    2. Aneu fins a «Eines → Neteja ràpida de l'esbós».
    3. Seleccioneu el model. Les «Opcions avançades» se seleccionaran de manera automàtica.
    4. Espereu fins que acabe el processament (el diàleg es tancarà automàticament).
    5. Vegeu que s'ha creat una capa nova amb el resultat.

Consells per al processament

Actualment és millor utilitzar el SketchyModel.xml, en la majoria dels casos funciona significativament millor que el SmoothModel.xml.

Heu d'assegurar-vos que el fons és força brillant, i les línies que voleu mantenir en el resultat són relativament fosques (sigui una mica gris fosc o negre; el gris clar podria donar com a resultat moltes línies perdudes). Pot ser una bona idea utilitzar un filtre com Nivells abans.

Després del processament, és possible que vulgueu millorar els resultats amb el filtre Nivells o el filtre Aguditza, depenent del resultat.

Base de ciència i tecnologia

Requisits únics

El primer requisit únic era que havia de funcionar sobre llenços de totes les mides. Això significava que la xarxa no podia tenir capes lineals denses/plenes o densament connectades que són molt habituals en la majoria de les xarxes neuronals de processament d'imatges (que requereixen una entrada d'una mida específica i produiran resultats diferents per al mateix píxel depenent de la seva ubicació), només convolucions o capes d'agrupació o similars que produeixin els mateixos resultats per a cada píxel del llenç, independentment de la ubicació. Afortunadament, el article de Simo Sierra publicat el 2016 va descriure una xarxa així.

Un altre repte era que realment no podíem utilitzar el model que van crear, ja que no era compatible amb la llicència del Krita, i ni tan sols podíem utilitzar realment el tipus de model exacte que van descriure, perquè un d'aquests fitxers del model seria gairebé tan gran com el Krita, i l'entrenament trigaria molt temps. Necessitàvem alguna cosa que funcionés igual de bé o millor, però prou petit perquè es pogués afegir al Krita sense fer-lo el doble de gran. (En teoria, podríem fer com altres empreses i fer que el processament es faci en algun tipus de servidor, però això no era el que volíem. I fins i tot si resolgués alguns dels problemes, aportaria molts dels seus propis grans reptes. A més, volíem que els usuaris el poguessin utilitzar localment sense dependre dels nostres servidors i d'internet). A més, el model havia de ser raonablement ràpid i també modest pel que fa al consum de RAM/VRAM.

A més, no teníem cap conjunt de dades que poguéssim utilitzar. Simo Sierra va utilitzar un conjunt de dades, on les imatges esperades es dibuixaven utilitzant una amplada de línia constant i transparència, el que significava que els resultats de l'entrenament també tenien aquestes qualitats. Volíem una cosa que es veiés una mica més dibuixat a mà, amb línies d'amplada variable o extrems semitransparents a les línies, de manera que el nostre conjunt de dades havia de contenir aquest tipus d'imatges. Com que no érem conscients de cap conjunt de dades que coincidís amb els nostres requisits pel que fa a la llicència i el procés de recopilació de dades, hem demanat ajuda a la nostra pròpia comunitat, aquí podeu llegir el fil del Krita: https://krita-artists.org/t/call-for-donation-of-artworks-for-the-fast-line-art-project/96401.

L'enllaç al nostre conjunt de dades complet es pot trobar a continuació a l'apartat Conjunt de dades.

Arquitectura del model

Totes les capes principals són convolucionals o desconvolucionals (al final del model). Després de cada capa des/convolucional excepte l'última hi ha una capa d'activació ReLu, i després de l'última convolució hi ha una capa d'activació sigmoide.

Paquets utilitzats del Python: Pillow, Numpy, PyTorch i Openvino

Numpy és una biblioteca estàndard per a tot tipus de matrius i operacions de matrius avançades i utilitzem Pillow per llegir imatges i convertir-les en matrius «numpy» i al revés. Per a l'entrenament, utilitzem PyTorch, mentre que en el connector del Krita utilitzem Openvino per a la inferència (processament a través de la xarxa).

Ús de la NPU per a la inferència


Aquesta taula mostra el resultat de benchmark_app, que és una eina que es proporciona amb el paquet Python openvino d'Intel. Prova el model de forma aïllada sobre dades aleatòries. Com podeu veure, la NPU fou diverses vegades més ràpida que la CPU de la mateixa màquina.

D'altra banda, la introducció de les NPU afegeix un repte: els únics models que es poden executar en una NPU són models estàtics, el que significa que la mida d'entrada es coneix en el moment de desar el model al fitxer. Per a resoldre això, el connector primer talla el llenç en parts més petites d'una mida especificada (que depèn del fitxer de model), i després procedeix a processar-les totes i finalment cosir els resultats junts. Per a evitar defectes en les zones al costat de la costura, totes les parts es tallen amb una mica de marge i el marge es retalla més tard.

Com entrenar el vostre model propi

Per entrenar el vostre model propi, necessitareu algunes habilitats tècniques, parells d'imatges (entrada i sortida esperada) i un ordinador potent. És possible que també necessiteu molt espai al disc dur, encara que podeu eliminar models antics innecessaris si comenceu a tenir problemes amb la manca d'espai.

Controladors i preparació

Haureu d'instal·lar el Python3 i els paquets següents: Pillow, openvino, numpy, torch. Per a la quantificació del model també necessitareu nncf i sklearn. Si manca alguna cosa, es queixarà, així que també cal instal·lar els paquets que s'esmentin.

Si esteu al Windows, probablement teniu controladors per a la NPU i la GPU dedicada. Al Linux, és possible que calgui instal·lar els controladors de la NPU abans de poder utilitzar-lo: https://docs.openvino.ai/2024/get-started/configurations/configurations-intel-npu.html.

A més, si voleu utilitzar iGPU per a l'entrenament (que encara podria ser significativament més ràpid que a la CPU), probablement necessitareu utilitzar alguna cosa com IPEX que permet al PyTorch utilitzar un dispositiu «XPU», que és el vostre iGPU. No s'ha provat o recomanat, ja que personalment no he pogut utilitzar-lo perquè la meva versió del Python era més alta del que espera la instrucció, però la instrucció és aquí: https://pytorch-extension.intel.com/installation?platform=gpu&version=v2.5.10%2Bxpu .
La comprovació de sanejament per a la instal·lació és la següent:
python3 -c "import torch; import intel_extension_for_pytorch as ipex; print(f'Packages versions:'); print(f'Torch version: {torch.__version__}'); print(f'IPEX version: {ipex.__version__}'); print(f'Devices:'); print(f'Torch XPU device count: {torch.xpu.device_count()}'); [print(f'[Device {i}]: {torch.xpu.get_device_properties(i)}') for i in range(torch.xpu.device_count())];"
Hauria de mostrar més de 0 dispositius amb algunes propietats bàsiques.

Si aconseguiu que el dispositiu XPU funcioni a la vostra màquina, encara necessitareu editar els scripts d'entrenament perquè puguin utilitzar-lo: https://intel.github.io/intel-extension-for-pytorch/xpu/latest/tutorials/getting_started.html (probablement només haureu d'afegir aquesta línia:
import intel_extension_for_pytorch as ipex
a la part superior de l'script, just a sota d'«import torch», i utilitzeu «xpu» com a nom de dispositiu quan invoqueu l'script, i hauria de funcionar. Però com he dit, els scripts no s'han provat per això.

Conjunt de dades

Necessitareu algunes imatges per a poder entrenar el model. Les imatges han de ser per parelles, cada parell ha de contenir un esbós (entrada) i una imatge d'art lineal (sortida esperada). A més qualitat del conjunt de dades, millors resultats.

Abans de l'entrenament, és millor si augmenteu les dades: això vol dir que les imatges es giren, s'escalen cap amunt o cap avall, i es reflecteixen. Actualment, el script d'augment de dades també realitza una inversió amb la suposició que l'entrenament en imatges invertides portaria els resultats més ràpid (considerant que el negre significa zero o que no hi ha cap senyal, i ens agradaria que aquest fos el fons, de manera que els models aprenen les línies, no el fons al voltant de les línies).

A continuació s'explica com utilitzar el script d'augment de dades, en la instrucció detallada de la part d'entrenament.

Aquest és el conjunt de dades que hem utilitzat (si us plau, llegiu la llicència atentament si el voleu utilitzar): https://files.kde.org/krita/extras/FastSketchCleanupPluginKritaDataset.zip

Elecció del model i altres paràmetres

Per a resultats ràpids, utilitzeu «tooSmallConv»; si teniu més temps i recursos, el «typicalDeep» podria ser una idea millor. Si teniu accés a una màquina GPU potent, podríeu provar «original» o «originalSmaller», que representen la descripció original del model de l'article SIGGRAPH de Simo-Sierra 2016, i una versió més petita d'aquest.

Utilitza «adadelta» com a optimitzador.

Podeu utilitzar «blackWhite» o «mse» com a funció de pèrdua; «mse» és clàssic, però «blackWhite» pot portar a resultats més ràpids, ja que redueix l'error relatiu a les àrees completament blanques o completament negres (basat en la imatge de sortida esperada).

Entrenament

  1. Cloneu el repositori de https://invent.kde.org/tymond/fast-line-art (a 33869b6)
    git clone https://invent.kde.org/tymond/fast-line-art.git

  2. Després, prepareu la carpeta:

    • Creeu una carpeta nova per a l'entrenament.
    • A la carpeta, executeu:
      python3 [repository folder]/spawnExperiment.py --path [camí a la carpeta nova, sigui relatiu o absolut] --note "[la vostra nota personal sobre l'experiment]"
  3. Prepareu les dades:

    • Si teniu un conjunt de dades augmentat existent, poseu-ho tot a data/training/ i data/verify/, tenint en compte que les imatges aparellades a ink/ i sketch/ subcarpetes han de tenir els mateixos noms exactes (per exemple, si teniu sketch.png i ink.png com a dades, heu de posar-ne un a sketch/ com a imatge.png i un altre a tinta/ com a imatge.png per a aparellar-les).
    • Si no teniu un conjunt de dades augmentat existent:
      1. Poseu totes les vostres dades en brut a data/raw/, tenint en compte que les imatges aparellades haurien de tenir els mateixos noms amb prefix afegit ja sigui ink_ o sketch_ (per exemple si teniu imatge_1.png sent la imatge d'esbós i imatge_2.png sent la imatge de tinta, heu d'anomenar-les sketch_imatge.png i ink_imatge.png respectivament.)
      2. Executeu l'script de preparació de dades:
        python3 [carpeta de repositori]/dataPreparer.py -t taskfile.yml
        Això augmentarà les dades al directori RAW perquè l'entrenament tingui més èxit.
  4. Editeu el fitxer taskfile.yml al vostre gust. Les parts més importants que voldreu canviar són:

    • model type - nom de codi del tipus de model, utilitzeu «tinyTinier», «tooSmallConv», «typicalDeep» o «tinyNarrowerShallow»
    • optimizer - tipus d'optimitzador, utilitzeu «adadelta» o «sgd»
    • learning rate - taxa d'aprenentatge per al «sgd» si s'utilitza
    • loss function - nom de codi de la funció de pèrdua, utilitzeu «mse» per a l'error quadrat mitjà o «blackWhite» per a una funció de pèrdua personalitzada basada en «mse», però una mica més petita per als píxels on el valor del píxel de la imatge de destinació és proper a 0,5
  5. Executeu el codi d'entrenament:
    python3 [carpeta de repositori]/train.py -t taskfile.yml -d "cpu"

    Al Linux, si voleu que s'executi en segon pla, afegiu «&» al final. Si s'executa en primer pla, podeu fer una pausa a l'entrenament prement ctrl+C, i si s'executa en segon pla, cerqueu un ID de procés (usant l'ordre «jobs -l» o l'ordre «ps aux | grep train.py», el primer número seria l'ID de procés) i mateu-lo utilitzant l'ordre «kill [ID de procés]». Els resultats seguiran a la carpeta i podreu reprendre l'entrenament amb la mateixa ordre.

  6. Convertiu el model en un model openvino:
    python3 [carpeta de repositori]/modelConverter.py -s [mida de l'entrada, recomanem 256] -t [nom del model d'entrada, a partir del pytorch] -o [nom de model openvino, cal que acabi amb .xml]

  7. Col·loqueu els fitxers de model .xml i .bin a la carpeta de recursos del Krita (dins de la subcarpeta pykrita/fast_sketch_cleanup) al costat d'altres models per a utilitzar-los al connector.