Files
ESPDocs/components/PinRestrictions.jsx
T
Lucas RayanandClaude Sonnet 5.5 fe1802f818
CI / Lint e auditorias (push) Successful in 48s
CI / Trivy (dependências e segredos) (push) Successful in 12s
CI / Imagem Docker (linux/arm64) (push) Successful in 3m41s
Release / Plano (reaproveitar a imagem?) (push) Successful in 6s
Release / ci (push) Skipped
Release / Publica a imagem (linux/arm64) (push) Successful in 16s
Release / Cria a release no Gitea (push) Successful in 6s
fix: book canonical, fr/de pin warnings, pin grouping per locale, SEO checks
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-11-01 23:58:11 -03:00

541 lines
22 KiB
React
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import Link from "next/link";
import {
AlertTriangle,
ArrowDownToLine,
HardDrive,
Power,
Bug,
Usb,
Zap,
ArrowRight,
} from "lucide-react";
/**
* Restrições de pinos por série.
*
* Os grupos são DERIVADOS de public/conexoes/<serie>.json, o mesmo arquivo que
* alimenta o diagrama de conexões. Nada aqui é escrito à mão, então a seção e o
* diagrama nunca divergem: corrigir um pino no JSON corrige os dois.
*/
const GRUPOS_PT = [
{
id: "entrada",
titulo: "Somente entrada",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"Aceitam apenas leitura. Não podem ser configurados como saída e não possuem resistores de pull-up ou pull-down internos. Se precisar de um, coloque no circuito.",
combina: (avisos) => /apenas de entrada|input only/i.test(avisos),
},
{
id: "flash",
titulo: "Ligados à memória flash/PSRAM",
icone: HardDrive,
cor: "text-copper",
explicacao:
"Já estão conectados à memória de onde o firmware é lido. Usá-los como GPIO comum normalmente trava o chip ou corrompe a execução. Em módulos com flash interna eles nem chegam ao encapsulamento.",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(dedicad|utilizado pela mem|não deve ser utilizado|não é recomendado|connected to|dedicated to|should not be used|not recommended)/i.test(avisos),
},
{
id: "strapping",
titulo: "Strapping (modo de boot)",
icone: Power,
cor: "text-gold",
explicacao:
"O chip lê o nível destes pinos no instante do reset para decidir como inicializar. Dá para usá-los depois do boot, mas o circuito externo não pode forçar o nível errado durante o reset, senão a placa não inicia ou entra em modo de gravação sozinha.",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|modo de boot|modo de inicialização|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "Gravação e depuração",
icone: Bug,
cor: "text-accent",
explicacao:
"São a UART de gravação e as linhas de JTAG. Continuam utilizáveis como GPIO, mas ao reaproveitá-los você perde o caminho de gravar e depurar a placa sem desconectar o que estiver ali.",
combina: (avisos, cats) => /debugging|gravação/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "USB nativo",
icone: Usb,
cor: "text-accent",
explicacao:
"Saem de fábrica ligados ao USB Serial/JTAG interno. Para usá-los como GPIO é preciso desativar essa função, o que também remove a gravação por USB direto.",
combina: (avisos) => /usb serial\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "Não podem ficar flutuando",
icone: Zap,
cor: "text-gold",
explicacao:
"Precisam de nível definido por hardware: pull-up externo ou circuito RC de atraso. Deixá-los soltos causa reset aleatório ou inicialização instável.",
combina: (avisos) => /flutuando|floating/i.test(avisos),
},
];
const GRUPOS_EN = [
{
id: "entrada",
titulo: "Input only",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"Input only pins. They cannot be configured as outputs and do not have internal pull-up or pull-down resistors. If needed, add them to your external circuit.",
combina: (avisos) => /input[- ]only/i.test(avisos),
},
{
id: "flash",
titulo: "Connected to flash/PSRAM memory",
icone: HardDrive,
cor: "text-copper",
explicacao:
"Already connected to the memory where firmware is stored and executed. Using them as general-purpose GPIO typically crashes the chip or corrupts execution. In modules with internal flash, they are not brought out to the package pins.",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(dedicated|used by|must not be used|not recommended)/i.test(avisos),
},
{
id: "strapping",
titulo: "Strapping pins (boot mode)",
icone: Power,
cor: "text-gold",
explicacao:
"The chip samples the logic level of these pins during reset to determine the boot mode. You can use them after booting, but external circuitry must not force the wrong level during reset, or the board will fail to boot or enter download mode unexpectedly.",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "Flashing and debugging",
icone: Bug,
cor: "text-accent",
explicacao:
"These are the flashing UART and JTAG lines. They can still be used as GPIO, but reusing them removes the ability to flash and debug the board without disconnecting connected peripherals.",
combina: (avisos, cats) => /debugging|flashing/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "Native USB",
icone: Usb,
cor: "text-accent",
explicacao:
"Connected by default to the internal USB Serial/JTAG controller. Using them as GPIO requires disabling this peripheral, which also removes direct USB flashing.",
combina: (avisos) => /usb serial\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "Must not float",
icone: Zap,
cor: "text-gold",
explicacao:
"Require a defined hardware logic level: external pull-up or RC delay circuit. Leaving them floating causes random resets or unstable boot behavior.",
combina: (avisos) => /leave this pin floating/i.test(avisos),
},
];
const GRUPOS_ES = [
{
id: "entrada",
titulo: "Solo entrada",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"Aceptan únicamente lectura. No pueden configurarse como salida y no poseen resistencias de pull-up o pull-down internas. Si necesita una, agréguela en el circuito externo.",
combina: (avisos) => /solo de entrada|input[- ]only/i.test(avisos),
},
{
id: "flash",
titulo: "Conectados a la memoria flash/PSRAM",
icone: HardDrive,
cor: "text-copper",
explicacao:
"Ya están conectados a la memoria desde donde se lee el firmware. Usarlos como GPIO común normalmente bloquea el chip o corrompe la ejecución. En módulos con flash interna ni siquiera llegan a los pines del encapsulado.",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(dedicado|utilizado por la mem|no debe|no se recomienda|no recomendado|connected to|dedicated to)/i.test(avisos),
},
{
id: "strapping",
titulo: "Strapping (modo de arranque)",
icone: Power,
cor: "text-gold",
explicacao:
"El chip lee el nivel lógico de estos pines en el instante del reset para decidir cómo inicializarse. Pueden usarse después del arranque, pero el circuito externo no debe forzar el nivel incorrecto durante el reset, de lo contrario la placa no iniciará o entrará en modo de descarga inesperadamente.",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|modo de arranque|modo de inicialización|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "Grabación y depuración",
icone: Bug,
cor: "text-accent",
explicacao:
"Son la UART de grabación y las líneas de JTAG. Siguen utilizables como GPIO, pero al reutilizarlos pierde la posibilidad de grabar y depurar la placa sin desconectar lo que esté conectado allí.",
combina: (avisos, cats) => /depuración|grabación|debugging/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "USB nativo",
icone: Usb,
cor: "text-accent",
explicacao:
"Salen de fábrica conectados al USB Serial/JTAG interno. Para usarlos como GPIO es necesario desactivar esa función, lo que también elimina la grabación por USB directo.",
combina: (avisos) => /usb serial\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "No deben quedar flotando",
icone: Zap,
cor: "text-gold",
explicacao:
"Requieren un nivel lógico definido por hardware: pull-up externo o circuito RC de retardo. Dejarlos sueltos causa reinicios aleatorios o un arranque inestable.",
combina: (avisos) => /flotando|floating/i.test(avisos),
},
];
const GRUPOS_FR = [
{
id: "entrada",
titulo: "Entrée uniquement",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"Broches en entrée seule. Elles ne peuvent pas être configurées en sortie et ne possèdent pas de résistances de pull-up ou de pull-down internes. Si vous en avez besoin, ajoutez-en dans votre circuit externe.",
combina: (avisos) => /entrée uniquement|input[- ]only/i.test(avisos),
},
{
id: "flash",
titulo: "Liées à la mémoire flash/PSRAM",
icone: HardDrive,
cor: "text-copper",
explicacao:
"Déjà connectées à la mémoire depuis laquelle le firmware est exécuté. Les utiliser comme GPIO standard plante généralement la puce ou corrompt l'exécution. Sur les modules avec flash interne, elles ne sont même pas reliées aux broches du boîtier.",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(dédi|utilisé par la mém|ne doit pas|déconseillé)/i.test(avisos),
},
{
id: "strapping",
titulo: "Strapping (mode de démarrage)",
icone: Power,
cor: "text-gold",
explicacao:
"La puce lit l'état logique de ces broches au moment du reset pour déterminer son mode de démarrage. Vous pouvez les utiliser après le boot, mais le circuit externe ne doit pas forcer un niveau incorrect pendant le reset, sinon la carte ne démarrera pas ou entrera en mode flashage de manière inattendue.",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|mode de démarrage|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "Programmation et débogage",
icone: Bug,
cor: "text-accent",
explicacao:
"Ce sont l'UART de programmation et les lignes JTAG. Elles restent utilisables comme GPIO, mais les réutiliser supprime la possibilité de flasher et de déboguer la carte sans déconnecter ce qui y est relié.",
combina: (avisos, cats) => /débogage|flashage|debugging/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "USB natif",
icone: Usb,
cor: "text-accent",
explicacao:
"Reliées par défaut au contrôleur USB Série/JTAG interne. Les utiliser comme GPIO nécessite de désactiver ce périphérique, ce qui désactive également le flashage direct par USB.",
combina: (avisos) => /usb (série|serial)\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "Ne doivent pas être laissées flottantes",
icone: Zap,
cor: "text-gold",
explicacao:
"Nécessitent un niveau logique matériel défini : pull-up externe ou circuit RC de temporisation. Les laisser flottantes entraîne des redémarrages aléatoires ou un démarrage instable.",
combina: (avisos) => /laissez pas cette broche flottante/i.test(avisos),
},
];
const GRUPOS_DE = [
{
id: "entrada",
titulo: "Nur Eingang",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"Pins, die nur als Eingang arbeiten. Sie können nicht als Ausgang konfiguriert werden und besitzen keine internen Pull-up- oder Pull-down-Widerstände. Falls erforderlich, sehen Sie diese in Ihrer externen Schaltung vor.",
combina: (avisos) => /nur eingang|input[- ]only/i.test(avisos),
},
{
id: "flash",
titulo: "Mit Flash-/PSRAM-Speicher verbunden",
icone: HardDrive,
cor: "text-copper",
explicacao:
"Bereits mit dem Speicher verbunden, aus dem die Firmware ausgeführt wird. Die Verwendung als universelle GPIOs führt meist zu Abstürzen oder Speicherbeschädigungen. Bei Modulen mit internem Flash sind sie nicht nach außen geführt.",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(dediziert|belegt|darf nicht|nicht empfohlen)/i.test(avisos),
},
{
id: "strapping",
titulo: "Strapping-Pins (Bootmodus)",
icone: Power,
cor: "text-gold",
explicacao:
"Der Chip liest den Logikpegel dieser Pins beim Reset aus, um den Bootmodus festzulegen. Nach dem Booten können sie genutzt werden, die externe Schaltung darf beim Reset jedoch keinen falschen Pegel erzwingen, da das Board sonst nicht startet oder unerwartet in den Download-Modus wechselt.",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|bootmodus|boot-modus|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "Programmierung und Debugging",
icone: Bug,
cor: "text-accent",
explicacao:
"Dies sind die Flash-UART- und JTAG-Leitungen. Sie können als GPIO genutzt werden, doch dadurch entfällt die Möglichkeit, das Board ohne Trennen der Peripherie zu programmieren oder zu debuggen.",
combina: (avisos, cats) => /debugging|flashen/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "Natives USB",
icone: Usb,
cor: "text-accent",
explicacao:
"Standardmäßig mit dem internen USB-Serial/JTAG-Controller verbunden. Um sie als GPIO zu nutzen, muss diese Funktion deaktiviert werden, wodurch auch das direkte Flashen über USB entfällt.",
combina: (avisos) => /usb[- ](serial|seriell)\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "Dürfen nicht unbeschaltet bleiben",
icone: Zap,
cor: "text-gold",
explicacao:
"Erfordern einen definierten Hardwarepegel: externen Pull-up oder RC-Verzögerungsschaltung. Bleiben sie unbeschaltet (floating), führt dies zu sporadischen Resets oder instabilem Bootverhalten.",
combina: (avisos) => /nicht unbeschaltet( \(floating\))? lassen/i.test(avisos),
},
];
const GRUPOS_ZH = [
{
id: "entrada",
titulo: "仅输入",
icone: ArrowDownToLine,
cor: "text-accent",
explicacao:
"仅能作输入的引脚。它们不能配置为输出,也没有内部上拉或下拉电阻。如有需要,请在外部电路中添加。",
combina: (avisos) => /仅为输入|仅输入|input[- ]only/i.test(avisos),
},
{
id: "flash",
titulo: "连接到闪存/PSRAM",
icone: HardDrive,
cor: "text-copper",
explicacao:
"已连接到存放并执行固件的存储器。把它们当作通用 GPIO 使用,通常会使芯片崩溃或破坏程序执行。在带内置闪存的模组中,这些引脚不会引出到封装引脚上。",
combina: (avisos) =>
/(flash|psram)/i.test(avisos) &&
/(专用|存储使用|不得用于|不建议)/i.test(avisos),
},
{
id: "strapping",
titulo: "启动配置引脚(Strapping,启动模式)",
icone: Power,
cor: "text-gold",
explicacao:
"芯片在复位期间会对这些引脚的逻辑电平采样,以决定启动模式。启动完成后可以使用它们,但外部电路在复位期间不能把它们强制到错误的电平,否则开发板将无法启动,或意外进入下载模式。",
combina: (avisos, cats) =>
cats.includes("Strapping") ||
/strapping|启动模式|启动配置|boot mode/i.test(avisos),
},
{
id: "debug",
titulo: "烧录与调试",
icone: Bug,
cor: "text-accent",
explicacao:
"这些是用于烧录的 UART 和 JTAG 线。它们仍可用作 GPIO,但一旦复用,就必须先断开所接外设,才能对开发板烧录和调试。",
combina: (avisos, cats) => /调试|烧录|debugging/i.test(avisos) || cats.includes("JTAG"),
},
{
id: "usb",
titulo: "原生 USB",
icone: Usb,
cor: "text-accent",
explicacao:
"默认连接到内部的 USB Serial/JTAG 控制器。要把它们用作 GPIO,就必须禁用该外设,同时也会失去直接通过 USB 烧录的能力。",
combina: (avisos) => /usb serial\/jtag|usb_d[+-]/i.test(avisos),
},
{
id: "eletrico",
titulo: "不能悬空",
icone: Zap,
cor: "text-gold",
explicacao:
"需要确定的硬件逻辑电平:外部上拉或 RC 延时电路。悬空会导致随机复位或启动不稳定。",
combina: (avisos) => /请勿让该引脚浮空/i.test(avisos),
},
];
/** Nome do pino + o GPIO correspondente, quando o nome é uma função (ex.: SENSOR_VP). */
function rotuloDoPino(pino) {
const gpio = (pino.funcoes || []).find((f) => /^GPIO\d+$/.test(f));
return gpio && gpio !== pino.nome ? `${pino.nome} · ${gpio}` : pino.nome;
}
function derivarGrupos(conexoes, isEn, isEs, isFr, isDe, isZh = false) {
const listaGrupos = isEn
? GRUPOS_EN
: isEs
? GRUPOS_ES
: isFr
? GRUPOS_FR
: isZh ? GRUPOS_ZH : isDe
? GRUPOS_DE
: GRUPOS_PT;
return listaGrupos.map((grupo) => {
const vistos = new Map();
for (const pino of conexoes) {
if (!["io", "analog", "dedicated"].includes(pino.tipo)) continue;
const avisos = (pino.avisos || []).join(" ").toLowerCase();
const cats = pino.categorias || [];
if (grupo.combina(avisos, cats)) {
const rotulo = rotuloDoPino(pino);
if (!vistos.has(rotulo)) vistos.set(rotulo, pino);
}
}
return { ...grupo, pinos: [...vistos.keys()] };
}).filter((g) => g.pinos.length > 0);
}
export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs = false, isFr = false, isDe = false, isZh = false, locale }) {
if (!conexoes?.length) return null;
const effectiveIsEn = isEn || locale === "en";
const effectiveIsEs = isEs || locale === "es";
const effectiveIsFr = isFr || locale === "fr";
const effectiveIsDe = isDe || locale === "de";
const effectiveIsZh = isZh || locale === "zh-CN";
const grupos = derivarGrupos(conexoes, effectiveIsEn, effectiveIsEs, effectiveIsFr, effectiveIsDe, effectiveIsZh);
if (!grupos.length) return null;
const totalPinos = new Set(grupos.flatMap((g) => g.pinos)).size;
return (
<section id="restricoes" aria-labelledby="restricoes-titulo" className="card mt-5 scroll-mt-28 p-5 sm:p-7">
<h2 id="restricoes-titulo" className="flex items-center gap-3 font-display text-xl font-semibold tracking-[-0.03em] text-ink">
<span className="grid h-9 w-9 place-items-center rounded-full bg-gold-soft text-gold">
<AlertTriangle className="h-4 w-4" aria-hidden="true" />
</span>
{effectiveIsEn
? "Pins with usage restrictions"
: effectiveIsEs
? "Pines con restricción de uso"
: effectiveIsFr
? "Broches avec restrictions d'utilisation"
: effectiveIsZh ? "有使用限制的引脚" : effectiveIsDe
? "Pins mit Nutzungseinschränkungen"
: "Pinos com restrição de uso"}
</h2>
<p className="mt-3 max-w-3xl text-sm leading-relaxed text-muted">
{effectiveIsEn ? (
<>
Not every pin on the {serieKey} is free for general-purpose use. {totalPinos} of them have conditions: occupied by memory, sampled during boot, or function as input only. Check before finalizing your schematic.
</>
) : effectiveIsEs ? (
<>
No todos los pines del {serieKey} están libres para uso general. {totalPinos} de ellos tienen alguna condición: ya están ocupados por memoria, se leen durante el arranque o solo funcionan como entrada. Conviene comprobarlos antes de cerrar el esquemático.
</>
) : effectiveIsFr ? (
<>
Toutes les broches de l&apos;{serieKey} ne sont pas libres pour un usage général. {totalPinos} d&apos;entre elles ont des conditions : occupées par la mémoire, lues pendant le démarrage ou fonctionnent uniquement en entrée. Pensez à vérifier avant de finaliser votre schéma.
</>
) : effectiveIsZh ? ( <>
{serieKey} 上并非每个引脚都可以随意用作通用 IO。其中有 {totalPinos} 个带有使用条件:被存储器占用、在启动时被读取,或只能作输入。在定稿原理图之前,建议先核对一遍。
</> ) : effectiveIsDe ? (
<>
Nicht jeder Pin des {serieKey} steht für allgemeine Zwecke frei zur Verfügung. {totalPinos} davon unterliegen Bedingungen: durch Speicher belegt, beim Booten abgefragt oder reine Eingangspins. Prüfen Sie dies vor Abschluss Ihres Schaltplans.
</>
) : (
<>
Nem todo pino do {serieKey} está livre para uso geral. {totalPinos} deles têm alguma
condição: já estão ocupados por memória, são lidos durante o boot ou só funcionam
como entrada. Vale conferir antes de fechar o esquemático.
</>
)}
</p>
<div className="mt-6 grid gap-4 md:grid-cols-2">
{grupos.map(({ id, titulo, icone: Icone, cor: corIcone, explicacao, pinos }) => (
<div key={id} className="tile">
<div className="flex items-center gap-2.5">
<Icone className={`h-4 w-4 shrink-0 ${corIcone}`} aria-hidden="true" />
<h3 className="text-sm font-semibold text-ink">{titulo}</h3>
<span className="ml-auto text-xs text-muted tabular-nums">
{pinos.length}{" "}
{pinos.length === 1
? effectiveIsEn
? "pin"
: effectiveIsEs
? "pin"
: effectiveIsFr
? "broche"
: effectiveIsZh ? "个引脚" : effectiveIsDe
? "Pin"
: "pino"
: effectiveIsEn
? "pins"
: effectiveIsEs
? "pines"
: effectiveIsFr
? "broches"
: effectiveIsZh ? "个引脚" : effectiveIsDe
? "Pins"
: "pinos"}
</span>
</div>
<ul className="mt-3 flex flex-wrap gap-1.5">
{pinos.map((p) => (
<li key={p} className="rounded-md border border-line bg-surface px-2 py-1 font-mono text-xs text-ink-soft">
{p}
</li>
))}
</ul>
<p className="mt-3 text-sm leading-relaxed text-muted">{explicacao}</p>
</div>
))}
</div>
<div className="mt-6 flex flex-col justify-between gap-4 border-t border-line pt-5 sm:flex-row sm:items-center">
<p className="max-w-xl text-sm leading-relaxed text-muted">
{effectiveIsEn ? (
"These groups are derived from the same data as the pinout diagram. There you can see every pin's full functions, power domain, and complete engineering notes."
) : effectiveIsEs ? (
"Estos grupos proceden de los mismos datos que el diagrama de conexiones. Allí podrá consultar pino a pino todas las funciones, el dominio de alimentación y los avisos completos."
) : effectiveIsFr ? (
"Ces groupes sont issus des mêmes données que le schéma de brochage. Vous pouvez y consulter broche par broche l'ensemble des fonctions, le domaine d'alimentation et les remarques complètes."
) : effectiveIsZh ? ( "这些分组来自与连接图相同的数据。在那里可以逐个引脚查看全部功能、供电域和完整的警告。" ) : effectiveIsDe ? (
"Diese Gruppen stammen aus denselben Daten wie das Pinbelegungsdiagramm. Dort finden Sie für jeden Pin alle Funktionen, den Spannungsbereich und die vollständigen Entwicklungshinweise."
) : (
"Estes grupos vêm dos mesmos dados do diagrama de conexões. Lá você vê pino a pino todas as funções, o domínio de alimentação e os avisos completos."
)}
</p>
<Link href="#connections" className="btn btn-ghost shrink-0">
{effectiveIsEn ? "Open pinout diagram" : effectiveIsEs ? "Abrir diagrama de pines" : effectiveIsFr ? "Ouvrir le brochage" : effectiveIsZh ? "打开引脚图" : effectiveIsDe ? "Pinbelegung öffnen" : "Abrir diagrama de pinos"}
<ArrowRight className="h-4 w-4" aria-hidden="true" />
</Link>
</div>
</section>
);
}