
# WPML

WPML traduce atributele unui bloc personalizat doar în măsura în care acestea sunt declarate într-un fișier de configurare lingvistică. Blockstudio stochează fiecare valoare a câmpului în comentariul blocului, sub `blockstudio.attributes`, așa că fiecare bloc are nevoie de o intrare care să indice către WPML câmpurile sale text și ID-urile atașamentelor. Comanda `wp bs wpml config` scrie aceste intrări pentru fiecare bloc înregistrat.

## De ce au nevoie blocurile de o configurație

WPML citește configurația dintr-un fișier numit `wpml-config.xml` din folderul rădăcină al temei active și al fiecărui plugin activ. Pentru un plugin must-use care constă într-un singur fișier, folderul are numele fișierului fără `.php`. Consultați [Fișiere de configurare a limbii](https://wpml.org/documentation/support/language-configuration-files/) și [Faceți blocurile Gutenberg traductibile](https://wpml.org/documentation/support/language-configuration-files/make-custom-gutenberg-blocks-translatable/).

Un bloc fără o intrare este lăsat la detectarea automată a șirurilor de caractere de către WPML, care oferă pentru traducere fiecare atribut șir de caractere al blocului. Pentru un bloc Blockstudio care include valori selectate, referințe la fișiere, URL-uri și clase CSS. Traducătorii văd aceste valori tehnice lângă textul propriu-zis, iar o valoare selectată sau o clasă tradusă poate defecta blocul.

## Generarea configurației

Afișați configurația și salvați-o în folderul rădăcină al temei sau pluginului care include blocurile:

```bash
wp bs wpml config > wp-content/themes/my-theme/wpml-config.xml
```

Sau lăsați comanda să scrie fișierul:

```bash
wp bs wpml config --file=wp-content/themes/my-theme/wpml-config.xml
```

Un bloc cu un câmp de text, o imagine, un link și un repetor:

```json title="block.json"
{
  "name": "my-theme/cards",
  "title": "Cards",
  "blockstudio": {
    "attributes": [
      { "id": "heading", "type": "text", "label": "Heading" },
      { "id": "gallery", "type": "files", "label": "Gallery", "multiple": true },
      {
        "id": "style",
        "type": "select",
        "label": "Style",
        "options": [
          { "value": "light", "label": "Light" },
          { "value": "dark", "label": "Dark" }
        ]
      },
      {
        "id": "cards",
        "type": "repeater",
        "label": "Cards",
        "attributes": [
          { "id": "title", "type": "text", "label": "Title" },
          { "id": "image", "type": "files", "label": "Image" },
          { "id": "link", "type": "link", "label": "Button" }
        ]
      }
    ]
  }
}
```

devine:

```xml title="wpml-config.xml"
<wpml-config>
	<gutenberg-blocks>
		<!-- blockstudio:start -->
		<!-- Generated by wp bs wpml config. Run it again after changing block fields; edits between the markers are replaced. -->
		<gutenberg-block type="my-theme/cards" translate="1" label="Cards">
			<key name="blockstudio">
				<key name="attributes">
					<key name="heading" label="Heading" />
					<key name="gallery">
						<key name="*" type="post-ids" sub-type="attachment" />
					</key>
					<key name="cards">
						<key name="*">
							<key name="title" label="Cards: Title" />
							<key name="image" type="post-ids" sub-type="attachment" />
							<key name="link">
								<key name="title" label="Cards: Button: Link text" />
								<key name="url" type="link" label="Cards: Button: URL" />
							</key>
						</key>
					</key>
				</key>
			</key>
		</gutenberg-block>
		<!-- blockstudio:end -->
	</gutenberg-blocks>
</wpml-config>
```

Valoarea `style` nu este declarată, așa că WPML o copiază nemodificată în traducere. ID-urile `gallery` și `image` sunt copiate și ele, iar WPML le înlocuiește pe fiecare cu atașamentul corespunzător limbii paginii la randarea blocului, astfel încât o imagine tradusă poate avea propriul text alternativ. Consultați „Conversia automată a ID-urilor în blocuri” în [Faceți blocurile Gutenberg traductibile](https://wpml.org/documentation/support/language-configuration-files/make-custom-gutenberg-blocks-translatable/). Când un atașament nu are traducere, WPML păstrează ID-ul original.

## Ce se declară

Comanda citește blocurile înregistrate după extinderea câmpurilor `custom/` și a câmpurilor blocurilor și după aplicarea suprascrierilor și a filtrelor de atribute. Sunt incluse câmpurile pe care [extensiile](https://blockstudio.dev/ro/docs/extensions/) le adaugă unui bloc Blockstudio. Câmpurile pe care extensiile le adaugă blocurilor de bază sau blocurilor altor pluginuri nu sunt incluse, deoarece aceste blocuri își obțin configurația din WPML sau din propriul plugin.

| Câmp | Declarație |
| --- | --- |
| `text`, `textarea`, `richtext`, `wysiwyg` | Text traductibil. |
| `link` | `title` ca text și `url` cu `type="link"`, astfel încât WPML înlocuiește un link cu traducerea sa, dacă aceasta este disponibilă. |
| `files` | ID-ul atașamentului stocat, cu `type="post-ids"` și `sub-type="attachment"`. Cu `multiple`, un nivel numit `*` pentru listă, care corespunde și ID-ului unic stocat de câmp atunci când este selectat un singur fișier. |
| `repeater` | Un nivel numit `*` care corespunde fiecărui rând, cu declarațiile câmpurilor din rând. Repetorii imbricați funcționează la fel. |
| `group` cu un `id` | Câmpurile grupului, cu ID-ul grupului ca prefix de cheie (`cta_text` pentru câmpul `text` din grupul `cta`). |
| `group` fără un `id`, `tabs` | Câmpurile, fără un nivel propriu. |
| Tip de câmp personalizat înregistrat cu `translate` setat la `true` | Text traductibil, ca un câmp `text`. |
| Orice alt tip încorporat | Nedeclarat. WPML copiază valoarea nemodificată. |

Un bloc fără niciun câmp de text declarat primește `translate="0"`. Apoi, WPML îi copiază toate valorile și nu oferă nimic din acesta pentru traducere. Câmpurile sale `files` sunt totuși declarate în intrare, deoarece WPML convertește ID-urile atașamentelor indiferent de ce indică `translate`. Blocurile interne se traduc în mod obișnuit.

Nedeclarate:

- Câmpurile cu `hidden`, deoarece valorile lor nu sunt scrise de editori.
- Câmpurile cu `"translate": false`; consultați mai jos.
- Câmpurile [tipurilor de câmpuri personalizate](https://blockstudio.dev/ro/docs/blocks/attributes/custom-field-types/) care nu sunt înregistrate cu `translate` setat la `true`. Comanda afișează câte un avertisment pentru fiecare, deoarece numai tipul de câmp știe dacă valoarea sa conține text. Un `"translate": false` explicit pe un câmp suprimă și acest avertisment pentru câmpul respectiv. Consultați mai jos.
- Atributele pe care un bloc le declară în `attributes` nativ, în loc să le declare ca câmpuri Blockstudio.
- Cheile de stocare ale căror câmpuri au tipuri diferite; consultați mai jos.

Fiecare câmp text este declarat, inclusiv cel care conține o valoare tehnică, cum ar fi o clasă CSS, cu excepția cazului în care setează `"translate": false`.

### Excluderea unui câmp

Un câmp text poate conține o valoare care trebuie să fie aceeași în toate limbile: un nume de cont, o adresă de e-mail, o ancoră, o clasă CSS. WPML o oferă pentru traducere ca pe orice alt text, iar o valoare tradusă poate defecta blocul. Setați `translate` la `false` pentru a exclude câmpul din configurație, astfel încât WPML să-i copieze valoarea nemodificată în traducere:

```json title="block.json"
{
  "id": "account",
  "type": "text",
  "label": "Account handle",
  "translate": false
}
```

Pentru un `group`, `tabs` sau `repeater`, `"translate": false` se aplică fiecărui câmp din interior, inclusiv containerelor imbricate. Un copil nu poate anula excluderea unui container cu `"translate": true`. Pentru un câmp `files`, `false` exclude și ID-urile atașamentelor, astfel încât traducerea păstrează atașamentele originale.

Omiterea lui `translate` sau setarea acestuia la `true` păstrează comportamentul existent: tipul câmpului decide. Astfel nu devin traductibile câmpurile ascunse sau tipurile de valori precum `select`. Opțiunea se aplică câmpurilor blocurilor și extensiilor, nu ascunde și nu dezactivează controalele editorului și nu modifică valorile stocate. Rulați din nou `wp bs wpml config` după schimbarea setării și actualizați `wpml-config.xml` cu configurația generată.

`label` fiecărei chei este eticheta câmpului, precedată de etichetele repetorilor și grupurilor care îl conțin și au un ID. WPML o afișează drept nume de câmp în editorul de traduceri. Cele două chei ale unui câmp `link` adaugă `Link text` și `URL` la etichetă. Aceste sufixe sunt traduse în limba site-ului, așa că rulați comanda cu setările regionale folosite de traducători.

### Tipuri de câmpuri personalizate

Un tip de câmp care stochează un șir de text simplu declară acest lucru la înregistrare. Setați `translate` la `true` în definiție; pentru aceasta, `attribute` trebuie să fie `string`:

```php title="functions.php"
bs_register_field_type('acme/headline', [
  'attribute' => 'string',
  'translate' => true,
]);
```

Comanda declară apoi fiecare câmp de acest tip drept text traductibil. Un câmp poate seta în continuare `"translate": false` pentru a se exclude. Fără această opțiune, câmpurile de acest tip sunt omise și raportate, ca înainte.

### Schimbați etichetele

Etichetele câmpurilor sunt scrise pentru editorul de blocuri și pot conține indicații precum „Imagine (opțional)”, care nu au nicio relevanță în editorul de traduceri. Filtrul `blockstudio/wpml/config/label` primește fiecare etichetă înainte de a fi scrisă, împreună cu contextul cheii:

- `block`: numele blocului.
- `path`: calea de stocare a câmpului de sub `blockstudio.attributes`, cu un nivel `*` pentru rândurile fiecărui câmp repetabil, de exemplu `cards/*/link`.
- `field`: definiția câmpului.
- `parents`: etichetele câmpurilor repetabile și grupurilor care îl conțin și au un ID.
- `part`: `text` pentru un câmp text, `title` sau `url` pentru cele două chei ale unui câmp link.

```php title="functions.php"
add_filter('blockstudio/wpml/config/label', function ($label, $context) {
  return str_replace(' (optional)', '', $label);
}, 10, 2);
```

Returnați un șir gol pentru a omite eticheta unei chei, astfel încât WPML să afișeze în schimb eticheta blocului. O valoare returnată care nu este un șir păstrează eticheta originală. Rulați din nou comanda după ce modificați filtrul.

### Câmpuri cu aceeași cheie de stocare

Două câmpuri pot ajunge să aibă aceeași cheie de stocare, de exemplu un câmp al blocului și un câmp al unei extensii cu același `id` sau câmpul `text` dintr-un grup cu ID-ul `cta` și un câmp cu ID-ul `cta_text`. Comanda declară o astfel de cheie doar când este clar ce se stochează acolo:

- În câmpurile unui bloc, în afara rândurilor câmpurilor repetabile, Blockstudio înregistrează câte un atribut pentru fiecare cheie de stocare, astfel că un câmp ulterior îl înlocuiește pe cel anterior, indiferent de tipul acestuia. Câmpurile extensiilor unui bloc funcționează la fel: un câmp ulterior sau câmpul unei extensii înregistrate ulterior îl înlocuiește pe cel anterior.
- Un câmp al blocului și un câmp al unei extensii cu aceeași cheie rămân ambele active. Șablonul blocului primește valoarea așa cum o definește câmpul blocului, în timp ce extensia este aplicată cu propriul câmp. Cheia este declarată o singură dată când ambele câmpuri necesită aceeași declarație: ambele sunt câmpuri text (`text`, `textarea`, `richtext` sau `wysiwyg`), ambele sunt linkuri, ambele sunt câmpuri `files` (dacă oricare dintre ele are `multiple`, cheia primește nivelul `*`) sau niciunul nu este declarat, cum ar fi un `select` și un `number`. Două câmpuri repetabile sunt comparate câmp cu câmp în rândurile lor. Eticheta provine din câmpul blocului.
- Și două câmpuri cu același `id` în rândurile unui singur câmp repetabil rămân active și sunt comparate în același mod.

Când tipurile diferă, de exemplu un câmp `text` în bloc și un câmp `select` într-o extensie, valoarea stocată este text sau o opțiune de selectare, în funcție de controlul care a scris-o. Comanda nu declară cheia și afișează un avertisment:

```bash
Warning: Not declared, the fields that store this key have different types: my-theme/cards: tone (text in the block, select in an extension)
```

Redenumiți unul dintre câmpuri sau atribuiți-le același tip pentru ca cheia să fie declarată.

## Mențineți configurația actualizată

Rulați din nou comanda după ce adăugați, eliminați sau redenumiți câmpuri și includeți fișierul actualizat în tema sau pluginul dvs. Regenerați configurațiile create înainte de 7.7.5 pentru a include declarațiile ID-urilor atașamentelor. Conținutul existent anterior va afișa câmpurile noi pentru traducere după ce originalul său este actualizat, conform descrierii din ghidul WPML de mai sus.

Cu `--file`, comanda creează un fișier dacă acesta lipsește. Într-un fișier existent, înlocuiește doar textul dintre `<!-- blockstudio:start -->` și `<!-- blockstudio:end -->`, astfel încât celelalte secțiuni și intrările pentru alte blocuri să rămână neschimbate:

```xml title="wpml-config.xml"
<wpml-config>
	<custom-types>
		<custom-type translate="1">book</custom-type>
	</custom-types>
	<gutenberg-blocks>
		<gutenberg-block type="my-plugin/map" translate="1">
			<key name="caption" />
		</gutenberg-block>
		<!-- blockstudio:start -->
		<!-- blockstudio:end -->
	</gutenberg-blocks>
</wpml-config>
```

Pentru a folosi un fișier existent care nu are încă marcaje, adăugați o singură dată cele două linii de marcaj în elementul său `gutenberg-blocks` sau adăugați un element `gutenberg-blocks` care să conțină marcajele, dacă fișierul nu are niciunul. Fără marcaje sau dacă rezultatul nu ar fi o configurație validă, comanda lasă fișierul neschimbat și se încheie cu o eroare.

Intrările pentru blocurile Blockstudio, adăugate manual, cum ar fi intrările `translate="0"` care ascund valori tehnice, nu mai sunt necesare după ce blocul este acoperit de secțiunea generată. Comanda avertizează pentru fiecare bloc declarat de mai multe ori, astfel încât aceste intrări să poată fi eliminate.

## Textele imaginilor în sarcinile de traducere

WPML adaugă în sarcina de traducere a paginii textele imaginilor folosite de aceasta: titlul, textul alternativ, legenda și descrierea. După finalizarea sarcinii, WPML scrie textele traduse în atașamentul limbii țintă și creează acel atașament dacă nu există deja. Consultați [Cum se traduc fișierele media](https://wpml.org/documentation/translating-your-contents/media/).
WPML găsește imaginile în etichetele `<img>` din conținut, în galerii, în imaginea reprezentativă și în blocurile pe care le recunoaște. Un bloc Blockstudio stochează ID-urile atașamentelor în comentariul blocului, prin urmare WPML nu găsește niciunul dintre acestea.

Când WPML este activ, Blockstudio adaugă atașamentele stocate de câmpurile sale în blocurile unei pagini la imaginile WPML găsite:

- Câmpurile `files`, inclusiv cele ascunse, și câmpurile `attributes` cu `media`, aceleași câmpuri pe care editorul de blocuri le încarcă drept fișiere media.
- Câmpurile din grupuri, file, rânduri ale câmpurilor repetabile și blocuri interioare.
- Câmpurile [extensiilor](https://blockstudio.dev/ro/docs/extensions/), inclusiv cele din blocurile de bază și din blocurile altor pluginuri, deoarece valorile lor sunt stocate în atributele blocului extins.

Valorile care nu sunt ID-uri ale unor atașamente sunt omise. Nu este necesară nicio configurare, iar `wpml-config.xml` nu este implicat. Fără WPML, nu se scanează nimic pentru sarcinile de traducere și clasa de integrare media nu este încărcată.

Această funcție este separată de conversia ID-urilor atașamentelor: XML generat îi indică lui WPML ce atașament tradus să redea, iar această integrare îi indică ce texte ale atașamentelor să includă într-o sarcină de traducere. Referințele la șiruri și ID-urile articolelor care nu sunt atașamente nu sunt adăugate la sarcinile media. Valorile salvate ale câmpurilor imbricate au prioritate față de valorile de nivel superior din blocurile Blockstudio, ca și la redare.

Textele fac parte din sarcină doar dacă este activată una dintre opțiunile pentru textele imaginilor din WPML > Settings > Media Translation: „Detectează automat cele mai potrivite opțiuni pentru traducerea textelor imaginilor” sau „Tradu textele bibliotecii media la traducerea conținutului”, la fel ca pentru imaginile din blocurile de bază.

Blockstudio raportează imaginile prin filtrul `wpml_ids_of_media_used_in_post`, care WPML se aplică elementelor media ale unei postări în `PostWithMediaFiles`. Pentru a exclude o imagine din operațiuni, eliminați-i ID-ul într-un callback pe același filtru, cu o prioritate mai mare de 10:

```php
add_filter(
	'wpml_ids_of_media_used_in_post',
	function ( $ids ) {
		return array_values( array_diff( $ids, array( 42 ) ) );
	},
	20
);
```
