[{"data":1,"prerenderedAt":27},["ShallowReactive",2],{"note-from-a-plugin-file-to-a-page-ca":3},{"slug":4,"order":5,"title":6,"summary":7,"measured":8,"topic":9,"toc":10,"html":26},"from-a-plugin-file-to-a-page",70,"D'un fitxer de plugin a una pàgina a la pantalla","Cinc etapes converteixen un fitxer CLAP o LV2 en una fila de menú amb les seves xifres, pàgines de controls i una MOD GUI en un Zynthian. Cada etapa té un sol responsable, escriu un sol artefacte en un lloc fix i les etapes següents llegeixen aquest artefacte i res més.","plugin-hostd, plugin-qualify i omx-panel en una Raspberry Pi 5 amb Zynthian, octubre del 2026.","zynthian",[11,14,17,20,23],{"id":12,"title":13},"1-explorar-i-descriure","1. Explorar i descriure",{"id":15,"title":16},"2-qualificar","2. Qualificar",{"id":18,"title":19},"3-empremtes","3. Empremtes",{"id":21,"title":22},"4-disposicio","4. Disposició",{"id":24,"title":25},"5-llegir-a-l-aparell","5. Llegir a l'aparell","\u003Cp>Un instrument en un Zynthian és un fitxer al disc: un binari CLAP o LV2. El que veu qui toca és una fila en un menú amb les\nseves xifres, una cadena amb una entrada MIDI, pàgines de controls amb potenciòmetres, una MOD GUI i un peu de pàgina que\ndiu què costarà la cadena. Cinc etapes converteixen l'un en l'altre. Cada etapa té un sol responsable, escriu un sol\nartefacte en un lloc fix i el que ve després llegeix aquest artefacte i res més.\u003C\u002Fp>\n\u003Cp>L'exemple és un instrument: \u003Ca href=\"https:\u002F\u002Fgithub.com\u002FDISTRHO\u002FKars\">Kars\u003C\u002Fa>, un sintetitzador LV2 de corda pinçada, a les captures\nde l'aparell; Surge XT (CLAP) on importen les seves xifres; i un efecte una vegada, per mostrar on canvia la disposició.\u003C\u002Fp>\n\u003Cp>\u003Cimg src=\"\u002Ftechnical-notes\u002Ffrom-a-plugin-file-to-a-page\u002Ffrom-file-to-page.svg\" alt=\"Les cinc etapes, l'artefacte que escriu cadascuna i les superfícies que els llegeixen\">\u003C\u002Fp>\n\u003Ch2 id=\"1-explorar-i-descriure\">1. Explorar i descriure\u003C\u002Fh2>\n\u003Cp>\u003Cstrong>Responsable:\u003C\u002Fstrong> plugin-hostd. \u003Cstrong>Escriu:\u003C\u002Fstrong> el descriptor, un document JSON per binari de plugin a\n\u003Ccode>\u002Fvar\u002Flib\u002Fomx\u002Fdescriptors\u003C\u002Fcode>, amb el nom \u003Ccode>&lt;id&gt;@&lt;version&gt;-&lt;hash&gt;.json\u003C\u002Fcode>.\u003C\u002Fp>\n\u003Cp>El dimoni carrega el plugin una vegada a l'amfitrió que li correspon (omx-clap-host per a CLAP i per als plugins LV2 que\npren el seu adaptador, mod-host per a la resta) i en llegeix tot el que declara: l'identificador i la versió, els ports\nd'àudio i MIDI, cada paràmetre amb símbol, nom, unitat, rang, valor per defecte, passos o enumeració, indicadors, la\nlatència declarada i les extensions que admet.\u003C\u002Fp>\n\u003Cp>Per a un instrument, el descriptor diu el que no diu el d'un efecte: un port d'entrada MIDI i per tant les notes que\naccepta, els seus paràmetres i els seus presets. El descriptor de Kars té els tres paràmetres que el motor mostra després a\nla seva única pàgina: Sustain, Release i Volume.\u003C\u002Fp>\n\u003Cp>El descriptor ha d'encaixar amb el contracte: omx-contract en defineix el vocabulari (unitats, tipus de port, àmbits,\ncodis de resultat) i una exploració que troba una unitat o un camp desconeguts es refusa, no s'inventa. Els plugins\nd'OpenMixer se salten l'exploració: els seus paràmetres s'escriuen una sola vegada en una declaració i un generador n'escriu\nel descriptor, el paquet LV2, els paràmetres CLAP i la referència de paràmetres.\u003C\u002Fp>\n\u003Ch2 id=\"2-qualificar\">2. Qualificar\u003C\u002Fh2>\n\u003Cp>\u003Cstrong>Responsable:\u003C\u002Fstrong> plugin-qualify. \u003Cstrong>Escriu:\u003C\u002Fstrong> el registre de qualificació,\n\u003Ccode>&lt;plugin&gt;@&lt;version&gt;-&lt;hash&gt;.&lt;offer&gt;.qualification.json\u003C\u002Fcode>, amb la sortida de la sonda que ha jutjat al costat, a\n\u003Ccode>\u002Fvar\u002Flib\u002Fomx\u002Fqualification\u003C\u002Fcode>.\u003C\u002Fp>\n\u003Cp>La sonda fa córrer el plugin a cada cel·la d'una graella (44,1, 48, 96 i 192 kHz per blocs de 128, 256, 512 i 1024\nmostres) i n'escriu el registre: els resums dels fitxers del binari, el cost per bloc, la latència declarada i la mesurada,\nla seguretat en temps real sota l'interposador o un codi de motiu per a cada cel·la que no ha corregut. Per a un\ninstrument, la sonda manté unes quantes notes premudes mentre mesura, de manera que el cost és el cost amb aquelles veus\nsonant.\u003C\u002Fp>\n\u003Cp>En surt un veredicte per a cada amfitrió: apte, aïllat (corre en un worker propi i no s'agrupa mai) o no apte. Kars queda\napte per a omx-clap-host, segur en temps real amb un escombratge de paràmetres i amb notes, allotjat aïllat. Les xifres de\nla Pi són a \u003Ca href=\"\u002Fca\u002Fnotes\u002Fplugin-hostd-on-a-raspberry-pi-5\">plugin-hostd en una Raspberry Pi 5\u003C\u002Fa> i les de Surge XT a\n\u003Ca href=\"\u002Fca\u002Fnotes\u002Finstruments-on-a-pi-5\">Instruments en una Pi 5\u003C\u002Fa>.\u003C\u002Fp>\n\u003Ch2 id=\"3-empremtes\">3. Empremtes\u003C\u002Fh2>\n\u003Cp>\u003Cstrong>Responsable:\u003C\u002Fstrong> plugin-qualify. \u003Cstrong>Escriu:\u003C\u002Fstrong> \u003Ccode>\u002Fvar\u002Flib\u002Fomx\u002Fqualified.pins\u003C\u002Fcode>, una línia per plugin.\u003C\u002Fp>\n\u003Cp>A partir dels registres, una línia per plugin diu què pot allotjar plugin-hostd i com (vegeu\n\u003Ca href=\"\u002Fca\u002Fnotes\u002Fpins-on-first-use\">Empremtes al primer ús\u003C\u002Fa>). El dimoni carrega les empremtes com a única font de permís i el seu\nplanificador les llegeix per agrupar workers i col·locar-los en nuclis. Un instrument mai no es posa al worker compartit\nd'una cadena, de manera que una fallada o un búfer tardà d'una veu no poden arribar als efectes que la segueixen.\u003C\u002Fp>\n\u003Cp>És també el que necessiten els nuclis. Surge XT 1.4.0 no fa cas de l'extensió de grup de fils de CLAP, de manera que un\ninstrument és un fil d'àudio. Uns quants instruments fan servir uns quants nuclis quan cadascun és en el seu worker i els\nworkers es reparteixen pels nuclis d'àudio, amb el dimoni fora d'aquests nuclis.\u003C\u002Fp>\n\u003Ch2 id=\"4-disposicio\">4. Disposició\u003C\u002Fh2>\n\u003Cp>\u003Cstrong>Responsable:\u003C\u002Fstrong> omx-panel. \u003Cstrong>Escriu:\u003C\u002Fstrong> les pàgines, calculades a partir del descriptor amb\n\u003Ccode>omx-panel layout --descriptor\u003C\u002Fcode>; el registre guarda l'esquema i el resum de la disposició amb què s'ha jutjat.\u003C\u002Fp>\n\u003Cp>La disposició converteix els paràmetres d'un descriptor en pàgines: les seccions esdevenen grups i cada control rep una\nclau estable. La mateixa disposició governa les pàgines de controls del motor a Zynthian, la MOD GUI generada per a MOD-UI\ni el paquet que afegeix grups als plugins LV2 de tercers (vegeu \u003Ca href=\"\u002Fca\u002Fnotes\u002Fwhy-lv2-plugins-on-zynthian-need-inferred-port-groups\">Per què la majoria dels plugins LV2 d'un Zynthian\nnecessiten grups de ports inferits\u003C\u002Fa>).\u003C\u002Fp>\n\u003Cp>Kars té un grup de tres potenciòmetres i per tant una sola pàgina, &quot;Controls&quot;. Un efecte es disposa d'una altra manera:\nl'equalitzador d'OpenMixer posa cada banda en una pàgina pròpia.\u003C\u002Fp>\n\u003Ch2 id=\"5-llegir-a-l-aparell\">5. Llegir a l'aparell\u003C\u002Fh2>\n\u003Cp>\u003Cstrong>Responsable:\u003C\u002Fstrong> la interfície de Zynthian, amb el dimoni. \u003Cstrong>Escriu:\u003C\u002Fstrong> res; llegeix.\u003C\u002Fp>\n\u003Cp>La interfície llegeix les empremtes per als seus menús, els registres per a la latència, la seguretat en temps real i el\ncost de cada fila i la disposició per a les pàgines. Abans d'inserir un plugin pregunta al verb \u003Ccode>estimate\u003C\u002Fcode> del dimoni què\ncostarà la cadena. Res no es calcula dues vegades: el descriptor per als paràmetres, el registre per a les xifres,\nl'empremta per al permís, la disposició per a les pàgines.\u003C\u002Fp>\n\u003Cp>A l'aparell, per a Kars, la fila del menú de plugins amb el seu nivell, la latència (mostres mesurades i declarades) i la\nseguretat en temps real:\u003C\u002Fp>\n\u003Cp>\u003Cimg src=\"\u002Ftechnical-notes\u002Ffrom-a-plugin-file-to-a-page\u002Flist-by-tier.png\" alt=\"El menú de plugins, ordenat per nivell\">\u003C\u002Fp>\n\u003Cp>la pàgina de controls del motor:\u003C\u002Fp>\n\u003Cp>\u003Cimg src=\"\u002Ftechnical-notes\u002Ffrom-a-plugin-file-to-a-page\u002Fcontroller-page-1-controls.png\" alt=\"La pàgina de controls de Kars\">\u003C\u002Fp>\n\u003Cp>la MOD GUI a partir de la mateixa disposició:\u003C\u002Fp>\n\u003Cp>\u003Cimg src=\"\u002Ftechnical-notes\u002Ffrom-a-plugin-file-to-a-page\u002Fmodgui-pedalboard.png\" alt=\"La MOD GUI de Kars en un pedalboard\">\u003C\u002Fp>\n\u003Cp>i la cadena amb l'instrument:\u003C\u002Fp>\n\u003Cp>\u003Cimg src=\"\u002Ftechnical-notes\u002Ffrom-a-plugin-file-to-a-page\u002Fchain-view-kars-zamcomp.png\" alt=\"Una cadena amb Kars i un compressor\">\u003C\u002Fp>\n\u003Cp>Un aparell nou no repeteix l'etapa llarga. Un paquet porta els registres i les empremtes d'un conjunt de plugins conegut,\nindexats per resums, de manera que un aparell nou els aplica i només sondeja el que és diferent.\u003C\u002Fp>\n",1793954996431]