Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
06e8fac0ad | ||
|
|
684e0ee6f8 | ||
|
|
7fce46b9e1 |
No files matched your search
+29
-1
@@ -6,6 +6,33 @@ Tudo o que muda de relevante no ESPDocs está aqui. O formato segue o
|
||||
|
||||
## [Não lançado]
|
||||
|
||||
## [1.5.0] - 2026-11-02
|
||||
|
||||
### Adicionado
|
||||
|
||||
- Internacionalização completa para os idiomas Francês (`fr`) e Alemão (`de`) (Fase 5):
|
||||
- Ativação do francês e do alemão em `ENABLED_LOCALES = ["pt", "en", "es", "fr", "de"]` e no seletor de idiomas do cabeçalho.
|
||||
- Tradução técnica integral e paridade estrutural em `messages/fr.json` e `messages/de.json` (15 namespaces), nos arquivos de dados em `data/{fr,de}/` (`series.json`, `frameworks.json`, `conexoes/*.json`) e `lib/data/{fr,de}/` (`glossario.js`, `diagnostico.js`, `componentes.js`, `topicos.js`).
|
||||
- Tradução técnica natural com tratamento formal respeitado: "vous" em francês e "Sie" em alemão.
|
||||
- 14 exemplos práticos de código com comentários em francês e 14 em alemão em `public/exemplos/{fr,de}/`.
|
||||
- Slugs canônicos ASCII por idioma:
|
||||
- Francês: `/fr/series`, `/fr/catalogue`, `/fr/comparaison`, `/fr/composants`, `/fr/diagnostic`, `/fr/frameworks`, `/fr/glossaire`, `/fr/selecteur`, `/fr/a-propos`.
|
||||
- Alemão: `/de/serien`, `/de/katalog`, `/de/vergleich`, `/de/komponenten`, `/de/diagnose`, `/de/frameworks`, `/de/glossar`, `/de/auswahl`, `/de/ueber-uns`.
|
||||
- Busca dedicada por idioma em `/api/busca/fr` e `/api/busca/de` com normalização de acentos, caracteres alemães (ä, ö, ü, ß) e ligaduras francesas (œ, æ), sem menção ao livro e com links diretos aos slugs canônicos.
|
||||
- Exclusão total e estrita de referências ao livro fora do português, com `/fr/livro` e `/de/livro` respondendo HTTP 404 estrito.
|
||||
- Tabela do catálogo de placas com colunas traduzidas e mapeamento de valores técnicos nos idiomas francês e alemão.
|
||||
- Negociação de idioma na raiz com roteamento para `fr` ou `de` com base nos cabeçalhos Accept-Language ou cookies `NEXT_LOCALE=fr` / `NEXT_LOCALE=de`, e fallback padrão para `en` para navegadores com o idioma inativo restante (`zh-CN`).
|
||||
- Metadados de SEO, Open Graph e Twitter Cards localizados com `og:locale` (`fr_FR`, `de_DE`), `inLanguage` (`fr`, `de`) e `hreflang` cruzado entre `pt-BR`, `en`, `es-419`, `fr-FR`, `de-DE` e `x-default`.
|
||||
- Suporte CSS com hifenação automática (`hyphens: auto`) para alemão e francês via atributo `lang` dinâmico no layout raiz.
|
||||
- Extensão da suíte de verificação: `scripts/check-i18n.mjs` valida `fr` e `de`, `scripts/smoke-imagem.sh` testa as rotas francesas e alemãs e `scripts/verifica-vazamentos.py` varre todas as 36 rotas em francês e 36 em alemão (texto visível e blocos JSON-LD).
|
||||
|
||||
### Corrigido
|
||||
|
||||
- O cabeçalho passou a caber em telas estreitas. Desde o seletor de idioma, a faixa de
|
||||
ícones ficava com ~410 px de largura mínima e o botão do menu era cortado em
|
||||
celulares (390 e 360 px). Agora o seletor fica compacto no celular e o logo mostra
|
||||
só o ícone abaixo de 360 px; sem rolagem horizontal de 320 px para cima.
|
||||
|
||||
## [1.4.2] - 2026-11-02
|
||||
|
||||
### Corrigido
|
||||
@@ -167,7 +194,8 @@ entrada resume tudo desde o primeiro commit, em 2025-10-21, até a imagem Docker
|
||||
otimização de imagens (GHSA-2464-fhr4-w9xw), e `postcss` fixado acima da cópia
|
||||
embutida no `next`.
|
||||
|
||||
[Não lançado]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.4.2...HEAD
|
||||
[Não lançado]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.5.0...HEAD
|
||||
[1.5.0]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.4.2...v1.5.0
|
||||
[1.4.2]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.4.1...v1.4.2
|
||||
[1.4.1]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.4.0...v1.4.1
|
||||
[1.4.0]: https://git.lucasrguerra.dev.br/lucasrguerra/ESPDocs/compare/v1.3.0...v1.4.0
|
||||
|
||||
@@ -4,12 +4,18 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEn ? "ESP32 Board Catalog" : isEs ? "Catálogo de placas ESP32" : "Catálogo de placas ESP32",
|
||||
titulo: isEn ? "ESP32 Board Catalog" : isEs ? "Catálogo de placas ESP32" : isFr ? "Catalogue de cartes ESP32" : isDe ? "ESP32-Board-Katalog" : "Catálogo de placas ESP32",
|
||||
descricao: isEn
|
||||
? "ESP32 development boards and DevKits available in Brazil, with filters by series, connector, and USB-serial converter."
|
||||
: isEs
|
||||
? "Placas de desarrollo y DevKits con ESP32, con filtros por serie, conector y conversor USB-serial."
|
||||
: isFr
|
||||
? "Cartes de développement et DevKits ESP32, avec filtres par série, connecteur et convertisseur USB-série."
|
||||
: isDe
|
||||
? "ESP32-Entwicklungsboards und DevKits, mit Filtern nach Serie, Anschluss und USB-Seriell-Wandler."
|
||||
: "Placas de desenvolvimento com ESP32 disponíveis no Brasil, com filtro por série, conector e conversor USB-serial.",
|
||||
caminho: "/catalogo",
|
||||
locale,
|
||||
@@ -17,6 +23,10 @@ export async function generateMetadata({ params }) {
|
||||
? ["ESP32 boards", "ESP32 DevKit", "buy ESP32", "ESP32 DevKitC"]
|
||||
: isEs
|
||||
? ["placas ESP32", "DevKit ESP32", "comprar ESP32", "ESP32 DevKitC"]
|
||||
: isFr
|
||||
? ["cartes ESP32", "DevKit ESP32", "acheter ESP32", "ESP32 DevKitC"]
|
||||
: isDe
|
||||
? ["ESP32 Boards", "ESP32 DevKit", "ESP32 kaufen", "ESP32 DevKitC"]
|
||||
: ["placas ESP32", "DevKit ESP32", "comprar ESP32", "ESP32 DevKitC"],
|
||||
});
|
||||
}
|
||||
@@ -25,7 +35,9 @@ export default async function Layout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const canonPath = isEn ? "/en/catalog" : isEs ? "/es/catalogo" : "/catalogo";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const canonPath = isEn ? "/en/catalog" : isEs ? "/es/catalogo" : isFr ? "/fr/catalogue" : isDe ? "/de/katalog" : "/catalogo";
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -34,11 +46,15 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.aplicacaoWeb({
|
||||
nome: isEn ? "ESP32 Development Board Catalog" : isEs ? "Catálogo de placas de desarrollo ESP32" : "Catálogo de Placas ESP32",
|
||||
nome: isEn ? "ESP32 Development Board Catalog" : isEs ? "Catálogo de placas de desarrollo ESP32" : isFr ? "Catalogue de cartes de développement ESP32" : isDe ? "Katalog für ESP32-Entwicklungsboards" : "Catálogo de Placas ESP32",
|
||||
descricao: isEn
|
||||
? "Interactive guide and catalog of development boards and DevKits featuring ESP32 microcontrollers."
|
||||
: isEs
|
||||
? "Guía y catálogo interactivo de placas de desarrollo y DevKits con microcontroladores ESP32."
|
||||
: isFr
|
||||
? "Guide interactif et catalogue de cartes de développement et DevKits avec microcontrôleurs ESP32."
|
||||
: isDe
|
||||
? "Interaktiver Leitfaden und Katalog für Entwicklungsboards und DevKits mit ESP32-Mikrocontrollern."
|
||||
: "Guia e catálogo interativo de placas de desenvolvimento e DevKits com microcontroladores ESP32.",
|
||||
caminho: canonPath,
|
||||
locale,
|
||||
@@ -51,8 +67,8 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEn ? "Home" : isEs ? "Inicio" : "Início", caminho: isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isEn ? "Board Catalog" : isEs ? "Catálogo de placas" : "Catálogo de Placas", caminho: canonPath },
|
||||
{ nome: isEn ? "Home" : isEs ? "Inicio" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEn ? "/en" : isEs ? "/es" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: isEn ? "Board Catalog" : isEs ? "Catálogo de placas" : isFr ? "Catalogue de cartes" : isDe ? "Board-Katalog" : "Catálogo de Placas", caminho: canonPath },
|
||||
])
|
||||
),
|
||||
}}
|
||||
|
||||
@@ -58,10 +58,62 @@ const VALUE_MAP_ES = {
|
||||
"Opcional": "Opcional",
|
||||
};
|
||||
|
||||
const HEADER_MAP_FR = {
|
||||
"Nome": "Nom",
|
||||
"Descrição": "Description",
|
||||
"Série": "Série",
|
||||
"Loja Oficial": "Boutique officielle",
|
||||
"Fabricante": "Fabricant",
|
||||
"Processador": "Processeur",
|
||||
"Memória Flash": "Mémoire Flash",
|
||||
"PSRAM": "PSRAM",
|
||||
"Conector USB": "Connecteur USB",
|
||||
"Interface USB": "Interface USB",
|
||||
"Antena": "Antenne",
|
||||
"Bateria": "Batterie",
|
||||
"Display": "Écran",
|
||||
"Sensores": "Capteurs",
|
||||
"Botões": "Boutons",
|
||||
"LEDs": "LEDs",
|
||||
};
|
||||
|
||||
const VALUE_MAP_FR = {
|
||||
"Sim": "Oui",
|
||||
"Não": "Non",
|
||||
"Opcional": "Optionnel",
|
||||
};
|
||||
|
||||
const HEADER_MAP_DE = {
|
||||
"Nome": "Name",
|
||||
"Descrição": "Beschreibung",
|
||||
"Série": "Serie",
|
||||
"Loja Oficial": "Offizieller Store",
|
||||
"Fabricante": "Hersteller",
|
||||
"Processador": "Prozessor",
|
||||
"Memória Flash": "Flash-Speicher",
|
||||
"PSRAM": "PSRAM",
|
||||
"Conector USB": "USB-Anschluss",
|
||||
"Interface USB": "USB-Schnittstelle",
|
||||
"Antena": "Antenne",
|
||||
"Bateria": "Batterie",
|
||||
"Display": "Display",
|
||||
"Sensores": "Sensoren",
|
||||
"Botões": "Tasten",
|
||||
"LEDs": "LEDs",
|
||||
};
|
||||
|
||||
const VALUE_MAP_DE = {
|
||||
"Sim": "Ja",
|
||||
"Não": "Nein",
|
||||
"Opcional": "Optional",
|
||||
};
|
||||
|
||||
export default function PlacasPage() {
|
||||
const pathname = usePathname() || "";
|
||||
const isEn = pathname === "/en" || pathname.startsWith("/en/");
|
||||
const isEs = pathname === "/es" || pathname.startsWith("/es/");
|
||||
const isFr = pathname === "/fr" || pathname.startsWith("/fr/");
|
||||
const isDe = pathname === "/de" || pathname.startsWith("/de/");
|
||||
|
||||
const [boards, setBoards] = useState([]);
|
||||
const [filteredBoards, setFilteredBoards] = useState([]);
|
||||
@@ -90,7 +142,7 @@ export default function PlacasPage() {
|
||||
const response = await fetch("/api/placas");
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error(isEn ? "Failed to load board data" : isEs ? "Error al cargar los datos de las placas" : "Erro ao carregar dados das placas");
|
||||
throw new Error(isEn ? "Failed to load board data" : isEs ? "Error al cargar los datos de las placas" : isFr ? "Erreur lors du chargement des données des cartes" : isDe ? "Fehler beim Laden der Board-Daten" : "Erro ao carregar dados das placas");
|
||||
}
|
||||
|
||||
const result = await response.json();
|
||||
@@ -195,15 +247,21 @@ export default function PlacasPage() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEn ? "Board Catalog" : isEs ? "Catálogo de placas" : "Catálogo de placas" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEn ? "Board Catalog" : isEs ? "Catálogo de placas" : isFr ? "Catalogue de cartes" : isDe ? "Board-Katalog" : "Catálogo de placas" }]}
|
||||
icon={ShoppingCart}
|
||||
label={isEn ? "Real DevKits and modules" : isEs ? "DevKits y módulos reales" : "DevKits e módulos reais"}
|
||||
title={isEn ? "ESP32 Board Catalog" : isEs ? "Catálogo de placas ESP32" : "Catálogo de placas ESP32"}
|
||||
label={isEn ? "Real DevKits and modules" : isEs ? "DevKits y módulos reales" : isFr ? "DevKits et modules réels" : isDe ? "Echte DevKits und Module" : "DevKits e módulos reais"}
|
||||
title={isEn ? "ESP32 Board Catalog" : isEs ? "Catálogo de placas ESP32" : isFr ? "Catalogue de cartes ESP32" : isDe ? "ESP32-Board-Katalog" : "Catálogo de placas ESP32"}
|
||||
lede={
|
||||
isEn
|
||||
? "Compare official and third-party boards for your project: USB interface, on-board sensors and direct store links."
|
||||
: isEs
|
||||
? "Compare placas oficiales y alternativas para su proyecto: interfaz USB, sensores integrados y enlace directo a la tienda."
|
||||
: isFr
|
||||
? "Comparez les cartes officielles et alternatives pour votre projet : interface USB, capteurs intégrés et lien direct vers la boutique."
|
||||
: isDe
|
||||
? "Vergleichen Sie offizielle und Drittanbieter-Boards für Ihr Projekt: USB-Schnittstelle, integrierte Sensoren und direkter Store-Link."
|
||||
: "Compare placas oficiais e alternativas para o seu projeto: interface USB, sensores integrados e link direto para a loja."
|
||||
}
|
||||
/>
|
||||
@@ -215,14 +273,14 @@ export default function PlacasPage() {
|
||||
<Header />
|
||||
<main id="conteudo">
|
||||
{hero}
|
||||
<section className="shell section pt-10" aria-busy="true" aria-label={isEn ? "Loading boards" : isEs ? "Cargando placas" : "Carregando placas"}>
|
||||
<section className="shell section pt-10" aria-busy="true" aria-label={isEn ? "Loading boards" : isEs ? "Cargando placas" : isFr ? "Chargement des cartes" : isDe ? "Boards werden geladen" : "Carregando placas"}>
|
||||
<div className="grid gap-4 md:grid-cols-2 xl:grid-cols-3">
|
||||
{Array.from({ length: 6 }).map((_, i) => (
|
||||
<div key={i} className="card h-72 animate-pulse bg-surface-2" />
|
||||
))}
|
||||
</div>
|
||||
<p role="status" className="mt-6 text-center text-sm text-muted">
|
||||
{isEn ? "Querying boards database…" : isEs ? "Consultando la base de datos de placas…" : "Consultando o banco de placas…"}
|
||||
{isEn ? "Querying boards database…" : isEs ? "Consultando la base de datos de placas…" : isFr ? "Consultation de la base de cartes…" : isDe ? "Board-Datenbank wird abgefragt…" : "Consultando o banco de placas…"}
|
||||
</p>
|
||||
</section>
|
||||
</main>
|
||||
@@ -242,14 +300,14 @@ export default function PlacasPage() {
|
||||
<AlertTriangle className="mt-0.5 h-5 w-5 shrink-0 text-danger" aria-hidden="true" />
|
||||
<div>
|
||||
<p className="font-semibold text-ink">
|
||||
{isEn ? "Could not load boards" : isEs ? "No se pudieron cargar las placas" : "Não foi possível carregar as placas"}
|
||||
{isEn ? "Could not load boards" : isEs ? "No se pudieron cargar las placas" : isFr ? "Impossible de charger les cartes" : isDe ? "Boards konnten nicht geladen werden" : "Não foi possível carregar as placas"}
|
||||
</p>
|
||||
<p className="mt-1">
|
||||
{error}. {isEn ? "Check your connection and try again." : isEs ? "Compruebe la conexión y vuelva a intentarlo." : "Verifique a conexão e tente de novo."}
|
||||
{error}. {isEn ? "Check your connection and try again." : isEs ? "Compruebe la conexión y vuelva a intentarlo." : isFr ? "Vérifiez votre connexion et réessayez." : isDe ? "Prüfen Sie Ihre Verbindung und versuchen Sie es erneut." : "Verifique a conexão e tente de novo."}
|
||||
</p>
|
||||
<button type="button" onClick={fetchBoards} className="btn btn-primary btn-sm mt-4">
|
||||
<RefreshCw className="h-4 w-4" aria-hidden="true" />
|
||||
{isEn ? "Try again" : isEs ? "Reintentar" : "Tentar novamente"}
|
||||
{isEn ? "Try again" : isEs ? "Reintentar" : isFr ? "Réessayer" : isDe ? "Erneut versuchen" : "Tentar novamente"}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
@@ -264,14 +322,14 @@ export default function PlacasPage() {
|
||||
<div className="space-y-6">
|
||||
<div>
|
||||
<label htmlFor="busca-placa" className="text-sm font-semibold text-ink">
|
||||
{isEn ? "Search board" : isEs ? "Buscar placa" : "Buscar placa"}
|
||||
{isEn ? "Search board" : isEs ? "Buscar placa" : isFr ? "Rechercher une carte" : isDe ? "Board suchen" : "Buscar placa"}
|
||||
</label>
|
||||
<div className="relative mt-2">
|
||||
<Search className="pointer-events-none absolute left-3.5 top-1/2 h-4 w-4 -translate-y-1/2 text-muted" aria-hidden="true" />
|
||||
<input
|
||||
id="busca-placa"
|
||||
type="search"
|
||||
placeholder={isEn ? "Name or description" : isEs ? "Nombre o descripción" : "Nome ou descrição"}
|
||||
placeholder={isEn ? "Name or description" : isEs ? "Nombre o descripción" : isFr ? "Nom ou description" : isDe ? "Name oder Beschreibung" : "Nome ou descrição"}
|
||||
value={searchTerm}
|
||||
onChange={(e) => setSearchTerm(e.target.value)}
|
||||
className="field pl-10 text-sm"
|
||||
@@ -282,7 +340,7 @@ export default function PlacasPage() {
|
||||
{filterableColumns.map((column) => {
|
||||
const filterData = filterOptions[column];
|
||||
if (!filterData) return null;
|
||||
const colLabel = isEn ? (HEADER_MAP_EN[column] || column) : isEs ? (HEADER_MAP_ES[column] || column) : column;
|
||||
const colLabel = isEn ? (HEADER_MAP_EN[column] || column) : isEs ? (HEADER_MAP_ES[column] || column) : isFr ? (HEADER_MAP_FR[column] || column) : isDe ? (HEADER_MAP_DE[column] || column) : column;
|
||||
|
||||
if (filterData.isBinary) {
|
||||
return (
|
||||
@@ -306,7 +364,7 @@ export default function PlacasPage() {
|
||||
</legend>
|
||||
<div className="mt-2 max-h-44 space-y-0.5 overflow-y-auto pr-1">
|
||||
{filterData.values.map((option) => {
|
||||
const optLabel = isEn ? (VALUE_MAP_EN[option] || option) : isEs ? (VALUE_MAP_ES[option] || option) : option;
|
||||
const optLabel = isEn ? (VALUE_MAP_EN[option] || option) : isEs ? (VALUE_MAP_ES[option] || option) : isFr ? (VALUE_MAP_FR[option] || option) : isDe ? (VALUE_MAP_DE[option] || option) : option;
|
||||
return (
|
||||
<label key={option} className="flex min-h-10 cursor-pointer items-center gap-3 rounded-lg px-2 text-sm text-muted transition-colors hover:bg-surface-2 hover:text-ink">
|
||||
<input
|
||||
@@ -333,14 +391,14 @@ export default function PlacasPage() {
|
||||
<main id="conteudo">
|
||||
{hero}
|
||||
|
||||
<section className="shell section pt-10 sm:pt-12" aria-label={isEn ? "Boards" : isEs ? "Placas" : "Placas"}>
|
||||
<section className="shell section pt-10 sm:pt-12" aria-label={isEn ? "Boards" : isEs ? "Placas" : isFr ? "Cartes" : isDe ? "Boards" : "Placas"}>
|
||||
<div className="grid gap-8 lg:grid-cols-[17rem_1fr] lg:gap-10">
|
||||
<aside className="lg:sticky lg:top-28 lg:self-start">
|
||||
<details className="panel" open={filtrosAbertos} onToggle={(e) => setFiltrosAbertos(e.currentTarget.open)}>
|
||||
<summary className="flex min-h-12 cursor-pointer list-none items-center justify-between gap-3 px-5 py-3 lg:cursor-default">
|
||||
<span className="flex items-center gap-2 text-sm font-semibold text-ink">
|
||||
<SlidersHorizontal className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEn ? "Filters" : isEs ? "Filtros" : "Filtros"}
|
||||
{isEn ? "Filters" : isEs ? "Filtros" : isFr ? "Filtres" : isDe ? "Filter" : "Filtros"}
|
||||
{activeFilterCount > 0 && <span className="chip chip-accent px-2 py-0">{activeFilterCount}</span>}
|
||||
</span>
|
||||
{activeFilterCount > 0 && (
|
||||
@@ -352,7 +410,7 @@ export default function PlacasPage() {
|
||||
}}
|
||||
className="text-sm font-medium text-accent hover:text-accent-strong"
|
||||
>
|
||||
{isEn ? "Clear" : isEs ? "Limpiar" : "Limpar"}
|
||||
{isEn ? "Clear" : isEs ? "Limpiar" : isFr ? "Effacer" : isDe ? "Zurücksetzen" : "Limpar"}
|
||||
</button>
|
||||
)}
|
||||
</summary>
|
||||
@@ -371,6 +429,14 @@ export default function PlacasPage() {
|
||||
? filteredBoards.length === 1
|
||||
? "placa encontrada"
|
||||
: "placas encontradas"
|
||||
: isFr
|
||||
? filteredBoards.length === 1
|
||||
? "carte trouvée"
|
||||
: "cartes trouvées"
|
||||
: isDe
|
||||
? filteredBoards.length === 1
|
||||
? "Board gefunden"
|
||||
: "Boards gefunden"
|
||||
: filteredBoards.length === 1
|
||||
? "placa encontrada"
|
||||
: "placas encontradas"}
|
||||
@@ -380,17 +446,21 @@ export default function PlacasPage() {
|
||||
<div className="card mt-4 px-6 py-14 text-center">
|
||||
<Search className="mx-auto h-10 w-10 text-muted" aria-hidden="true" />
|
||||
<h2 className="mt-4 font-display text-xl font-semibold text-ink">
|
||||
{isEn ? "No boards match these filters" : isEs ? "Ninguna placa coincide con estos filtros" : "Nenhuma placa com esses filtros"}
|
||||
{isEn ? "No boards match these filters" : isEs ? "Ninguna placa coincide con estos filtros" : isFr ? "Aucune carte ne correspond à ces filtres" : isDe ? "Keine Boards entsprechen diesen Filtern" : "Nenhuma placa com esses filtros"}
|
||||
</h2>
|
||||
<p className="mx-auto mt-2 max-w-md text-sm text-muted">
|
||||
{isEn
|
||||
? "Remove some filters or search by another name."
|
||||
: isEs
|
||||
? "Elimine algunos filtros o busque por otro nombre."
|
||||
: isFr
|
||||
? "Supprimez certains filtres ou recherchez un autre nom."
|
||||
: isDe
|
||||
? "Entfernen Sie einige Filter oder suchen Sie nach einem anderen Namen."
|
||||
: "Remova alguns filtros ou busque por outro nome."}
|
||||
</p>
|
||||
<button type="button" onClick={clearFilters} className="btn btn-primary mt-6">
|
||||
{isEn ? "Clear filters" : isEs ? "Limpiar filtros" : "Limpar filtros"}
|
||||
{isEn ? "Clear filters" : isEs ? "Limpiar filtros" : isFr ? "Effacer les filtres" : isDe ? "Filter zurücksetzen" : "Limpar filtros"}
|
||||
</button>
|
||||
</div>
|
||||
) : (
|
||||
|
||||
@@ -4,12 +4,18 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEn ? "Compare ESP32 Series: Side-by-Side Table" : isEs ? "Comparar series ESP32: tabla comparativa" : "Comparar séries ESP32",
|
||||
titulo: isEn ? "Compare ESP32 Series: Side-by-Side Table" : isEs ? "Comparar series ESP32: tabla comparativa" : isFr ? "Comparer les séries ESP32 : tableau comparatif" : isDe ? "ESP32-Serien vergleichen: Vergleichstabelle" : "Comparar séries ESP32",
|
||||
descricao: isEn
|
||||
? "Compare up to four ESP32 series side by side: processor, Wi-Fi, Bluetooth, memory, GPIO, peripherals, and hardware security, with official datasheet data."
|
||||
: isEs
|
||||
? "Compare hasta cuatro series de ESP32 frente a frente: procesador, Wi-Fi, Bluetooth, memoria, GPIO, periféricos y seguridad en hardware, con datos de hojas de datos oficiales."
|
||||
: isFr
|
||||
? "Comparez jusqu'à quatre séries d'ESP32 côte à côte : processeur, Wi-Fi, Bluetooth, mémoire, GPIO, périphériques et sécurité matérielle, avec les données des fiches techniques officielles."
|
||||
: isDe
|
||||
? "Vergleichen Sie bis zu vier ESP32-Serien nebeneinander: Prozessor, Wi-Fi, Bluetooth, Speicher, GPIO, Peripherie und Hardware-Sicherheit mit Daten aus offiziellen Datenblättern."
|
||||
: "Compare até quatro séries de ESP32 lado a lado: processador, Wi-Fi, Bluetooth, memória, GPIO, periféricos e segurança em hardware, com os dados dos datasheets oficiais.",
|
||||
caminho: "/comparacao",
|
||||
locale,
|
||||
@@ -17,6 +23,10 @@ export async function generateMetadata({ params }) {
|
||||
? ["compare ESP32", "ESP32 vs ESP32-S3", "ESP32 comparison table", "which ESP32 is best"]
|
||||
: isEs
|
||||
? ["comparar ESP32", "ESP32 vs ESP32-S3", "tabla comparativa ESP32", "cuál ESP32 es mejor"]
|
||||
: isFr
|
||||
? ["comparer ESP32", "ESP32 vs ESP32-S3", "tableau comparatif ESP32", "quel ESP32 choisir"]
|
||||
: isDe
|
||||
? ["ESP32 vergleichen", "ESP32 vs ESP32-S3", "ESP32 Vergleichstabelle", "welcher ESP32 ist der beste"]
|
||||
: ["comparar ESP32", "ESP32 vs ESP32-S3", "tabela comparativa ESP32", "qual ESP32 é melhor"],
|
||||
});
|
||||
}
|
||||
@@ -66,12 +76,44 @@ const faqsEs = [
|
||||
},
|
||||
];
|
||||
|
||||
const faqsFr = [
|
||||
{
|
||||
pergunta: "Comment comparer les microcontrôleurs ESP32 côte à côte ?",
|
||||
resposta: "Le comparateur d'ESPDocs vous permet de sélectionner jusqu'à quatre séries simultanément pour confronter architecture, fréquence d'horloge, mémoire SRAM/PSRAM, normes radio (Wi-Fi 4/6, Bluetooth 5/6, 802.15.4), interfaces de périphériques et blocs de sécurité matérielle.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quelle est la différence entre l'ESP32 classique et l'ESP32-S3 ?",
|
||||
resposta: "L'ESP32 classique utilise des cœurs Xtensa LX6 et le Bluetooth classique/LE. L'ESP32-S3 intègre des cœurs Xtensa LX7 avec instructions vectorielles pour l'intelligence artificielle (TinyML), l'USB natif OTG, davantage de GPIOs (45 contre 36) et le Bluetooth 5.0 LE.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quelle est la différence entre l'ESP32-C3 et l'ESP32-C6 ?",
|
||||
resposta: "L'ESP32-C3 est un microcontrôleur RISC-V avec Wi-Fi 4 et Bluetooth 5 LE. L'ESP32-C6 évolue vers le Wi-Fi 6 (802.11ax), le Bluetooth 5.4 LE, une radio IEEE 802.15.4 pour Zigbee 3.0 et Thread 1.3, ainsi qu'un coprocesseur à ultra-faible consommation.",
|
||||
},
|
||||
];
|
||||
|
||||
const faqsDe = [
|
||||
{
|
||||
pergunta: "Wie lassen sich ESP32-Mikrocontroller im direkten Vergleich gegenüberstellen?",
|
||||
resposta: "Der ESPDocs-Vergleich ermöglicht es Ihnen, bis zu vier Serien gleichzeitig auszuwählen, um Architektur, Taktfrequenz, SRAM/PSRAM-Speicher, Funkstandards (Wi-Fi 4/6, Bluetooth 5/6, 802.15.4), Peripherieschnittstellen und Hardware-Sicherheitsblöcke zu vergleichen.",
|
||||
},
|
||||
{
|
||||
pergunta: "Was ist der Unterschied zwischen dem klassischen ESP32 und dem ESP32-S3?",
|
||||
resposta: "Der klassische ESP32 nutzt Xtensa-LX6-Kerne und klassisches Bluetooth/LE. Der ESP32-S3 bietet Xtensa-LX7-Kerne mit Vektoranweisungen für künstliche Intelligenz (TinyML), natives USB-OTG, mehr GPIOs (45 gegenüber 36) und Bluetooth 5.0 LE.",
|
||||
},
|
||||
{
|
||||
pergunta: "Was ist der Unterschied zwischen ESP32-C3 und ESP32-C6?",
|
||||
resposta: "Der ESP32-C3 ist ein RISC-V-Mikrocontroller mit Wi-Fi 4 und Bluetooth 5 LE. Der ESP32-C6 erweitert dies um Wi-Fi 6 (802.11ax), Bluetooth 5.4 LE, ein IEEE-802.15.4-Funkmodul für Zigbee 3.0 und Thread 1.3 sowie einen extrem stromsparenden Coprozessor.",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function Layout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const faqs = isEn ? faqsEn : isEs ? faqsEs : faqsPt;
|
||||
const canonPath = isEn ? "/en/compare" : isEs ? "/es/comparacion" : "/comparacao";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const faqs = isEn ? faqsEn : isEs ? faqsEs : isFr ? faqsFr : isDe ? faqsDe : faqsPt;
|
||||
const canonPath = isEn ? "/en/compare" : isEs ? "/es/comparacion" : isFr ? "/fr/comparaison" : isDe ? "/de/vergleich" : "/comparacao";
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -80,11 +122,15 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.aplicacaoWeb({
|
||||
nome: isEn ? "ESP32 Series Comparator" : isEs ? "Comparador de series ESP32" : "Comparador de Séries ESP32",
|
||||
nome: isEn ? "ESP32 Series Comparator" : isEs ? "Comparador de series ESP32" : isFr ? "Comparateur de séries ESP32" : isDe ? "ESP32-Serien-Vergleich" : "Comparador de Séries ESP32",
|
||||
descricao: isEn
|
||||
? "Technical comparison table to analyze specifications, pinouts, and features of multiple ESP32 series."
|
||||
: isEs
|
||||
? "Tabla comparativa técnica para analizar especificaciones, patillaje y características de múltiples series de ESP32."
|
||||
: isFr
|
||||
? "Tableau comparatif technique pour analyser les spécifications, le brochage et les fonctionnalités de plusieurs séries ESP32."
|
||||
: isDe
|
||||
? "Technische Vergleichstabelle zur Analyse von Spezifikationen, Pinbelegungen und Merkmalen mehrerer ESP32-Serien."
|
||||
: "Tabela comparativa técnica para analisar especificações, pinagens e recursos de múltiplas séries de ESP32.",
|
||||
caminho: canonPath,
|
||||
locale,
|
||||
@@ -97,8 +143,8 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEn ? "Home" : isEs ? "Inicio" : "Início", caminho: isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isEn ? "Compare Series" : isEs ? "Comparar series" : "Comparar Séries", caminho: canonPath },
|
||||
{ nome: isEn ? "Home" : isEs ? "Inicio" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEn ? "/en" : isEs ? "/es" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: isEn ? "Compare Series" : isEs ? "Comparar series" : isFr ? "Comparer les séries" : isDe ? "Serien vergleichen" : "Comparar Séries", caminho: canonPath },
|
||||
])
|
||||
),
|
||||
}}
|
||||
|
||||
@@ -9,6 +9,8 @@ import Link from "next/link";
|
||||
import seriesDataPt from "@/public/series.json";
|
||||
import seriesDataEn from "@/data/en/series.json";
|
||||
import seriesDataEs from "@/data/es/series.json";
|
||||
import seriesDataFr from "@/data/fr/series.json";
|
||||
import seriesDataDe from "@/data/de/series.json";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import { ArrowRight, ArrowUpRight, Check, ChevronDown, Scale } from "lucide-react";
|
||||
|
||||
@@ -257,19 +259,179 @@ const COMPARE_FIELDS_ES = [
|
||||
]},
|
||||
];
|
||||
|
||||
const COMPARE_FIELDS_FR = [
|
||||
{ category: "Général", fields: [
|
||||
{ key: "nome_completo", label: "Nom complet" },
|
||||
{ key: "descricao", label: "Description" },
|
||||
]},
|
||||
{ category: "Disponibilité et outils", fields: [
|
||||
{ key: "esp_idf_minimo", label: "ESP-IDF minimum" },
|
||||
{ key: "arduino_core", label: "Core Arduino" },
|
||||
{ key: "depuracao", label: "Débogage / JTAG" },
|
||||
{ key: "encapsulamento", label: "Boîtier" },
|
||||
{ key: "modulos", label: "Modules disponibles" },
|
||||
]},
|
||||
{ category: "Processeur", fields: [
|
||||
{ key: "arquitetura", label: "Architecture" },
|
||||
{ key: "nucleos", label: "Cœurs" },
|
||||
{ key: "frequencia", label: "Fréquence" },
|
||||
{ key: "coprocessador_ulp", label: "Coprocesseur ULP" },
|
||||
{ key: "aceleradores_ia", label: "Accélérateurs IA" },
|
||||
]},
|
||||
{ category: "Connectivité", fields: [
|
||||
{ key: "wifi", label: "Wi-Fi" },
|
||||
{ key: "bluetooth", label: "Bluetooth" },
|
||||
{ key: "zigbee_thread", label: "Zigbee/Thread" },
|
||||
{ key: "matter", label: "Matter" },
|
||||
{ key: "ethernet", label: "Ethernet" },
|
||||
]},
|
||||
{ category: "Mémoire", fields: [
|
||||
{ key: "memoria_sram", label: "SRAM" },
|
||||
{ key: "memoria_sram_rtc", label: "SRAM RTC" },
|
||||
{ key: "memoria_rom", label: "ROM" },
|
||||
{ key: "flash_externa", label: "Flash externe" },
|
||||
{ key: "psram_externa", label: "PSRAM externe" },
|
||||
]},
|
||||
{ category: "Périphériques numériques", fields: [
|
||||
{ key: "gpio", label: "GPIO" },
|
||||
{ key: "uart", label: "UART" },
|
||||
{ key: "spi", label: "SPI" },
|
||||
{ key: "i2c", label: "I²C" },
|
||||
{ key: "i2s", label: "I²S" },
|
||||
{ key: "pwm", label: "PWM" },
|
||||
{ key: "can", label: "CAN" },
|
||||
{ key: "usb", label: "USB" },
|
||||
{ key: "depuracao", label: "Débogage / JTAG" },
|
||||
{ key: "sdio", label: "SDIO" },
|
||||
]},
|
||||
{ category: "Périphériques analogiques", fields: [
|
||||
{ key: "adc", label: "ADC" },
|
||||
{ key: "dac", label: "DAC" },
|
||||
{ key: "touch", label: "Touch capacitif" },
|
||||
{ key: "sensor_hall", label: "Capteur Hall" },
|
||||
{ key: "sensor_temperatura", label: "Capteur de température" },
|
||||
]},
|
||||
{ category: "Sécurité", fields: [
|
||||
{ key: "seguranca.aes", label: "AES" },
|
||||
{ key: "seguranca.sha", label: "SHA" },
|
||||
{ key: "seguranca.rsa", label: "RSA / MPI" },
|
||||
{ key: "seguranca.ecc", label: "ECC (courbes elliptiques)" },
|
||||
{ key: "seguranca.ecdsa", label: "ECDSA matériel" },
|
||||
{ key: "seguranca.hmac", label: "HMAC" },
|
||||
{ key: "seguranca.assinatura_digital", label: "Signature numérique (DS)" },
|
||||
{ key: "seguranca.key_manager", label: "Key Manager" },
|
||||
{ key: "seguranca.rng", label: "Générateur aléatoire (TRNG)" },
|
||||
{ key: "seguranca.criptografia_flash", label: "Chiffrement de flash" },
|
||||
{ key: "seguranca.secure_boot", label: "Secure Boot" },
|
||||
{ key: "seguranca.protecao_dpa", label: "Protection contre DPA" },
|
||||
]},
|
||||
{ category: "Interfaces spéciales", fields: [
|
||||
{ key: "lcd", label: "LCD" },
|
||||
{ key: "camera", label: "Caméra" },
|
||||
{ key: "mipi_csi", label: "MIPI CSI" },
|
||||
{ key: "mipi_dsi", label: "MIPI DSI" },
|
||||
{ key: "ethernet_mac", label: "Ethernet MAC" },
|
||||
]},
|
||||
{ category: "Spécifications environnementales", fields: [
|
||||
{ key: "temperatura_operacao", label: "Temp. de fonctionnement" },
|
||||
{ key: "temperatura_armazenamento", label: "Temp. de stockage" },
|
||||
]},
|
||||
];
|
||||
|
||||
const COMPARE_FIELDS_DE = [
|
||||
{ category: "Allgemein", fields: [
|
||||
{ key: "nome_completo", label: "Vollständiger Name" },
|
||||
{ key: "descricao", label: "Beschreibung" },
|
||||
]},
|
||||
{ category: "Verfügbarkeit und Werkzeuge", fields: [
|
||||
{ key: "esp_idf_minimo", label: "Mindest-ESP-IDF" },
|
||||
{ key: "arduino_core", label: "Arduino-Core" },
|
||||
{ key: "depuracao", label: "Debugging / JTAG" },
|
||||
{ key: "encapsulamento", label: "Gehäuse" },
|
||||
{ key: "modulos", label: "Verfügbare Module" },
|
||||
]},
|
||||
{ category: "Prozessor", fields: [
|
||||
{ key: "arquitetura", label: "Architektur" },
|
||||
{ key: "nucleos", label: "Kerne" },
|
||||
{ key: "frequencia", label: "Taktfrequenz" },
|
||||
{ key: "coprocessador_ulp", label: "ULP-Coprozessor" },
|
||||
{ key: "aceleradores_ia", label: "KI-Beschleuniger" },
|
||||
]},
|
||||
{ category: "Konnektivität", fields: [
|
||||
{ key: "wifi", label: "Wi-Fi" },
|
||||
{ key: "bluetooth", label: "Bluetooth" },
|
||||
{ key: "zigbee_thread", label: "Zigbee/Thread" },
|
||||
{ key: "matter", label: "Matter" },
|
||||
{ key: "ethernet", label: "Ethernet" },
|
||||
]},
|
||||
{ category: "Speicher", fields: [
|
||||
{ key: "memoria_sram", label: "SRAM" },
|
||||
{ key: "memoria_sram_rtc", label: "RTC-SRAM" },
|
||||
{ key: "memoria_rom", label: "ROM" },
|
||||
{ key: "flash_externa", label: "Externer Flash" },
|
||||
{ key: "psram_externa", label: "Externer PSRAM" },
|
||||
]},
|
||||
{ category: "Digitale Peripherie", fields: [
|
||||
{ key: "gpio", label: "GPIO" },
|
||||
{ key: "uart", label: "UART" },
|
||||
{ key: "spi", label: "SPI" },
|
||||
{ key: "i2c", label: "I²C" },
|
||||
{ key: "i2s", label: "I²S" },
|
||||
{ key: "pwm", label: "PWM" },
|
||||
{ key: "can", label: "CAN" },
|
||||
{ key: "usb", label: "USB" },
|
||||
{ key: "depuracao", label: "Debugging / JTAG" },
|
||||
{ key: "sdio", label: "SDIO" },
|
||||
]},
|
||||
{ category: "Analoge Peripherie", fields: [
|
||||
{ key: "adc", label: "ADC" },
|
||||
{ key: "dac", label: "DAC" },
|
||||
{ key: "touch", label: "Kapazitiver Touch" },
|
||||
{ key: "sensor_hall", label: "Hall-Sensor" },
|
||||
{ key: "sensor_temperatura", label: "Temperatursensor" },
|
||||
]},
|
||||
{ category: "Sicherheit", fields: [
|
||||
{ key: "seguranca.aes", label: "AES" },
|
||||
{ key: "seguranca.sha", label: "SHA" },
|
||||
{ key: "seguranca.rsa", label: "RSA / MPI" },
|
||||
{ key: "seguranca.ecc", label: "ECC (Elliptische Kurven)" },
|
||||
{ key: "seguranca.ecdsa", label: "Hardware-ECDSA" },
|
||||
{ key: "seguranca.hmac", label: "HMAC" },
|
||||
{ key: "seguranca.assinatura_digital", label: "Digitale Signatur (DS)" },
|
||||
{ key: "seguranca.key_manager", label: "Key Manager" },
|
||||
{ key: "seguranca.rng", label: "Zufallsgenerator (TRNG)" },
|
||||
{ key: "seguranca.criptografia_flash", label: "Flash-Verschlüsselung" },
|
||||
{ key: "seguranca.secure_boot", label: "Secure Boot" },
|
||||
{ key: "seguranca.protecao_dpa", label: "DPA-Schutz" },
|
||||
]},
|
||||
{ category: "Spezielle Schnittstellen", fields: [
|
||||
{ key: "lcd", label: "LCD" },
|
||||
{ key: "camera", label: "Kamera" },
|
||||
{ key: "mipi_csi", label: "MIPI CSI" },
|
||||
{ key: "mipi_dsi", label: "MIPI DSI" },
|
||||
{ key: "ethernet_mac", label: "Ethernet MAC" },
|
||||
]},
|
||||
{ category: "Umgebungsbedingungen", fields: [
|
||||
{ key: "temperatura_operacao", label: "Betriebstemp." },
|
||||
{ key: "temperatura_armazenamento", label: "Lagertemp." },
|
||||
]},
|
||||
];
|
||||
|
||||
export default function Comparacao() {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const compareFields = isEs ? COMPARE_FIELDS_ES : isEn ? COMPARE_FIELDS_EN : COMPARE_FIELDS_PT;
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : isFr ? "fr" : isDe ? "de" : "pt";
|
||||
const seriesData = isEs ? seriesDataEs : isEn ? seriesDataEn : isFr ? seriesDataFr : isDe ? seriesDataDe : seriesDataPt;
|
||||
const compareFields = isEs ? COMPARE_FIELDS_ES : isEn ? COMPARE_FIELDS_EN : isFr ? COMPARE_FIELDS_FR : isDe ? COMPARE_FIELDS_DE : COMPARE_FIELDS_PT;
|
||||
|
||||
const [selectedSeries, setSelectedSeries] = useState(["ESP32", "ESP32-S3"]);
|
||||
const [soDiferencas, setSoDiferencas] = useState(false);
|
||||
const [collapsedCategories, setCollapsedCategories] = useState(() => ({
|
||||
[isEs ? "Interfaces especiales" : isEn ? "Special Interfaces" : "Interfaces Especiais"]: true,
|
||||
[isEs ? "Especificaciones ambientales" : isEn ? "Environmental Specifications" : "Especificações Ambientais"]: true,
|
||||
[isEs ? "Interfaces especiales" : isEn ? "Special Interfaces" : isFr ? "Interfaces spéciales" : isDe ? "Spezielle Schnittstellen" : "Interfaces Especiais"]: true,
|
||||
[isEs ? "Especificaciones ambientales" : isEn ? "Environmental Specifications" : isFr ? "Spécifications environnementales" : isDe ? "Umgebungsbedingungen" : "Especificações Ambientais"]: true,
|
||||
}));
|
||||
|
||||
const series = Object.entries(seriesData);
|
||||
@@ -295,19 +457,19 @@ export default function Comparacao() {
|
||||
};
|
||||
|
||||
const renderValue = (value) => {
|
||||
if (!value || value === "Não" || value === "No") return <span className="text-muted">{isEs || isEn ? "No" : "Não"}</span>;
|
||||
if (value === "Sim" || value === "Yes" || value === "Sí") {
|
||||
if (!value || value === "Não" || value === "No" || value === "Non" || value === "Nein") return <span className="text-muted">{isEs || isEn ? "No" : isFr ? "Non" : isDe ? "Nein" : "Não"}</span>;
|
||||
if (value === "Sim" || value === "Yes" || value === "Sí" || value === "Oui" || value === "Ja") {
|
||||
return (
|
||||
<span className="inline-flex items-center gap-1.5 font-medium text-ok">
|
||||
<Check className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Sí" : isEn ? "Yes" : "Sim"}
|
||||
{isEs ? "Sí" : isEn ? "Yes" : isFr ? "Oui" : isDe ? "Ja" : "Sim"}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
return <span className="font-medium text-ink">{value}</span>;
|
||||
};
|
||||
|
||||
const valores = (key) => selectedSeries.map((k) => String(valorDe(seriesData[k], key) ?? (isEs || isEn ? "No" : "Não")));
|
||||
const valores = (key) => selectedSeries.map((k) => String(valorDe(seriesData[k], key) ?? (isEs || isEn ? "No" : isFr ? "Non" : isDe ? "Nein" : "Não")));
|
||||
const diferem = (key) => new Set(valores(key)).size > 1;
|
||||
|
||||
return (
|
||||
@@ -318,15 +480,21 @@ export default function Comparacao() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Comparador" : isEn ? "Comparator" : "Comparador" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEs ? "Comparador" : isEn ? "Comparator" : isFr ? "Comparateur" : isDe ? "Vergleich" : "Comparador" }]}
|
||||
icon={Scale}
|
||||
label={isEs ? "Hasta cuatro series lado a lado" : isEn ? "Up to four series side by side" : "Até quatro séries lado a lado"}
|
||||
title={isEs ? "Comparador de series ESP32" : isEn ? "ESP32 Series Comparator" : "Comparador de séries"}
|
||||
label={isEs ? "Hasta cuatro series lado a lado" : isEn ? "Up to four series side by side" : isFr ? "Jusqu'à quatre séries côte à côte" : isDe ? "Bis zu vier Serien im Vergleich" : "Até quatro séries lado a lado"}
|
||||
title={isEs ? "Comparador de series ESP32" : isEn ? "ESP32 Series Comparator" : isFr ? "Comparateur de séries ESP32" : isDe ? "ESP32-Serien-Vergleich" : "Comparador de séries"}
|
||||
lede={
|
||||
isEs
|
||||
? "Ponga núcleos, radio, memoria, periféricos y seguridad en la misma tabla y vea lo que realmente cambia de un chip a otro."
|
||||
: isEn
|
||||
? "Put cores, radio, memory, peripherals, and security in the same table and see what really changes from chip to chip."
|
||||
: isFr
|
||||
? "Placez les cœurs, la radio, la mémoire, les périphériques et la sécurité dans le même tableau et voyez ce qui change réellement d'une puce à l'autre."
|
||||
: isDe
|
||||
? "Stellen Sie Kerne, Funk, Speicher, Peripherie und Sicherheit in derselben Tabelle gegenüber und sehen Sie, was sich wirklich von Chip zu Chip ändert."
|
||||
: "Coloque núcleos, rádio, memória, periféricos e segurança na mesma tabela e veja o que realmente muda de um chip para outro."
|
||||
}
|
||||
/>
|
||||
@@ -340,6 +508,10 @@ export default function Comparacao() {
|
||||
<>Elija de {MIN_SERIES} a {MAX_SERIES} series</>
|
||||
) : isEn ? (
|
||||
<>Choose {MIN_SERIES} to {MAX_SERIES} series</>
|
||||
) : isFr ? (
|
||||
<>Choisissez de {MIN_SERIES} à {MAX_SERIES} séries</>
|
||||
) : isDe ? (
|
||||
<>Wählen Sie {MIN_SERIES} bis {MAX_SERIES} Serien</>
|
||||
) : (
|
||||
<>Escolha de {MIN_SERIES} a {MAX_SERIES} séries</>
|
||||
)}
|
||||
@@ -355,6 +527,16 @@ export default function Comparacao() {
|
||||
{selectedSeries.length} of {MAX_SERIES} selected
|
||||
{selectedSeries.length === MAX_SERIES && ". Remove one to switch."}
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
{selectedSeries.length} sur {MAX_SERIES} sélectionnées
|
||||
{selectedSeries.length === MAX_SERIES && ". Supprimez-en une pour en changer."}
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
{selectedSeries.length} von {MAX_SERIES} ausgewählt
|
||||
{selectedSeries.length === MAX_SERIES && ". Entfernen Sie eine zum Wechseln."}
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
{selectedSeries.length} de {MAX_SERIES} selecionadas
|
||||
@@ -389,7 +571,7 @@ export default function Comparacao() {
|
||||
<section className="shell mt-8" aria-labelledby="tabela-titulo">
|
||||
<div className="flex flex-wrap items-center justify-between gap-3">
|
||||
<h2 id="tabela-titulo" className="text-base font-semibold text-ink">
|
||||
{isEs ? "Especificaciones" : isEn ? "Specifications" : "Especificações"}
|
||||
{isEs ? "Especificaciones" : isEn ? "Specifications" : isFr ? "Spécifications" : isDe ? "Spezifikationen" : "Especificações"}
|
||||
</h2>
|
||||
<label className="flex min-h-11 cursor-pointer items-center gap-2.5 text-sm font-medium text-ink-soft">
|
||||
<input
|
||||
@@ -398,7 +580,7 @@ export default function Comparacao() {
|
||||
onChange={(e) => setSoDiferencas(e.target.checked)}
|
||||
className="h-5 w-5 cursor-pointer accent-[var(--accent)]"
|
||||
/>
|
||||
{isEs ? "Mostrar solo diferencias" : isEn ? "Show differences only" : "Mostrar só as diferenças"}
|
||||
{isEs ? "Mostrar solo diferencias" : isEn ? "Show differences only" : isFr ? "Afficher uniquement les différences" : isDe ? "Nur Unterschiede anzeigen" : "Mostrar só as diferenças"}
|
||||
</label>
|
||||
</div>
|
||||
|
||||
@@ -410,6 +592,10 @@ export default function Comparacao() {
|
||||
<>Comparación de las series {selectedSeries.join(", ")}</>
|
||||
) : isEn ? (
|
||||
<>Comparison of series {selectedSeries.join(", ")}</>
|
||||
) : isFr ? (
|
||||
<>Comparaison des séries {selectedSeries.join(", ")}</>
|
||||
) : isDe ? (
|
||||
<>Vergleich der Serien {selectedSeries.join(", ")}</>
|
||||
) : (
|
||||
<>Comparação das séries {selectedSeries.join(", ")}</>
|
||||
)}
|
||||
@@ -417,7 +603,7 @@ export default function Comparacao() {
|
||||
<thead>
|
||||
<tr className="border-b border-line bg-surface-2">
|
||||
<th scope="col" className="sticky left-0 z-20 w-28 bg-surface-2 px-4 py-4 text-left font-semibold text-muted sm:w-52 sm:px-6">
|
||||
{isEs ? "Especificación" : isEn ? "Specification" : "Especificação"}
|
||||
{isEs ? "Especificación" : isEn ? "Specification" : isFr ? "Spécification" : isDe ? "Spezifikation" : "Especificação"}
|
||||
</th>
|
||||
{selectedSeries.map((seriesKey) => (
|
||||
<th key={seriesKey} scope="col" className="min-w-40 px-4 py-4 text-left sm:px-6">
|
||||
@@ -474,7 +660,7 @@ export default function Comparacao() {
|
||||
|
||||
<section className="shell section" aria-labelledby="docs-titulo">
|
||||
<h2 id="docs-titulo" className="section-title">
|
||||
{isEs ? "Documentación oficial" : isEn ? "Official documentation" : "Documentação oficial"}
|
||||
{isEs ? "Documentación oficial" : isEn ? "Official documentation" : isFr ? "Documentation officielle" : isDe ? "Offizielle Dokumentation" : "Documentação oficial"}
|
||||
</h2>
|
||||
<div className="mt-6 grid gap-3 sm:grid-cols-2 lg:grid-cols-4">
|
||||
{selectedSeries.map((seriesKey) => {
|
||||
@@ -486,13 +672,13 @@ export default function Comparacao() {
|
||||
</Link>
|
||||
{seriesItem.datasheet ? (
|
||||
<a href={seriesItem.datasheet} target="_blank" rel="noopener noreferrer" className="btn btn-ghost btn-sm">
|
||||
{isEs ? "Datasheet oficial" : isEn ? "Official datasheet" : "Datasheet oficial"}
|
||||
{isEs ? "Datasheet oficial" : isEn ? "Official datasheet" : isFr ? "Fiche technique officielle" : isDe ? "Offizielles Datenblatt" : "Datasheet oficial"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : "(abre em nova aba)"}</span>
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : isFr ? "(ouvre un nouvel onglet)" : isDe ? "(öffnet in neuem Tab)" : "(abre em nova aba)"}</span>
|
||||
</a>
|
||||
) : (
|
||||
<span className="text-sm text-muted">
|
||||
{isEs ? "Datasheet aún no publicado" : isEn ? "Datasheet not yet published" : "Datasheet ainda não publicado"}
|
||||
{isEs ? "Datasheet aún no publicado" : isEn ? "Datasheet not yet published" : isFr ? "Fiche technique pas encore publiée" : isDe ? "Datenblatt noch nicht veröffentlicht" : "Datasheet ainda não publicado"}
|
||||
</span>
|
||||
)}
|
||||
</div>
|
||||
@@ -503,18 +689,22 @@ export default function Comparacao() {
|
||||
<div className="panel mt-10 flex flex-col items-start justify-between gap-6 p-7 sm:p-10 md:flex-row md:items-center">
|
||||
<div className="max-w-2xl">
|
||||
<h2 className="section-title">
|
||||
{isEs ? "¿Desea probar en banco?" : isEn ? "Want to test on the bench?" : "Quer testar na bancada?"}
|
||||
{isEs ? "¿Desea probar en banco?" : isEn ? "Want to test on the bench?" : isFr ? "Envie de tester sur l'établi ?" : isDe ? "Möchten Sie es auf dem Prüfplatz testen ?" : "Quer testar na bancada?"}
|
||||
</h2>
|
||||
<p className="mt-3 text-base text-muted">
|
||||
{isEs
|
||||
? "Vea las placas de desarrollo con patillaje, periféricos y enlace a la tienda oficial."
|
||||
: isEn
|
||||
? "Explore development boards with pinouts, peripherals, and official store links."
|
||||
: isFr
|
||||
? "Découvrez les cartes de développement avec brochage, périphériques et lien vers la boutique officielle."
|
||||
: isDe
|
||||
? "Entdecken Sie die Entwicklungsboards mit Pinbelegung, Peripherie und Link zum offiziellen Store."
|
||||
: "Veja as placas de desenvolvimento com pinagem, periféricos e link para a loja."}
|
||||
</p>
|
||||
</div>
|
||||
<Link href={getLocalizedHref("/catalogo", currentLocale)} className="btn btn-primary shrink-0">
|
||||
{isEs ? "Ver catálogo de placas" : isEn ? "View boards catalog" : "Ver catálogo de placas"}
|
||||
{isEs ? "Ver catálogo de placas" : isEn ? "View boards catalog" : isFr ? "Voir le catalogue de cartes" : isDe ? "Board-Katalog ansehen" : "Ver catálogo de placas"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
@@ -4,16 +4,18 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEs
|
||||
? "ESP Component Registry & IDF Component Manager · ESPDocs"
|
||||
: isEn
|
||||
? "ESP Component Registry & IDF Component Manager · ESPDocs"
|
||||
: "ESP Component Registry & IDF Component Manager · ESPDocs",
|
||||
titulo: "ESP Component Registry & IDF Component Manager · ESPDocs",
|
||||
descricao: isEs
|
||||
? "Catálogo interactivo del ESP Component Registry: controladores de pantalla, LVGL, reconocimiento de voz ESP-SR, RainMaker, BSPs y generador de idf_component.yml."
|
||||
: isEn
|
||||
? "Official interactive catalog of the ESP Component Registry: display drivers, LVGL, ESP-SR voice recognition, RainMaker, BSPs, and idf_component.yml generator."
|
||||
: isFr
|
||||
? "Catalogue interactif du ESP Component Registry : pilotes d'écran, LVGL, reconnaissance vocale ESP-SR, RainMaker, BSPs et générateur d'idf_component.yml."
|
||||
: isDe
|
||||
? "Interaktiver Katalog der ESP Component Registry: Display-Treiber, LVGL, ESP-SR-Sprachkennung, RainMaker, BSPs und idf_component.yml-Generator."
|
||||
: "Catálogo oficial e interativo do ESP Component Registry: drivers de displays, LVGL, reconhecimento de voz ESP-SR, RainMaker, BSPs e gerador de idf_component.yml.",
|
||||
caminho: "/componentes",
|
||||
locale,
|
||||
@@ -41,6 +43,30 @@ export async function generateMetadata({ params }) {
|
||||
"espressif esp-sr",
|
||||
"ESP-IDF libraries",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"ESP Component Registry",
|
||||
"IDF Component Manager",
|
||||
"idf_component.yml",
|
||||
"idf.py add-dependency",
|
||||
"composants ESP32",
|
||||
"espressif esp_lvgl_port",
|
||||
"espressif esp_rainmaker",
|
||||
"espressif esp-sr",
|
||||
"bibliothèques ESP-IDF",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
"ESP Component Registry",
|
||||
"IDF Component Manager",
|
||||
"idf_component.yml",
|
||||
"idf.py add-dependency",
|
||||
"ESP32 Komponenten",
|
||||
"espressif esp_lvgl_port",
|
||||
"espressif esp_rainmaker",
|
||||
"espressif esp-sr",
|
||||
"ESP-IDF Bibliotheken",
|
||||
]
|
||||
: [
|
||||
"ESP Component Registry",
|
||||
"IDF Component Manager",
|
||||
@@ -112,11 +138,52 @@ const faqsEs = [
|
||||
},
|
||||
];
|
||||
|
||||
const faqsFr = [
|
||||
{
|
||||
pergunta: "Qu'est-ce que l'ESP Component Registry et l'IDF Component Manager ?",
|
||||
resposta: "L'ESP Component Registry (components.espressif.com) est le dépôt officiel de paquets modulaires d'Espressif. L'IDF Component Manager est l'outil intégré à ESP-IDF (dès la v4.4 et standard en v5.x+) qui télécharge, compile et résout automatiquement les versions des dépendances à partir du manifeste idf_component.yml.",
|
||||
},
|
||||
{
|
||||
pergunta: "Comment ajouter un composant à mon projet ESP-IDF ?",
|
||||
resposta: "Vous pouvez exécuter la commande 'idf.py add-dependency \"namespace/composant^version\"' dans le terminal de votre projet (par exemple : idf.py add-dependency \"espressif/esp_lvgl_port^2.4.0\") ou modifier directement le fichier main/idf_component.yml.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quelle est la différence entre le Component Registry et les sous-modules git ?",
|
||||
resposta: "Le Component Registry élimine la complexité de gestion des sous-modules Git volumineux et des versions manuelles. Il apporte le versionnement sémantique (^ et ~), la résolution automatique des dépendances transitives et la compilation modulaire à la demande.",
|
||||
},
|
||||
{
|
||||
pergunta: "Puis-je créer et publier mes propres composants ?",
|
||||
resposta: "Oui, tout développeur ou entreprise peut publier des composants publics ou privés sur l'ESP Component Registry à l'aide de l'outil officiel Compote CLI (pip install idf-component-manager).",
|
||||
},
|
||||
];
|
||||
|
||||
const faqsDe = [
|
||||
{
|
||||
pergunta: "Was sind die ESP Component Registry und der IDF Component Manager?",
|
||||
resposta: "Die ESP Component Registry (components.espressif.com) ist das offizielle Repository für modulare Espressif-Pakete. Der IDF Component Manager ist das in ESP-IDF (ab v4.4 und Standard in v5.x+) integrierte Werkzeug, das Abhängigkeiten anhand des idf_component.yml-Manifests automatisch herunterlädt, kompiliert und auflöst.",
|
||||
},
|
||||
{
|
||||
pergunta: "Wie füge ich eine Komponente zu meinem ESP-IDF-Projekt hinzu?",
|
||||
resposta: "Sie können den Befehl 'idf.py add-dependency \"namespace/komponente^version\"' im Projektterminal ausführen (z. B.: idf.py add-dependency \"espressif/esp_lvgl_port^2.4.0\") oder direkt die Datei main/idf_component.yml bearbeiten.",
|
||||
},
|
||||
{
|
||||
pergunta: "Was ist der Unterschied zwischen der Component Registry und Git-Submodulen?",
|
||||
resposta: "Die Component Registry beseitigt die Komplexität schwerfälliger Git-Submodule und manueller Versionsverwaltung. Sie bietet semantische Versionierung (^ und ~), automatische transitive Abhängigkeitsauflösung und modulare On-Demand-Kompilierung.",
|
||||
},
|
||||
{
|
||||
pergunta: "Kann ich eigene Komponenten erstellen und veröffentlichen?",
|
||||
resposta: "Ja, Entwickler und Unternehmen können öffentliche oder private Komponenten mit dem offiziellen Compote-CLI-Tool (pip install idf-component-manager) in der ESP Component Registry veröffentlichen.",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function ComponentesLayout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : isFr ? faqsFr : isDe ? faqsDe : faqsPt;
|
||||
const canonPath = isEs ? "/es/componentes" : isEn ? "/en/components" : isFr ? "/fr/composants" : isDe ? "/de/komponenten" : "/componentes";
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -125,8 +192,8 @@ export default async function ComponentesLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: "ESP Component Registry", caminho: isEs ? "/es/componentes" : isEn ? "/en/components" : "/componentes" },
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: "ESP Component Registry", caminho: canonPath },
|
||||
])
|
||||
),
|
||||
}}
|
||||
@@ -146,13 +213,21 @@ export default async function ComponentesLayout({ children, params }) {
|
||||
? "Hub de ESP Component Registry & Generador de Manifiesto"
|
||||
: isEn
|
||||
? "ESP Component Registry Hub & Manifest Builder"
|
||||
: isFr
|
||||
? "Hub de l'ESP Component Registry & Générateur de Manifeste"
|
||||
: isDe
|
||||
? "ESP Component Registry Hub & Manifest-Generator"
|
||||
: "Hub do ESP Component Registry & Construtor de Manifesto",
|
||||
descricao: isEs
|
||||
? "Catálogo curado y generador de manifiesto idf_component.yml para componentes modulares de ESP-IDF."
|
||||
: isEn
|
||||
? "Curated catalog and idf_component.yml manifest generator for modular ESP-IDF components."
|
||||
: isFr
|
||||
? "Catalogue sélectionné et générateur de manifeste idf_component.yml pour les composants modulaires d'ESP-IDF."
|
||||
: isDe
|
||||
? "Kuratierter Katalog und idf_component.yml-Manifest-Generator für modulare ESP-IDF-Komponenten."
|
||||
: "Catálogo curado e gerador de manifesto idf_component.yml para componentes modulares do ESP-IDF.",
|
||||
caminho: isEs ? "/es/componentes" : isEn ? "/en/components" : "/componentes",
|
||||
caminho: canonPath,
|
||||
locale,
|
||||
})
|
||||
),
|
||||
|
||||
@@ -9,6 +9,8 @@ import SectionHead from "@/components/SectionHead";
|
||||
import * as componentesPt from "@/lib/componentRegistryData";
|
||||
import * as componentesEn from "@/lib/data/en/componentes";
|
||||
import * as componentesEs from "@/lib/data/es/componentes";
|
||||
import * as componentesFr from "@/lib/data/fr/componentes";
|
||||
import * as componentesDe from "@/lib/data/de/componentes";
|
||||
import {
|
||||
ArrowUpRight,
|
||||
Box,
|
||||
@@ -46,7 +48,9 @@ export default function ComponentRegistryPage() {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const { CATEGORIAS_COMPONENTES, COMPONENTES_REGISTRY, GUIA_COMPONENT_MANAGER } = isEs ? componentesEs : isEn ? componentesEn : componentesPt;
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const { CATEGORIAS_COMPONENTES, COMPONENTES_REGISTRY, GUIA_COMPONENT_MANAGER } = isEs ? componentesEs : isEn ? componentesEn : isFr ? componentesFr : isDe ? componentesDe : componentesPt;
|
||||
|
||||
const [busca, setBusca] = useState("");
|
||||
const [categoriaAtiva, setCategoriaAtiva] = useState("todos");
|
||||
@@ -104,6 +108,10 @@ export default function ComponentRegistryPage() {
|
||||
? `# No hay componentes seleccionados.\n# Haga clic en "+ Agregar al manifiesto" en las tarjetas de abajo.`
|
||||
: isEn
|
||||
? `# No components selected.\n# Click "+ Add to Manifest" on the cards below.`
|
||||
: isFr
|
||||
? `# Aucun composant sélectionné.\n# Cliquez sur "+ Ajouter au manifeste" sur les cartes ci-dessous.`
|
||||
: isDe
|
||||
? `# Keine Komponenten ausgewählt.\n# Klicken Sie auf den Karten unten auf "+ Zum Manifest hinzufügen".`
|
||||
: `# Nenhum componente selecionado.\n# Clique em "+ Adicionar ao Manifesto" nos cards abaixo.`;
|
||||
}
|
||||
|
||||
@@ -111,12 +119,16 @@ export default function ComponentRegistryPage() {
|
||||
? `# main/idf_component.yml\n# Generado mediante ESPDocs Component Hub (https://espdocs.cienciaembarcada.com.br/es/componentes)\n\ndependencies:\n`
|
||||
: isEn
|
||||
? `# main/idf_component.yml\n# Generated via ESPDocs Component Hub (https://espdocs.cienciaembarcada.com.br/en/components)\n\ndependencies:\n`
|
||||
: isFr
|
||||
? `# main/idf_component.yml\n# Généré via ESPDocs Component Hub (https://espdocs.cienciaembarcada.com.br/fr/composants)\n\ndependencies:\n`
|
||||
: isDe
|
||||
? `# main/idf_component.yml\n# Erstellt über den ESPDocs Component Hub (https://espdocs.cienciaembarcada.com.br/de/komponenten)\n\ndependencies:\n`
|
||||
: `# main/idf_component.yml\n# Gerado via ESPDocs Component Hub (https://espdocs.cienciaembarcada.com.br/componentes)\n\ndependencies:\n`;
|
||||
selecionados.forEach((c) => {
|
||||
yaml += ` ${c.namespace}/${c.name}: "${c.versao}"\n`;
|
||||
});
|
||||
return yaml;
|
||||
}, [componentesSelecionados, COMPONENTES_REGISTRY, isEn, isEs]);
|
||||
}, [componentesSelecionados, COMPONENTES_REGISTRY, isEn, isEs, isFr, isDe]);
|
||||
|
||||
const copiarManifesto = () => {
|
||||
navigator.clipboard.writeText(manifestoYaml);
|
||||
@@ -152,7 +164,9 @@ export default function ComponentRegistryPage() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Component Registry" : isEn ? "Component Registry" : "Component Registry" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEs ? "Component Registry" : isEn ? "Component Registry" : isFr ? "Component Registry" : isDe ? "Component Registry" : "Component Registry" }]}
|
||||
icon={Box}
|
||||
label="ESP-IDF Component Manager"
|
||||
title="ESP Component Registry"
|
||||
@@ -161,24 +175,28 @@ export default function ComponentRegistryPage() {
|
||||
? "El catálogo oficial de paquetes reutilizables de Espressif para ESP-IDF. Elija controladores, voz y pilas industriales, copie el comando y genere el manifiesto del proyecto."
|
||||
: isEn
|
||||
? "Official Espressif catalog of reusable packages for ESP-IDF. Choose drivers, voice stacks, and industrial protocols, copy commands, and generate project manifests."
|
||||
: isFr
|
||||
? "Le catalogue officiel de paquets réutilisables d'Espressif pour ESP-IDF. Choisissez vos pilotes, piles vocales et protocoles industriels, copiez la commande et générez le manifeste du projet."
|
||||
: isDe
|
||||
? "Der offizielle Espressif-Katalog für wiederverwendbare Pakete für ESP-IDF. Wählen Sie Treiber, Sprach- und Industrieprotokolle, kopieren Sie den Befehl und erstellen Sie das Projektmanifest."
|
||||
: "O catálogo oficial de pacotes reutilizáveis da Espressif para o ESP-IDF. Escolha drivers, voz e pilhas industriais, copie o comando e gere o manifesto do projeto."
|
||||
}
|
||||
>
|
||||
<a href="https://components.espressif.com" target="_blank" rel="noopener noreferrer" className="btn btn-primary">
|
||||
{isEs ? "Abrir el registro oficial" : isEn ? "Open official registry" : "Abrir o registro oficial"}
|
||||
{isEs ? "Abrir el registro oficial" : isEn ? "Open official registry" : isFr ? "Ouvrir le registre officiel" : isDe ? "Offizielles Repository öffnen" : "Abrir o registro oficial"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : "(abre em nova aba)"}</span>
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : isFr ? "(ouvre un nouvel onglet)" : isDe ? "(öffnet in neuem Tab)" : "(abre em nova aba)"}</span>
|
||||
</a>
|
||||
<a href="#manifesto-builder" className="btn btn-ghost">
|
||||
{isEs ? "Generar idf_component.yml" : isEn ? "Generate idf_component.yml" : "Gerar idf_component.yml"}
|
||||
{isEs ? "Generar idf_component.yml" : isEn ? "Generate idf_component.yml" : isFr ? "Générer idf_component.yml" : isDe ? "idf_component.yml erstellen" : "Gerar idf_component.yml"}
|
||||
</a>
|
||||
</PageHero>
|
||||
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Búsqueda y filtros" : isEn ? "Search and filters" : "Busca e filtros"}>
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Búsqueda y filtros" : isEn ? "Search and filters" : isFr ? "Recherche et filtres" : isDe ? "Suche und Filter" : "Busca e filtros"}>
|
||||
<div className="panel p-5 sm:p-6">
|
||||
<div className="relative">
|
||||
<label htmlFor="busca-componente" className="sr-only">
|
||||
{isEs ? "Buscar por nombre, namespace o etiqueta" : isEn ? "Search by name, namespace, or tag" : "Buscar por nome, namespace ou tag"}
|
||||
{isEs ? "Buscar por nombre, namespace o etiqueta" : isEn ? "Search by name, namespace, or tag" : isFr ? "Rechercher par nom, namespace ou tag" : isDe ? "Nach Name, Namespace oder Tag suchen" : "Buscar por nome, namespace ou tag"}
|
||||
</label>
|
||||
<Search className="pointer-events-none absolute left-4 top-1/2 h-5 w-5 -translate-y-1/2 text-muted" aria-hidden="true" />
|
||||
<input
|
||||
@@ -186,14 +204,14 @@ export default function ComponentRegistryPage() {
|
||||
type="search"
|
||||
value={busca}
|
||||
onChange={(e) => setBusca(e.target.value)}
|
||||
placeholder={isEs ? "Buscar por nombre, namespace o etiqueta" : isEn ? "Search by name, namespace, or tag" : "Buscar por nome, namespace ou tag"}
|
||||
placeholder={isEs ? "Buscar por nombre, namespace o etiqueta" : isEn ? "Search by name, namespace, or tag" : isFr ? "Rechercher par nom, namespace ou tag" : isDe ? "Nach Name, Namespace oder Tag suchen" : "Buscar por nome, namespace ou tag"}
|
||||
autoComplete="off"
|
||||
className="field pl-12 pr-4 text-base"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="mt-5">
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Categoría" : isEn ? "Category" : "Categoria"}</h2>
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Categoría" : isEn ? "Category" : isFr ? "Catégorie" : isDe ? "Kategorie" : "Categoria"}</h2>
|
||||
<div className="mt-3 flex flex-wrap gap-2">
|
||||
{CATEGORIAS_COMPONENTES.map((cat) => {
|
||||
const Icone = ICONES_CATEGORIA[cat.id] ?? Layers;
|
||||
@@ -201,7 +219,7 @@ export default function ComponentRegistryPage() {
|
||||
return (
|
||||
<button key={cat.id} type="button" onClick={() => setCategoriaAtiva(cat.id)} aria-pressed={categoriaAtiva === cat.id} className="chip-btn">
|
||||
<Icone className="h-4 w-4" aria-hidden="true" />
|
||||
{cat.id === "todos" ? (isEs ? "Todos" : isEn ? "All" : "Todos") : cat.nome.replace(/\s*\(.*\)/, "").split(",")[0].split(" &")[0]}
|
||||
{cat.id === "todos" ? (isEs ? "Todos" : isEn ? "All" : isFr ? "Tous" : isDe ? "Alle" : "Todos") : cat.nome.replace(/\s*\(.*\)/, "").split(",")[0].split(" &")[0]}
|
||||
<span className="tabular-nums opacity-80">{contagem}</span>
|
||||
</button>
|
||||
);
|
||||
@@ -210,11 +228,11 @@ export default function ComponentRegistryPage() {
|
||||
</div>
|
||||
|
||||
<div className="mt-5 border-t border-line pt-5">
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Chip compatible" : isEn ? "Compatible chip" : "Chip compatível"}</h2>
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Chip compatible" : isEn ? "Compatible chip" : isFr ? "Puce compatible" : isDe ? "Kompatibler Chip" : "Chip compatível"}</h2>
|
||||
<div className="mt-3 flex flex-wrap gap-2">
|
||||
{chipsDisponiveis.map((chip) => (
|
||||
<button key={chip} type="button" onClick={() => setChipFiltro(chip)} aria-pressed={chipFiltro === chip} className="chip-btn">
|
||||
{chip === "todos" ? (isEs ? "Todos" : isEn ? "All" : "Todos") : chip}
|
||||
{chip === "todos" ? (isEs ? "Todos" : isEn ? "All" : isFr ? "Tous" : isDe ? "Alle" : "Todos") : chip}
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
@@ -225,17 +243,17 @@ export default function ComponentRegistryPage() {
|
||||
<section className="shell section pt-8 sm:pt-10" aria-labelledby="lista-titulo">
|
||||
<div className="flex flex-wrap items-center justify-between gap-3">
|
||||
<h2 id="lista-titulo" role="status" aria-live="polite" className="text-base font-semibold text-ink">
|
||||
{componentesFiltrados.length} {componentesFiltrados.length === 1 ? (isEs ? "componente" : isEn ? "component" : "componente") : (isEs ? "componentes" : isEn ? "components" : "componentes")}
|
||||
{componentesFiltrados.length} {componentesFiltrados.length === 1 ? (isEs ? "componente" : isEn ? "component" : isFr ? "composant" : isDe ? "Komponente" : "componente") : (isEs ? "componentes" : isEn ? "components" : isFr ? "composants" : isDe ? "Komponenten" : "componentes")}
|
||||
</h2>
|
||||
<div className="flex flex-wrap items-center gap-x-5 gap-y-1">
|
||||
{totalFiltros > 0 && (
|
||||
<button type="button" onClick={limparFiltros} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
<X className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : "Limpar filtros"}
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : isFr ? "Effacer les filtres" : isDe ? "Filter zurücksetzen" : "Limpar filtros"}
|
||||
</button>
|
||||
)}
|
||||
<a href="#manifesto-builder" className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
{isEs ? "Manifiesto:" : isEn ? "Manifest:" : "Manifesto:"} {componentesSelecionados.length} {componentesSelecionados.length === 1 ? (isEs ? "componente" : isEn ? "component" : "componente") : (isEs ? "componentes" : isEn ? "components" : "componentes")}
|
||||
{isEs ? "Manifiesto:" : isEn ? "Manifest:" : isFr ? "Manifeste :" : isDe ? "Manifest :" : "Manifesto:"} {componentesSelecionados.length} {componentesSelecionados.length === 1 ? (isEs ? "componente" : isEn ? "component" : isFr ? "composant" : isDe ? "Komponente" : "componente") : (isEs ? "componentes" : isEn ? "components" : isFr ? "composants" : isDe ? "Komponenten" : "componentes")}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
@@ -244,17 +262,21 @@ export default function ComponentRegistryPage() {
|
||||
<div className="card mt-6 px-6 py-14 text-center">
|
||||
<Box className="mx-auto h-10 w-10 text-muted" aria-hidden="true" />
|
||||
<h3 className="mt-4 font-display text-xl font-semibold text-ink">
|
||||
{isEs ? "No se encontraron componentes" : isEn ? "No components found" : "Nenhum componente encontrado"}
|
||||
{isEs ? "No se encontraron componentes" : isEn ? "No components found" : isFr ? "Aucun composant trouvé" : isDe ? "Keine Komponenten gefunden" : "Nenhum componente encontrado"}
|
||||
</h3>
|
||||
<p className="mx-auto mt-2 max-w-md text-sm text-muted">
|
||||
{isEs
|
||||
? "Busque por un término más general o regrese a todas las categorías."
|
||||
: isEn
|
||||
? "Search for a more general term or return to all categories."
|
||||
: isFr
|
||||
? "Recherchez un terme plus général ou revenez à toutes les catégories."
|
||||
: isDe
|
||||
? "Suchen Sie nach einem allgemeineren Begriff oder kehren Sie zu allen Kategorien zurück."
|
||||
: "Busque por um termo mais geral ou volte para todas as categorias."}
|
||||
</p>
|
||||
<button type="button" onClick={limparFiltros} className="btn btn-primary mt-6">
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : "Limpar filtros"}
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : isFr ? "Effacer les filtres" : isDe ? "Filter zurücksetzen" : "Limpar filtros"}
|
||||
</button>
|
||||
</div>
|
||||
) : (
|
||||
@@ -274,7 +296,7 @@ export default function ComponentRegistryPage() {
|
||||
{comp.oficial && (
|
||||
<span className="chip chip-accent px-2 py-0">
|
||||
<ShieldCheck className="h-3 w-3" aria-hidden="true" />
|
||||
{isEs ? "Oficial" : isEn ? "Official" : "Oficial"}
|
||||
{isEs ? "Oficial" : isEn ? "Official" : isFr ? "Officiel" : isDe ? "Offiziell" : "Oficial"}
|
||||
</span>
|
||||
)}
|
||||
</p>
|
||||
@@ -298,12 +320,12 @@ export default function ComponentRegistryPage() {
|
||||
type="button"
|
||||
onClick={() => copiarComando(comp.id, cliCmd)}
|
||||
className="code-panel flex w-full min-h-11 items-center justify-between gap-3 rounded-lg px-3 py-2 text-left font-mono text-xs transition-colors hover:border-white/30"
|
||||
aria-label={isEs ? `Copiar comando para agregar ${comp.name}` : isEn ? `Copy command to add ${comp.name}` : `Copiar comando para adicionar ${comp.name}`}
|
||||
aria-label={isEs ? `Copiar comando para agregar ${comp.name}` : isEn ? `Copy command to add ${comp.name}` : isFr ? `Copier la commande pour ajouter ${comp.name}` : isDe ? `Befehl zum Hinzufügen von ${comp.name} kopieren` : `Copiar comando para adicionar ${comp.name}`}
|
||||
>
|
||||
<span className="truncate text-[#e9eef4]">{cliCmd}</span>
|
||||
{foiCopiado ? <Check className="h-4 w-4 shrink-0 text-[#5fe0a2]" aria-hidden="true" /> : <Copy className="h-4 w-4 shrink-0 text-[#a6afbd]" aria-hidden="true" />}
|
||||
</button>
|
||||
<p role="status" className="sr-only">{foiCopiado ? (isEs ? "Comando copiado" : isEn ? "Command copied" : "Comando copiado") : ""}</p>
|
||||
<p role="status" className="sr-only">{foiCopiado ? (isEs ? "Comando copiado" : isEn ? "Command copied" : isFr ? "Commande copiée" : isDe ? "Befehl kopiert" : "Comando copiado") : ""}</p>
|
||||
|
||||
<p className="mt-3 text-xs text-muted">
|
||||
<span className="font-medium text-ink-soft">Chips: </span>
|
||||
@@ -319,14 +341,14 @@ export default function ComponentRegistryPage() {
|
||||
className={`btn btn-sm ${selecionado ? "btn-primary" : "btn-ghost"}`}
|
||||
>
|
||||
{selecionado ? <Check className="h-4 w-4" aria-hidden="true" /> : <Plus className="h-4 w-4" aria-hidden="true" />}
|
||||
{selecionado ? (isEs ? "En manifiesto" : isEn ? "In manifest" : "No manifesto") : (isEs ? "Agregar al manifiesto" : isEn ? "Add to manifest" : "Adicionar ao manifesto")}
|
||||
{selecionado ? (isEs ? "En manifiesto" : isEn ? "In manifest" : isFr ? "Dans le manifeste" : isDe ? "Im Manifest" : "No manifesto") : (isEs ? "Agregar al manifiesto" : isEn ? "Add to manifest" : isFr ? "Ajouter au manifeste" : isDe ? "Zum Manifest hinzufügen" : "Adicionar ao manifesto")}
|
||||
</button>
|
||||
<a
|
||||
href={comp.urlRegistry}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="btn-icon inline-flex h-11 w-11 items-center justify-center rounded-full text-muted transition-colors hover:bg-surface-2 hover:text-accent"
|
||||
aria-label={isEs ? `Abrir ${comp.name} en el registro oficial (nueva pestaña)` : isEn ? `Open ${comp.name} in official registry (new tab)` : `Abrir ${comp.name} no registro oficial (nova aba)`}
|
||||
aria-label={isEs ? `Abrir ${comp.name} en el registro oficial (nueva pestaña)` : isEn ? `Open ${comp.name} in official registry (new tab)` : isFr ? `Ouvrir ${comp.name} sur le registre officiel (nouvel onglet)` : isDe ? `${comp.name} in der offiziellen Registry öffnen (neuer Tab)` : `Abrir ${comp.name} no registro oficial (nova aba)`}
|
||||
>
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
@@ -342,15 +364,19 @@ export default function ComponentRegistryPage() {
|
||||
<div className="panel p-6 sm:p-9">
|
||||
<div className="flex flex-col justify-between gap-5 md:flex-row md:items-end">
|
||||
<div className="max-w-2xl">
|
||||
<p className="eyebrow">{isEs ? "Generador de manifiesto" : isEn ? "Manifest generator" : "Gerador de manifesto"}</p>
|
||||
<p className="eyebrow">{isEs ? "Generador de manifiesto" : isEn ? "Manifest generator" : isFr ? "Générateur de manifeste" : isDe ? "Manifest-Generator" : "Gerador de manifesto"}</p>
|
||||
<h2 id="manifesto-titulo" className="section-title mt-3">
|
||||
{isEs ? "Su idf_component.yml" : isEn ? "Your idf_component.yml" : "Seu idf_component.yml"}
|
||||
{isEs ? "Su idf_component.yml" : isEn ? "Your idf_component.yml" : isFr ? "Votre idf_component.yml" : isDe ? "Ihre idf_component.yml" : "Seu idf_component.yml"}
|
||||
</h2>
|
||||
<p className="mt-3 text-sm leading-relaxed text-muted">
|
||||
{isEs ? (
|
||||
<>Guarde el archivo en la carpeta <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono">main/</code> del proyecto y ESP-IDF descargará todas las bibliotecas durante la compilación.</>
|
||||
) : isEn ? (
|
||||
<>Save this file in your project's <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono">main/</code> folder and ESP-IDF will download all dependencies during build.</>
|
||||
) : isFr ? (
|
||||
<>Enregistrez le fichier dans le dossier <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono">main/</code> du projet et ESP-IDF téléchargera toutes les bibliothèques lors de la compilation.</>
|
||||
) : isDe ? (
|
||||
<>Speichern Sie die Datei im Ordner <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono">main/</code> Ihres Projekts, und ESP-IDF lädt beim Build alle Abhängigkeiten herunter.</>
|
||||
) : (
|
||||
<>Salve o arquivo na pasta <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono">main/</code> do projeto e o ESP-IDF baixa todas as bibliotecas na compilação.</>
|
||||
)}
|
||||
@@ -359,27 +385,27 @@ export default function ComponentRegistryPage() {
|
||||
<div className="flex flex-wrap items-center gap-2">
|
||||
<button type="button" onClick={copiarManifesto} className="btn btn-primary btn-sm">
|
||||
{manifestoCopiado ? <Check className="h-4 w-4" aria-hidden="true" /> : <Copy className="h-4 w-4" aria-hidden="true" />}
|
||||
<span role="status">{manifestoCopiado ? (isEs ? "Copiado" : isEn ? "Copied" : "Copiado") : (isEs ? "Copiar YAML" : isEn ? "Copy YAML" : "Copiar YAML")}</span>
|
||||
<span role="status">{manifestoCopiado ? (isEs ? "Copiado" : isEn ? "Copied" : isFr ? "Copié" : isDe ? "Kopiert" : "Copiado") : (isEs ? "Copiar YAML" : isEn ? "Copy YAML" : isFr ? "Copier le YAML" : isDe ? "YAML kopieren" : "Copiar YAML")}</span>
|
||||
</button>
|
||||
<button type="button" onClick={baixarManifesto} className="btn btn-ghost btn-sm">
|
||||
<Download className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Descargar .yml" : isEn ? "Download .yml" : "Baixar .yml"}
|
||||
{isEs ? "Descargar .yml" : isEn ? "Download .yml" : isFr ? "Télécharger .yml" : isDe ? ".yml herunterladen" : "Baixar .yml"}
|
||||
</button>
|
||||
{componentesSelecionados.length > 0 && (
|
||||
<button type="button" onClick={() => setComponentesSelecionados([])} className="btn btn-ghost btn-sm">
|
||||
<Trash2 className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Limpiar" : isEn ? "Clear" : "Limpar"}
|
||||
{isEs ? "Limpiar" : isEn ? "Clear" : isFr ? "Effacer" : isDe ? "Leeren" : "Limpar"}
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="code-panel mt-6">
|
||||
<pre tabIndex={0} aria-label={isEs ? "Contenido de idf_component.yml" : isEn ? "Content of idf_component.yml" : "Conteúdo do idf_component.yml"} className="!text-sm"><code className="text-[#e9eef4]">{manifestoYaml}</code></pre>
|
||||
<pre tabIndex={0} aria-label={isEs ? "Contenido de idf_component.yml" : isEn ? "Content of idf_component.yml" : isFr ? "Contenu de idf_component.yml" : isDe ? "Inhalt von idf_component.yml" : "Conteúdo do idf_component.yml"} className="!text-sm"><code className="text-[#e9eef4]">{manifestoYaml}</code></pre>
|
||||
</div>
|
||||
|
||||
{componentesSelecionados.length > 0 && (
|
||||
<ul className="mt-5 flex flex-wrap items-center gap-2" aria-label={isEs ? "Componentes incluidos" : isEn ? "Included components" : "Componentes incluídos"}>
|
||||
<ul className="mt-5 flex flex-wrap items-center gap-2" aria-label={isEs ? "Componentes incluidos" : isEn ? "Included components" : isFr ? "Composants inclus" : isDe ? "Enthaltene Komponenten" : "Componentes incluídos"}>
|
||||
{componentesSelecionados.map((id) => {
|
||||
const c = COMPONENTES_REGISTRY.find((item) => item.id === id);
|
||||
if (!c) return null;
|
||||
@@ -390,7 +416,7 @@ export default function ComponentRegistryPage() {
|
||||
type="button"
|
||||
onClick={() => toggleSelecaoManifesto(id)}
|
||||
className="-my-2 grid h-11 w-11 place-items-center rounded-full hover:bg-accent/15"
|
||||
aria-label={isEs ? `Eliminar ${c.name} del manifiesto` : isEn ? `Remove ${c.name} from manifest` : `Remover ${c.name} do manifesto`}
|
||||
aria-label={isEs ? `Eliminar ${c.name} del manifiesto` : isEn ? `Remove ${c.name} from manifest` : isFr ? `Retirer ${c.name} du manifeste` : isDe ? `${c.name} aus dem Manifest entfernen` : `Remover ${c.name} do manifesto`}
|
||||
>
|
||||
<X className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
</button>
|
||||
@@ -403,7 +429,7 @@ export default function ComponentRegistryPage() {
|
||||
</section>
|
||||
|
||||
<section className="shell section border-t border-line pt-14" aria-labelledby="guia-titulo">
|
||||
<SectionHead id="guia-titulo" eyebrow={isEs ? "Guía rápida" : isEn ? "Quick guide" : "Guia rápido"} title={GUIA_COMPONENT_MANAGER.titulo} lede={GUIA_COMPONENT_MANAGER.resumo} />
|
||||
<SectionHead id="guia-titulo" eyebrow={isEs ? "Guía rápida" : isEn ? "Quick guide" : isFr ? "Guide rapide" : isDe ? "Kurzanleitung" : "Guia rápido"} title={GUIA_COMPONENT_MANAGER.titulo} lede={GUIA_COMPONENT_MANAGER.resumo} />
|
||||
|
||||
<ul className="mt-8 grid gap-3 md:grid-cols-2 lg:grid-cols-4">
|
||||
{GUIA_COMPONENT_MANAGER.vantagens.map((v) => (
|
||||
@@ -416,7 +442,7 @@ export default function ComponentRegistryPage() {
|
||||
|
||||
<h3 className="mt-12 flex items-center gap-2 font-display text-xl font-semibold tracking-[-0.03em] text-ink">
|
||||
<Terminal className="h-5 w-5 text-accent" aria-hidden="true" />
|
||||
{isEs ? "Comandos esenciales" : isEn ? "Essential commands" : "Comandos essenciais"}
|
||||
{isEs ? "Comandos esenciales" : isEn ? "Essential commands" : isFr ? "Commandes essentielles" : isDe ? "Wichtige Befehle" : "Comandos essenciais"}
|
||||
</h3>
|
||||
<ul className="mt-4 space-y-3">
|
||||
{GUIA_COMPONENT_MANAGER.comandosCli.map((cmd, i) => (
|
||||
@@ -431,7 +457,7 @@ export default function ComponentRegistryPage() {
|
||||
className="inline-flex min-h-11 shrink-0 items-center gap-1.5 self-start rounded-full border border-white/15 px-4 text-sm font-medium text-[#e9eef4] transition-colors hover:bg-white/10 md:self-auto"
|
||||
>
|
||||
{copiadoId === `cmd-${i}` ? <Check className="h-4 w-4 text-[#5fe0a2]" aria-hidden="true" /> : <Copy className="h-4 w-4" aria-hidden="true" />}
|
||||
{copiadoId === `cmd-${i}` ? (isEs ? "Copiado" : isEn ? "Copied" : "Copiado") : (isEs ? "Copiar" : isEn ? "Copy" : "Copiar")}
|
||||
{copiadoId === `cmd-${i}` ? (isEs ? "Copiado" : isEn ? "Copied" : isFr ? "Copié" : isDe ? "Kopiert" : "Copiado") : (isEs ? "Copiar" : isEn ? "Copy" : isFr ? "Copier" : isDe ? "Kopieren" : "Copiar")}
|
||||
</button>
|
||||
</li>
|
||||
))}
|
||||
@@ -440,7 +466,7 @@ export default function ComponentRegistryPage() {
|
||||
<div className="callout mt-8">
|
||||
<h3 className="flex items-center gap-2 font-semibold text-ink">
|
||||
<HelpCircle className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEs ? "Versionamiento semántico en ESP-IDF" : isEn ? "Semantic versioning in ESP-IDF" : "Versionamento semântico no ESP-IDF"}
|
||||
{isEs ? "Versionamiento semántico en ESP-IDF" : isEn ? "Semantic versioning in ESP-IDF" : isFr ? "Versionnement sémantique dans ESP-IDF" : isDe ? "Semantische Versionierung in ESP-IDF" : "Versionamento semântico no ESP-IDF"}
|
||||
</h3>
|
||||
<ul className="mt-2 list-disc space-y-1.5 pl-5">
|
||||
{isEs ? (
|
||||
@@ -457,6 +483,20 @@ export default function ComponentRegistryPage() {
|
||||
<li><code>1.2.0</code>: locks to this exact version.</li>
|
||||
<li><code>*</code>: accepts any version. Avoid in production.</li>
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
<li><code>^1.2.0</code>: accepte les mises à jour mineures et les correctifs (1.2.1, 1.3.0), mais bloque les changements majeurs d'API (2.0.0). <strong>Recommandé.</strong></li>
|
||||
<li><code>~1.2.0</code>: accepte uniquement les correctifs de bugs (1.2.1, 1.2.5).</li>
|
||||
<li><code>1.2.0</code>: verrouille sur cette version exacte.</li>
|
||||
<li><code>*</code>: accepte n'importe quelle version. À éviter en production.</li>
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
<li><code>^1.2.0</code>: akzeptiert Minor-Updates und Bugfixes (1.2.1, 1.3.0), blockiert aber Breaking Changes (2.0.0). <strong>Empfohlen.</strong></li>
|
||||
<li><code>~1.2.0</code>: akzeptiert nur Patch-Releases (1.2.1, 1.2.5).</li>
|
||||
<li><code>1.2.0</code>: bindet fest an diese Version.</li>
|
||||
<li><code>*</code>: akzeptiert jede Version. In Produktion vermeiden.</li>
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<li><code>^1.2.0</code>: aceita atualizações menores e correções (1.2.1, 1.3.0), mas bloqueia mudanças grandes de API (2.0.0). <strong>Recomendado.</strong></li>
|
||||
|
||||
@@ -4,16 +4,26 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEs
|
||||
? "Diagnóstico de errores comunes en ESP32: Guía profesional"
|
||||
: isEn
|
||||
? "Common ESP32 Errors & Diagnostics: Professional Guide"
|
||||
: isFr
|
||||
? "Diagnostic des erreurs courantes sur ESP32 : guide professionnel"
|
||||
: isDe
|
||||
? "Diagnose häufiger ESP32-Fehler: Professioneller Leitfaden"
|
||||
: "Diagnóstico de Erros Comuns no ESP32: Guia Profissional",
|
||||
descricao: isEs
|
||||
? "Guía técnica definitiva para identificar y solucionar Brownout, Guru Meditation, Task Watchdog, Stack Overflow, fugas de memoria y fallas de arranque en ESP32 (Arduino y ESP-IDF)."
|
||||
: isEn
|
||||
? "Definitive technical guide to identify and fix Brownout, Guru Meditation, Task Watchdog, Stack Overflow, memory leaks, and boot issues on ESP32 (Arduino & ESP-IDF)."
|
||||
: isFr
|
||||
? "Guide technique pour identifier et résoudre Brownout, Guru Meditation, Task Watchdog, Stack Overflow, fuites de mémoire et pannes de démarrage sur ESP32 (Arduino et ESP-IDF)."
|
||||
: isDe
|
||||
? "Technischer Leitfaden zur Behebung von Brownout, Guru Meditation, Task Watchdog, Stack Overflow, Speicherlecks und Boot-Problemen beim ESP32 (Arduino & ESP-IDF)."
|
||||
: "Guia técnico definitivo para identificar e resolver Brownout, Guru Meditation, Task Watchdog, Stack Overflow, vazamento de memória e falhas de boot no ESP32 (Arduino e ESP-IDF).",
|
||||
caminho: "/diagnostico",
|
||||
locale,
|
||||
@@ -39,6 +49,28 @@ export async function generateMetadata({ params }) {
|
||||
"ESP32 bootloop rebooting",
|
||||
"failed to connect to esp32",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"erreurs courantes ESP32",
|
||||
"brownout detector was triggered",
|
||||
"guru meditation error",
|
||||
"task watchdog got triggered",
|
||||
"stack canary watchpoint triggered",
|
||||
"comment déboguer ESP32",
|
||||
"ESP32 redémarre en boucle",
|
||||
"failed to connect to esp32",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
"häufige ESP32-Fehler",
|
||||
"brownout detector was triggered",
|
||||
"guru meditation error",
|
||||
"task watchdog got triggered",
|
||||
"stack canary watchpoint triggered",
|
||||
"ESP32 debuggen",
|
||||
"ESP32 Bootloop Neustart",
|
||||
"failed to connect to esp32",
|
||||
]
|
||||
: [
|
||||
"erros comuns ESP32",
|
||||
"brownout detector was triggered",
|
||||
@@ -109,11 +141,52 @@ const faqsEs = [
|
||||
},
|
||||
];
|
||||
|
||||
const faqsFr = [
|
||||
{
|
||||
pergunta: "Quelle est la cause de l'erreur 'Brownout detector was triggered' sur l'ESP32 ?",
|
||||
resposta: "Elle survient lorsque la tension sur la broche 3V3 chute sous 2.8V ~ 2.43V en raison des pics rapides de courant de la radio Wi-Fi/BLE (dépassant 500mA), de câbles USB trop fins ou d'un régulateur LDO sous-dimensionné. La solution d'ingénierie consiste à ajouter des condensateurs Low-ESR de 10µF à 100µF près du VCC et à utiliser un régulateur LDO robuste de 600mA+.",
|
||||
},
|
||||
{
|
||||
pergunta: "Comment résoudre le 'Guru Meditation Error (LoadProhibited)' ?",
|
||||
resposta: "LoadProhibited indique une tentative d'accès à un pointeur nul (NULL) ou invalide en mémoire. La solution consiste à utiliser l'Espressif Exception Decoder ou addr2line pour identifier la ligne exacte du code et à appliquer des vérifications défensives telles que if (pointeur != NULL).",
|
||||
},
|
||||
{
|
||||
pergunta: "Pourquoi le Task Watchdog Timer (TWDT) se déclenche-t-il sous FreeRTOS ?",
|
||||
resposta: "Le TWDT se déclenche lorsqu'une tâche de priorité plus élevée monopolise le CPU dans une boucle bloquante (par exemple : while(1) sans vTaskDelay), empêchant la tâche IDLE de nourrir le watchdog du système d'exploitation.",
|
||||
},
|
||||
{
|
||||
pergunta: "Pourquoi les connexions HTTPS et TLS échouent-elles avec l'erreur -0x2700 sur l'ESP32 ?",
|
||||
resposta: "Au démarrage, l'horloge interne de l'ESP32 démarre à l'année 1970. Le validateur de certificats TLS considère le certificat du serveur invalide car situé dans le 'futur'. Synchroniser l'horloge via SNTP (configTime) avant la connexion résout le problème.",
|
||||
},
|
||||
];
|
||||
|
||||
const faqsDe = [
|
||||
{
|
||||
pergunta: "Was verursacht den Fehler 'Brownout detector was triggered' beim ESP32?",
|
||||
resposta: "Er tritt auf, wenn die Spannung an der 3V3-Leitung durch schnelle Stromspitzen des Wi-Fi/BLE-Funkmoduls (über 500mA), dünne USB-Kabel oder einen unterdimensionierten LDO-Regler unter 2.8V ~ 2.43V abfällt. Die Lösung besteht darin, Low-ESR-Kondensatoren von 10µF bis 100µF nahe an VCC zu platzieren und robuste LDO-Regler mit 600mA+ einzusetzen.",
|
||||
},
|
||||
{
|
||||
pergunta: "Wie behebt man den 'Guru Meditation Error (LoadProhibited)'?",
|
||||
resposta: "LoadProhibited weist auf den Versuch hin, auf einen Null-Zeiger (NULL) oder eine ungültige Speicheradresse zuzugreifen. Die Lösung besteht darin, den Espressif Exception Decoder oder addr2line zu verwenden, um die genaue Quellcodezeile zu lokalisieren, und defensive Prüfungen wie if (ptr != NULL) einzufügen.",
|
||||
},
|
||||
{
|
||||
pergunta: "Warum löst der Task Watchdog Timer (TWDT) in FreeRTOS aus?",
|
||||
resposta: "Der TWDT löst aus, wenn ein Task mit höherer Priorität die CPU in einer blockierenden Schleife monopolisiert (z. B. while(1) ohne vTaskDelay) und so verhindert, dass der IDLE-Task den Watchdog des Betriebssystems bedient.",
|
||||
},
|
||||
{
|
||||
pergunta: "Warum schlagen HTTPS- und TLS-Verbindungen beim ESP32 mit Fehler -0x2700 fehl?",
|
||||
resposta: "Beim Start beginnt die interne Systemuhr des ESP32 im Jahr 1970. Die TLS-Zertifikatsprüfung stuft das Serverzertifikat als ungültig ein, da es in der fernen 'Zukunft' liegt. Eine Zeitsynchronisation über SNTP (configTime) vor dem Verbindungsaufbau behebt das Problem.",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function DiagnosticoLayout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : isFr ? faqsFr : isDe ? faqsDe : faqsPt;
|
||||
const canonPath = isEs ? "/es/diagnostico" : isEn ? "/en/diagnostics" : isFr ? "/fr/diagnostic" : isDe ? "/de/diagnose" : "/diagnostico";
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -122,8 +195,8 @@ export default async function DiagnosticoLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: isEs ? "Diagnóstico y errores comunes" : isEn ? "Diagnostics & Common Errors" : "Diagnóstico & Erros Comuns", caminho: isEs ? "/es/diagnostico" : isEn ? "/en/diagnostics" : "/diagnostico" },
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: isEs ? "Diagnóstico y errores comunes" : isEn ? "Diagnostics & Common Errors" : isFr ? "Diagnostic et erreurs courantes" : isDe ? "Diagnose und häufige Fehler" : "Diagnóstico & Erros Comuns", caminho: canonPath },
|
||||
])
|
||||
),
|
||||
}}
|
||||
@@ -141,13 +214,17 @@ export default async function DiagnosticoLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.aplicacaoWeb({
|
||||
nome: isEs ? "Guía de diagnóstico y errores en ESP32" : isEn ? "ESP32 Error Diagnostics & Debugging Guide" : "Guia de Diagnóstico e Erros no ESP32",
|
||||
nome: isEs ? "Guía de diagnóstico y errores en ESP32" : isEn ? "ESP32 Error Diagnostics & Debugging Guide" : isFr ? "Guide de diagnostic et erreurs sur ESP32" : isDe ? "ESP32-Fehlerdiagnose und Debugging-Leitfaden" : "Guia de Diagnóstico e Erros no ESP32",
|
||||
descricao: isEs
|
||||
? "Herramienta y guía técnica de análisis de fallas, pánicos de CPU y decodificación de registros en ESP32."
|
||||
: isEn
|
||||
? "Technical guide and log decoder for troubleshooting CPU panics, crashes, and exceptions on ESP32."
|
||||
: isFr
|
||||
? "Outil et guide technique d'analyse des pannes, des paniques CPU et du décodage de logs sur ESP32."
|
||||
: isDe
|
||||
? "Werkzeug und technischer Leitfaden zur Fehleranalyse, Behebung von CPU-Panics und Dekodierung von Logs auf dem ESP32."
|
||||
: "Ferramenta e guia técnico de análise de falhas, pânicos de CPU e decodificação de logs no ESP32.",
|
||||
caminho: isEs ? "/es/diagnostico" : isEn ? "/en/diagnostics" : "/diagnostico",
|
||||
caminho: canonPath,
|
||||
locale,
|
||||
})
|
||||
),
|
||||
|
||||
@@ -8,6 +8,8 @@ import PageHero from "@/components/PageHero";
|
||||
import * as diagnosticoPt from "@/lib/diagnosticoData";
|
||||
import * as diagnosticoEn from "@/lib/data/en/diagnostico";
|
||||
import * as diagnosticoEs from "@/lib/data/es/diagnostico";
|
||||
import * as diagnosticoFr from "@/lib/data/fr/diagnostico";
|
||||
import * as diagnosticoDe from "@/lib/data/de/diagnostico";
|
||||
import {
|
||||
Activity,
|
||||
AlertTriangle,
|
||||
@@ -57,14 +59,34 @@ const EXEMPLOS_LOG_ES = [
|
||||
["Handshake TLS", "mbedtls_ssl_handshake returned -0x2700\nThe certificate is not yet valid"],
|
||||
];
|
||||
|
||||
const EXEMPLOS_LOG_FR = [
|
||||
["Brownout", "Brownout detector was triggered\n\nrst:0xc (SW_CPU_RESET),boot:0x13"],
|
||||
["LoadProhibited", "Guru Meditation Error: Core 0 panic'ed (LoadProhibited).\nEXCVADDR: 0x00000000"],
|
||||
["Task watchdog", "Task watchdog got triggered. The following tasks/users did not reset the watchdog: - IDLE0"],
|
||||
["Handshake TLS", "mbedtls_ssl_handshake returned -0x2700\nThe certificate is not yet valid"],
|
||||
];
|
||||
|
||||
const EXEMPLOS_LOG_DE = [
|
||||
["Brownout", "Brownout detector was triggered\n\nrst:0xc (SW_CPU_RESET),boot:0x13"],
|
||||
["LoadProhibited", "Guru Meditation Error: Core 0 panic'ed (LoadProhibited).\nEXCVADDR: 0x00000000"],
|
||||
["Task watchdog", "Task watchdog got triggered. The following tasks/users did not reset the watchdog: - IDLE0"],
|
||||
["TLS-Handshake", "mbedtls_ssl_handshake returned -0x2700\nThe certificate is not yet valid"],
|
||||
];
|
||||
|
||||
const GRAVIDADE = {
|
||||
"Crítica": "text-danger",
|
||||
"Critical": "text-danger",
|
||||
"Critique": "text-danger",
|
||||
"Kritisch": "text-danger",
|
||||
Alta: "text-gold",
|
||||
High: "text-gold",
|
||||
"Élevée": "text-gold",
|
||||
Hoch: "text-gold",
|
||||
"Média": "text-accent",
|
||||
Medium: "text-accent",
|
||||
Media: "text-accent",
|
||||
Moyenne: "text-accent",
|
||||
Mittel: "text-accent",
|
||||
};
|
||||
|
||||
const CHECKLISTS_PT = [
|
||||
@@ -136,13 +158,61 @@ const CHECKLISTS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const CHECKLISTS_FR = [
|
||||
{
|
||||
icon: Zap,
|
||||
titulo: "Matériel et alimentation",
|
||||
itens: [
|
||||
"Condensateur de 10 µF à 100 µF à faible ESR sur VCC, plus un céramique de 100 nF près de la puce.",
|
||||
"Régulateur LDO dimensionné pour des pointes de 600 mA à 1 A, avec marge thermique.",
|
||||
"Aucun périphérique ne forçant de niveau logique sur les broches de strapping pendant le boot.",
|
||||
"Condensateur de 10 µF ou 1 µF sur la broche EN (RST) pour un auto-reset stable au flashage.",
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Layers,
|
||||
titulo: "Firmware et FreeRTOS",
|
||||
itens: [
|
||||
"Chaque tâche FreeRTOS cède la CPU avec vTaskDelay, des files ou des sémaphores.",
|
||||
"Chaque ISR marquée avec IRAM_ATTR et exempte d'appels bloquants.",
|
||||
"Pas d'usage continu de String d'Arduino dans les boucles, afin d'éviter la fragmentation du tas.",
|
||||
"Horloge synchronisée par SNTP avant d'ouvrir des connexions TLS/HTTPS.",
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const CHECKLISTS_DE = [
|
||||
{
|
||||
icon: Zap,
|
||||
titulo: "Hardware und Spannungsversorgung",
|
||||
itens: [
|
||||
"10 µF bis 100 µF Low-ESR-Kondensator an VCC, plus ein 100-nF-Keramikkondensator nah am Chip.",
|
||||
"LDO-Regler ausgelegt für 600 mA bis 1 A Stromspitzen mit thermischer Reserve.",
|
||||
"Keine Peripheriegeräte, die beim Booten Logikpegel an Strapping-Pins erzwingen.",
|
||||
"10 µF- oder 1 µF-Kondensator am EN-Pin (RST) für zuverlässigen Auto-Reset beim Flashen.",
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Layers,
|
||||
titulo: "Firmware und FreeRTOS",
|
||||
itens: [
|
||||
"Jeder FreeRTOS-Task gibt CPU-Zeit mit vTaskDelay, Queues oder Semaphoren ab.",
|
||||
"Jede ISR mit IRAM_ATTR versehen und frei von blockierenden Aufrufen.",
|
||||
"Keine fortlaufende Verwendung von Arduino-Strings in Schleifen zur Vermeidung von Heap-Fragmentierung.",
|
||||
"Uhrzeit vor dem Aufbau von TLS/HTTPS-Verbindungen per SNTP synchronisiert.",
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
export default function DiagnosticoPage() {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const { categoriasDiagnostico, sintomasRapidos, errosCatalogo, regrasDecodificadorLog } = isEs ? diagnosticoEs : isEn ? diagnosticoEn : diagnosticoPt;
|
||||
const exemplosLog = isEs ? EXEMPLOS_LOG_ES : isEn ? EXEMPLOS_LOG_EN : EXEMPLOS_LOG_PT;
|
||||
const checklists = isEs ? CHECKLISTS_ES : isEn ? CHECKLISTS_EN : CHECKLISTS_PT;
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const { categoriasDiagnostico, sintomasRapidos, errosCatalogo, regrasDecodificadorLog } = isEs ? diagnosticoEs : isEn ? diagnosticoEn : isFr ? diagnosticoFr : isDe ? diagnosticoDe : diagnosticoPt;
|
||||
const exemplosLog = isEs ? EXEMPLOS_LOG_ES : isEn ? EXEMPLOS_LOG_EN : isFr ? EXEMPLOS_LOG_FR : isDe ? EXEMPLOS_LOG_DE : EXEMPLOS_LOG_PT;
|
||||
const checklists = isEs ? CHECKLISTS_ES : isEn ? CHECKLISTS_EN : isFr ? CHECKLISTS_FR : isDe ? CHECKLISTS_DE : CHECKLISTS_PT;
|
||||
|
||||
const [termoBusca, setTermoBusca] = useState("");
|
||||
const [categoriaAtiva, setCategoriaAtiva] = useState("todos");
|
||||
@@ -190,6 +260,24 @@ export default function DiagnosticoPage() {
|
||||
acaoRecomendada:
|
||||
"Look for keywords such as 'Guru Meditation', 'rst:', 'LoadProhibited', 'watchdog', or 'panic' in the serial output.",
|
||||
}
|
||||
: isFr
|
||||
? {
|
||||
titulo: "Modèle d'erreur non catégorisé automatiquement",
|
||||
tipo: "Inconnu",
|
||||
explicacao:
|
||||
"Nous n'avons pas identifié de signature classique de Guru Meditation ou Brownout dans cet extrait. Vérifiez que la vitesse en bauds (ex. : 115200) est correcte et si l'en-tête 'rst:' ou 'panic' est présent.",
|
||||
acaoRecomendada:
|
||||
"Recherchez des mots-clés tels que 'Guru Meditation', 'rst:', 'LoadProhibited', 'watchdog' ou 'panic' dans la console série.",
|
||||
}
|
||||
: isDe
|
||||
? {
|
||||
titulo: "Fehlermuster nicht automatisch kategorisiert",
|
||||
tipo: "Unbekannt",
|
||||
explicacao:
|
||||
"Wir konnten in diesem Ausschnitt keine klassische Guru-Meditation- oder Brownout-Signatur erkennen. Prüfen Sie, ob die Baudrate (z. B. 115200) korrekt ist und ob der Header 'rst:' oder 'panic' vorhanden ist.",
|
||||
acaoRecomendada:
|
||||
"Suchen Sie in der seriellen Konsole nach Begriffen wie 'Guru Meditation', 'rst:', 'LoadProhibited', 'watchdog' oder 'panic'.",
|
||||
}
|
||||
: {
|
||||
titulo: "Padrão de erro não categorizado automaticamente",
|
||||
tipo: "Desconhecido",
|
||||
@@ -256,15 +344,21 @@ export default function DiagnosticoPage() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Diagnóstico" : isEn ? "Diagnostics" : "Diagnóstico" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEs ? "Diagnóstico" : isEn ? "Diagnostics" : isFr ? "Diagnostic" : isDe ? "Diagnose" : "Diagnóstico" }]}
|
||||
icon={AlertTriangle}
|
||||
label={isEs ? "Depuración de firmware" : isEn ? "Firmware Debugging" : "Depuração de firmware"}
|
||||
title={isEs ? "Diagnóstico de fallas del ESP32" : isEn ? "ESP32 Diagnostics and Crash Decoder" : "Diagnóstico de falhas do ESP32"}
|
||||
label={isEs ? "Depuración de firmware" : isEn ? "Firmware Debugging" : isFr ? "Débogage du firmware" : isDe ? "Firmware-Debugging" : "Depuração de firmware"}
|
||||
title={isEs ? "Diagnóstico de fallas del ESP32" : isEn ? "ESP32 Diagnostics and Crash Decoder" : isFr ? "Diagnostic des pannes de l'ESP32" : isDe ? "ESP32-Fehlerdiagnose und Crash-Decoder" : "Diagnóstico de falhas do ESP32"}
|
||||
lede={
|
||||
isEs
|
||||
? "Comprenda la causa raíz de las fallas por Brownout, Guru Meditation, Watchdog y Stack Overflow, y aplique la corrección de ingeniería en lugar de soluciones improvisadas."
|
||||
: isEn
|
||||
? "Understand the root cause of Brownout, Guru Meditation, Watchdog, and Stack Overflow crashes, and apply engineering solutions instead of workarounds."
|
||||
: isFr
|
||||
? "Comprenez la cause racine des pannes de Brownout, Guru Meditation, Watchdog et Stack Overflow, et appliquez la correction d'ingénierie plutôt qu'un bricolage."
|
||||
: isDe
|
||||
? "Verstehen Sie die Ursache von Brownout, Guru Meditation, Watchdog und Stack Overflow und wenden Sie saubere Ingenieurlösungen statt Notbehelfen an."
|
||||
: "Entenda a causa de Brownout, Guru Meditation, Watchdog e Stack Overflow, e aplique a correção de engenharia, não o remendo."
|
||||
}
|
||||
>
|
||||
@@ -274,9 +368,9 @@ export default function DiagnosticoPage() {
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong"
|
||||
>
|
||||
{isEs ? "Basado en el artículo de Ciência Embarcada" : isEn ? "Based on article by Ciência Embarcada" : "Baseado no artigo do Ciência Embarcada"}
|
||||
{isEs ? "Basado en el artículo de Ciência Embarcada" : isEn ? "Based on article by Ciência Embarcada" : isFr ? "D'après l'article de Ciência Embarcada" : isDe ? "Basierend auf dem Artikel von Ciência Embarcada" : "Baseado no artigo do Ciência Embarcada"}
|
||||
<ExternalLink className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : "(abre em nova aba)"}</span>
|
||||
<span className="sr-only"> {isEs ? "(abre en una nueva pestaña)" : isEn ? "(opens in a new tab)" : isFr ? "(ouvre un nouvel onglet)" : isDe ? "(öffnet in neuem Tab)" : "(abre em nova aba)"}</span>
|
||||
</a>
|
||||
</PageHero>
|
||||
|
||||
@@ -285,14 +379,14 @@ export default function DiagnosticoPage() {
|
||||
<div className="flex flex-col justify-between gap-4 md:flex-row md:items-end">
|
||||
<div className="max-w-xl">
|
||||
<h2 id="decodificador-titulo" className="section-title">
|
||||
{isEs ? "Pegue el registro y descubra la causa" : isEn ? "Paste the log to see the cause" : "Cole o log e veja a causa"}
|
||||
{isEs ? "Pegue el registro y descubra la causa" : isEn ? "Paste the log to see the cause" : isFr ? "Collez le journal et découvrez la cause" : isDe ? "Log einfügen und Ursache ermitteln" : "Cole o log e veja a causa"}
|
||||
</h2>
|
||||
<p className="mt-2 text-sm text-muted">
|
||||
{isEs ? "Copie el fragmento del monitor serie. El diagnóstico aparece al instante." : isEn ? "Copy the serial monitor output snippet. Diagnostics appear instantly." : "Copie o trecho do monitor serial. O diagnóstico aparece na hora."}
|
||||
{isEs ? "Copie el fragmento del monitor serie. El diagnóstico aparece al instante." : isEn ? "Copy the serial monitor output snippet. Diagnostics appear instantly." : isFr ? "Copiez l'extrait du moniteur série. Le diagnostic apparaît immédiatement." : isDe ? "Kopieren Sie den Ausschnitt aus dem seriellen Monitor. Die Diagnose erscheint sofort." : "Copie o trecho do monitor serial. O diagnóstico aparece na hora."}
|
||||
</p>
|
||||
</div>
|
||||
<div className="flex flex-wrap items-center gap-2">
|
||||
<span className="text-sm text-muted">{isEs ? "Probar con" : isEn ? "Test with" : "Testar com"}</span>
|
||||
<span className="text-sm text-muted">{isEs ? "Probar con" : isEn ? "Test with" : isFr ? "Tester avec" : isDe ? "Testen mit" : "Testar com"}</span>
|
||||
{exemplosLog.map(([rotulo, texto]) => (
|
||||
<button key={rotulo} type="button" onClick={() => analisarLog(texto)} className="chip-btn">
|
||||
{rotulo}
|
||||
@@ -303,21 +397,21 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<div className="relative mt-5">
|
||||
<label htmlFor="log-serial" className="sr-only">
|
||||
{isEs ? "Registro del monitor serie" : isEn ? "Serial monitor log" : "Log do monitor serial"}
|
||||
{isEs ? "Registro del monitor serie" : isEn ? "Serial monitor log" : isFr ? "Journal du moniteur série" : isDe ? "Serieller Monitor-Log" : "Log do monitor serial"}
|
||||
</label>
|
||||
<textarea
|
||||
id="log-serial"
|
||||
rows={4}
|
||||
value={logInput}
|
||||
onChange={(e) => analisarLog(e.target.value)}
|
||||
placeholder={isEs ? "Pegue el registro del monitor serie aquí" : isEn ? "Paste serial monitor log here" : "Cole o log do monitor serial aqui"}
|
||||
placeholder={isEs ? "Pegue el registro del monitor serie aquí" : isEn ? "Paste serial monitor log here" : isFr ? "Collez le journal du moniteur série ici" : isDe ? "Seriellen Monitor-Log hier einfügen" : "Cole o log do monitor serial aqui"}
|
||||
spellCheck={false}
|
||||
className="code-panel field !min-h-32 w-full resize-y !rounded-xl !border-white/10 !bg-[var(--code-bg)] p-4 font-mono text-sm !text-[#e9eef4] placeholder:!text-[#a6afbd]"
|
||||
/>
|
||||
{logInput && (
|
||||
<button type="button" onClick={() => analisarLog("")} className="absolute right-3 top-3 inline-flex min-h-11 items-center gap-1 rounded-full border border-white/15 px-3 text-xs font-medium text-[#e9eef4] hover:bg-white/10">
|
||||
<X className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isEs ? "Limpiar" : isEn ? "Clear" : "Limpar"}
|
||||
{isEs ? "Limpiar" : isEn ? "Clear" : isFr ? "Effacer" : isDe ? "Löschen" : "Limpar"}
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
@@ -331,8 +425,8 @@ export default function DiagnosticoPage() {
|
||||
<h3 className="font-semibold text-ink">{resultadoLog.titulo}</h3>
|
||||
<span className="chip">{resultadoLog.tipo}</span>
|
||||
</div>
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Causa probable:" : isEn ? "Likely cause:" : "Causa provável:"}</strong> {resultadoLog.explicacao}</p>
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Qué hacer:" : isEn ? "What to do:" : "O que fazer:"}</strong> {resultadoLog.acaoRecomendada}</p>
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Causa probable:" : isEn ? "Likely cause:" : isFr ? "Cause probable :" : isDe ? "Wahrscheinliche Ursache :" : "Causa provável:"}</strong> {resultadoLog.explicacao}</p>
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Qué hacer:" : isEn ? "What to do:" : isFr ? "Que faire :" : isDe ? "Was zu tun ist :" : "O que fazer:"}</strong> {resultadoLog.acaoRecomendada}</p>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
@@ -342,13 +436,13 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<section className="shell section pt-12 sm:pt-14" aria-labelledby="catalogo-titulo">
|
||||
<h2 id="catalogo-titulo" className="section-title">
|
||||
{isEs ? "Catálogo de fallas" : isEn ? "Fault catalog" : "Catálogo de falhas"}
|
||||
{isEs ? "Catálogo de fallas" : isEn ? "Fault catalog" : isFr ? "Catalogue de pannes" : isDe ? "Fehlerkatalog" : "Catálogo de falhas"}
|
||||
</h2>
|
||||
|
||||
<div className="panel mt-6 p-5 sm:p-6">
|
||||
<div className="relative">
|
||||
<label htmlFor="busca-erro" className="sr-only">
|
||||
{isEs ? "Buscar por error, síntoma o mensaje serie" : isEn ? "Search by error, symptom, or serial message" : "Buscar por erro, sintoma ou mensagem serial"}
|
||||
{isEs ? "Buscar por error, síntoma o mensaje serie" : isEn ? "Search by error, symptom, or serial message" : isFr ? "Rechercher par erreur, symptôme ou message série" : isDe ? "Nach Fehler, Symptom oder serieller Meldung suchen" : "Buscar por erro, sintoma ou mensagem serial"}
|
||||
</label>
|
||||
<Search className="pointer-events-none absolute left-4 top-1/2 h-5 w-5 -translate-y-1/2 text-muted" aria-hidden="true" />
|
||||
<input
|
||||
@@ -357,14 +451,14 @@ export default function DiagnosticoPage() {
|
||||
type="search"
|
||||
value={termoBusca}
|
||||
onChange={(e) => setTermoBusca(e.target.value)}
|
||||
placeholder={isEs ? "Buscar error, síntoma o mensaje" : isEn ? "Search error, symptom, or message" : "Buscar erro, sintoma ou mensagem"}
|
||||
placeholder={isEs ? "Buscar error, síntoma o mensaje" : isEn ? "Search error, symptom, or message" : isFr ? "Rechercher une erreur, un symptôme ou un message" : isDe ? "Fehler, Symptom oder Meldung suchen" : "Buscar erro, sintoma ou mensagem"}
|
||||
autoComplete="off"
|
||||
className="field pl-12 pr-4 text-base"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="mt-5">
|
||||
<h3 className="text-sm font-semibold text-ink">{isEs ? "Síntoma" : isEn ? "Symptom" : "Sintoma"}</h3>
|
||||
<h3 className="text-sm font-semibold text-ink">{isEs ? "Síntoma" : isEn ? "Symptom" : isFr ? "Symptôme" : isDe ? "Symptom" : "Sintoma"}</h3>
|
||||
<div className="mt-3 flex flex-wrap gap-2">
|
||||
{sintomasRapidos.map((sintoma) => (
|
||||
<button key={sintoma.id} type="button" onClick={() => setSintomaAtivo(sintomaAtivo === sintoma.id ? null : sintoma.id)} aria-pressed={sintomaAtivo === sintoma.id} className="chip-btn">
|
||||
@@ -375,11 +469,11 @@ export default function DiagnosticoPage() {
|
||||
</div>
|
||||
|
||||
<div className="mt-5 border-t border-line pt-5">
|
||||
<h3 className="text-sm font-semibold text-ink">{isEs ? "Área" : isEn ? "Area" : "Área"}</h3>
|
||||
<h3 className="text-sm font-semibold text-ink">{isEs ? "Área" : isEn ? "Area" : isFr ? "Domaine" : isDe ? "Bereich" : "Área"}</h3>
|
||||
<div className="mt-3 flex flex-wrap gap-2">
|
||||
<button type="button" onClick={() => setCategoriaAtiva("todos")} aria-pressed={categoriaAtiva === "todos"} className="chip-btn">
|
||||
<LayoutGrid className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Todas" : isEn ? "All" : "Todas"}
|
||||
{isEs ? "Todas" : isEn ? "All" : isFr ? "Tous" : isDe ? "Alle" : "Todas"}
|
||||
<span className="tabular-nums opacity-80">{errosCatalogo.length}</span>
|
||||
</button>
|
||||
{categoriasDiagnostico.map((cat) => {
|
||||
@@ -399,13 +493,13 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<div className="mt-6 flex flex-wrap items-center justify-between gap-3">
|
||||
<p role="status" aria-live="polite" className="text-sm font-semibold text-ink">
|
||||
{errosFiltrados.length} {errosFiltrados.length === 1 ? (isEs ? "falla" : isEn ? "fault" : "falha") : (isEs ? "fallas" : isEn ? "faults" : "falhas")}
|
||||
{totalFiltros > 0 && <span className="font-normal text-muted">{isEs ? " con los filtros actuales" : isEn ? " with current filters" : " com os filtros atuais"}</span>}
|
||||
{errosFiltrados.length} {errosFiltrados.length === 1 ? (isEs ? "falla" : isEn ? "fault" : isFr ? "panne" : isDe ? "Fehler" : "falha") : (isEs ? "fallas" : isEn ? "faults" : isFr ? "pannes" : isDe ? "Fehler" : "falhas")}
|
||||
{totalFiltros > 0 && <span className="font-normal text-muted">{isEs ? " con los filtros actuales" : isEn ? " with current filters" : isFr ? " avec les filtres actuels" : isDe ? " mit aktuellen Filtern" : " com os filtros atuais"}</span>}
|
||||
</p>
|
||||
{temFiltroAtivo && (
|
||||
<button type="button" onClick={limparTodosFiltros} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
<RotateCcw className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Restablecer filtros" : isEn ? "Reset filters" : "Redefinir filtros"}
|
||||
{isEs ? "Restablecer filtros" : isEn ? "Reset filters" : isFr ? "Réinitialiser les filtres" : isDe ? "Filter zurücksetzen" : "Redefinir filtros"}
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
@@ -415,13 +509,13 @@ export default function DiagnosticoPage() {
|
||||
<div className="card px-6 py-14 text-center">
|
||||
<HelpCircle className="mx-auto h-10 w-10 text-muted" aria-hidden="true" />
|
||||
<h3 className="mt-4 font-display text-xl font-semibold text-ink">
|
||||
{isEs ? "Ninguna falla coincide con estos filtros" : isEn ? "No faults matching these filters" : "Nenhuma falha com esses filtros"}
|
||||
{isEs ? "Ninguna falla coincide con estos filtros" : isEn ? "No faults matching these filters" : isFr ? "Aucune panne ne correspond à ces filtres" : isDe ? "Keine Fehler entsprechen diesen Filtern" : "Nenhuma falha com esses filtros"}
|
||||
</h3>
|
||||
<p className="mx-auto mt-2 max-w-md text-sm text-muted">
|
||||
{isEs ? "Busque por un término más general o elimine el síntoma y el área seleccionados." : isEn ? "Search for a more general term or remove selected symptom and area." : "Busque por um termo mais geral ou remova o sintoma e a área selecionados."}
|
||||
{isEs ? "Busque por un término más general o elimine el síntoma y el área seleccionados." : isEn ? "Search for a more general term or remove selected symptom and area." : isFr ? "Recherchez un terme plus général ou retirez le symptôme et le domaine sélectionnés." : isDe ? "Suchen Sie nach einem allgemeineren Begriff oder entfernen Sie gewähltes Symptom und Bereich." : "Busque por um termo mais geral ou remova o sintoma e a área selecionados."}
|
||||
</p>
|
||||
<button type="button" onClick={limparTodosFiltros} className="btn btn-primary mt-6">
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : "Limpar filtros"}
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : isFr ? "Effacer les filtres" : isDe ? "Filter zurücksetzen" : "Limpar filtros"}
|
||||
</button>
|
||||
</div>
|
||||
) : (
|
||||
@@ -429,7 +523,7 @@ export default function DiagnosticoPage() {
|
||||
const estaAberto = cardAberto === erro.id;
|
||||
const lang = linguagemCodigo[erro.id] || "arduino";
|
||||
const codigoAtual =
|
||||
lang === "arduino" ? erro.codigoArduino : lang === "espidf" ? erro.codigoEspIdf : erro.codigoMicroPython || (isEs ? "# Ejemplo no aplicable" : isEn ? "# Example not applicable" : "# Exemplo não aplicável");
|
||||
lang === "arduino" ? erro.codigoArduino : lang === "espidf" ? erro.codigoEspIdf : erro.codigoMicroPython || (isEs ? "# Ejemplo no aplicable" : isEn ? "# Example not applicable" : isFr ? "# Exemple non applicable" : isDe ? "# Beispiel nicht anwendbar" : "# Exemplo não aplicável");
|
||||
const catInfo = categoriasDiagnostico.find((c) => c.id === erro.categoria);
|
||||
const IconeCat = ICONES[catInfo?.icone] ?? AlertTriangle;
|
||||
|
||||
@@ -454,6 +548,10 @@ export default function DiagnosticoPage() {
|
||||
<>Severidad {erro.gravidade.toLowerCase()}</>
|
||||
) : isEn ? (
|
||||
<>Severity: {erro.gravidade.toLowerCase()}</>
|
||||
) : isFr ? (
|
||||
<>Gravité : {erro.gravidade.toLowerCase()}</>
|
||||
) : isDe ? (
|
||||
<>Schweregrad: {erro.gravidade.toLowerCase()}</>
|
||||
) : (
|
||||
<>Gravidade {erro.gravidade.toLowerCase()}</>
|
||||
)}
|
||||
@@ -474,11 +572,11 @@ export default function DiagnosticoPage() {
|
||||
<div className="flex items-center justify-between gap-3">
|
||||
<h4 className="flex items-center gap-2 text-sm font-semibold text-ink">
|
||||
<Terminal className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEs ? "Cómo aparece en el monitor serie" : isEn ? "How it appears in serial monitor" : "Como aparece no monitor serial"}
|
||||
{isEs ? "Cómo aparece en el monitor serie" : isEn ? "How it appears in serial monitor" : isFr ? "Apparence dans le moniteur série" : isDe ? "Erscheinungsbild im seriellen Monitor" : "Como aparece no monitor serial"}
|
||||
</h4>
|
||||
<button type="button" onClick={() => copiarParaClipboard(erro.logSerial, `log-${erro.id}`)} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
{copiadoId === `log-${erro.id}` ? <Check className="h-4 w-4 text-ok" aria-hidden="true" /> : <Copy className="h-4 w-4" aria-hidden="true" />}
|
||||
{copiadoId === `log-${erro.id}` ? (isEs ? "Copiado" : isEn ? "Copied" : "Copiado") : (isEs ? "Copiar registro" : isEn ? "Copy log" : "Copiar log")}
|
||||
{copiadoId === `log-${erro.id}` ? (isEs ? "Copiado" : isEn ? "Copied" : isFr ? "Copié" : isDe ? "Kopiert" : "Copiado") : (isEs ? "Copiar registro" : isEn ? "Copy log" : isFr ? "Copier le log" : isDe ? "Log kopieren" : "Copiar log")}
|
||||
</button>
|
||||
</div>
|
||||
<div className="code-panel mt-1">
|
||||
@@ -489,7 +587,7 @@ export default function DiagnosticoPage() {
|
||||
<div>
|
||||
<h4 className="flex items-center gap-2 text-sm font-semibold text-ink">
|
||||
<Cpu className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEs ? "Causa raíz" : isEn ? "Root cause" : "Causa raiz"}
|
||||
{isEs ? "Causa raíz" : isEn ? "Root cause" : isFr ? "Cause racine" : isDe ? "Ursache" : "Causa raiz"}
|
||||
</h4>
|
||||
<p className="callout mt-2">{erro.causaRaiz}</p>
|
||||
</div>
|
||||
@@ -498,17 +596,17 @@ export default function DiagnosticoPage() {
|
||||
<div className="callout callout-danger">
|
||||
<p className="flex items-center gap-2 font-semibold text-ink">
|
||||
<XCircle className="h-4 w-4 shrink-0 text-danger" aria-hidden="true" />
|
||||
{isEs ? "La solución improvisada común" : isEn ? "The common workaround" : "O remendo comum"}
|
||||
{isEs ? "La solución improvisada común" : isEn ? "The common workaround" : isFr ? "Le bricolage courant" : isDe ? "Der verbreitete Notbehelf" : "O remendo comum"}
|
||||
</p>
|
||||
<p className="mt-2 font-medium text-ink">{erro.gambiarra.titulo}</p>
|
||||
<p className="mt-1">{erro.gambiarra.descricao}</p>
|
||||
<p className="mt-2"><strong className="font-semibold text-danger">{isEs ? "Consecuencia:" : isEn ? "Consequence:" : "Consequência:"}</strong> {erro.gambiarra.consequencia}</p>
|
||||
<p className="mt-2"><strong className="font-semibold text-danger">{isEs ? "Consecuencia:" : isEn ? "Consequence:" : isFr ? "Conséquence :" : isDe ? "Folge :" : "Consequência:"}</strong> {erro.gambiarra.consequencia}</p>
|
||||
</div>
|
||||
|
||||
<div className="callout callout-ok">
|
||||
<p className="flex items-center gap-2 font-semibold text-ink">
|
||||
<CheckCircle2 className="h-4 w-4 shrink-0 text-ok" aria-hidden="true" />
|
||||
{isEs ? "La solución de ingeniería" : isEn ? "The engineering solution" : "A solução de engenharia"}
|
||||
{isEs ? "La solución de ingeniería" : isEn ? "The engineering solution" : isFr ? "La solution d'ingénierie" : isDe ? "Die Ingenieurlösung" : "A solução de engenharia"}
|
||||
</p>
|
||||
<p className="mt-2 font-medium text-ink">{erro.solucaoEngenharia.titulo}</p>
|
||||
<ul className="mt-2 space-y-1.5">
|
||||
@@ -524,7 +622,7 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<div>
|
||||
<div className="flex flex-wrap items-center justify-between gap-3">
|
||||
<div role="group" aria-label={isEs ? "Lenguaje del ejemplo" : isEn ? "Example language" : "Linguagem do exemplo"} className="flex flex-wrap gap-2">
|
||||
<div role="group" aria-label={isEs ? "Lenguaje del ejemplo" : isEn ? "Example language" : isFr ? "Langage de l'exemple" : isDe ? "Sprache des Beispiels" : "Linguagem do exemplo"} className="flex flex-wrap gap-2">
|
||||
{[
|
||||
["arduino", "Arduino C++"],
|
||||
["espidf", "ESP-IDF (C)"],
|
||||
@@ -537,7 +635,7 @@ export default function DiagnosticoPage() {
|
||||
</div>
|
||||
<button type="button" onClick={() => copiarParaClipboard(codigoAtual, `code-${erro.id}`)} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
{copiadoId === `code-${erro.id}` ? <Check className="h-4 w-4 text-ok" aria-hidden="true" /> : <Copy className="h-4 w-4" aria-hidden="true" />}
|
||||
{copiadoId === `code-${erro.id}` ? (isEs ? "Copiado" : isEn ? "Copied" : "Copiado") : (isEs ? "Copiar código" : isEn ? "Copy code" : "Copiar código")}
|
||||
{copiadoId === `code-${erro.id}` ? (isEs ? "Copiado" : isEn ? "Copied" : isFr ? "Copié" : isDe ? "Kopiert" : "Copiado") : (isEs ? "Copiar código" : isEn ? "Copy code" : isFr ? "Copier le code" : isDe ? "Code kopieren" : "Copiar código")}
|
||||
</button>
|
||||
</div>
|
||||
<div className="code-panel mt-3">
|
||||
@@ -547,7 +645,7 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<div className="callout callout-warn flex items-start gap-3">
|
||||
<Wrench className="mt-0.5 h-4 w-4 shrink-0 text-gold" aria-hidden="true" />
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Consejo de ingeniería:" : isEn ? "Engineering tip:" : "Dica de engenharia:"}</strong> {erro.dicaPro}</p>
|
||||
<p><strong className="font-semibold text-ink">{isEs ? "Consejo de ingeniería:" : isEn ? "Engineering tip:" : isFr ? "Conseil d'ingénierie :" : isDe ? "Praxistipp :" : "Dica de engenharia:"}</strong> {erro.dicaPro}</p>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
@@ -560,10 +658,10 @@ export default function DiagnosticoPage() {
|
||||
|
||||
<section className="shell pb-20 md:pb-28" aria-labelledby="checklist-titulo">
|
||||
<h2 id="checklist-titulo" className="section-title">
|
||||
{isEs ? "Lista de verificación previa a campo" : isEn ? "Pre-deployment checklist" : "Checklist antes de ir para campo"}
|
||||
{isEs ? "Lista de verificación previa a campo" : isEn ? "Pre-deployment checklist" : isFr ? "Checklist avant déploiement" : isDe ? "Checkliste vor dem Feldeinsatz" : "Checklist antes de ir para campo"}
|
||||
</h2>
|
||||
<p className="mt-3 max-w-2xl text-base text-muted">
|
||||
{isEs ? "Elementos esenciales para validar en hardware y firmware antes de entregar el producto." : isEn ? "Essential items to validate on hardware and firmware before shipping a product." : "Itens essenciais para validar no hardware e no firmware antes de entregar o produto."}
|
||||
{isEs ? "Elementos esenciales para validar en hardware y firmware antes de entregar el producto." : isEn ? "Essential items to validate on hardware and firmware before shipping a product." : isFr ? "Éléments essentiels à valider sur le matériel et le firmware avant de livrer le produit." : isDe ? "Wesentliche Punkte zur Prüfung von Hardware und Firmware vor der Auslieferung." : "Itens essenciais para validar no hardware e no firmware antes de entregar o produto."}
|
||||
</p>
|
||||
<div className="mt-8 grid gap-4 md:grid-cols-2">
|
||||
{checklists.map(({ icon: Icon, titulo, itens }) => (
|
||||
|
||||
@@ -8,6 +8,8 @@ import CodeExample from "@/components/CodeExample";
|
||||
import frameworksDataPt from "@/public/frameworks.json";
|
||||
import frameworksDataEn from "@/data/en/frameworks.json";
|
||||
import frameworksDataEs from "@/data/es/frameworks.json";
|
||||
import frameworksDataFr from "@/data/fr/frameworks.json";
|
||||
import frameworksDataDe from "@/data/de/frameworks.json";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import { ArrowRight, ArrowUpRight, BookOpen, Box, Check, Code, Layers } from "lucide-react";
|
||||
|
||||
@@ -15,8 +17,10 @@ export default async function FrameworkDetail({ params }) {
|
||||
const { locale, key } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : frameworksDataPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : isFr ? "fr" : isDe ? "de" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : isFr ? frameworksDataFr : isDe ? frameworksDataDe : frameworksDataPt;
|
||||
const framework = frameworksData[key];
|
||||
|
||||
if (!framework) {
|
||||
@@ -38,7 +42,7 @@ export default async function FrameworkDetail({ params }) {
|
||||
type="application/ld+json"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: "Frameworks", caminho: getLocalizedHref("/frameworks", currentLocale) },
|
||||
{ nome: framework.nome, caminho: getLocalizedHref(`/frameworks/${encodeURIComponent(key)}`, currentLocale) },
|
||||
])),
|
||||
@@ -51,7 +55,9 @@ export default async function FrameworkDetail({ params }) {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Frameworks y SDKs" : isEn ? "Frameworks & SDKs" : "Frameworks e SDKs", href: getLocalizedHref("/frameworks", currentLocale) }, { label: framework.nome }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEs ? "Frameworks y SDKs" : isEn ? "Frameworks & SDKs" : isFr ? "Frameworks et SDKs" : isDe ? "Frameworks & SDKs" : "Frameworks e SDKs", href: getLocalizedHref("/frameworks", currentLocale) }, { label: framework.nome }]}
|
||||
icon={Layers}
|
||||
label={framework.tipo}
|
||||
title={framework.nome}
|
||||
@@ -60,41 +66,41 @@ export default async function FrameworkDetail({ params }) {
|
||||
{framework.documentacao && (
|
||||
<a href={framework.documentacao} target="_blank" rel="noopener noreferrer" className="btn btn-primary">
|
||||
<BookOpen className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Documentación oficial" : isEn ? "Official documentation" : "Documentação oficial"}
|
||||
{isEs ? "Documentación oficial" : isEn ? "Official documentation" : isFr ? "Documentation officielle" : isDe ? "Offizielle Dokumentation" : "Documentação oficial"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
)}
|
||||
{framework.repositorio && (
|
||||
<a href={framework.repositorio} target="_blank" rel="noopener noreferrer" className="btn btn-ghost">
|
||||
<Code className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Repositorio en GitHub" : isEn ? "GitHub repository" : "Repositório no GitHub"}
|
||||
{isEs ? "Repositorio en GitHub" : isEn ? "GitHub repository" : isFr ? "Dépôt sur GitHub" : isDe ? "GitHub-Repository" : "Repositório no GitHub"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
)}
|
||||
</PageHero>
|
||||
|
||||
<section className="shell mt-10" aria-label={isEs ? "Resumen" : isEn ? "Summary" : "Resumo"}>
|
||||
<section className="shell mt-10" aria-label={isEs ? "Resumen" : isEn ? "Summary" : isFr ? "Résumé" : isDe ? "Übersicht" : "Resumo"}>
|
||||
<dl className="grid gap-3 md:grid-cols-3">
|
||||
<div className="tile">
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Lenguaje" : isEn ? "Language" : "Linguagem"}</dt>
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Lenguaje" : isEn ? "Language" : isFr ? "Langage" : isDe ? "Sprache" : "Linguagem"}</dt>
|
||||
<dd className="mt-1 font-display text-2xl font-semibold tracking-[-0.03em] text-ink">{framework.linguagem}</dd>
|
||||
<dd className="mt-0.5 text-xs text-muted">{framework.nome_completo}</dd>
|
||||
</div>
|
||||
<div className="tile">
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Categoría" : isEn ? "Category" : "Categoria"}</dt>
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Categoría" : isEn ? "Category" : isFr ? "Catégorie" : isDe ? "Kategorie" : "Categoria"}</dt>
|
||||
<dd className="mt-1 font-display text-2xl font-semibold tracking-[-0.03em] text-ink">{framework.tipo}</dd>
|
||||
</div>
|
||||
<div className="tile">
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Objetivo principal" : isEn ? "Main purpose" : "Objetivo principal"}</dt>
|
||||
<dt className="text-xs font-medium text-muted">{isEs ? "Objetivo principal" : isEn ? "Main purpose" : isFr ? "Objectif principal" : isDe ? "Hauptzweck" : "Objetivo principal"}</dt>
|
||||
<dd className="mt-1 text-sm font-medium leading-relaxed text-ink">{framework.funcao_principal}</dd>
|
||||
</div>
|
||||
</dl>
|
||||
</section>
|
||||
|
||||
<section className="shell mt-12 grid gap-5 lg:grid-cols-2" aria-label={isEs ? "Funciones y aplicaciones" : isEn ? "Features and applications" : "Recursos e aplicações"}>
|
||||
<section className="shell mt-12 grid gap-5 lg:grid-cols-2" aria-label={isEs ? "Funciones y aplicaciones" : isEn ? "Features and applications" : isFr ? "Fonctionnalités et applications" : isDe ? "Features und Anwendungen" : "Recursos e aplicações"}>
|
||||
<div className="card p-5 sm:p-7">
|
||||
<h2 className="font-display text-xl font-semibold tracking-[-0.03em] text-ink">
|
||||
{isEs ? "Funciones destacadas" : isEn ? "Key features" : "Recursos de destaque"}
|
||||
{isEs ? "Funciones destacadas" : isEn ? "Key features" : isFr ? "Fonctionnalités clés" : isDe ? "Wichtigste Features" : "Recursos de destaque"}
|
||||
</h2>
|
||||
<ul className="mt-5 space-y-3">
|
||||
{features.map((feature) => (
|
||||
@@ -108,7 +114,7 @@ export default async function FrameworkDetail({ params }) {
|
||||
|
||||
<div className="card p-5 sm:p-7">
|
||||
<h2 className="font-display text-xl font-semibold tracking-[-0.03em] text-ink">
|
||||
{isEs ? "Cuándo usar" : isEn ? "When to use" : "Quando usar"}
|
||||
{isEs ? "Cuándo usar" : isEn ? "When to use" : isFr ? "Quand l'utiliser" : isDe ? "Einsatzbereiche" : "Quando usar"}
|
||||
</h2>
|
||||
<ul className="mt-5 space-y-2.5">
|
||||
{useCases.map((useCase) => (
|
||||
@@ -126,10 +132,10 @@ export default async function FrameworkDetail({ params }) {
|
||||
<div className="max-w-2xl">
|
||||
<span className="chip chip-accent">
|
||||
<Box className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isEs ? "ESP-IDF 4.4 o superior" : isEn ? "ESP-IDF 4.4 or higher" : "ESP-IDF 4.4 ou superior"}
|
||||
{isEs ? "ESP-IDF 4.4 o superior" : isEn ? "ESP-IDF 4.4 or higher" : isFr ? "ESP-IDF 4.4 ou supérieur" : isDe ? "ESP-IDF 4.4 oder höher" : "ESP-IDF 4.4 ou superior"}
|
||||
</span>
|
||||
<h2 className="section-title mt-4">
|
||||
{isEs ? "Módulos con ESP Component Registry" : isEn ? "Modules with the ESP Component Registry" : "Módulos com o ESP Component Registry"}
|
||||
{isEs ? "Módulos con ESP Component Registry" : isEn ? "Modules with the ESP Component Registry" : isFr ? "Modules avec l'ESP Component Registry" : isDe ? "Module mit der ESP Component Registry" : "Módulos com o ESP Component Registry"}
|
||||
</h2>
|
||||
<p className="mt-3 text-base leading-relaxed text-muted">
|
||||
{isEs ? (
|
||||
@@ -144,6 +150,18 @@ export default async function FrameworkDetail({ params }) {
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code> and the command{" "}
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf.py add-dependency</code> to download display drivers (LVGL), industrial stacks (Modbus), RainMaker, and more.
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
Dans les projets ESP-IDF v4.4+ et v5.x, les bibliothèques n'ont plus besoin d'être ajoutées comme sous-modules Git. Utilisez le fichier{" "}
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code> et la commande{" "}
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf.py add-dependency</code> pour télécharger des pilotes d'écran (LVGL), des piles industrielles (Modbus), RainMaker et bien plus encore.
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
In Projekten mit ESP-IDF v4.4+ und v5.x müssen Bibliotheken nicht mehr als Git-Submodule eingebunden werden. Nutzen Sie{" "}
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code> und den Befehl{" "}
|
||||
<code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf.py add-dependency</code>, um Display-Treiber (LVGL), Industrieprotokolle (Modbus), RainMaker und mehr herunterzuladen.
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
Nos projetos ESP-IDF v4.4+ e v5.x, as bibliotecas não precisam mais entrar como submódulos Git. Use o{" "}
|
||||
@@ -154,7 +172,7 @@ export default async function FrameworkDetail({ params }) {
|
||||
</p>
|
||||
</div>
|
||||
<Link href={getLocalizedHref("/componentes", currentLocale)} className="btn btn-primary shrink-0">
|
||||
{isEs ? "Explorar componentes" : isEn ? "Explore components" : "Explorar componentes"}
|
||||
{isEs ? "Explorar componentes" : isEn ? "Explore components" : isFr ? "Explorer les composants" : isDe ? "Komponenten erkunden" : "Explorar componentes"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
@@ -170,7 +188,7 @@ export default async function FrameworkDetail({ params }) {
|
||||
<div className="shell section pt-10">
|
||||
<Link href={getLocalizedHref("/frameworks", currentLocale)} className="inline-flex min-h-11 items-center gap-2 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
<ArrowRight className="h-4 w-4 rotate-180" aria-hidden="true" />
|
||||
{isEs ? "Ver todos los frameworks" : isEn ? "View all frameworks" : "Ver todos os frameworks"}
|
||||
{isEs ? "Ver todos los frameworks" : isEn ? "View all frameworks" : isFr ? "Voir tous les frameworks" : isDe ? "Alle Frameworks ansehen" : "Ver todos os frameworks"}
|
||||
</Link>
|
||||
</div>
|
||||
</main>
|
||||
@@ -184,21 +202,27 @@ export async function generateMetadata({ params }) {
|
||||
const { locale, key } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : frameworksDataPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : isFr ? "fr" : isDe ? "de" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : isFr ? frameworksDataFr : isDe ? frameworksDataDe : frameworksDataPt;
|
||||
const framework = frameworksData[key];
|
||||
|
||||
if (!framework) {
|
||||
return { title: isEs ? "Framework no encontrado" : isEn ? "Framework not found" : "Framework não encontrado", robots: { index: false, follow: false } };
|
||||
return { title: isEs ? "Framework no encontrado" : isEn ? "Framework not found" : isFr ? "Framework introuvable" : isDe ? "Framework nicht gefunden" : "Framework não encontrado", robots: { index: false, follow: false } };
|
||||
}
|
||||
|
||||
return {
|
||||
...paginaMeta({
|
||||
titulo: isEs ? `${framework.nome} para ESP32 · Guía técnica` : isEn ? `${framework.nome} for ESP32 · Technical Guide` : `${framework.nome} para ESP32 · Guia Técnico`,
|
||||
titulo: isEs ? `${framework.nome} para ESP32 · Guía técnica` : isEn ? `${framework.nome} for ESP32 · Technical Guide` : isFr ? `${framework.nome} pour ESP32 · Guide technique` : isDe ? `${framework.nome} für ESP32 · Technischer Leitfaden` : `${framework.nome} para ESP32 · Guia Técnico`,
|
||||
descricao: isEs
|
||||
? `${framework.nome_completo}: ${framework.descricao} Guía con ejemplos prácticos de código y casos de uso.`
|
||||
: isEn
|
||||
? `${framework.nome_completo}: ${framework.descricao} Guide with practical code examples and use cases.`
|
||||
: isFr
|
||||
? `${framework.nome_completo} : ${framework.descricao} Guide avec exemples pratiques de code et cas d'usage.`
|
||||
: isDe
|
||||
? `${framework.nome_completo}: ${framework.descricao} Leitfaden mit praktischen Codebeispielen und Anwendungsfällen.`
|
||||
: `${framework.nome_completo}: ${framework.descricao} Guia com exemplos práticos de código e casos de uso.`,
|
||||
caminho: `/frameworks/${encodeURIComponent(key)}`,
|
||||
tipo: "article",
|
||||
@@ -215,6 +239,18 @@ export async function generateMetadata({ params }) {
|
||||
`${framework.nome} ESP32`, `program ESP32 with ${framework.nome}`,
|
||||
"ESP32", "ESP32 framework",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
framework.nome, framework.nome_completo,
|
||||
`${framework.nome} ESP32`, `programmer ESP32 avec ${framework.nome}`,
|
||||
"ESP32", "framework ESP32",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
framework.nome, framework.nome_completo,
|
||||
`${framework.nome} ESP32`, `ESP32 programmieren mit ${framework.nome}`,
|
||||
"ESP32", "ESP32 Framework",
|
||||
]
|
||||
: [
|
||||
framework.nome, framework.nome_completo,
|
||||
`${framework.nome} ESP32`, `programar ESP32 com ${framework.nome}`,
|
||||
|
||||
@@ -4,17 +4,27 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return {
|
||||
...paginaMeta({
|
||||
titulo: isEs
|
||||
? "Frameworks y SDKs para ESP32: Guía completa y comparativa"
|
||||
: isEn
|
||||
? "ESP32 Frameworks & SDKs: Complete Guide and Comparison"
|
||||
: isFr
|
||||
? "Frameworks et SDKs pour ESP32 : guide complet et comparatif"
|
||||
: isDe
|
||||
? "ESP32-Frameworks & SDKs: Vollständiger Leitfaden und Vergleich"
|
||||
: "Frameworks & SDKs para ESP32: Guia Completo e Comparativo",
|
||||
descricao: isEs
|
||||
? "Guía completa de desarrollo: ESP-IDF, ESP-RainMaker, ESP-Matter, Rust, ESP-ADF, ESP-SR, ESP-WHO, Arduino y MicroPython con ejemplos de código."
|
||||
: isEn
|
||||
? "Complete development guide: ESP-IDF, ESP-RainMaker, ESP-Matter, Rust, ESP-ADF, ESP-SR, ESP-WHO, Arduino, and MicroPython with code examples."
|
||||
: isFr
|
||||
? "Guide complet de développement : ESP-IDF, ESP-RainMaker, ESP-Matter, Rust, ESP-ADF, ESP-SR, ESP-WHO, Arduino et MicroPython avec exemples de code."
|
||||
: isDe
|
||||
? "Vollständiger Entwicklungsleitfaden: ESP-IDF, ESP-RainMaker, ESP-Matter, Rust, ESP-ADF, ESP-SR, ESP-WHO, Arduino und MicroPython mit Codebeispielen."
|
||||
: "Guia completo de desenvolvimento: ESP-IDF, ESP-RainMaker, ESP-Matter, Rust, ESP-ADF, ESP-SR, ESP-WHO, Arduino e MicroPython com exemplos de código.",
|
||||
caminho: "/frameworks",
|
||||
locale,
|
||||
@@ -46,6 +56,34 @@ export async function generateMetadata({ params }) {
|
||||
"frameworks ESP32",
|
||||
"program ESP32",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"ESP-IDF",
|
||||
"ESP-RainMaker",
|
||||
"ESP-Matter",
|
||||
"Rust ESP32",
|
||||
"ESP-SR",
|
||||
"ESP-ADF",
|
||||
"ESP-IoT-Solution",
|
||||
"Arduino ESP32",
|
||||
"MicroPython ESP32",
|
||||
"frameworks ESP32",
|
||||
"programmer ESP32",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
"ESP-IDF",
|
||||
"ESP-RainMaker",
|
||||
"ESP-Matter",
|
||||
"Rust ESP32",
|
||||
"ESP-SR",
|
||||
"ESP-ADF",
|
||||
"ESP-IoT-Solution",
|
||||
"Arduino ESP32",
|
||||
"MicroPython ESP32",
|
||||
"ESP32 Frameworks",
|
||||
"ESP32 programmieren",
|
||||
]
|
||||
: [
|
||||
"ESP-IDF",
|
||||
"ESP-RainMaker",
|
||||
@@ -67,6 +105,8 @@ export default async function FrameworksLayout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return (
|
||||
<>
|
||||
<script
|
||||
@@ -74,8 +114,8 @@ export default async function FrameworksLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: "Frameworks", caminho: isEs ? "/es/frameworks" : isEn ? "/en/frameworks" : "/frameworks" },
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: "Frameworks", caminho: isEs ? "/es/frameworks" : isEn ? "/en/frameworks" : isFr ? "/fr/frameworks" : isDe ? "/de/frameworks" : "/frameworks" },
|
||||
])
|
||||
),
|
||||
}}
|
||||
|
||||
@@ -6,6 +6,8 @@ import Link from "next/link";
|
||||
import frameworksDataPt from "@/public/frameworks.json";
|
||||
import frameworksDataEn from "@/data/en/frameworks.json";
|
||||
import frameworksDataEs from "@/data/es/frameworks.json";
|
||||
import frameworksDataFr from "@/data/fr/frameworks.json";
|
||||
import frameworksDataDe from "@/data/de/frameworks.json";
|
||||
import { paginaMeta } from "@/lib/seo";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import { ArrowRight, ArrowUpRight, Box, Brain, Cloud, GraduationCap, Layers, Mic, Music, Sparkles } from "lucide-react";
|
||||
@@ -109,14 +111,82 @@ const GUIAS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const GUIAS_FR = [
|
||||
{
|
||||
icon: GraduationCap,
|
||||
titulo: "Je débute",
|
||||
texto: "Arduino ou MicroPython sont les voies les plus rapides pour tester capteurs et APIs. Pour la production, optez pour ESP-IDF ou Rust.",
|
||||
links: [
|
||||
["Arduino", "/frameworks/Arduino"],
|
||||
["MicroPython", "/frameworks/MicroPython"],
|
||||
["Rust", "/frameworks/Rust-ESP"],
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Cloud,
|
||||
titulo: "Cloud et maison connectée",
|
||||
texto: "ESP-Matter pour l'interopérabilité, ESP-RainMaker pour un cloud clé en main et Zigbee pour les réseaux maillés locaux à basse consommation.",
|
||||
links: [
|
||||
["RainMaker", "/frameworks/ESP-RainMaker"],
|
||||
["Matter", "/frameworks/ESP-Matter"],
|
||||
["Zigbee", "/frameworks/ESP-Zigbee-SDK"],
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Sparkles,
|
||||
titulo: "Audio, voix et IA",
|
||||
texto: "ESP-ADF pour le traitement audio, ESP-SR pour la reconnaissance vocale hors ligne et ESP-NN pour accélérer le TinyML.",
|
||||
links: [
|
||||
["Audio", "/frameworks/ESP-ADF", Music],
|
||||
["Voix", "/frameworks/ESP-SR", Mic],
|
||||
["IA", "/frameworks/ESP-NN", Brain],
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const GUIAS_DE = [
|
||||
{
|
||||
icon: GraduationCap,
|
||||
titulo: "Erste Schritte",
|
||||
texto: "Arduino oder MicroPython sind die schnellsten Wege, um Sensoren und APIs zu testen. Für den Produkteinsatz empfehlen sich ESP-IDF oder Rust.",
|
||||
links: [
|
||||
["Arduino", "/frameworks/Arduino"],
|
||||
["MicroPython", "/frameworks/MicroPython"],
|
||||
["Rust", "/frameworks/Rust-ESP"],
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Cloud,
|
||||
titulo: "Cloud und Smart Home",
|
||||
texto: "ESP-Matter für Interoperabilität, ESP-RainMaker für eine fertige Cloud-Lösung und Zigbee für stromsparende lokale Mesh-Netzwerke.",
|
||||
links: [
|
||||
["RainMaker", "/frameworks/ESP-RainMaker"],
|
||||
["Matter", "/frameworks/ESP-Matter"],
|
||||
["Zigbee", "/frameworks/ESP-Zigbee-SDK"],
|
||||
],
|
||||
},
|
||||
{
|
||||
icon: Sparkles,
|
||||
titulo: "Audio, Sprache und KI",
|
||||
texto: "ESP-ADF für Audioverarbeitung, ESP-SR für Offline-Sprachkennung und ESP-NN zur Beschleunigung von TinyML.",
|
||||
links: [
|
||||
["Audio", "/frameworks/ESP-ADF", Music],
|
||||
["Sprache", "/frameworks/ESP-SR", Mic],
|
||||
["KI", "/frameworks/ESP-NN", Brain],
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
export default async function Frameworks({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : frameworksDataPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : isFr ? "fr" : isDe ? "de" : "pt";
|
||||
const frameworksData = isEs ? frameworksDataEs : isEn ? frameworksDataEn : isFr ? frameworksDataFr : isDe ? frameworksDataDe : frameworksDataPt;
|
||||
const frameworks = Object.entries(frameworksData);
|
||||
const guias = isEs ? GUIAS_ES : isEn ? GUIAS_EN : GUIAS_PT;
|
||||
const guias = isEs ? GUIAS_ES : isEn ? GUIAS_EN : isFr ? GUIAS_FR : isDe ? GUIAS_DE : GUIAS_PT;
|
||||
|
||||
return (
|
||||
<div className="site-canvas min-h-screen">
|
||||
@@ -126,20 +196,26 @@ export default async function Frameworks({ params }) {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Frameworks y SDKs" : isEn ? "Frameworks & SDKs" : "Frameworks e SDKs" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isEs ? "Frameworks y SDKs" : isEn ? "Frameworks & SDKs" : isFr ? "Frameworks et SDKs" : isDe ? "Frameworks & SDKs" : "Frameworks e SDKs" }]}
|
||||
icon={Layers}
|
||||
label={isEs ? `${frameworks.length} frameworks y SDKs` : isEn ? `${frameworks.length} frameworks and SDKs` : `${frameworks.length} frameworks e SDKs`}
|
||||
title={isEs ? "Frameworks y SDKs de ESP32" : isEn ? "ESP32 Frameworks and SDKs" : "Frameworks e SDKs do ESP32"}
|
||||
label={isEs ? `${frameworks.length} frameworks y SDKs` : isEn ? `${frameworks.length} frameworks and SDKs` : isFr ? `${frameworks.length} frameworks et SDKs` : isDe ? `${frameworks.length} Frameworks und SDKs` : `${frameworks.length} frameworks e SDKs`}
|
||||
title={isEs ? "Frameworks y SDKs de ESP32" : isEn ? "ESP32 Frameworks and SDKs" : isFr ? "Frameworks et SDKs pour ESP32" : isDe ? "ESP32-Frameworks und SDKs" : "Frameworks e SDKs do ESP32"}
|
||||
lede={
|
||||
isEs
|
||||
? "Desde C/C++ nativo con FreeRTOS hasta Rust, nube IoT, reconocimiento de voz, audio y Matter. Elija según lo que desee construir."
|
||||
: isEn
|
||||
? "From native C/C++ with FreeRTOS to Rust, IoT cloud, speech recognition, audio, and Matter. Choose by what you want to build."
|
||||
: isFr
|
||||
? "Du C/C++ natif avec FreeRTOS à Rust, en passant par le cloud IoT, la reconnaissance vocale, l'audio et Matter. Choisissez selon ce que vous souhaitez concevoir."
|
||||
: isDe
|
||||
? "Von nativem C/C++ mit FreeRTOS bis hin zu Rust, IoT-Cloud, Spracherkennung, Audio und Matter. Wählen Sie passend zu Ihrem Projekt."
|
||||
: "Do C/C++ nativo com FreeRTOS ao Rust, passando por nuvem IoT, reconhecimento de voz, áudio e Matter. Escolha pelo que você quer construir."
|
||||
}
|
||||
/>
|
||||
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Por dónde empezar" : isEn ? "Where to begin" : "Por onde começar"}>
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Por dónde empezar" : isEn ? "Where to begin" : isFr ? "Par où commencer" : isDe ? "Wo anfangen" : "Por onde começar"}>
|
||||
<div className="grid gap-4 md:grid-cols-3">
|
||||
{guias.map(({ icon: Icon, titulo, texto, links }) => (
|
||||
<div key={titulo} className="card flex flex-col p-5 sm:p-6">
|
||||
@@ -168,7 +244,7 @@ export default async function Frameworks({ params }) {
|
||||
<div className="max-w-2xl">
|
||||
<span className="chip chip-accent">
|
||||
<Box className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isEs ? "Arquitectura modular" : isEn ? "Modular architecture" : "Arquitetura modular"}
|
||||
{isEs ? "Arquitectura modular" : isEn ? "Modular architecture" : isFr ? "Architecture modulaire" : isDe ? "Modulare Architektur" : "Arquitetura modular"}
|
||||
</span>
|
||||
<h2 className="section-title mt-4">ESP Component Registry</h2>
|
||||
<p className="mt-3 text-base leading-relaxed text-muted">
|
||||
@@ -182,6 +258,16 @@ export default async function Frameworks({ params }) {
|
||||
Install display drivers (LVGL), industrial stacks (Modbus), cloud integrations, and board support packages
|
||||
(BSPs) with a single line in your <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code> manifest.
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
Installez des pilotes d'écran (LVGL), des piles industrielles (Modbus), des fonctionnalités cloud et des paquets de support de cartes
|
||||
(BSPs) avec une seule ligne dans votre manifeste <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code>.
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
Installieren Sie Display-Treiber (LVGL), Industrieprotokolle (Modbus), Cloud-Funktionen und Board-Support-Pakete
|
||||
(BSPs) mit einer einzigen Zeile in Ihrem <code className="rounded bg-surface-2 px-1.5 py-0.5 font-mono text-sm">idf_component.yml</code>-Manifest.
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
Instale drivers de display (LVGL), pilhas industriais (Modbus), recursos de nuvem e pacotes de placa
|
||||
@@ -191,7 +277,7 @@ export default async function Frameworks({ params }) {
|
||||
</p>
|
||||
</div>
|
||||
<Link href={getLocalizedHref("/componentes", currentLocale)} className="btn btn-primary shrink-0">
|
||||
{isEs ? "Explorar componentes" : isEn ? "Explore components" : "Explorar componentes"}
|
||||
{isEs ? "Explorar componentes" : isEn ? "Explore components" : isFr ? "Explorer les composants" : isDe ? "Komponenten erkunden" : "Explorar componentes"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
@@ -201,8 +287,8 @@ export default async function Frameworks({ params }) {
|
||||
<SectionHead
|
||||
id="todos-titulo"
|
||||
eyebrow={isEs ? "Todos" : isEn ? "All" : "Todos"}
|
||||
title={isEs ? "Todos los frameworks" : isEn ? "All frameworks" : "Todos os frameworks"}
|
||||
lede={isEs ? "Cada ficha ofrece funciones, aplicaciones ideales, ejemplos de código y enlaces oficiales." : isEn ? "Each page provides features, ideal use cases, code examples, and official links." : "Cada ficha traz recursos, aplicações ideais, exemplo de código e links oficiais."}
|
||||
title={isEs ? "Todos los frameworks" : isEn ? "All frameworks" : isFr ? "Tous les frameworks" : isDe ? "Alle Frameworks" : "Todos os frameworks"}
|
||||
lede={isEs ? "Cada ficha ofrece funciones, aplicaciones ideales, ejemplos de código y enlaces oficiales." : isEn ? "Each page provides features, ideal use cases, code examples, and official links." : isFr ? "Chaque fiche présente les fonctionnalités, les cas d'usage idéaux, des exemples de code et les liens officiels." : isDe ? "Jedes Datenblatt bietet Features, ideale Anwendungsbereiche, Codebeispiele und offizielle Links." : "Cada ficha traz recursos, aplicações ideais, exemplo de código e links oficiais."}
|
||||
/>
|
||||
|
||||
<div className="mt-8 grid gap-4 md:grid-cols-2 lg:grid-cols-3">
|
||||
@@ -224,7 +310,7 @@ export default async function Frameworks({ params }) {
|
||||
</ul>
|
||||
|
||||
<span className="mt-5 inline-flex items-center gap-1 border-t border-line pt-4 text-sm font-medium text-accent">
|
||||
{isEs ? "Ver detalles y ejemplo" : isEn ? "View details and example" : "Ver detalhes e exemplo"}
|
||||
{isEs ? "Ver detalles y ejemplo" : isEn ? "View details and example" : isFr ? "Voir les détails et l'exemple" : isDe ? "Details und Beispiel ansehen" : "Ver detalhes e exemplo"}
|
||||
<ArrowUpRight className="h-4 w-4 transition-transform group-hover:-translate-y-0.5 group-hover:translate-x-0.5" aria-hidden="true" />
|
||||
</span>
|
||||
</Link>
|
||||
|
||||
@@ -2,21 +2,33 @@ import { paginaMeta, jsonLd } from "@/lib/seo";
|
||||
import { categoriasGlossario as categoriasGlossarioPt } from "@/lib/glossarioData";
|
||||
import { categoriasGlossario as categoriasGlossarioEn } from "@/lib/data/en/glossario.js";
|
||||
import { categoriasGlossario as categoriasGlossarioEs } from "@/lib/data/es/glossario.js";
|
||||
import { categoriasGlossario as categoriasGlossarioFr } from "@/lib/data/fr/glossario.js";
|
||||
import { categoriasGlossario as categoriasGlossarioDe } from "@/lib/data/de/glossario.js";
|
||||
|
||||
export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEs
|
||||
? "Glosario técnico de ESP32: Términos y conceptos"
|
||||
: isEn
|
||||
? "ESP32 Technical Glossary: Terms and Concepts"
|
||||
: isFr
|
||||
? "Glossaire technique de l'ESP32 : termes et concepts"
|
||||
: isDe
|
||||
? "Technisches ESP32-Glossar: Begriffe und Konzepte"
|
||||
: "Glossário Técnico do ESP32: Termos e Conceitos",
|
||||
descricao: isEs
|
||||
? "Más de 50 conceptos esenciales de ESP32 explicados: GPIO, Strapping Pins, ULP, PSRAM, FreeRTOS, eFuse, Deep Sleep, OTA, Secure Boot, ECDSA, Matter y Thread."
|
||||
: isEn
|
||||
? "Over 50 essential ESP32 concepts explained: GPIO, Strapping Pins, ULP, PSRAM, FreeRTOS, eFuse, Deep Sleep, OTA, Secure Boot, ECDSA, Matter, and Thread."
|
||||
: isFr
|
||||
? "Plus de 50 concepts essentiels de l'ESP32 expliqués : GPIO, Strapping Pins, ULP, PSRAM, FreeRTOS, eFuse, Deep Sleep, OTA, Secure Boot, ECDSA, Matter et Thread."
|
||||
: isDe
|
||||
? "Über 50 wichtige ESP32-Konzepte verständlich erklärt: GPIO, Strapping-Pins, ULP, PSRAM, FreeRTOS, eFuse, Deep Sleep, OTA, Secure Boot, ECDSA, Matter und Thread."
|
||||
: "Mais de 50 termos e conceitos essenciais do ecossistema ESP32 explicados em português: GPIO, Strapping Pins, ULP, PSRAM, FreeRTOS, eFuse, Deep Sleep, OTA, Secure Boot, ECDSA, Matter e Thread.",
|
||||
caminho: "/glossario",
|
||||
locale,
|
||||
@@ -40,6 +52,26 @@ export async function generateMetadata({ params }) {
|
||||
"microcontroller technical terms",
|
||||
"ESP32 hardware concepts",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"glossaire ESP32",
|
||||
"qu'est-ce que le GPIO",
|
||||
"que sont les strapping pins",
|
||||
"qu'est-ce que l'ESP32 ULP",
|
||||
"qu'est-ce que l'ESP32 PSRAM",
|
||||
"termes techniques microcontrôleur",
|
||||
"concepts matériels ESP32",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
"ESP32 Glossar",
|
||||
"was ist GPIO",
|
||||
"was sind Strapping-Pins",
|
||||
"was ist ESP32 ULP",
|
||||
"was ist ESP32 PSRAM",
|
||||
"technische Mikrocontroller-Begriffe",
|
||||
"ESP32 Hardware-Konzepte",
|
||||
]
|
||||
: [
|
||||
"glossário ESP32",
|
||||
"o que é GPIO",
|
||||
@@ -56,7 +88,10 @@ export default async function GlossarioLayout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const categorias = isEs ? categoriasGlossarioEs : isEn ? categoriasGlossarioEn : categoriasGlossarioPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const categorias = isEs ? categoriasGlossarioEs : isEn ? categoriasGlossarioEn : isFr ? categoriasGlossarioFr : isDe ? categoriasGlossarioDe : categoriasGlossarioPt;
|
||||
const canonPath = isEs ? "/es/glosario" : isEn ? "/en/glossary" : isFr ? "/fr/glossaire" : isDe ? "/de/glossar" : "/glossario";
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -71,8 +106,8 @@ export default async function GlossarioLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: isEs ? "Glosario técnico" : isEn ? "Technical Glossary" : "Glossário Técnico", caminho: isEs ? "/es/glosario" : isEn ? "/en/glossary" : "/glossario" },
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : isFr ? "Accueil" : isDe ? "Startseite" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : isFr ? "/fr" : isDe ? "/de" : "/" },
|
||||
{ nome: isEs ? "Glosario técnico" : isEn ? "Technical Glossary" : isFr ? "Glossaire technique" : isDe ? "Technisches Glossar" : "Glossário Técnico", caminho: canonPath },
|
||||
])
|
||||
),
|
||||
}}
|
||||
@@ -82,13 +117,17 @@ export default async function GlossarioLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.aplicacaoWeb({
|
||||
nome: isEs ? "Glosario técnico de ESP32" : isEn ? "ESP32 Technical Glossary" : "Glossário Técnico do ESP32",
|
||||
nome: isEs ? "Glosario técnico de ESP32" : isEn ? "ESP32 Technical Glossary" : isFr ? "Glossaire technique de l'ESP32" : isDe ? "Technisches ESP32-Glossar" : "Glossário Técnico do ESP32",
|
||||
descricao: isEs
|
||||
? "Enciclopedia de términos técnicos y conceptos de hardware y software del ecosistema ESP32."
|
||||
: isEn
|
||||
? "Encyclopedia of hardware and software technical terms for the ESP32 ecosystem."
|
||||
: isFr
|
||||
? "Encyclopédie des termes techniques et des concepts matériels et logiciels de l'écosystème ESP32."
|
||||
: isDe
|
||||
? "Enzyklopädie technischer Begriffe und Hardware-/Softwarekonzepte für das ESP32-Ökosystem."
|
||||
: "Enciclopédia de termos técnicos e conceitos de hardware e software do ecossistema ESP32.",
|
||||
caminho: isEs ? "/es/glosario" : isEn ? "/en/glossary" : "/glossario",
|
||||
caminho: canonPath,
|
||||
locale,
|
||||
})
|
||||
),
|
||||
|
||||
+107
-28
@@ -9,6 +9,8 @@ import Link from "next/link";
|
||||
import * as glossarioPt from "@/lib/glossarioData";
|
||||
import * as glossarioEn from "@/lib/data/en/glossario";
|
||||
import * as glossarioEs from "@/lib/data/es/glossario";
|
||||
import * as glossarioFr from "@/lib/data/fr/glossario";
|
||||
import * as glossarioDe from "@/lib/data/de/glossario";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import {
|
||||
ArrowRight,
|
||||
@@ -42,8 +44,10 @@ export default function GlossarioPage() {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const { categoriasGlossario } = isEs ? glossarioEs : isEn ? glossarioEn : glossarioPt;
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const currentLocale = isDe ? "de" : isFr ? "fr" : isEs ? "es" : isEn ? "en" : "pt";
|
||||
const { categoriasGlossario } = isDe ? glossarioDe : isFr ? glossarioFr : isEs ? glossarioEs : isEn ? glossarioEn : glossarioPt;
|
||||
|
||||
const [busca, setBusca] = useState("");
|
||||
const [categoriaSelecionada, setCategoriaSelecionada] = useState("todas");
|
||||
@@ -112,12 +116,38 @@ export default function GlossarioPage() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Glosario" : isEn ? "Glossary" : "Glossário" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isDe ? "Glossar" : isFr ? "Glossaire" : isEs ? "Glosario" : isEn ? "Glossary" : "Glossário" }]}
|
||||
icon={BookOpen}
|
||||
label={isEs ? `${todosOsTermos.length} términos explicados` : isEn ? `${todosOsTermos.length} terms explained` : `${todosOsTermos.length} termos explicados`}
|
||||
title={isEs ? "Glosario técnico de ESP32" : isEn ? "ESP32 Technical Glossary" : "Glossário técnico do ESP32"}
|
||||
label={
|
||||
isDe
|
||||
? `${todosOsTermos.length} Begriffe erklärt`
|
||||
: isFr
|
||||
? `${todosOsTermos.length} termes expliqués`
|
||||
: isEs
|
||||
? `${todosOsTermos.length} términos explicados`
|
||||
: isEn
|
||||
? `${todosOsTermos.length} terms explained`
|
||||
: `${todosOsTermos.length} termos explicados`
|
||||
}
|
||||
title={
|
||||
isDe
|
||||
? "Technisches Glossar für ESP32"
|
||||
: isFr
|
||||
? "Glossaire technique ESP32"
|
||||
: isEs
|
||||
? "Glosario técnico de ESP32"
|
||||
: isEn
|
||||
? "ESP32 Technical Glossary"
|
||||
: "Glossário técnico do ESP32"
|
||||
}
|
||||
lede={
|
||||
isEs
|
||||
isDe
|
||||
? "Präzise Definitionen, Hardware-Parameter und praktische Beispiele für jeden Begriff des Ökosystems – von ADC bis Secure Boot."
|
||||
: isFr
|
||||
? "Définitions précises, paramètres matériels et exemples pratiques pour chaque terme de l'écosystème, de l'ADC au Secure Boot."
|
||||
: isEs
|
||||
? "Definiciones directas, parámetros de hardware y un ejemplo práctico para cada término del ecosistema, desde ADC hasta Secure Boot."
|
||||
: isEn
|
||||
? "Direct definitions, hardware parameters, and practical examples for every ecosystem term, from ADC to Secure Boot."
|
||||
@@ -125,11 +155,11 @@ export default function GlossarioPage() {
|
||||
}
|
||||
/>
|
||||
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Búsqueda y filtros" : isEn ? "Search and filters" : "Busca e filtros"}>
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isDe ? "Suche und Filter" : isFr ? "Recherche et filtres" : isEs ? "Búsqueda y filtros" : isEn ? "Search and filters" : "Busca e filtros"}>
|
||||
<div className="panel p-5 sm:p-7">
|
||||
<div className="relative">
|
||||
<label htmlFor="busca-glossario" className="sr-only">
|
||||
{isEs ? "Buscar término, sigla o concepto" : isEn ? "Search term, acronym, or concept" : "Buscar termo, sigla ou conceito"}
|
||||
{isDe ? "Nach Begriff, Abkürzung oder Konzept suchen" : isFr ? "Rechercher un terme, un sigle ou un concept" : isEs ? "Buscar término, sigla o concepto" : isEn ? "Search term, acronym, or concept" : "Buscar termo, sigla ou conceito"}
|
||||
</label>
|
||||
<Search className="pointer-events-none absolute left-4 top-1/2 h-5 w-5 -translate-y-1/2 text-muted" aria-hidden="true" />
|
||||
<input
|
||||
@@ -138,7 +168,7 @@ export default function GlossarioPage() {
|
||||
type="search"
|
||||
value={busca}
|
||||
onChange={(e) => setBusca(e.target.value)}
|
||||
placeholder={isEs ? "Buscar término, sigla o concepto" : isEn ? "Search term, acronym, or concept" : "Buscar termo, sigla ou conceito"}
|
||||
placeholder={isDe ? "Nach Begriff, Abkürzung oder Konzept suchen" : isFr ? "Rechercher un terme, un sigle ou un concept" : isEs ? "Buscar término, sigla o concepto" : isEn ? "Search term, acronym, or concept" : "Buscar termo, sigla ou conceito"}
|
||||
autoComplete="off"
|
||||
className={`field pl-12 text-base ${busca ? "pr-28" : "pr-4"}`}
|
||||
/>
|
||||
@@ -146,14 +176,14 @@ export default function GlossarioPage() {
|
||||
{busca && (
|
||||
<button type="button" onClick={() => { setBusca(""); searchInputRef.current?.focus(); }} className="btn btn-ghost btn-sm">
|
||||
<X className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isEs ? "Limpiar" : isEn ? "Clear" : "Limpar"}
|
||||
{isDe ? "Löschen" : isFr ? "Effacer" : isEs ? "Limpiar" : isEn ? "Clear" : "Limpar"}
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="mt-4 flex flex-wrap items-center gap-2">
|
||||
<span className="mr-1 text-sm text-muted">{isEs ? "Más buscados" : isEn ? "Popular searches" : "Mais buscados"}</span>
|
||||
<span className="mr-1 text-sm text-muted">{isDe ? "Häufig gesucht" : isFr ? "Plus recherchés" : isEs ? "Más buscados" : isEn ? "Popular searches" : "Mais buscados"}</span>
|
||||
{BUSCAS_POPULARES.map((rotulo) => (
|
||||
<button
|
||||
key={rotulo}
|
||||
@@ -167,7 +197,7 @@ export default function GlossarioPage() {
|
||||
</div>
|
||||
|
||||
<div className="mt-5 border-t border-line pt-5">
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Categoría" : isEn ? "Category" : "Categoria"}</h2>
|
||||
<h2 className="text-sm font-semibold text-ink">{isDe ? "Kategorie" : isFr ? "Catégorie" : isEs ? "Categoría" : isEn ? "Category" : "Categoria"}</h2>
|
||||
<div className="mt-3 flex flex-wrap gap-2">
|
||||
<button
|
||||
type="button"
|
||||
@@ -176,7 +206,7 @@ export default function GlossarioPage() {
|
||||
className="chip-btn"
|
||||
>
|
||||
<LayoutGrid className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Todas" : isEn ? "All" : "Todas"}
|
||||
{isDe ? "Alle" : isFr ? "Toutes" : isEs ? "Todas" : isEn ? "All" : "Todas"}
|
||||
<span className="tabular-nums opacity-80">{todosOsTermos.length}</span>
|
||||
</button>
|
||||
{categoriasGlossario.map((cat) => {
|
||||
@@ -199,10 +229,10 @@ export default function GlossarioPage() {
|
||||
</div>
|
||||
|
||||
<div className="mt-6 border-t border-line pt-6">
|
||||
<h2 className="text-sm font-semibold text-ink">{isEs ? "Orden alfabético" : isEn ? "Alphabetical order" : "Ordem alfabética"}</h2>
|
||||
<div className="mt-3 flex flex-wrap gap-1.5" role="group" aria-label={isEs ? "Filtrar por letra inicial" : isEn ? "Filter by first letter" : "Filtrar pela letra inicial"}>
|
||||
<h2 className="text-sm font-semibold text-ink">{isDe ? "Alphabetische Reihenfolge" : isFr ? "Ordre alphabétique" : isEs ? "Orden alfabético" : isEn ? "Alphabetical order" : "Ordem alfabética"}</h2>
|
||||
<div className="mt-3 flex flex-wrap gap-1.5" role="group" aria-label={isDe ? "Nach Anfangsbuchstaben filtern" : isFr ? "Filtrer par lettre initiale" : isEs ? "Filtrar por letra inicial" : isEn ? "Filter by first letter" : "Filtrar pela letra inicial"}>
|
||||
<button type="button" onClick={() => setLetraFiltro(null)} aria-pressed={letraFiltro === null} className="chip-btn">
|
||||
{isEs ? "Todas" : isEn ? "All" : "Todas"}
|
||||
{isDe ? "Alle" : isFr ? "Toutes" : isEs ? "Todas" : isEn ? "All" : "Todas"}
|
||||
</button>
|
||||
{alfabeto.map(({ letra, temTermos }) => (
|
||||
<button
|
||||
@@ -224,13 +254,44 @@ export default function GlossarioPage() {
|
||||
<section className="shell section pt-8 sm:pt-10" aria-labelledby="resultado-titulo">
|
||||
<div className="flex flex-wrap items-center justify-between gap-3">
|
||||
<h2 id="resultado-titulo" className="text-base font-semibold text-ink" role="status" aria-live="polite">
|
||||
{total} {total === 1 ? (isEs ? "término" : isEn ? "term" : "termo") : (isEs ? "términos" : isEn ? "terms" : "termos")}
|
||||
{temFiltroAtivo && <span className="font-normal text-muted">{isEs ? " con los filtros actuales" : isEn ? " with current filters" : " com os filtros atuais"}</span>}
|
||||
{total}{" "}
|
||||
{total === 1
|
||||
? isDe
|
||||
? "Begriff"
|
||||
: isFr
|
||||
? "terme"
|
||||
: isEs
|
||||
? "término"
|
||||
: isEn
|
||||
? "term"
|
||||
: "termo"
|
||||
: isDe
|
||||
? "Begriffe"
|
||||
: isFr
|
||||
? "termes"
|
||||
: isEs
|
||||
? "términos"
|
||||
: isEn
|
||||
? "terms"
|
||||
: "termos"}
|
||||
{temFiltroAtivo && (
|
||||
<span className="font-normal text-muted">
|
||||
{isDe
|
||||
? " mit den aktuellen Filtern"
|
||||
: isFr
|
||||
? " avec les filtres actuels"
|
||||
: isEs
|
||||
? " con los filtros actuales"
|
||||
: isEn
|
||||
? " with current filters"
|
||||
: " com os filtros atuais"}
|
||||
</span>
|
||||
)}
|
||||
</h2>
|
||||
{temFiltroAtivo && (
|
||||
<button type="button" onClick={limparTodosFiltros} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent hover:text-accent-strong">
|
||||
<RotateCcw className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Restablecer filtros" : isEn ? "Reset filters" : "Redefinir filtros"}
|
||||
{isDe ? "Filter zurücksetzen" : isFr ? "Réinitialiser les filtres" : isEs ? "Restablecer filtros" : isEn ? "Reset filters" : "Redefinir filtros"}
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
@@ -239,10 +300,14 @@ export default function GlossarioPage() {
|
||||
<div className="card mt-6 px-6 py-14 text-center">
|
||||
<HelpCircle className="mx-auto h-10 w-10 text-muted" aria-hidden="true" />
|
||||
<h3 className="mt-4 font-display text-xl font-semibold text-ink">
|
||||
{isEs ? "No se encontraron términos" : isEn ? "No terms found" : "Nenhum termo encontrado"}
|
||||
{isDe ? "Keine Begriffe gefunden" : isFr ? "Aucun terme trouvé" : isEs ? "No se encontraron términos" : isEn ? "No terms found" : "Nenhum termo encontrado"}
|
||||
</h3>
|
||||
<p className="mx-auto mt-2 max-w-md text-sm text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Nichts entspricht Ihrer aktuellen Suche und den Filtern. Versuchen Sie eine kürzere Abkürzung oder wählen Sie alle Kategorien."
|
||||
: isFr
|
||||
? "Rien ne correspond à votre recherche et à vos filtres actuels. Essayez avec un sigle plus court ou revenez à toutes les catégories."
|
||||
: isEs
|
||||
? "Nada coincide con la búsqueda y los filtros actuales. Pruebe con una sigla más corta o vuelva a todas las categorías."
|
||||
: isEn
|
||||
? "Nothing matches your current search and filters. Try a shorter acronym or reset to all categories."
|
||||
@@ -250,7 +315,7 @@ export default function GlossarioPage() {
|
||||
</p>
|
||||
<button type="button" onClick={limparTodosFiltros} className="btn btn-primary mt-6">
|
||||
<RotateCcw className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Limpiar filtros" : isEn ? "Clear filters" : "Limpar filtros"}
|
||||
{isDe ? "Filter zurücksetzen" : isFr ? "Réinitialiser les filtres" : isEs ? "Limpiar filtros" : isEn ? "Clear filters" : "Limpar filtros"}
|
||||
</button>
|
||||
</div>
|
||||
) : (
|
||||
@@ -267,7 +332,17 @@ export default function GlossarioPage() {
|
||||
<button
|
||||
type="button"
|
||||
onClick={() => copiarLinkTermo(item.slug)}
|
||||
aria-label={isEs ? `Copiar enlace para ${item.termo}` : isEn ? `Copy link for ${item.termo}` : `Copiar link para ${item.termo}`}
|
||||
aria-label={
|
||||
isDe
|
||||
? `Link für ${item.termo} kopieren`
|
||||
: isFr
|
||||
? `Copier le lien pour ${item.termo}`
|
||||
: isEs
|
||||
? `Copiar enlace para ${item.termo}`
|
||||
: isEn
|
||||
? `Copy link for ${item.termo}`
|
||||
: `Copiar link para ${item.termo}`
|
||||
}
|
||||
className="btn-icon inline-flex h-11 w-11 items-center justify-center rounded-full text-muted transition-colors hover:bg-surface-2 hover:text-accent"
|
||||
>
|
||||
{copiadoSlug === item.slug ? <Check className="h-4 w-4 text-ok" aria-hidden="true" /> : <Link2 className="h-4 w-4" aria-hidden="true" />}
|
||||
@@ -282,7 +357,7 @@ export default function GlossarioPage() {
|
||||
<div className="callout mt-5">
|
||||
<p className="flex items-center gap-1.5 text-sm font-semibold text-ink">
|
||||
<Lightbulb className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEs ? "En la práctica" : isEn ? "In practice" : "Na prática"}
|
||||
{isDe ? "In der Praxis" : isFr ? "En pratique" : isEs ? "En la práctica" : isEn ? "In practice" : "Na prática"}
|
||||
</p>
|
||||
<p className="mt-1">
|
||||
<TextoComLinks texto={item.exemplo} currentLocale={currentLocale} />
|
||||
@@ -298,10 +373,14 @@ export default function GlossarioPage() {
|
||||
<section className="shell pb-20 md:pb-28">
|
||||
<div className="panel p-8 text-center sm:p-12">
|
||||
<h2 className="section-title mx-auto max-w-2xl">
|
||||
{isEs ? "Del concepto al chip adecuado." : isEn ? "From concept to the right chip." : "Do conceito ao chip certo."}
|
||||
{isDe ? "Vom Konzept zum richtigen Chip." : isFr ? "Du concept à la bonne puce." : isEs ? "Del concepto al chip adecuado." : isEn ? "From concept to the right chip." : "Do conceito ao chip certo."}
|
||||
</h2>
|
||||
<p className="lede mx-auto mt-4 max-w-2xl">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Mit den Begriffen zur Hand vergleichen Sie die Serien Seite an Seite oder nutzen Sie die Auswahlhilfe, um das Modell für Ihr Projekt zu finden."
|
||||
: isFr
|
||||
? "Avec les termes sous la main, comparez les séries côte à côte ou répondez au sélecteur pour trouver le modèle adapté à votre projet."
|
||||
: isEs
|
||||
? "Con los términos a mano, compare las series lado a lado o responda al selector para encontrar el modelo que se adapta a su proyecto."
|
||||
: isEn
|
||||
? "With the terms in hand, compare series side by side or answer the selector to find the model that fits your project."
|
||||
@@ -310,10 +389,10 @@ export default function GlossarioPage() {
|
||||
<div className="mt-8 flex flex-col items-center justify-center gap-3 sm:flex-row">
|
||||
<Link href={getLocalizedHref("/seletor", currentLocale)} className="btn btn-primary w-full sm:w-auto">
|
||||
<Sliders className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Elegir mi chip" : isEn ? "Choose my chip" : "Escolher meu chip"}
|
||||
{isDe ? "Meinen Chip wählen" : isFr ? "Choisir ma puce" : isEs ? "Elegir mi chip" : isEn ? "Choose my chip" : "Escolher meu chip"}
|
||||
</Link>
|
||||
<Link href={getLocalizedHref("/series", currentLocale)} className="btn btn-ghost w-full sm:w-auto">
|
||||
{isEs ? "Explorar las series" : isEn ? "Explore series" : "Explorar as séries"}
|
||||
{isDe ? "Serien erkunden" : isFr ? "Explorer les séries" : isEs ? "Explorar las series" : isEn ? "Explore series" : "Explorar as séries"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
+33
-1
@@ -46,6 +46,8 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
|
||||
const ogLocaleMap = {
|
||||
pt: "pt_BR",
|
||||
@@ -62,12 +64,20 @@ export async function generateMetadata({ params }) {
|
||||
? "ESPDocs · ESP32 Open Documentation"
|
||||
: isEs
|
||||
? "ESPDocs · Documentación abierta de ESP32"
|
||||
: isFr
|
||||
? "ESPDocs · Documentation ouverte ESP32"
|
||||
: isDe
|
||||
? "ESPDocs · Offene ESP32-Dokumentation"
|
||||
: "ESPDocs · Documentação do ESP32 em português";
|
||||
|
||||
const description = isEn
|
||||
? "Specifications, pinouts, comparison and selection of 12 ESP32 microcontroller series. Datasheets, peripherals, hardware security and connection diagrams."
|
||||
: isEs
|
||||
? "Especificaciones, patillaje, comparación y selección de las 12 series de microcontroladores ESP32. Hojas de datos, periféricos, seguridad en hardware y diagramas de conexión."
|
||||
: isFr
|
||||
? "Spécifications, brochages, comparaison et sélection des 12 séries de microcontrôleurs ESP32. Fiches techniques, périphériques, sécurité matérielle et schémas de connexion."
|
||||
: isDe
|
||||
? "Spezifikationen, Pinbelegungen, Vergleich und Auswahl der 12 ESP32-Mikrocontrollerserien. Datenblätter, Peripheriegeräte, Hardwaresicherheit und Anschlussdiagramme."
|
||||
: "Especificações, pinagem, comparação e seleção das 12 séries de microcontroladores ESP32, em português brasileiro. Datasheets, periféricos, segurança em hardware e diagramas de conexão.";
|
||||
|
||||
const keywords = isEn
|
||||
@@ -84,6 +94,20 @@ export async function generateMetadata({ params }) {
|
||||
"comparar ESP32", "cuál ESP32 elegir", "datasheet ESP32", "hoja de datos ESP32",
|
||||
"microcontrolador", "Espressif", "ESP-IDF", "IoT", "sistemas embebidos",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"ESP32", "ESP32 en français", "documentation ESP32", "brochage ESP32", "pinout ESP32",
|
||||
"ESP32-S3", "ESP32-C3", "ESP32-C6", "ESP32-P4", "ESP32-H2",
|
||||
"comparer ESP32", "quel ESP32 choisir", "datasheet ESP32", "fiche technique ESP32",
|
||||
"microcontrôleur", "Espressif", "ESP-IDF", "IoT", "systèmes embarqués",
|
||||
]
|
||||
: isDe
|
||||
? [
|
||||
"ESP32", "ESP32 auf Deutsch", "ESP32 Dokumentation", "ESP32 Pinbelegung", "ESP32 Pinout",
|
||||
"ESP32-S3", "ESP32-C3", "ESP32-C6", "ESP32-P4", "ESP32-H2",
|
||||
"ESP32 vergleichen", "welchen ESP32 wählen", "ESP32 Datenblatt",
|
||||
"Mikrocontroller", "Espressif", "ESP-IDF", "IoT", "eingebettete Systeme",
|
||||
]
|
||||
: [
|
||||
"ESP32", "ESP32 português", "documentação ESP32", "pinout ESP32",
|
||||
"ESP32-S3", "ESP32-C3", "ESP32-C6", "ESP32-P4", "ESP32-H2",
|
||||
@@ -126,6 +150,10 @@ export async function generateMetadata({ params }) {
|
||||
? "Specifications, pinouts, comparison and selection of 12 ESP32 microcontroller series."
|
||||
: isEs
|
||||
? "Especificaciones, patillaje, comparación y selección de las 12 series de microcontroladores ESP32."
|
||||
: isFr
|
||||
? "Spécifications, brochages, comparaison et sélection des 12 séries de microcontrôleurs ESP32."
|
||||
: isDe
|
||||
? "Spezifikationen, Pinbelegungen, Vergleich und Auswahl der 12 ESP32-Mikrocontrollerserien."
|
||||
: "Especificações, pinagem, comparação e seleção das 12 séries de microcontroladores ESP32, em português brasileiro.",
|
||||
},
|
||||
twitter: {
|
||||
@@ -135,6 +163,10 @@ export async function generateMetadata({ params }) {
|
||||
? "Specifications, pinouts, comparison and selection of 12 ESP32 series."
|
||||
: isEs
|
||||
? "Especificaciones, patillaje, comparación y selección de las 12 series de ESP32."
|
||||
: isFr
|
||||
? "Spécifications, brochages, comparaison et sélection des 12 séries ESP32."
|
||||
: isDe
|
||||
? "Spezifikationen, Pinbelegungen, Vergleich und Auswahl der 12 ESP32-Serien."
|
||||
: "Especificações, pinagem, comparação e seleção das 12 séries de ESP32, em português.",
|
||||
},
|
||||
robots: {
|
||||
@@ -194,7 +226,7 @@ export default async function RootLayout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{ __html: JSON.stringify(jsonLd.siteESociedade(locale)) }}
|
||||
/>
|
||||
</head>
|
||||
<body className="font-sans antialiased bg-canvas text-ink overflow-x-clip" suppressHydrationWarning>
|
||||
<body className="font-sans antialiased bg-canvas text-ink overflow-x-clip hyphens-auto" suppressHydrationWarning>
|
||||
<a
|
||||
href="#conteudo"
|
||||
className="sr-only focus:not-sr-only focus:fixed focus:left-4 focus:top-4 focus:z-[200] focus:rounded-full focus:bg-ink focus:px-5 focus:py-3 focus:text-sm focus:font-semibold focus:text-canvas"
|
||||
|
||||
@@ -31,6 +31,20 @@ const CAMINHOS_ES = [
|
||||
{ href: "/glossario", icon: BookOpen, titulo: "Glosario", texto: "Términos de hardware explicados con claridad." },
|
||||
];
|
||||
|
||||
const CAMINHOS_FR = [
|
||||
{ href: "/series", icon: Compass, titulo: "Séries ESP32", texto: "Les 12 familles, avec brochage et spécifications." },
|
||||
{ href: "/seletor", icon: SlidersHorizontal, titulo: "Sélecteur de puce", texto: "Répondez à huit questions et obtenez les modèles recommandés." },
|
||||
{ href: "/comparacao", icon: Scale, titulo: "Comparateur", texto: "Jusqu'à quatre séries côte à côte." },
|
||||
{ href: "/glossario", icon: BookOpen, titulo: "Glossaire", texto: "Les termes matériels expliqués clairement." },
|
||||
];
|
||||
|
||||
const CAMINHOS_DE = [
|
||||
{ href: "/series", icon: Compass, titulo: "ESP32-Serien", texto: "Die 12 Familien mit Pinbelegung und Spezifikationen." },
|
||||
{ href: "/seletor", icon: SlidersHorizontal, titulo: "Chip-Auswahl", texto: "Beantworten Sie acht Fragen und erhalten Sie passende Empfehlungen." },
|
||||
{ href: "/comparacao", icon: Scale, titulo: "Vergleich", texto: "Bis zu vier Serien im direkten Vergleich." },
|
||||
{ href: "/glossario", icon: BookOpen, titulo: "Glossar", texto: "Hardware-Begriffe verständlich erklärt." },
|
||||
];
|
||||
|
||||
export default async function NotFound() {
|
||||
let locale = "pt";
|
||||
try {
|
||||
@@ -40,7 +54,9 @@ export default async function NotFound() {
|
||||
}
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const caminhos = isEn ? CAMINHOS_EN : isEs ? CAMINHOS_ES : CAMINHOS_PT;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const caminhos = isEn ? CAMINHOS_EN : isEs ? CAMINHOS_ES : isFr ? CAMINHOS_FR : isDe ? CAMINHOS_DE : CAMINHOS_PT;
|
||||
|
||||
return (
|
||||
<div className="site-canvas min-h-screen">
|
||||
@@ -48,18 +64,22 @@ export default async function NotFound() {
|
||||
|
||||
<main id="conteudo" className="shell section">
|
||||
<div className="mx-auto max-w-2xl text-center">
|
||||
<p className="eyebrow justify-center">{isEn ? "Error 404" : "Error 404"}</p>
|
||||
<h1 className="page-title mt-4">{isEn ? "This page does not exist." : isEs ? "Esta página no existe." : "Essa página não existe."}</h1>
|
||||
<p className="eyebrow justify-center">{isEn ? "Error 404" : isFr ? "Erreur 404" : isDe ? "Fehler 404" : "Error 404"}</p>
|
||||
<h1 className="page-title mt-4">{isEn ? "This page does not exist." : isEs ? "Esta página no existe." : isFr ? "Cette page n'existe pas." : isDe ? "Diese Seite existiert nicht." : "Essa página não existe."}</h1>
|
||||
<p className="lede mx-auto mt-5 max-w-xl">
|
||||
{isEn
|
||||
? "The address may have changed or was mistyped. Choose one of these paths to continue."
|
||||
: isEs
|
||||
? "La dirección puede haber cambiado o estar mal escrita. Elija uno de estos caminos para continuar."
|
||||
: isFr
|
||||
? "L'adresse a peut-être changé ou a été mal saisie. Choisissez l'un de ces chemins pour continuer."
|
||||
: isDe
|
||||
? "Die Adresse wurde möglicherweise geändert oder falsch eingegeben. Wählen Sie einen dieser Wege, um fortzufahren."
|
||||
: "O endereço pode ter mudado ou estar digitado errado. Escolha um destes caminhos para continuar."}
|
||||
</p>
|
||||
<div className="mt-8 flex justify-center">
|
||||
<Link href={isEn ? "/en" : isEs ? "/es" : "/"} className="btn btn-primary">
|
||||
{isEn ? "Back to home" : isEs ? "Volver al inicio" : "Voltar ao início"}
|
||||
<Link href={isEn ? "/en" : isEs ? "/es" : isFr ? "/fr" : isDe ? "/de" : "/"} className="btn btn-primary">
|
||||
{isEn ? "Back to home" : isEs ? "Volver al inicio" : isFr ? "Retour à l'accueil" : isDe ? "Zur Startseite" : "Voltar ao início"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
+204
-22
@@ -8,6 +8,10 @@ import seriesDataEn from "@/data/en/series.json";
|
||||
import frameworksDataEn from "@/data/en/frameworks.json";
|
||||
import seriesDataEs from "@/data/es/series.json";
|
||||
import frameworksDataEs from "@/data/es/frameworks.json";
|
||||
import seriesDataFr from "@/data/fr/series.json";
|
||||
import frameworksDataFr from "@/data/fr/frameworks.json";
|
||||
import seriesDataDe from "@/data/de/series.json";
|
||||
import frameworksDataDe from "@/data/de/frameworks.json";
|
||||
import { SITE } from "@/lib/seo";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import {
|
||||
@@ -159,6 +163,96 @@ const TOOLS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const TOOLS_FR = [
|
||||
{
|
||||
href: "/seletor",
|
||||
title: "Sélecteur intelligent",
|
||||
desc: "Répondez à huit questions sur votre projet et découvrez les puces recommandées, avec justification technique.",
|
||||
icon: SlidersHorizontal,
|
||||
action: "Trouver ma puce",
|
||||
},
|
||||
{
|
||||
href: "/comparacao",
|
||||
title: "Comparateur de séries",
|
||||
desc: "Comparez jusqu'à quatre modèles côte à côte : cœurs, radio, mémoire, périphériques et sécurité.",
|
||||
icon: Scale,
|
||||
action: "Comparer maintenant",
|
||||
},
|
||||
{
|
||||
href: "/diagnostico",
|
||||
title: "Diagnostic de pannes",
|
||||
desc: "Causes et solutions pour brownout, bootloop, Guru Meditation, watchdog et erreurs de flash.",
|
||||
icon: AlertTriangle,
|
||||
action: "Ouvrir le diagnostic",
|
||||
},
|
||||
{
|
||||
href: "/componentes",
|
||||
title: "Component Registry",
|
||||
desc: "Pilotes, bibliothèques et BSP du registre officiel Espressif, avec manifeste prêt pour votre projet.",
|
||||
icon: Box,
|
||||
action: "Explorer les composants",
|
||||
},
|
||||
{
|
||||
href: "/frameworks",
|
||||
title: "Frameworks et SDKs",
|
||||
desc: "ESP-IDF, Arduino, Rust, Matter, MicroPython et les outils gravitant autour de la puce.",
|
||||
icon: Terminal,
|
||||
action: "Voir les frameworks",
|
||||
},
|
||||
{
|
||||
href: "/catalogo",
|
||||
title: "Catalogue de cartes",
|
||||
desc: "DevKits et modules réels, avec interface USB, capteurs intégrés et lien vers la boutique officielle.",
|
||||
icon: Cpu,
|
||||
action: "Voir les cartes",
|
||||
},
|
||||
];
|
||||
|
||||
const TOOLS_DE = [
|
||||
{
|
||||
href: "/seletor",
|
||||
title: "Intelligente Auswahl",
|
||||
desc: "Beantworten Sie acht Fragen zu Ihrem Projekt und erhalten Sie passende Chip-Empfehlungen mit technischer Begründung.",
|
||||
icon: SlidersHorizontal,
|
||||
action: "Meinen Chip finden",
|
||||
},
|
||||
{
|
||||
href: "/comparacao",
|
||||
title: "Serienvergleich",
|
||||
desc: "Vergleichen Sie bis zu vier Modelle nebeneinander: Kerne, Funk, Speicher, Peripherie und Sicherheit.",
|
||||
icon: Scale,
|
||||
action: "Jetzt vergleichen",
|
||||
},
|
||||
{
|
||||
href: "/diagnostico",
|
||||
title: "Fehlerdiagnose",
|
||||
desc: "Ursachen und Lösungen für Brownout, Bootloops, Guru Meditation, Watchdog und Flash-Fehler.",
|
||||
icon: AlertTriangle,
|
||||
action: "Diagnose öffnen",
|
||||
},
|
||||
{
|
||||
href: "/componentes",
|
||||
title: "Component Registry",
|
||||
desc: "Treiber, Bibliotheken und BSPs aus der offiziellen Espressif-Registry, mit fertigem Manifest für Ihr Projekt.",
|
||||
icon: Box,
|
||||
action: "Komponenten erkunden",
|
||||
},
|
||||
{
|
||||
href: "/frameworks",
|
||||
title: "Frameworks & SDKs",
|
||||
desc: "ESP-IDF, Arduino, Rust, Matter, MicroPython und die Werkzeuge rund um den Chip.",
|
||||
icon: Terminal,
|
||||
action: "Frameworks ansehen",
|
||||
},
|
||||
{
|
||||
href: "/catalogo",
|
||||
title: "Board-Katalog",
|
||||
desc: "Reale DevKits und Module, mit USB-Schnittstelle, integrierten Sensoren und Link zum offiziellen Shop.",
|
||||
icon: Cpu,
|
||||
action: "Boards ansehen",
|
||||
},
|
||||
];
|
||||
|
||||
const ERRORS_PT = [
|
||||
{
|
||||
code: "Brownout detector was triggered",
|
||||
@@ -194,7 +288,7 @@ const ERRORS_EN = [
|
||||
fix: "Inspect backtrace with addr2line and properly size FreeRTOS task stacks.",
|
||||
},
|
||||
{
|
||||
code: "ADC2 indisponível com Wi-Fi",
|
||||
code: "ADC2 unavailable with Wi-Fi",
|
||||
cause: "Internal radio controller reserves ADC2 while active.",
|
||||
fix: "Use ADC1 pins for analog sensors operating alongside Wi-Fi.",
|
||||
},
|
||||
@@ -228,17 +322,65 @@ const ERRORS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const ERRORS_FR = [
|
||||
{
|
||||
code: "Brownout detector was triggered",
|
||||
cause: "Baisse de tension lors du démarrage de la radio.",
|
||||
fix: "Condensateur de 10 à 100 µF au plus près de la puce et alimentation 5 V avec courant suffisant.",
|
||||
},
|
||||
{
|
||||
code: "Guru Meditation Error",
|
||||
cause: "Pointeur invalide, dépassement de pile ou mauvaise utilisation des interruptions.",
|
||||
fix: "Analysez le backtrace avec addr2line et dimensionnez la pile de la tâche sous FreeRTOS.",
|
||||
},
|
||||
{
|
||||
code: "ADC2 indisponible avec le Wi-Fi",
|
||||
cause: "Le contrôleur radio réserve l'ADC2 tant qu'il est actif.",
|
||||
fix: "Utilisez les broches de l'ADC1 pour les capteurs analogiques fonctionnant conjointement avec le Wi-Fi.",
|
||||
},
|
||||
{
|
||||
code: "Flash Read err / bootloader",
|
||||
cause: "Tension ou mode de flash incorrect, ou broche de strapping forcée au démarrage.",
|
||||
fix: "Vérifiez la ligne 3,3 V, les pull-ups de démarrage et la configuration de flash dans esptool.",
|
||||
},
|
||||
];
|
||||
|
||||
const ERRORS_DE = [
|
||||
{
|
||||
code: "Brownout detector was triggered",
|
||||
cause: "Spannungseinbruch beim Starten der Funkeinheit.",
|
||||
fix: "Kondensator mit 10–100 µF nah am Chip und 5-V-Netzteil mit ausreichender Stromstärke.",
|
||||
},
|
||||
{
|
||||
code: "Guru Meditation Error",
|
||||
cause: "Ungültiger Zeiger, Stack-Überlauf oder fehlerhafte Interrupt-Nutzung.",
|
||||
fix: "Backtrace mit addr2line analysieren und Stack-Größe der FreeRTOS-Task anpassen.",
|
||||
},
|
||||
{
|
||||
code: "ADC2 nicht verfügbar bei aktivem Wi-Fi",
|
||||
cause: "Der Funk-Controller reserviert ADC2, solange er aktiv ist.",
|
||||
fix: "Nutzen Sie ADC1-Pins für analoge Sensoren, die gleichzeitig mit Wi-Fi betrieben werden.",
|
||||
},
|
||||
{
|
||||
code: "Flash Read err / bootloader",
|
||||
cause: "Falsche Flash-Spannung/-Modus oder beim Booten falsch beschalteter Strapping-Pin.",
|
||||
fix: "3,3-V-Schiene, Boot-Pull-ups und Flash-Konfiguration in esptool überprüfen.",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function Home({ params }) {
|
||||
const { locale } = await params;
|
||||
const isPt = locale === "pt";
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const getLinkHref = (href) => getLocalizedHref(`/${locale}${href}`, locale);
|
||||
|
||||
const seriesData = isPt ? seriesDataPt : isEs ? seriesDataEs : seriesDataEn;
|
||||
const frameworksData = isPt ? frameworksDataPt : isEs ? frameworksDataEs : frameworksDataEn;
|
||||
const tools = isPt ? TOOLS_PT : isEs ? TOOLS_ES : TOOLS_EN;
|
||||
const errors = isPt ? ERRORS_PT : isEs ? ERRORS_ES : ERRORS_EN;
|
||||
const seriesData = isPt ? seriesDataPt : isEs ? seriesDataEs : isFr ? seriesDataFr : isDe ? seriesDataDe : seriesDataEn;
|
||||
const frameworksData = isPt ? frameworksDataPt : isEs ? frameworksDataEs : isFr ? frameworksDataFr : isDe ? frameworksDataDe : frameworksDataEn;
|
||||
const tools = isPt ? TOOLS_PT : isEs ? TOOLS_ES : isFr ? TOOLS_FR : isDe ? TOOLS_DE : TOOLS_EN;
|
||||
const errors = isPt ? ERRORS_PT : isEs ? ERRORS_ES : isFr ? ERRORS_FR : isDe ? ERRORS_DE : ERRORS_EN;
|
||||
|
||||
const seriesCount = Object.keys(seriesData).length;
|
||||
const frameworkCount = Object.keys(frameworksData).length;
|
||||
@@ -253,7 +395,7 @@ export default async function Home({ params }) {
|
||||
<div className="mx-auto max-w-4xl text-center">
|
||||
<span className="chip chip-accent">
|
||||
<Cpu className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isPt ? "Documentação aberta do ESP32" : isEs ? "Documentación abierta de ESP32" : "Open ESP32 documentation"}
|
||||
{isPt ? "Documentação aberta do ESP32" : isEs ? "Documentación abierta de ESP32" : isFr ? "Documentation ouverte de l'ESP32" : isDe ? "Offene ESP32-Dokumentation" : "Open ESP32 documentation"}
|
||||
</span>
|
||||
<h1 className="display mt-6 text-[clamp(2.9rem,7.4vw,5.4rem)]">
|
||||
{isPt ? (
|
||||
@@ -266,6 +408,16 @@ export default async function Home({ params }) {
|
||||
El ESP32,
|
||||
<br className="sm:hidden" /> sin ruido.
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
L'ESP32,
|
||||
<br className="sm:hidden" /> sans bruit.
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
Der ESP32,
|
||||
<br className="sm:hidden" /> ohne Umwege.
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
The ESP32,
|
||||
@@ -278,19 +430,27 @@ export default async function Home({ params }) {
|
||||
? "Especificações, pinagem, comparações e diagnóstico em uma leitura só. Menos tradução de datasheet, mais tempo com o protótipo na bancada."
|
||||
: isEs
|
||||
? "Especificaciones, patillaje, comparaciones y diagnóstico en una sola lectura. Menos traducción de hojas de datos, más tiempo con el prototipo en el banco de trabajo."
|
||||
: isFr
|
||||
? "Spécifications, brochage, comparaisons et diagnostics en une seule lecture. Moins de traduction de fiches techniques, plus de temps à l'établi."
|
||||
: isDe
|
||||
? "Spezifikationen, Pinbelegung, Vergleiche und Diagnose auf einen Blick. Weniger Datenblatt-Übersetzung, mehr Zeit am Prüfplatz."
|
||||
: "Specifications, pinouts, comparisons and diagnostics in a single read. Less datasheet translation, more workbench time."}
|
||||
</p>
|
||||
|
||||
<div className="mt-8 flex flex-col items-center justify-center gap-3 sm:flex-row">
|
||||
<Link href={getLinkHref("/seletor")} className="btn btn-primary w-full sm:w-auto">
|
||||
<SlidersHorizontal className="h-4 w-4" aria-hidden="true" />
|
||||
{isPt ? "Escolher meu chip" : isEs ? "Elegir mi chip" : "Choose my chip"}
|
||||
{isPt ? "Escolher meu chip" : isEs ? "Elegir mi chip" : isFr ? "Choisir ma puce" : isDe ? "Meinen Chip wählen" : "Choose my chip"}
|
||||
</Link>
|
||||
<Link href={getLinkHref("/series")} className="btn btn-ghost w-full sm:w-auto">
|
||||
{isPt ? (
|
||||
<>Explorar as {seriesCount} séries</>
|
||||
) : isEs ? (
|
||||
<>Explorar las {seriesCount} series</>
|
||||
) : isFr ? (
|
||||
<>Explorer les {seriesCount} séries</>
|
||||
) : isDe ? (
|
||||
<>Die {seriesCount} Serien erkunden</>
|
||||
) : (
|
||||
<>Explore the {seriesCount} series</>
|
||||
)}
|
||||
@@ -299,7 +459,7 @@ export default async function Home({ params }) {
|
||||
</div>
|
||||
|
||||
<p className="mt-7 flex flex-wrap items-center justify-center gap-x-5 gap-y-2 text-sm text-muted">
|
||||
<span><strong className="font-semibold text-ink">{seriesCount}</strong> {isPt ? "séries" : isEs ? "series" : "series"}</span>
|
||||
<span><strong className="font-semibold text-ink">{seriesCount}</strong> {isPt ? "séries" : isEs ? "series" : isFr ? "séries" : isDe ? "Serien" : "series"}</span>
|
||||
<span aria-hidden="true" className="text-line-strong">·</span>
|
||||
<span><strong className="font-semibold text-ink">{frameworkCount}</strong> frameworks</span>
|
||||
{isPt ? (
|
||||
@@ -314,6 +474,16 @@ export default async function Home({ params }) {
|
||||
<span aria-hidden="true" className="text-line-strong">·</span>
|
||||
<span>100% en español</span>
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
<span aria-hidden="true" className="text-line-strong">·</span>
|
||||
<span>100 % en français</span>
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
<span aria-hidden="true" className="text-line-strong">·</span>
|
||||
<span>100 % auf Deutsch</span>
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<span aria-hidden="true" className="text-line-strong">·</span>
|
||||
@@ -326,13 +496,13 @@ export default async function Home({ params }) {
|
||||
<div className="panel mt-12 overflow-hidden sm:mt-16">
|
||||
<div className="flex flex-wrap items-center justify-between gap-3 px-5 py-4 sm:px-7">
|
||||
<div>
|
||||
<h2 className="text-sm font-semibold text-ink">{isPt ? "Séries em destaque" : isEs ? "Series destacadas" : "Featured series"}</h2>
|
||||
<h2 className="text-sm font-semibold text-ink">{isPt ? "Séries em destaque" : isEs ? "Series destacadas" : isFr ? "Séries en vedette" : isDe ? "Vorgestellte Serien" : "Featured series"}</h2>
|
||||
<p className="mt-0.5 text-xs text-muted">
|
||||
{isPt ? "O essencial de cada família, antes de abrir o datasheet." : isEs ? "Lo esencial de cada familia, antes de abrir la hoja de datos." : "The essentials of each family before opening the datasheet."}
|
||||
{isPt ? "O essencial de cada família, antes de abrir o datasheet." : isEs ? "Lo esencial de cada familia, antes de abrir la hoja de datos." : isFr ? "L'essentiel de chaque famille, avant d'ouvrir la fiche technique." : isDe ? "Das Wesentliche jeder Familie, bevor Sie das Datenblatt öffnen." : "The essentials of each family before opening the datasheet."}
|
||||
</p>
|
||||
</div>
|
||||
<Link href={getLinkHref("/series")} className="inline-flex min-h-11 items-center gap-1.5 text-sm font-medium text-accent transition-colors hover:text-accent-strong">
|
||||
{isPt ? "Índice completo" : isEs ? "Índice completo" : "Full index"}
|
||||
{isPt ? "Índice completo" : isEs ? "Índice completo" : isFr ? "Index complet" : isDe ? "Vollständiger Index" : "Full index"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
@@ -357,7 +527,7 @@ export default async function Home({ params }) {
|
||||
<div className="mt-5 flex items-center justify-between gap-3 border-t border-line pt-3.5">
|
||||
<span className="truncate font-mono text-[0.6875rem] text-ink-soft">{serie.frequencia}</span>
|
||||
<span className="inline-flex shrink-0 items-center gap-1 text-xs font-medium text-accent">
|
||||
{isPt ? "Ficha" : isEs ? "Ficha" : "Spec sheet"}
|
||||
{isPt ? "Ficha" : isEs ? "Ficha" : isFr ? "Fiche" : isDe ? "Datenblatt" : "Spec sheet"}
|
||||
<ArrowUpRight className="h-3.5 w-3.5 transition-transform duration-300 group-hover:-translate-y-0.5 group-hover:translate-x-0.5" aria-hidden="true" />
|
||||
</span>
|
||||
</div>
|
||||
@@ -438,15 +608,19 @@ export default async function Home({ params }) {
|
||||
|
||||
<section className="shell section" aria-labelledby="ferramentas-titulo">
|
||||
<div className="mx-auto max-w-2xl text-center">
|
||||
<p className="eyebrow">{isPt ? "Ferramentas" : isEs ? "Herramientas" : "Tools"}</p>
|
||||
<p className="eyebrow">{isPt ? "Ferramentas" : isEs ? "Herramientas" : isFr ? "Outils" : isDe ? "Werkzeuge" : "Tools"}</p>
|
||||
<h2 id="ferramentas-titulo" className="display mt-4 text-[clamp(2rem,4.8vw,3.4rem)]">
|
||||
{isPt ? "Comece pelo problema." : isEs ? "Empiece por el problema." : "Start with the problem."}
|
||||
{isPt ? "Comece pelo problema." : isEs ? "Empiece por el problema." : isFr ? "Commencez par le problème." : isDe ? "Beginnen Sie beim Problem." : "Start with the problem."}
|
||||
</h2>
|
||||
<p className="lede mt-4">
|
||||
{isPt
|
||||
? "Cada ferramenta resolve uma etapa concreta do projeto, sem cadastro e sem rodeio."
|
||||
: isEs
|
||||
? "Cada herramienta resuelve una fase concreta del proyecto, sin registros ni rodeos."
|
||||
: isFr
|
||||
? "Chaque outil répond à une étape concrète du projet, sans inscription ni détour."
|
||||
: isDe
|
||||
? "Jedes Werkzeug löst einen konkreten Projektschritt – ohne Registrierung und ohne Umwege."
|
||||
: "Each tool addresses a concrete development phase, with no sign-ups and zero fluff."}
|
||||
</p>
|
||||
</div>
|
||||
@@ -474,20 +648,24 @@ export default async function Home({ params }) {
|
||||
<section className="shell section pt-0" aria-labelledby="diagnostico-titulo">
|
||||
<div className="grid items-start gap-10 lg:grid-cols-[0.78fr_1.22fr] lg:gap-16">
|
||||
<div className="lg:sticky lg:top-28">
|
||||
<p className="eyebrow">{isPt ? "Diagnóstico" : isEs ? "Diagnóstico" : "Diagnostics"}</p>
|
||||
<p className="eyebrow">{isPt ? "Diagnóstico" : isEs ? "Diagnóstico" : isFr ? "Diagnostic" : isDe ? "Diagnose" : "Diagnostics"}</p>
|
||||
<h2 id="diagnostico-titulo" className="display mt-4 text-[clamp(2rem,4.8vw,3.4rem)]">
|
||||
{isPt ? "O primeiro boot não precisa virar noite." : isEs ? "El primer arranque no tiene por qué desvelarlo." : "First boot doesn't have to take all night."}
|
||||
{isPt ? "O primeiro boot não precisa virar noite." : isEs ? "El primer arranque no tiene por qué desvelarlo." : isFr ? "Le premier démarrage n'a pas à vous gâcher la nuit." : isDe ? "Der erste Boot muss nicht die Nacht kosten." : "First boot doesn't have to take all night."}
|
||||
</h2>
|
||||
<p className="lede mt-4">
|
||||
{isPt
|
||||
? "Os erros mais comuns têm causa conhecida. O guia parte da mensagem no terminal e chega ao ajuste de hardware ou firmware."
|
||||
: isEs
|
||||
? "Los errores más comunes tienen una causa conocida. Esta guía parte del mensaje en el terminal y llega al ajuste de hardware o firmware."
|
||||
: isFr
|
||||
? "Les erreurs les plus courantes ont une cause connue. Ce guide part du message dans le terminal pour arriver au réglage matériel ou logiciel."
|
||||
: isDe
|
||||
? "Die häufigsten Fehler haben bekannte Ursachen. Dieser Leitfaden geht von der Terminalmeldung aus und führt zur passenden Hardware- oder Firmware-Anpassung."
|
||||
: "Common errors have known causes. This guide starts with the serial terminal log and leads to the hardware or firmware adjustment."}
|
||||
</p>
|
||||
<Link href={getLinkHref("/diagnostico")} className="btn btn-accent mt-7">
|
||||
<AlertTriangle className="h-4 w-4" aria-hidden="true" />
|
||||
{isPt ? "Abrir os 30+ diagnósticos" : isEs ? "Abrir los 30+ diagnósticos" : "Open the 30+ diagnostics"}
|
||||
{isPt ? "Abrir os 30+ diagnósticos" : isEs ? "Abrir los 30+ diagnósticos" : isFr ? "Ouvrir les 30+ diagnostics" : isDe ? "Die 30+ Diagnosen öffnen" : "Open the 30+ diagnostics"}
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
@@ -497,7 +675,7 @@ export default async function Home({ params }) {
|
||||
<Terminal className="h-4 w-4" aria-hidden="true" />
|
||||
boot.log
|
||||
</span>
|
||||
<span className="text-xs text-[#a6afbd]">{isPt ? "4 exemplos de 30+" : isEs ? "4 ejemplos de 30+" : "4 examples of 30+"}</span>
|
||||
<span className="text-xs text-[#a6afbd]">{isPt ? "4 exemplos de 30+" : isEs ? "4 ejemplos de 30+" : isFr ? "4 exemples sur 30+" : isDe ? "4 Beispiele von 30+" : "4 examples of 30+"}</span>
|
||||
</div>
|
||||
<div className="divide-y divide-white/10">
|
||||
{errors.map((item) => (
|
||||
@@ -514,24 +692,28 @@ export default async function Home({ params }) {
|
||||
|
||||
<section className="shell pb-20 pt-4 md:pb-28">
|
||||
<div className="mx-auto max-w-3xl text-center">
|
||||
<p className="eyebrow">{isPt ? "Curadoria independente" : isEs ? "Curaduría independiente" : "Independent curation"}</p>
|
||||
<p className="eyebrow">{isPt ? "Curadoria independente" : isEs ? "Curaduría independiente" : isFr ? "Sélection indépendante" : isDe ? "Unabhängige Kuration" : "Independent curation"}</p>
|
||||
<h2 className="display mt-4 text-[clamp(2rem,4.5vw,3.2rem)]">
|
||||
{isPt ? "Feito para consultar no meio do projeto." : isEs ? "Diseñado para consultar en mitad del proyecto." : "Built for quick lookup mid-project."}
|
||||
{isPt ? "Feito para consultar no meio do projeto." : isEs ? "Diseñado para consultar en mitad del proyecto." : isFr ? "Conçu pour être consulté en plein projet." : isDe ? "Gemacht für das Nachschlagen mitten im Projekt." : "Built for quick lookup mid-project."}
|
||||
</h2>
|
||||
<p className="lede mx-auto mt-4 max-w-2xl">
|
||||
{isPt
|
||||
? "O ESPDocs organiza dados públicos da Espressif e aponta sempre para a fonte oficial. Para decisões críticas, o datasheet e o Technical Reference Manual continuam sendo a palavra final."
|
||||
: isEs
|
||||
? "ESPDocs organiza datos públicos de Espressif y apunta siempre a la fuente oficial. Para decisiones críticas, la hoja de datos y el Technical Reference Manual continúan teniendo la última palabra."
|
||||
: isFr
|
||||
? "ESPDocs organise les données publiques d'Espressif et renvoie systématiquement vers la source officielle. Pour les décisions critiques, la fiche technique et le Technical Reference Manual restent la référence définitive."
|
||||
: isDe
|
||||
? "ESPDocs strukturiert öffentliche Espressif-Daten und verweist stets auf die offizielle Quelle. Für kritische Entscheidungen bleiben das Datenblatt und das Technical Reference Manual maßgeblich."
|
||||
: "ESPDocs organizes public Espressif data and points directly to official sources. For critical engineering decisions, the datasheet and Technical Reference Manual remain the definitive authority."}
|
||||
</p>
|
||||
<div className="mt-8 flex flex-col items-center justify-center gap-3 sm:flex-row">
|
||||
<Link href={getLinkHref("/glossario")} className="btn btn-ghost w-full sm:w-auto">
|
||||
<BookOpen className="h-4 w-4" aria-hidden="true" />
|
||||
{isPt ? "Glossário" : isEs ? "Glosario" : "Glossary"}
|
||||
{isPt ? "Glossário" : isEs ? "Glosario" : isFr ? "Glossaire" : isDe ? "Glossar" : "Glossary"}
|
||||
</Link>
|
||||
<Link href={getLinkHref("/sobre")} className="btn btn-primary w-full sm:w-auto">
|
||||
{isPt ? "Sobre o projeto" : isEs ? "Acerca del proyecto" : "About the project"}
|
||||
{isPt ? "Sobre o projeto" : isEs ? "Acerca del proyecto" : isFr ? "À propos du projet" : isDe ? "Über das Projekt" : "About the project"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
@@ -4,16 +4,34 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEs ? "Qué ESP32 elegir" : isEn ? "Which ESP32 to Choose" : "Qual ESP32 escolher",
|
||||
descricao: isEs
|
||||
titulo: isDe
|
||||
? "Welchen ESP32 wählen"
|
||||
: isFr
|
||||
? "Quel ESP32 choisir"
|
||||
: isEs
|
||||
? "Qué ESP32 elegir"
|
||||
: isEn
|
||||
? "Which ESP32 to Choose"
|
||||
: "Qual ESP32 escolher",
|
||||
descricao: isDe
|
||||
? "Beantworten Sie einfache Fragen zu Konnektivität (Wi-Fi 6, 5 GHz, Matter), Energie, Peripherie und Sicherheit oder nutzen Sie den parametrischen Filter, um den perfekten ESP32 zu finden."
|
||||
: isFr
|
||||
? "Répondez à des questions simples sur la connectivité (Wi-Fi 6, 5 GHz, Matter), l'énergie, les périphériques et la sécurité ou utilisez le filtre paramétrique pour trouver l'ESP32 parfait."
|
||||
: isEs
|
||||
? "Responda a preguntas sencillas sobre conectividad (Wi-Fi 6, 5GHz, Matter), energía, periféricos y seguridad o use el filtro paramétrico para encontrar el ESP32 perfecto."
|
||||
: isEn
|
||||
? "Answer simple questions about connectivity (Wi-Fi 6, 5GHz, Matter), power, peripherals, and security or use the parametric filter to find the perfect ESP32."
|
||||
: "Responda a perguntas simples sobre conectividade (Wi-Fi 6, 5GHz, Matter), energia, periféricos e segurança ou use o filtro paramétrico para encontrar o ESP32 perfeito.",
|
||||
caminho: "/seletor",
|
||||
locale,
|
||||
keywords: isEs
|
||||
keywords: isDe
|
||||
? ["welchen ESP32 wählen", "welchen ESP32 verwenden", "Mikrocontroller auswählen", "ESP32 für mein Projekt", "ESP32 vergleichen"]
|
||||
: isFr
|
||||
? ["quel ESP32 choisir", "quel ESP32 utiliser", "choisir microcontrôleur", "ESP32 pour mon projet", "comparer ESP32"]
|
||||
: isEs
|
||||
? ["qué ESP32 elegir", "cuál ESP32 usar", "elegir microcontrolador", "ESP32 para mi proyecto", "comparar ESP32"]
|
||||
: isEn
|
||||
? ["which ESP32 to choose", "which ESP32 to use", "choose microcontroller", "ESP32 for my project", "compare ESP32"]
|
||||
@@ -78,11 +96,51 @@ const faqsEs = [
|
||||
},
|
||||
];
|
||||
|
||||
const faqsFr = [
|
||||
{
|
||||
pergunta: "Quel ESP32 choisir pour débuter ?",
|
||||
resposta: "Pour débuter dans le monde Maker et l'IoT, l'ESP32 classique (NodeMCU/DevKitC) ou l'ESP32-C3 sont les meilleurs choix grâce au vaste support de bibliothèques, aux exemples prêts à l'emploi dans l'IDE Arduino et à une documentation abondante.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quel ESP32 prend en charge le Wi-Fi 6, le Bluetooth 6 et Thread/Zigbee/Matter ?",
|
||||
resposta: "L'ESP32-C6 et l'ESP32-C5 sont les séries phares pour les réseaux modernes. L'ESP32-C6 offre le Wi-Fi 6 (2,4 GHz) et une radio 802.15.4 (Zigbee 3.0 / Thread / Matter). L'ESP32-C5 est le premier à offrir la prise en charge du Wi-Fi 6 bi-bande fonctionnant simultanément en 2,4 GHz et 5 GHz.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quel est l'ESP32 le plus puissant pour l'Intelligence Artificielle (TinyML) et les écrans ?",
|
||||
resposta: "L'ESP32-P4 (dual-core RISC-V à 400 MHz avec extensions vectorielles IA, interfaces MIPI-CSI/DSI pour caméras/écrans et jusqu'à 64 Mo de PSRAM) et l'ESP32-S3 (dual-core Xtensa à 240 MHz avec accélérateurs vectoriels pour réseaux neuronaux et écrans LCD RGB) sont les plus rapides pour l'IA en périphérie et les interfaces graphiques riches.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quel ESP32 consomme le moins d'énergie pour les projets sur batterie ?",
|
||||
resposta: "Les microcontrôleurs à architecture RISC-V compacte avec coprocesseur ULP, comme l'ESP32-C2, l'ESP32-C3 et l'ESP32-H2 (dédié au 802.15.4 sans radio Wi-Fi), offrent des courants de deep sleep extrêmement faibles (de l'ordre de 5 µA à 10 µA).",
|
||||
},
|
||||
];
|
||||
|
||||
const faqsDe = [
|
||||
{
|
||||
pergunta: "Welchen ESP32 sollten Einsteiger wählen?",
|
||||
resposta: "Für Einsteiger in die Maker- und IoT-Welt sind der klassische ESP32 (NodeMCU/DevKitC) oder der ESP32-C3 die beste Wahl, dank breiter Bibliotheksunterstützung, zahlreicher fertiger Beispiele in der Arduino IDE und umfassender Dokumentation.",
|
||||
},
|
||||
{
|
||||
pergunta: "Welcher ESP32 unterstützt Wi-Fi 6, Bluetooth 6 und Thread/Zigbee/Matter?",
|
||||
resposta: "Der ESP32-C6 und der ESP32-C5 sind die führenden Serien für moderne Netzwerke. Der ESP32-C6 bietet Wi-Fi 6 (2,4 GHz) und ein 802.15.4-Funkmodul (Zigbee 3.0 / Thread / Matter). Der ESP32-C5 bietet als erster Dual-Band Wi-Fi 6 mit simultanem Betrieb auf 2,4 GHz und 5 GHz.",
|
||||
},
|
||||
{
|
||||
pergunta: "Welcher ESP32 ist am leistungsfähigsten für Künstliche Intelligenz (TinyML) und Displays?",
|
||||
resposta: "Der ESP32-P4 (Dual-Core RISC-V mit 400 MHz, KI-Vektorerweiterungen, MIPI-CSI/DSI-Schnittstellen für Kameras/Displays und bis zu 64 MB PSRAM) und der ESP32-S3 (Dual-Core Xtensa mit 240 MHz, Vektorbeschleunigern für neuronale Netze und RGB-LCD-Unterstützung) sind am schnellsten für Edge-KI und anspruchsvolle grafische Benutzeroberflächen.",
|
||||
},
|
||||
{
|
||||
pergunta: "Welcher ESP32 verbraucht am wenigsten Energie für batteriebetriebene Projekte?",
|
||||
resposta: "Kompakte RISC-V-Mikrocontroller mit ULP-Coprozessor wie der ESP32-C2, ESP32-C3 und ESP32-H2 (dediziert für 802.15.4 ohne Wi-Fi-Funk) bieten extrem niedrige Deep-Sleep-Ströme im Bereich von 5 µA bis 10 µA.",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function Layout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const faqs = isDe ? faqsDe : isFr ? faqsFr : isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -91,13 +149,33 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.aplicacaoWeb({
|
||||
nome: isEs ? "Selector Inteligente de ESP32" : isEn ? "Intelligent ESP32 Selector" : "Seletor Inteligente de ESP32",
|
||||
descricao: isEs
|
||||
nome: isDe
|
||||
? "Intelligente ESP32-Auswahl"
|
||||
: isFr
|
||||
? "Sélecteur intelligent d'ESP32"
|
||||
: isEs
|
||||
? "Selector Inteligente de ESP32"
|
||||
: isEn
|
||||
? "Intelligent ESP32 Selector"
|
||||
: "Seletor Inteligente de ESP32",
|
||||
descricao: isDe
|
||||
? "Interaktives Werkzeug zur Analyse von Konnektivität, Stromverbrauch, Peripherie und Sicherheit zur Ermittlung der idealen ESP32-Serie."
|
||||
: isFr
|
||||
? "Outil interactif analysant la connectivité, la consommation, les périphériques et la sécurité pour recommander la série idéale d'ESP32."
|
||||
: isEs
|
||||
? "Herramienta interactiva que analiza conectividad, consumo, periféricos y seguridad para recomendar la serie ideal de ESP32."
|
||||
: isEn
|
||||
? "Interactive tool analyzing connectivity, power consumption, peripherals, and security to recommend the ideal ESP32 series."
|
||||
: "Ferramenta interativa que analisa conectividade, consumo, periféricos e segurança para indicar a série ideal de ESP32.",
|
||||
caminho: isEs ? "/es/selector" : isEn ? "/en/selector" : "/seletor",
|
||||
caminho: isDe
|
||||
? "/de/auswahl"
|
||||
: isFr
|
||||
? "/fr/selecteur"
|
||||
: isEs
|
||||
? "/es/selector"
|
||||
: isEn
|
||||
? "/en/selector"
|
||||
: "/seletor",
|
||||
locale,
|
||||
})
|
||||
),
|
||||
@@ -108,8 +186,30 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: isEs ? "Selector de ESP32" : isEn ? "ESP32 Selector" : "Seletor de ESP32", caminho: isEs ? "/es/selector" : isEn ? "/en/selector" : "/seletor" },
|
||||
{
|
||||
nome: isDe ? "Startseite" : isFr ? "Accueil" : isEs ? "Inicio" : isEn ? "Home" : "Início",
|
||||
caminho: isDe ? "/de" : isFr ? "/fr" : isEs ? "/es" : isEn ? "/en" : "/",
|
||||
},
|
||||
{
|
||||
nome: isDe
|
||||
? "ESP32-Auswahl"
|
||||
: isFr
|
||||
? "Sélecteur d'ESP32"
|
||||
: isEs
|
||||
? "Selector de ESP32"
|
||||
: isEn
|
||||
? "ESP32 Selector"
|
||||
: "Seletor de ESP32",
|
||||
caminho: isDe
|
||||
? "/de/auswahl"
|
||||
: isFr
|
||||
? "/fr/selecteur"
|
||||
: isEs
|
||||
? "/es/selector"
|
||||
: isEn
|
||||
? "/en/selector"
|
||||
: "/seletor",
|
||||
},
|
||||
])
|
||||
),
|
||||
}}
|
||||
|
||||
+760
-148
File diff suppressed because it is too large.
Load diff
@@ -8,6 +8,8 @@ import { notFound } from "next/navigation";
|
||||
import seriesDataPt from "@/public/series.json";
|
||||
import seriesDataEn from "@/data/en/series.json";
|
||||
import seriesDataEs from "@/data/es/series.json";
|
||||
import seriesDataFr from "@/data/fr/series.json";
|
||||
import seriesDataDe from "@/data/de/series.json";
|
||||
import ConnectionsDiagram from "@/components/ConnectionsDiagram";
|
||||
import SeriesTabMenu from "@/components/SeriesTabMenu";
|
||||
import PinRestrictions from "@/components/PinRestrictions";
|
||||
@@ -37,8 +39,10 @@ export default async function SerieDetail({ params }) {
|
||||
const { locale, key } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const currentLocale = isDe ? "de" : isFr ? "fr" : isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isDe ? seriesDataDe : isFr ? seriesDataFr : isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const serie = seriesData[key];
|
||||
|
||||
if (!serie) {
|
||||
@@ -47,7 +51,11 @@ export default async function SerieDetail({ params }) {
|
||||
|
||||
let conexoes = [];
|
||||
try {
|
||||
conexoes = isEs
|
||||
conexoes = isDe
|
||||
? require(`@/data/de/conexoes/${key}.json`)
|
||||
: isFr
|
||||
? require(`@/data/fr/conexoes/${key}.json`)
|
||||
: isEs
|
||||
? require(`@/data/es/conexoes/${key}.json`)
|
||||
: isEn
|
||||
? require(`@/data/en/conexoes/${key}.json`)
|
||||
@@ -61,10 +69,26 @@ export default async function SerieDetail({ params }) {
|
||||
const previousKey = currentIndex > 0 ? seriesKeys[currentIndex - 1] : null;
|
||||
const nextKey = currentIndex < seriesKeys.length - 1 ? seriesKeys[currentIndex + 1] : null;
|
||||
|
||||
const nao = isEs || isEn ? "No" : "Não";
|
||||
const naoInformado = isEs ? "No informado" : isEn ? "Not informed" : "Não informado";
|
||||
const nao = isDe ? "Nein" : isFr ? "Non" : isEs || isEn ? "No" : "Não";
|
||||
const naoInformado = isDe ? "Nicht angegeben" : isFr ? "Non communiqué" : isEs ? "No informado" : isEn ? "Not informed" : "Não informado";
|
||||
|
||||
const processadorSpecs = isEs
|
||||
const processadorSpecs = isDe
|
||||
? [
|
||||
{ label: "Architektur", value: serie.arquitetura },
|
||||
{ label: "Kerne", value: serie.nucleos },
|
||||
{ label: "Taktfrequenz", value: serie.frequencia },
|
||||
{ label: "ULP-Coprozessor", value: serie.coprocessador_ulp || nao },
|
||||
{ label: "KI-Beschleuniger", value: serie.aceleradores_ia || nao },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "Architecture", value: serie.arquitetura },
|
||||
{ label: "Cœurs", value: serie.nucleos },
|
||||
{ label: "Fréquence", value: serie.frequencia },
|
||||
{ label: "Coprocesseur ULP", value: serie.coprocessador_ulp || nao },
|
||||
{ label: "Accélérateurs IA", value: serie.aceleradores_ia || nao },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "Arquitectura", value: serie.arquitetura },
|
||||
{ label: "Núcleos", value: serie.nucleos },
|
||||
@@ -89,7 +113,37 @@ export default async function SerieDetail({ params }) {
|
||||
];
|
||||
|
||||
const seg = serie.seguranca || {};
|
||||
const segurancaSpecs = isEs
|
||||
const segurancaSpecs = isDe
|
||||
? [
|
||||
{ label: "AES", value: seg.aes || nao },
|
||||
{ label: "SHA", value: seg.sha || nao },
|
||||
{ label: "RSA / MPI", value: seg.rsa || nao },
|
||||
{ label: "ECC (elliptische Kurven)", value: seg.ecc || nao },
|
||||
{ label: "Hardware-ECDSA", value: seg.ecdsa || nao },
|
||||
{ label: "HMAC", value: seg.hmac || nao },
|
||||
{ label: "Digitale Signatur (DS)", value: seg.assinatura_digital || nao },
|
||||
{ label: "Key Manager", value: seg.key_manager || nao },
|
||||
{ label: "Zufallszahlengenerator (TRNG)", value: seg.rng || nao },
|
||||
{ label: "Flash-Verschlüsselung", value: seg.criptografia_flash || nao },
|
||||
{ label: "Secure Boot", value: seg.secure_boot || nao },
|
||||
{ label: "DPA-Schutz", value: seg.protecao_dpa || nao },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "AES", value: seg.aes || nao },
|
||||
{ label: "SHA", value: seg.sha || nao },
|
||||
{ label: "RSA / MPI", value: seg.rsa || nao },
|
||||
{ label: "ECC (courbes elliptiques)", value: seg.ecc || nao },
|
||||
{ label: "ECDSA matériel", value: seg.ecdsa || nao },
|
||||
{ label: "HMAC", value: seg.hmac || nao },
|
||||
{ label: "Signature numérique (DS)", value: seg.assinatura_digital || nao },
|
||||
{ label: "Key Manager", value: seg.key_manager || nao },
|
||||
{ label: "Générateur aléatoire (TRNG)", value: seg.rng || nao },
|
||||
{ label: "Chiffrement Flash", value: seg.criptografia_flash || nao },
|
||||
{ label: "Secure Boot", value: seg.secure_boot || nao },
|
||||
{ label: "Protection DPA", value: seg.protecao_dpa || nao },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "AES", value: seg.aes || nao },
|
||||
{ label: "SHA", value: seg.sha || nao },
|
||||
@@ -134,7 +188,23 @@ export default async function SerieDetail({ params }) {
|
||||
{ label: "Proteção contra DPA", value: seg.protecao_dpa || "Não" },
|
||||
];
|
||||
|
||||
const ferramentasSpecs = isEs
|
||||
const ferramentasSpecs = isDe
|
||||
? [
|
||||
{ label: "Minimales ESP-IDF", value: serie.esp_idf_minimo || naoInformado },
|
||||
{ label: "Arduino-Core", value: serie.arduino_core || naoInformado },
|
||||
{ label: "Debugging", value: serie.depuracao || naoInformado },
|
||||
{ label: "Gehäuse", value: serie.encapsulamento || naoInformado },
|
||||
{ label: "Verfügbare Module", value: serie.modulos || naoInformado },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "ESP-IDF minimal", value: serie.esp_idf_minimo || naoInformado },
|
||||
{ label: "Core Arduino", value: serie.arduino_core || naoInformado },
|
||||
{ label: "Débogage", value: serie.depuracao || naoInformado },
|
||||
{ label: "Boîtier", value: serie.encapsulamento || naoInformado },
|
||||
{ label: "Modules disponibles", value: serie.modulos || naoInformado },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "ESP-IDF mínimo", value: serie.esp_idf_minimo || naoInformado },
|
||||
{ label: "Core Arduino", value: serie.arduino_core || naoInformado },
|
||||
@@ -158,7 +228,25 @@ export default async function SerieDetail({ params }) {
|
||||
{ label: "Módulos disponíveis", value: serie.modulos || "Não informado" },
|
||||
];
|
||||
|
||||
const conectividadeSpecs = isEs
|
||||
const conectividadeSpecs = isDe
|
||||
? [
|
||||
{ label: "Wi-Fi", value: serie.wifi || nao },
|
||||
{ label: "Bluetooth", value: serie.bluetooth || nao },
|
||||
{ label: "Zigbee/Thread", value: serie.zigbee_thread || nao },
|
||||
{ label: "Matter", value: serie.matter || nao },
|
||||
{ label: "Ethernet", value: serie.ethernet || serie.ethernet_mac || nao },
|
||||
{ label: "CAN", value: serie.can || nao },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "Wi-Fi", value: serie.wifi || nao },
|
||||
{ label: "Bluetooth", value: serie.bluetooth || nao },
|
||||
{ label: "Zigbee/Thread", value: serie.zigbee_thread || nao },
|
||||
{ label: "Matter", value: serie.matter || nao },
|
||||
{ label: "Ethernet", value: serie.ethernet || serie.ethernet_mac || nao },
|
||||
{ label: "CAN", value: serie.can || nao },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "Wi-Fi", value: serie.wifi || nao },
|
||||
{ label: "Bluetooth", value: serie.bluetooth || nao },
|
||||
@@ -185,7 +273,23 @@ export default async function SerieDetail({ params }) {
|
||||
{ label: "CAN", value: serie.can || "Não" },
|
||||
];
|
||||
|
||||
const memoriaSpecs = isEs
|
||||
const memoriaSpecs = isDe
|
||||
? [
|
||||
{ label: "SRAM", value: serie.memoria_sram },
|
||||
{ label: "RTC-SRAM", value: serie.memoria_sram_rtc },
|
||||
{ label: "ROM", value: serie.memoria_rom },
|
||||
{ label: "Externer Flash", value: serie.flash_externa },
|
||||
{ label: "Externer PSRAM", value: serie.psram_externa || nao },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "SRAM", value: serie.memoria_sram },
|
||||
{ label: "SRAM RTC", value: serie.memoria_sram_rtc },
|
||||
{ label: "ROM", value: serie.memoria_rom },
|
||||
{ label: "Flash externe", value: serie.flash_externa },
|
||||
{ label: "PSRAM externe", value: serie.psram_externa || nao },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "SRAM", value: serie.memoria_sram },
|
||||
{ label: "SRAM RTC", value: serie.memoria_sram_rtc },
|
||||
@@ -209,7 +313,33 @@ export default async function SerieDetail({ params }) {
|
||||
{ label: "PSRAM Externa", value: serie.psram_externa || "Não" },
|
||||
];
|
||||
|
||||
const perifericos = isEs
|
||||
const perifericos = isDe
|
||||
? [
|
||||
{ label: "GPIO", value: serie.gpio },
|
||||
{ label: "ADC", value: serie.adc },
|
||||
{ label: "DAC", value: serie.dac || nao },
|
||||
{ label: "Touch", value: serie.touch || nao },
|
||||
{ label: "UART", value: serie.uart },
|
||||
{ label: "SPI", value: serie.spi },
|
||||
{ label: "I2C", value: serie.i2c },
|
||||
{ label: "I2S", value: serie.i2s },
|
||||
{ label: "PWM", value: serie.pwm },
|
||||
{ label: "USB", value: serie.usb || nao },
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
{ label: "GPIO", value: serie.gpio },
|
||||
{ label: "ADC", value: serie.adc },
|
||||
{ label: "DAC", value: serie.dac || nao },
|
||||
{ label: "Touch", value: serie.touch || nao },
|
||||
{ label: "UART", value: serie.uart },
|
||||
{ label: "SPI", value: serie.spi },
|
||||
{ label: "I2C", value: serie.i2c },
|
||||
{ label: "I2S", value: serie.i2s },
|
||||
{ label: "PWM", value: serie.pwm },
|
||||
{ label: "USB", value: serie.usb || nao },
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
{ label: "GPIO", value: serie.gpio },
|
||||
{ label: "ADC", value: serie.adc },
|
||||
@@ -250,12 +380,12 @@ export default async function SerieDetail({ params }) {
|
||||
|
||||
const interfacesEspeciais = [];
|
||||
if (serie.lcd) interfacesEspeciais.push({ label: "LCD", value: serie.lcd });
|
||||
if (serie.camera) interfacesEspeciais.push({ label: isEs ? "Cámara" : isEn ? "Camera" : "Câmera", value: serie.camera });
|
||||
if (serie.camera) interfacesEspeciais.push({ label: isDe ? "Kamera" : isFr ? "Caméra" : isEs ? "Cámara" : isEn ? "Camera" : "Câmera", value: serie.camera });
|
||||
if (serie.mipi_csi) interfacesEspeciais.push({ label: "MIPI CSI", value: serie.mipi_csi });
|
||||
if (serie.mipi_dsi) interfacesEspeciais.push({ label: "MIPI DSI", value: serie.mipi_dsi });
|
||||
if (serie.sdio) interfacesEspeciais.push({ label: "SDIO", value: serie.sdio });
|
||||
if (serie.sensor_hall) interfacesEspeciais.push({ label: isEs ? "Sensor Hall" : isEn ? "Hall Sensor" : "Sensor Hall", value: serie.sensor_hall });
|
||||
if (serie.sensor_temperatura) interfacesEspeciais.push({ label: isEs ? "Sensor de temperatura" : isEn ? "Temperature Sensor" : "Sensor Temperatura", value: serie.sensor_temperatura });
|
||||
if (serie.sensor_hall) interfacesEspeciais.push({ label: isDe ? "Hall-Sensor" : isFr ? "Capteur Hall" : isEs ? "Sensor Hall" : isEn ? "Hall Sensor" : "Sensor Hall", value: serie.sensor_hall });
|
||||
if (serie.sensor_temperatura) interfacesEspeciais.push({ label: isDe ? "Temperatursensor" : isFr ? "Capteur de température" : isEs ? "Sensor de temperatura" : isEn ? "Temperature Sensor" : "Sensor Temperatura", value: serie.sensor_temperatura });
|
||||
|
||||
// Consumo de Energia
|
||||
const consumoEnergia = [];
|
||||
@@ -302,7 +432,35 @@ export default async function SerieDetail({ params }) {
|
||||
'deep_sleep': 'Deep Sleep',
|
||||
'hibernation': 'Hibernación'
|
||||
};
|
||||
const modoLabels = isEs ? modoLabelsEs : isEn ? modoLabelsEn : modoLabelsPt;
|
||||
const modoLabelsFr = {
|
||||
'active': 'Mode actif',
|
||||
'active_cpu_240mhz': 'Actif (CPU 240MHz)',
|
||||
'active_cpu_160mhz': 'Actif (CPU 160MHz)',
|
||||
'active_wifi_tx': 'Actif (Wi-Fi TX)',
|
||||
'active_wifi_tx_peak': 'Actif (Wi-Fi TX Pic)',
|
||||
'active_wifi': 'Actif (Wi-Fi)',
|
||||
'active_wifi6': 'Actif (Wi-Fi 6)',
|
||||
'modem_sleep': 'Modem Sleep',
|
||||
'modem_sleep_cpu_160mhz': 'Modem Sleep (CPU 160MHz)',
|
||||
'light_sleep': 'Light Sleep',
|
||||
'deep_sleep': 'Deep Sleep',
|
||||
'hibernation': 'Hibernation'
|
||||
};
|
||||
const modoLabelsDe = {
|
||||
'active': 'Aktivmodus',
|
||||
'active_cpu_240mhz': 'Aktiv (CPU 240MHz)',
|
||||
'active_cpu_160mhz': 'Aktiv (CPU 160MHz)',
|
||||
'active_wifi_tx': 'Aktiv (Wi-Fi TX)',
|
||||
'active_wifi_tx_peak': 'Aktiv (Wi-Fi TX Spitze)',
|
||||
'active_wifi': 'Aktiv (Wi-Fi)',
|
||||
'active_wifi6': 'Aktiv (Wi-Fi 6)',
|
||||
'modem_sleep': 'Modem Sleep',
|
||||
'modem_sleep_cpu_160mhz': 'Modem Sleep (CPU 160MHz)',
|
||||
'light_sleep': 'Light Sleep',
|
||||
'deep_sleep': 'Deep Sleep',
|
||||
'hibernation': 'Ruhezustand'
|
||||
};
|
||||
const modoLabels = isDe ? modoLabelsDe : isFr ? modoLabelsFr : isEs ? modoLabelsEs : isEn ? modoLabelsEn : modoLabelsPt;
|
||||
|
||||
Object.entries(serie.consumo_energia).forEach(([modo, consumo]) => {
|
||||
consumoEnergia.push({
|
||||
@@ -315,18 +473,18 @@ export default async function SerieDetail({ params }) {
|
||||
const tabs = [
|
||||
{
|
||||
id: "devboard",
|
||||
label: isEs ? "Placa de desarrollo" : isEn ? "Development board" : "Placa de desenvolvimento",
|
||||
label: isDe ? "Entwicklungsboard" : isFr ? "Carte de développement" : isEs ? "Placa de desarrollo" : isEn ? "Development board" : "Placa de desenvolvimento",
|
||||
available: serie.placa,
|
||||
content: (
|
||||
<div className="card p-5 sm:p-7">
|
||||
<h2 className="text-lg font-semibold text-ink">
|
||||
{isEs ? "Kit de desarrollo oficial" : isEn ? "Official development kit" : "Kit de desenvolvimento oficial"}
|
||||
{isDe ? "Offizielles Development Kit" : isFr ? "Kit de développement officiel" : isEs ? "Kit de desarrollo oficial" : isEn ? "Official development kit" : "Kit de desenvolvimento oficial"}
|
||||
</h2>
|
||||
{/* As fotos oficiais foram feitas para fundo claro: o quadro fica branco nos dois temas. */}
|
||||
<div className="mt-5 overflow-hidden rounded-xl border border-line bg-white p-4">
|
||||
<Image
|
||||
src={serie.placa}
|
||||
alt={isEs ? `Placa de desarrollo ${key}` : isEn ? `Development board ${key}` : `Placa de desenvolvimento ${key}`}
|
||||
alt={isDe ? `Entwicklungsboard ${key}` : isFr ? `Carte de développement ${key}` : isEs ? `Placa de desarrollo ${key}` : isEn ? `Development board ${key}` : `Placa de desenvolvimento ${key}`}
|
||||
width={1200}
|
||||
height={800}
|
||||
className="mx-auto h-auto max-h-[28rem] w-full rounded-lg object-contain"
|
||||
@@ -334,7 +492,11 @@ export default async function SerieDetail({ params }) {
|
||||
/>
|
||||
</div>
|
||||
<p className="mt-3 text-sm text-muted">
|
||||
{isEs ? (
|
||||
{isDe ? (
|
||||
<>Offizielles Espressif-Board für die Serie {key}.</>
|
||||
) : isFr ? (
|
||||
<>Carte officielle d'Espressif pour la série {key}.</>
|
||||
) : isEs ? (
|
||||
<>Placa estándar de Espressif para la serie {key}.</>
|
||||
) : isEn ? (
|
||||
<>Official Espressif board for the {key} series.</>
|
||||
@@ -347,7 +509,7 @@ export default async function SerieDetail({ params }) {
|
||||
},
|
||||
{
|
||||
id: "connections",
|
||||
label: isEs ? "Diagrama de patillaje" : isEn ? "Pinout diagram" : "Diagrama de conexões",
|
||||
label: isDe ? "Pinbelegungsdiagramm" : isFr ? "Diagramme de brochage" : isEs ? "Diagrama de patillaje" : isEn ? "Pinout diagram" : "Diagrama de conexões",
|
||||
available: conexoes.length > 0,
|
||||
content: (
|
||||
<div className="card p-5 sm:p-7">
|
||||
@@ -355,10 +517,14 @@ export default async function SerieDetail({ params }) {
|
||||
<AlertTriangle className="mt-0.5 h-5 w-5 shrink-0 text-gold" aria-hidden="true" />
|
||||
<div>
|
||||
<p className="font-semibold text-ink">
|
||||
{isEs ? "Este es el diagrama del chip, no de la placa" : isEn ? "This is the chip diagram, not the development board" : "Este é o diagrama do chip, não da placa"}
|
||||
{isDe ? "Dies ist das Diagramm des Chips, nicht des Entwicklungsboards" : isFr ? "Ceci est le schéma de la puce, pas de la carte de développement" : isEs ? "Este es el diagrama del chip, no de la placa" : isEn ? "This is the chip diagram, not the development board" : "Este é o diagrama do chip, não da placa"}
|
||||
</p>
|
||||
<p className="mt-1">
|
||||
{isEs ? (
|
||||
{isDe ? (
|
||||
`Das Diagramm zeigt die Silizium-Anschlüsse des ${key}. Jedes Entwicklungsboard führt nur einen Teil heraus oder leitet sie anders weiter.`
|
||||
) : isFr ? (
|
||||
`Le schéma montre les connexions du silicium du ${key}. Chaque carte de développement n'en expose qu'une partie ou les route différemment.`
|
||||
) : isEs ? (
|
||||
`El mapa muestra las conexiones del silicio del ${key}. Cada placa de desarrollo expone solo parte de ellas o las enruta de otra forma.`
|
||||
) : isEn ? (
|
||||
`The map shows the silicon connections for the ${key}. Each development board exposes only a subset or routes them differently.`
|
||||
@@ -379,10 +545,41 @@ export default async function SerieDetail({ params }) {
|
||||
<div className="callout mt-8">
|
||||
<p className="flex items-center gap-2 font-semibold text-ink">
|
||||
<Lightbulb className="h-4 w-4 text-accent" aria-hidden="true" />
|
||||
{isEs ? "Casi todos los pines son reconfigurables" : isEn ? "Almost every pin is reconfigurable" : "Quase todo pino é reconfigurável"}
|
||||
{isDe ? "Nahezu jeder Pin ist rekonfigurierbar" : isFr ? "La quasi-totalité des broches est reconfigurable" : isEs ? "Casi todos los pines son reconfigurables" : isEn ? "Almost every pin is reconfigurable" : "Quase todo pino é reconfigurável"}
|
||||
</p>
|
||||
<p className="mt-1">
|
||||
{isEs ? (
|
||||
{isDe ? (
|
||||
<>
|
||||
Die IO-Matrix des {key} ermöglicht das Zuweisen von SPI, I2C, UART, PWM und Kamera-/Displaybussen
|
||||
zu den meisten digitalen Pins. Für Strapping-Einschränkungen und analoge Pins konsultieren Sie den{" "}
|
||||
<a
|
||||
href={`https://docs.espressif.com/projects/esp-idf/en/latest/${String(key).toLowerCase().replace("-", "")}/api-reference/peripherals/gpio.html`}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-1 font-medium text-accent underline decoration-accent/30 underline-offset-2 hover:decoration-accent"
|
||||
>
|
||||
offiziellen GPIO-Leitfaden
|
||||
<ExternalLink className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
</a>
|
||||
.
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
La matrice d'E/S du {key} permet d'assigner SPI, I2C, UART, PWM et bus caméra/écran
|
||||
à la majorité des broches numériques. Pour les restrictions de strapping et broches analogiques,
|
||||
consultez le{" "}
|
||||
<a
|
||||
href={`https://docs.espressif.com/projects/esp-idf/en/latest/${String(key).toLowerCase().replace("-", "")}/api-reference/peripherals/gpio.html`}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
className="inline-flex items-center gap-1 font-medium text-accent underline decoration-accent/30 underline-offset-2 hover:decoration-accent"
|
||||
>
|
||||
guide officiel GPIO
|
||||
<ExternalLink className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
</a>
|
||||
.
|
||||
</>
|
||||
) : isEs ? (
|
||||
<>
|
||||
La matriz de E/S del {key} permite mover buses SPI, I2C, UART, PWM y cámara/pantalla
|
||||
a la mayoría de los pines digitales. Para las restricciones de strapping y pines analógicos,
|
||||
@@ -438,44 +635,48 @@ export default async function SerieDetail({ params }) {
|
||||
];
|
||||
|
||||
const secoes = [
|
||||
{ id: "processador", titulo: isEs ? "Procesador" : isEn ? "Processor" : "Processador", icon: Cpu, specs: processadorSpecs },
|
||||
{ id: "conectividade", titulo: isEs ? "Conectividad" : isEn ? "Connectivity" : "Conectividade", icon: Wifi, specs: conectividadeSpecs },
|
||||
{ id: "ferramentas", titulo: isEs ? "Herramientas y disponibilidad" : isEn ? "Tools and availability" : "Ferramentas e disponibilidade", icon: Package, specs: ferramentasSpecs },
|
||||
{ id: "seguranca", titulo: isEs ? "Seguridad" : isEn ? "Security" : "Segurança", icon: ShieldCheck, specs: segurancaSpecs },
|
||||
{ id: "memoria", titulo: isEs ? "Memoria" : isEn ? "Memory" : "Memória", icon: Database, specs: memoriaSpecs },
|
||||
{ id: "processador", titulo: isDe ? "Prozessor" : isFr ? "Processeur" : isEs ? "Procesador" : isEn ? "Processor" : "Processador", icon: Cpu, specs: processadorSpecs },
|
||||
{ id: "conectividade", titulo: isDe ? "Konnektivität" : isFr ? "Connectivité" : isEs ? "Conectividad" : isEn ? "Connectivity" : "Conectividade", icon: Wifi, specs: conectividadeSpecs },
|
||||
{ id: "ferramentas", titulo: isDe ? "Werkzeuge und Verfügbarkeit" : isFr ? "Outils et disponibilité" : isEs ? "Herramientas y disponibilidad" : isEn ? "Tools and availability" : "Ferramentas e disponibilidade", icon: Package, specs: ferramentasSpecs },
|
||||
{ id: "seguranca", titulo: isDe ? "Sicherheit" : isFr ? "Sécurité" : isEs ? "Seguridad" : isEn ? "Security" : "Segurança", icon: ShieldCheck, specs: segurancaSpecs },
|
||||
{ id: "memoria", titulo: isDe ? "Speicher" : isFr ? "Mémoire" : isEs ? "Memoria" : isEn ? "Memory" : "Memória", icon: Database, specs: memoriaSpecs },
|
||||
...(consumoEnergia.length > 0
|
||||
? [{
|
||||
id: "energia",
|
||||
titulo: isEs ? "Consumo de energía" : isEn ? "Power consumption" : "Consumo de energia",
|
||||
titulo: isDe ? "Stromverbrauch" : isFr ? "Consommation d'énergie" : isEs ? "Consumo de energía" : isEn ? "Power consumption" : "Consumo de energia",
|
||||
icon: Battery,
|
||||
specs: consumoEnergia,
|
||||
nota: isEs
|
||||
nota: isDe
|
||||
? "Typische Werte bei 3,3 V und 25 °C. Der tatsächliche Stromverbrauch hängt vom Funk-Tastgrad und der konfigurierten Taktfrequenz ab."
|
||||
: isFr
|
||||
? "Valeurs typiques à 3,3 V et 25 °C. La consommation réelle dépend du cycle de travail de la radio et de la fréquence d'horloge configurée."
|
||||
: isEs
|
||||
? "Valores típicos a 3,3 V y 25 °C. El consumo real depende del ciclo de trabajo de la radio y de la frecuencia de reloj configurada."
|
||||
: isEn
|
||||
? "Typical values at 3.3 V and 25 °C. Actual power consumption depends on radio duty cycle and configured clock frequency."
|
||||
: "Valores típicos a 3,3 V e 25 °C. O consumo real depende do ciclo de trabalho do rádio e da frequência de clock configurada.",
|
||||
}]
|
||||
: []),
|
||||
{ id: "perifericos", titulo: isEs ? "Periféricos" : isEn ? "Peripherals" : "Periféricos", icon: Sliders, specs: perifericos },
|
||||
{ id: "perifericos", titulo: isDe ? "Peripherie" : isFr ? "Périphériques" : isEs ? "Periféricos" : isEn ? "Peripherals" : "Periféricos", icon: Sliders, specs: perifericos },
|
||||
...(interfacesEspeciais.length > 0
|
||||
? [{ id: "interfaces", titulo: isEs ? "Interfaces especiales" : isEn ? "Special interfaces" : "Interfaces especiais", icon: Sliders, specs: interfacesEspeciais }]
|
||||
? [{ id: "interfaces", titulo: isDe ? "Spezielle Schnittstellen" : isFr ? "Interfaces spéciales" : isEs ? "Interfaces especiales" : isEn ? "Special interfaces" : "Interfaces especiais", icon: Sliders, specs: interfacesEspeciais }]
|
||||
: []),
|
||||
{
|
||||
id: "temperatura",
|
||||
titulo: isEs ? "Límites de temperatura" : isEn ? "Temperature limits" : "Limites de temperatura",
|
||||
titulo: isDe ? "Temperaturgrenzwerte" : isFr ? "Limites de température" : isEs ? "Límites de temperatura" : isEn ? "Temperature limits" : "Limites de temperatura",
|
||||
icon: Thermometer,
|
||||
specs: [
|
||||
{ label: isEs ? "Operación" : isEn ? "Operating" : "Operação", value: serie.temperatura_operacao },
|
||||
{ label: isEs ? "Almacenamiento" : isEn ? "Storage" : "Armazenamento", value: serie.temperatura_armazenamento },
|
||||
{ label: isDe ? "Betrieb" : isFr ? "Fonctionnement" : isEs ? "Operación" : isEn ? "Operating" : "Operação", value: serie.temperatura_operacao },
|
||||
{ label: isDe ? "Lagerung" : isFr ? "Stockage" : isEs ? "Almacenamiento" : isEn ? "Storage" : "Armazenamento", value: serie.temperatura_armazenamento },
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const fatos = [
|
||||
{ label: isEs ? "Procesador" : isEn ? "Processor" : "Processador", value: String(serie.nucleos).includes("2") ? "Dual-core" : "Single-core", detail: serie.frequencia },
|
||||
{ label: "SRAM", value: serie.memoria_sram, detail: isEs ? `+ ${serie.memoria_sram_rtc} de SRAM RTC` : isEn ? `+ ${serie.memoria_sram_rtc} RTC SRAM` : `+ ${serie.memoria_sram_rtc} de SRAM RTC` },
|
||||
{ label: "GPIO", value: serie.gpio, detail: isEs ? "pines programables" : isEn ? "programmable pins" : "pinos programáveis" },
|
||||
{ label: isEs ? "Arquitectura" : isEn ? "Architecture" : "Arquitetura", value: String(serie.arquitetura).includes("RISC-V") ? "RISC-V" : "Xtensa", detail: serie.arquitetura },
|
||||
{ label: isDe ? "Prozessor" : isFr ? "Processeur" : isEs ? "Procesador" : isEn ? "Processor" : "Processador", value: String(serie.nucleos).includes("2") ? "Dual-core" : "Single-core", detail: serie.frequencia },
|
||||
{ label: "SRAM", value: serie.memoria_sram, detail: isDe ? `+ ${serie.memoria_sram_rtc} RTC-SRAM` : isFr ? `+ ${serie.memoria_sram_rtc} de SRAM RTC` : isEs ? `+ ${serie.memoria_sram_rtc} de SRAM RTC` : isEn ? `+ ${serie.memoria_sram_rtc} RTC SRAM` : `+ ${serie.memoria_sram_rtc} de SRAM RTC` },
|
||||
{ label: "GPIO", value: serie.gpio, detail: isDe ? "programmierbare Pins" : isFr ? "broches programmables" : isEs ? "pines programables" : isEn ? "programmable pins" : "pinos programáveis" },
|
||||
{ label: isDe ? "Architektur" : isFr ? "Architecture" : isEs ? "Arquitectura" : isEn ? "Architecture" : "Arquitetura", value: String(serie.arquitetura).includes("RISC-V") ? "RISC-V" : "Xtensa", detail: serie.arquitetura },
|
||||
];
|
||||
|
||||
return (
|
||||
@@ -488,8 +689,8 @@ export default async function SerieDetail({ params }) {
|
||||
type="application/ld+json"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isEs ? "Series" : isEn ? "Series" : "Séries", caminho: getLocalizedHref("/series", currentLocale) },
|
||||
{ nome: isDe ? "Startseite" : isFr ? "Accueil" : isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isDe ? "/de" : isFr ? "/fr" : isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isDe ? "ESP32-Serien" : isFr ? "Séries ESP32" : isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32", caminho: getLocalizedHref("/series", currentLocale) },
|
||||
{ nome: serie.nome_completo, caminho: getLocalizedHref(`/series/${key}`, currentLocale) },
|
||||
])),
|
||||
}}
|
||||
@@ -501,7 +702,9 @@ export default async function SerieDetail({ params }) {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Series" : isEn ? "Series" : "Séries", href: getLocalizedHref("/series", currentLocale) }, { label: key }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isDe ? "Serien" : isFr ? "Séries" : isEs ? "Series" : isEn ? "Series" : "Séries", href: getLocalizedHref("/series", currentLocale) }, { label: key }]}
|
||||
icon={Cpu}
|
||||
label={serie.arquitetura}
|
||||
title={key}
|
||||
@@ -510,32 +713,32 @@ export default async function SerieDetail({ params }) {
|
||||
{serie.datasheet ? (
|
||||
<a href={serie.datasheet} target="_blank" rel="noopener noreferrer" className="btn btn-primary">
|
||||
<FileText className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Datasheet oficial" : isEn ? "Official datasheet" : "Datasheet oficial"}
|
||||
{isDe ? "Offizielles Datenblatt" : isFr ? "Datasheet officiel" : isEs ? "Datasheet oficial" : isEn ? "Official datasheet" : "Datasheet oficial"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
) : (
|
||||
<span className="btn btn-ghost cursor-not-allowed opacity-70" aria-disabled="true">
|
||||
<FileText className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Datasheet aún no publicado" : isEn ? "Datasheet not yet published" : "Datasheet ainda não publicado"}
|
||||
{isDe ? "Datenblatt noch nicht veröffentlicht" : isFr ? "Datasheet pas encore publié" : isEs ? "Datasheet aún no publicado" : isEn ? "Datasheet not yet published" : "Datasheet ainda não publicado"}
|
||||
</span>
|
||||
)}
|
||||
{serie.guia_de_programacao && (
|
||||
<a href={serie.guia_de_programacao} target="_blank" rel="noopener noreferrer" className="btn btn-ghost">
|
||||
<Code className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Guía de programación" : isEn ? "Programming guide" : "Guia de programação"}
|
||||
{isDe ? "Programmierleitfaden" : isFr ? "Guide de programmation" : isEs ? "Guía de programación" : isEn ? "Programming guide" : "Guia de programação"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
)}
|
||||
{serie.manual_tecnico && (
|
||||
<a href={serie.manual_tecnico} target="_blank" rel="noopener noreferrer" className="btn btn-ghost">
|
||||
<BookOpen className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Manual de referencia técnica" : isEn ? "Technical reference manual" : "Manual técnico"}
|
||||
{isDe ? "Technisches Referenzhandbuch" : isFr ? "Manuel technique de référence" : isEs ? "Manual de referencia técnica" : isEn ? "Technical reference manual" : "Manual técnico"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
)}
|
||||
</PageHero>
|
||||
|
||||
<section className="shell mt-10" aria-label={isEs ? "Resumen" : isEn ? "Summary" : "Resumo"}>
|
||||
<section className="shell mt-10" aria-label={isDe ? "Zusammenfassung" : isFr ? "Résumé" : isEs ? "Resumen" : isEn ? "Summary" : "Resumo"}>
|
||||
<dl className="grid grid-cols-2 gap-3 lg:grid-cols-4">
|
||||
{fatos.map((fato) => (
|
||||
<div key={fato.label} className="tile">
|
||||
@@ -551,7 +754,7 @@ export default async function SerieDetail({ params }) {
|
||||
<AlertTriangle className="mt-0.5 h-5 w-5 shrink-0 text-gold" aria-hidden="true" />
|
||||
<div>
|
||||
<p className="font-semibold text-ink">
|
||||
{isEs ? "Documentación preliminar" : isEn ? "Preliminary documentation" : "Documentação preliminar"}
|
||||
{isDe ? "Vorläufige Dokumentation" : isFr ? "Documentation préliminaire" : isEs ? "Documentación preliminar" : isEn ? "Preliminary documentation" : "Documentação preliminar"}
|
||||
</p>
|
||||
<p className="mt-1">{serie.status_documentacao}</p>
|
||||
</div>
|
||||
@@ -560,13 +763,13 @@ export default async function SerieDetail({ params }) {
|
||||
</section>
|
||||
|
||||
<div className="shell mt-10">
|
||||
<SeriesTabMenu tabs={tabs} isEn={isEn} isEs={isEs} />
|
||||
<PinRestrictions conexoes={conexoes} serieKey={key} isEn={isEn} isEs={isEs} />
|
||||
<SeriesTabMenu tabs={tabs} isEn={isEn} isEs={isEs} isFr={isFr} isDe={isDe} />
|
||||
<PinRestrictions conexoes={conexoes} serieKey={key} isEn={isEn} isEs={isEs} isFr={isFr} isDe={isDe} />
|
||||
</div>
|
||||
|
||||
<div className="shell mt-12">
|
||||
<nav
|
||||
aria-label={isEs ? "Secciones de la ficha" : isEn ? "Datasheet sections" : "Seções da ficha"}
|
||||
aria-label={isDe ? "Abschnitte des Datenblatts" : isFr ? "Sections de la fiche" : isEs ? "Secciones de la ficha" : isEn ? "Datasheet sections" : "Seções da ficha"}
|
||||
className="nav-pill no-scrollbar sticky top-20 z-30 flex gap-1 overflow-x-auto rounded-full p-1.5"
|
||||
>
|
||||
{secoes.map((secao) => (
|
||||
@@ -587,7 +790,11 @@ export default async function SerieDetail({ params }) {
|
||||
<div className="panel flex flex-col items-start justify-between gap-6 p-7 sm:p-10 md:flex-row md:items-center">
|
||||
<div className="max-w-2xl">
|
||||
<h2 className="section-title">
|
||||
{isEs ? (
|
||||
{isDe ? (
|
||||
<>Bereit zum Prototyping mit {key}?</>
|
||||
) : isFr ? (
|
||||
<>Prêt à prototyper avec {key} ?</>
|
||||
) : isEs ? (
|
||||
<>¿Listo para prototipar con {key}?</>
|
||||
) : isEn ? (
|
||||
<>Ready to prototype with {key}?</>
|
||||
@@ -596,7 +803,11 @@ export default async function SerieDetail({ params }) {
|
||||
)}
|
||||
</h2>
|
||||
<p className="mt-3 text-base text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Entdecken Sie die für diese Serie verfügbaren Entwicklungsboards mit USB, integrierten Sensoren und Links zum offiziellen Shop."
|
||||
: isFr
|
||||
? "Explorez les cartes de développement disponibles pour cette série, avec USB, capteurs intégrés et liens vers la boutique officielle."
|
||||
: isEs
|
||||
? "Explore las placas de desarrollo disponibles para esta serie, con USB, sensores integrados y enlaces a la tienda oficial."
|
||||
: isEn
|
||||
? "Explore development boards available for this series, with USB, onboard sensors, and official store links."
|
||||
@@ -604,17 +815,17 @@ export default async function SerieDetail({ params }) {
|
||||
</p>
|
||||
</div>
|
||||
<Link href={getLocalizedHref("/catalogo", currentLocale)} className="btn btn-primary shrink-0">
|
||||
{isEs ? "Ver placas" : isEn ? "View boards" : "Ver placas"}
|
||||
{isDe ? "Boards ansehen" : isFr ? "Voir les cartes" : isEs ? "Ver placas" : isEn ? "View boards" : "Ver placas"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
<nav aria-label={isEs ? "Otras series" : isEn ? "Other series" : "Outras séries"} className="mt-6 grid gap-3 sm:grid-cols-[1fr_auto_1fr] sm:items-center">
|
||||
<nav aria-label={isDe ? "Andere Serien" : isFr ? "Autres séries" : isEs ? "Otras series" : isEn ? "Other series" : "Outras séries"} className="mt-6 grid gap-3 sm:grid-cols-[1fr_auto_1fr] sm:items-center">
|
||||
{previousKey ? (
|
||||
<Link href={getLocalizedHref(`/series/${previousKey}`, currentLocale)} className="card card-interactive group flex items-center gap-3 px-5 py-4">
|
||||
<ArrowLeft className="h-4 w-4 text-muted transition-transform group-hover:-translate-x-1" aria-hidden="true" />
|
||||
<span>
|
||||
<span className="block text-xs text-muted">{isEs ? "Serie anterior" : isEn ? "Previous series" : "Série anterior"}</span>
|
||||
<span className="block text-xs text-muted">{isDe ? "Vorherige Serie" : isFr ? "Série précédente" : isEs ? "Serie anterior" : isEn ? "Previous series" : "Série anterior"}</span>
|
||||
<span className="block font-display text-lg font-semibold text-ink">{previousKey}</span>
|
||||
</span>
|
||||
</Link>
|
||||
@@ -623,12 +834,12 @@ export default async function SerieDetail({ params }) {
|
||||
)}
|
||||
<Link href={getLocalizedHref("/comparacao", currentLocale)} className="btn btn-ghost justify-self-center">
|
||||
<Scale className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Comparar series" : isEn ? "Compare series" : "Comparar séries"}
|
||||
{isDe ? "Serien vergleichen" : isFr ? "Comparer les séries" : isEs ? "Comparar series" : isEn ? "Compare series" : "Comparar séries"}
|
||||
</Link>
|
||||
{nextKey ? (
|
||||
<Link href={getLocalizedHref(`/series/${nextKey}`, currentLocale)} className="card card-interactive group flex items-center justify-end gap-3 px-5 py-4 text-right">
|
||||
<span>
|
||||
<span className="block text-xs text-muted">{isEs ? "Siguiente serie" : isEn ? "Next series" : "Próxima série"}</span>
|
||||
<span className="block text-xs text-muted">{isDe ? "Nächste Serie" : isFr ? "Série suivante" : isEs ? "Siguiente serie" : isEn ? "Next series" : "Próxima série"}</span>
|
||||
<span className="block font-display text-lg font-semibold text-ink">{nextKey}</span>
|
||||
</span>
|
||||
<ArrowRight className="h-4 w-4 text-muted transition-transform group-hover:translate-x-1" aria-hidden="true" />
|
||||
@@ -674,12 +885,25 @@ export async function generateMetadata({ params }) {
|
||||
const { locale, key } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const currentLocale = isDe ? "de" : isFr ? "fr" : isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isDe ? seriesDataDe : isFr ? seriesDataFr : isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const serie = seriesData[key];
|
||||
|
||||
if (!serie) {
|
||||
return { title: isEs ? "Serie no encontrada" : isEn ? "Series not found" : "Série não encontrada", robots: { index: false, follow: false } };
|
||||
return {
|
||||
title: isDe
|
||||
? "Serie nicht gefunden"
|
||||
: isFr
|
||||
? "Série non trouvée"
|
||||
: isEs
|
||||
? "Serie no encontrada"
|
||||
: isEn
|
||||
? "Series not found"
|
||||
: "Série não encontrada",
|
||||
robots: { index: false, follow: false },
|
||||
};
|
||||
}
|
||||
|
||||
const radio = [
|
||||
@@ -688,7 +912,17 @@ export async function generateMetadata({ params }) {
|
||||
serie.zigbee_thread && !String(serie.zigbee_thread).startsWith("Não") && !String(serie.zigbee_thread).startsWith("No") ? "802.15.4" : null,
|
||||
].filter(Boolean).join(", ");
|
||||
|
||||
const descricao = isEs
|
||||
const descricao = isDe
|
||||
? `${serie.nome_completo}: ${serie.arquitetura}, ${serie.frequencia}, ` +
|
||||
`${serie.memoria_sram} SRAM und ${serie.gpio} GPIOs` +
|
||||
(radio ? `. Funk: ${radio}` : "") +
|
||||
`. Vollständige Pinbelegung, Peripherie, Hardwaresicherheit und eingeschränkte Pins auf Deutsch.`
|
||||
: isFr
|
||||
? `${serie.nome_completo} : ${serie.arquitetura}, ${serie.frequencia}, ` +
|
||||
`${serie.memoria_sram} de SRAM et ${serie.gpio} GPIO` +
|
||||
(radio ? `. Radio : ${radio}` : "") +
|
||||
`. Brochage complet, périphériques, sécurité matérielle et broches avec restrictions, en français.`
|
||||
: isEs
|
||||
? `${serie.nome_completo}: ${serie.arquitetura}, ${serie.frequencia}, ` +
|
||||
`${serie.memoria_sram} de SRAM y ${serie.gpio} GPIO` +
|
||||
(radio ? `. Radio: ${radio}` : "") +
|
||||
@@ -704,10 +938,22 @@ export async function generateMetadata({ params }) {
|
||||
`. Pinagem completa, periféricos, segurança em hardware e pinos com restrição, em português.`;
|
||||
|
||||
const imagem = serie.placa
|
||||
? [{ url: serie.placa, width: 1600, height: 1091, alt: isEs ? `Patillaje de ${serie.nome_completo}` : isEn ? `Pinout of ${serie.nome_completo}` : `Pinagem do ${serie.nome_completo}` }]
|
||||
? [{ url: serie.placa, width: 1600, height: 1091, alt: isDe ? `Pinbelegung von ${serie.nome_completo}` : isFr ? `Brochage de ${serie.nome_completo}` : isEs ? `Patillaje de ${serie.nome_completo}` : isEn ? `Pinout of ${serie.nome_completo}` : `Pinagem do ${serie.nome_completo}` }]
|
||||
: [{ url: "/opengraph-image.png", width: 1200, height: 630, alt: "ESPDocs" }];
|
||||
|
||||
const keywords = isEs
|
||||
const keywords = isDe
|
||||
? [
|
||||
serie.nome_completo, `${serie.nome_completo} pinout`, `${serie.nome_completo} Pinbelegung`,
|
||||
`${serie.nome_completo} datasheet`, `${serie.nome_completo} Spezifikationen`,
|
||||
`${serie.nome_completo} deutsch`, "ESP32", "Espressif", "Mikrocontroller",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
serie.nome_completo, `${serie.nome_completo} pinout`, `${serie.nome_completo} brochage`,
|
||||
`${serie.nome_completo} datasheet`, `${serie.nome_completo} spécifications`,
|
||||
`${serie.nome_completo} français`, "ESP32", "Espressif", "microcontrôleur",
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
serie.nome_completo, `${serie.nome_completo} pinout`, `${serie.nome_completo} patillaje`,
|
||||
`${serie.nome_completo} datasheet`, `${serie.nome_completo} especificaciones`,
|
||||
@@ -727,14 +973,32 @@ export async function generateMetadata({ params }) {
|
||||
|
||||
const meta = {
|
||||
...paginaMeta({
|
||||
titulo: isEs ? `${serie.nome_completo}: especificaciones y patillaje` : isEn ? `${serie.nome_completo}: specifications and pinout` : `${serie.nome_completo}: especificações e pinagem`,
|
||||
titulo: isDe
|
||||
? `${serie.nome_completo}: Spezifikationen und Pinbelegung`
|
||||
: isFr
|
||||
? `${serie.nome_completo} : spécifications et brochage`
|
||||
: isEs
|
||||
? `${serie.nome_completo}: especificaciones y patillaje`
|
||||
: isEn
|
||||
? `${serie.nome_completo}: specifications and pinout`
|
||||
: `${serie.nome_completo}: especificações e pinagem`,
|
||||
descricao,
|
||||
caminho: `/series/${key}`,
|
||||
tipo: "article",
|
||||
locale: currentLocale,
|
||||
keywords,
|
||||
}),
|
||||
other: { "article:section": isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32" },
|
||||
other: {
|
||||
"article:section": isDe
|
||||
? "ESP32-Serien"
|
||||
: isFr
|
||||
? "Séries ESP32"
|
||||
: isEs
|
||||
? "Series ESP32"
|
||||
: isEn
|
||||
? "ESP32 Series"
|
||||
: "Séries ESP32",
|
||||
},
|
||||
};
|
||||
|
||||
meta.openGraph = { ...meta.openGraph, images: imagem };
|
||||
|
||||
@@ -4,23 +4,41 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const meta = paginaMeta({
|
||||
titulo: isEs ? "Series ESP32: Guía técnica y patillaje" : isEn ? "ESP32 Series: Technical Guide and Pinouts" : "Séries ESP32",
|
||||
descricao: isEs
|
||||
titulo: isDe
|
||||
? "ESP32-Serien: Technischer Leitfaden und Pinbelegung"
|
||||
: isFr
|
||||
? "Séries ESP32 : Guide technique et brochage"
|
||||
: isEs
|
||||
? "Series ESP32: Guía técnica y patillaje"
|
||||
: isEn
|
||||
? "ESP32 Series: Technical Guide and Pinouts"
|
||||
: "Séries ESP32",
|
||||
descricao: isDe
|
||||
? "Alle 12 ESP32-Serien Seite an Seite: ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 und H4. Architektur, Speicher, Funk, Peripherie und Pinbelegung jeder Serie."
|
||||
: isFr
|
||||
? "Les 12 séries d'ESP32 côte à côte : ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 et H4. Architecture, mémoire, radio, périphériques et brochage de chacune."
|
||||
: isEs
|
||||
? "Las 12 series de ESP32 lado a lado: ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 y H4. Arquitectura, memoria, radio, periféricos y patillaje de cada una."
|
||||
: isEn
|
||||
? "All 12 ESP32 series side by side: ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 and H4. Architecture, memory, radio, peripherals and pinouts for each one."
|
||||
: "As 12 séries de ESP32 lado a lado: ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 e H4. Arquitetura, memória, rádio, periféricos e pinagem de cada uma, em português.",
|
||||
caminho: "/series",
|
||||
locale,
|
||||
keywords: isEs
|
||||
keywords: isDe
|
||||
? ["ESP32-Serien", "ESP32-Modelle", "ESP32 S3", "ESP32 C6", "ESP32 P4", "Unterschied zwischen ESP32"]
|
||||
: isFr
|
||||
? ["séries ESP32", "modèles ESP32", "ESP32 S3", "ESP32 C6", "ESP32 P4", "différence entre ESP32"]
|
||||
: isEs
|
||||
? ["series ESP32", "modelos de ESP32", "ESP32 S3", "ESP32 C6", "ESP32 P4", "diferencia entre ESP32"]
|
||||
: isEn
|
||||
? ["ESP32 series", "ESP32 models", "ESP32 S3", "ESP32 C6", "ESP32 P4", "difference between ESP32"]
|
||||
: ["séries ESP32", "modelos de ESP32", "ESP32 S3", "ESP32 C6", "ESP32 P4", "diferença entre ESP32"],
|
||||
});
|
||||
meta.title = {
|
||||
default: isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32",
|
||||
default: isDe ? "ESP32-Serien" : isFr ? "Séries ESP32" : isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32",
|
||||
template: "%s · ESPDocs",
|
||||
};
|
||||
return meta;
|
||||
@@ -59,11 +77,35 @@ const faqsEs = [
|
||||
},
|
||||
];
|
||||
|
||||
const faqsFr = [
|
||||
{
|
||||
pergunta: "Combien de séries d'ESP32 existent actuellement ?",
|
||||
resposta: "Actuellement, l'écosystème Espressif compte 12 séries principales : ESP32 classique, ESP32-S2, ESP32-S3, ESP32-S31, ESP32-C2, ESP32-C3, ESP32-C5, ESP32-C6, ESP32-C61, ESP32-P4, ESP32-H2 et ESP32-H4.",
|
||||
},
|
||||
{
|
||||
pergunta: "Quelles sont les séries les plus récentes d'Espressif ?",
|
||||
resposta: "Les séries les plus récentes incluent l'ESP32-P4 (axé sur la haute performance avec dual-core RISC-V à 400 MHz), l'ESP32-C5 (première puce avec Wi-Fi bi-bande 2,4/5 GHz d'Espressif) et l'ESP32-C61 (Wi-Fi 6 et Bluetooth 6 à faible coût).",
|
||||
},
|
||||
];
|
||||
|
||||
const faqsDe = [
|
||||
{
|
||||
pergunta: "Wie viele ESP32-Serien gibt es derzeit?",
|
||||
resposta: "Derzeit umfasst das Espressif-Ökosystem 12 Hauptserien: klassischer ESP32, ESP32-S2, ESP32-S3, ESP32-S31, ESP32-C2, ESP32-C3, ESP32-C5, ESP32-C6, ESP32-C61, ESP32-P4, ESP32-H2 und ESP32-H4.",
|
||||
},
|
||||
{
|
||||
pergunta: "Welche sind die neuesten Serien von Espressif?",
|
||||
resposta: "Zu den neuesten Serien gehören der ESP32-P4 (fokussiert auf Hochleistung mit Dual-Core RISC-V bei 400 MHz), der ESP32-C5 (erster Chip mit Dual-Band 2,4/5 GHz Wi-Fi von Espressif) und der ESP32-C61 (kostengünstiges Wi-Fi 6 und Bluetooth 6).",
|
||||
},
|
||||
];
|
||||
|
||||
export default async function Layout({ children, params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const faqs = isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const faqs = isDe ? faqsDe : isFr ? faqsFr : isEs ? faqsEs : isEn ? faqsEn : faqsPt;
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -72,8 +114,14 @@ export default async function Layout({ children, params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isEn ? "Home" : "Início", caminho: isEs ? "/es" : isEn ? "/en" : "/" },
|
||||
{ nome: isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32", caminho: isEs ? "/es/series" : isEn ? "/en/series" : "/series" },
|
||||
{
|
||||
nome: isDe ? "Startseite" : isFr ? "Accueil" : isEs ? "Inicio" : isEn ? "Home" : "Início",
|
||||
caminho: isDe ? "/de" : isFr ? "/fr" : isEs ? "/es" : isEn ? "/en" : "/",
|
||||
},
|
||||
{
|
||||
nome: isDe ? "ESP32-Serien" : isFr ? "Séries ESP32" : isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32",
|
||||
caminho: isDe ? "/de/serien" : isFr ? "/fr/series" : isEs ? "/es/series" : isEn ? "/en/series" : "/series",
|
||||
},
|
||||
])
|
||||
),
|
||||
}}
|
||||
|
||||
+106
-27
@@ -9,6 +9,8 @@ import Link from "next/link";
|
||||
import seriesDataPt from "@/public/series.json";
|
||||
import seriesDataEn from "@/data/en/series.json";
|
||||
import seriesDataEs from "@/data/es/series.json";
|
||||
import seriesDataFr from "@/data/fr/series.json";
|
||||
import seriesDataDe from "@/data/de/series.json";
|
||||
import { getLocalizedHref } from "@/i18n/links";
|
||||
import {
|
||||
AlertTriangle,
|
||||
@@ -45,31 +47,51 @@ const FILTROS_ES = [
|
||||
{ id: "ia", rotulo: "Aceleración de IA", testa: (s) => Boolean(s.aceleradores_ia) },
|
||||
];
|
||||
|
||||
const FILTROS_FR = [
|
||||
{ id: "todas", rotulo: "Toutes", testa: () => true },
|
||||
{ id: "riscv", rotulo: "RISC-V", testa: (s) => s.arquitetura.includes("RISC-V") },
|
||||
{ id: "xtensa", rotulo: "Xtensa", testa: (s) => !s.arquitetura.includes("RISC-V") },
|
||||
{ id: "matter", rotulo: "Matter", testa: (s) => s.matter === "Oui" || s.matter === "Yes" || s.matter === "Sim" || s.matter === "Sí" },
|
||||
{ id: "ia", rotulo: "Accélération IA", testa: (s) => Boolean(s.aceleradores_ia) },
|
||||
];
|
||||
|
||||
const FILTROS_DE = [
|
||||
{ id: "todas", rotulo: "Alle", testa: () => true },
|
||||
{ id: "riscv", rotulo: "RISC-V", testa: (s) => s.arquitetura.includes("RISC-V") },
|
||||
{ id: "xtensa", rotulo: "Xtensa", testa: (s) => !s.arquitetura.includes("RISC-V") },
|
||||
{ id: "matter", rotulo: "Matter", testa: (s) => s.matter === "Ja" || s.matter === "Yes" || s.matter === "Sim" || s.matter === "Sí" },
|
||||
{ id: "ia", rotulo: "KI-Beschleunigung", testa: (s) => Boolean(s.aceleradores_ia) },
|
||||
];
|
||||
|
||||
/** Marcador de segurança: o recurso que diferencia a série, não o que todas têm. */
|
||||
function nivelSeguranca(serie, isEn, isEs) {
|
||||
function nivelSeguranca(serie, isEn, isEs, isFr, isDe) {
|
||||
const seg = serie.seguranca || {};
|
||||
if (seg.key_manager === "Sim" || seg.key_manager === "Yes" || seg.key_manager === "Sí") return "Key Manager";
|
||||
if (String(seg.ecdsa).startsWith("Sim") || String(seg.ecdsa).startsWith("Yes") || String(seg.ecdsa).startsWith("Sí")) {
|
||||
return isEs ? "ECDSA en hardware" : isEn ? "Hardware ECDSA" : "ECDSA em hardware";
|
||||
if (seg.key_manager === "Sim" || seg.key_manager === "Yes" || seg.key_manager === "Sí" || seg.key_manager === "Oui" || seg.key_manager === "Ja") return "Key Manager";
|
||||
if (String(seg.ecdsa).startsWith("Sim") || String(seg.ecdsa).startsWith("Yes") || String(seg.ecdsa).startsWith("Sí") || String(seg.ecdsa).startsWith("Oui") || String(seg.ecdsa).startsWith("Ja")) {
|
||||
return isDe ? "Hardware-ECDSA" : isFr ? "ECDSA matériel" : isEs ? "ECDSA en hardware" : isEn ? "Hardware ECDSA" : "ECDSA em hardware";
|
||||
}
|
||||
if (String(seg.ecc).startsWith("Sim") || String(seg.ecc).startsWith("Yes") || String(seg.ecc).startsWith("Sí")) {
|
||||
return isEs ? "ECC en hardware" : isEn ? "Hardware ECC" : "ECC em hardware";
|
||||
if (String(seg.ecc).startsWith("Sim") || String(seg.ecc).startsWith("Yes") || String(seg.ecc).startsWith("Sí") || String(seg.ecc).startsWith("Oui") || String(seg.ecc).startsWith("Ja")) {
|
||||
return isDe ? "Hardware-ECC" : isFr ? "ECC matériel" : isEs ? "ECC en hardware" : isEn ? "Hardware ECC" : "ECC em hardware";
|
||||
}
|
||||
if (String(seg.aes).startsWith("AES")) return "AES + SHA";
|
||||
return isEs ? "Solo SHA" : isEn ? "SHA only" : "Só SHA";
|
||||
return isDe ? "Nur SHA" : isFr ? "SHA uniquement" : isEs ? "Solo SHA" : isEn ? "SHA only" : "Só SHA";
|
||||
}
|
||||
|
||||
const simPt = (v) => !String(v).includes("Não");
|
||||
const simEn = (v) => !String(v).includes("No") && !String(v).includes("Não");
|
||||
const simEs = (v) => !String(v).includes("No") && !String(v).includes("Não");
|
||||
const simFr = (v) => !String(v).includes("Non") && !String(v).includes("No") && !String(v).includes("Não");
|
||||
const simDe = (v) => !String(v).includes("Nein") && !String(v).includes("No") && !String(v).includes("Não");
|
||||
|
||||
export default function Series() {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const currentLocale = isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const filtros = isEs ? FILTROS_ES : isEn ? FILTROS_EN : FILTROS_PT;
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const currentLocale = isDe ? "de" : isFr ? "fr" : isEs ? "es" : isEn ? "en" : "pt";
|
||||
const seriesData = isDe ? seriesDataDe : isFr ? seriesDataFr : isEs ? seriesDataEs : isEn ? seriesDataEn : seriesDataPt;
|
||||
const filtros = isDe ? FILTROS_DE : isFr ? FILTROS_FR : isEs ? FILTROS_ES : isEn ? FILTROS_EN : FILTROS_PT;
|
||||
|
||||
const [filtro, setFiltro] = useState("todas");
|
||||
const todas = Object.entries(seriesData);
|
||||
@@ -84,12 +106,28 @@ export default function Series() {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Series" : isEn ? "Series" : "Séries" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isDe ? "Serien" : isFr ? "Séries" : isEs ? "Series" : isEn ? "Series" : "Séries" }]}
|
||||
icon={Compass}
|
||||
label={isEs ? `${todas.length} familias de Espressif` : isEn ? `${todas.length} Espressif families` : `${todas.length} famílias da Espressif`}
|
||||
title={isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32"}
|
||||
label={
|
||||
isDe
|
||||
? `${todas.length} Espressif-Familien`
|
||||
: isFr
|
||||
? `${todas.length} familles d'Espressif`
|
||||
: isEs
|
||||
? `${todas.length} familias de Espressif`
|
||||
: isEn
|
||||
? `${todas.length} Espressif families`
|
||||
: `${todas.length} famílias da Espressif`
|
||||
}
|
||||
title={isDe ? "ESP32-Serien" : isFr ? "Séries ESP32" : isEs ? "Series ESP32" : isEn ? "ESP32 Series" : "Séries ESP32"}
|
||||
lede={
|
||||
isEs
|
||||
isDe
|
||||
? "Jede Serie wurde für einen bestimmten Projekttyp entwickelt, von Batteriesensoren bis hin zu KI-Beschleunigern. Öffnen Sie das Datenblatt für Pinbelegung, Peripherie und Sicherheit."
|
||||
: isFr
|
||||
? "Chaque série a été conçue pour un type de projet spécifique, des capteurs sur batterie aux accélérateurs IA. Ouvrez la fiche pour consulter le brochage, les périphériques et la sécurité."
|
||||
: isEs
|
||||
? "Cada serie fue diseñada para un tipo de proyecto específico, desde sensores a batería hasta aceleradores de IA. Abra la ficha para ver patillaje, periféricos y seguridad."
|
||||
: isEn
|
||||
? "Each series was designed for a specific project type, from battery-powered sensors to AI accelerators. Open the sheet to see pinout, peripherals, and security."
|
||||
@@ -97,8 +135,8 @@ export default function Series() {
|
||||
}
|
||||
/>
|
||||
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isEs ? "Lista de series" : isEn ? "Series list" : "Lista de séries"}>
|
||||
<div role="group" aria-label={isEs ? "Filtrar series" : isEn ? "Filter series" : "Filtrar séries"} className="flex flex-wrap gap-2">
|
||||
<section className="shell pt-10 sm:pt-12" aria-label={isDe ? "Serienliste" : isFr ? "Liste des séries" : isEs ? "Lista de series" : isEn ? "Series list" : "Lista de séries"}>
|
||||
<div role="group" aria-label={isDe ? "Serien filtern" : isFr ? "Filtrer les séries" : isEs ? "Filtrar series" : isEn ? "Filter series" : "Filtrar séries"} className="flex flex-wrap gap-2">
|
||||
{filtros.map((f) => (
|
||||
<button key={f.id} type="button" aria-pressed={filtro === f.id} onClick={() => setFiltro(f.id)} className="chip-btn">
|
||||
{f.rotulo}
|
||||
@@ -106,13 +144,50 @@ export default function Series() {
|
||||
))}
|
||||
</div>
|
||||
<p role="status" aria-live="polite" className="mt-4 text-sm text-muted">
|
||||
{series.length} {series.length === 1 ? (isEs ? "serie" : isEn ? "series" : "série") : (isEs ? "series" : isEn ? "series" : "séries")}
|
||||
{series.length}{" "}
|
||||
{series.length === 1
|
||||
? isDe
|
||||
? "Serie"
|
||||
: isFr
|
||||
? "série"
|
||||
: isEs
|
||||
? "serie"
|
||||
: isEn
|
||||
? "series"
|
||||
: "série"
|
||||
: isDe
|
||||
? "Serien"
|
||||
: isFr
|
||||
? "séries"
|
||||
: isEs
|
||||
? "series"
|
||||
: isEn
|
||||
? "series"
|
||||
: "séries"}
|
||||
</p>
|
||||
|
||||
<div className="mt-4 grid gap-4 md:grid-cols-2 lg:grid-cols-3">
|
||||
{series.map(([key, serie]) => {
|
||||
const riscv = serie.arquitetura.includes("RISC-V");
|
||||
const fatos = isEs
|
||||
const fatos = isDe
|
||||
? [
|
||||
["Kerne", serie.nucleos],
|
||||
["Taktfrequenz", serie.frequencia],
|
||||
["SRAM", serie.memoria_sram],
|
||||
["Wi-Fi", simDe(serie.wifi) ? "Ja" : "Nein"],
|
||||
["Bluetooth", String(serie.bluetooth).includes("Nein") || String(serie.bluetooth).includes("No") || String(serie.bluetooth).includes("Não") ? "Nein" : "Ja"],
|
||||
serie.consumo_energia?.deep_sleep ? ["Deep sleep", serie.consumo_energia.deep_sleep] : null,
|
||||
].filter(Boolean)
|
||||
: isFr
|
||||
? [
|
||||
["Cœurs", serie.nucleos],
|
||||
["Fréquence", serie.frequencia],
|
||||
["SRAM", serie.memoria_sram],
|
||||
["Wi-Fi", simFr(serie.wifi) ? "Oui" : "Non"],
|
||||
["Bluetooth", String(serie.bluetooth).includes("Non") || String(serie.bluetooth).includes("No") || String(serie.bluetooth).includes("Não") ? "Non" : "Oui"],
|
||||
serie.consumo_energia?.deep_sleep ? ["Deep sleep", serie.consumo_energia.deep_sleep] : null,
|
||||
].filter(Boolean)
|
||||
: isEs
|
||||
? [
|
||||
["Núcleos", serie.nucleos],
|
||||
["Frecuencia", serie.frequencia],
|
||||
@@ -150,7 +225,7 @@ export default function Series() {
|
||||
{fatos.map(([rotulo, valor]) => (
|
||||
<div key={rotulo} className="flex items-baseline justify-between gap-4 py-2">
|
||||
<dt className="text-muted">{rotulo}</dt>
|
||||
<dd className={`text-right font-medium ${valor === "Não" || valor === "No" ? "text-muted" : "text-ink"}`}>{valor}</dd>
|
||||
<dd className={`text-right font-medium ${valor === "Não" || valor === "No" || valor === "Non" || valor === "Nein" ? "text-muted" : "text-ink"}`}>{valor}</dd>
|
||||
</div>
|
||||
))}
|
||||
</dl>
|
||||
@@ -159,14 +234,14 @@ export default function Series() {
|
||||
{serie.aceleradores_ia && (
|
||||
<li className="chip chip-accent">
|
||||
<Sparkles className="h-3 w-3" aria-hidden="true" />
|
||||
{isEs ? "Aceleradores de IA" : isEn ? "AI Accelerators" : "Aceleradores de IA"}
|
||||
{isDe ? "KI-Beschleuniger" : isFr ? "Accélérateurs IA" : isEs ? "Aceleradores de IA" : isEn ? "AI Accelerators" : "Aceleradores de IA"}
|
||||
</li>
|
||||
)}
|
||||
<li className="chip">
|
||||
<ShieldCheck className="h-3 w-3 text-accent" aria-hidden="true" />
|
||||
{nivelSeguranca(serie, isEn, isEs)}
|
||||
{nivelSeguranca(serie, isEn, isEs, isFr, isDe)}
|
||||
</li>
|
||||
{(serie.matter === "Sim" || serie.matter === "Yes" || serie.matter === "Sí") && (
|
||||
{(serie.matter === "Sim" || serie.matter === "Yes" || serie.matter === "Sí" || serie.matter === "Oui" || serie.matter === "Ja") && (
|
||||
<li className="chip">
|
||||
<Home className="h-3 w-3 text-accent" aria-hidden="true" />
|
||||
Matter
|
||||
@@ -175,13 +250,13 @@ export default function Series() {
|
||||
{serie.status_documentacao && (
|
||||
<li className="chip">
|
||||
<AlertTriangle className="h-3 w-3 text-gold" aria-hidden="true" />
|
||||
{isEs ? "Documentación preliminar" : isEn ? "Preliminary documentation" : "Documentação preliminar"}
|
||||
{isDe ? "Vorläufige Dokumentation" : isFr ? "Documentation préliminaire" : isEs ? "Documentación preliminar" : isEn ? "Preliminary documentation" : "Documentação preliminar"}
|
||||
</li>
|
||||
)}
|
||||
</ul>
|
||||
|
||||
<span className="mt-5 inline-flex items-center gap-1 text-sm font-medium text-accent">
|
||||
{isEs ? "Abrir ficha" : isEn ? "Open datasheet" : "Abrir ficha"}
|
||||
{isDe ? "Datenblatt öffnen" : isFr ? "Ouvrir la fiche" : isEs ? "Abrir ficha" : isEn ? "Open datasheet" : "Abrir ficha"}
|
||||
<ArrowUpRight className="h-4 w-4 transition-transform group-hover:-translate-y-0.5 group-hover:translate-x-0.5" aria-hidden="true" />
|
||||
</span>
|
||||
</Link>
|
||||
@@ -194,10 +269,14 @@ export default function Series() {
|
||||
<div className="panel flex flex-col items-start justify-between gap-6 p-7 sm:p-10 md:flex-row md:items-center">
|
||||
<div className="max-w-2xl">
|
||||
<h2 className="section-title">
|
||||
{isEs ? "¿Tiene dudas entre dos series?" : isEn ? "Unsure between two series?" : "Ficou em dúvida entre duas séries?"}
|
||||
{isDe ? "Unsicher zwischen zwei Serien?" : isFr ? "Vous hésitez entre deux séries ?" : isEs ? "¿Tiene dudas entre dos series?" : isEn ? "Unsure between two series?" : "Ficou em dúvida entre duas séries?"}
|
||||
</h2>
|
||||
<p className="mt-3 text-base text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Der Vergleicher stellt bis zu vier Modelle gegenüber: Kerne, Funk, Speicher, Peripherie und Sicherheit."
|
||||
: isFr
|
||||
? "Le comparateur place jusqu'à quatre modèles côte à côte : cœurs, radio, mémoire, périphériques et sécurité."
|
||||
: isEs
|
||||
? "El comparador coloca hasta cuatro modelos lado a lado: núcleos, radio, memoria, periféricos y seguridad."
|
||||
: isEn
|
||||
? "The comparator tool puts up to four models side by side: cores, radio, memory, peripherals, and security."
|
||||
@@ -206,7 +285,7 @@ export default function Series() {
|
||||
</div>
|
||||
<Link href={getLocalizedHref("/comparacao", currentLocale)} className="btn btn-primary shrink-0">
|
||||
<Scale className="h-4 w-4" aria-hidden="true" />
|
||||
{isEs ? "Comparar series" : isEn ? "Compare series" : "Comparar séries"}
|
||||
{isDe ? "Serien vergleichen" : isFr ? "Comparer les séries" : isEs ? "Comparar series" : isEn ? "Compare series" : "Comparar séries"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
+116
-26
@@ -12,15 +12,33 @@ export async function generateMetadata({ params }) {
|
||||
const { locale } = await params;
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
return paginaMeta({
|
||||
titulo: isEs ? "Acerca del proyecto" : isEn ? "About the Project" : "Sobre o projeto",
|
||||
descricao: isEs
|
||||
titulo: isDe
|
||||
? "Über das Projekt"
|
||||
: isFr
|
||||
? "À propos du projet"
|
||||
: isEs
|
||||
? "Acerca del proyecto"
|
||||
: isEn
|
||||
? "About the Project"
|
||||
: "Sobre o projeto",
|
||||
descricao: isDe
|
||||
? "ESPDocs ist eine unabhängige Plattform, die die technische Dokumentation des ESP32-Ökosystems strukturiert. Erfahren Sie mehr über das Projekt und wie Sie beitragen können."
|
||||
: isFr
|
||||
? "ESPDocs est une plateforme indépendante qui organise la documentation technique de l'écosystème ESP32. Découvrez le projet et comment contribuer."
|
||||
: isEs
|
||||
? "ESPDocs es una plataforma independiente que organiza la documentación técnica del ecosistema ESP32. Conozca el proyecto y cómo contribuir."
|
||||
: isEn
|
||||
? "ESPDocs is an independent platform organizing technical documentation of the ESP32 ecosystem. Learn about the project and how to contribute."
|
||||
: "O ESPDocs é uma plataforma independente que reúne a documentação do ecossistema ESP32 em português brasileiro. Saiba como o projeto nasceu e como contribuir.",
|
||||
caminho: "/sobre",
|
||||
keywords: isEs
|
||||
keywords: isDe
|
||||
? ["ESPDocs", "ESP32 Dokumentation", "ESP32 Open-Source-Projekt", "Open Source"]
|
||||
: isFr
|
||||
? ["ESPDocs", "documentation ESP32", "projet open source ESP32", "open source"]
|
||||
: isEs
|
||||
? ["ESPDocs", "documentación ESP32", "proyecto open source ESP32", "código abierto"]
|
||||
: isEn
|
||||
? ["ESPDocs", "ESP32 documentation", "open source ESP32 project"]
|
||||
@@ -34,6 +52,8 @@ export default async function Sobre({ params }) {
|
||||
const isPt = locale === "pt";
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
|
||||
const featuresPt = [
|
||||
{ icon: Languages, title: "Em português", desc: "Dados técnicos organizados e apresentados em português do Brasil." },
|
||||
@@ -56,7 +76,21 @@ export default async function Sobre({ params }) {
|
||||
{ icon: Code, title: "Código abierto", desc: "Las contribuciones son bienvenidas en Gitea." },
|
||||
];
|
||||
|
||||
const features = isEs ? featuresEs : isEn ? featuresEn : featuresPt;
|
||||
const featuresFr = [
|
||||
{ icon: Languages, title: "En français", desc: "Données techniques organisées et présentées clairement en français." },
|
||||
{ icon: GitCompare, title: "Comparaisons visuelles", desc: "Tableaux et schémas pour choisir la bonne série sans ouvrir dix datasheets." },
|
||||
{ icon: Globe, title: "Accès centralisé", desc: "Liens directs vers la documentation officielle, les dépôts et les exemples." },
|
||||
{ icon: Code, title: "Open source", desc: "Les contributions sont les bienvenues sur Gitea." },
|
||||
];
|
||||
|
||||
const featuresDe = [
|
||||
{ icon: Languages, title: "Auf Deutsch", desc: "Technische Daten übersichtlich und strukturiert auf Deutsch aufbereitet." },
|
||||
{ icon: GitCompare, title: "Visuelle Vergleiche", desc: "Tabellen und Diagramme zur Auswahl der richtigen Serie, ohne zehn Datenblätter zu öffnen." },
|
||||
{ icon: Globe, title: "Zentraler Zugang", desc: "Direkte Links zu offizieller Dokumentation, Repositories und Beispielen." },
|
||||
{ icon: Code, title: "Open Source", desc: "Beiträge sind auf Gitea herzlich willkommen." },
|
||||
];
|
||||
|
||||
const features = isDe ? featuresDe : isFr ? featuresFr : isEs ? featuresEs : isEn ? featuresEn : featuresPt;
|
||||
|
||||
return (
|
||||
<div className="site-canvas min-h-screen">
|
||||
@@ -70,8 +104,8 @@ export default async function Sobre({ params }) {
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: JSON.stringify(
|
||||
jsonLd.trilha([
|
||||
{ nome: isEs ? "Inicio" : isPt ? "Início" : "Home", caminho: isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isEs ? "Acerca del proyecto" : isPt ? "Sobre o Projeto" : "About the Project", caminho: isEn ? "/en/about" : isEs ? "/es/acerca" : "/sobre" },
|
||||
{ nome: isDe ? "Startseite" : isFr ? "Accueil" : isEs ? "Inicio" : isPt ? "Início" : "Home", caminho: isDe ? "/de" : isFr ? "/fr" : isEn ? "/en" : isEs ? "/es" : "/" },
|
||||
{ nome: isDe ? "Über das Projekt" : isFr ? "À propos du projet" : isEs ? "Acerca del proyecto" : isPt ? "Sobre o Projeto" : "About the Project", caminho: isDe ? "/de/ueber-uns" : isFr ? "/fr/a-propos" : isEn ? "/en/about" : isEs ? "/es/acerca" : "/sobre" },
|
||||
])
|
||||
),
|
||||
}}
|
||||
@@ -83,12 +117,18 @@ export default async function Sobre({ params }) {
|
||||
<PageHero
|
||||
isEn={isEn}
|
||||
isEs={isEs}
|
||||
trail={[{ label: isEs ? "Acerca" : isPt ? "Sobre" : "About" }]}
|
||||
isFr={isFr}
|
||||
isDe={isDe}
|
||||
trail={[{ label: isDe ? "Über uns" : isFr ? "À propos" : isEs ? "Acerca" : isPt ? "Sobre" : "About" }]}
|
||||
icon={Info}
|
||||
label={isEs ? "Proyecto independiente" : isPt ? "Projeto independente" : "Independent project"}
|
||||
title={isEs ? "Acerca de ESPDocs" : isPt ? "Sobre o ESPDocs" : "About ESPDocs"}
|
||||
label={isDe ? "Unabhängiges Projekt" : isFr ? "Projet indépendant" : isEs ? "Proyecto independiente" : isPt ? "Projeto independente" : "Independent project"}
|
||||
title={isDe ? "Über ESPDocs" : isFr ? "À propos d'ESPDocs" : isEs ? "Acerca de ESPDocs" : isPt ? "Sobre o ESPDocs" : "About ESPDocs"}
|
||||
lede={
|
||||
isEs
|
||||
isDe
|
||||
? "Eine inoffizielle deutschsprachige Plattform, die technische Informationen zum ESP32 strukturiert und Sie mit der offiziellen Dokumentation von Espressif verbindet. Entwickelt für die Open-Hardware-Community."
|
||||
: isFr
|
||||
? "Une plateforme non officielle en français qui organise les informations techniques de l'ESP32 et vous oriente vers la documentation officielle d'Espressif. Conçue pour la communauté du matériel libre."
|
||||
: isEs
|
||||
? "Una plataforma no oficial, en español, que organiza la información técnica del ESP32 y le conecta con la documentación oficial de Espressif. Creada para la comunidad de hardware abierto."
|
||||
: isPt
|
||||
? "Uma plataforma não oficial, em português, que organiza as informações técnicas do ESP32 e leva você à documentação oficial da Espressif. Feita para a comunidade de hardware livre."
|
||||
@@ -97,7 +137,7 @@ export default async function Sobre({ params }) {
|
||||
>
|
||||
<a href={REPOSITORIO} target="_blank" rel="noopener noreferrer" className="btn btn-primary">
|
||||
<GiteaMark className="h-4 w-4" />
|
||||
{isEs ? "Ver el repositorio" : isPt ? "Ver o repositório" : "View repository"}
|
||||
{isDe ? "Repository ansehen" : isFr ? "Voir le dépôt" : isEs ? "Ver el repositorio" : isPt ? "Ver o repositório" : "View repository"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
</PageHero>
|
||||
@@ -105,9 +145,13 @@ export default async function Sobre({ params }) {
|
||||
<div className="shell section grid grid-cols-1 gap-10 pt-12 sm:pt-16 lg:grid-cols-[1fr_22rem] lg:gap-14">
|
||||
<div className="min-w-0 max-w-3xl space-y-12">
|
||||
<section aria-labelledby="missao">
|
||||
<h2 id="missao" className="section-title">{isEs ? "Misión" : isPt ? "Missão" : "Mission"}</h2>
|
||||
<h2 id="missao" className="section-title">{isDe ? "Mission" : isFr ? "Mission" : isEs ? "Misión" : isPt ? "Missão" : "Mission"}</h2>
|
||||
<p className="mt-4 text-base leading-relaxed text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Den Zugang zum und das Verständnis für das ESP32-Ökosystem durch eine deutsche Oberfläche erleichtern, die Spezifikationen bündelt, Serien vergleicht, Frameworks vorstellt und offizielle Dokumentationslinks zentralisiert. Ziel ist es, Entwicklungszeit bei Firmware und IoT-Projekten zu sparen."
|
||||
: isFr
|
||||
? "Faciliter l'accès et la compréhension de l'écosystème ESP32 avec une interface en français qui organise les spécifications, compare les séries, présente les frameworks et centralise les liens vers la documentation officielle. L'objectif est de vous faire gagner du temps dans le développement de firmware et d'IoT."
|
||||
: isEs
|
||||
? "Facilitar el acceso y la comprensión del ecosistema ESP32 con una interfaz en español que organiza especificaciones, compara series, presenta frameworks y centraliza los enlaces a la documentación oficial. El objetivo es ahorrar tiempo en el desarrollo de firmware e IoT."
|
||||
: isPt
|
||||
? "Facilitar o acesso e a compreensão do ecossistema ESP32 com uma interface em português que organiza especificações, compara séries, apresenta frameworks e centraliza os links da documentação oficial. O objetivo é economizar o seu tempo no desenvolvimento de firmware e IoT."
|
||||
@@ -116,9 +160,13 @@ export default async function Sobre({ params }) {
|
||||
</section>
|
||||
|
||||
<section aria-labelledby="porque">
|
||||
<h2 id="porque" className="section-title">{isEs ? "¿Por qué existe ESPDocs?" : isPt ? "Por que o ESPDocs existe" : "Why ESPDocs exists"}</h2>
|
||||
<h2 id="porque" className="section-title">{isDe ? "Warum es ESPDocs gibt" : isFr ? "Pourquoi ESPDocs existe" : isEs ? "¿Por qué existe ESPDocs?" : isPt ? "Por que o ESPDocs existe" : "Why ESPDocs exists"}</h2>
|
||||
<p className="mt-4 text-base leading-relaxed text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Informationen über den ESP32 sind oft über dichte Datenblätter, technische Referenzhandbücher (TRM) und sekundäre Repositories verstreut. ESPDocs verdichtet und strukturiert diese Daten für eine schnelle Vorabauswahl, bevor Sie tiefer in die offizielle Technik einsteigen."
|
||||
: isFr
|
||||
? "Les informations sur l'ESP32 sont souvent dispersées entre des fiches techniques denses, des manuels de référence technique (TRM) et des dépôts secondaires. ESPDocs condense et structure ces données pour une évaluation rapide avant d'approfondir l'ingénierie officielle."
|
||||
: isEs
|
||||
? "La información sobre el ESP32 suele estar dispersa entre hojas de datos densas, manuales de referencia técnica (TRM) y repositorios secundarios. ESPDocs condensa y estructura estos datos para una evaluación rápida antes de profundizar en la ingeniería oficial."
|
||||
: isPt
|
||||
? "As informações sobre os ESP32 costumam estar espalhadas entre datasheets densos, manuais de referência (TRM) e repositórios secundários, tudo em inglês. O ESPDocs condensa e estrutura esses dados para a triagem rápida, antes de você aprofundar na engenharia oficial."
|
||||
@@ -140,16 +188,32 @@ export default async function Sobre({ params }) {
|
||||
</section>
|
||||
|
||||
<section aria-labelledby="contribuir">
|
||||
<h2 id="contribuir" className="section-title">{isEs ? "Cómo contribuir" : isPt ? "Como contribuir" : "How to contribute"}</h2>
|
||||
<h2 id="contribuir" className="section-title">{isDe ? "Wie Sie beitragen können" : isFr ? "Comment contribuer" : isEs ? "Cómo contribuir" : isPt ? "Como contribuir" : "How to contribute"}</h2>
|
||||
<p className="mt-4 text-base leading-relaxed text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "Übersetzungskorrekturen, Tabellenanpassungen und neue Codebeispiele sind herzlich willkommen. Das Projekt wächst gemeinsam mit der Community."
|
||||
: isFr
|
||||
? "Les corrections de traduction, les ajustements de tableaux et les nouveaux exemples de code sont très appréciés. Le projet grandit avec la communauté."
|
||||
: isEs
|
||||
? "Las correcciones de traducción, ajustes en tablas y nuevos ejemplos de código son muy bienvenidos. El proyecto crece junto con la comunidad."
|
||||
: isPt
|
||||
? "Correções de tradução, ajustes em tabelas e novos exemplos de código são muito bem-vindos. O projeto cresce com a comunidade."
|
||||
: "Translation fixes, table refinements and new code examples are welcome. The project grows with the community."}
|
||||
</p>
|
||||
<ol className="mt-6 space-y-3">
|
||||
{(isEs
|
||||
{(isDe
|
||||
? [
|
||||
"Erstellen Sie einen Fork des Repositories auf Gitea.",
|
||||
"Implementieren Sie die Verbesserungen und prüfen Sie die offiziellen technischen Referenzen.",
|
||||
"Eröffnen Sie einen Pull Request mit einer Beschreibung der vorgenommenen Änderungen.",
|
||||
]
|
||||
: isFr
|
||||
? [
|
||||
"Forkez le dépôt sur Gitea.",
|
||||
"Apportez les améliorations et vérifiez les références techniques officielles.",
|
||||
"Ouvrez une Pull Request décrivant les modifications apportées.",
|
||||
]
|
||||
: isEs
|
||||
? [
|
||||
"Haga un fork del repositorio en Gitea.",
|
||||
"Implemente las mejoras y verifique las referencias técnicas oficiales.",
|
||||
@@ -178,9 +242,13 @@ export default async function Sobre({ params }) {
|
||||
</section>
|
||||
|
||||
<section aria-labelledby="acessibilidade">
|
||||
<h2 id="acessibilidade" className="section-title">{isEs ? "Accesibilidad" : isPt ? "Acessibilidade" : "Accessibility"}</h2>
|
||||
<h2 id="acessibilidade" className="section-title">{isDe ? "Barrierefreiheit" : isFr ? "Accessibilité" : isEs ? "Accesibilidad" : isPt ? "Acessibilidade" : "Accessibility"}</h2>
|
||||
<p className="mt-4 text-base leading-relaxed text-muted">
|
||||
{isEs
|
||||
{isDe
|
||||
? "ESPDocs legt großen Wert auf Lesbarkeit, hohen Kontrast (WCAG-Stufe AAA) und vollständige Tastaturnavigation. Wenn Sie auf Lese- oder Navigationsbarrieren stoßen, eröffnen Sie bitte ein Issue im Repository."
|
||||
: isFr
|
||||
? "ESPDocs privilégie la lisibilité, un contraste élevé (niveau AAA du WCAG) et une navigation complète au clavier. Si vous rencontrez un obstacle de lecture ou de navigation, ouvrez un ticket dans le dépôt."
|
||||
: isEs
|
||||
? "ESPDocs prioriza la legibilidad, el alto contraste (nivel AAA de WCAG) y la navegación completa por teclado. Si encuentra alguna barrera de lectura o navegación, abra un issue en el repositorio."
|
||||
: isPt
|
||||
? "O ESPDocs prioriza a legibilidade, o contraste alto (nível AAA da WCAG) e a navegação completa por teclado. Se encontrar alguma barreira de leitura ou navegação, abra uma issue no repositório."
|
||||
@@ -189,7 +257,7 @@ export default async function Sobre({ params }) {
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<aside className="space-y-5 lg:sticky lg:top-28 lg:self-start" aria-label={isEs ? "Autor y aviso legal" : isPt ? "Autor e aviso legal" : "Author and legal notice"}>
|
||||
<aside className="space-y-5 lg:sticky lg:top-28 lg:self-start" aria-label={isDe ? "Autor und rechtlicher Hinweis" : isFr ? "Auteur et mentions légales" : isEs ? "Autor y aviso legal" : isPt ? "Autor e aviso legal" : "Author and legal notice"}>
|
||||
<div className="panel p-6 sm:p-7">
|
||||
<div className="flex items-center gap-4">
|
||||
<span className="grid h-16 w-16 shrink-0 place-items-center rounded-2xl border border-line bg-white">
|
||||
@@ -197,11 +265,29 @@ export default async function Sobre({ params }) {
|
||||
</span>
|
||||
<div>
|
||||
<h2 className="font-display text-lg font-semibold text-ink">Lucas Rayan Guerra</h2>
|
||||
<p className="text-sm text-muted">{isEs ? "Creador de Ciência Embarcada" : isPt ? "Criador do Ciência Embarcada" : "Creator of Ciência Embarcada"}</p>
|
||||
<p className="text-sm text-muted">{isDe ? "Gründer von Ciência Embarcada" : isFr ? "Créateur de Ciência Embarcada" : isEs ? "Creador de Ciência Embarcada" : isPt ? "Criador do Ciência Embarcada" : "Creator of Ciência Embarcada"}</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="mt-5 space-y-3 text-sm leading-relaxed text-muted">
|
||||
{isEs ? (
|
||||
{isDe ? (
|
||||
<>
|
||||
<p>
|
||||
Systementwicklungstechniker, Informatikstudent an der UFRPE und Forscher im Bereich Blockchain und Kryptographie.
|
||||
</p>
|
||||
<p>
|
||||
Software-Direktor bei Semine AgriTech und Referent bei Veranstaltungen wie REC'n'Play, der Inhalte zu Hardware, IoT und Cybersicherheit vermittelt.
|
||||
</p>
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
<p>
|
||||
Technicien en développement de systèmes, étudiant en informatique à l'UFRPE et chercheur en blockchain et cryptographie.
|
||||
</p>
|
||||
<p>
|
||||
Directeur logiciel chez Semine AgriTech et conférencier lors d'événements comme REC'n'Play, partageant des connaissances sur le matériel, l'IoT et la cybersécurité.
|
||||
</p>
|
||||
</>
|
||||
) : isEs ? (
|
||||
<>
|
||||
<p>
|
||||
Técnico en Desarrollo de Sistemas, estudiante de Ciencias de la Computación en la UFRPE e investigador en Blockchain y Criptografía.
|
||||
@@ -233,15 +319,19 @@ export default async function Sobre({ params }) {
|
||||
)}
|
||||
</div>
|
||||
<a href="https://cienciaembarcada.com.br" target="_blank" rel="noopener noreferrer" className="btn btn-ghost mt-6 w-full">
|
||||
{isEs ? "Visitar Ciência Embarcada" : isPt ? "Visitar o Ciência Embarcada" : "Visit Ciência Embarcada"}
|
||||
{isDe ? "Ciência Embarcada besuchen" : isFr ? "Visiter Ciência Embarcada" : isEs ? "Visitar Ciência Embarcada" : isPt ? "Visitar o Ciência Embarcada" : "Visit Ciência Embarcada"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div className="callout callout-warn">
|
||||
<p className="font-semibold text-ink">{isEs ? "Aviso legal" : isPt ? "Aviso legal" : "Legal notice"}</p>
|
||||
<p className="font-semibold text-ink">{isDe ? "Rechtlicher Hinweis" : isFr ? "Mentions légales" : isEs ? "Aviso legal" : isPt ? "Aviso legal" : "Legal notice"}</p>
|
||||
<p className="mt-1">
|
||||
{isEs
|
||||
{isDe
|
||||
? "ESPDocs ist ein Aggregator und Kurator. Die referenzierten Handbücher und Repositories sind Eigentum von Espressif Systems. Konsultieren Sie bei geschäftskritischen oder kommerziellen Projekten stets die offizielle Dokumentation."
|
||||
: isFr
|
||||
? "ESPDocs est une plateforme d'agrégation et de synthèse. Les manuels et dépôts référencés appartiennent à Espressif Systems. Pour les projets critiques ou commerciaux, consultez systématiquement la documentation officielle."
|
||||
: isEs
|
||||
? "ESPDocs es un agregador y organizador. Los manuales y repositorios referenciados pertenecen a Espressif Systems. En proyectos críticos o comerciales, consulte siempre la documentación oficial."
|
||||
: isPt
|
||||
? "O ESPDocs é um agregador e organizador. Os manuais e repositórios referenciados pertencem à Espressif Systems. Em projetos críticos ou comerciais, consulte sempre a documentação oficial."
|
||||
|
||||
@@ -3,12 +3,12 @@ import { construirIndiceBusca } from "@/lib/searchIndex";
|
||||
export const dynamic = "force-static";
|
||||
|
||||
export function generateStaticParams() {
|
||||
return [{ locale: "pt" }, { locale: "en" }, { locale: "es" }];
|
||||
return [{ locale: "pt" }, { locale: "en" }, { locale: "es" }, { locale: "fr" }, { locale: "de" }];
|
||||
}
|
||||
|
||||
export async function GET(request, { params }) {
|
||||
const { locale } = await params;
|
||||
const loc = locale === "en" ? "en" : locale === "es" ? "es" : "pt";
|
||||
const loc = ["en", "es", "fr", "de"].includes(locale) ? locale : "pt";
|
||||
return Response.json(construirIndiceBusca(loc), {
|
||||
headers: {
|
||||
"Cache-Control": "no-cache, no-store, must-revalidate",
|
||||
|
||||
@@ -41,10 +41,50 @@ const HEADER_MAP_ES = {
|
||||
"LEDs": "LEDs",
|
||||
};
|
||||
|
||||
const HEADER_MAP_FR = {
|
||||
"Nome": "Nom",
|
||||
"Descrição": "Description",
|
||||
"Série": "Série",
|
||||
"Loja Oficial": "Boutique officielle",
|
||||
"Fabricante": "Fabricant",
|
||||
"Processador": "Processeur",
|
||||
"Memória Flash": "Mémoire flash",
|
||||
"PSRAM": "PSRAM",
|
||||
"Conector USB": "Connecteur USB",
|
||||
"Interface USB": "Interface USB",
|
||||
"Antena": "Antenne",
|
||||
"Bateria": "Batterie",
|
||||
"Display": "Écran",
|
||||
"Sensores": "Capteurs",
|
||||
"Botões": "Boutons",
|
||||
"LEDs": "LEDs",
|
||||
};
|
||||
|
||||
const HEADER_MAP_DE = {
|
||||
"Nome": "Name",
|
||||
"Descrição": "Beschreibung",
|
||||
"Série": "Serie",
|
||||
"Loja Oficial": "Offizieller Shop",
|
||||
"Fabricante": "Hersteller",
|
||||
"Processador": "Prozessor",
|
||||
"Memória Flash": "Flash-Speicher",
|
||||
"PSRAM": "PSRAM",
|
||||
"Conector USB": "USB-Anschluss",
|
||||
"Interface USB": "USB-Schnittstelle",
|
||||
"Antena": "Antenne",
|
||||
"Bateria": "Batterie",
|
||||
"Display": "Display",
|
||||
"Sensores": "Sensoren",
|
||||
"Botões": "Taster",
|
||||
"LEDs": "LEDs",
|
||||
};
|
||||
|
||||
export default function BoardCard({ board }) {
|
||||
const pathname = usePathname() || "";
|
||||
const isEn = pathname === "/en" || pathname.startsWith("/en/");
|
||||
const isEs = pathname === "/es" || pathname.startsWith("/es/");
|
||||
const isFr = pathname === "/fr" || pathname.startsWith("/fr/");
|
||||
const isDe = pathname === "/de" || pathname.startsWith("/de/");
|
||||
|
||||
const mainFields = ["Nome", "Link", "Imagem", "Loja Oficial"];
|
||||
|
||||
@@ -67,21 +107,31 @@ export default function BoardCard({ board }) {
|
||||
{lojaOficial && (
|
||||
<span className="chip chip-accent mb-3 w-fit">
|
||||
<Award className="h-3.5 w-3.5" aria-hidden="true" />
|
||||
{isEn ? "Official store" : isEs ? "Tienda oficial" : "Loja oficial"}
|
||||
{isEn ? "Official store" : isEs ? "Tienda oficial" : isFr ? "Boutique officielle" : isDe ? "Offizieller Shop" : "Loja oficial"}
|
||||
</span>
|
||||
)}
|
||||
|
||||
<h3 className="line-clamp-2 font-display text-lg font-semibold leading-snug tracking-[-0.02em] text-ink">
|
||||
{board.Nome || (isEn ? "Generic board" : isEs ? "Placa genérica" : "Placa genérica")}
|
||||
{board.Nome || (isEn ? "Generic board" : isEs ? "Placa genérica" : isFr ? "Carte générique" : isDe ? "Generisches Board" : "Placa genérica")}
|
||||
</h3>
|
||||
|
||||
{recursos.length > 0 && (
|
||||
<div className="mt-4">
|
||||
<p className="text-xs font-medium text-muted">{isEn ? "On-board features" : isEs ? "Recursos integrados" : "Recursos embarcados"}</p>
|
||||
<p className="text-xs font-medium text-muted">
|
||||
{isEn ? "On-board features" : isEs ? "Recursos integrados" : isFr ? "Fonctionnalités intégrées" : isDe ? "Integrierte Funktionen" : "Recursos embarcados"}
|
||||
</p>
|
||||
<ul className="mt-2 flex flex-wrap gap-1.5">
|
||||
{recursos.map((campo) => {
|
||||
const opcional = valor(campo) === "opcional";
|
||||
const label = isEn ? (HEADER_MAP_EN[campo] || campo) : isEs ? (HEADER_MAP_ES[campo] || campo) : campo;
|
||||
const label = isEn
|
||||
? (HEADER_MAP_EN[campo] || campo)
|
||||
: isEs
|
||||
? (HEADER_MAP_ES[campo] || campo)
|
||||
: isFr
|
||||
? (HEADER_MAP_FR[campo] || campo)
|
||||
: isDe
|
||||
? (HEADER_MAP_DE[campo] || campo)
|
||||
: campo;
|
||||
return (
|
||||
<li key={campo} className={`chip ${opcional ? "text-gold" : "text-ink-soft"}`}>
|
||||
{opcional ? (
|
||||
@@ -90,7 +140,7 @@ export default function BoardCard({ board }) {
|
||||
<Check className="h-3 w-3 text-ok" aria-hidden="true" />
|
||||
)}
|
||||
{label}
|
||||
{opcional && <span className="sr-only">{isEn ? " (optional)" : " (opcional)"}</span>}
|
||||
{opcional && <span className="sr-only">{isEn ? " (optional)" : isEs ? " (opcional)" : isFr ? " (optionnel)" : isDe ? " (optional)" : " (opcional)"}</span>}
|
||||
</li>
|
||||
);
|
||||
})}
|
||||
@@ -100,9 +150,11 @@ export default function BoardCard({ board }) {
|
||||
|
||||
{board.Link && (
|
||||
<a href={board.Link} target="_blank" rel="noopener noreferrer" className="btn btn-primary mt-6 w-full">
|
||||
{isEn ? "View on AliExpress" : isEs ? "Ver en AliExpress" : "Ver no AliExpress"}
|
||||
{isEn ? "View on AliExpress" : isEs ? "Ver en AliExpress" : isFr ? "Voir sur AliExpress" : isDe ? "Auf AliExpress ansehen" : "Ver no AliExpress"}
|
||||
<ArrowUpRight className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="sr-only">{isEn ? " (opens in new tab)" : isEs ? " (abre en una pestaña nueva)" : " (abre em nova aba)"}</span>
|
||||
<span className="sr-only">
|
||||
{isEn ? " (opens in new tab)" : isEs ? " (abre en una pestaña nueva)" : isFr ? " (ouvre un nouvel onglet)" : isDe ? " (öffnet in neuem Tab)" : " (abre em nova aba)"}
|
||||
</span>
|
||||
</a>
|
||||
)}
|
||||
</div>
|
||||
|
||||
+100
-10
@@ -8,7 +8,9 @@ export default function CodeExample({ framework }) {
|
||||
const pathname = usePathname() || "";
|
||||
const isEn = pathname === "/en" || pathname.startsWith("/en/");
|
||||
const isEs = pathname === "/es" || pathname.startsWith("/es/");
|
||||
const loc = isEn ? "en" : isEs ? "es" : "pt";
|
||||
const isFr = pathname === "/fr" || pathname.startsWith("/fr/");
|
||||
const isDe = pathname === "/de" || pathname.startsWith("/de/");
|
||||
const loc = isEn ? "en" : isEs ? "es" : isFr ? "fr" : isDe ? "de" : "pt";
|
||||
|
||||
const examplesUrl = framework?.exemplos;
|
||||
|
||||
@@ -31,6 +33,10 @@ export default function CodeExample({ framework }) {
|
||||
? `// Full examples: ${examplesUrl || "see repository"}\n`
|
||||
: isEs
|
||||
? `// Ejemplos completos: ${examplesUrl || "ver repositorio"}\n`
|
||||
: isFr
|
||||
? `// Exemples complets : ${examplesUrl || "voir le dépôt"}\n`
|
||||
: isDe
|
||||
? `// Vollständige Beispiele: ${examplesUrl || "Repository ansehen"}\n`
|
||||
: `// Exemplos completos: ${examplesUrl || "ver repositório"}\n`
|
||||
);
|
||||
return;
|
||||
@@ -70,9 +76,23 @@ export default function CodeExample({ framework }) {
|
||||
? "// The example file is empty. Refer to the official repository.\n"
|
||||
: isEs
|
||||
? "// El archivo de ejemplo está vacío. Consulte el repositorio oficial.\n"
|
||||
: isFr
|
||||
? "// Le fichier d'exemple est vide. Consultez le dépôt officiel.\n"
|
||||
: isDe
|
||||
? "// Die Beispieldatei ist leer. Bitte konsultieren Sie das offizielle Repository.\n"
|
||||
: "// O arquivo de exemplo está vazio. Consulte o repositório oficial.\n"
|
||||
);
|
||||
setError(isEn ? "empty file" : isEs ? "archivo vacío" : "arquivo vazio");
|
||||
setError(
|
||||
isEn
|
||||
? "empty file"
|
||||
: isEs
|
||||
? "archivo vacío"
|
||||
: isFr
|
||||
? "fichier vide"
|
||||
: isDe
|
||||
? "leere Datei"
|
||||
: "arquivo vazio"
|
||||
);
|
||||
}
|
||||
})
|
||||
.catch((err) => {
|
||||
@@ -82,9 +102,24 @@ export default function CodeExample({ framework }) {
|
||||
? "// Could not load example.\n// Refer to official repository for complete examples.\n"
|
||||
: isEs
|
||||
? "// No fue posible cargar el ejemplo.\n// Consulte el repositorio oficial para ver los ejemplos completos.\n"
|
||||
: isFr
|
||||
? "// Impossible de charger l'exemple.\n// Consultez le dépôt officiel pour des exemples complets.\n"
|
||||
: isDe
|
||||
? "// Beispiel konnte nicht geladen werden.\n// Vollständige Beispiele finden Sie im offiziellen Repository.\n"
|
||||
: "// Não foi possível carregar o exemplo.\n// Consulte o repositório oficial para exemplos completos.\n"
|
||||
);
|
||||
setError(err.message || (isEn ? "load failure" : isEs ? "fallo al cargar" : "falha ao carregar"));
|
||||
setError(
|
||||
err.message ||
|
||||
(isEn
|
||||
? "load failure"
|
||||
: isEs
|
||||
? "fallo al cargar"
|
||||
: isFr
|
||||
? "échec du chargement"
|
||||
: isDe
|
||||
? "Ladefehler"
|
||||
: "falha ao carregar")
|
||||
);
|
||||
})
|
||||
.finally(() => {
|
||||
if (!cancelled) setLoading(false);
|
||||
@@ -93,7 +128,7 @@ export default function CodeExample({ framework }) {
|
||||
return () => {
|
||||
cancelled = true;
|
||||
};
|
||||
}, [framework?.exemplo, framework?.exemplos, isEn, isEs, loc]);
|
||||
}, [framework?.exemplo, framework?.exemplos, isEn, isEs, isFr, isDe, loc]);
|
||||
|
||||
const lines = (sample || "").replace(/\n$/, "").split("\n");
|
||||
|
||||
@@ -110,13 +145,25 @@ export default function CodeExample({ framework }) {
|
||||
<div className="flex flex-wrap items-start justify-between gap-4">
|
||||
<div>
|
||||
<h2 className="font-display text-xl font-semibold tracking-[-0.03em] text-ink">
|
||||
{isEn ? "Code example" : isEs ? "Ejemplo de código" : "Exemplo de código"}
|
||||
{isEn
|
||||
? "Code example"
|
||||
: isEs
|
||||
? "Ejemplo de código"
|
||||
: isFr
|
||||
? "Exemple de code"
|
||||
: isDe
|
||||
? "Codebeispiel"
|
||||
: "Exemplo de código"}
|
||||
</h2>
|
||||
<p className="mt-1 text-sm text-muted">
|
||||
{isEn
|
||||
? `Starter snippet in ${framework?.linguagem}. Adjust pins and configuration for your board.`
|
||||
: isEs
|
||||
? `Fragmento de inicio en ${framework?.linguagem}. Ajuste los pines y la configuración para su placa.`
|
||||
: isFr
|
||||
? `Extrait de départ en ${framework?.linguagem}. Adaptez les broches et la configuration à votre carte.`
|
||||
: isDe
|
||||
? `Startbeispiel in ${framework?.linguagem}. Passen Sie Pins und Konfiguration an Ihr Board an.`
|
||||
: `Trecho de partida em ${framework?.linguagem}. Ajuste pinos e configuração à sua placa.`}
|
||||
</p>
|
||||
</div>
|
||||
@@ -124,13 +171,27 @@ export default function CodeExample({ framework }) {
|
||||
<div className="flex flex-wrap items-center gap-2">
|
||||
<button type="button" onClick={handleCopy} className="btn btn-ghost btn-sm">
|
||||
{copied ? <Check className="h-4 w-4 text-ok" aria-hidden="true" /> : <Copy className="h-4 w-4" aria-hidden="true" />}
|
||||
<span role="status">{copied ? (isEn ? "Copied" : isEs ? "Copiado" : "Copiado") : (isEn ? "Copy" : isEs ? "Copiar" : "Copiar")}</span>
|
||||
<span role="status">
|
||||
{copied
|
||||
? (isEn ? "Copied" : isEs ? "Copiado" : isFr ? "Copié" : isDe ? "Kopiert" : "Copiado")
|
||||
: (isEn ? "Copy" : isEs ? "Copiar" : isFr ? "Copier" : isDe ? "Kopieren" : "Copiar")}
|
||||
</span>
|
||||
</button>
|
||||
{examplesUrl && (
|
||||
<a href={examplesUrl} target="_blank" rel="noopener noreferrer" className="btn btn-ghost btn-sm">
|
||||
{isEn ? "More examples" : isEs ? "Más ejemplos" : "Mais exemplos"}
|
||||
{isEn ? "More examples" : isEs ? "Más ejemplos" : isFr ? "Plus d'exemples" : isDe ? "Weitere Beispiele" : "Mais exemplos"}
|
||||
<ExternalLink className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="sr-only">{isEn ? " (opens in new tab)" : isEs ? " (abre en una pestaña nueva)" : " (abre em nova aba)"}</span>
|
||||
<span className="sr-only">
|
||||
{isEn
|
||||
? " (opens in new tab)"
|
||||
: isEs
|
||||
? " (abre en una pestaña nueva)"
|
||||
: isFr
|
||||
? " (ouvre un nouvel onglet)"
|
||||
: isDe
|
||||
? " (öffnet in neuem Tab)"
|
||||
: " (abre em nova aba)"}
|
||||
</span>
|
||||
</a>
|
||||
)}
|
||||
</div>
|
||||
@@ -139,9 +200,34 @@ export default function CodeExample({ framework }) {
|
||||
<div className="code-panel mt-5" aria-busy={loading}>
|
||||
<div className="flex items-center justify-between border-b border-white/10 px-4 py-2.5 text-xs text-[#a6afbd]">
|
||||
<span className="font-mono">{framework?.nome}</span>
|
||||
<span>{loading ? (isEn ? "Loading example…" : isEs ? "Cargando ejemplo…" : "Carregando exemplo…") : framework?.linguagem}</span>
|
||||
<span>
|
||||
{loading
|
||||
? (isEn
|
||||
? "Loading example…"
|
||||
: isEs
|
||||
? "Cargando ejemplo…"
|
||||
: isFr
|
||||
? "Chargement de l'exemple…"
|
||||
: isDe
|
||||
? "Beispiel wird geladen…"
|
||||
: "Carregando exemplo…")
|
||||
: framework?.linguagem}
|
||||
</span>
|
||||
</div>
|
||||
<pre tabIndex={0} aria-label={isEn ? `Code example in ${framework?.linguagem}` : isEs ? `Código de ejemplo en ${framework?.linguagem}` : `Código de exemplo em ${framework?.linguagem}`}>
|
||||
<pre
|
||||
tabIndex={0}
|
||||
aria-label={
|
||||
isEn
|
||||
? `Code example in ${framework?.linguagem}`
|
||||
: isEs
|
||||
? `Código de ejemplo en ${framework?.linguagem}`
|
||||
: isFr
|
||||
? `Exemple de code en ${framework?.linguagem}`
|
||||
: isDe
|
||||
? `Codebeispiel in ${framework?.linguagem}`
|
||||
: `Código de exemplo em ${framework?.linguagem}`
|
||||
}
|
||||
>
|
||||
<code>
|
||||
{lines.map((line, idx) => (
|
||||
<span key={idx} className="flex">
|
||||
@@ -159,6 +245,10 @@ export default function CodeExample({ framework }) {
|
||||
? `Could not load local example (${error}). Use “More examples” to view official code.`
|
||||
: isEs
|
||||
? `No se pudo cargar el ejemplo local (${error}). Utilice “Más ejemplos” para ver el código oficial.`
|
||||
: isFr
|
||||
? `Impossible de charger l'exemple local (${error}). Utilisez « Plus d'exemples » pour consulter le code officiel.`
|
||||
: isDe
|
||||
? `Lokales Beispiel konnte nicht geladen werden (${error}). Nutzen Sie „Weitere Beispiele“, um den offiziellen Code anzusehen.`
|
||||
: `Não foi possível carregar o exemplo local (${error}). Use “Mais exemplos” para ver o código oficial.`}
|
||||
</p>
|
||||
)}
|
||||
|
||||
@@ -79,6 +79,52 @@ const FILTER_CATEGORIES_ES = [
|
||||
{ id: "Antena", name: "Antena", color: "#06b6d4" },
|
||||
];
|
||||
|
||||
const FILTER_CATEGORIES_FR = [
|
||||
{ id: "All", name: "Tous", color: "#8b5cf6" },
|
||||
{ id: "GND", name: "Masse (GND)", color: "#64748b" },
|
||||
{ id: "Power", name: "Alimentation", color: "#ef4444" },
|
||||
{ id: "GPIO", name: "GPIO", color: "#22c55e" },
|
||||
{ id: "Low Power", name: "GPIO LP", color: "#f59e0b" },
|
||||
{ id: "ADC", name: "ADC", color: "#ec4899" },
|
||||
{ id: "DAC", name: "DAC", color: "#a855f7" },
|
||||
{ id: "Touch", name: "Touch", color: "#06b6d4" },
|
||||
{ id: "UART", name: "UART", color: "#3b82f6" },
|
||||
{ id: "SPI", name: "SPI", color: "#f43f5e" },
|
||||
{ id: "USB", name: "USB", color: "#a855f7" },
|
||||
{ id: "Clock", name: "Horloge", color: "#eab308" },
|
||||
{ id: "JTAG", name: "JTAG", color: "#6366f1" },
|
||||
{ id: "Strapping", name: "Démarrage (Boot)", color: "#dc2626" },
|
||||
{ id: "DSI", name: "Affichage (DSI)", color: "#f97316" },
|
||||
{ id: "CSI", name: "Caméra (CSI)", color: "#14b8a6" },
|
||||
{ id: "Ethernet", name: "Ethernet", color: "#0284c7" },
|
||||
{ id: "SD", name: "Carte SD", color: "#10b981" },
|
||||
{ id: "I2C", name: "I2C", color: "#f59e0b" },
|
||||
{ id: "Antenne", name: "Antenne", color: "#06b6d4" },
|
||||
];
|
||||
|
||||
const FILTER_CATEGORIES_DE = [
|
||||
{ id: "All", name: "Alle", color: "#8b5cf6" },
|
||||
{ id: "GND", name: "Masse (GND)", color: "#64748b" },
|
||||
{ id: "Power", name: "Stromversorgung", color: "#ef4444" },
|
||||
{ id: "GPIO", name: "GPIO", color: "#22c55e" },
|
||||
{ id: "Low Power", name: "LP GPIO", color: "#f59e0b" },
|
||||
{ id: "ADC", name: "ADC", color: "#ec4899" },
|
||||
{ id: "DAC", name: "DAC", color: "#a855f7" },
|
||||
{ id: "Touch", name: "Touch", color: "#06b6d4" },
|
||||
{ id: "UART", name: "UART", color: "#3b82f6" },
|
||||
{ id: "SPI", name: "SPI", color: "#f43f5e" },
|
||||
{ id: "USB", name: "USB", color: "#a855f7" },
|
||||
{ id: "Clock", name: "Takt", color: "#eab308" },
|
||||
{ id: "JTAG", name: "JTAG", color: "#6366f1" },
|
||||
{ id: "Strapping", name: "Bootmodus", color: "#dc2626" },
|
||||
{ id: "DSI", name: "Display (DSI)", color: "#f97316" },
|
||||
{ id: "CSI", name: "Kamera (CSI)", color: "#14b8a6" },
|
||||
{ id: "Ethernet", name: "Ethernet", color: "#0284c7" },
|
||||
{ id: "SD", name: "SD-Karte", color: "#10b981" },
|
||||
{ id: "I2C", name: "I2C", color: "#f59e0b" },
|
||||
{ id: "Antenne", name: "Antenne", color: "#06b6d4" },
|
||||
];
|
||||
|
||||
const type_colors = {
|
||||
power: "#ef4444", // high-voltage red
|
||||
ground: "#64748b", // slate gray
|
||||
@@ -106,6 +152,8 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
const pathname = usePathname();
|
||||
const isEn = pathname?.startsWith("/en");
|
||||
const isEs = pathname?.startsWith("/es");
|
||||
const isFr = pathname?.startsWith("/fr");
|
||||
const isDe = pathname?.startsWith("/de");
|
||||
const router = useRouter();
|
||||
const pinosFiltro = useMemo(() => new Set((params.get("pinos") ?? "").split(",").filter(Boolean)), [params]);
|
||||
const motivoFiltro = params.get("motivo") ?? "";
|
||||
@@ -117,7 +165,15 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
const dialogRef = useRef(null);
|
||||
const gatilhoRef = useRef(null);
|
||||
|
||||
const filterCategories = isEn ? FILTER_CATEGORIES_EN : isEs ? FILTER_CATEGORIES_ES : FILTER_CATEGORIES;
|
||||
const filterCategories = isEn
|
||||
? FILTER_CATEGORIES_EN
|
||||
: isEs
|
||||
? FILTER_CATEGORIES_ES
|
||||
: isFr
|
||||
? FILTER_CATEGORIES_FR
|
||||
: isDe
|
||||
? FILTER_CATEGORIES_DE
|
||||
: FILTER_CATEGORIES;
|
||||
|
||||
useEffect(() => {
|
||||
setMounted(true);
|
||||
@@ -139,7 +195,9 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
};
|
||||
|
||||
const nomeCategoria = (cat) => {
|
||||
if (cat === "Strapping") return isEn ? "Boot mode" : isEs ? "Arranque (Boot)" : "Inicialização";
|
||||
if (cat === "Strapping") {
|
||||
return isEn ? "Boot mode" : isEs ? "Arranque (Boot)" : isFr ? "Démarrage (Boot)" : isDe ? "Bootmodus" : "Inicialização";
|
||||
}
|
||||
if (isEn) {
|
||||
const found = FILTER_CATEGORIES_EN.find((f) => f.id === cat);
|
||||
if (found) return found.name;
|
||||
@@ -148,6 +206,14 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
const found = FILTER_CATEGORIES_ES.find((f) => f.id === cat);
|
||||
if (found) return found.name;
|
||||
}
|
||||
if (isFr) {
|
||||
const found = FILTER_CATEGORIES_FR.find((f) => f.id === cat);
|
||||
if (found) return found.name;
|
||||
}
|
||||
if (isDe) {
|
||||
const found = FILTER_CATEGORIES_DE.find((f) => f.id === cat);
|
||||
if (found) return found.name;
|
||||
}
|
||||
return cat;
|
||||
};
|
||||
|
||||
@@ -204,10 +270,18 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="px-4 py-14 text-center">
|
||||
<Sliders className="mx-auto h-10 w-10 text-muted" aria-hidden="true" />
|
||||
<p className="mt-4 font-display text-xl font-semibold text-ink">
|
||||
{isEn ? "Pinout diagram unavailable" : isEs ? "Diagrama de conexiones no disponible" : "Diagrama de conexões indisponível"}
|
||||
{isEn ? "Pinout diagram unavailable" : isEs ? "Diagrama de conexiones no disponible" : isFr ? "Brochage non disponible" : isDe ? "Pinbelegungsdiagramm nicht verfügbar" : "Diagrama de conexões indisponível"}
|
||||
</p>
|
||||
<p className="mt-1 text-sm text-muted">
|
||||
{isEn ? "This model does not yet have a detailed pinout and bus map." : isEs ? "Este modelo todavía no dispone de un mapa detallado de conexiones y buses." : "Este modelo ainda não tem um mapa detalhado de conexões e barramentos."}
|
||||
{isEn
|
||||
? "This model does not yet have a detailed pinout and bus map."
|
||||
: isEs
|
||||
? "Este modelo todavía no dispone de un mapa detallado de conexiones y buses."
|
||||
: isFr
|
||||
? "Ce modèle ne dispose pas encore d'un plan détaillé des broches et des bus."
|
||||
: isDe
|
||||
? "Dieses Modell verfügt noch über keinen detaillierten Pinbelegungs- und Busplan."
|
||||
: "Este modelo ainda não tem um mapa detalhado de conexões e barramentos."}
|
||||
</p>
|
||||
</div>
|
||||
);
|
||||
@@ -219,13 +293,17 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="space-y-6">
|
||||
<div>
|
||||
<h2 className="font-display text-xl font-semibold tracking-[-0.03em] text-ink">
|
||||
{isEn ? "Interactive pinout diagram" : isEs ? "Diagrama de conexiones interactivo" : "Diagrama de conexões interativo"}
|
||||
{isEn ? "Interactive pinout diagram" : isEs ? "Diagrama de conexiones interactivo" : isFr ? "Brochage interactif" : isDe ? "Interaktives Pinbelegungsdiagramm" : "Diagrama de conexões interativo"}
|
||||
</h2>
|
||||
<p className="mt-2 max-w-3xl text-sm leading-relaxed text-muted">
|
||||
{isEn ? (
|
||||
`All connections and multiplexing for the ${serie.nome_completo}. Search by name or number, filter by function, and open a pin to see details.`
|
||||
) : isEs ? (
|
||||
`Todas las conexiones y la multiplexación del ${serie.nome_completo}. Busque por nombre o número, filtre por función y abra un pin para ver los detalles.`
|
||||
) : isFr ? (
|
||||
`Toutes les connexions et le multiplexage de l'${serie.nome_completo}. Recherchez par nom ou numéro, filtrez par fonction et ouvrez une broche pour voir les détails.`
|
||||
) : isDe ? (
|
||||
`Alle Anschlüsse und das Multiplexing des ${serie.nome_completo}. Suchen Sie nach Name oder Nummer, filtern Sie nach Funktion und öffnen Sie einen Pin für Details.`
|
||||
) : (
|
||||
`Todas as conexões e a multiplexação do ${serie.nome_completo}. Busque por nome ou número, filtre por função e abra um pino para ver os detalhes.`
|
||||
)}
|
||||
@@ -235,11 +313,16 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
{pinosFiltro.size > 0 && (
|
||||
<div role="status" className="callout flex flex-wrap items-center justify-between gap-3">
|
||||
<p className="text-sm text-ink">
|
||||
<strong className="font-semibold">{isEn ? "Filtered by search:" : isEs ? "Filtrado por la búsqueda:" : "Filtrado pela busca:"}</strong> {motivoFiltro || (isEn ? "selected pins" : isEs ? "pines seleccionados" : "pinos selecionados")} ({pinosFiltro.size}{" "}
|
||||
{pinosFiltro.size === 1 ? (isEn ? "pin" : isEs ? "pin" : "pino") : (isEn ? "pins" : isEs ? "pines" : "pinos")})
|
||||
<strong className="font-semibold">
|
||||
{isEn ? "Filtered by search:" : isEs ? "Filtrado por la búsqueda:" : isFr ? "Filtré par la recherche :" : isDe ? "Nach Suche gefiltert:" : "Filtrado pela busca:"}
|
||||
</strong>{" "}
|
||||
{motivoFiltro || (isEn ? "selected pins" : isEs ? "pines seleccionados" : isFr ? "broches sélectionnées" : isDe ? "ausgewählte Pins" : "pinos selecionados")} ({pinosFiltro.size}{" "}
|
||||
{pinosFiltro.size === 1
|
||||
? (isEn ? "pin" : isEs ? "pin" : isFr ? "broche" : isDe ? "Pin" : "pino")
|
||||
: (isEn ? "pins" : isEs ? "pines" : isFr ? "broches" : isDe ? "Pins" : "pinos")})
|
||||
</p>
|
||||
<button type="button" onClick={mostrarTodos} className="btn btn-ghost btn-sm">
|
||||
{isEn ? "Show all pins" : isEs ? "Mostrar todos los pines" : "Mostrar todos os pinos"}
|
||||
{isEn ? "Show all pins" : isEs ? "Mostrar todos los pines" : isFr ? "Afficher toutes les broches" : isDe ? "Alle Pins anzeigen" : "Mostrar todos os pinos"}
|
||||
</button>
|
||||
</div>
|
||||
)}
|
||||
@@ -247,45 +330,59 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="flex flex-col gap-3 sm:flex-row">
|
||||
<div className="relative flex-1">
|
||||
<label htmlFor="busca-pino" className="sr-only">
|
||||
{isEn ? "Search connection by name or number" : isEs ? "Buscar conexión por nombre o número" : "Buscar conexão por nome ou número"}
|
||||
{isEn ? "Search connection by name or number" : isEs ? "Buscar conexión por nombre o número" : isFr ? "Rechercher une connexion par nom ou numéro" : isDe ? "Anschluss nach Name oder Nummer suchen" : "Buscar conexão por nome ou número"}
|
||||
</label>
|
||||
<Search className="pointer-events-none absolute left-4 top-1/2 h-4 w-4 -translate-y-1/2 text-muted" aria-hidden="true" />
|
||||
<input
|
||||
id="busca-pino"
|
||||
type="search"
|
||||
placeholder={isEn ? "Search pin (e.g.: GPIO1, TXD, XTAL)" : isEs ? "Buscar pin (ej.: GPIO1, TXD, XTAL)" : "Buscar pino (ex.: GPIO1, TXD, XTAL)"}
|
||||
placeholder={
|
||||
isEn
|
||||
? "Search pin (e.g.: GPIO1, TXD, XTAL)"
|
||||
: isEs
|
||||
? "Buscar pin (ej.: GPIO1, TXD, XTAL)"
|
||||
: isFr
|
||||
? "Rechercher une broche (ex. : GPIO1, TXD, XTAL)"
|
||||
: isDe
|
||||
? "Pin suchen (z. B.: GPIO1, TXD, XTAL)"
|
||||
: "Buscar pino (ex.: GPIO1, TXD, XTAL)"
|
||||
}
|
||||
value={searchQuery}
|
||||
onChange={(e) => setSearchQuery(e.target.value)}
|
||||
autoComplete="off"
|
||||
className="field pl-11 pr-4 text-sm"
|
||||
/>
|
||||
</div>
|
||||
<div role="group" aria-label={isEn ? "Display mode" : isEs ? "Modo de visualización" : "Modo de exibição"} className="flex gap-2">
|
||||
<div role="group" aria-label={isEn ? "Display mode" : isEs ? "Modo de visualización" : isFr ? "Mode d'affichage" : isDe ? "Anzeigemodus" : "Modo de exibição"} className="flex gap-2">
|
||||
<button type="button" onClick={() => setViewMode("grid")} aria-pressed={viewMode === "grid"} className="chip-btn">
|
||||
<Grid className="h-4 w-4" aria-hidden="true" />
|
||||
{isEn ? "Grid" : isEs ? "Cuadrícula" : "Grade"}
|
||||
{isEn ? "Grid" : isEs ? "Cuadrícula" : isFr ? "Grille" : isDe ? "Raster" : "Grade"}
|
||||
</button>
|
||||
<button type="button" onClick={() => setViewMode("list")} aria-pressed={viewMode === "list"} className="chip-btn">
|
||||
<List className="h-4 w-4" aria-hidden="true" />
|
||||
{isEn ? "List" : isEs ? "Lista" : "Lista"}
|
||||
{isEn ? "List" : isEs ? "Lista" : isFr ? "Liste" : isDe ? "Liste" : "Lista"}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<div className="flex items-center justify-between gap-3">
|
||||
<h3 className="text-sm font-semibold text-ink">{isEn ? "Pin function" : isEs ? "Función del pin" : "Função do pino"}</h3>
|
||||
<h3 className="text-sm font-semibold text-ink">{isEn ? "Pin function" : isEs ? "Función del pin" : isFr ? "Fonction de la broche" : isDe ? "Pin-Funktion" : "Função do pino"}</h3>
|
||||
<p role="status" aria-live="polite" className="text-sm text-muted">
|
||||
{isEn ? (
|
||||
`${visibleConnections.length} of ${connections.length} pins`
|
||||
) : isEs ? (
|
||||
`${visibleConnections.length} de ${connections.length} pines`
|
||||
) : isFr ? (
|
||||
`${visibleConnections.length} sur ${connections.length} broches`
|
||||
) : isDe ? (
|
||||
`${visibleConnections.length} von ${connections.length} Pins`
|
||||
) : (
|
||||
`${visibleConnections.length} de ${connections.length} pinos`
|
||||
)}
|
||||
</p>
|
||||
</div>
|
||||
<div role="group" aria-label={isEn ? "Filter by function" : isEs ? "Filtrar por función" : "Filtrar por função"} className="mt-3 flex flex-wrap gap-2">
|
||||
<div role="group" aria-label={isEn ? "Filter by function" : isEs ? "Filtrar por función" : isFr ? "Filtrer par fonction" : isDe ? "Nach Funktion filtern" : "Filtrar por função"} className="mt-3 flex flex-wrap gap-2">
|
||||
{filterCategories.map((filter) => {
|
||||
const isActive = activeFilter === filter.id;
|
||||
const count = connections.filter((c) => (filter.id === "All" ? true : c.categorias.includes(filter.id))).length;
|
||||
@@ -304,10 +401,20 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
{visibleConnections.length === 0 ? (
|
||||
<div className="rounded-2xl border border-dashed border-line-strong px-6 py-12 text-center">
|
||||
<Search className="mx-auto h-8 w-8 text-muted" aria-hidden="true" />
|
||||
<p className="mt-3 font-semibold text-ink">{isEn ? "No connections found" : isEs ? "No se encontraron conexiones" : "Nenhuma conexão encontrada"}</p>
|
||||
<p className="mt-1 text-sm text-muted">{isEn ? "Adjust your search or return to all functions." : isEs ? "Ajuste la búsqueda o vuelva a todas las funciones." : "Ajuste a busca ou volte para todas as funções."}</p>
|
||||
<p className="mt-3 font-semibold text-ink">{isEn ? "No connections found" : isEs ? "No se encontraron conexiones" : isFr ? "Aucune connexion trouvée" : isDe ? "Keine Anschlüsse gefunden" : "Nenhuma conexão encontrada"}</p>
|
||||
<p className="mt-1 text-sm text-muted">
|
||||
{isEn
|
||||
? "Adjust your search or return to all functions."
|
||||
: isEs
|
||||
? "Ajuste la búsqueda o vuelva a todas las funciones."
|
||||
: isFr
|
||||
? "Ajustez votre recherche ou revenez à toutes les fonctions."
|
||||
: isDe
|
||||
? "Passen Sie Ihre Suche an oder kehren Sie zu allen Funktionen zurück."
|
||||
: "Ajuste a busca ou volte para todas as funções."}
|
||||
</p>
|
||||
<button type="button" onClick={() => { setActiveFilter("All"); setSearchQuery(""); if (pinosFiltro.size) mostrarTodos(); }} className="btn btn-primary btn-sm mt-5">
|
||||
{isEn ? "Clear search and filters" : isEs ? "Limpiar búsqueda y filtros" : "Limpar busca e filtros"}
|
||||
{isEn ? "Clear search and filters" : isEs ? "Limpiar búsqueda y filtros" : isFr ? "Effacer la recherche et les filtres" : isDe ? "Suche und Filter zurücksetzen" : "Limpar busca e filtros"}
|
||||
</button>
|
||||
</div>
|
||||
) : viewMode === "grid" ? (
|
||||
@@ -320,7 +427,17 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
type="button"
|
||||
onClick={(e) => abrir(connection, e)}
|
||||
aria-haspopup="dialog"
|
||||
aria-label={isEn ? `Pin ${connection.nome}, number ${connection.numero}${connection.avisos ? ", with usage restrictions" : ""}` : isEs ? `Pin ${connection.nome}, número ${connection.numero}${connection.avisos ? ", con restricciones de uso" : ""}` : `Pino ${connection.nome}, número ${connection.numero}${connection.avisos ? ", com restrições de uso" : ""}`}
|
||||
aria-label={
|
||||
isEn
|
||||
? `Pin ${connection.nome}, number ${connection.numero}${connection.avisos ? ", with usage restrictions" : ""}`
|
||||
: isEs
|
||||
? `Pin ${connection.nome}, número ${connection.numero}${connection.avisos ? ", con restricciones de uso" : ""}`
|
||||
: isFr
|
||||
? `Broche ${connection.nome}, numéro ${connection.numero}${connection.avisos ? ", avec restrictions d'utilisation" : ""}`
|
||||
: isDe
|
||||
? `Pin ${connection.nome}, Nummer ${connection.numero}${connection.avisos ? ", mit Nutzungseinschränkungen" : ""}`
|
||||
: `Pino ${connection.nome}, número ${connection.numero}${connection.avisos ? ", com restrições de uso" : ""}`
|
||||
}
|
||||
className="flex w-full flex-col items-center rounded-xl border border-line bg-surface p-3 transition-colors hover:bg-surface-2"
|
||||
>
|
||||
<span
|
||||
@@ -349,14 +466,22 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="overflow-x-auto rounded-xl border border-line">
|
||||
<table className="w-full min-w-[40rem] border-collapse text-left text-sm">
|
||||
<caption className="sr-only">
|
||||
{isEn ? `Connections of ${serie.nome_completo}` : isEs ? `Conexiones del ${serie.nome_completo}` : `Conexões do ${serie.nome_completo}`}
|
||||
{isEn
|
||||
? `Connections of ${serie.nome_completo}`
|
||||
: isEs
|
||||
? `Conexiones del ${serie.nome_completo}`
|
||||
: isFr
|
||||
? `Connexions de l'${serie.nome_completo}`
|
||||
: isDe
|
||||
? `Anschlüsse des ${serie.nome_completo}`
|
||||
: `Conexões do ${serie.nome_completo}`}
|
||||
</caption>
|
||||
<thead>
|
||||
<tr className="border-b border-line bg-surface-2 text-muted">
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Pin" : isEs ? "Pin" : "Pino"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Name" : isEs ? "Nombre" : "Nome"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Functions" : isEs ? "Funciones" : "Funções"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Usage" : isEs ? "Uso" : "Uso"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Pin" : isEs ? "Pin" : isFr ? "Broche" : isDe ? "Pin" : "Pino"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Name" : isEs ? "Nombre" : isFr ? "Nom" : isDe ? "Name" : "Nome"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Functions" : isEs ? "Funciones" : isFr ? "Fonctions" : isDe ? "Funktionen" : "Funções"}</th>
|
||||
<th scope="col" className="px-4 py-3 font-medium">{isEn ? "Usage" : isEs ? "Uso" : isFr ? "Utilisation" : isDe ? "Nutzung" : "Uso"}</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody className="divide-y divide-line">
|
||||
@@ -369,7 +494,17 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
type="button"
|
||||
onClick={(e) => abrir(connection, e)}
|
||||
aria-haspopup="dialog"
|
||||
aria-label={isEn ? `Open pin details for ${connection.nome}, number ${connection.numero}` : isEs ? `Abrir detalles del pin ${connection.nome}, número ${connection.numero}` : `Abrir detalhes do pino ${connection.nome}, número ${connection.numero}`}
|
||||
aria-label={
|
||||
isEn
|
||||
? `Open pin details for ${connection.nome}, number ${connection.numero}`
|
||||
: isEs
|
||||
? `Abrir detalles del pin ${connection.nome}, número ${connection.numero}`
|
||||
: isFr
|
||||
? `Ouvrir les détails de la broche ${connection.nome}, numéro ${connection.numero}`
|
||||
: isDe
|
||||
? `Pindetails für ${connection.nome}, Nummer ${connection.numero} öffnen`
|
||||
: `Abrir detalhes do pino ${connection.nome}, número ${connection.numero}`
|
||||
}
|
||||
className="grid h-11 w-11 place-items-center rounded-full border-2 bg-surface text-sm font-semibold tabular-nums text-ink hover:bg-surface-2"
|
||||
style={{ borderColor: baseColor }}
|
||||
>
|
||||
@@ -384,12 +519,12 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
{connection.avisos ? (
|
||||
<span className="inline-flex items-center gap-1.5 font-medium text-danger">
|
||||
<AlertTriangle className="h-4 w-4" aria-hidden="true" />
|
||||
{isEn ? "Restricted" : isEs ? "Restringido" : "Restrito"}
|
||||
{isEn ? "Restricted" : isEs ? "Restringido" : isFr ? "Restreint" : isDe ? "Eingeschränkt" : "Restrito"}
|
||||
</span>
|
||||
) : (
|
||||
<span className="inline-flex items-center gap-1.5 text-ok">
|
||||
<CheckCircle className="h-4 w-4" aria-hidden="true" />
|
||||
{isEn ? "Free" : isEs ? "Libre" : "Livre"}
|
||||
{isEn ? "Free" : isEs ? "Libre" : isFr ? "Libre" : isDe ? "Frei" : "Livre"}
|
||||
</span>
|
||||
)}
|
||||
</td>
|
||||
@@ -405,7 +540,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="callout callout-warn flex items-start gap-3">
|
||||
<AlertTriangle className="mt-0.5 h-5 w-5 shrink-0 text-gold" aria-hidden="true" />
|
||||
<div>
|
||||
<p className="font-semibold text-ink">{isEn ? "Pinout notes" : isEs ? "Notas sobre el patillaje" : "Notas sobre a pinagem"}</p>
|
||||
<p className="font-semibold text-ink">{isEn ? "Pinout notes" : isEs ? "Notas sobre el patillaje" : isFr ? "Remarques sur le brochage" : isDe ? "Hinweise zur Pinbelegung" : "Notas sobre a pinagem"}</p>
|
||||
<ul className="mt-1 list-disc space-y-1 pl-5">
|
||||
{isEn ? (
|
||||
<>
|
||||
@@ -417,6 +552,16 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<li>Los pines con icono de advertencia tienen un papel especial en el arranque o limitaciones analógicas. Abra el pin para ver los detalles.</li>
|
||||
<li>Aísle las pistas táctiles capacitivas del ruido de RF acoplado.</li>
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
<li>Les broches signalées par une icône d'avertissement ont un rôle spécial au démarrage ou des restrictions analogiques. Ouvrez la broche pour voir les détails.</li>
|
||||
<li>Isolez les pistes tactiles capacitives des bruits RF couplés.</li>
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
<li>Pins mit einem Warnsymbol spielen eine besondere Rolle beim Booten oder unterliegen analogen Einschränkungen. Öffnen Sie den Pin für Details.</li>
|
||||
<li>Isolieren Sie kapazitive Touch-Leitungen von eingekoppeltem HF-Rauschen.</li>
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<li>Pinos com o ícone de alerta têm papel especial no boot ou limitações analógicas. Abra o pino para ver os detalhes.</li>
|
||||
@@ -451,11 +596,24 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
{selectedConnection.nome}
|
||||
</h3>
|
||||
<p className="text-sm text-muted">
|
||||
{isEn ? `Physical pin ${selectedConnection.numero}` : isEs ? `Pin físico ${selectedConnection.numero}` : `Pino físico ${selectedConnection.numero}`}
|
||||
{isEn
|
||||
? `Physical pin ${selectedConnection.numero}`
|
||||
: isEs
|
||||
? `Pin físico ${selectedConnection.numero}`
|
||||
: isFr
|
||||
? `Broche physique ${selectedConnection.numero}`
|
||||
: isDe
|
||||
? `Physischer Pin ${selectedConnection.numero}`
|
||||
: `Pino físico ${selectedConnection.numero}`}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<button type="button" onClick={fechar} aria-label={isEn ? "Close pin details" : isEs ? "Cerrar detalles del pin" : "Fechar detalhes do pino"} className="grid h-11 w-11 shrink-0 place-items-center rounded-full text-muted transition-colors hover:bg-surface-2 hover:text-ink">
|
||||
<button
|
||||
type="button"
|
||||
onClick={fechar}
|
||||
aria-label={isEn ? "Close pin details" : isEs ? "Cerrar detalles del pin" : isFr ? "Fermer les détails de la broche" : isDe ? "Pindetails schließen" : "Fechar detalhes do pino"}
|
||||
className="grid h-11 w-11 shrink-0 place-items-center rounded-full text-muted transition-colors hover:bg-surface-2 hover:text-ink"
|
||||
>
|
||||
<X className="h-5 w-5" aria-hidden="true" />
|
||||
</button>
|
||||
</div>
|
||||
@@ -463,7 +621,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<div className="flex-1 space-y-6 overflow-y-auto p-5 sm:p-7">
|
||||
{selectedConnection.categorias.length > 0 && (
|
||||
<section>
|
||||
<h4 className="text-sm font-semibold text-ink">{isEn ? "Categories" : isEs ? "Categorías" : "Categorias"}</h4>
|
||||
<h4 className="text-sm font-semibold text-ink">{isEn ? "Categories" : isEs ? "Categorías" : isFr ? "Catégories" : isDe ? "Kategorien" : "Categorias"}</h4>
|
||||
<ul className="mt-3 flex flex-wrap gap-2">
|
||||
{selectedConnection.categorias.map((cat) => (
|
||||
<li key={cat} className="chip">
|
||||
@@ -479,7 +637,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<section>
|
||||
<h4 className="flex items-center gap-2 text-sm font-semibold text-ink">
|
||||
<Zap className="h-4 w-4 text-danger" aria-hidden="true" />
|
||||
{isEn ? "Power domain" : isEs ? "Dominio de alimentación" : "Domínio de alimentação"}
|
||||
{isEn ? "Power domain" : isEs ? "Dominio de alimentación" : isFr ? "Domaine d'alimentation" : isDe ? "Spannungsbereich" : "Domínio de alimentação"}
|
||||
</h4>
|
||||
<ul className="tile mt-3 space-y-2">
|
||||
{selectedConnection.alimentacao.map((source) => (
|
||||
@@ -490,7 +648,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
)}
|
||||
|
||||
<section>
|
||||
<h4 className="text-sm font-semibold text-ink">{isEn ? "Available functions" : isEs ? "Funciones disponibles" : "Funções disponíveis"}</h4>
|
||||
<h4 className="text-sm font-semibold text-ink">{isEn ? "Available functions" : isEs ? "Funciones disponibles" : isFr ? "Fonctions disponibles" : isDe ? "Verfügbare Funktionen" : "Funções disponíveis"}</h4>
|
||||
<ul className="tile mt-3 grid gap-2.5 sm:grid-cols-2">
|
||||
{selectedConnection.funcoes.map((func) => (
|
||||
<li key={func} className="flex items-center gap-2.5 text-sm text-ink-soft">
|
||||
@@ -505,7 +663,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
<section className="callout callout-danger">
|
||||
<h4 className="flex items-center gap-2 font-semibold text-ink">
|
||||
<AlertTriangle className="h-4 w-4 text-danger" aria-hidden="true" />
|
||||
{isEn ? "Engineering notes" : isEs ? "Notas de ingeniería" : "Avisos de engenharia"}
|
||||
{isEn ? "Engineering notes" : isEs ? "Notas de ingeniería" : isFr ? "Notes d'ingénierie" : isDe ? "Entwicklungshinweise" : "Avisos de engenharia"}
|
||||
</h4>
|
||||
<ul className="mt-2 list-disc space-y-1.5 pl-5">
|
||||
{selectedConnection.avisos.map((aviso) => (
|
||||
@@ -518,7 +676,7 @@ function ConnectionsDiagramInner({ connections, serie }) {
|
||||
|
||||
<div className="border-t border-line p-4 sm:px-7">
|
||||
<button type="button" onClick={fechar} className="btn btn-primary w-full">
|
||||
{isEn ? "Close" : isEs ? "Cerrar" : "Fechar"}
|
||||
{isEn ? "Close" : isEs ? "Cerrar" : isFr ? "Fermer" : isDe ? "Schließen" : "Fechar"}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+149
-7
@@ -96,6 +96,64 @@ const COLUMNS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const COLUMNS_FR = [
|
||||
{
|
||||
title: "Explorer",
|
||||
links: [
|
||||
{ href: "/series", label: "Séries ESP32" },
|
||||
{ href: "/comparacao", label: "Comparateur" },
|
||||
{ href: "/catalogo", label: "Catalogue de cartes" },
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "Outils",
|
||||
links: [
|
||||
{ href: "/seletor", label: "Sélecteur intelligent" },
|
||||
{ href: "/diagnostico", label: "Diagnostic" },
|
||||
{ href: "/componentes", label: "Component Registry" },
|
||||
{ href: "/frameworks", label: "Frameworks et SDKs" },
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "Projet",
|
||||
links: [
|
||||
{ href: "/sobre", label: "À propos d'ESPDocs" },
|
||||
{ href: "/glossario", label: "Glossaire" },
|
||||
{ href: SITE.repositorio, label: "Dépôt", external: true },
|
||||
{ href: `${SITE.repositorio}/issues`, label: "Signaler un problème", external: true },
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const COLUMNS_DE = [
|
||||
{
|
||||
title: "Erkunden",
|
||||
links: [
|
||||
{ href: "/series", label: "ESP32-Serien" },
|
||||
{ href: "/comparacao", label: "Vergleich" },
|
||||
{ href: "/catalogo", label: "Board-Katalog" },
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "Werkzeuge",
|
||||
links: [
|
||||
{ href: "/seletor", label: "Intelligente Auswahl" },
|
||||
{ href: "/diagnostico", label: "Diagnose" },
|
||||
{ href: "/componentes", label: "Component Registry" },
|
||||
{ href: "/frameworks", label: "Frameworks & SDKs" },
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "Projekt",
|
||||
links: [
|
||||
{ href: "/sobre", label: "Über ESPDocs" },
|
||||
{ href: "/glossario", label: "Glossar" },
|
||||
{ href: SITE.repositorio, label: "Repository", external: true },
|
||||
{ href: `${SITE.repositorio}/issues`, label: "Problem melden", external: true },
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
export default function Footer() {
|
||||
const pathname = usePathname() || "";
|
||||
const year = new Date().getFullYear();
|
||||
@@ -105,6 +163,8 @@ export default function Footer() {
|
||||
const isPt = currentLocale === "pt";
|
||||
const isEn = currentLocale === "en";
|
||||
const isEs = currentLocale === "es";
|
||||
const isFr = currentLocale === "fr";
|
||||
const isDe = currentLocale === "de";
|
||||
|
||||
const getLinkHref = (href) => getLocalizedHref(`/${currentLocale}${href}`, currentLocale);
|
||||
|
||||
@@ -115,14 +175,45 @@ export default function Footer() {
|
||||
}))
|
||||
: isEs
|
||||
? COLUMNS_ES
|
||||
: isFr
|
||||
? COLUMNS_FR
|
||||
: isDe
|
||||
? COLUMNS_DE
|
||||
: COLUMNS_EN;
|
||||
|
||||
return (
|
||||
<footer className="mt-20 border-t border-line md:mt-28" aria-label={isPt ? "Rodapé do ESPDocs" : isEs ? "Pie de página de ESPDocs" : "ESPDocs footer"}>
|
||||
<footer
|
||||
className="mt-20 border-t border-line md:mt-28"
|
||||
aria-label={
|
||||
isPt
|
||||
? "Rodapé do ESPDocs"
|
||||
: isEs
|
||||
? "Pie de página de ESPDocs"
|
||||
: isFr
|
||||
? "Pied de page d'ESPDocs"
|
||||
: isDe
|
||||
? "ESPDocs-Fußzeile"
|
||||
: "ESPDocs footer"
|
||||
}
|
||||
>
|
||||
<div className="shell py-14 md:py-20">
|
||||
<div className="grid gap-12 lg:grid-cols-[1.1fr_2fr]">
|
||||
<div>
|
||||
<Link href={getLinkHref("/")} className="inline-flex min-h-11 items-center gap-2.5" aria-label={isPt ? "ESPDocs, página inicial" : isEs ? "ESPDocs, página de inicio" : "ESPDocs, homepage"}>
|
||||
<Link
|
||||
href={getLinkHref("/")}
|
||||
className="inline-flex min-h-11 items-center gap-2.5"
|
||||
aria-label={
|
||||
isPt
|
||||
? "ESPDocs, página inicial"
|
||||
: isEs
|
||||
? "ESPDocs, página de inicio"
|
||||
: isFr
|
||||
? "ESPDocs, page d'accueil"
|
||||
: isDe
|
||||
? "ESPDocs, Startseite"
|
||||
: "ESPDocs, homepage"
|
||||
}
|
||||
>
|
||||
<Logo className="h-7 w-7" />
|
||||
<span className="font-display text-2xl font-semibold tracking-[-0.045em] text-ink">ESPDocs</span>
|
||||
</Link>
|
||||
@@ -137,6 +228,16 @@ export default function Footer() {
|
||||
Documentación independiente del ecosistema ESP32.
|
||||
Datos públicos, curaduría editorial y enlaces a las fuentes oficiales.
|
||||
</>
|
||||
) : isFr ? (
|
||||
<>
|
||||
Documentation indépendante de l'écosystème ESP32.
|
||||
Données publiques, sélection éditoriale et liens vers les sources officielles.
|
||||
</>
|
||||
) : isDe ? (
|
||||
<>
|
||||
Unabhängige Dokumentation des ESP32-Ökosystems.
|
||||
Öffentliche Daten, redaktionelle Betreuung und Links zu offiziellen Quellen.
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
Independent documentation of the ESP32 ecosystem.
|
||||
@@ -211,7 +312,7 @@ export default function Footer() {
|
||||
))}
|
||||
|
||||
<div>
|
||||
<h2 className="text-sm font-semibold text-ink">{isPt ? "Autor" : isEs ? "Autor" : "Author"}</h2>
|
||||
<h2 className="text-sm font-semibold text-ink">{isPt ? "Autor" : isEs ? "Autor" : isFr ? "Auteur" : isDe ? "Autor" : "Author"}</h2>
|
||||
<p className="mt-4 text-sm leading-relaxed text-muted">
|
||||
Lucas Rayan Guerra
|
||||
<br />
|
||||
@@ -222,7 +323,17 @@ export default function Footer() {
|
||||
href={SITE.repositorio}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
aria-label={isPt ? "Gitea do projeto (abre em nova aba)" : isEs ? "Gitea del proyecto (abre en una pestaña nueva)" : "Project Gitea (opens in new tab)"}
|
||||
aria-label={
|
||||
isPt
|
||||
? "Gitea do projeto (abre em nova aba)"
|
||||
: isEs
|
||||
? "Gitea del proyecto (abre en una pestaña nueva)"
|
||||
: isFr
|
||||
? "Gitea du projet (ouvre un nouvel onglet)"
|
||||
: isDe
|
||||
? "Projekt-Gitea (öffnet in neuem Tab)"
|
||||
: "Project Gitea (opens in new tab)"
|
||||
}
|
||||
className="grid h-11 w-11 place-items-center rounded-full border border-line text-ink transition-colors hover:border-line-strong hover:bg-surface"
|
||||
>
|
||||
<GiteaMark className="h-4 w-4" />
|
||||
@@ -231,7 +342,17 @@ export default function Footer() {
|
||||
href={SITE.autorLinkedin}
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
aria-label={isPt ? "LinkedIn do autor (abre em nova aba)" : isEs ? "LinkedIn del autor (abre en una pestaña nueva)" : "Author LinkedIn (opens in new tab)"}
|
||||
aria-label={
|
||||
isPt
|
||||
? "LinkedIn do autor (abre em nova aba)"
|
||||
: isEs
|
||||
? "LinkedIn del autor (abre en una pestaña nueva)"
|
||||
: isFr
|
||||
? "LinkedIn de l'auteur (ouvre un nouvel onglet)"
|
||||
: isDe
|
||||
? "LinkedIn des Autors (öffnet in neuem Tab)"
|
||||
: "Author LinkedIn (opens in new tab)"
|
||||
}
|
||||
className="grid h-11 w-11 place-items-center rounded-full border border-line text-ink transition-colors hover:border-line-strong hover:bg-surface"
|
||||
>
|
||||
<svg className="h-4 w-4" viewBox="0 0 24 24" fill="currentColor" aria-hidden="true">
|
||||
@@ -244,7 +365,18 @@ export default function Footer() {
|
||||
</div>
|
||||
|
||||
<div className="mt-14 flex flex-col gap-4 border-t border-line pt-6 text-xs leading-relaxed text-faint md:flex-row md:items-center md:justify-between">
|
||||
<p>© {year} {isPt ? "ESPDocs. Projeto independente, sem afiliação com a Espressif Systems." : isEs ? "ESPDocs. Proyecto independiente, sin afiliación con Espressif Systems." : "ESPDocs. Independent project, not affiliated with Espressif Systems."}</p>
|
||||
<p>
|
||||
© {year}{" "}
|
||||
{isPt
|
||||
? "ESPDocs. Projeto independente, sem afiliação com a Espressif Systems."
|
||||
: isEs
|
||||
? "ESPDocs. Proyecto independiente, sin afiliación con Espressif Systems."
|
||||
: isFr
|
||||
? "ESPDocs. Projet indépendant, sans affiliation avec Espressif Systems."
|
||||
: isDe
|
||||
? "ESPDocs. Unabhängiges Projekt, nicht verbunden mit Espressif Systems."
|
||||
: "ESPDocs. Independent project, not affiliated with Espressif Systems."}
|
||||
</p>
|
||||
<p className="flex flex-wrap items-center gap-x-5 gap-y-2">
|
||||
<a href={SITE.blog} target="_blank" rel="noopener noreferrer" className="inline-flex min-h-11 items-center gap-1 transition-colors hover:text-accent">
|
||||
Ciência Embarcada
|
||||
@@ -254,7 +386,17 @@ export default function Footer() {
|
||||
lucasrguerra.dev.br
|
||||
<ArrowUpRight className="h-3 w-3" aria-hidden="true" />
|
||||
</a>
|
||||
<span>{isPt ? "Fontes oficiais: Espressif Systems." : isEs ? "Fuentes oficiales: Espressif Systems." : "Official sources: Espressif Systems."}</span>
|
||||
<span>
|
||||
{isPt
|
||||
? "Fontes oficiais: Espressif Systems."
|
||||
: isEs
|
||||
? "Fuentes oficiales: Espressif Systems."
|
||||
: isFr
|
||||
? "Sources officielles : Espressif Systems."
|
||||
: isDe
|
||||
? "Offizielle Quellen: Espressif Systems."
|
||||
: "Official sources: Espressif Systems."}
|
||||
</span>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+209
-20
@@ -118,6 +118,66 @@ const MENUS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
const MENUS_FR = [
|
||||
{
|
||||
id: "hardware",
|
||||
label: "Matériel",
|
||||
items: [
|
||||
{ href: "/series", label: "Séries ESP32", desc: "12 puces, brochages et spécifications", icon: Cpu },
|
||||
{ href: "/comparacao", label: "Comparateur", desc: "Jusqu'à quatre séries côte à côte", icon: Scale },
|
||||
{ href: "/catalogo", label: "Catalogue de cartes", desc: "DevKits, broches et où acheter", icon: Box },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: "tools",
|
||||
label: "Outils",
|
||||
items: [
|
||||
{ href: "/seletor", label: "Sélecteur intelligent", desc: "La puce idéale pour votre projet", icon: SlidersHorizontal },
|
||||
{ href: "/diagnostico", label: "Diagnostic", desc: "Brownout, bootloop, WDT et plus", icon: AlertTriangle },
|
||||
{ href: "/componentes", label: "Component Registry", desc: "Pilotes et manifestes idf_component.yml", icon: Search },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: "library",
|
||||
label: "Bibliothèque",
|
||||
items: [
|
||||
{ href: "/frameworks", label: "Frameworks et SDKs", desc: "ESP-IDF, Arduino, Rust et Matter", icon: BookOpen },
|
||||
{ href: "/glossario", label: "Glossaire technique", desc: "Les termes des fiches techniques", icon: BookA },
|
||||
{ href: "/sobre", label: "À propos du projet", desc: "Auteur, méthode et open source", icon: Sparkles },
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const MENUS_DE = [
|
||||
{
|
||||
id: "hardware",
|
||||
label: "Hardware",
|
||||
items: [
|
||||
{ href: "/series", label: "ESP32-Serien", desc: "12 Chips, Pinbelegungen und Spezifikationen", icon: Cpu },
|
||||
{ href: "/comparacao", label: "Vergleich", desc: "Bis zu vier Serien nebeneinander", icon: Scale },
|
||||
{ href: "/catalogo", label: "Board-Katalog", desc: "DevKits, Pins und Bezugsquellen", icon: Box },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: "tools",
|
||||
label: "Werkzeuge",
|
||||
items: [
|
||||
{ href: "/seletor", label: "Intelligente Auswahl", desc: "Der richtige Chip für Ihr Projekt", icon: SlidersHorizontal },
|
||||
{ href: "/diagnostico", label: "Diagnose", desc: "Brownout, Bootloops, WDT und mehr", icon: AlertTriangle },
|
||||
{ href: "/componentes", label: "Component Registry", desc: "Treiber und idf_component.yml-Manifeste", icon: Search },
|
||||
],
|
||||
},
|
||||
{
|
||||
id: "library",
|
||||
label: "Bibliothek",
|
||||
items: [
|
||||
{ href: "/frameworks", label: "Frameworks & SDKs", desc: "ESP-IDF, Arduino, Rust und Matter", icon: BookOpen },
|
||||
{ href: "/glossario", label: "Technisches Glossar", desc: "Begriffe aus den Datenblättern", icon: BookA },
|
||||
{ href: "/sobre", label: "Über das Projekt", desc: "Autorschaft, Methode und Open Source", icon: Sparkles },
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
const MOBILE_LINKS_PT = [
|
||||
{ href: "/series", label: "Séries ESP32" },
|
||||
{ href: "/comparacao", label: "Comparador" },
|
||||
@@ -155,6 +215,30 @@ const MOBILE_LINKS_ES = [
|
||||
{ href: "/sobre", label: "Acerca de" },
|
||||
];
|
||||
|
||||
const MOBILE_LINKS_FR = [
|
||||
{ href: "/series", label: "Séries ESP32" },
|
||||
{ href: "/comparacao", label: "Comparateur" },
|
||||
{ href: "/seletor", label: "Sélecteur intelligent" },
|
||||
{ href: "/diagnostico", label: "Diagnostic" },
|
||||
{ href: "/frameworks", label: "Frameworks et SDKs" },
|
||||
{ href: "/componentes", label: "Component Registry" },
|
||||
{ href: "/glossario", label: "Glossaire" },
|
||||
{ href: "/catalogo", label: "Catalogue de cartes" },
|
||||
{ href: "/sobre", label: "À propos" },
|
||||
];
|
||||
|
||||
const MOBILE_LINKS_DE = [
|
||||
{ href: "/series", label: "ESP32-Serien" },
|
||||
{ href: "/comparacao", label: "Vergleich" },
|
||||
{ href: "/seletor", label: "Intelligente Auswahl" },
|
||||
{ href: "/diagnostico", label: "Diagnose" },
|
||||
{ href: "/frameworks", label: "Frameworks & SDKs" },
|
||||
{ href: "/componentes", label: "Component Registry" },
|
||||
{ href: "/glossario", label: "Glossar" },
|
||||
{ href: "/catalogo", label: "Board-Katalog" },
|
||||
{ href: "/sobre", label: "Über uns" },
|
||||
];
|
||||
|
||||
function isActivePath(pathname, href, currentLocale) {
|
||||
const localized = getLocalizedHref(`/${currentLocale}${href}`, currentLocale);
|
||||
if (href === "/" || localized === `/${currentLocale}/` || localized === `/${currentLocale}`) {
|
||||
@@ -177,6 +261,8 @@ export default function Header() {
|
||||
const isPt = currentLocale === "pt";
|
||||
const isEn = currentLocale === "en";
|
||||
const isEs = currentLocale === "es";
|
||||
const isFr = currentLocale === "fr";
|
||||
const isDe = currentLocale === "de";
|
||||
|
||||
const getLinkHref = (href) => getLocalizedHref(`/${currentLocale}${href}`, currentLocale);
|
||||
|
||||
@@ -216,19 +302,55 @@ export default function Header() {
|
||||
};
|
||||
}, [drawerOpen]);
|
||||
|
||||
const visibleMobileLinks = isPt ? MOBILE_LINKS_PT : isEs ? MOBILE_LINKS_ES : MOBILE_LINKS_EN;
|
||||
const MENUS = isPt ? MENUS_PT : isEs ? MENUS_ES : MENUS_EN;
|
||||
const visibleMobileLinks = isPt
|
||||
? MOBILE_LINKS_PT
|
||||
: isEs
|
||||
? MOBILE_LINKS_ES
|
||||
: isFr
|
||||
? MOBILE_LINKS_FR
|
||||
: isDe
|
||||
? MOBILE_LINKS_DE
|
||||
: MOBILE_LINKS_EN;
|
||||
const MENUS = isPt ? MENUS_PT : isEs ? MENUS_ES : isFr ? MENUS_FR : isDe ? MENUS_DE : MENUS_EN;
|
||||
|
||||
return (
|
||||
<header className="sticky top-0 z-50 pt-3 sm:pt-4">
|
||||
<div className="shell">
|
||||
<div className="nav-pill flex h-16 items-center justify-between gap-3 rounded-full px-3 sm:px-4">
|
||||
<Link href={getLinkHref("/")} className="flex min-h-11 shrink-0 items-center gap-2.5 rounded-full pl-1 pr-2" aria-label={isPt ? "ESPDocs, página inicial" : isEs ? "ESPDocs, página de inicio" : "ESPDocs, homepage"}>
|
||||
<div className="nav-pill flex h-16 items-center justify-between gap-1.5 rounded-full px-2.5 sm:gap-3 sm:px-4">
|
||||
<Link
|
||||
href={getLinkHref("/")}
|
||||
className="flex min-h-11 shrink-0 items-center gap-2.5 rounded-full pl-1 pr-2"
|
||||
aria-label={
|
||||
isPt
|
||||
? "ESPDocs, página inicial"
|
||||
: isEs
|
||||
? "ESPDocs, página de inicio"
|
||||
: isFr
|
||||
? "ESPDocs, page d'accueil"
|
||||
: isDe
|
||||
? "ESPDocs, Startseite"
|
||||
: "ESPDocs, homepage"
|
||||
}
|
||||
>
|
||||
<Logo className="h-[30px] w-[30px]" />
|
||||
<span className="font-display text-[1.3rem] font-semibold leading-none tracking-[-0.045em] text-ink">ESPDocs</span>
|
||||
<span className="font-display text-[1.3rem] font-semibold max-[359px]:sr-only leading-none tracking-[-0.045em] text-ink">ESPDocs</span>
|
||||
</Link>
|
||||
|
||||
<nav ref={navRef} className="hidden items-center gap-0.5 lg:flex" aria-label={isPt ? "Navegação principal" : isEs ? "Navegación principal" : "Main navigation"}>
|
||||
<nav
|
||||
ref={navRef}
|
||||
className="hidden items-center gap-0.5 lg:flex"
|
||||
aria-label={
|
||||
isPt
|
||||
? "Navegação principal"
|
||||
: isEs
|
||||
? "Navegación principal"
|
||||
: isFr
|
||||
? "Navigation principale"
|
||||
: isDe
|
||||
? "Hauptnavigation"
|
||||
: "Main navigation"
|
||||
}
|
||||
>
|
||||
{MENUS.map((menu) => {
|
||||
const active = menu.items.some((item) => isActivePath(pathname, item.href, currentLocale));
|
||||
const expanded = openMenu === menu.id;
|
||||
@@ -281,23 +403,33 @@ export default function Header() {
|
||||
</Link>
|
||||
)}
|
||||
<Link href={getLinkHref("/sobre")} className={`nav-link ${isActivePath(pathname, "/sobre", currentLocale) ? "is-active" : ""}`} aria-current={isActivePath(pathname, "/sobre", currentLocale) ? "page" : undefined}>
|
||||
{isPt ? "Sobre" : isEs ? "Acerca de" : "About"}
|
||||
{isPt ? "Sobre" : isEs ? "Acerca de" : isFr ? "À propos" : isDe ? "Über uns" : "About"}
|
||||
</Link>
|
||||
</nav>
|
||||
|
||||
<div className="flex items-center gap-1.5">
|
||||
<div className="flex items-center gap-1 sm:gap-1.5">
|
||||
<Link href={getLinkHref("/seletor")} className="btn btn-primary btn-sm hidden lg:inline-flex">
|
||||
<SlidersHorizontal className="h-4 w-4" aria-hidden="true" />
|
||||
{isPt ? "Selecionar chip" : isEs ? "Seleccionar chip" : "Select chip"}
|
||||
{isPt ? "Selecionar chip" : isEs ? "Seleccionar chip" : isFr ? "Choisir une puce" : isDe ? "Chip auswählen" : "Select chip"}
|
||||
</Link>
|
||||
<SearchDialog />
|
||||
<LanguageSelector />
|
||||
<ThemeToggle isPt={isPt} isEs={isEs} />
|
||||
<ThemeToggle isPt={isPt} isEs={isEs} isFr={isFr} isDe={isDe} />
|
||||
<button
|
||||
ref={menuButtonRef}
|
||||
type="button"
|
||||
className="grid h-11 w-11 place-items-center rounded-full border border-line text-ink transition-colors hover:bg-surface-2 lg:hidden"
|
||||
aria-label={isPt ? "Abrir menu de navegação" : isEs ? "Abrir menú de navegación" : "Open navigation menu"}
|
||||
aria-label={
|
||||
isPt
|
||||
? "Abrir menu de navegação"
|
||||
: isEs
|
||||
? "Abrir menú de navegación"
|
||||
: isFr
|
||||
? "Ouvrir le menu de navigation"
|
||||
: isDe
|
||||
? "Navigationsmenü öffnen"
|
||||
: "Open navigation menu"
|
||||
}
|
||||
aria-expanded={drawerOpen}
|
||||
onClick={() => setDrawerOpen(true)}
|
||||
>
|
||||
@@ -320,7 +452,17 @@ export default function Header() {
|
||||
<div
|
||||
role="dialog"
|
||||
aria-modal="true"
|
||||
aria-label={isPt ? "Menu de navegação" : isEs ? "Menú de navegación" : "Navigation menu"}
|
||||
aria-label={
|
||||
isPt
|
||||
? "Menu de navegação"
|
||||
: isEs
|
||||
? "Menú de navegación"
|
||||
: isFr
|
||||
? "Menu de navigation"
|
||||
: isDe
|
||||
? "Navigationsmenü"
|
||||
: "Navigation menu"
|
||||
}
|
||||
aria-hidden={!drawerOpen}
|
||||
inert={!drawerOpen}
|
||||
className={`fixed inset-y-0 right-0 z-[101] flex w-[min(23rem,94vw)] flex-col rounded-l-[2rem] border-l border-line bg-canvas transition-transform duration-300 ${
|
||||
@@ -329,15 +471,19 @@ export default function Header() {
|
||||
>
|
||||
<div className="flex items-start justify-between px-5 py-5">
|
||||
<div>
|
||||
<p className="text-xs font-semibold text-muted">{isPt ? "Navegação" : isEs ? "Navegación" : "Navigation"}</p>
|
||||
<p className="mt-1 font-display text-2xl font-semibold tracking-[-0.04em] text-ink">{isPt ? "Para onde ir" : isEs ? "A dónde ir" : "Where to go"}</p>
|
||||
<p className="text-xs font-semibold text-muted">
|
||||
{isPt ? "Navegação" : isEs ? "Navegación" : isFr ? "Navigation" : isDe ? "Navigation" : "Navigation"}
|
||||
</p>
|
||||
<p className="mt-1 font-display text-2xl font-semibold tracking-[-0.04em] text-ink">
|
||||
{isPt ? "Para onde ir" : isEs ? "A dónde ir" : isFr ? "Où aller" : isDe ? "Wohin möchten Sie" : "Where to go"}
|
||||
</p>
|
||||
</div>
|
||||
<button
|
||||
ref={closeRef}
|
||||
type="button"
|
||||
onClick={() => setDrawerOpen(false)}
|
||||
className="grid h-10 w-10 place-items-center rounded-full border border-line text-ink transition-colors hover:bg-surface-2"
|
||||
aria-label={isPt ? "Fechar menu" : isEs ? "Cerrar menú" : "Close menu"}
|
||||
aria-label={isPt ? "Fechar menu" : isEs ? "Cerrar menú" : isFr ? "Fermer le menu" : isDe ? "Menü schließen" : "Close menu"}
|
||||
>
|
||||
<X className="h-5 w-5" aria-hidden="true" />
|
||||
</button>
|
||||
@@ -369,7 +515,10 @@ export default function Header() {
|
||||
</div>
|
||||
)}
|
||||
|
||||
<nav className="flex-1 overflow-y-auto px-3 py-2" aria-label={isPt ? "Navegação móvel" : isEs ? "Navegación móvil" : "Mobile navigation"}>
|
||||
<nav
|
||||
className="flex-1 overflow-y-auto px-3 py-2"
|
||||
aria-label={isPt ? "Navegação móvel" : isEs ? "Navegación móvil" : isFr ? "Navigation mobile" : isDe ? "Mobile Navigation" : "Mobile navigation"}
|
||||
>
|
||||
{visibleMobileLinks.map((link) => (
|
||||
<Link
|
||||
key={link.href}
|
||||
@@ -387,7 +536,7 @@ export default function Header() {
|
||||
<div className="p-4 pt-2">
|
||||
<Link href={getLinkHref("/seletor")} onClick={() => setDrawerOpen(false)} className="btn btn-primary w-full">
|
||||
<SlidersHorizontal className="h-4 w-4" aria-hidden="true" />
|
||||
{isPt ? "Selecionar meu chip" : isEs ? "Seleccionar mi chip" : "Select my chip"}
|
||||
{isPt ? "Selecionar meu chip" : isEs ? "Seleccionar mi chip" : isFr ? "Choisir ma puce" : isDe ? "Meinen Chip auswählen" : "Select my chip"}
|
||||
</Link>
|
||||
</div>
|
||||
</div>
|
||||
@@ -398,7 +547,7 @@ export default function Header() {
|
||||
);
|
||||
}
|
||||
|
||||
function ThemeToggle({ isPt = true, isEs = false }) {
|
||||
function ThemeToggle({ isPt = true, isEs = false, isFr = false, isDe = false }) {
|
||||
const { resolvedTheme, setTheme } = useTheme();
|
||||
const [mounted, setMounted] = useState(false);
|
||||
|
||||
@@ -415,8 +564,48 @@ function ThemeToggle({ isPt = true, isEs = false }) {
|
||||
type="button"
|
||||
onClick={() => setTheme(dark ? "light" : "dark")}
|
||||
className="grid h-11 w-11 place-items-center rounded-full border border-line text-ink transition-colors hover:bg-surface-2"
|
||||
aria-label={dark ? (isPt ? "Ativar tema claro" : isEs ? "Activar tema claro" : "Switch to light theme") : (isPt ? "Ativar tema escuro" : isEs ? "Activar tema oscuro" : "Switch to dark theme")}
|
||||
title={dark ? (isPt ? "Tema claro" : isEs ? "Tema claro" : "Light theme") : (isPt ? "Tema escuro" : isEs ? "Tema oscuro" : "Dark theme")}
|
||||
aria-label={
|
||||
dark
|
||||
? isPt
|
||||
? "Ativar tema claro"
|
||||
: isEs
|
||||
? "Activar tema claro"
|
||||
: isFr
|
||||
? "Activer le thème clair"
|
||||
: isDe
|
||||
? "Helles Design aktivieren"
|
||||
: "Switch to light theme"
|
||||
: isPt
|
||||
? "Ativar tema escuro"
|
||||
: isEs
|
||||
? "Activar tema oscuro"
|
||||
: isFr
|
||||
? "Activer le thème sombre"
|
||||
: isDe
|
||||
? "Dunkles Design aktivieren"
|
||||
: "Switch to dark theme"
|
||||
}
|
||||
title={
|
||||
dark
|
||||
? isPt
|
||||
? "Tema claro"
|
||||
: isEs
|
||||
? "Tema claro"
|
||||
: isFr
|
||||
? "Thème clair"
|
||||
: isDe
|
||||
? "Helles Design"
|
||||
: "Light theme"
|
||||
: isPt
|
||||
? "Tema escuro"
|
||||
: isEs
|
||||
? "Tema oscuro"
|
||||
: isFr
|
||||
? "Thème sombre"
|
||||
: isDe
|
||||
? "Dunkles Design"
|
||||
: "Dark theme"
|
||||
}
|
||||
>
|
||||
{dark ? <Sun className="h-4 w-4" aria-hidden="true" /> : <Moon className="h-4 w-4" aria-hidden="true" />}
|
||||
</button>
|
||||
|
||||
@@ -60,16 +60,34 @@ export default function LanguageSelector() {
|
||||
<button
|
||||
type="button"
|
||||
onClick={() => setOpen(!open)}
|
||||
className="flex h-11 min-w-[44px] items-center gap-1.5 rounded-full border border-line bg-surface px-3 text-sm font-semibold text-ink transition-colors hover:bg-surface-2 focus-visible:outline-2 focus-visible:outline-accent"
|
||||
className="flex h-11 min-w-[44px] items-center justify-center gap-1.5 rounded-full border border-line bg-surface px-2.5 text-sm sm:px-3 font-semibold text-ink transition-colors hover:bg-surface-2 focus-visible:outline-2 focus-visible:outline-accent"
|
||||
aria-haspopup="listbox"
|
||||
aria-expanded={open}
|
||||
aria-label={currentLocaleCode === "en" ? `Current language: ${currentLocale.label}. Click to switch language.` : currentLocaleCode === "es" ? `Idioma actual: ${currentLocale.label}. Haga clic para cambiar de idioma.` : `Idioma atual: ${currentLocale.label}. Clique para trocar de idioma.`}
|
||||
title={currentLocaleCode === "en" ? `Language: ${currentLocale.label}` : `Idioma: ${currentLocale.label}`}
|
||||
aria-label={
|
||||
currentLocaleCode === "en"
|
||||
? `Current language: ${currentLocale.label}. Click to switch language.`
|
||||
: currentLocaleCode === "es"
|
||||
? `Idioma actual: ${currentLocale.label}. Haga clic para cambiar de idioma.`
|
||||
: currentLocaleCode === "fr"
|
||||
? `Langue actuelle : ${currentLocale.label}. Cliquez pour changer de langue.`
|
||||
: currentLocaleCode === "de"
|
||||
? `Aktuelle Sprache: ${currentLocale.label}. Klicken Sie, um die Sprache zu wechseln.`
|
||||
: `Idioma atual: ${currentLocale.label}. Clique para trocar de idioma.`
|
||||
}
|
||||
title={
|
||||
currentLocaleCode === "en"
|
||||
? `Language: ${currentLocale.label}`
|
||||
: currentLocaleCode === "fr"
|
||||
? `Langue : ${currentLocale.label}`
|
||||
: currentLocaleCode === "de"
|
||||
? `Sprache: ${currentLocale.label}`
|
||||
: `Idioma: ${currentLocale.label}`
|
||||
}
|
||||
>
|
||||
<Globe className="h-4 w-4 text-muted" aria-hidden="true" />
|
||||
<Globe className="hidden h-4 w-4 text-muted sm:block" aria-hidden="true" />
|
||||
<span className="font-semibold">{currentLocale.short}</span>
|
||||
<ChevronDown
|
||||
className={`h-3 w-3 text-muted transition-transform duration-200 ${open ? "rotate-180" : ""}`}
|
||||
className={`hidden h-3 w-3 text-muted transition-transform duration-200 sm:block ${open ? "rotate-180" : ""}`}
|
||||
aria-hidden="true"
|
||||
/>
|
||||
</button>
|
||||
@@ -77,7 +95,17 @@ export default function LanguageSelector() {
|
||||
{open && (
|
||||
<div
|
||||
role="listbox"
|
||||
aria-label={currentLocaleCode === "en" ? "Available languages" : currentLocaleCode === "es" ? "Idiomas disponibles" : "Idiomas disponíveis"}
|
||||
aria-label={
|
||||
currentLocaleCode === "en"
|
||||
? "Available languages"
|
||||
: currentLocaleCode === "es"
|
||||
? "Idiomas disponibles"
|
||||
: currentLocaleCode === "fr"
|
||||
? "Langues disponibles"
|
||||
: currentLocaleCode === "de"
|
||||
? "Verfügbare Sprachen"
|
||||
: "Idiomas disponíveis"
|
||||
}
|
||||
className="absolute right-0 top-full mt-2 w-48 rounded-2xl border border-line bg-surface p-1.5 shadow-[0_24px_60px_-20px_rgba(15,23,42,0.35)] dark:shadow-[0_24px_60px_-20px_rgba(0,0,0,0.8)] z-50"
|
||||
>
|
||||
{LOCALES.map((loc) => {
|
||||
|
||||
+29
-3
@@ -15,6 +15,8 @@ export default function PageHero({
|
||||
children,
|
||||
isEn: isEnProp,
|
||||
isEs: isEsProp,
|
||||
isFr: isFrProp,
|
||||
isDe: isDeProp,
|
||||
locale: localeProp,
|
||||
}) {
|
||||
const center = align === "center";
|
||||
@@ -30,13 +32,37 @@ export default function PageHero({
|
||||
: localeProp
|
||||
? localeProp === "es"
|
||||
: trail.some((t) => t.isEs || (t.href && t.href.startsWith("/es")));
|
||||
const isFr =
|
||||
isFrProp !== undefined
|
||||
? isFrProp
|
||||
: localeProp
|
||||
? localeProp === "fr"
|
||||
: trail.some((t) => t.isFr || (t.href && t.href.startsWith("/fr")));
|
||||
const isDe =
|
||||
isDeProp !== undefined
|
||||
? isDeProp
|
||||
: localeProp
|
||||
? localeProp === "de"
|
||||
: trail.some((t) => t.isDe || (t.href && t.href.startsWith("/de")));
|
||||
|
||||
const homeHref = isEn ? "/en" : isEs ? "/es" : isFr ? "/fr" : isDe ? "/de" : "/";
|
||||
const homeLabel = isEn ? "Home" : isEs ? "Inicio" : isFr ? "Accueil" : isDe ? "Startseite" : "Início";
|
||||
const breadcrumbAria = isEn
|
||||
? "Breadcrumb navigation"
|
||||
: isEs
|
||||
? "Navegación por migas de pan"
|
||||
: isFr
|
||||
? "Fil d'Ariane"
|
||||
: isDe
|
||||
? "Brotkrumennavigation"
|
||||
: "Trilha de navegação";
|
||||
|
||||
return (
|
||||
<section className="shell pt-8 sm:pt-12">
|
||||
{trail.length > 0 && (
|
||||
<nav aria-label={isEn ? "Breadcrumb navigation" : isEs ? "Navegación por migas de pan" : "Trilha de navegação"} className="flex flex-wrap items-center gap-2 text-sm text-muted">
|
||||
<Link href={isEn ? "/en" : isEs ? "/es" : "/"} className="inline-flex min-h-11 min-w-11 items-center justify-center transition-colors hover:text-accent">
|
||||
{isEn ? "Home" : isEs ? "Inicio" : "Início"}
|
||||
<nav aria-label={breadcrumbAria} className="flex flex-wrap items-center gap-2 text-sm text-muted">
|
||||
<Link href={homeHref} className="inline-flex min-h-11 min-w-11 items-center justify-center transition-colors hover:text-accent">
|
||||
{homeLabel}
|
||||
</Link>
|
||||
{trail.map((item, i) => (
|
||||
<span key={item.label} className="flex min-h-11 items-center gap-2">
|
||||
|
||||
@@ -201,14 +201,144 @@ const GRUPOS_ES = [
|
||||
},
|
||||
];
|
||||
|
||||
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|mémoire|ne doit pas|déconseillé|connected to|dedicated to|should not)/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|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|programmation|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) => /flottant|floating/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|speicher|sollte nicht|nicht empfohlen|connected to|dedicated to|should not)/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|programmierung/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) => /unbeschaltet|floating/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) {
|
||||
const listaGrupos = isEn ? GRUPOS_EN : isEs ? GRUPOS_ES : GRUPOS_PT;
|
||||
function derivarGrupos(conexoes, isEn, isEs, isFr, isDe) {
|
||||
const listaGrupos = isEn
|
||||
? GRUPOS_EN
|
||||
: isEs
|
||||
? GRUPOS_ES
|
||||
: isFr
|
||||
? GRUPOS_FR
|
||||
: isDe
|
||||
? GRUPOS_DE
|
||||
: GRUPOS_PT;
|
||||
return listaGrupos.map((grupo) => {
|
||||
const vistos = new Map();
|
||||
for (const pino of conexoes) {
|
||||
@@ -224,13 +354,15 @@ function derivarGrupos(conexoes, isEn, isEs) {
|
||||
}).filter((g) => g.pinos.length > 0);
|
||||
}
|
||||
|
||||
export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs = false, locale }) {
|
||||
export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs = false, isFr = false, isDe = 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 grupos = derivarGrupos(conexoes, effectiveIsEn, effectiveIsEs);
|
||||
const grupos = derivarGrupos(conexoes, effectiveIsEn, effectiveIsEs, effectiveIsFr, effectiveIsDe);
|
||||
if (!grupos.length) return null;
|
||||
|
||||
const totalPinos = new Set(grupos.flatMap((g) => g.pinos)).size;
|
||||
@@ -241,7 +373,15 @@ export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs
|
||||
<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" : "Pinos com restrição de uso"}
|
||||
{effectiveIsEn
|
||||
? "Pins with usage restrictions"
|
||||
: effectiveIsEs
|
||||
? "Pines con restricción de uso"
|
||||
: effectiveIsFr
|
||||
? "Broches avec restrictions d'utilisation"
|
||||
: 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">
|
||||
@@ -253,6 +393,14 @@ export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs
|
||||
<>
|
||||
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'{serieKey} ne sont pas libres pour un usage général. {totalPinos} d'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.
|
||||
</>
|
||||
) : 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
|
||||
@@ -269,7 +417,26 @@ export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs
|
||||
<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" : "pino") : (effectiveIsEn ? "pins" : effectiveIsEs ? "pines" : "pinos")}
|
||||
{pinos.length}{" "}
|
||||
{pinos.length === 1
|
||||
? effectiveIsEn
|
||||
? "pin"
|
||||
: effectiveIsEs
|
||||
? "pin"
|
||||
: effectiveIsFr
|
||||
? "broche"
|
||||
: effectiveIsDe
|
||||
? "Pin"
|
||||
: "pino"
|
||||
: effectiveIsEn
|
||||
? "pins"
|
||||
: effectiveIsEs
|
||||
? "pines"
|
||||
: effectiveIsFr
|
||||
? "broches"
|
||||
: effectiveIsDe
|
||||
? "Pins"
|
||||
: "pinos"}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
@@ -292,12 +459,16 @@ export default function PinRestrictions({ conexoes, serieKey, isEn = false, isEs
|
||||
"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."
|
||||
) : 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" : "Abrir diagrama de pinos"}
|
||||
{effectiveIsEn ? "Open pinout diagram" : effectiveIsEs ? "Abrir diagrama de pines" : effectiveIsFr ? "Ouvrir le brochage" : effectiveIsDe ? "Pinbelegung öffnen" : "Abrir diagrama de pinos"}
|
||||
<ArrowRight className="h-4 w-4" aria-hidden="true" />
|
||||
</Link>
|
||||
</div>
|
||||
|
||||
+141
-25
@@ -54,10 +54,34 @@ const TIPOS_ES = {
|
||||
componente: { label: "Componente", Icon: Box, cor: "bg-surface-2 text-ink-soft" },
|
||||
};
|
||||
|
||||
const TIPOS_FR = {
|
||||
resposta: { label: "Réponse", Icon: Sparkles, cor: "bg-accent text-accent-contrast" },
|
||||
pino: { label: "Broches", Icon: Plug, cor: "bg-accent text-accent-contrast" },
|
||||
pagina: { label: "Page", Icon: FileText, cor: "bg-surface-2 text-ink-soft" },
|
||||
serie: { label: "Série", Icon: Cpu, cor: "bg-accent-soft text-accent" },
|
||||
framework: { label: "Framework", Icon: Terminal, cor: "bg-teal-soft text-teal" },
|
||||
glossario: { label: "Glossaire", Icon: BookOpen, cor: "bg-copper-soft text-copper" },
|
||||
erro: { label: "Erreur", Icon: AlertTriangle, cor: "bg-gold-soft text-gold" },
|
||||
componente: { label: "Composant", Icon: Box, cor: "bg-surface-2 text-ink-soft" },
|
||||
};
|
||||
|
||||
const TIPOS_DE = {
|
||||
resposta: { label: "Antwort", Icon: Sparkles, cor: "bg-accent text-accent-contrast" },
|
||||
pino: { label: "Pins", Icon: Plug, cor: "bg-accent text-accent-contrast" },
|
||||
pagina: { label: "Seite", Icon: FileText, cor: "bg-surface-2 text-ink-soft" },
|
||||
serie: { label: "Serie", Icon: Cpu, cor: "bg-accent-soft text-accent" },
|
||||
framework: { label: "Framework", Icon: Terminal, cor: "bg-teal-soft text-teal" },
|
||||
glossario: { label: "Glossar", Icon: BookOpen, cor: "bg-copper-soft text-copper" },
|
||||
erro: { label: "Fehler", Icon: AlertTriangle, cor: "bg-gold-soft text-gold" },
|
||||
componente: { label: "Komponente", Icon: Box, cor: "bg-surface-2 text-ink-soft" },
|
||||
};
|
||||
|
||||
const INTELIGENTES = new Set(["resposta", "pino"]);
|
||||
|
||||
const EXEMPLOS_EN = ["flash s3", "usb pins c6", "gpio0 esp32", "brownout", "LVGL", "FreeRTOS"];
|
||||
const EXEMPLOS_ES = ["flash s3", "pines usb c6", "gpio0 esp32", "brownout", "LVGL", "FreeRTOS"];
|
||||
const EXEMPLOS_FR = ["flash s3", "broches usb c6", "gpio0 esp32", "brownout", "LVGL", "FreeRTOS"];
|
||||
const EXEMPLOS_DE = ["flash s3", "usb pins c6", "gpio0 esp32", "brownout", "LVGL", "FreeRTOS"];
|
||||
|
||||
function Destaque({ texto, termos }) {
|
||||
if (!termos.length) return texto;
|
||||
@@ -110,12 +134,22 @@ function Pilula({ children, onClick, forte = false }) {
|
||||
|
||||
export default function SearchDialog() {
|
||||
const pathname = usePathname() || "";
|
||||
const locale = pathname === "/en" || pathname.startsWith("/en/") ? "en" : (pathname === "/es" || pathname.startsWith("/es/") ? "es" : "pt");
|
||||
const locale = pathname === "/en" || pathname.startsWith("/en/")
|
||||
? "en"
|
||||
: pathname === "/es" || pathname.startsWith("/es/")
|
||||
? "es"
|
||||
: pathname === "/fr" || pathname.startsWith("/fr/")
|
||||
? "fr"
|
||||
: pathname === "/de" || pathname.startsWith("/de/")
|
||||
? "de"
|
||||
: "pt";
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
|
||||
const TIPOS = isEn ? TIPOS_EN : isEs ? TIPOS_ES : TIPOS_PT;
|
||||
const EXEMPLOS = isEn ? EXEMPLOS_EN : isEs ? EXEMPLOS_ES : EXEMPLOS_DE_BUSCA;
|
||||
const TIPOS = isEn ? TIPOS_EN : isEs ? TIPOS_ES : isFr ? TIPOS_FR : isDe ? TIPOS_DE : TIPOS_PT;
|
||||
const EXEMPLOS = isEn ? EXEMPLOS_EN : isEs ? EXEMPLOS_ES : isFr ? EXEMPLOS_FR : isDe ? EXEMPLOS_DE : EXEMPLOS_DE_BUSCA;
|
||||
|
||||
const [aberto, setAberto] = useState(false);
|
||||
const [montado, setMontado] = useState(false);
|
||||
@@ -156,7 +190,15 @@ export default function SearchDialog() {
|
||||
const carregarIndice = useCallback(() => {
|
||||
setErro(false);
|
||||
let cancelado = false;
|
||||
const url = isEn ? "/api/busca/en?v=2" : isEs ? "/api/busca/es?v=2" : "/api/busca?v=2";
|
||||
const url = isEn
|
||||
? "/api/busca/en?v=2"
|
||||
: isEs
|
||||
? "/api/busca/es?v=2"
|
||||
: isFr
|
||||
? "/api/busca/fr?v=2"
|
||||
: isDe
|
||||
? "/api/busca/de?v=2"
|
||||
: "/api/busca?v=2";
|
||||
fetch(url, { cache: "no-cache" })
|
||||
.then((r) => {
|
||||
if (!r.ok) {
|
||||
@@ -180,7 +222,7 @@ export default function SearchDialog() {
|
||||
return () => {
|
||||
cancelado = true;
|
||||
};
|
||||
}, [isEn, isEs]);
|
||||
}, [isEn, isEs, isFr, isDe]);
|
||||
|
||||
// Carrega o índice (textos + especificações + pinos) na primeira abertura.
|
||||
useEffect(() => {
|
||||
@@ -251,17 +293,17 @@ export default function SearchDialog() {
|
||||
id="botao-busca"
|
||||
onClick={() => setAberto(true)}
|
||||
className="flex h-11 min-w-11 shrink-0 cursor-pointer items-center justify-center gap-2 rounded-full border border-line px-3 text-ink transition-colors hover:bg-surface-2 xl:px-4"
|
||||
aria-label={isEn ? "Search ESPDocs (Ctrl+K)" : isEs ? "Buscar en ESPDocs (Ctrl+K)" : "Buscar no ESPDocs (Ctrl+K)"}
|
||||
aria-label={isEn ? "Search ESPDocs (Ctrl+K)" : isEs ? "Buscar en ESPDocs (Ctrl+K)" : isFr ? "Rechercher sur ESPDocs (Ctrl+K)" : isDe ? "ESPDocs durchsuchen (Strg+K)" : "Buscar no ESPDocs (Ctrl+K)"}
|
||||
>
|
||||
<Search className="h-4 w-4" aria-hidden="true" />
|
||||
<span className="hidden text-sm font-medium xl:inline">{isEn ? "Search" : "Buscar"}</span>
|
||||
<kbd className="hidden rounded-md border border-line bg-surface-2 px-1.5 py-0.5 font-mono text-xs font-semibold text-muted xl:inline">Ctrl K</kbd>
|
||||
<span className="hidden text-sm font-medium xl:inline">{isEn ? "Search" : isEs ? "Buscar" : isFr ? "Rechercher" : isDe ? "Suchen" : "Buscar"}</span>
|
||||
<kbd className="hidden rounded-md border border-line bg-surface-2 px-1.5 py-0.5 font-mono text-xs font-semibold text-muted xl:inline">{isDe ? "Strg K" : "Ctrl K"}</kbd>
|
||||
</button>
|
||||
|
||||
{montado &&
|
||||
aberto &&
|
||||
createPortal(
|
||||
<div className="fixed inset-0 z-[120] flex items-start justify-center px-4 pt-[8vh]" role="dialog" aria-modal="true" aria-label={isEn ? "Search ESPDocs" : isEs ? "Buscar en ESPDocs" : "Buscar no ESPDocs"}>
|
||||
<div className="fixed inset-0 z-[120] flex items-start justify-center px-4 pt-[8vh]" role="dialog" aria-modal="true" aria-label={isEn ? "Search ESPDocs" : isEs ? "Buscar en ESPDocs" : isFr ? "Rechercher sur ESPDocs" : isDe ? "ESPDocs durchsuchen" : "Buscar no ESPDocs"}>
|
||||
<div className="dialog-scrim absolute inset-0 bg-black/45 backdrop-blur-sm" onClick={fechar} />
|
||||
<div className="dialog-panel relative flex max-h-[80vh] w-full max-w-2xl flex-col overflow-hidden rounded-3xl border border-line bg-canvas shadow-2xl">
|
||||
<div className="flex items-center gap-3 border-b border-line px-5">
|
||||
@@ -273,17 +315,27 @@ export default function SearchDialog() {
|
||||
value={consulta}
|
||||
onChange={(e) => setConsulta(e.target.value)}
|
||||
onKeyDown={onInputKey}
|
||||
placeholder={isEn ? "Ask ESPDocs: “flash s3”, “usb pins c6”, “gpio0 esp32”…" : isEs ? "Pregunte a ESPDocs: “flash s3”, “pines usb c6”, “gpio0 esp32”…" : "Pergunte ao ESPDocs: “flash s3”, “pinos usb c6”, “gpio0 esp32”…"}
|
||||
placeholder={
|
||||
isEn
|
||||
? "Ask ESPDocs: “flash s3”, “usb pins c6”, “gpio0 esp32”…"
|
||||
: isEs
|
||||
? "Pregunte a ESPDocs: “flash s3”, “pines usb c6”, “gpio0 esp32”…"
|
||||
: isFr
|
||||
? "Demandez à ESPDocs : « flash s3 », « broches usb c6 », « gpio0 esp32 »…"
|
||||
: isDe
|
||||
? "ESPDocs fragen: „flash s3“, „usb pins c6“, „gpio0 esp32“… "
|
||||
: "Pergunte ao ESPDocs: “flash s3”, “pinos usb c6”, “gpio0 esp32”…"
|
||||
}
|
||||
className="flex-1 bg-transparent py-5 text-base text-ink outline-none placeholder:text-muted"
|
||||
autoComplete="off"
|
||||
spellCheck={false}
|
||||
aria-label={isEn ? "Search query" : isEs ? "Término de búsqueda" : "Termo de busca"}
|
||||
aria-label={isEn ? "Search query" : isEs ? "Término de búsqueda" : isFr ? "Requête de recherche" : isDe ? "Suchbegriff" : "Termo de busca"}
|
||||
/>
|
||||
<button
|
||||
type="button"
|
||||
onClick={fechar}
|
||||
className="grid h-9 w-9 cursor-pointer place-items-center rounded-full text-muted transition-colors hover:bg-surface-2 hover:text-ink"
|
||||
aria-label={isEn ? "Close search" : isEs ? "Cerrar búsqueda" : "Fechar busca"}
|
||||
aria-label={isEn ? "Close search" : isEs ? "Cerrar búsqueda" : isFr ? "Fermer la recherche" : isDe ? "Suche schließen" : "Fechar busca"}
|
||||
>
|
||||
<X className="h-4 w-4" />
|
||||
</button>
|
||||
@@ -291,7 +343,7 @@ export default function SearchDialog() {
|
||||
|
||||
{entendeu && (
|
||||
<div className="flex flex-wrap items-center gap-2 border-b border-line bg-surface px-5 py-2.5">
|
||||
<span className="text-xs font-semibold text-muted">{isEn ? "Understood:" : isEs ? "Entendido:" : "Entendi:"}</span>
|
||||
<span className="text-xs font-semibold text-muted">{isEn ? "Understood:" : isEs ? "Entendido:" : isFr ? "Compris :" : isDe ? "Erkannt:" : "Entendi:"}</span>
|
||||
{interpretacao.chips.map((c) => (
|
||||
<Pilula key={c.chave} forte>{c.nome}</Pilula>
|
||||
))}
|
||||
@@ -303,7 +355,11 @@ export default function SearchDialog() {
|
||||
|
||||
{sugestoes.length > 0 && (
|
||||
<div className="flex flex-wrap items-center gap-2 border-b border-line px-5 py-2.5">
|
||||
<span className="text-xs font-semibold text-muted">{interpretacao.chips.length ? (isEn ? "Ask about:" : isEs ? "Preguntar sobre:" : "Perguntar sobre:") : (isEn ? "Which chip?" : isEs ? "¿Para qué chip?" : "Para qual chip?")}</span>
|
||||
<span className="text-xs font-semibold text-muted">
|
||||
{interpretacao.chips.length
|
||||
? (isEn ? "Ask about:" : isEs ? "Preguntar sobre:" : isFr ? "Poser une question sur :" : isDe ? "Frage zu:" : "Perguntar sobre:")
|
||||
: (isEn ? "Which chip?" : isEs ? "¿Para qué chip?" : isFr ? "Pour quelle puce ?" : isDe ? "Für welchen Chip?" : "Para qual chip?")}
|
||||
</span>
|
||||
{sugestoes.map((s) => (
|
||||
<Pilula key={s.rotulo} onClick={() => anexar(s.anexar)}>
|
||||
{s.rotulo}
|
||||
@@ -315,21 +371,37 @@ export default function SearchDialog() {
|
||||
<div ref={listaRef} className="flex-1 overflow-y-auto p-2" role="listbox">
|
||||
{erro && (
|
||||
<div className="p-6 text-center">
|
||||
<p className="text-sm font-semibold text-danger">{isEn ? "Could not load search index." : isEs ? "No se pudo cargar el índice de búsqueda." : "Não foi possível carregar o índice de busca."}</p>
|
||||
<p className="text-sm font-semibold text-danger">
|
||||
{isEn
|
||||
? "Could not load search index."
|
||||
: isEs
|
||||
? "No se pudo cargar el índice de búsqueda."
|
||||
: isFr
|
||||
? "Impossible de charger l'index de recherche."
|
||||
: isDe
|
||||
? "Suchindex konnte nicht geladen werden."
|
||||
: "Não foi possível carregar o índice de busca."}
|
||||
</p>
|
||||
<button
|
||||
type="button"
|
||||
onClick={carregarIndice}
|
||||
className="btn btn-primary btn-sm mt-3"
|
||||
>
|
||||
{isEn ? "Try again" : isEs ? "Reintentar" : "Tentar novamente"}
|
||||
{isEn ? "Try again" : isEs ? "Reintentar" : isFr ? "Réessayer" : isDe ? "Erneut versuchen" : "Tentar novamente"}
|
||||
</button>
|
||||
</div>
|
||||
)}
|
||||
{!erro && !indice && <p className="p-6 text-center text-sm text-muted">{isEn ? "Loading…" : isEs ? "Cargando…" : "Carregando…"}</p>}
|
||||
{!erro && !indice && (
|
||||
<p className="p-6 text-center text-sm text-muted">
|
||||
{isEn ? "Loading…" : isEs ? "Cargando…" : isFr ? "Chargement…" : isDe ? "Wird geladen…" : "Carregando…"}
|
||||
</p>
|
||||
)}
|
||||
|
||||
{indice && vazia && (
|
||||
<div className="px-3 pb-3 pt-1">
|
||||
<p className="text-xs font-semibold text-muted">{isEn ? "Try asking" : isEs ? "Pruebe a preguntar" : "Experimente perguntar"}</p>
|
||||
<p className="text-xs font-semibold text-muted">
|
||||
{isEn ? "Try asking" : isEs ? "Pruebe a preguntar" : isFr ? "Essayez de demander" : isDe ? "Versuchen Sie" : "Experimente perguntar"}
|
||||
</p>
|
||||
<div className="mt-2 flex flex-wrap gap-2">
|
||||
{EXEMPLOS.map((ex) => (
|
||||
<Pilula key={ex} onClick={() => setConsulta(ex)}>
|
||||
@@ -337,14 +409,36 @@ export default function SearchDialog() {
|
||||
</Pilula>
|
||||
))}
|
||||
</div>
|
||||
<p className="mt-4 text-xs font-semibold text-muted">{isEn ? "Go to" : isEs ? "Ir a" : "Ir para"}</p>
|
||||
<p className="mt-4 text-xs font-semibold text-muted">
|
||||
{isEn ? "Go to" : isEs ? "Ir a" : isFr ? "Aller à" : isDe ? "Gehe zu" : "Ir para"}
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{indice && !vazia && resultados.length === 0 && (
|
||||
<div className="p-8 text-center">
|
||||
<p className="font-display text-lg font-semibold text-ink">{isEn ? `No results for “${consulta}”` : isEs ? `Sin resultados para “${consulta}”` : `Nenhum resultado para “${consulta}”`}</p>
|
||||
<p className="mt-1 text-sm text-muted">{isEn ? "Try “brownout”, “flash s3”, “usb pins c6” or “LVGL”." : isEs ? "Pruebe “brownout”, “flash s3”, “pines usb c6” o “LVGL”." : "Tente “brownout”, “flash s3”, “pinos usb c6” ou “LVGL”."}</p>
|
||||
<p className="font-display text-lg font-semibold text-ink">
|
||||
{isEn
|
||||
? `No results for “${consulta}”`
|
||||
: isEs
|
||||
? `Sin resultados para “${consulta}”`
|
||||
: isFr
|
||||
? `Aucun résultat pour « ${consulta} »`
|
||||
: isDe
|
||||
? `Keine Ergebnisse für „${consulta}“`
|
||||
: `Nenhum resultado para “${consulta}”`}
|
||||
</p>
|
||||
<p className="mt-1 text-sm text-muted">
|
||||
{isEn
|
||||
? "Try “brownout”, “flash s3”, “usb pins c6” or “LVGL”."
|
||||
: isEs
|
||||
? "Pruebe “brownout”, “flash s3”, “pines usb c6” o “LVGL”."
|
||||
: isFr
|
||||
? "Essayez « brownout », « flash s3 », « broches usb c6 » ou « LVGL »."
|
||||
: isDe
|
||||
? "Versuchen Sie „brownout“, „flash s3“, „usb pins c6“ oder „LVGL“."
|
||||
: "Tente “brownout”, “flash s3”, “pinos usb c6” ou “LVGL”."}
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
|
||||
@@ -407,10 +501,32 @@ export default function SearchDialog() {
|
||||
</div>
|
||||
|
||||
<div className="hidden items-center gap-4 border-t border-line bg-surface px-4 py-2.5 text-xs text-muted md:flex">
|
||||
<span className="flex items-center gap-1"><ArrowUp className="h-3 w-3" /><ArrowDown className="h-3 w-3" /> {isEn ? "navigate" : "navegar"}</span>
|
||||
<span className="flex items-center gap-1"><CornerDownLeft className="h-3 w-3" /> {isEn ? "open" : "abrir"}</span>
|
||||
<span><kbd className="font-mono font-semibold">Esc</kbd> {isEn ? "close" : isEs ? "cerrar" : "fechar"}</span>
|
||||
<span className="ml-auto">{vazia ? (isEn ? "Tip: press / on any page" : isEs ? "Consejo: presione / en cualquier página" : "Dica: pressione / em qualquer página") : `${resultados.length} ${isEn ? "result(s)" : "resultado(s)"}`}</span>
|
||||
<span className="flex items-center gap-1"><ArrowUp className="h-3 w-3" /><ArrowDown className="h-3 w-3" /> {isEn ? "navigate" : isEs ? "navegar" : isFr ? "naviguer" : isDe ? "navigieren" : "navegar"}</span>
|
||||
<span className="flex items-center gap-1"><CornerDownLeft className="h-3 w-3" /> {isEn ? "open" : isEs ? "abrir" : isFr ? "ouvrir" : isDe ? "öffnen" : "abrir"}</span>
|
||||
<span><kbd className="font-mono font-semibold">Esc</kbd> {isEn ? "close" : isEs ? "cerrar" : isFr ? "fermer" : isDe ? "schließen" : "fechar"}</span>
|
||||
<span className="ml-auto">
|
||||
{vazia
|
||||
? (isEn
|
||||
? "Tip: press / on any page"
|
||||
: isEs
|
||||
? "Consejo: presione / en cualquier página"
|
||||
: isFr
|
||||
? "Astuce : appuyez sur / sur n'importe quelle page"
|
||||
: isDe
|
||||
? "Tipp: Drücken Sie / auf einer beliebigen Seite"
|
||||
: "Dica: pressione / em qualquer página")
|
||||
: `${resultados.length} ${
|
||||
isEn
|
||||
? "result(s)"
|
||||
: isEs
|
||||
? "resultado(s)"
|
||||
: isFr
|
||||
? "résultat(s)"
|
||||
: isDe
|
||||
? "Ergebnis(se)"
|
||||
: "resultado(s)"
|
||||
}`}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>,
|
||||
|
||||
@@ -2,9 +2,11 @@
|
||||
|
||||
import { useEffect, useRef, useState } from "react";
|
||||
|
||||
export default function SeriesTabMenu({ tabs, isEn = false, isEs = false, locale }) {
|
||||
export default function SeriesTabMenu({ tabs, isEn = false, isEs = false, isFr = false, isDe = false, locale }) {
|
||||
const effectiveIsEn = isEn || locale === "en";
|
||||
const effectiveIsEs = isEs || locale === "es";
|
||||
const effectiveIsFr = isFr || locale === "fr";
|
||||
const effectiveIsDe = isDe || locale === "de";
|
||||
const availableTabs = tabs.filter((tab) => tab.available);
|
||||
const [activeTab, setActiveTab] = useState(availableTabs[0]?.id);
|
||||
const refs = useRef({});
|
||||
@@ -61,7 +63,21 @@ export default function SeriesTabMenu({ tabs, isEn = false, isEs = false, locale
|
||||
|
||||
return (
|
||||
<div id="diagrama-abas" className="scroll-mt-28">
|
||||
<div role="tablist" aria-label={effectiveIsEn ? "Board and diagram" : effectiveIsEs ? "Placa y diagrama" : "Placa e diagrama"} className="no-scrollbar flex gap-2 overflow-x-auto pb-1">
|
||||
<div
|
||||
role="tablist"
|
||||
aria-label={
|
||||
effectiveIsEn
|
||||
? "Board and diagram"
|
||||
: effectiveIsEs
|
||||
? "Placa y diagrama"
|
||||
: effectiveIsFr
|
||||
? "Carte et schéma"
|
||||
: effectiveIsDe
|
||||
? "Board und Diagramm"
|
||||
: "Placa e diagrama"
|
||||
}
|
||||
className="no-scrollbar flex gap-2 overflow-x-auto pb-1"
|
||||
>
|
||||
{availableTabs.map((tab, indice) => (
|
||||
<button
|
||||
key={tab.id}
|
||||
|
||||
@@ -0,0 +1,385 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss (Wi-Fi und Bluetooth)"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne",
|
||||
"RF"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedizierter HF-Pin. Vermeiden Sie lange Leiterbahnen ohne 50-Ohm-Impedanzanpassung."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Analoge 3.3V-Stromversorgung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V (3.0V bis 3.6V)",
|
||||
"Versorgt analoge und HF-Schaltungen des Chips mit Energie"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Analoge 3.3V-Stromversorgung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V (3.0V bis 3.6V)",
|
||||
"Versorgt analoge und HF-Schaltungen des Chips mit Energie"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Analoger Eingangspin ADC1 Kanal 0"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Analoger Eingangspin ADC1 Kanal 1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Beim Flash-Boot standardmäßig auf die Funktion SPI MISO (FSPIQ) gemappt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung (Power-up / Reset)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Aktiv High. Auf High-Pegel ziehen, um den Chip zu starten.",
|
||||
"Diesen Pin nicht unbeschaltet (floating) lassen. Für einen stabilen Start externe RC-Verzögerungsschaltung verwenden."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Analoger Eingangspin ADC1 Kanal 3"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO4",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"MTMS",
|
||||
"FSPIQ",
|
||||
"ADC1_CH4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTMS, SPI2 MISO und ADC1 Kanal 4.",
|
||||
"Kann zusammen mit anderen JTAG-Pins für JTAG-Debugging verwendet werden."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO5",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"MTDI",
|
||||
"FSPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTDI und SPI2 Write Protect (FSPIWP)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "VDD3P3_RTC",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der RTC-Domäne und Low-Power-E/As"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"MTCK",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTCK und SPI2-Takt (FSPICLK)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"MTDO",
|
||||
"FSPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTDO und SPI2 MOSI (FSPID)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Strapping-Pin für die Boot-Steuerung.",
|
||||
"Wählt zusammen mit GPIO9 den Boot-Modus des SoCs (muss beim Reset auf 1 liegen für Joint Download Boot, wenn GPIO9=0)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Primärer Strapping-Pin. High-Pegel (1) beim Reset aktiviert SPI-Boot (Standard über schwachen Pull-up).",
|
||||
"Low-Pegel (0) beim Reset versetzt den Chip in den UART/SPI-Download-Modus."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: SPI2 Chip Select 0 (FSPICS0)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "VDD3P3_CPU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Digitale Stromversorgung der CPU und zugehörigen E/As (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO18",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"UART0 receive pin (Serial RX by default for flashing and monitoring)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "GPIO20",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"UART0 transmit pin (Serial TX by default for flashing and monitoring)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Analoge 3.3V-Eingangsversorgung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Externer Quarzoszillator-Anschluss (Ausgang)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Externer Quarzoszillator-Anschluss (Eingang)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Analoge 3.3V-Eingangsversorgung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GND",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Zentraler Massepunkt (Exposed Pad)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Muss für stabile Leistung und Entwärmung ordnungsgemäß mit der Massefläche (GND) der Leiterplatte verlötet werden."
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,574 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "LNA_IN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Ein- und Ausgang für HF-Signale (Wi-Fi und Bluetooth) zur Antenne"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"XTAL_32K_P",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"XTAL_32K_N",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"This pin does not set boot mode, but connecting it with a pull-up is recommended to prevent glitches (see datasheet section 3.1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Ein High-Pegel an diesem Pin aktiviert den Betrieb des Chips",
|
||||
"Ein Low-Pegel an diesem Pin deaktiviert den Betrieb des Chips",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"ADC1_CH4",
|
||||
"FSPIHD",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"ADC2_CH0",
|
||||
"FSPIWP",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "VDD3P3_RTC",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der Low-Power-Domäne und Teilen der digitalen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"FSPICLK",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"FSPID",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "VDD3P3_CPU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungsein-/ausgang für internen/externen Flash-Speicher",
|
||||
"GPIO11"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts",
|
||||
"Kann nur als GPIO genutzt werden, wenn der Flash-Speicher über eine externe Quelle versorgt wird"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO18",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist an diesem Pin der interne Pull-up aktiviert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Negativer Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.2 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Positiver Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.2 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,862 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "VDDA6",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA7",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Negativer Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.3 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Positiver Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.3 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "VDDA8",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Ein High-Pegel an diesem Pin aktiviert den Betrieb des Chips",
|
||||
"Ein Low-Pegel an diesem Pin deaktiviert den Betrieb des Chips",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen Low-Power-Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"LP_GDIO0",
|
||||
"XTAL_32K_P",
|
||||
"LP_UART_DTRN"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"LP_GDIO1",
|
||||
"XTAL_32K_N",
|
||||
"LP_UART_DSRN",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"LP_GDIO2",
|
||||
"LP_UART_RTSN",
|
||||
"LP_I2C_SDA",
|
||||
"ADC1_CH1",
|
||||
"FSPIQ",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Die I2C_SDA-Funktion ist im Low-Power-Modus (LP) verfügbar",
|
||||
"Pin für Debugging genutzt",
|
||||
"Steuert die Frequenz des Quarzoszillators (siehe Abschnitt 3.5 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"LP_GDIO3",
|
||||
"LP_UART_CTSN",
|
||||
"LP_I2C_SCL",
|
||||
"ADC1_CH2",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"JTAG",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Die I2C_SDA-Funktion ist im Low-Power-Modus (LP) verfügbar",
|
||||
"Pin für Debugging genutzt",
|
||||
"Steuert das Timing des SDIO-Slave (siehe Abschnitt 3.2 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"LP_GDIO4",
|
||||
"LP_UART_RXD",
|
||||
"ADC1_CH3",
|
||||
"FSPIHD",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"LP_GDIO5",
|
||||
"LP_UART_TXD",
|
||||
"ADC1_CH4",
|
||||
"FSPIWP",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"LP_GDIO6",
|
||||
"ADC1_CH5",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"FSPID",
|
||||
"SDIO_DATA1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert die Quelle der JTAG-Signale (siehe Abschnitt 3.4 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8",
|
||||
"SDIO_DATA0",
|
||||
"PAD_COMP0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9",
|
||||
"SDIO_CLK",
|
||||
"PAD_COMP1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0",
|
||||
"SDIO_CMD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist an diesem Pin der interne Pull-up aktiviert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D-",
|
||||
"SDIO_DATA3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "GPIO14",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"USB_D+",
|
||||
"SDIO_DATA4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne USB-Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen USB-Pull-up konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDDPST2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen High-Performance-Domäne und Teilen der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "SPICS1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungsausgang für externen Flash",
|
||||
"GPIO19"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts",
|
||||
"Kann nur als GPIO genutzt werden, wenn der externe Flash-Speicher über eine externe Quelle versorgt wird"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GPIO23",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "GPIO24",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert das Timing des SDIO-Slave (siehe Abschnitt 3.4 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)",
|
||||
"Steuert die Ausgabe von ROM-Meldungen auf UART0 (siehe Abschnitt 3.3 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "GPIO28",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "VDDPST3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen High-Performance-Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "42",
|
||||
"nome": "ANT_2G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss für 2-GHz-Band"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "43",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "44",
|
||||
"nome": "VDDA3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "44",
|
||||
"nome": "VDDA4",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "45",
|
||||
"nome": "VDDA5",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "47",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "48",
|
||||
"nome": "ANT_5G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss für 5-GHz-Band"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,757 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Ein High-Pegel an diesem Pin aktiviert den Betrieb des Chips",
|
||||
"Ein Low-Pegel an diesem Pin deaktiviert den Betrieb des Chips",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen Low-Power-Domäne und Teilen der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"LP_GDIO0",
|
||||
"XTAL_32K_P",
|
||||
"LP_UART_DTRN",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"LP_GDIO1",
|
||||
"XTAL_32K_N",
|
||||
"LP_UART_DSRN",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"LP_GDIO2",
|
||||
"LP_UART_RTSN",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"LP_GDIO3",
|
||||
"LP_UART_CTSN",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"LP_GDIO4",
|
||||
"LP_UART_RXD",
|
||||
"ADC1_CH3",
|
||||
"FSPIHD",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt",
|
||||
"Steuert das Timing des SDIO-Slave (siehe Abschnitt 3.2 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"LP_GDIO5",
|
||||
"LP_UART_TXD",
|
||||
"ADC1_CH5",
|
||||
"FSPIWP",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt",
|
||||
"Steuert das Timing des SDIO-Slave (siehe Abschnitt 3.2 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"LP_GDIO6",
|
||||
"LP_I2C_SDA",
|
||||
"ADC1_CH6",
|
||||
"FSPICLK",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Die I2C_SDA-Funktion ist im Low-Power-Modus (LP) verfügbar",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"LP_GDIO7",
|
||||
"LP_I2C_SCL",
|
||||
"FSPID",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"I2C",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Die I2C_SDA-Funktion ist im Low-Power-Modus (LP) verfügbar",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)",
|
||||
"Steuert die Ausgabe von ROM-Meldungen auf UART0 (siehe Abschnitt 3.3 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungsein-/ausgang für Flash-Speicher",
|
||||
"GPIO27"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts",
|
||||
"Kann nur als GPIO genutzt werden, wenn der externe Flash-Speicher über eine externe Quelle versorgt wird"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO29",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO30",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Vom SPI-Flash-Speicher belegt",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "GPIO15",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert die Quelle der JTAG-Signale (siehe Abschnitt 3.4 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der digitalen High-Performance-Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"U0TXD",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist an diesem Pin der interne Pull-up aktiviert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"U0RXD",
|
||||
"FSPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "SDIO_CMD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"SDIO_CMD",
|
||||
"FSPICS2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "SDIO_CLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"SDIO_CLK",
|
||||
"FSPICS3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "SDIO_DATA0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SDIO_DATA0",
|
||||
"FSPICS4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "SDIO_DATA1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SDIO_DATA1",
|
||||
"FSPICS5"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "SDIO_DATA2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SDIO_DATA2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "SDIO_DATA3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"SDIO_DATA3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist der interne Pull-up aktiviert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Negativer Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Positiver Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,642 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT_2G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss (Wi-Fi und Bluetooth)"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne",
|
||||
"RF"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated 2.4 GHz RF pin. Requires 50-ohm impedance matching."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der analogen Domäne (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V (3.0V bis 3.6V). Versorgt HF- und Taktschaltungen mit Energie."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA4",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der analogen Domäne (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V (3.0V bis 3.6V). Versorgt HF- und Taktschaltungen mit Energie."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung (Power-up / Reset)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Aktiv High. Auf High-Pegel ziehen, um den Chip zu starten.",
|
||||
"Do not leave this pin floating. An external RC circuit is recommended for clean reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Digitale Stromversorgung der HP- und LP-Domänen (High Performance / Low Power)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V. Versorgt den digitalen Low-Power-Bereich und zugehörige Pins."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"XTAL_32K_P"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Low-power multifunction pin. Can connect to external 32 kHz crystal (Input P)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"XTAL_32K_N",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin. External 32 kHz crystal connection (Output N) and ADC1 Channel 0 analog input."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"MTMS",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTMS, ADC1 Kanal 1 und Strapping-Pin für SDIO-Taktflankensteuerung.",
|
||||
"Floating by default during reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO4",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"MTDI",
|
||||
"ADC1_CH2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunktionspin: JTAG MTDI, ADC1 Kanal 2 und Strapping-Pin für SDIO-Taktflankensteuerung.",
|
||||
"Floating by default during reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "GPIO5",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"MTCK",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin: JTAG MTCK and ADC1 Channel 3 analog input."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin: JTAG MTDO."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25",
|
||||
"SDIO_CMD",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Command or SPI2 Chip Select 0."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"SDIO_CLK",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Clock or SPI2 Clock."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27",
|
||||
"SDIO_DATA0",
|
||||
"FSPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Data 0 or SPI2 MOSI (FSPID)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO28",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28",
|
||||
"SDIO_DATA1",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 1 or SPI2 MISO (FSPIQ)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO22",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SDIO_DATA2",
|
||||
"FSPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 2 or SPI2 Write Protect."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO23",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"SDIO_DATA3",
|
||||
"FSPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 3 or SPI2 Hold."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO14",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"SPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated Chip Select 1 pin for SPI Flash/PSRAM memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "GPIO15",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated Chip Select 0 pin for SPI Flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "VDDPST2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der digitalen HP-Domäne (High Performance)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V (3.0V bis 3.6V). Versorgt die schnellen digitalen Schnittstellen."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "GPIO16",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Data Q (MISO) pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "GPIO17",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Write Protect pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Aus VDDPST2 generierte LDO-Ausgangsspannung zur Speisung von Flash und PSRAM"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Ausgangsspannung per Software konfigurierbar gemäß Flash-Spezifikation (üblicherweise 3.3V oder 1.8V).",
|
||||
"Must not be used as a general high-current power source."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Hold control pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO20",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Clock signal pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "GPIO21",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Data D (MOSI) pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Negative signal pin of integrated USB Serial/JTAG transceiver."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Positive signal pin of integrated USB Serial/JTAG transceiver.",
|
||||
"Verfügt über integrierten Pull-up-Widerstand, der beim USB-Start standardmäßig aktiv ist."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "GPIO24",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Strapping pin for boot mode selection and ROM log printing control.",
|
||||
"Floating by default during reset. High level (1) enables boot log printing."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Primary Strapping pin for boot mode selection.",
|
||||
"Mit integriertem schwachen Pull-up ausgestattet. High-Pegel (1) beim Reset aktiviert SPI-Boot (Flash). Low-Pegel (0) erzwingt den Download-Modus."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Serieller Empfang UART0 (Serial RX für externes Flashen und Debugging)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Serielle Übertragung UART0 (Serial TX für externes Flashen und Debugging)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "GPIO29",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO29"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Strapping pin for JTAG signal source selection (early boot).",
|
||||
"Keine internen Pull-Widerstände beim Reset. Muss bei Verwendung extern stabil gehalten werden."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der analogen Domäne (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Externer 40-MHz-Quarzoszillator-Anschluss (Ausgang N)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Externer 40-MHz-Quarzoszillator-Anschluss (Eingang P)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Stromversorgung der analogen Domäne (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "GND",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Zentraler Massepunkt (Exposed Pad)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Muss für stabilen HF- und thermischen Betrieb ordnungsgemäß mit der Massefläche (GND) der Leiterplatte verlötet werden."
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,549 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"FSPICS0",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"FSPIWP",
|
||||
"ADC1_CH1",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"FSPIHD",
|
||||
"ADC1_CH2",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"FSPICLK",
|
||||
"ADC1_CH3",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"FSPID",
|
||||
"ADC1_CH4",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der E/A-Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)",
|
||||
"Steuert die Ausgabe von ROM-Meldungen auf UART0 (siehe Abschnitt 3.3 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Steuert den Boot-Modus des Chips (siehe Abschnitt 3.1 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"ZCD0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"ZCD1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"XTAL_32K_P"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"XTAL_32K_N"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Chip-Aktivierung"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Ein High-Pegel an diesem Pin aktiviert den Betrieb des Chips",
|
||||
"Ein Low-Pegel an diesem Pin deaktiviert den Betrieb des Chips",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "VBAT",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne oder Batterie"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "VDDA_PMU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der E/A-Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "GPIO22",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"U0RXD",
|
||||
"FSPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"U0TXD",
|
||||
"FSPICS2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen Pull-up konfiguriert",
|
||||
"Pin für Debugging genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"FSPICS3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Während des Resets ist dieser Pin als Eingang konfiguriert",
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Steuert die Quelle der JTAG-Signale (siehe Abschnitt 3.3 des Datenblatts für Details)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"FSPICS4",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27",
|
||||
"FSPICS5",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Nach dem Reset ist dieser Pin als Eingang mit aktivem internen USB-Pull-up konfiguriert",
|
||||
"Standardmäßig wird dieser Pin für USB Serial/JTAG genutzt"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Negativer Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.2 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Positiver Taktein-/ausgang"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.3.2 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Versorgungseingang der analogen Domäne"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Empfohlene Spannung: 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Weitere Details zur Stromversorgung des Chips finden Sie in Abschnitt 2.5 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"HF-Antennenanschluss"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Weitere Details zu analogen Pins finden Sie in Abschnitt 2.4 des Datenblatts"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Elektrische Schaltungsmasse (GND)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
@@ -0,0 +1,423 @@
|
||||
{
|
||||
"ESP-IDF": {
|
||||
"nome": "ESP-IDF",
|
||||
"icone": "⚙️",
|
||||
"nome_completo": "Espressif IoT Development Framework",
|
||||
"descricao": "Offizielles natives Framework von Espressif für alle ESP32-SoCs. Basiert auf Multicore-FreeRTOS und CMake und bietet die vollständige Kontrolle über Silizium, Peripheriegeräte, Funk sowie eine modulare Komponentenarchitektur.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Offizielles Basis-Framework",
|
||||
"funcao_principal": "Industrielle und hochperformante Entwicklung mit direktem Registerzugriff, Echtzeit-RTOS und vollständigem Protokoll-Stack",
|
||||
"caracteristicas": [
|
||||
"Echtzeitbetriebssystem (FreeRTOS SMP Multicore)",
|
||||
"Nativer Support für ESP Component Registry über idf_component.yml",
|
||||
"Vollständiger Konnektivitäts-Stack für Wi-Fi 4/6, BLE 5.x, Zigbee und Thread",
|
||||
"Unterstützung aller SoCs (ESP32, S2, S3, C2, C3, C6, H2, P4)",
|
||||
"Erweitertes Energiemanagement und Deep-Sleep-Modi",
|
||||
"Robuste Sicherheit: Secure Boot v2, Flash-Verschlüsselung und Hardware-Kryptografie",
|
||||
"Verschlüsselte OTA-Updates mit automatischem Rollback",
|
||||
"Moderne Clang/GCC-Toolchain, C++23-Unterstützung und JTAG-OpenOCD-Debugging"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Kommerzielle und industrielle IoT-Produkte",
|
||||
"Geräte mit strengen Batterie- und Low-Power-Anforderungen",
|
||||
"Echtzeitanwendungen mit präziser Interrupt-Steuerung",
|
||||
"Sicherheitssysteme mit Hardware-Verschlüsselung",
|
||||
"Leistungsstarke Multiprotokoll-Gateways"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-idf.c",
|
||||
"exemplos": "https://github.com/espressif/esp-idf/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-idf/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-idf",
|
||||
"cor": "#E74C3C"
|
||||
},
|
||||
"ESP-RainMaker": {
|
||||
"nome": "ESP-RainMaker",
|
||||
"icone": "☁️",
|
||||
"nome_completo": "ESP RainMaker AIoT Cloud Platform",
|
||||
"descricao": "Komplette Cloud- und Firmware-Plattform von Espressif für vernetzte Produkte. Ermöglicht die Entwicklung von IoT-Geräten ohne eigenen Backend- oder App-Aufbau von Grund auf.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Cloud & AIoT Framework",
|
||||
"funcao_principal": "Beschleunigte Entwicklung intelligenter Produkte mit mobilen Apps (iOS/Android), AWS-Serverless-Cloud und Sprachsteuerung (Alexa/Google Home)",
|
||||
"caracteristicas": [
|
||||
"Assistiere Wi-Fi- und BLE-Bereitstellung über die offizielle mobile App",
|
||||
"Dynamische Generierung der Benutzeroberfläche in der App basierend auf Firmware-Parametern",
|
||||
"Native Integration mit Alexa und Google Assistant",
|
||||
"Gleichzeitige lokale Steuerung (über mDNS/HTTP) und Cloud-Steuerung",
|
||||
"RainMaker-Dashboard für Flottenmanagement und OTA-Aktualisierungen",
|
||||
"Native Kompatibilität mit Matter-Knoten und Geräte-Bridges",
|
||||
"Integrierte Bibliothek über ESP Component Registry (espressif/esp_rainmaker)"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Smarte Haushaltsgeräte und vernetzte weiße Ware",
|
||||
"Intelligente Beleuchtung und Steckdosen für Endverbraucher",
|
||||
"Klimasysteme (HVAC) und vernetzte Thermostate",
|
||||
"Kommerzielle IoT-Prototypen mit schneller Marktvalidierung",
|
||||
"Produkte mit Zertifizierungsanforderungen für Apple Home, Alexa und Google Home"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-rainmaker.c",
|
||||
"exemplos": "https://github.com/espressif/esp-rainmaker/tree/master/examples",
|
||||
"documentacao": "https://rainmaker.espressif.com/docs/get-started.html",
|
||||
"repositorio": "https://github.com/espressif/esp-rainmaker",
|
||||
"cor": "#2980B9"
|
||||
},
|
||||
"ESP-Matter": {
|
||||
"nome": "ESP-Matter",
|
||||
"icone": "🏠",
|
||||
"nome_completo": "ESP-Matter SDK",
|
||||
"descricao": "Offizielles SDK von Espressif für den universellen Matter-Standard (CSA). Bietet direkte Interoperabilität mit Apple Home, Google Home, Alexa und SmartThings.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Smart Home Framework",
|
||||
"funcao_principal": "Entwicklung einheitlicher, interoperabler Smart-Home-Geräte über Wi-Fi oder Thread (OpenThread)",
|
||||
"caracteristicas": [
|
||||
"Standardkonforme Implementierung von Connected Home over IP (Project CHIP / CSA)",
|
||||
"Unterstützung für Matter over Wi-Fi (ESP32, S3, C3, C6) und Matter over Thread (ESP32-H2, C6)",
|
||||
"Unterstützung für Endgeräte-Rollen (Device), Controller und Bridges (Matter Bridge)",
|
||||
"Sichere universelle Kopplung mit DAC-Zertifikaten (Device Attestation Certificate)",
|
||||
"Nahtlose Integration mit ESP-IDF und ESP-RainMaker",
|
||||
"Standard-Cluster-Unterstützung: Ein/Aus, Dimmer, Sensoren, Thermostate",
|
||||
"Synchronisation mit Apple-, Google-, Alexa- und SmartThings-Ökosystemen ohne herstellerspezifisches Gateway"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Matter-zertifizierte Smart-Home-Geräte (Lampen, Steckdosen, Schlösser)",
|
||||
"Bridges von Zigbee/BLE zu Matter (Matter Bridges)",
|
||||
"Energiesparende Umgebungssensoren in Thread-Netzwerken (ESP32-H2)",
|
||||
"Universelle Wandtaster und Aktoren",
|
||||
"Ökosystem-übergreifende Geräte ohne proprietäre App-Pflicht"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-matter.c",
|
||||
"exemplos": "https://github.com/espressif/esp-matter/tree/main/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-matter/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-matter",
|
||||
"cor": "#16A085"
|
||||
},
|
||||
"ESP-ADF": {
|
||||
"nome": "ESP-ADF",
|
||||
"icone": "🎵",
|
||||
"nome_completo": "ESP Audio Development Framework",
|
||||
"descricao": "Offizielles Framework für Audioanwendungen auf ESP32-SoCs. Enthält Pipelines für Decodierung/Codierung, Treiber für I2S-Codecs und Netzwerk-Audiostreaming.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Audio Processing Framework",
|
||||
"funcao_principal": "Audioverarbeitung, Erfassung, Wiedergabe und Streaming auf eingebetteten Systemen mit Hardware- und Software-Codecs",
|
||||
"caracteristicas": [
|
||||
"Elementbasierte Pipeline-Architektur (Audio Pipeline Framework)",
|
||||
"Decodierung und Codierung: MP3, AAC, WAV, OGG, FLAC, OPUS und AMR",
|
||||
"Integrierte Treiber für gängige I2S-Codecs (ES8388, ES8311, TAS5805M, AC101)",
|
||||
"Streaming-Protokolle: HTTP Live Streaming (HLS), DLNA, SIP und Webradio",
|
||||
"Integration mit ESP-SR für lokale Sprachsteuerung und akustische Echounterdrückung (AEC)",
|
||||
"Lautstärkeregelung, grafischer Equalizer (EQ) und Mehrkanal-Audiomixer",
|
||||
"Unterstützung für Bluetooth-Audioprofile: A2DP Sink, A2DP Source und BLE Audio"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Smarte Lautsprecher und Bluetooth-/Wi-Fi-Audioempfänger",
|
||||
"Zweiwege-Gegensprechanlagen (VoIP / SIP)",
|
||||
"Intelligente Türklingeln mit Audioerfassung und -übertragung",
|
||||
"Netzwerk-Audioplayer für Online-Radio und Podcasts",
|
||||
"Alarmsysteme und industrielle akustische Rückmeldungen"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-adf.c",
|
||||
"exemplos": "https://github.com/espressif/esp-adf/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-adf/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-adf",
|
||||
"cor": "#9B59B6"
|
||||
},
|
||||
"ESP-SR": {
|
||||
"nome": "ESP-SR",
|
||||
"icone": "🎙️",
|
||||
"nome_completo": "ESP Speech Recognition Framework",
|
||||
"descricao": "Framework von Espressif für Spracherkennung und lokale Audioverarbeitung (On-Device) ohne Internetverbindung – mit minimaler Latenz und vollem Datenschutz.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "AI & Speech Framework",
|
||||
"funcao_principal": "On-Chip-Spracherkennung: Wake-Word-Erkennung (WakeNet) und lokale Offline-Befehle (MultiNet)",
|
||||
"caracteristicas": [
|
||||
"WakeNet-Aktivierungsworterkennung (z. B. 'Hi ESP', 'Hi Lexin') mit hoher Präzision",
|
||||
"Erkennung lokaler MultiNet-Befehle mit mehrsprachiger Unterstützung",
|
||||
"Akustisches Front-End (AFE): akustische Echounterdrückung (AEC)",
|
||||
"Hintergrundgeräuschunterdrückung (BSS/NS) und Richtmikrofonie (Beamforming)",
|
||||
"Automatische Verstärkungsregelung (AGC) und Sprachaktivitätserkennung (VAD)",
|
||||
"Vektorbeschleunigung auf ESP32-S3 (Xtensa-SIMD-Instruktionen)",
|
||||
"Vollständiger Offline-Betrieb ohne Datenübertragung an Cloud-Dienste"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Wandbedienfelder für die Gebäudeautomation mit Sprachsteuerung",
|
||||
"Sprachgesteuerte Haushaltsgeräte ohne Internetabhängigkeit",
|
||||
"Industriegeräte mit freihändiger Bedienung",
|
||||
"Interaktives Spielzeug und Lernsysteme",
|
||||
"Sprachschnittstellen mit strikten Datenschutzanforderungen"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-sr.c",
|
||||
"exemplos": "https://github.com/espressif/esp-sr/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-sr/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-sr",
|
||||
"cor": "#3498DB"
|
||||
},
|
||||
"ESP-IoT-Solution": {
|
||||
"nome": "ESP-IoT-Solution",
|
||||
"icone": "🧰",
|
||||
"nome_completo": "ESP-IoT-Solution Component Library",
|
||||
"descricao": "Offizielle Sammlung von Peripherietreibern, Touch-Algorithmen, Energieverwaltungsfunktionen und IoT-Dienstprogrammen zur Beschleunigung der Entwicklung auf ESP-IDF.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Drivers & IoT Utilities",
|
||||
"funcao_principal": "Einsatzbereite Bibliothek für Sensortreiber, Displays, Industriebusse und kapazitive Berührungssensorik",
|
||||
"caracteristicas": [
|
||||
"Fertige Treiber für Sensoren (I2C, SPI): Temperatur, Druck, IMU, Licht",
|
||||
"Treiber für OLED- und LCD-Displays (SSD1306, ST7789, ILI9341, GC9A01)",
|
||||
"Erweiterte Tastenverwaltung (Klick, Doppelklick, langes Drücken) und Drehimpulsgeber",
|
||||
"Kapazitive Berührungsalgorithmen: Tasten, Schieberegler, Räder und Näherungserkennung",
|
||||
"E/A-Expander-Treiber (PCA9557, MCP23017, CH422G)",
|
||||
"Komponenten für Industriebusse: Modbus RTU/TCP und RS485-Kommunikation",
|
||||
"Direkte Einbindung als ESP-IDF-Komponenten über idf_component.yml"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Kapazitive Touch-Oberflächen für Haushaltsgeräte und Wandtaster",
|
||||
"Wetterstationen und Umweltmonitore mit I2C-Sensoren",
|
||||
"Industrielle Automatisierungsgeräte mit RS485- und Modbus-Kommunikation",
|
||||
"Projekte mit Grafikdisplays und Drehreglern",
|
||||
"Systeme mit komplexen Tastenkombinationen und Benutzerereignissen"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-iot-solution.c",
|
||||
"exemplos": "https://github.com/espressif/esp-iot-solution/tree/usb/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-iot-solution/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-iot-solution",
|
||||
"cor": "#F39C12"
|
||||
},
|
||||
"ESP-NOW": {
|
||||
"nome": "ESP-NOW",
|
||||
"icone": "⚡",
|
||||
"nome_completo": "ESP-NOW Wireless Communication Protocol",
|
||||
"descricao": "Proprietäres Drahtlosprotokoll von Espressif basierend auf 802.11-Aktionsframes. Ermöglicht schnelle, energiesparende Punkt-zu-Punkt-Kommunikation ohne Wi-Fi-Router.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Fast Wireless Protocol",
|
||||
"funcao_principal": "Ultraschnelle, energiesparende Funkkommunikation zwischen ESP-Geräten ohne Wi-Fi-Router",
|
||||
"caracteristicas": [
|
||||
"Direkte Peer-to-Peer-Kommunikation ohne Verbindungsaushandlung oder Access Point",
|
||||
"Extrem geringe Übertragungsverzögerung: Latenzen im Millisekundenbereich",
|
||||
"Unterstützung für Unicast- und Broadcast-Übertragungen",
|
||||
"Sichere Frame-Verschlüsselung mit CCMP-Schlüsseln (AES-128)",
|
||||
"Geringer Energieverbrauch, ideal für batteriebetriebene Sensoren",
|
||||
"Rückwärtskompatibel mit allen ESP32- und ESP8266-Modellen",
|
||||
"Nutzlast bis zu 250 Bytes pro Paket – ausreichend für Telemetrie und Schaltbefehle"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Fernbedienungen und Funkschalter mit sofortigem Aufwachen",
|
||||
"Batteriebetriebene Sensornetzwerke mit periodischer Messwertübertragung",
|
||||
"Steuerungen für Drohnen, Roboter und RC-Modelle",
|
||||
"Industrielle Not-Aus-Taster mit kritischen Latenzanforderungen",
|
||||
"Lokale Ausfallsicherung bei nicht verfügbarem WLAN-Netzwerk"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-now.c",
|
||||
"exemplos": "https://github.com/espressif/esp-now/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-now/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-now",
|
||||
"cor": "#E67E22"
|
||||
},
|
||||
"ESP-Zigbee-SDK": {
|
||||
"nome": "ESP-Zigbee-SDK",
|
||||
"icone": "🐝",
|
||||
"nome_completo": "Espressif Zigbee Software Development Kit",
|
||||
"descricao": "Offizielles SDK für die Entwicklung von Zigbee 3.0-Geräten auf SoCs mit 802.15.4-Funk (ESP32-H2 und ESP32-C6). Unterstützt Koordinator-, Router- und Endgeräte-Rollen.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Mesh & 802.15.4 Framework",
|
||||
"funcao_principal": "Entwicklung von Geräten für Zigbee 3.0-Mesh-Netzwerke mit zertifizierter industrieller Interoperabilität",
|
||||
"caracteristicas": [
|
||||
"Konform mit den Spezifikationen Zigbee 3.0 und Zigbee PRO",
|
||||
"Unterstützung aller Netzwerkrollen: Koordinator (ZC), Router (ZR) und Endgerät (ZED)",
|
||||
"Energiesparende Sleepy-End-Device-Rollen (SED) für Batteriebetrieb",
|
||||
"Unterstützung von Standardprofilen: Zigbee Home Automation (ZHA) und Light Link",
|
||||
"Zigbee-zu-Wi-Fi/Ethernet-Gateway in Kombination von ESP32-H2 mit Zweit-SoC",
|
||||
"Standardkonforme Zigbee-OTA-Cluster-Firmware-Updates",
|
||||
"Nahtlose Integration mit ESP-IDF und Z-Stack-Kompatibilität"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Türkontakte, Bewegungsmelder und Wassersensoren im Batteriebetrieb",
|
||||
"Interoperable Zigbee 3.0-Leuchtmittel, Dimmer und Wandschalter",
|
||||
"Zigbee-zu-Ethernet/Wi-Fi-Gateways für Smart-Home-Zentralen",
|
||||
"Industrielle Thermostate und Energiezähler",
|
||||
"Erweiterung bestehender Installationen im standardisierten Zigbee-Ökosystem"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-zigbee.c",
|
||||
"exemplos": "https://github.com/espressif/esp-zigbee-sdk/tree/main/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-zigbee-sdk/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-zigbee-sdk",
|
||||
"cor": "#F1C40F"
|
||||
},
|
||||
"ESP-WHO": {
|
||||
"nome": "ESP-WHO",
|
||||
"icone": "👁️",
|
||||
"nome_completo": "ESP-WHO Face Detection & Recognition Framework",
|
||||
"descricao": "Computer-Vision-Framework für ESP32, optimiert für Kameramodule (OV2640, OV3660, OV5640) mit lokaler Gesichtserkennung und Identifikation.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Computer Vision & Edge AI",
|
||||
"funcao_principal": "Eingebettete Bildverarbeitung mit Gesichtserkennung, Ausrichtung und Identifikation",
|
||||
"caracteristicas": [
|
||||
"Leichtgewichtige Inferenzmodelle, optimiert für ESP32 und ESP32-S3",
|
||||
"Deep-Learning-basierte Gesichtserkennung mit Bestimmung von Gesichtsmerkmalen",
|
||||
"Gesichtserkennung und Registrierung direkt im Gerätespeicher",
|
||||
"Performanter Kameratreiber für DVP- und SPI-Busse",
|
||||
"Unterstützung von Bildauflösungen von QVGA bis QSXGA",
|
||||
"Vektorbeschleunigung durch dedizierte KI-Befehle des ESP32-S3",
|
||||
"Integrierter HTTP-Videostreaming-Server für Debugging und Vorschau"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Biometrische Zugangskontrollen und intelligente Türschlösser",
|
||||
"Video-Türklingeln mit Personen- und Anwesenheitserkennung",
|
||||
"Personenzählung und Belegungsanalyse für Konferenzräume",
|
||||
"Intelligente Sicherheitskameras mit lokaler Fehlalarmfilterung",
|
||||
"Assistenzgeräte und Mensch-Maschine-Interaktion"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-who.c",
|
||||
"exemplos": "https://github.com/espressif/esp-who/tree/master/examples",
|
||||
"documentacao": "https://github.com/espressif/esp-who#readme",
|
||||
"repositorio": "https://github.com/espressif/esp-who",
|
||||
"cor": "#1ABC9C"
|
||||
},
|
||||
"ESP-NN": {
|
||||
"nome": "ESP-NN",
|
||||
"icone": "🧠",
|
||||
"nome_completo": "ESP Neural Network Acceleration Library",
|
||||
"descricao": "Beschleunigungsbibliothek für neuronale Netze auf ESP32-SoCs zur Optimierung von Faltungskernen, Matrixmultiplikationen und Aktivierungsfunktionen für Edge-KI.",
|
||||
"linguagem": "C / C++ / Asm",
|
||||
"tipo": "Neural Network Kernel Library",
|
||||
"funcao_principal": "Hochoptimierte Assembler-Kerne für neuronale Inferenz unter TensorFlow Lite for Microcontrollers",
|
||||
"caracteristicas": [
|
||||
"Assembler-Optimierungen unter Nutzung der SIMD-Vektorbefehle des ESP32-S3",
|
||||
"Beschleunigte Operationen: 2D-Faltung, Depthwise Conv, Fully Connected und Pooling",
|
||||
"Unterstützung für 8-Bit- (int8) und 16-Bit-Quantisierung (int16)",
|
||||
"Nahtlose Integration als Optimierungs-Backend für TensorFlow Lite for Microcontrollers",
|
||||
"Deutliche Reduzierung der Inferenzlatenz gegenüber generischen Implementierungen",
|
||||
"Optimierter SRAM-Speicherbedarf für ressourcenbeschränkte Mikrocontroller",
|
||||
"Unterstützung für ESP32, ESP32-S3 und RISC-V-Architekturen (C3, C6, P4)"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Edge-Vision-Modelle (Objekterkennung und Klassifikation)",
|
||||
"Vibrations- und Akustikanomalieerkennung für vorausschauende Wartung",
|
||||
"Klassifikation biometrischer Signale (EKG, PPG) auf Wearables",
|
||||
"Gestenerkennung und Schnittstellen basierend auf Inertialsensoren (IMU)",
|
||||
"Benutzerdefinierte Audiomodelle zur Erkennung spezifischer Signalmuster"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-nn.c",
|
||||
"exemplos": "https://github.com/espressif/esp-nn/tree/master/examples",
|
||||
"documentacao": "https://github.com/espressif/esp-nn#readme",
|
||||
"repositorio": "https://github.com/espressif/esp-nn",
|
||||
"cor": "#8E44AD"
|
||||
},
|
||||
"ESP-DSP": {
|
||||
"nome": "ESP-DSP",
|
||||
"icone": "📊",
|
||||
"nome_completo": "ESP Digital Signal Processing Library",
|
||||
"descricao": "Offizielle DSP-Bibliothek für ESP32-SoCs mit Algorithmen für FFT, digitale Filterung, Matrixberechnungen und numerische Operationen.",
|
||||
"linguagem": "C / Asm",
|
||||
"tipo": "DSP & Math Library",
|
||||
"funcao_principal": "Hochperformante mathematische Funktionen und digitale Signalverarbeitung mit Hardware-Optimierung",
|
||||
"caracteristicas": [
|
||||
"Schnelle Fourier-Transformation (FFT) für reelle und komplexe Daten mit Fensterfunktionen (Hann, Hamming, Blackman)",
|
||||
"Optimierte digitale IIR- (Biquad) und FIR-Filter",
|
||||
"Matrixoperationen: Multiplikation, Invertierung, Zerlegung und Transposition",
|
||||
"Hardware-beschleunigte Gleitkomma- und Ganzzahl-Vektoroperationen",
|
||||
"Generierung von Testsignalen: Sinus, weißes Rauschen und modulierte Signale",
|
||||
"Assembler-Routinen für den Xtensa-Kern und Vektorinstruktionserweiterungen",
|
||||
"Kompatibel mit ESP-IDF als native Komponente"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Echtzeit-Spektrumanalyse für Audio- und Schwingungsmessgeräte",
|
||||
"Signalverarbeitung und Rauschfilterung für industrielle Sensoren",
|
||||
"Regelungsalgorithmen für Motorsteuerungen und Wechselrichter",
|
||||
"Intelligente Stromzähler mit Wirk- und Blindleistungsberechnung",
|
||||
"Signalanalyse für Radarsensoren und Ultraschallmessungen"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-dsp.c",
|
||||
"exemplos": "https://github.com/espressif/esp-dsp/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-dsp/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-dsp",
|
||||
"cor": "#2C3E50"
|
||||
},
|
||||
"Rust-ESP": {
|
||||
"nome": "Rust-ESP",
|
||||
"icone": "🦀",
|
||||
"nome_completo": "Rust on ESP32 Ecosystem",
|
||||
"descricao": "Rust-Entwicklungsökosystem für ESP32-Mikrocontroller. Bietet Speichersicherheit ohne Garbage Collector, ein starkes Typsystem und moderne Ausdrucksstärke.",
|
||||
"linguagem": "Rust",
|
||||
"tipo": "Memory-Safe Modern Language",
|
||||
"funcao_principal": "Entwicklung robuster Firmware mit Schutz vor Speicherbeschädigungen und garantierter Datenrennfreiheit bei Nebenläufigkeit",
|
||||
"caracteristicas": [
|
||||
"Zwei Entwicklungsansätze: no_std (Bare-Metal über esp-hal) und std (auf FreeRTOS über esp-idf-svc)",
|
||||
"Offizielle Rust-Toolchain für Xtensa- und RISC-V-Architekturen",
|
||||
"Garantierte Speichersicherheit zur Kompilierzeit",
|
||||
"Modernes asynchrones Modell mit async/await für Netzwerk- und E/A-Aufgaben",
|
||||
"Unterstützung für Wi-Fi-, BLE-, MQTT-, HTTP- und TLS-Stacks über Ökosystem-Crates",
|
||||
"Kommandozeilenwerkzeug espflash zum Flashen und Überwachen von Entwicklungsboards",
|
||||
"Direkte Integration mit Cargo und dem gesamten Rust-Open-Source-Ökosystem"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Industrielle kritische Firmware mit höchsten Zuverlässigkeitsanforderungen",
|
||||
"Medizin- und Sicherheitsgeräte, bei denen Speicherfehler unzulässig sind",
|
||||
"Netzwerk-Gateways mit sicherer Verarbeitung kryptografischer und TLS-Protokolle",
|
||||
"Moderne eingebettete Anwendungen mit asynchroner Nebenläufigkeit",
|
||||
"Projekte nach neuesten Standards des modernen Embedded Software Engineerings"
|
||||
],
|
||||
"exemplo": "/exemplos/rust-esp.rs",
|
||||
"exemplos": "https://github.com/esp-rs/esp-idf-template",
|
||||
"documentacao": "https://esp-rs.github.io/book/",
|
||||
"repositorio": "https://github.com/esp-rs",
|
||||
"cor": "#D35400"
|
||||
},
|
||||
"Arduino": {
|
||||
"nome": "Arduino",
|
||||
"icone": "♾️",
|
||||
"nome_completo": "Arduino Core for ESP32",
|
||||
"descricao": "Offizieller Arduino-Core für ESP32-SoCs. Bietet die vertraute setup()/loop()-API mit Zugriff auf Tausende Bibliotheken von Drittanbietern auf einem stabilen ESP-IDF-Fundament.",
|
||||
"linguagem": "C++ (Arduino)",
|
||||
"tipo": "Maker & Educational Framework",
|
||||
"funcao_principal": "Schnelles Prototyping und zugängliche Projekterstellung mit dem weltweit größten Open-Source-Bibliotheksökosystem",
|
||||
"caracteristicas": [
|
||||
"Vertraute Struktur aus setup()-Initialisierung und loop()-Hauptschleife",
|
||||
"Sofortiger Zugriff auf das riesige Repository der Arduino-Bibliotheken",
|
||||
"Basiert im Hintergrund auf FreeRTOS und erlaubt eigene Tasks per xTaskCreate",
|
||||
"Unterstützung für nahezu jedes ESP32-Entwicklungsboard am Markt",
|
||||
"Intuitives Wi-Fi- und Bluetooth-Management (WiFi, BluetoothSerial, BLEDevice)",
|
||||
"Einfache OTA-Firmware-Updates über die ArduinoOTA-Klasse",
|
||||
"Kompatibel mit Arduino IDE, PlatformIO, VS Code und Arduino CLI"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Schnelles Prototyping von IoT-Projekten und Machbarkeitsstudien",
|
||||
"Ausbildung, universitäre Lehre und Schulung in eingebetteten Systemen",
|
||||
"Maker-Projekte und Do-It-Yourself-Elektronik",
|
||||
"Geräte mit bestehenden Sensor- und Aktor-Bibliotheken",
|
||||
"Interaktive Kunstinstallationen und Funktionsmodelle"
|
||||
],
|
||||
"exemplo": "/exemplos/arduino.ino",
|
||||
"exemplos": "https://github.com/espressif/arduino-esp32/tree/master/libraries",
|
||||
"documentacao": "https://docs.espressif.com/projects/arduino-esp32/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/arduino-esp32",
|
||||
"cor": "#00979C"
|
||||
},
|
||||
"MicroPython": {
|
||||
"nome": "MicroPython",
|
||||
"icone": "🐍",
|
||||
"nome_completo": "MicroPython for ESP32",
|
||||
"descricao": "Schlanke und effiziente Python-3-Implementierung für Mikrocontroller. Ermöglicht interaktive Programmierung über REPL an der seriellen Schnittstelle ohne vorherige Kompilierung.",
|
||||
"linguagem": "Python 3",
|
||||
"tipo": "Interactive Scripting Engine",
|
||||
"funcao_principal": "Schnelle und interaktive Entwicklung mit der Einfachheit von Python und unmittelbarem Hardwarezugriff",
|
||||
"caracteristicas": [
|
||||
"Vollständiger Python-3-Interpreter, optimiert für Mikrocontroller",
|
||||
"Interaktive REPL-Konsole (Read-Eval-Print Loop) über serielle Schnittstelle oder Wi-Fi (WebREPL)",
|
||||
"Virtuelles Dateisystem mit Unterstützung für .py-Dateien und vorkompilierte .mpy-Module",
|
||||
"Intuitive Hardwaremodule: machine (Pin, ADC, PWM, I2C, SPI, UART, Timer, RTC)",
|
||||
"Native Netzwerkunterstützung: network-Modul (Wi-Fi-Station und Access Point)",
|
||||
"Asynchrone Programmierung mit dem Modul uasyncio",
|
||||
"Offizielle Unterstützung aller ESP32-Varianten mit vorkompilierten Firmware-Binärdateien"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Programmierausbildung und MINT-Lernprojekte",
|
||||
"Schnelles Prototyping und Sensortests ohne Kompilierzyklen",
|
||||
"Gerätesteuerung und Skripte, die ohne Neu-Flashen anpassbar sind",
|
||||
"Eigenständige Datenlogger und kompakte HTTP-/WebSocket-Server",
|
||||
"Laborautomatisierung und Auswertung von Sensordaten"
|
||||
],
|
||||
"exemplo": "/exemplos/micropython.py",
|
||||
"exemplos": "https://github.com/micropython/micropython/tree/master/examples",
|
||||
"documentacao": "https://docs.micropython.org/en/latest/esp32/quickref.html",
|
||||
"repositorio": "https://github.com/micropython/micropython",
|
||||
"cor": "#2B5B84"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,732 @@
|
||||
{
|
||||
"ESP32": {
|
||||
"nome_completo": "ESP32 (Clássico)",
|
||||
"icone": "🔷",
|
||||
"descricao": "Der Pionier der Reihe mit Xtensa-Dual-Core, Wi-Fi 4 und klassischem Bluetooth/BLE. Empfohlen für klassische Audioprojekte und etablierte IoT-Gateways.",
|
||||
"arquitetura": "32-Bit-Xtensa®-LX6-Dual-Core",
|
||||
"nucleos": "1 (Single-core) ou 2 (Dual-core)",
|
||||
"frequencia": "Bis zu 240 MHz",
|
||||
"coprocessador_ulp": "Ja",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/192/256",
|
||||
"sha": "SHA-1/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 4096 bits)",
|
||||
"ecc": "Nein",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Nein",
|
||||
"assinatura_digital": "Nein",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "Ja (AES-256, Legacy-Verfahren)",
|
||||
"secure_boot": "V1 (AES, Legacy); V2 (RSA-3072, RSA-PSS) ab Revision v3.0 (ECO3)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, bis zu 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 4.2 BR/EDR (Clássico) und Bluetooth LE (dual mode)",
|
||||
"ethernet": "Ja (Ethernet MAC integrado)",
|
||||
"memoria_sram": "520 KB",
|
||||
"memoria_sram_rtc": "16 KB (dividida em RTC FAST e RTC SLOW)",
|
||||
"memoria_rom": "448 KB (für Boot- und Core-Funktionen)",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI",
|
||||
"psram_externa": "Bis zu 8 MB über QSPI (in spezifischen Modulen wie WROVER)",
|
||||
"gpio": "34",
|
||||
"adc": "2x SAR ADC de 12 bits, até 18 canais",
|
||||
"dac": "2x DAC de 8 bits",
|
||||
"touch": "10 canais capacitivos",
|
||||
"uart": "3",
|
||||
"spi": "4 (SPI, HSPI, VSPI - 2 podem ser usados para Flash/PSRAM)",
|
||||
"i2c": "2",
|
||||
"i2s": "2",
|
||||
"pwm": "LED-PWM (bis zu 16 Kanäle), Motor-PWM",
|
||||
"ethernet_mac": "1 (requer PHY externo)",
|
||||
"can": "1 (CAN 2.0, TWAI®)",
|
||||
"sdio": "1 (SD/SDIO/MMC Host), 1 (SDIO/SPI Slave)",
|
||||
"sensor_hall": "1 (interno)",
|
||||
"sensor_temperatura": "Nein (retirado do datasheet em 2018; sem driver no ESP-IDF)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_240mhz": "30-68 mA",
|
||||
"active_wifi_tx": "180-240 mA",
|
||||
"modem_sleep": "20-44 mA",
|
||||
"light_sleep": "0.8 mA",
|
||||
"deep_sleep": "10-150 µA",
|
||||
"hibernation": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 125°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Externes JTAG (erfordert Sonde, z. B. ESP-PROG)",
|
||||
"esp_idf_minimo": "Seit Beginn (v3.x und früher)",
|
||||
"arduino_core": "Ja (147 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN48 (6×6 mm) und QFN48 (5×5 mm)",
|
||||
"modulos": "ESP32-MINI-1, ESP32-PICO-MINI-02, ESP32-PICO-V3, ESP32-PICO-V3-02 e mais 11",
|
||||
"datasheet": "https://documentation.espressif.com/esp32_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32/get-started/index.html",
|
||||
"placa": "/placas/esp32.png",
|
||||
"cor": "#007bff"
|
||||
},
|
||||
"ESP32-S2": {
|
||||
"nome_completo": "ESP32-S2",
|
||||
"icone": "🔒",
|
||||
"descricao": "Single-Core-SoC mit nativer USB-OTG-Schnittstelle, erweiterter Hardware-Sicherheit und bis zu 43 GPIOs. Entwickelt für einfache Display-Schnittstellen und sichere USB-Peripherie.",
|
||||
"arquitetura": "32-Bit-Xtensa®-LX7-Single-Core",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Bis zu 240 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/192/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 4096 bits)",
|
||||
"ecc": "Nein",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, bis zu 150 Mbps)",
|
||||
"bluetooth": "Nein",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Bis zu 1 GB über QSPI",
|
||||
"psram_externa": "Bis zu 1 GB über QSPI/Octal SPI",
|
||||
"gpio": "43",
|
||||
"adc": "2x SAR ADC, até 20 canais: saída de 13 bits (0–8191, única da família), resolução efetiva de 12 bits a partir da revisão v1.0 (errata ADC-112)",
|
||||
"dac": "2x DAC de 8 bits",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "2",
|
||||
"spi": "4 (SPI0/1 para Flash, SPI2/3 para uso geral)",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 8 Kanäle)",
|
||||
"usb": "1 (USB OTG 1.1 Full-Speed)",
|
||||
"lcd": "8/16-Bit-LCD-Schnittstelle",
|
||||
"camera": "8/16-Bit-DVP-Kameraschnittstelle",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi_tx": "160-310 mA",
|
||||
"modem_sleep_cpu_160mhz": "14-24 mA",
|
||||
"light_sleep": "750 µA",
|
||||
"deep_sleep": "20-190 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Externes JTAG (erfordert Sonde, z. B. ESP-PROG)",
|
||||
"esp_idf_minimo": "v4.2",
|
||||
"arduino_core": "Ja (26 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN56 (7×7 mm)",
|
||||
"modulos": "ESP32-S2-MINI-1, ESP32-S2-MINI-2, ESP32-S2-SOLO, ESP32-S2-SOLO-2 e mais 4",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s2/get-started/index.html",
|
||||
"placa": "/placas/esp32-s2.png",
|
||||
"cor": "#28a745"
|
||||
},
|
||||
"ESP32-S3": {
|
||||
"nome_completo": "ESP32-S3",
|
||||
"icone": "🤖",
|
||||
"descricao": "Hochleistungs-Dual-Core mit Vektorbefehlen für KI, nativem USB und bis zu 45 GPIOs. Die Standardwahl für Computer Vision, Sprachverarbeitung und anspruchsvolle HMIs.",
|
||||
"arquitetura": "32-Bit-Xtensa®-LX7-Dual-Core",
|
||||
"nucleos": "2 (Dual-core)",
|
||||
"frequencia": "Bis zu 240 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V)",
|
||||
"aceleradores_ia": "Sim (Vector Instructions para IA)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 4096 bits)",
|
||||
"ecc": "Nein",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, bis zu 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 5 (LE) und Bluetooth Mesh",
|
||||
"memoria_sram": "512 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "384 KB",
|
||||
"flash_externa": "Bis zu 1 GB über QSPI/Octal SPI",
|
||||
"psram_externa": "Bis zu 1 GB über QSPI/Octal SPI",
|
||||
"gpio": "45",
|
||||
"adc": "2x SAR ADC de 12 bits, até 20 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "3",
|
||||
"spi": "4 (SPI0/1 para Flash, SPI2/3 para uso geral)",
|
||||
"i2c": "2",
|
||||
"i2s": "2",
|
||||
"pwm": "LED-PWM (bis zu 8 Kanäle), Motor-PWM (6 Kanäle)",
|
||||
"usb": "1 (USB OTG 1.1 Full-Speed) + 1 (USB Serial/JTAG)",
|
||||
"lcd": "8/16-Bit-RGB-LCD-Schnittstelle",
|
||||
"camera": "8/16-Bit-DVP-Kameraschnittstelle",
|
||||
"sdio": "1 (SD/SDIO/MMC Host)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "78 mW (~24 mA @3.3V)",
|
||||
"modem_sleep": "13-42 mA (40-80 MHz, conforme a carga)",
|
||||
"light_sleep": "240 µA (+40 a 200 µA für PSRAM)",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 65/85/105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v4.4",
|
||||
"arduino_core": "Ja (158 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN56 (7×7 mm)",
|
||||
"modulos": "ESP32-S3-MINI-1, ESP32-S3-WROOM-1, ESP32-S3-WROOM-2",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s3/get-started/index.html",
|
||||
"placa": "/placas/esp32-s3.png",
|
||||
"cor": "#fd7e14"
|
||||
},
|
||||
"ESP32-S31": {
|
||||
"nome_completo": "ESP32-S31",
|
||||
"icone": "🌀",
|
||||
"descricao": "Fortschrittlicher SoC, optimiert für generative KI und Vision-Edge-Verarbeitung, der hochfrequente Xtensa-Dual-Cores mit modernster Hardware-Sicherheit verbindet.",
|
||||
"arquitetura": "RISC-V dual-core de 32 bits (HP) + RISC-V single-core (LP)",
|
||||
"nucleos": "2 (Dual-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Bis zu 320 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V, LP CPU de 40 MHz)",
|
||||
"aceleradores_ia": "Sim (Custom AI and DSP extension XespV)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 4096 bits)",
|
||||
"ecc": "Ja (P-192, P-256, P-384)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Ja",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Ja"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5.4 LE und Bluetooth Classic",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Ja",
|
||||
"memoria_sram": "512 KB (HP SRAM)",
|
||||
"memoria_sram_rtc": "32 KB (LP SRAM)",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Bis zu 256 MB über QSPI",
|
||||
"psram_externa": "16 MB oder 32 MB Octal-DDR, nur im Gehäuse integriert (NRV16, NRV32)",
|
||||
"gpio": "60",
|
||||
"adc": "2x SAR ADC de 12 bits, até 16 canais",
|
||||
"dac": "Ja (2x DAC de 10 bits e 2x DAC de 12 bits)",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "5 (4 UART + 1 LP UART)",
|
||||
"spi": "7 (6 SPI + 1 LP SPI)",
|
||||
"i2c": "3 (2 I2C + 1 LP I2C)",
|
||||
"i2s": "2",
|
||||
"pwm": "LED-PWM (bis zu 8 Kanäle), Motor-PWM (MCPWM)",
|
||||
"usb": "1 (USB 2.0 High-Speed OTG e USB Serial/JTAG)",
|
||||
"can": "Ja (CAN FD Controller)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "Konfigurierbarer, leistungsoptimierter Hochleistungsbetrieb",
|
||||
"light_sleep": "0.1-0.8 mA",
|
||||
"deep_sleep": "Baixo consumo com LP CPU ativa"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 85°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v6.1 in Vorschau; offizielle Unterstützung ab v6.1.1",
|
||||
"arduino_core": "Noch nicht vom arduino-esp32-Core unterstützt",
|
||||
"encapsulamento": "QFN80 (8×8 mm)",
|
||||
"modulos": "ESP32-S31-WROOM-1, ESP32-S31-WROOM-3",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s31_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s31_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s31/get-started/index.html",
|
||||
"placa": "/placas/esp32-s31.png",
|
||||
"cor": "#ff2a5f",
|
||||
"sdio": "1 (SDIO Host 3.0)"
|
||||
},
|
||||
"ESP32-C2": {
|
||||
"nome_completo": "ESP32-C2 (ESP8684)",
|
||||
"icone": "🌱",
|
||||
"descricao": "Kompakter und kostengünstiger RISC-V-Chip für einfache Sensoren und den direkten Ersatz des ESP8266 in volumenstarken Massenproduktionen.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Bis zu 120 MHz",
|
||||
"seguranca": {
|
||||
"aes": "Nein",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Nein",
|
||||
"ecc": "Ja (P-192, P-256)",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Nein",
|
||||
"assinatura_digital": "Nein",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (ECDSA P-192 ou P-256)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, bis zu 72.2 Mbps)",
|
||||
"bluetooth": "Bluetooth 5.3 LE (certificado)",
|
||||
"memoria_sram": "272 KB (16 KB para cache)",
|
||||
"memoria_sram_rtc": "Nein",
|
||||
"memoria_rom": "576 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI, jedoch bei im Handel erhältlichen Varianten nicht verfügbar (ESP8684H2X/H4X haben 2 MB oder 4 MB im Gehäuse und führen keine Flash-Pins heraus)",
|
||||
"psram_externa": "Nein",
|
||||
"gpio": "14",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "2",
|
||||
"spi": "3 (SPI0/1 para Flash interna, SPI2 para uso geral)",
|
||||
"i2c": "1 (Master-only)",
|
||||
"i2s": "Nein",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_120mhz": "10,7-15,6 mA (modem-sleep)",
|
||||
"light_sleep": "140 µA",
|
||||
"deep_sleep": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Externes JTAG (erfordert Sonde, z. B. ESP-PROG)",
|
||||
"esp_idf_minimo": "v5.0",
|
||||
"arduino_core": "Ja (1 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN24 (4×4 mm)",
|
||||
"modulos": "ESP8684-MINI-1, ESP8684-WROOM-01C, ESP8684-WROOM-02C, ESP8684-WROOM-02UC e mais 5",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c2/get-started/index.html",
|
||||
"placa": "/placas/esp32-c2.png",
|
||||
"cor": "#8c52ff"
|
||||
},
|
||||
"ESP32-C3": {
|
||||
"nome_completo": "ESP32-C3",
|
||||
"icone": "💎",
|
||||
"descricao": "Kostengünstiger RISC-V-Single-Core, anschlusskompatibel zum ESP8266. Bietet Wi-Fi 4 und Bluetooth 5 (BLE) für kompakte vernetzte Geräte.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Bis zu 160 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Ja (RSA/MPI bis zu 3072 bits)",
|
||||
"ecc": "Nein",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072), ab Revision v0.3 (ECO3)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, bis zu 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 5 (LE) und Bluetooth Mesh",
|
||||
"memoria_sram": "400 KB",
|
||||
"memoria_sram_rtc": "8 KB",
|
||||
"memoria_rom": "384 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI",
|
||||
"psram_externa": "Nein",
|
||||
"gpio": "22",
|
||||
"adc": "2x SAR ADC de 12 bits, até 6 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "2",
|
||||
"spi": "3 (SPI0/1 para Flash, SPI2 para uso geral)",
|
||||
"i2c": "1",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_160mhz": "20 mA",
|
||||
"active_wifi_tx_peak": "335 mA",
|
||||
"modem_sleep_cpu_160mhz": "16-28 mA",
|
||||
"light_sleep": "130 µA",
|
||||
"deep_sleep": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40 °C bis 105 °C (85 °C beim ESP32-C3FN4)",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v4.3",
|
||||
"arduino_core": "Ja (29 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN32 (5×5 mm) und QFN28 (4×4 mm)",
|
||||
"modulos": "ESP32-C3-MINI-1, ESP32-C3-WROOM-02",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c3/get-started/index.html",
|
||||
"placa": "/placas/esp32-c3.png",
|
||||
"cor": "#20c997"
|
||||
},
|
||||
"ESP32-C5": {
|
||||
"nome_completo": "ESP32-C5",
|
||||
"icone": "📶",
|
||||
"descricao": "Erster Dualband-SoC (2,4 GHz und 5 GHz) der C-Serie mit RISC-V-Architektur. Konzipiert für Industrieumgebungen mit hoher Kanalauslastung im 2,4-GHz-Band.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits (HP) + RISC-V single-core (LP)",
|
||||
"nucleos": "1 (Single-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Bis zu 240 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V, LP CPU de 48 MHz)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 3072 bits)",
|
||||
"ecc": "Ja (P-192, P-256, P-384)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Ja",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA P-256/P-384)",
|
||||
"protecao_dpa": "Ja"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) Dualband 2.4 GHz e 5 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth Core 6.0 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Ja",
|
||||
"memoria_sram": "384 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI",
|
||||
"psram_externa": "Ja, via SPI (controlador de flash/PSRAM com cache)",
|
||||
"gpio": "29",
|
||||
"adc": "1x SAR ADC de 12 bits, até 6 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "3 (2 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "2 (1 I2C + 1 LP I2C)",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle), Motor-PWM",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi": "bis zu 377 mA (TX bei 5 GHz)",
|
||||
"light_sleep": "60-250 µA",
|
||||
"deep_sleep": "12 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v5.5.2",
|
||||
"arduino_core": "Ja (10 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN48 (6×6 mm)",
|
||||
"modulos": "ESP32-C5-MINI-1, ESP32-C5-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c5_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c5_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c5/get-started/index.html",
|
||||
"placa": "/placas/esp32-c5.png",
|
||||
"cor": "#6f42c1",
|
||||
"sdio": "1 (SDIO Slave, a partir da revisão v1.0)",
|
||||
"can": "2 (CAN FD)"
|
||||
},
|
||||
"ESP32-C6": {
|
||||
"nome_completo": "ESP32-C6",
|
||||
"icone": "🌐",
|
||||
"descricao": "Moderner RISC-V-SoC mit Wi-Fi 6, Bluetooth 5 (LE) und integriertem IEEE-802.15.4-Funk. Ideal für stromsparende Smart-Home-Knoten nach Matter- und Thread-Standard.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits (HP) + RISC-V single-core (LP)",
|
||||
"nucleos": "1 (Single-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Bis zu 160 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V, LP CPU de 20 MHz)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Ja (RSA/MPI bis zu 3072 bits)",
|
||||
"ecc": "Ja (P-192, P-256)",
|
||||
"ecdsa": "Nein",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Ja"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth 5.3 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.3)",
|
||||
"matter": "Ja",
|
||||
"memoria_sram": "512 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI",
|
||||
"psram_externa": "Nein",
|
||||
"gpio": "30",
|
||||
"adc": "1x SAR ADC de 12 bits, até 7 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "3 (2 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "2 (1 I2C + 1 LP I2C)",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle), Motor-PWM",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sdio": "1 (SDIO 2.0 Slave)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi6": "252-354 mA (TX)",
|
||||
"light_sleep": "35-180 µA",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v5.1",
|
||||
"arduino_core": "Ja (21 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN40 (5×5 mm) und QFN32 (5×5 mm)",
|
||||
"modulos": "ESP32-C6-MINI-1, ESP32-C6-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c6_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c6_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c6/get-started/index.html",
|
||||
"placa": "/placas/esp32-c6.png",
|
||||
"cor": "#17a2b8"
|
||||
},
|
||||
"ESP32-C61": {
|
||||
"nome_completo": "ESP32-C61",
|
||||
"icone": "🛰️",
|
||||
"descricao": "Kostengünstige Variante des C6, optimiert für Wi-Fi 6- und BLE-Endknoten ohne 802.15.4-Funk, ideal für großflächig vernetzte Sensoren.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Bis zu 160 MHz",
|
||||
"seguranca": {
|
||||
"aes": "Nein",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Nein",
|
||||
"ecc": "Ja (P-192, P-256)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Nein",
|
||||
"assinatura_digital": "Nein",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (ECDSA)",
|
||||
"protecao_dpa": "Ja"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth Core 6.0 certificado)",
|
||||
"zigbee_thread": "Nein",
|
||||
"matter": "Ja (via Wi-Fi)",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "Nein",
|
||||
"memoria_rom": "256 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI (Modelle mit 4 MB oder 8 MB im Gehäuse integriert)",
|
||||
"psram_externa": "Bis zu 16 MB über QSPI (Modelle mit 2 MB oder 8 MB im Gehäuse integriert)",
|
||||
"gpio": "30",
|
||||
"adc": "1x SAR ADC de 12 bits, até 4 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "3",
|
||||
"spi": "3 (2 para Flash/PSRAM, 1 para uso geral)",
|
||||
"i2c": "1",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sdio": "1 (SDIO 2.0 Slave)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "240-360 mA (TX)",
|
||||
"light_sleep": "50-200 µA",
|
||||
"deep_sleep": "10 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v5.5.2",
|
||||
"arduino_core": "Ja (1 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN40 (5×5 mm) oder LGA40 (5×5 mm)",
|
||||
"modulos": "ESP32-C61-MINI-1, ESP32-C61-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c61_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c61_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c61/get-started/index.html",
|
||||
"placa": "/placas/esp32-c61.png",
|
||||
"cor": "#0dcaf0"
|
||||
},
|
||||
"ESP32-P4": {
|
||||
"nome_completo": "ESP32-P4",
|
||||
"icone": "⚡",
|
||||
"descricao": "Hochleistungs-Mikrocontroller ohne integriertes Funkmodul mit 400-MHz-RISC-V-Dual-Core, MIPI-CSI/DSI-Schnittstellen und erweiterter Sicherheit für anspruchsvolle HMIs und Gateways.",
|
||||
"arquitetura": "RISC-V de 32 bits dual-core de alto desempenho (HP) + single-core de baixo consumo (LP)",
|
||||
"nucleos": "2 (Dual-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Bis zu 400 MHz (HP, revisão v3.x; 360 MHz na v1.x); LP até 40 MHz",
|
||||
"coprocessador_ulp": "Ja (RISC-V, LP CPU de 40 MHz)",
|
||||
"aceleradores_ia": "Sim (Vector Instructions, aceleradores de IA)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Ja (RSA/MPI bis zu 4096 bits)",
|
||||
"ecc": "Ja (P-192, P-256, P-384)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Ja",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "Nein",
|
||||
"bluetooth": "Nein",
|
||||
"ethernet": "Ja (Ethernet MAC integrado)",
|
||||
"memoria_sram": "768 KB",
|
||||
"memoria_sram_rtc": "32 KB",
|
||||
"memoria_rom": "128 KB (HP ROM) + 16 KB (LP ROM)",
|
||||
"flash_externa": "Bis zu 128 MB über QSPI/Octal SPI",
|
||||
"psram_externa": "16 MB oder 32 MB im Gehäuse integriert (OPI/HPI, 1,8 V)",
|
||||
"gpio": "55",
|
||||
"adc": "2x SAR ADC de 12 bits, até 14 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Ja (sensor de toque capacitivo)",
|
||||
"uart": "6 (5 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "3 (2 I2C + 1 LP I2C)",
|
||||
"i2s": "4 (3 I2S + 1 LP I2S)",
|
||||
"pwm": "LED-PWM (bis zu 8 Kanäle), Motor-PWM (6 Kanäle)",
|
||||
"usb": "USB 2.0 High-Speed OTG + USB 2.0 Full-Speed OTG + USB Serial/JTAG",
|
||||
"mipi_csi": "MIPI-CSI-Kameraschnittstelle",
|
||||
"mipi_dsi": "Interface MIPI DSI para display",
|
||||
"lcd": "8/16/24-Bit-LCD-Schnittstelle",
|
||||
"camera": "8/16-Bit-DVP-Kameraschnittstelle",
|
||||
"sdio": "1 SD/MMC-Host-Controller (SDHOST)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "15-150 mA (40 a 400 MHz, conforme a carga)",
|
||||
"light_sleep": "75-800 µA",
|
||||
"deep_sleep": "12 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 85°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v5.3",
|
||||
"arduino_core": "Ja (7 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN104 (10×10 mm)",
|
||||
"modulos": "Kein Modul im offiziellen Katalog (nur nackter Chip)",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-p4-chip-revision-v1.3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-p4-chip-revision-v1.3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32p4/get-started/index.html",
|
||||
"placa": "/placas/esp32-p4.png",
|
||||
"cor": "#ffc107"
|
||||
},
|
||||
"ESP32-H2": {
|
||||
"nome_completo": "ESP32-H2",
|
||||
"icone": "🔋",
|
||||
"descricao": "Ultra-Low-Power-Chip ohne Wi-Fi, ausgelegt für Zigbee 3.0, Thread 1.3 und Matter über 802.15.4 sowie Bluetooth 5.4 LE. Perfekt für batteriebetriebene Sensoren.",
|
||||
"arquitetura": "RISC-V single-core de 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Bis zu 96 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Ja (RSA/MPI bis zu 3072 bits)",
|
||||
"ecc": "Ja (P-192, P-256)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Ja",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Ja"
|
||||
},
|
||||
"wifi": "Nein",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth 5.3 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Ja",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "4 KB (LP Memory)",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Bis zu 16 MB über QSPI",
|
||||
"psram_externa": "Nein",
|
||||
"gpio": "19",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "Nein",
|
||||
"uart": "2",
|
||||
"spi": "3",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 6 Kanäle)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "24-140 mA (Funk, von -24 a 20 dBm)",
|
||||
"light_sleep": "25-85 µA",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v5.1",
|
||||
"arduino_core": "Ja (3 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN32 (4×4 mm)",
|
||||
"modulos": "ESP32-H2-MINI-1, ESP32-H2-WROOM-02C",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-h2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-h2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32h2/get-started/index.html",
|
||||
"placa": "/placas/esp32-h2.png",
|
||||
"cor": "#6c757d"
|
||||
},
|
||||
"ESP32-H4": {
|
||||
"nome_completo": "ESP32-H4",
|
||||
"icone": "🛡️",
|
||||
"descricao": "Weiterentwicklung der 802.15.4-Reihe mit RISC-V-Dual-Core, Bluetooth 5.4 und erweiterter Funkreichweite, optimiert für Thread-Border-Router und Gateways.",
|
||||
"status_documentacao": "Vorläufige Dokumentation: Espressif hat noch kein Datenblatt oder technisches Handbuch für den ESP32-H4 veröffentlicht. Die folgenden Daten stammen aus der offiziellen Produktankündigung und den Hardwaredefinitionen (soc_caps) von ESP-IDF und können sich bis zur Veröffentlichung ändern.",
|
||||
"arquitetura": "RISC-V dual-core de 32 bits",
|
||||
"nucleos": "2 (Dual-core)",
|
||||
"frequencia": "Bis zu 96 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Nein",
|
||||
"ecc": "Ja (P-192, P-256, P-384)",
|
||||
"ecdsa": "Ja (modo determinístico, RFC 6979)",
|
||||
"hmac": "Ja",
|
||||
"assinatura_digital": "Nein",
|
||||
"key_manager": "Nein",
|
||||
"rng": "Ja (TRNG Hardware-TRNG)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "Ja auf Hardware-Ebene; in ESP-IDF noch nicht aktiviert",
|
||||
"protecao_dpa": "Nein"
|
||||
},
|
||||
"wifi": "Nein",
|
||||
"bluetooth": "Bluetooth 5.4 LE (certificado Bluetooth 6.0; LE Audio, canais isócronos BIS/CIS, PAwR, Connection Subrating und Direction Finding AoA/AoD)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Ja",
|
||||
"memoria_sram": "384 KB",
|
||||
"memoria_sram_rtc": "Sim (LP SRAM)",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Sim, via QSPI (4 MB integrada no encapsulamento no ESP32-H4HF4)",
|
||||
"psram_externa": "Ja (2 MB integrada no encapsulamento no ESP32-H4HR2)",
|
||||
"gpio": "40",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nein",
|
||||
"touch": "15 canais capacitivos (versão 3, com waterproof e proximidade)",
|
||||
"uart": "2",
|
||||
"spi": "3",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED-PWM (bis zu 8 Kanäle), Motor-PWM (MCPWM)",
|
||||
"can": "1 (CAN 2.0, TWAI®)",
|
||||
"usb": "1 (USB OTG 1.1) + 1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "Nicht bekannt gegeben (vorläufige Dokumentation)"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "Nicht bekannt gegeben (vorläufige Dokumentation)",
|
||||
"depuracao": "Integriertes JTAG über USB (keine externe Sonde erforderlich)",
|
||||
"esp_idf_minimo": "v6.0 in Vorschau (ohne stabile Unterstützung)",
|
||||
"arduino_core": "Noch nicht vom arduino-esp32-Core unterstützt",
|
||||
"encapsulamento": "QFN56 (6×6 mm)",
|
||||
"modulos": "ESP32-H4-WROOM-1",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32h4/get-started/index.html",
|
||||
"cor": "#e83e8c"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,385 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF (Wi-Fi et Bluetooth)"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne",
|
||||
"RF"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche RF dédiée. Évitez les pistes longues ou sans adaptation d'impédance de 50 ohms."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V (3.0V à 3.6V)",
|
||||
"Alimente les circuits analogiques et RF de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V (3.0V à 3.6V)",
|
||||
"Alimente les circuits analogiques et RF de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche d'entrée analogique ADC1 Canal 0"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche d'entrée analogique ADC1 Canal 1"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Mappé sur la fonction SPI MISO (FSPIQ) par défaut lors de l'initialisation de la flash"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce (Power-up / Reset)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Actif à l'état haut. Tirez au niveau haut pour initialiser la puce.",
|
||||
"Ne laissez pas cette broche flottante. Utilisez un circuit de retard RC externe pour un démarrage stable."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche d'entrée analogique ADC1 Canal 3"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO4",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"MTMS",
|
||||
"FSPIQ",
|
||||
"ADC1_CH4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTMS, SPI2 MISO et ADC1 Canal 4.",
|
||||
"Peut être utilisée pour le débogage JTAG conjointement avec les autres broches JTAG."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO5",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"MTDI",
|
||||
"FSPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTDI et SPI2 Write Protect (FSPIWP)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "VDD3P3_RTC",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine RTC et des E/S basse consommation"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"MTCK",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTCK et horloge SPI2 (FSPICLK)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"MTDO",
|
||||
"FSPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTDO et SPI2 MOSI (FSPID)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche de strapping pour le contrôle du démarrage (boot).",
|
||||
"En association avec GPIO9, sélectionne le mode de démarrage du SoC (doit être à 1 pendant le reset pour le Joint Download Boot si GPIO9=0)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche de strapping principale. Niveau haut (1) au reset active le boot SPI (par défaut via pull-up faible).",
|
||||
"Niveau bas (0) au reset place la puce en mode téléchargement (Download) UART/SPI."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : SPI2 Chip Select 0 (FSPICS0)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "VDD3P3_CPU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation numérique du CPU et des E/S correspondantes (3.3V)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO18",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"UART0 receive pin (Serial RX by default for flashing and monitoring)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "GPIO20",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"UART0 transmit pin (Serial TX by default for flashing and monitoring)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation d'entrée analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion externe du quartz oscillateur (Sortie)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion externe du quartz oscillateur (Entrée)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation d'entrée analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GND",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Plot de masse central (Exposed Pad)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Doit être correctement soudé au plan de masse (GND) du circuit imprimé pour des performances stables et une bonne dissipation thermique."
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,574 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "LNA_IN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée et sortie des signaux RF (Wi-Fi et Bluetooth) vers l'antenne"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"XTAL_32K_P",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"XTAL_32K_N",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"This pin does not set boot mode, but connecting it with a pull-up is recommended to prevent glitches (see datasheet section 3.1)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Porter cette broche au niveau haut active le fonctionnement de la puce",
|
||||
"Porter cette broche au niveau bas désactive le fonctionnement de la puce",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"ADC1_CH4",
|
||||
"FSPIHD",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"ADC2_CH0",
|
||||
"FSPIWP",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "VDD3P3_RTC",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine basse consommation et d'une partie du domaine numérique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"FSPICLK",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"FSPID",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée avec pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "VDD3P3_CPU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée/sortie d'alimentation de la flash interne/externe",
|
||||
"GPIO11"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce",
|
||||
"Ne peut être utilisée comme GPIO que si la mémoire flash est alimentée par une source externe"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO18",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche aura son pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie négative d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.2 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie positive d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.2 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "VDDA",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,862 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "VDDA6",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA7",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie négative d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.3 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie positive d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.3 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "VDDA8",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Porter cette broche au niveau haut active le fonctionnement de la puce",
|
||||
"Porter cette broche au niveau bas désactive le fonctionnement de la puce",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique basse consommation"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"LP_GDIO0",
|
||||
"XTAL_32K_P",
|
||||
"LP_UART_DTRN"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"LP_GDIO1",
|
||||
"XTAL_32K_N",
|
||||
"LP_UART_DSRN",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"LP_GDIO2",
|
||||
"LP_UART_RTSN",
|
||||
"LP_I2C_SDA",
|
||||
"ADC1_CH1",
|
||||
"FSPIQ",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"La fonction I2C_SDA est disponible en mode basse consommation (LP)",
|
||||
"Broche utilisée pour le débogage (debugging)",
|
||||
"Utilisé pour contrôler la fréquence du quartz oscillateur (consultez la section 3.5 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"LP_GDIO3",
|
||||
"LP_UART_CTSN",
|
||||
"LP_I2C_SCL",
|
||||
"ADC1_CH2",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"JTAG",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"La fonction I2C_SDA est disponible en mode basse consommation (LP)",
|
||||
"Broche utilisée pour le débogage (debugging)",
|
||||
"Utilisé pour contrôler la synchronisation du SDIO Slave (consultez la section 3.2 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"LP_GDIO4",
|
||||
"LP_UART_RXD",
|
||||
"ADC1_CH3",
|
||||
"FSPIHD",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"LP_GDIO5",
|
||||
"LP_UART_TXD",
|
||||
"ADC1_CH4",
|
||||
"FSPIWP",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"LP_GDIO6",
|
||||
"ADC1_CH5",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"FSPID",
|
||||
"SDIO_DATA1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler la source des signaux JTAG (consultez la section 3.4 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8",
|
||||
"SDIO_DATA0",
|
||||
"PAD_COMP0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9",
|
||||
"SDIO_CLK",
|
||||
"PAD_COMP1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"FSPICS0",
|
||||
"SDIO_CMD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche aura son pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D-",
|
||||
"SDIO_DATA3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "GPIO14",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"USB_D+",
|
||||
"SDIO_DATA4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up USB interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up USB interne activé",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDDPST2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique haute performance et d'une partie du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "SPICS1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Sortie d'alimentation pour la flash externe",
|
||||
"GPIO19"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce",
|
||||
"Ne peut être utilisée comme GPIO que si la mémoire flash externe est alimentée par une source externe"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GPIO23",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "GPIO24",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler la synchronisation du SDIO Slave (consultez la section 3.4 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée avec pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)",
|
||||
"Utilisé pour contrôler l'affichage des messages ROM sur UART0 (consultez la section 3.3 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "GPIO28",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée avec pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "VDDPST3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique haute performance"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "42",
|
||||
"nome": "ANT_2G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF pour la bande 2 GHz"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "43",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "44",
|
||||
"nome": "VDDA3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "44",
|
||||
"nome": "VDDA4",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "45",
|
||||
"nome": "VDDA5",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "47",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "48",
|
||||
"nome": "ANT_5G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF pour la bande 5 GHz"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,757 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Porter cette broche au niveau haut active le fonctionnement de la puce",
|
||||
"Porter cette broche au niveau bas désactive le fonctionnement de la puce",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique basse consommation et d'une partie du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"LP_GDIO0",
|
||||
"XTAL_32K_P",
|
||||
"LP_UART_DTRN",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"LP_GDIO1",
|
||||
"XTAL_32K_N",
|
||||
"LP_UART_DSRN",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"Clock",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2",
|
||||
"LP_GDIO2",
|
||||
"LP_UART_RTSN",
|
||||
"ADC1_CH2",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"LP_GDIO3",
|
||||
"LP_UART_CTSN",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"LP_GDIO4",
|
||||
"LP_UART_RXD",
|
||||
"ADC1_CH3",
|
||||
"FSPIHD",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)",
|
||||
"Utilisé pour contrôler la synchronisation du SDIO Slave (consultez la section 3.2 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"LP_GDIO5",
|
||||
"LP_UART_TXD",
|
||||
"ADC1_CH5",
|
||||
"FSPIWP",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"UART",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)",
|
||||
"Utilisé pour contrôler la synchronisation du SDIO Slave (consultez la section 3.2 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"LP_GDIO6",
|
||||
"LP_I2C_SDA",
|
||||
"ADC1_CH6",
|
||||
"FSPICLK",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"I2C",
|
||||
"ADC",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"La fonction I2C_SDA est disponible en mode basse consommation (LP)",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7",
|
||||
"LP_GDIO7",
|
||||
"LP_I2C_SCL",
|
||||
"FSPID",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Low Power",
|
||||
"I2C",
|
||||
"SPI",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"La fonction I2C_SDA est disponible en mode basse consommation (LP)",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)",
|
||||
"Utilisé pour contrôler l'affichage des messages ROM sur UART0 (consultez la section 3.3 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée avec pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "SPICS0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "SPIQ",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "SPIWP",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée/sortie d'alimentation pour la mémoire flash",
|
||||
"GPIO27"
|
||||
],
|
||||
"categorias": [
|
||||
"Power",
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce",
|
||||
"Ne peut être utilisée comme GPIO que si la mémoire flash externe est alimentée par une source externe"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "SPIHD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "SPICLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO29",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "SPID",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO30",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé par la mémoire flash SPI",
|
||||
"Not recommended to use this pin as GPIO"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "GPIO15",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler la source des signaux JTAG (consultez la section 3.4 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine numérique haute performance"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"U0TXD",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche aura son pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"U0RXD",
|
||||
"FSPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "SDIO_CMD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO18",
|
||||
"SDIO_CMD",
|
||||
"FSPICS2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "SDIO_CLK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"SDIO_CLK",
|
||||
"FSPICS3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "SDIO_DATA0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SDIO_DATA0",
|
||||
"FSPICS4"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "SDIO_DATA1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SDIO_DATA1",
|
||||
"FSPICS5"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "SDIO_DATA2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SDIO_DATA2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "SDIO_DATA3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"SDIO_DATA3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SD"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche a son pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie négative d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie positive d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,642 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "ANT_2G",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF (Wi-Fi et Bluetooth)"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne",
|
||||
"RF"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated 2.4 GHz RF pin. Requires 50-ohm impedance matching."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDDA3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V (3.0V à 3.6V). Fournit l'alimentation aux circuits RF et d'horloge."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "VDDA4",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V (3.0V à 3.6V). Fournit l'alimentation aux circuits RF et d'horloge."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "CHIP_PU",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce (Power-up / Reset)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Actif à l'état haut. Tirez au niveau haut pour initialiser la puce.",
|
||||
"Do not leave this pin floating. An external RC circuit is recommended for clean reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation numérique des domaines HP (High Performance) et LP (Low Power)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V. Alimente la partie numérique basse consommation et les broches associées."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"XTAL_32K_P"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Low-power multifunction pin. Can connect to external 32 kHz crystal (Input P)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"XTAL_32K_N",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin. External 32 kHz crystal connection (Output N) and ADC1 Channel 0 analog input."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "GPIO2",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "GPIO3",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"MTMS",
|
||||
"ADC1_CH1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTMS, ADC1 Canal 1 et broche de strapping pour le contrôle du front d'horloge SDIO.",
|
||||
"Floating by default during reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO4",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"MTDI",
|
||||
"ADC1_CH2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Broche multifonction : JTAG MTDI, ADC1 Canal 2 et broche de strapping pour le contrôle du front d'horloge SDIO.",
|
||||
"Floating by default during reset."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "GPIO5",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"MTCK",
|
||||
"ADC1_CH3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin: JTAG MTCK and ADC1 Channel 3 analog input."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO6",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO6",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Multifunction pin: JTAG MTDO."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO25",
|
||||
"SDIO_CMD",
|
||||
"FSPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Command or SPI2 Chip Select 0."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"SDIO_CLK",
|
||||
"FSPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Clock or SPI2 Clock."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27",
|
||||
"SDIO_DATA0",
|
||||
"FSPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed multifunction pin: SDIO Data 0 or SPI2 MOSI (FSPID)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "GPIO28",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO28",
|
||||
"SDIO_DATA1",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 1 or SPI2 MISO (FSPIQ)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "GPIO22",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22",
|
||||
"SDIO_DATA2",
|
||||
"FSPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 2 or SPI2 Write Protect."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "GPIO23",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"SDIO_DATA3",
|
||||
"FSPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SDIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"High-speed pin: SDIO Data 3 or SPI2 Hold."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "GPIO14",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"SPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated Chip Select 1 pin for SPI Flash/PSRAM memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "GPIO15",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO15",
|
||||
"SPICS0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Dedicated Chip Select 0 pin for SPI Flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "VDDPST2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine numérique HP (High Performance)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V (3.0V à 3.6V). Alimente les interfaces numériques rapides."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "GPIO16",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO16",
|
||||
"SPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Data Q (MISO) pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "GPIO17",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO17",
|
||||
"SPIWP"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Write Protect pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "VDD_SPI",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Tension de sortie LDO générée à partir de VDDPST2 pour alimenter la flash et la PSRAM"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension de sortie configurable par logiciel selon les spécifications de la flash interne/externe (habituellement 3.3V ou 1.8V).",
|
||||
"Must not be used as a general high-current power source."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO19",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO19",
|
||||
"SPIHD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Hold control pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO20",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO20",
|
||||
"SPICLK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Clock signal pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "GPIO21",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO21",
|
||||
"SPID"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Data D (MOSI) pin for SPI flash memory interface."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Negative signal pin of integrated USB Serial/JTAG transceiver."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "GPIO13",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Positive signal pin of integrated USB Serial/JTAG transceiver.",
|
||||
"Possède une résistance de pull-up intégrée activée par défaut à l'initialisation de l'USB."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "GPIO24",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Strapping pin for boot mode selection and ROM log printing control.",
|
||||
"Floating by default during reset. High level (1) enables boot log printing."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Primary Strapping pin for boot mode selection.",
|
||||
"Équipé d'un pull-up faible intégré. Niveau haut (1) au reset active le boot SPI (chargement depuis la flash). Niveau bas (0) force le mode téléchargement (Download)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"U0RXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Réception série UART0 (Serial RX pour la programmation externe du firmware et le débogage)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "34",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"U0TXD"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART"
|
||||
],
|
||||
"avisos": [
|
||||
"Transmission série UART0 (Serial TX pour la programmation externe du firmware et le débogage)."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "35",
|
||||
"nome": "GPIO29",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO29"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "36",
|
||||
"nome": "GPIO7",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO7"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Strapping pin for JTAG signal source selection (early boot).",
|
||||
"Sans résistances de tirage (pull) internes au reset. Doit être maintenue stable par circuit externe si utilisée."
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "37",
|
||||
"nome": "VDDA1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "38",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion externe du quartz oscillateur 40 MHz (Sortie N)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "39",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion externe du quartz oscillateur 40 MHz (Entrée P)"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "40",
|
||||
"nome": "VDDA2",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Alimentation du domaine analogique 3.3V"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "41",
|
||||
"nome": "GND",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Plot de masse central (Exposed Pad)"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Doit être correctement soudé au plan de masse (GND) du circuit imprimé pour un contrôle RF et thermique stables."
|
||||
]
|
||||
}
|
||||
]
|
||||
@@ -0,0 +1,549 @@
|
||||
[
|
||||
{
|
||||
"numero": "1",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "2",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "3",
|
||||
"nome": "GPIO0",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO0",
|
||||
"FSPIQ"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "4",
|
||||
"nome": "GPIO1",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"FSPICS0",
|
||||
"ADC1_CH0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "5",
|
||||
"nome": "MTMS",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO1",
|
||||
"FSPIWP",
|
||||
"ADC1_CH1",
|
||||
"MTMS"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "6",
|
||||
"nome": "MTDO",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO3",
|
||||
"FSPIHD",
|
||||
"ADC1_CH2",
|
||||
"MTDO"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "7",
|
||||
"nome": "MTCK",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO4",
|
||||
"FSPICLK",
|
||||
"ADC1_CH3",
|
||||
"MTCK"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "8",
|
||||
"nome": "MTDI",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO5",
|
||||
"FSPID",
|
||||
"ADC1_CH4",
|
||||
"MTDI"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"ADC",
|
||||
"JTAG"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "9",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine des E/S"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "10",
|
||||
"nome": "GPIO8",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO8"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)",
|
||||
"Utilisé pour contrôler l'affichage des messages ROM sur UART0 (consultez la section 3.3 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "11",
|
||||
"nome": "GPIO9",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO9"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée avec pull-up interne activé",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Utilisé pour contrôler le mode de démarrage (boot) de la puce (consultez la section 3.1 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "12",
|
||||
"nome": "GPIO10",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO10",
|
||||
"ZCD0"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "13",
|
||||
"nome": "GPIO11",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO11",
|
||||
"ZCD1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "14",
|
||||
"nome": "GPIO12",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO12"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "15",
|
||||
"nome": "XTAL_32K_P",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO13",
|
||||
"XTAL_32K_P"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "16",
|
||||
"nome": "XTAL_32K_N",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO14",
|
||||
"XTAL_32K_N"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"Clock"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "17",
|
||||
"nome": "CHIP_EN",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Activation de la puce"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Porter cette broche au niveau haut active le fonctionnement de la puce",
|
||||
"Porter cette broche au niveau bas désactive le fonctionnement de la puce",
|
||||
"Do not leave this pin floating, use an external pull-up resistor"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "18",
|
||||
"nome": "VBAT",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique ou de la batterie"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "19",
|
||||
"nome": "VDDA_PMU",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "20",
|
||||
"nome": "VDDPST1",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine des E/S"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "21",
|
||||
"nome": "GPIO22",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO22"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO"
|
||||
],
|
||||
"avisos": []
|
||||
},
|
||||
{
|
||||
"numero": "22",
|
||||
"nome": "U0RXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO23",
|
||||
"U0RXD",
|
||||
"FSPICS1"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "23",
|
||||
"nome": "U0TXD",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"U0TXD",
|
||||
"FSPICS2"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"UART",
|
||||
"SPI"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up interne activé",
|
||||
"Broche utilisée pour le débogage (debugging)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "24",
|
||||
"nome": "GPIO25",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO24",
|
||||
"FSPICS3"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"Strapping"
|
||||
],
|
||||
"avisos": [
|
||||
"Pendant la réinitialisation, cette broche est configurée en entrée",
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Utilisé pour contrôler la source des signaux JTAG (consultez la section 3.3 de la fiche technique pour plus de détails)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "25",
|
||||
"nome": "GPIO26",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO26",
|
||||
"FSPICS4",
|
||||
"USB_D-"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "26",
|
||||
"nome": "GPIO27",
|
||||
"tipo": "io",
|
||||
"funcoes": [
|
||||
"GPIO27",
|
||||
"FSPICS5",
|
||||
"USB_D+"
|
||||
],
|
||||
"categorias": [
|
||||
"GPIO",
|
||||
"SPI",
|
||||
"USB"
|
||||
],
|
||||
"avisos": [
|
||||
"Après la réinitialisation, cette broche sera configurée en entrée avec pull-up USB interne activé",
|
||||
"Par défaut, cette broche est utilisée pour USB Série/JTAG"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "27",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "28",
|
||||
"nome": "XTAL_N",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie négative d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.2 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "29",
|
||||
"nome": "XTAL_P",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Entrée/sortie positive d'horloge"
|
||||
],
|
||||
"categorias": [
|
||||
"Clock"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.3.2 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "30",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "31",
|
||||
"nome": "VDD3P3",
|
||||
"tipo": "power",
|
||||
"funcoes": [
|
||||
"Entrée d'alimentation du domaine analogique"
|
||||
],
|
||||
"categorias": [
|
||||
"Power"
|
||||
],
|
||||
"avisos": [
|
||||
"Tension recommandée : 3.3V",
|
||||
"Minimum Recommended Voltage: 3.0V",
|
||||
"Maximum Recommended Voltage: 3.6V",
|
||||
"Consultez la section 2.5 de la fiche technique pour plus de détails sur l'alimentation de la puce"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "32",
|
||||
"nome": "ANT",
|
||||
"tipo": "analog",
|
||||
"funcoes": [
|
||||
"Connexion de l'antenne RF"
|
||||
],
|
||||
"categorias": [
|
||||
"Antenne"
|
||||
],
|
||||
"avisos": [
|
||||
"Consultez la section 2.4 de la fiche technique pour plus de détails sur les broches analogiques"
|
||||
]
|
||||
},
|
||||
{
|
||||
"numero": "33",
|
||||
"nome": "GND",
|
||||
"tipo": "ground",
|
||||
"funcoes": [
|
||||
"Référence électrique du circuit (masse)"
|
||||
],
|
||||
"categorias": [
|
||||
"GND"
|
||||
],
|
||||
"avisos": []
|
||||
}
|
||||
]
|
||||
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
File diff suppressed because it is too large.
Load diff
@@ -0,0 +1,423 @@
|
||||
{
|
||||
"ESP-IDF": {
|
||||
"nome": "ESP-IDF",
|
||||
"icone": "⚙️",
|
||||
"nome_completo": "Espressif IoT Development Framework",
|
||||
"descricao": "Framework officiel natif d'Espressif pour tous les SoCs ESP32. Basé sur FreeRTOS multicoeur et CMake, offrant un contrôle complet du silicium, des périphériques, de la radio et d'une architecture modulaire de composants.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Framework de Base Officiel",
|
||||
"funcao_principal": "Développement industriel et haute performance avec accès direct aux registres, RTOS temps réel et pile complète de protocoles",
|
||||
"caracteristicas": [
|
||||
"Système d'exploitation temps réel (FreeRTOS SMP multicoeur)",
|
||||
"Support natif de l'ESP Component Registry via idf_component.yml",
|
||||
"Pile complète de connectivité pour Wi-Fi 4/6, BLE 5.x, Zigbee et Thread",
|
||||
"Support de tous les SoCs (ESP32, S2, S3, C2, C3, C6, H2, P4)",
|
||||
"Gestion avancée de l'énergie et modes Deep Sleep",
|
||||
"Sécurité robuste : Secure Boot v2, chiffrement Flash et cryptographie matérielle",
|
||||
"Mises à jour OTA chiffrées avec retour automatique (rollback)",
|
||||
"Chaîne d'outils moderne Clang/GCC, support de C++23 et débogage JTAG OpenOCD"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Produits IoT commerciaux et industriels",
|
||||
"Dispositifs avec contraintes strictes de batterie et basse consommation",
|
||||
"Applications temps réel avec contrôle précis des interruptions",
|
||||
"Systèmes de sécurité avec chiffrement matériel",
|
||||
"Passerelles multiprotocoles haute performance"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-idf.c",
|
||||
"exemplos": "https://github.com/espressif/esp-idf/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-idf/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-idf",
|
||||
"cor": "#E74C3C"
|
||||
},
|
||||
"ESP-RainMaker": {
|
||||
"nome": "ESP-RainMaker",
|
||||
"icone": "☁️",
|
||||
"nome_completo": "ESP RainMaker AIoT Cloud Platform",
|
||||
"descricao": "Plateforme cloud et firmware complète d'Espressif pour produits connectés. Développez des objets connectés sans concevoir de backend ni d'application mobile à partir de zéro.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Cloud & AIoT Framework",
|
||||
"funcao_principal": "Développement accéléré de produits intelligents avec applications mobiles (iOS/Android), cloud AWS Serverless et contrôle vocal (Alexa/Google Home)",
|
||||
"caracteristicas": [
|
||||
"Approvisionnement Wi-Fi et BLE assisté via l'application mobile officielle",
|
||||
"Génération dynamique d'interface dans l'application selon les paramètres du firmware",
|
||||
"Intégration native avec Alexa et Google Assistant",
|
||||
"Contrôle local simultané (via mDNS/HTTP) et contrôle cloud",
|
||||
"Tableau de bord RainMaker pour la gestion de flotte et les mises à jour OTA",
|
||||
"Compatibilité native avec les noeuds Matter et les ponts (Bridges)",
|
||||
"Bibliothèque intégrée via ESP Component Registry (espressif/esp_rainmaker)"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Appareils électroménagers intelligents et domotique",
|
||||
"Éclairage connecté et prises intelligentes grand public",
|
||||
"Systèmes de climatisation (CVC) et thermostats connectés",
|
||||
"Prototypes IoT commerciaux avec validation rapide du marché",
|
||||
"Produits nécessitant une certification pour Apple Home, Alexa et Google Home"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-rainmaker.c",
|
||||
"exemplos": "https://github.com/espressif/esp-rainmaker/tree/master/examples",
|
||||
"documentacao": "https://rainmaker.espressif.com/docs/get-started.html",
|
||||
"repositorio": "https://github.com/espressif/esp-rainmaker",
|
||||
"cor": "#2980B9"
|
||||
},
|
||||
"ESP-Matter": {
|
||||
"nome": "ESP-Matter",
|
||||
"icone": "🏠",
|
||||
"nome_completo": "ESP-Matter SDK",
|
||||
"descricao": "SDK officiel d'Espressif pour le standard universel de connectivité Matter (CSA). Permet une interopérabilité directe avec Apple Home, Google Home, Alexa et SmartThings.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Smart Home Framework",
|
||||
"funcao_principal": "Développement de dispositifs domotiques unifiés et interopérables via Wi-Fi ou Thread (OpenThread)",
|
||||
"caracteristicas": [
|
||||
"Implémentation conforme au Connected Home over IP (Project CHIP / CSA)",
|
||||
"Support de Matter over Wi-Fi (ESP32, S3, C3, C6) et Matter over Thread (ESP32-H2, C6)",
|
||||
"Prise en charge des rôles d'accessoire (Device), contrôleur et pont (Matter Bridge)",
|
||||
"Couplage universel sécurisé avec certificats DAC (Device Attestation Certificate)",
|
||||
"Intégration transparente avec ESP-IDF et ESP-RainMaker",
|
||||
"Prise en charge de clusters standard : On/Off, variateur, capteurs, thermostats",
|
||||
"Synchronisation avec les écosystèmes Apple, Google, Alexa et SmartThings sans passerelle propriétaire"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Dispositifs domotiques certifiés Matter (ampoules, prises, serrures)",
|
||||
"Ponts de communication Zigbee/BLE vers Matter (Matter Bridges)",
|
||||
"Capteurs environnementaux basse consommation sur réseau Thread (ESP32-H2)",
|
||||
"Actionneurs et commutateurs muraux universels",
|
||||
"Équipements multi-écosystèmes sans application propriétaire requise"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-matter.c",
|
||||
"exemplos": "https://github.com/espressif/esp-matter/tree/main/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-matter/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-matter",
|
||||
"cor": "#16A085"
|
||||
},
|
||||
"ESP-ADF": {
|
||||
"nome": "ESP-ADF",
|
||||
"icone": "🎵",
|
||||
"nome_completo": "ESP Audio Development Framework",
|
||||
"descricao": "Framework officiel pour les applications audio sur SoCs ESP32. Comprend des pipelines de décodage/encodage, des pilotes pour codecs I2S et le streaming audio réseau.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Audio Processing Framework",
|
||||
"funcao_principal": "Traitement, capture, lecture et diffusion audio sur dispositifs embarqués avec codecs matériels et logiciels",
|
||||
"caracteristicas": [
|
||||
"Architecture basée sur des éléments de pipeline (Audio Pipeline Framework)",
|
||||
"Décodage et encodage : MP3, AAC, WAV, OGG, FLAC, OPUS et AMR",
|
||||
"Pilotes intégrés pour codecs I2S populaires (ES8388, ES8311, TAS5805M, AC101)",
|
||||
"Protocoles de streaming : HTTP Live Streaming (HLS), DLNA, SIP et radio Web",
|
||||
"Intégration avec ESP-SR pour la commande vocale locale et la suppression d'écho (AEC)",
|
||||
"Gestion du volume, égaliseur graphique (EQ) et mélangeur audio multi-canaux",
|
||||
"Prise en charge des profils Bluetooth Audio : A2DP Sink, A2DP Source et BLE Audio"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Enceintes connectées et récepteurs audio Bluetooth / Wi-Fi",
|
||||
"Systèmes d'interphonie bidirectionnelle (VoIP / SIP)",
|
||||
"Sonnettes intelligentes avec capture et transmission audio",
|
||||
"Lecteurs audio réseau pour la radio en ligne et les podcasts",
|
||||
"Dispositifs d'alarme et retour sonore industriel"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-adf.c",
|
||||
"exemplos": "https://github.com/espressif/esp-adf/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-adf/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-adf",
|
||||
"cor": "#9B59B6"
|
||||
},
|
||||
"ESP-SR": {
|
||||
"nome": "ESP-SR",
|
||||
"icone": "🎙️",
|
||||
"nome_completo": "ESP Speech Recognition Framework",
|
||||
"descricao": "Framework d'Espressif pour la reconnaissance vocale et le traitement audio local (on-device), sans connexion Internet, garantissant une faible latence et une confidentialité totale.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "AI & Speech Framework",
|
||||
"funcao_principal": "Reconnaissance vocale sur puce : détection de mot de réveil (WakeNet) et commandes locales (MultiNet) hors ligne",
|
||||
"caracteristicas": [
|
||||
"Détection de mot d'activation WakeNet (ex. : 'Hi ESP', 'Hi Lexin') avec haute précision",
|
||||
"Reconnaissance de commandes locales MultiNet avec support multilingue",
|
||||
"Algorithme frontal acoustique (AFE) : annulation d'écho acoustique (AEC)",
|
||||
"Suppression de bruit de fond (BSS/NS) et formation de faisceau (Beamforming)",
|
||||
"Gain automatique (AGC) et détection d'activité vocale (VAD)",
|
||||
"Accélération vectorielle sur ESP32-S3 (instructions SIMD Xtensa)",
|
||||
"Fonctionnement 100% hors ligne sans envoi de données vers des serveurs tiers"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Panneaux muraux de contrôle domotique avec commandes vocales",
|
||||
"Appareils électroménagers commandés à la voix sans besoin d'Internet",
|
||||
"Équipements industriels nécessitant un fonctionnement mains-libres",
|
||||
"Jouets interactifs et dispositifs éducatifs",
|
||||
"Interfaces vocales garantissant la confidentialité des utilisateurs"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-sr.c",
|
||||
"exemplos": "https://github.com/espressif/esp-sr/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-sr/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-sr",
|
||||
"cor": "#3498DB"
|
||||
},
|
||||
"ESP-IoT-Solution": {
|
||||
"nome": "ESP-IoT-Solution",
|
||||
"icone": "🧰",
|
||||
"nome_completo": "ESP-IoT-Solution Component Library",
|
||||
"descricao": "Collection officielle de pilotes de périphériques, algorithmes de contrôle tactile, gestion d'énergie et utilitaires IoT conçus pour accélérer le développement sur ESP-IDF.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Drivers & IoT Utilities",
|
||||
"funcao_principal": "Bibliothèque prête à l'emploi de pilotes pour capteurs, écrans, bus industriels et algorithmes tactiles capacitifs",
|
||||
"caracteristicas": [
|
||||
"Pilotes prêts à l'emploi pour capteurs (I2C, SPI) : température, pression, IMU, lumière",
|
||||
"Pilotes d'écrans OLED et LCD (SSD1306, ST7789, ILI9341, GC9A01)",
|
||||
"Gestion avancée des boutons (clic, double-clic, appui long) et encodeurs rotatifs",
|
||||
"Algorithmes tactiles capacitifs : touches, curseurs, roues et détection d'approche",
|
||||
"Pilotes d'extension d'E/S (PCA9557, MCP23017, CH422G)",
|
||||
"Composants pour bus industriels : Modbus RTU/TCP et communication RS485",
|
||||
"Intégration directe comme composants ESP-IDF via idf_component.yml"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Interfaces tactiles capacitives pour l'électroménager et les commandes murales",
|
||||
"Stations météo et moniteurs environnementaux avec capteurs I2C",
|
||||
"Dispositifs d'automatisation industrielle communiquant via RS485 et Modbus",
|
||||
"Projets intégrant des écrans graphiques et des encodeurs rotatifs",
|
||||
"Systèmes nécessitant une gestion avancée d'événements de boutons"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-iot-solution.c",
|
||||
"exemplos": "https://github.com/espressif/esp-iot-solution/tree/usb/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-iot-solution/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-iot-solution",
|
||||
"cor": "#F39C12"
|
||||
},
|
||||
"ESP-NOW": {
|
||||
"nome": "ESP-NOW",
|
||||
"icone": "⚡",
|
||||
"nome_completo": "ESP-NOW Wireless Communication Protocol",
|
||||
"descricao": "Protocole sans fil propriétaire d'Espressif basé sur les trames d'action du standard 802.11. Permet une communication peer-to-peer rapide et basse consommation sans routeur Wi-Fi.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Fast Wireless Protocol",
|
||||
"funcao_principal": "Communication sans fil ultra-rapide et basse consommation entre dispositifs ESP sans routeur Wi-Fi",
|
||||
"caracteristicas": [
|
||||
"Communication directe peer-to-peer sans négociation AP ni point d'accès",
|
||||
"Temps de transmission ultra-faible : latence de quelques millisecondes",
|
||||
"Prise en charge de la diffusion unicast et broadcast",
|
||||
"Chiffrement sécurisé des trames via clés CCMP (AES-128)",
|
||||
"Faible consommation d'énergie, idéal pour les appareils fonctionnant sur batterie",
|
||||
"Compatibilité ascendante avec tous les modèles de SoCs ESP32 et ESP8266",
|
||||
"Charge utile jusqu'à 250 octets par paquet, suffisante pour la télémétrie et le contrôle"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Télécommandes et interrupteurs muraux sans fil à réveil instantané",
|
||||
"Réseaux de capteurs sur batterie envoyant des relevés périodiques",
|
||||
"Contrôleurs de drones, robots et modélisme télécommandé",
|
||||
"Boutons d'urgence industriels nécessitant une latence critique",
|
||||
"Communication de secours locale lorsque le réseau Wi-Fi est indisponible"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-now.c",
|
||||
"exemplos": "https://github.com/espressif/esp-now/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-now/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-now",
|
||||
"cor": "#E67E22"
|
||||
},
|
||||
"ESP-Zigbee-SDK": {
|
||||
"nome": "ESP-Zigbee-SDK",
|
||||
"icone": "🐝",
|
||||
"nome_completo": "Espressif Zigbee Software Development Kit",
|
||||
"descricao": "SDK officiel pour le développement de dispositifs Zigbee 3.0 sur les SoCs équipés de radio 802.15.4 (ESP32-H2 et ESP32-C6). Supporte les rôles de coordinateur, routeur et terminal.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Mesh & 802.15.4 Framework",
|
||||
"funcao_principal": "Création de dispositifs pour réseaux maillés Zigbee 3.0 avec interopérabilité industrielle certifiée",
|
||||
"caracteristicas": [
|
||||
"Conforme aux spécifications Zigbee 3.0 et Zigbee PRO",
|
||||
"Support de tous les rôles du réseau : Coordinateur (ZC), Routeur (ZR) et Terminal (ZED)",
|
||||
"Rôles basse consommation Sleepy End Device (SED) pour capteurs sur pile",
|
||||
"Prise en charge des profils standard : Zigbee Home Automation (ZHA) et Light Link",
|
||||
"Passerelle Zigbee vers Wi-Fi/Ethernet en combinant ESP32-H2 avec un autre SoC",
|
||||
"Mises à jour OTA conformes au protocole Zigbee OTA Cluster",
|
||||
"Intégration directe avec ESP-IDF et compatibilité Z-Stack"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Capteurs d'ouverture de porte, présence et fuite d'eau sur batterie",
|
||||
"Ampoules, variateurs et commutateurs Zigbee 3.0 interopérables",
|
||||
"Passerelles Zigbee vers Ethernet/Wi-Fi pour plateformes domotiques",
|
||||
"Thermostats et compteurs d'énergie industriels",
|
||||
"Modernisation d'installations existantes avec l'écosystème Zigbee standard"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-zigbee.c",
|
||||
"exemplos": "https://github.com/espressif/esp-zigbee-sdk/tree/main/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-zigbee-sdk/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-zigbee-sdk",
|
||||
"cor": "#F1C40F"
|
||||
},
|
||||
"ESP-WHO": {
|
||||
"nome": "ESP-WHO",
|
||||
"icone": "👁️",
|
||||
"nome_completo": "ESP-WHO Face Detection & Recognition Framework",
|
||||
"descricao": "Framework de vision par ordinateur pour ESP32, optimisé pour les modules caméra (OV2640, OV3660, OV5640) avec détection et reconnaissance de visages locales.",
|
||||
"linguagem": "C / C++",
|
||||
"tipo": "Computer Vision & Edge AI",
|
||||
"funcao_principal": "Vision par ordinateur embarquée avec détection, alignement et reconnaissance de visages",
|
||||
"caracteristicas": [
|
||||
"Modèles d'inférence légers optimisés pour le matériel ESP32 et ESP32-S3",
|
||||
"Détection de visages par apprentissage profond avec localisation de points de repère",
|
||||
"Reconnaissance faciale et inscription de visages directement dans la mémoire de l'appareil",
|
||||
"Pilote de caméra haute performance prenant en charge les bus DVP et SPI",
|
||||
"Support des résolutions de capture de QVGA à QSXGA",
|
||||
"Accélération vectorielle grâce aux instructions d'IA de l'ESP32-S3",
|
||||
"Serveur de streaming vidéo HTTP intégré pour le débogage et la prévisualisation"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Contrôle d'accès biométrique et serrures intelligentes avec reconnaissance faciale",
|
||||
"Sonnettes vidéo avec détection de présence humaine",
|
||||
"Comptage de personnes et analyse d'occupation de salles de réunion",
|
||||
"Caméras de sécurité intelligentes avec filtrage d'alertes locales",
|
||||
"Dispositifs d'assistance et interaction homme-machine"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-who.c",
|
||||
"exemplos": "https://github.com/espressif/esp-who/tree/master/examples",
|
||||
"documentacao": "https://github.com/espressif/esp-who#readme",
|
||||
"repositorio": "https://github.com/espressif/esp-who",
|
||||
"cor": "#1ABC9C"
|
||||
},
|
||||
"ESP-NN": {
|
||||
"nome": "ESP-NN",
|
||||
"icone": "🧠",
|
||||
"nome_completo": "ESP Neural Network Acceleration Library",
|
||||
"descricao": "Bibliothèque d'accélération d'opérations de réseaux neuronaux pour SoCs ESP32, optimisant les noyaux de convolution, produits matriciels et activations pour l'IA embarquée.",
|
||||
"linguagem": "C / C++ / Asm",
|
||||
"tipo": "Neural Network Kernel Library",
|
||||
"funcao_principal": "Noyaux d'inférence neuronale hautement optimisés en assembleur pour TensorFlow Lite for Microcontrollers",
|
||||
"caracteristicas": [
|
||||
"Optimisations assembleur exploitant les instructions vectorielles SIMD de l'ESP32-S3",
|
||||
"Opérations accélérées : convolutions 2D, Depthwise Conv, Fully Connected et Pooling",
|
||||
"Prise en charge de la quantification 8 bits (int8) et 16 bits (int16)",
|
||||
"Intégration transparente comme backend d'optimisation de TensorFlow Lite for Microcontrollers",
|
||||
"Réduction significative de la latence d'inférence par rapport aux implémentations génériques",
|
||||
"Empreinte mémoire SRAM optimisée pour les puces avec ressources restreintes",
|
||||
"Support de l'ESP32, ESP32-S3 et des architectures RISC-V (C3, C6, P4)"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Modèles de vision embarquée (détection d'objets et classification)",
|
||||
"Détection d'anomalies vibratoires et acoustiques pour la maintenance prédictive",
|
||||
"Classification de signaux biométriques (ECG, PPG) sur dispositifs portables",
|
||||
"Reconnaissance gestuelle et interfaces basées sur des capteurs inertiels (IMU)",
|
||||
"Modèles audio personnalisés pour la détection de sons spécifiques"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-nn.c",
|
||||
"exemplos": "https://github.com/espressif/esp-nn/tree/master/examples",
|
||||
"documentacao": "https://github.com/espressif/esp-nn#readme",
|
||||
"repositorio": "https://github.com/espressif/esp-nn",
|
||||
"cor": "#8E44AD"
|
||||
},
|
||||
"ESP-DSP": {
|
||||
"nome": "ESP-DSP",
|
||||
"icone": "📊",
|
||||
"nome_completo": "ESP Digital Signal Processing Library",
|
||||
"descricao": "Bibliothèque officielle de traitement du signal numérique (DSP) pour SoCs ESP32, fournissant des algorithmes de FFT, filtrage numérique, calcul matriciel et opérations mathématiques.",
|
||||
"linguagem": "C / Asm",
|
||||
"tipo": "DSP & Math Library",
|
||||
"funcao_principal": "Fonctions mathématiques et traitement numérique du signal haute performance optimisés pour le matériel",
|
||||
"caracteristicas": [
|
||||
"Transformée de Fourier rapide (FFT) réelle et complexe avec fenêtrage (Hann, Hamming, Blackman)",
|
||||
"Filtres numériques IIR (Biquad) et FIR optimisés",
|
||||
"Opérations matricielles : multiplication, inversion, décomposition et transposition",
|
||||
"Opérations vectorielles en virgule flottante et entière accélérées par le matériel",
|
||||
"Génération de signaux de test : sinus, bruit blanc et signaux modulés",
|
||||
"Routines en assembleur pour le coeur Xtensa et extensions d'instructions vectorielles",
|
||||
"Compatible avec ESP-IDF sous forme de composant natif"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Analyse spectrale en temps réel pour équipements audio et vibrationnels",
|
||||
"Traitement et filtrage de données de capteurs industriels bruités",
|
||||
"Algorithmes de contrôle de moteurs et onduleurs de puissance",
|
||||
"Compteurs d'énergie intelligents avec calcul de puissance active et réactive",
|
||||
"Analyse de signaux radar et capteurs à ultrasons"
|
||||
],
|
||||
"exemplo": "/exemplos/esp-dsp.c",
|
||||
"exemplos": "https://github.com/espressif/esp-dsp/tree/master/examples",
|
||||
"documentacao": "https://docs.espressif.com/projects/esp-dsp/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/esp-dsp",
|
||||
"cor": "#2C3E50"
|
||||
},
|
||||
"Rust-ESP": {
|
||||
"nome": "Rust-ESP",
|
||||
"icone": "🦀",
|
||||
"nome_completo": "Rust on ESP32 Ecosystem",
|
||||
"descricao": "Écosystème de programmation Rust pour microcontrôleurs ESP32, offrant une sécurité mémoire sans ramasse-miettes (garbage collector), un typage fort et une excellente expressivité.",
|
||||
"linguagem": "Rust",
|
||||
"tipo": "Memory-Safe Modern Language",
|
||||
"funcao_principal": "Développement de micrologiciels sécurisés avec prévention de corruptions mémoire et accès concurrentiel garanti sans data races",
|
||||
"caracteristicas": [
|
||||
"Support de deux approches : no_std (sur métal nu via esp-hal) et std (sur FreeRTOS via esp-idf-svc)",
|
||||
"Chaîne d'outils Rust officielle pour architectures Xtensa et RISC-V",
|
||||
"Sécurité de gestion mémoire garantie au moment de la compilation",
|
||||
"Modèle asynchrone moderne avec async/await pour les tâches réseau et périphériques",
|
||||
"Support des piles Wi-Fi, BLE, MQTT, HTTP et TLS via les crates de l'écosystème",
|
||||
"Outil espflash pour graver et surveiller les cartes en ligne de commande",
|
||||
"Intégration directe avec Cargo et l'ensemble de l'écosystème open source de Rust"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Micrologiciels industriels critiques nécessitant une haute fiabilité",
|
||||
"Dispositifs médicaux et de sécurité où les failles de mémoire sont intolérables",
|
||||
"Passerelles réseau nécessitant un traitement sécurisé des protocoles TLS et cryptographiques",
|
||||
"Applications modernes tirant parti de la programmation concurrente asynchrone",
|
||||
"Projets explorant les normes les plus récentes en matière de génie logiciel pour systèmes embarqués"
|
||||
],
|
||||
"exemplo": "/exemplos/rust-esp.rs",
|
||||
"exemplos": "https://github.com/esp-rs/esp-idf-template",
|
||||
"documentacao": "https://esp-rs.github.io/book/",
|
||||
"repositorio": "https://github.com/esp-rs",
|
||||
"cor": "#D35400"
|
||||
},
|
||||
"Arduino": {
|
||||
"nome": "Arduino",
|
||||
"icone": "♾️",
|
||||
"nome_completo": "Arduino Core for ESP32",
|
||||
"descricao": "Noyau officiel Arduino pour SoCs ESP32. Propose l'API familière setup()/loop() avec un accès à des milliers de bibliothèques tierces, reposant sur une base ESP-IDF robuste.",
|
||||
"linguagem": "C++ (Arduino)",
|
||||
"tipo": "Maker & Educational Framework",
|
||||
"funcao_principal": "Prototypage rapide et création de projets accessibles grâce au plus grand écosystème de bibliothèques open source au monde",
|
||||
"caracteristicas": [
|
||||
"Structure familière d'initialisation et boucle principale (setup / loop)",
|
||||
"Accès instantané à l'immense répertoire de bibliothèques Arduino",
|
||||
"Fonctionne sur FreeRTOS en arrière-plan, permettant la création de tâches avec xTaskCreate",
|
||||
"Support de la quasi-totalité des cartes ESP32 du marché",
|
||||
"Gestion du Wi-Fi et Bluetooth par des classes intuitives (WiFi, BluetoothSerial, BLEDevice)",
|
||||
"Mises à jour OTA facilitées avec la classe ArduinoOTA",
|
||||
"Compatible avec Arduino IDE, PlatformIO, VS Code et Arduino CLI"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Prototypage rapide de projets IoT et validation d'idées",
|
||||
"Éducation, projets universitaires et formation en systèmes embarqués",
|
||||
"Projets de la communauté Maker et bricolage électronique",
|
||||
"Appareils utilisant des bibliothèques de capteurs et d'actionneurs préexistantes",
|
||||
"Installations artistiques et projets interactifs"
|
||||
],
|
||||
"exemplo": "/exemplos/arduino.ino",
|
||||
"exemplos": "https://github.com/espressif/arduino-esp32/tree/master/libraries",
|
||||
"documentacao": "https://docs.espressif.com/projects/arduino-esp32/en/latest/",
|
||||
"repositorio": "https://github.com/espressif/arduino-esp32",
|
||||
"cor": "#00979C"
|
||||
},
|
||||
"MicroPython": {
|
||||
"nome": "MicroPython",
|
||||
"icone": "🐍",
|
||||
"nome_completo": "MicroPython for ESP32",
|
||||
"descricao": "Implémentation légère et efficace de Python 3 conçue pour les microcontrôleurs. Permet une programmation interactive via REPL sur console série sans étape de compilation.",
|
||||
"linguagem": "Python 3",
|
||||
"tipo": "Interactive Scripting Engine",
|
||||
"funcao_principal": "Développement rapide et interactif avec la simplicité de Python et la commande immédiate du matériel",
|
||||
"caracteristicas": [
|
||||
"Interpréteur Python 3 complet optimisé pour fonctionner sur microcontrôleur",
|
||||
"Console interactive REPL (Read-Eval-Print Loop) accessible via port série ou Wi-Fi (WebREPL)",
|
||||
"Système de fichiers virtuel avec support de fichiers .py et modules compilés .mpy",
|
||||
"Modules matériels intuitifs : machine (Pin, ADC, PWM, I2C, SPI, UART, Timer, RTC)",
|
||||
"Support natif du réseau : module network (Wi-Fi Station et Access Point)",
|
||||
"Prise en charge de la programmation asynchrone avec le module uasyncio",
|
||||
"Support officiel pour tous les modèles ESP32 avec micrologiciels binaires précompilés"
|
||||
],
|
||||
"casos_uso": [
|
||||
"Apprentissage de la programmation et projets éducatifs",
|
||||
"Prototypage rapide de scripts de test et de validation de capteurs",
|
||||
"Contrôle d'appareils et interfaces de script modifiables sans flash complet",
|
||||
"Enregistreurs de données autonomes et petits serveurs HTTP/WebSockets",
|
||||
"Automatisation légère et intégration de capteurs de laboratoire"
|
||||
],
|
||||
"exemplo": "/exemplos/micropython.py",
|
||||
"exemplos": "https://github.com/micropython/micropython/tree/master/examples",
|
||||
"documentacao": "https://docs.micropython.org/en/latest/esp32/quickref.html",
|
||||
"repositorio": "https://github.com/micropython/micropython",
|
||||
"cor": "#2B5B84"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,732 @@
|
||||
{
|
||||
"ESP32": {
|
||||
"nome_completo": "ESP32 (Clássico)",
|
||||
"icone": "🔷",
|
||||
"descricao": "Le pionnier de la gamme avec double cœur Xtensa, Wi-Fi 4 et Bluetooth classique/BLE. Recommandé pour les projets audio classiques et les passerelles IoT établies.",
|
||||
"arquitetura": "Xtensa® LX6 bicœur 32 bits",
|
||||
"nucleos": "1 (Single-core) ou 2 (Dual-core)",
|
||||
"frequencia": "Jusqu'à 240 MHz",
|
||||
"coprocessador_ulp": "Oui",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/192/256",
|
||||
"sha": "SHA-1/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 4096 bits)",
|
||||
"ecc": "Nonn",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Nonn",
|
||||
"assinatura_digital": "Nonn",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "Oui (AES-256, schéma hérité)",
|
||||
"secure_boot": "V1 (AES, hérité); V2 (RSA-3072, RSA-PSS) à partir de la révision v3.0 (ECO3)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, jusqu'à 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 4.2 BR/EDR (Clássico) et Bluetooth LE (dual mode)",
|
||||
"ethernet": "Oui (Ethernet MAC integrado)",
|
||||
"memoria_sram": "520 KB",
|
||||
"memoria_sram_rtc": "16 KB (dividida em RTC FAST e RTC SLOW)",
|
||||
"memoria_rom": "448 KB (pour le démarrage et les fonctions du noyau)",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI",
|
||||
"psram_externa": "Jusqu'à 8 MB via QSPI (dans des modules spécifiques comme WROVER)",
|
||||
"gpio": "34",
|
||||
"adc": "2x SAR ADC de 12 bits, até 18 canais",
|
||||
"dac": "2x DAC de 8 bits",
|
||||
"touch": "10 canais capacitivos",
|
||||
"uart": "3",
|
||||
"spi": "4 (SPI, HSPI, VSPI - 2 podem ser usados para Flash/PSRAM)",
|
||||
"i2c": "2",
|
||||
"i2s": "2",
|
||||
"pwm": "LED PWM (jusqu'à 16 canaux), Motor PWM",
|
||||
"ethernet_mac": "1 (requer PHY externo)",
|
||||
"can": "1 (CAN 2.0, TWAI®)",
|
||||
"sdio": "1 (SD/SDIO/MMC Host), 1 (SDIO/SPI Slave)",
|
||||
"sensor_hall": "1 (interno)",
|
||||
"sensor_temperatura": "Nonn (retirado do datasheet em 2018; sem driver no ESP-IDF)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_240mhz": "30-68 mA",
|
||||
"active_wifi_tx": "180-240 mA",
|
||||
"modem_sleep": "20-44 mA",
|
||||
"light_sleep": "0.8 mA",
|
||||
"deep_sleep": "10-150 µA",
|
||||
"hibernation": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 125°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG externe (nécessite une sonde, ex. : ESP-PROG)",
|
||||
"esp_idf_minimo": "Depuis le début (v3.x et versions antérieures)",
|
||||
"arduino_core": "Oui (147 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN48 (6×6 mm) et QFN48 (5×5 mm)",
|
||||
"modulos": "ESP32-MINI-1, ESP32-PICO-MINI-02, ESP32-PICO-V3, ESP32-PICO-V3-02 e mais 11",
|
||||
"datasheet": "https://documentation.espressif.com/esp32_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32/get-started/index.html",
|
||||
"placa": "/placas/esp32.png",
|
||||
"cor": "#007bff"
|
||||
},
|
||||
"ESP32-S2": {
|
||||
"nome_completo": "ESP32-S2",
|
||||
"icone": "🔒",
|
||||
"descricao": "SoC monocœur avec interface USB OTG native, sécurité matérielle renforcée et jusqu'à 43 GPIO. Conçu pour les interfaces d'affichage simples et les périphériques USB sécurisés.",
|
||||
"arquitetura": "Xtensa® LX7 monocœur 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Jusqu'à 240 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/192/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 4096 bits)",
|
||||
"ecc": "Nonn",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, jusqu'à 150 Mbps)",
|
||||
"bluetooth": "Nonn",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Jusqu'à 1 GB via QSPI",
|
||||
"psram_externa": "Jusqu'à 1 GB via QSPI/Octal SPI",
|
||||
"gpio": "43",
|
||||
"adc": "2x SAR ADC, até 20 canais: saída de 13 bits (0–8191, única da família), resolução efetiva de 12 bits a partir da revisão v1.0 (errata ADC-112)",
|
||||
"dac": "2x DAC de 8 bits",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "2",
|
||||
"spi": "4 (SPI0/1 para Flash, SPI2/3 para uso geral)",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 8 canaux)",
|
||||
"usb": "1 (USB OTG 1.1 Full-Speed)",
|
||||
"lcd": "Interface LCD 8/16 bits",
|
||||
"camera": "Interface DVP 8/16 bits",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi_tx": "160-310 mA",
|
||||
"modem_sleep_cpu_160mhz": "14-24 mA",
|
||||
"light_sleep": "750 µA",
|
||||
"deep_sleep": "20-190 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG externe (nécessite une sonde, ex. : ESP-PROG)",
|
||||
"esp_idf_minimo": "v4.2",
|
||||
"arduino_core": "Oui (26 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN56 (7×7 mm)",
|
||||
"modulos": "ESP32-S2-MINI-1, ESP32-S2-MINI-2, ESP32-S2-SOLO, ESP32-S2-SOLO-2 e mais 4",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s2/get-started/index.html",
|
||||
"placa": "/placas/esp32-s2.png",
|
||||
"cor": "#28a745"
|
||||
},
|
||||
"ESP32-S3": {
|
||||
"nome_completo": "ESP32-S3",
|
||||
"icone": "🤖",
|
||||
"descricao": "Double cœur haute performance avec extensions vectorielles pour l'IA, USB natif et jusqu'à 45 GPIO. Le choix standard pour la vision par ordinateur, la reconnaissance vocale et les interfaces riches (HMI).",
|
||||
"arquitetura": "Xtensa® LX7 bicœur 32 bits",
|
||||
"nucleos": "2 (Dual-core)",
|
||||
"frequencia": "Jusqu'à 240 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V)",
|
||||
"aceleradores_ia": "Sim (Vector Instructions para IA)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 4096 bits)",
|
||||
"ecc": "Nonn",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, jusqu'à 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 5 (LE) et Bluetooth Mesh",
|
||||
"memoria_sram": "512 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "384 KB",
|
||||
"flash_externa": "Jusqu'à 1 GB via QSPI/Octal SPI",
|
||||
"psram_externa": "Jusqu'à 1 GB via QSPI/Octal SPI",
|
||||
"gpio": "45",
|
||||
"adc": "2x SAR ADC de 12 bits, até 20 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "3",
|
||||
"spi": "4 (SPI0/1 para Flash, SPI2/3 para uso geral)",
|
||||
"i2c": "2",
|
||||
"i2s": "2",
|
||||
"pwm": "LED PWM (jusqu'à 8 canaux), Motor PWM (6 canaux)",
|
||||
"usb": "1 (USB OTG 1.1 Full-Speed) + 1 (USB Serial/JTAG)",
|
||||
"lcd": "Interface LCD RGB 8/16 bits",
|
||||
"camera": "Interface DVP 8/16 bits",
|
||||
"sdio": "1 (SD/SDIO/MMC Host)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "78 mW (~24 mA @3.3V)",
|
||||
"modem_sleep": "13-42 mA (40-80 MHz, conforme a carga)",
|
||||
"light_sleep": "240 µA (+40 a 200 µA pour la PSRAM)",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 65/85/105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v4.4",
|
||||
"arduino_core": "Oui (158 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN56 (7×7 mm)",
|
||||
"modulos": "ESP32-S3-MINI-1, ESP32-S3-WROOM-1, ESP32-S3-WROOM-2",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s3/get-started/index.html",
|
||||
"placa": "/placas/esp32-s3.png",
|
||||
"cor": "#fd7e14"
|
||||
},
|
||||
"ESP32-S31": {
|
||||
"nome_completo": "ESP32-S31",
|
||||
"icone": "🌀",
|
||||
"descricao": "SoC avancé optimisé pour le traitement d'IA générative et de vision sur l'edge, combinant double cœur Xtensa haute fréquence et sécurité matérielle de nouvelle génération.",
|
||||
"arquitetura": "RISC-V bicœur 32 bits (HP) + RISC-V monocœur (LP)",
|
||||
"nucleos": "2 (Dual-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Jusqu'à 320 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V, LP CPU de 40 MHz)",
|
||||
"aceleradores_ia": "Sim (Custom AI and DSP extension XespV)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 4096 bits)",
|
||||
"ecc": "Oui (P-192, P-256, P-384)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Oui",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072)",
|
||||
"protecao_dpa": "Oui"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5.4 LE et Bluetooth Classic",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Oui",
|
||||
"memoria_sram": "512 KB (HP SRAM)",
|
||||
"memoria_sram_rtc": "32 KB (LP SRAM)",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Jusqu'à 256 MB via QSPI",
|
||||
"psram_externa": "16 MB ou 32 MB octal DDR, uniquement dans le boîtier (NRV16, NRV32)",
|
||||
"gpio": "60",
|
||||
"adc": "2x SAR ADC de 12 bits, até 16 canais",
|
||||
"dac": "Oui (2x DAC de 10 bits e 2x DAC de 12 bits)",
|
||||
"touch": "14 canais capacitivos",
|
||||
"uart": "5 (4 UART + 1 LP UART)",
|
||||
"spi": "7 (6 SPI + 1 LP SPI)",
|
||||
"i2c": "3 (2 I2C + 1 LP I2C)",
|
||||
"i2s": "2",
|
||||
"pwm": "LED PWM (jusqu'à 8 canaux), Motor PWM (MCPWM)",
|
||||
"usb": "1 (USB 2.0 High-Speed OTG e USB Serial/JTAG)",
|
||||
"can": "Oui (CAN FD Controller)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "Consommation optimisée haute performance configurable",
|
||||
"light_sleep": "0.1-0.8 mA",
|
||||
"deep_sleep": "Baixo consumo com LP CPU ativa"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 85°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v6.1 en aperçu ; support officiel à partir de la v6.1.1",
|
||||
"arduino_core": "Pas encore pris en charge par le core arduino-esp32",
|
||||
"encapsulamento": "QFN80 (8×8 mm)",
|
||||
"modulos": "ESP32-S31-WROOM-1, ESP32-S31-WROOM-3",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-s31_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-s31_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32s31/get-started/index.html",
|
||||
"placa": "/placas/esp32-s31.png",
|
||||
"cor": "#ff2a5f",
|
||||
"sdio": "1 (SDIO Host 3.0)"
|
||||
},
|
||||
"ESP32-C2": {
|
||||
"nome_completo": "ESP32-C2 (ESP8684)",
|
||||
"icone": "🌱",
|
||||
"descricao": "Puce RISC-V compacte et économique conçue pour les capteurs simples et le remplacement direct de l'ESP8266 dans les déploiements de volume.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Jusqu'à 120 MHz",
|
||||
"seguranca": {
|
||||
"aes": "Nonn",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Nonn",
|
||||
"ecc": "Oui (P-192, P-256)",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Nonn",
|
||||
"assinatura_digital": "Nonn",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (ECDSA P-192 ou P-256)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, jusqu'à 72.2 Mbps)",
|
||||
"bluetooth": "Bluetooth 5.3 LE (certificado)",
|
||||
"memoria_sram": "272 KB (16 KB para cache)",
|
||||
"memoria_sram_rtc": "Non",
|
||||
"memoria_rom": "576 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI, mais indisponible sur les variantes vendues (ESP8684H2X/H4X ont 2 MB ou 4 MB dans le boîtier et n'exposent pas les broches de flash)",
|
||||
"psram_externa": "Nonn",
|
||||
"gpio": "14",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "2",
|
||||
"spi": "3 (SPI0/1 para Flash interna, SPI2 para uso geral)",
|
||||
"i2c": "1 (Master-only)",
|
||||
"i2s": "Non",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_120mhz": "10,7-15,6 mA (modem-sleep)",
|
||||
"light_sleep": "140 µA",
|
||||
"deep_sleep": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG externe (nécessite une sonde, ex. : ESP-PROG)",
|
||||
"esp_idf_minimo": "v5.0",
|
||||
"arduino_core": "Oui (1 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN24 (4×4 mm)",
|
||||
"modulos": "ESP8684-MINI-1, ESP8684-WROOM-01C, ESP8684-WROOM-02C, ESP8684-WROOM-02UC e mais 5",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c2/get-started/index.html",
|
||||
"placa": "/placas/esp32-c2.png",
|
||||
"cor": "#8c52ff"
|
||||
},
|
||||
"ESP32-C3": {
|
||||
"nome_completo": "ESP32-C3",
|
||||
"icone": "💎",
|
||||
"descricao": "Puce RISC-V monocœur économique, compatible broche à broche avec l'ESP8266. Offre Wi-Fi 4 et Bluetooth 5 (BLE) pour les appareils connectés compacts.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Jusqu'à 160 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 3072 bits)",
|
||||
"ecc": "Nonn",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072), à partir de la révision v0.3 (ECO3)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "IEEE 802.11 b/g/n (2.4 GHz, jusqu'à 150 Mbps)",
|
||||
"bluetooth": "Bluetooth 5 (LE) et Bluetooth Mesh",
|
||||
"memoria_sram": "400 KB",
|
||||
"memoria_sram_rtc": "8 KB",
|
||||
"memoria_rom": "384 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI",
|
||||
"psram_externa": "Nonn",
|
||||
"gpio": "22",
|
||||
"adc": "2x SAR ADC de 12 bits, até 6 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "2",
|
||||
"spi": "3 (SPI0/1 para Flash, SPI2 para uso geral)",
|
||||
"i2c": "1",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_cpu_160mhz": "20 mA",
|
||||
"active_wifi_tx_peak": "335 mA",
|
||||
"modem_sleep_cpu_160mhz": "16-28 mA",
|
||||
"light_sleep": "130 µA",
|
||||
"deep_sleep": "5 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40 °C à 105 °C (85 °C sur l'ESP32-C3FN4)",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v4.3",
|
||||
"arduino_core": "Oui (29 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN32 (5×5 mm) et QFN28 (4×4 mm)",
|
||||
"modulos": "ESP32-C3-MINI-1, ESP32-C3-WROOM-02",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c3/get-started/index.html",
|
||||
"placa": "/placas/esp32-c3.png",
|
||||
"cor": "#20c997"
|
||||
},
|
||||
"ESP32-C5": {
|
||||
"nome_completo": "ESP32-C5",
|
||||
"icone": "📶",
|
||||
"descricao": "Premier SoC double bande (2,4 GHz et 5 GHz) de la série C avec architecture RISC-V. Conçu pour les environnements industriels avec saturation radio en 2,4 GHz.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits (HP) + RISC-V monocœur (LP)",
|
||||
"nucleos": "1 (Single-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Jusqu'à 240 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V, LP CPU de 48 MHz)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 3072 bits)",
|
||||
"ecc": "Oui (P-192, P-256, P-384)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Oui",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA P-256/P-384)",
|
||||
"protecao_dpa": "Oui"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) double bande 2.4 GHz e 5 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth Core 6.0 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Oui",
|
||||
"memoria_sram": "384 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI",
|
||||
"psram_externa": "Oui, via SPI (controlador de flash/PSRAM com cache)",
|
||||
"gpio": "29",
|
||||
"adc": "1x SAR ADC de 12 bits, até 6 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "3 (2 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "2 (1 I2C + 1 LP I2C)",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux), Motor PWM",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi": "jusqu'à 377 mA (TX en 5 GHz)",
|
||||
"light_sleep": "60-250 µA",
|
||||
"deep_sleep": "12 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v5.5.2",
|
||||
"arduino_core": "Oui (10 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN48 (6×6 mm)",
|
||||
"modulos": "ESP32-C5-MINI-1, ESP32-C5-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c5_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c5_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c5/get-started/index.html",
|
||||
"placa": "/placas/esp32-c5.png",
|
||||
"cor": "#6f42c1",
|
||||
"sdio": "1 (SDIO Slave, a partir da revisão v1.0)",
|
||||
"can": "2 (CAN FD)"
|
||||
},
|
||||
"ESP32-C6": {
|
||||
"nome_completo": "ESP32-C6",
|
||||
"icone": "🌐",
|
||||
"descricao": "SoC RISC-V moderne avec Wi-Fi 6, Bluetooth 5 (LE) et radio IEEE 802.15.4 intégrée. Idéal pour les appareils connectés basse consommation conformes à Matter et Thread.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits (HP) + RISC-V monocœur (LP)",
|
||||
"nucleos": "1 (Single-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Jusqu'à 160 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V, LP CPU de 20 MHz)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 3072 bits)",
|
||||
"ecc": "Oui (P-192, P-256)",
|
||||
"ecdsa": "Nonn",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Oui"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth 5.3 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.3)",
|
||||
"matter": "Oui",
|
||||
"memoria_sram": "512 KB",
|
||||
"memoria_sram_rtc": "16 KB",
|
||||
"memoria_rom": "320 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI",
|
||||
"psram_externa": "Nonn",
|
||||
"gpio": "30",
|
||||
"adc": "1x SAR ADC de 12 bits, até 7 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "3 (2 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "2 (1 I2C + 1 LP I2C)",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux), Motor PWM",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sdio": "1 (SDIO 2.0 Slave)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active_wifi6": "252-354 mA (TX)",
|
||||
"light_sleep": "35-180 µA",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v5.1",
|
||||
"arduino_core": "Oui (21 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN40 (5×5 mm) et QFN32 (5×5 mm)",
|
||||
"modulos": "ESP32-C6-MINI-1, ESP32-C6-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c6_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c6_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c6/get-started/index.html",
|
||||
"placa": "/placas/esp32-c6.png",
|
||||
"cor": "#17a2b8"
|
||||
},
|
||||
"ESP32-C61": {
|
||||
"nome_completo": "ESP32-C61",
|
||||
"icone": "🛰️",
|
||||
"descricao": "Variante économique du C6 optimisée pour les nœuds finaux Wi-Fi 6 et BLE, sans la radio 802.15.4, idéale pour les capteurs connectés à grande échelle.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Jusqu'à 160 MHz",
|
||||
"seguranca": {
|
||||
"aes": "Nonn",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Nonn",
|
||||
"ecc": "Oui (P-192, P-256)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Nonn",
|
||||
"assinatura_digital": "Nonn",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (ECDSA)",
|
||||
"protecao_dpa": "Oui"
|
||||
},
|
||||
"wifi": "Wi-Fi 6 (802.11ax) 2.4 GHz",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth Core 6.0 certificado)",
|
||||
"zigbee_thread": "Nonn",
|
||||
"matter": "Oui (via Wi-Fi)",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "Non",
|
||||
"memoria_rom": "256 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI (modèles avec 4 MB ou 8 MB intégrés dans le boîtier)",
|
||||
"psram_externa": "Jusqu'à 16 MB via QSPI (modèles avec 2 MB ou 8 MB intégrés dans le boîtier)",
|
||||
"gpio": "30",
|
||||
"adc": "1x SAR ADC de 12 bits, até 4 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "3",
|
||||
"spi": "3 (2 para Flash/PSRAM, 1 para uso geral)",
|
||||
"i2c": "1",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sdio": "1 (SDIO 2.0 Slave)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "240-360 mA (TX)",
|
||||
"light_sleep": "50-200 µA",
|
||||
"deep_sleep": "10 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v5.5.2",
|
||||
"arduino_core": "Oui (1 definições de placa no core oficial)",
|
||||
"encapsulamento": "Boîtier QFN40 (5×5 mm) ou LGA40 (5×5 mm)",
|
||||
"modulos": "ESP32-C61-MINI-1, ESP32-C61-WROOM-1",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-c61_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-c61_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32c61/get-started/index.html",
|
||||
"placa": "/placas/esp32-c61.png",
|
||||
"cor": "#0dcaf0"
|
||||
},
|
||||
"ESP32-P4": {
|
||||
"nome_completo": "ESP32-P4",
|
||||
"icone": "⚡",
|
||||
"descricao": "Microcontrôleur haute performance sans radio intégrée, doté d'un double cœur RISC-V à 400 MHz, d'interfaces vidéo MIPI-CSI/DSI et d'une sécurité renforcée pour les écrans complexes et les passerelles.",
|
||||
"arquitetura": "RISC-V 32 bits bicœur de alto desempenho (HP) + monocœur de baixo consumo (LP)",
|
||||
"nucleos": "2 (Dual-core HP) + 1 (Single-core LP)",
|
||||
"frequencia": "Jusqu'à 400 MHz (HP, revisão v3.x; 360 MHz na v1.x); LP até 40 MHz",
|
||||
"coprocessador_ulp": "Oui (RISC-V, LP CPU de 40 MHz)",
|
||||
"aceleradores_ia": "Sim (Vector Instructions, aceleradores de IA)",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256 com GCM",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 4096 bits)",
|
||||
"ecc": "Oui (P-192, P-256, P-384)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Oui",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "Nonn",
|
||||
"bluetooth": "Nonn",
|
||||
"ethernet": "Oui (Ethernet MAC integrado)",
|
||||
"memoria_sram": "768 KB",
|
||||
"memoria_sram_rtc": "32 KB",
|
||||
"memoria_rom": "128 KB (HP ROM) + 16 KB (LP ROM)",
|
||||
"flash_externa": "Jusqu'à 128 MB via QSPI/Octal SPI",
|
||||
"psram_externa": "16 MB ou 32 MB intégrés dans le boîtier (OPI/HPI, 1,8 V)",
|
||||
"gpio": "55",
|
||||
"adc": "2x SAR ADC de 12 bits, até 14 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Oui (sensor de toque capacitivo)",
|
||||
"uart": "6 (5 UART + 1 LP UART)",
|
||||
"spi": "3",
|
||||
"i2c": "3 (2 I2C + 1 LP I2C)",
|
||||
"i2s": "4 (3 I2S + 1 LP I2S)",
|
||||
"pwm": "LED PWM (jusqu'à 8 canaux), Motor PWM (6 canaux)",
|
||||
"usb": "USB 2.0 High-Speed OTG + USB 2.0 Full-Speed OTG + USB Serial/JTAG",
|
||||
"mipi_csi": "Interface de caméra MIPI CSI",
|
||||
"mipi_dsi": "Interface MIPI DSI para display",
|
||||
"lcd": "Interface LCD 8/16/24 bits",
|
||||
"camera": "Interface DVP 8/16 bits",
|
||||
"sdio": "1 contrôleur hôte SD/MMC (SDHOST)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "15-150 mA (40 a 400 MHz, conforme a carga)",
|
||||
"light_sleep": "75-800 µA",
|
||||
"deep_sleep": "12 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 85°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v5.3",
|
||||
"arduino_core": "Oui (7 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN104 (10×10 mm)",
|
||||
"modulos": "Aucun module au catalogue officiel (puce nue uniquement)",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-p4-chip-revision-v1.3_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-p4-chip-revision-v1.3_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32p4/get-started/index.html",
|
||||
"placa": "/placas/esp32-p4.png",
|
||||
"cor": "#ffc107"
|
||||
},
|
||||
"ESP32-H2": {
|
||||
"nome_completo": "ESP32-H2",
|
||||
"icone": "🔋",
|
||||
"descricao": "Puce ultra-basse consommation sans Wi-Fi, dédiée à Zigbee 3.0, Thread 1.3 et Matter sur 802.15.4, avec Bluetooth 5.4 LE. Parfaite pour les capteurs fonctionnant sur pile.",
|
||||
"arquitetura": "RISC-V monocœur 32 bits",
|
||||
"nucleos": "1 (Single-core)",
|
||||
"frequencia": "Jusqu'à 96 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256",
|
||||
"rsa": "Oui (RSA/MPI jusqu'à 3072 bits)",
|
||||
"ecc": "Oui (P-192, P-256)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Oui",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128",
|
||||
"secure_boot": "V2 (RSA-3072 ou ECDSA)",
|
||||
"protecao_dpa": "Oui"
|
||||
},
|
||||
"wifi": "Nonn",
|
||||
"bluetooth": "Bluetooth 5 (LE) (Bluetooth 5.3 certificado)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Oui",
|
||||
"memoria_sram": "320 KB",
|
||||
"memoria_sram_rtc": "4 KB (LP Memory)",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Jusqu'à 16 MB via QSPI",
|
||||
"psram_externa": "Nonn",
|
||||
"gpio": "19",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "Nonn",
|
||||
"uart": "2",
|
||||
"spi": "3",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 6 canaux)",
|
||||
"usb": "1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "24-140 mA (radio, de -24 a 20 dBm)",
|
||||
"light_sleep": "25-85 µA",
|
||||
"deep_sleep": "7 µA"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "-40°C a 150°C",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v5.1",
|
||||
"arduino_core": "Oui (3 definições de placa no core oficial)",
|
||||
"encapsulamento": "QFN32 (4×4 mm)",
|
||||
"modulos": "ESP32-H2-MINI-1, ESP32-H2-WROOM-02C",
|
||||
"datasheet": "https://documentation.espressif.com/esp32-h2_datasheet_en.html",
|
||||
"manual_tecnico": "https://documentation.espressif.com/esp32-h2_technical_reference_manual_en.html",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32h2/get-started/index.html",
|
||||
"placa": "/placas/esp32-h2.png",
|
||||
"cor": "#6c757d"
|
||||
},
|
||||
"ESP32-H4": {
|
||||
"nome_completo": "ESP32-H4",
|
||||
"icone": "🛡️",
|
||||
"descricao": "Évolution de la gamme 802.15.4 avec double cœur RISC-V, Bluetooth 5.4 et portée radio étendue, optimisée pour les passerelles et routeurs de bordure Thread.",
|
||||
"status_documentacao": "Documentation préliminaire : Espressif n'a pas encore publié la fiche technique ni le manuel technique de l'ESP32-H4. Les données ci-dessous proviennent de l'annonce officielle du produit et des définitions matérielles (soc_caps) d'ESP-IDF, et peuvent évoluer jusqu'au lancement.",
|
||||
"arquitetura": "RISC-V bicœur 32 bits",
|
||||
"nucleos": "2 (Dual-core)",
|
||||
"frequencia": "Jusqu'à 96 MHz",
|
||||
"seguranca": {
|
||||
"aes": "AES-128/256",
|
||||
"sha": "SHA-1/224/256/384/512",
|
||||
"rsa": "Nonn",
|
||||
"ecc": "Oui (P-192, P-256, P-384)",
|
||||
"ecdsa": "Oui (modo determinístico, RFC 6979)",
|
||||
"hmac": "Oui",
|
||||
"assinatura_digital": "Nonn",
|
||||
"key_manager": "Nonn",
|
||||
"rng": "Oui (TRNG matériel)",
|
||||
"criptografia_flash": "XTS-AES-128/256",
|
||||
"secure_boot": "Oui au niveau matériel ; pas encore activé dans ESP-IDF",
|
||||
"protecao_dpa": "Nonn"
|
||||
},
|
||||
"wifi": "Nonn",
|
||||
"bluetooth": "Bluetooth 5.4 LE (certificado Bluetooth 6.0; LE Audio, canais isócronos BIS/CIS, PAwR, Connection Subrating et Direction Finding AoA/AoD)",
|
||||
"zigbee_thread": "IEEE 802.15.4 (Zigbee 3.0, Thread 1.4)",
|
||||
"matter": "Oui",
|
||||
"memoria_sram": "384 KB",
|
||||
"memoria_sram_rtc": "Sim (LP SRAM)",
|
||||
"memoria_rom": "128 KB",
|
||||
"flash_externa": "Sim, via QSPI (4 MB integrada no encapsulamento no ESP32-H4HF4)",
|
||||
"psram_externa": "Oui (2 MB integrada no encapsulamento no ESP32-H4HR2)",
|
||||
"gpio": "40",
|
||||
"adc": "1x SAR ADC de 12 bits, até 5 canais",
|
||||
"dac": "Nonn",
|
||||
"touch": "15 canais capacitivos (versão 3, com waterproof e proximidade)",
|
||||
"uart": "2",
|
||||
"spi": "3",
|
||||
"i2c": "2",
|
||||
"i2s": "1",
|
||||
"pwm": "LED PWM (jusqu'à 8 canaux), Motor PWM (MCPWM)",
|
||||
"can": "1 (CAN 2.0, TWAI®)",
|
||||
"usb": "1 (USB OTG 1.1) + 1 (USB Serial/JTAG)",
|
||||
"sensor_temperatura": "1 (interno)",
|
||||
"consumo_energia": {
|
||||
"active": "Non communiqué (documentation préliminaire)"
|
||||
},
|
||||
"temperatura_operacao": "-40°C a 105°C",
|
||||
"temperatura_armazenamento": "Non communiqué (documentation préliminaire)",
|
||||
"depuracao": "JTAG intégré via USB (aucune sonde externe requise)",
|
||||
"esp_idf_minimo": "v6.0 en aperçu (sans support stable)",
|
||||
"arduino_core": "Pas encore pris en charge par le core arduino-esp32",
|
||||
"encapsulamento": "QFN56 (6×6 mm)",
|
||||
"modulos": "ESP32-H4-WROOM-1",
|
||||
"guia_de_programacao": "https://docs.espressif.com/projects/esp-idf/en/latest/esp32h4/get-started/index.html",
|
||||
"cor": "#e83e8c"
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -5,7 +5,7 @@
|
||||
|
||||
// Ponto único de configuração de idiomas ATIVOS.
|
||||
// Para ativar um novo idioma no site, basta adicionar seu código aqui (ex.: ["pt", "en", "es"]).
|
||||
export const ENABLED_LOCALES = ["pt", "en", "es"];
|
||||
export const ENABLED_LOCALES = ["pt", "en", "es", "fr", "de"];
|
||||
|
||||
export const ALL_LOCALES = [
|
||||
{ code: "pt", label: "Português", short: "PT", lang: "pt-BR", og: "pt_BR" },
|
||||
|
||||
File diff suppressed because it is too large.
Load diff
@@ -0,0 +1,724 @@
|
||||
/**
|
||||
* Strukturierte Datenbank für Fehlerdiagnose, häufige Fehler und Problembehebung auf ESP32.
|
||||
* Umfasst 6 technische Kategorien mit Ursachenanalysen, Best Practices vs. Behelfslösungen und Codebeispielen
|
||||
* in Arduino C++, ESP-IDF (C) und MicroPython.
|
||||
*/
|
||||
|
||||
export const categoriasDiagnostico = [
|
||||
{
|
||||
id: "alimentacao",
|
||||
nome: "Stromversorgung & Hardware",
|
||||
icone: "Zap",
|
||||
cor: "amber",
|
||||
descricao: "Spannungseinbrüche durch Wi-Fi-/BLE-Sendeimpulse, fehlerhafte Pegel an Strapping-Pins, elektromagnetisches Rauschen und überlastete LDOs.",
|
||||
},
|
||||
{
|
||||
id: "cpu-panics",
|
||||
nome: "CPU-Panics & Guru Meditation",
|
||||
icone: "Cpu",
|
||||
cor: "red",
|
||||
descricao: "Nullzeiger, Speicherzugriffsverletzungen (Load/StoreProhibited), ungültige Befehle und Cache-Panics in Interrupt-Routinen (ISRs).",
|
||||
},
|
||||
{
|
||||
id: "freertos",
|
||||
nome: "FreeRTOS & Multitasking",
|
||||
icone: "Layers",
|
||||
cor: "purple",
|
||||
descricao: "Task Watchdog (TWDT), Interrupt Watchdog (IWDT), Stack-Überlauf (Stack Overflow) und Blockaden des RTOS-Schedulers.",
|
||||
},
|
||||
{
|
||||
id: "memoria",
|
||||
nome: "Speicher, Heap & PSRAM",
|
||||
icone: "Activity",
|
||||
cor: "blue",
|
||||
descricao: "Heap-Fragmentierung, Speicherlecks (Memory Leaks), DMA-Speicherallokation und Zugriffsrestriktionen bei externem PSRAM.",
|
||||
},
|
||||
{
|
||||
id: "boot-flash",
|
||||
nome: "Bootloader & Flashen",
|
||||
icone: "Terminal",
|
||||
cor: "emerald",
|
||||
descricao: "Serielle Verbindungsfehler (DTR/RTS), SPI-Flash-Lesefehler, Taktunstimmigkeiten und beschädigte Partitionstabellen.",
|
||||
},
|
||||
{
|
||||
id: "conectividade",
|
||||
nome: "Konnektivität & Protokolle",
|
||||
icone: "Wifi",
|
||||
cor: "cyan",
|
||||
descricao: "Wi-Fi-Beacon-Timeouts, fehlgeschlagene TLS/HTTPS-Handshakes mangels synchronisierter SNTP-Uhrzeit und instabile Funkverbindungen.",
|
||||
},
|
||||
];
|
||||
|
||||
export const sintomasRapidos = [
|
||||
{ id: "bootloop", rotulo: "🔄 Boot-Schleife (Crash Loop)", categoria: "todos" },
|
||||
{ id: "wifi-crash", rotulo: "📶 Absturz bei Wi-Fi-/BLE-Aktivierung", categoria: "alimentacao" },
|
||||
{ id: "upload-fail", rotulo: "🔌 Firmware-Upload fehlgeschlagen (Flash-Fehler)", categoria: "boot-flash" },
|
||||
{ id: "random-freeze", rotulo: "⏱️ Friert nach Minuten oder Stunden ein", categoria: "memoria" },
|
||||
{ id: "null-pointer", rotulo: "💥 Guru Meditation (CPU-Absturz)", categoria: "cpu-panics" },
|
||||
{ id: "wdt-reset", rotulo: "🐕 Watchdog ausgelöst (TWDT-Reset)", categoria: "freertos" },
|
||||
{ id: "tls-fail", rotulo: "🔒 HTTPS-/SSL-Verbindung schlägt fehl", categoria: "conectividade" },
|
||||
];
|
||||
|
||||
export const errosCatalogo = [
|
||||
{
|
||||
id: "brownout-reset",
|
||||
titulo: "Reset durch Brownout-Detektor (Spannungseinbruch)",
|
||||
categoria: "alimentacao",
|
||||
sintomas: ["bootloop", "wifi-crash"],
|
||||
gravidade: "Hoch",
|
||||
logSerial: "Brownout detector was triggered\n\nrst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)",
|
||||
resumo: "Die ESP32-Versorgungsspannung fiel unter die sichere Betriebsgrenze (ca. 2.8V ~ 2.43V).",
|
||||
causaRaiz:
|
||||
"Bei der Initialisierung von Wi-Fi- oder BLE-Funkmodulen zieht der Leistungsverstärker (PA) kurzzeitige Stromspitzen von über 500 mA in weniger als einer Millisekunde. Können Stromquelle, lange/dünne USB-Kabel, Steckbrettschienen oder der LDO-Regler diesen Spitzenstrom nicht niederohmig liefern, bricht die 3.3V-Spannung kurzzeitig ein. Dies löst den internen Brownout-Komparator aus, um Flash-Korruption zu verhindern.",
|
||||
gambiarra: {
|
||||
titulo: "Brownout-Detektor per Software deaktivieren",
|
||||
descricao: "Aufruf von WRITE_PERI_REG(RTC_CNTL_BROWN_OUT_REG, 0) zur Fehlerunterdrückung im Code.",
|
||||
consequencia: "Extrem gefährlich: Der ESP32 führt Befehle bei Unterspannung weiter aus, was zur Korruption des SPI-Flash-Speichers, Blockaden von Peripherieregistern und unvorhersehbaren Feldausfällen führt.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Korrekte Hardware-Dimensionierung und Entkopplungskondensatoren",
|
||||
passos: [
|
||||
"Schalten Sie einen 10-µF- bis 100-µF-Low-ESR-Tantal- oder Keramikkondensator parallel zu einem 100-nF-Keramikkondensator so nah wie möglich an die 3V3- und GND-Pins des ESP32.",
|
||||
"Verwenden Sie LDO-Regler mit mindestens 600 mA bis 1 A Spitzenstrom und hervorragendem Einschwingverhalten (z. B. AP2112K, ME6211, TPS73733). Vermeiden Sie minderwertige AMS1117-Klone.",
|
||||
"Vermeiden Sie es, den ESP32 bei voller Wi-Fi-Sendeleistung über lange Steckbrettleitungen mit dünnen Jumper-Kabeln zu versorgen.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Do NOT disable the Brownout detector! If you need to reduce current peaks in bench testing:
|
||||
#include <WiFi.h>
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
|
||||
// Optional: Slightly reducing maximum Wi-Fi TX power from 20dBm to 17dBm cuts current spikes by ~20%
|
||||
WiFi.setTxPower(WIFI_POWER_17dBm);
|
||||
WiFi.begin("SSID", "PASSWORD");
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF configuration:
|
||||
#include "esp_wifi.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void app_main(void) {
|
||||
// In menuconfig: Component config -> ESP32-specific -> Hardware Brownout Reset (Keep ENABLED)
|
||||
// To mitigate transient peaks in power-constrained designs:
|
||||
esp_wifi_set_max_tx_power(68); // 68 = 17dBm (units of 0.25dBm)
|
||||
}`,
|
||||
codigoMicroPython: `# Safe Wi-Fi connection in MicroPython with supply stabilization:
|
||||
import network
|
||||
import time
|
||||
|
||||
wlan = network.WLAN(network.STA_IF)
|
||||
wlan.active(True)
|
||||
|
||||
# Wait for supply rails to settle before turning on transmitter
|
||||
time.sleep_ms(200)
|
||||
wlan.connect("SSID", "PASSWORD")
|
||||
|
||||
attempts = 0
|
||||
while not wlan.isconnected() and attempts < 30:
|
||||
time.sleep_ms(200)
|
||||
attempts += 1
|
||||
|
||||
if wlan.isconnected():
|
||||
print("Wi-Fi Connected! IP:", wlan.ifconfig()[0])
|
||||
else:
|
||||
print("[ERROR] Failed to connect Wi-Fi")`,
|
||||
dicaPro: "Verlegen Sie bei eigenen Leiterplatten eine durchgehende Massefläche direkt unter dem Modul und führen Sie 3.3V-Leiterbahnen mit mindestens 0.5 mm bis 1 mm Breite aus, um ohmsche Spannungsabfälle bei HF-Sendeimpulsen zu verhindern.",
|
||||
},
|
||||
{
|
||||
id: "strapping-pins",
|
||||
titulo: "Konflikt an den Strapping-Pins beim Booten",
|
||||
categoria: "alimentacao",
|
||||
sintomas: ["bootloop", "upload-fail"],
|
||||
gravidade: "Kritisch",
|
||||
logSerial: "rst:0x1 (POWERON_RESET),boot:0x12 (SPI_FAST_FLASH_BOOT)\nflash read err, 1000\nwaiting for download",
|
||||
resumo: "The ESP32 fails to boot firmware from Flash or enters download mode unintentionally because a strapping pin was pulled to an incorrect logic level during reset.",
|
||||
causaRaiz:
|
||||
"The instant EN/CHIP_PU rises (Power-On Reset), the CPU latches the electrical logic level on specific strapping pins to configure Flash voltage (1.8V vs 3.3V), boot mode (UART Download vs SPI Flash Boot), and clock output. Connecting external sensors, relays, or LEDs with pull-up/pull-down resistors to these pins forces invalid strapping states, halting the bootloader.",
|
||||
gambiarra: {
|
||||
titulo: "Adding delays in code or manually disconnecting cables at each boot",
|
||||
descricao: "Attempting to fix the problem in setup() or manually unplugging wires before every reset.",
|
||||
consequencia: "Useless: Strapping pins are sampled by silicon hardware before the CPU executes a single line of application code or the second-stage bootloader.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Safe GPIO allocation and reset isolation",
|
||||
passos: [
|
||||
"ESP32 (Classic): Avoid using GPIO 0 (Boot mode), GPIO 2 (must be LOW or floating during flashing), GPIO 12 (selects Flash voltage: pulling HIGH at reset burns/locks 3.3V flash), and GPIO 15 (suppresses boot log output if LOW).",
|
||||
"ESP32-C3: Avoid pulling GPIO 8 LOW or GPIO 9 LOW during reset.",
|
||||
"ESP32-S3: Watch GPIO 0, GPIO 45 (VDD_SPI voltage level), and GPIO 46.",
|
||||
"If these pins must interface with peripherals, use transistors or digital bus switches to isolate them until the EN pin has completely risen and stabilized.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// SAFE PINOUT RECOMMENDATIONS (ESP32 Classic):
|
||||
// Preferred pins for I2C / SPI / General Sensors:
|
||||
// SDA: GPIO 21 | SCL: GPIO 22
|
||||
// SPI: MOSI 23 | MISO 19 | SCK 18 | CS 5
|
||||
|
||||
// WARNING: GPIOs 34, 35, 36 (VP), 39 (VN) are INPUT-ONLY (no internal pull-up/pull-down).
|
||||
// Never configure them as pinMode(..., OUTPUT); nor for I2C/SPI buses.`,
|
||||
codigoEspIdf: `// In ESP-IDF, lock Flash voltage via eFuse to free GPIO 12 (WARNING: IRREVERSIBLE):
|
||||
// If using classic ESP32 and GPIO 12 is needed for peripherals:
|
||||
// espefuse.py --port /dev/ttyUSB0 set_flash_voltage 3.3V
|
||||
// This permanently disables hardware strapping sampling on GPIO 12.`,
|
||||
codigoMicroPython: `# Safe pin setup in MicroPython:
|
||||
from machine import Pin
|
||||
|
||||
# Safe pins for outputs and buttons with internal pull-up:
|
||||
led = Pin(2, Pin.OUT) # GPIO 2
|
||||
button = Pin(4, Pin.IN, Pin.PULL_UP) # GPIO 4 (safe)
|
||||
|
||||
# Pins 34, 35, 36, 39 are INPUT-ONLY with no internal pull-ups:
|
||||
analog_sensor = Pin(36, Pin.IN) # Correct (requires external pull-up if used as a digital input)`,
|
||||
dicaPro: "Remember: Input-only pins (GPI 34 to 39 on classic ESP32) have neither internal silicon pull-up/pull-down circuits nor output drivers. External resistors are mandatory.",
|
||||
},
|
||||
{
|
||||
id: "guru-load-prohibited",
|
||||
titulo: "Guru Meditation: LoadProhibited / StoreProhibited (Nullzeigerzugriff)",
|
||||
categoria: "cpu-panics",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Kritisch",
|
||||
logSerial: "Guru Meditation Error: Core 0 panic'ed (LoadProhibited). Exception was unhandled.\nCore 0 register dump:\nPC : 0x400d14bc PS : 0x00060830 A0 : 0x800d1512 A1 : 0x3ffb1f20 \nEXCVADDR: 0x00000000",
|
||||
resumo: "The CPU attempted to read (Load) or write (Store) to an inaccessible or invalid memory address, typically null pointer 0x00000000.",
|
||||
causaRaiz:
|
||||
"This is the classic null pointer dereference or dangling pointer access. The EXCVADDR register shows the faulty memory address: if EXCVADDR is 0x00000000 or near zero (e.g. 0x00000008, a struct offset), code attempted to access members of an uninitialized object or a failed malloc allocation.",
|
||||
gambiarra: {
|
||||
titulo: "Inserting random delays or rebooting in loop without fixing root cause",
|
||||
descricao: "Assuming it is a timing glitch and scattering delay() calls or masking reboots.",
|
||||
consequencia: "The firmware continues crashing intermittently in production whenever the null pointer condition recurs.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Defensive validation and Backtrace decoding",
|
||||
passos: [
|
||||
"Always verify that pointers returned by allocation or lookup functions (malloc, WiFi.client(), JSON parsing, xQueueReceive) are non-NULL before accessing their fields.",
|
||||
"Install 'Espressif Exception Decoder' in your IDE (Arduino IDE / PlatformIO) or run 'xtensa-esp32-elf-addr2line -pfia -e firmware.elf 0x400d14bc' to pinpoint the exact line of code that triggered the crash.",
|
||||
"In ESP-IDF, run 'idf.py monitor' which decodes the call backtrace in real-time.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// DEFENSIVE CODING:
|
||||
struct SensorData {
|
||||
float temperature;
|
||||
float humidity;
|
||||
};
|
||||
|
||||
void processSensor(SensorData* sensor) {
|
||||
// Mandatory check against LoadProhibited:
|
||||
if (sensor == nullptr) {
|
||||
Serial.println("[ERROR] Null sensor pointer!");
|
||||
return;
|
||||
}
|
||||
|
||||
Serial.printf("Temp: %.1f C\\n", sensor->temperature);
|
||||
}`,
|
||||
codigoEspIdf: `// In ESP-IDF, use ESP_RETURN_ON_FALSE or explicit assertions:
|
||||
#include "esp_log.h"
|
||||
#include "esp_check.h"
|
||||
|
||||
static const char* TAG = "SENSOR";
|
||||
|
||||
esp_err_t read_data(char* buffer, size_t max_len) {
|
||||
ESP_RETURN_ON_FALSE(buffer != NULL, ESP_ERR_INVALID_ARG, TAG, "Null buffer supplied!");
|
||||
// Safe operation...
|
||||
return ESP_OK;
|
||||
}`,
|
||||
codigoMicroPython: `# Preventing NoneType exceptions in MicroPython:
|
||||
import json
|
||||
|
||||
def process_sensor(raw_data):
|
||||
if raw_data is None:
|
||||
print("[ERROR] Null data received!")
|
||||
return None
|
||||
|
||||
try:
|
||||
obj = json.loads(raw_data)
|
||||
# Safe lookup with fallback default
|
||||
temperature = obj.get("temp", 0.0)
|
||||
return temperature
|
||||
except (ValueError, AttributeError) as e:
|
||||
print("Error processing payload:", e)
|
||||
return None`,
|
||||
dicaPro: "If EXCVADDR is 0x3fxxxxxx or 0x40xxxxxx but the code crashes, you likely experienced a buffer overflow that corrupted adjacent pointers in RAM.",
|
||||
},
|
||||
{
|
||||
id: "guru-iram-cache",
|
||||
titulo: "Cache-Fehler und InstructionFetchError in Interrupt-Serviceroutinen (ISRs)",
|
||||
categoria: "cpu-panics",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Hoch",
|
||||
logSerial: "Guru Meditation Error: Core 0 panic'ed (Cache disabled but cached memory region accessed)\nGuru Meditation Error: Core 0 panic'ed (InstructionFetchError)",
|
||||
resumo: "An interrupt service routine (ISR) tried to execute code or read constants from SPI Flash while the Flash memory controller was disabled for a write or erase operation.",
|
||||
causaRaiz:
|
||||
"By default, ESP32 application code resides in external SPI Flash and is fetched into CPU execution pipeline via internal Instruction Cache. When the ESP32 writes to Flash (such as NVS commits, LittleFS, SPIFFS, or OTA updates), the hardware cache is momentarily disabled. If an ISR fires during this window and its function body resides in Flash, the CPU cannot fetch the instruction and enters an immediate panic.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling all interrupts before writing to Flash",
|
||||
descricao: "Wrapping Flash file operations in indiscriminate noInterrupts() blocks.",
|
||||
consequencia: "Causes dropped sensor pulses, jitter on system timers, and potential watchdog resets.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Allocating ISRs and callback constants in IRAM / DRAM",
|
||||
passos: [
|
||||
"Decorate EVERY hardware interrupt handler with the IRAM_ATTR attribute (e.g., void IRAM_ATTR isrHandler()).",
|
||||
"Ensure any variables or constant strings accessed inside the ISR reside in DRAM (avoid inline string literals in ISR without DRAM_ATTR in ESP-IDF).",
|
||||
"Never call heavy library functions (such as Serial.print or floating-point formatting) inside an interrupt handler.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// ISR properly placed in internal IRAM:
|
||||
volatile uint32_t pulseCount = 0;
|
||||
|
||||
void IRAM_ATTR handleGpioInterrupt() {
|
||||
pulseCount++;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
pinMode(4, INPUT_PULLUP);
|
||||
attachInterrupt(digitalPinToInterrupt(4), handleGpioInterrupt, FALLING);
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF:
|
||||
#include "esp_attr.h"
|
||||
#include "driver/gpio.h"
|
||||
|
||||
static volatile uint32_t pulses = 0;
|
||||
|
||||
// Placed explicitly in IRAM:
|
||||
static void IRAM_ATTR gpio_isr_handler(void* arg) {
|
||||
pulses++;
|
||||
}
|
||||
|
||||
void app_main(void) {
|
||||
gpio_install_isr_service(ESP_INTR_FLAG_IRAM);
|
||||
gpio_isr_handler_add(GPIO_NUM_4, gpio_isr_handler, NULL);
|
||||
}`,
|
||||
codigoMicroPython: `# Safe interrupt handling (ISR) in MicroPython:
|
||||
import micropython
|
||||
from machine import Pin
|
||||
|
||||
# Pre-allocate emergency exception buffer for ISR debugging:
|
||||
micropython.alloc_emergency_exception_buf(100)
|
||||
|
||||
pulse_count = 0
|
||||
|
||||
# Interrupt callback: do NOT allocate memory (no new strings, no new floats)
|
||||
def handle_pulse(pin):
|
||||
global pulse_count
|
||||
pulse_count += 1
|
||||
|
||||
sensor = Pin(4, Pin.IN, Pin.PULL_UP)
|
||||
sensor.irq(trigger=Pin.IRQ_FALLING, handler=handle_pulse)`,
|
||||
dicaPro: "When passing ESP_INTR_FLAG_IRAM in ESP-IDF, every function invoked by the ISR (including FreeRTOS API calls) MUST support IRAM (e.g. xQueueSendFromISR).",
|
||||
},
|
||||
{
|
||||
id: "freertos-twdt",
|
||||
titulo: "Timeout des Task Watchdog Timers (TWDT-Timeout auf Core 0 oder Core 1)",
|
||||
categoria: "freertos",
|
||||
sintomas: ["bootloop", "wdt-reset"],
|
||||
gravidade: "Kritisch",
|
||||
logSerial: "E (10532) task_wdt: Task watchdog got triggered. The following tasks/users did not reset the watchdog in time:\nE (10532) task_wdt: - IDLE0 (CPU 0)\nTask watchdog got triggered. System will be reset.",
|
||||
resumo: "A high-priority task entered a busy loop without yielding CPU time, preventing the FreeRTOS IDLE task from feeding the watchdog.",
|
||||
causaRaiz:
|
||||
"FreeRTOS runs an essential priority-0 task called IDLE on each CPU core. The Task Watchdog monitors whether the IDLE task executes periodically (by default, within 5 seconds). If a task with priority >= 1 runs a tight while(1) loop without blocking calls (vTaskDelay, queue reads, semaphores), it starves the IDLE task, triggering an emergency hardware reset.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling Task Watchdog in menuconfig or increasing timeout to 60s",
|
||||
descricao: "Turning off the TWDT to prevent the board from rebooting.",
|
||||
consequencia: "If the firmware encounters an unexpected deadlock or infinite loop, the device freezes permanently and requires manual power cycling.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Event-driven architecture and periodic CPU yield",
|
||||
passos: [
|
||||
"Never write empty busy-wait loops like while(!condition); in FreeRTOS tasks.",
|
||||
"Always insert vTaskDelay(pdMS_TO_TICKS(10)) or wait for events with xQueueReceive(), ulTaskNotifyTake(), or xSemaphoreTake() with a timeout.",
|
||||
"If heavy compute tasks must run continuously, feed the watchdog explicitly via esp_task_wdt_reset().",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// CORRECT ARDUINO FREERTOS PATTERN:
|
||||
void myTask(void *pvParameters) {
|
||||
for (;;) {
|
||||
float sensorValue = analogRead(36);
|
||||
|
||||
// YIELD CPU to FreeRTOS scheduler and IDLE task:
|
||||
vTaskDelay(pdMS_TO_TICKS(100)); // Non-blocking 100ms pause
|
||||
}
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF Task Watchdog pattern:
|
||||
#include "esp_task_wdt.h"
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
|
||||
void compute_task(void *pvParameters) {
|
||||
esp_task_wdt_add(NULL);
|
||||
|
||||
while (1) {
|
||||
// Compute...
|
||||
|
||||
// Feed watchdog during long processing cycles:
|
||||
esp_task_wdt_reset();
|
||||
vTaskDelay(pdMS_TO_TICKS(50));
|
||||
}
|
||||
}`,
|
||||
codigoMicroPython: `# Watchdog and non-blocking tasks with uasyncio in MicroPython:
|
||||
from machine import WDT
|
||||
import uasyncio as asyncio
|
||||
|
||||
wdt = WDT(timeout=5000)
|
||||
|
||||
async def sensor_task():
|
||||
while True:
|
||||
wdt.feed()
|
||||
await asyncio.sleep_ms(100)
|
||||
|
||||
async def main():
|
||||
asyncio.create_task(sensor_task())
|
||||
while True:
|
||||
await asyncio.sleep(1)
|
||||
|
||||
asyncio.run(main())`,
|
||||
dicaPro: "In Arduino, delay(ms) internally calls vTaskDelay. However, delayMicroseconds() or raw compute loops do not yield CPU time and will trigger the TWDT if held for more than a few seconds.",
|
||||
},
|
||||
{
|
||||
id: "freertos-stack-overflow",
|
||||
titulo: "Task-Stack-Überlauf in FreeRTOS (Stack Overflow)",
|
||||
categoria: "freertos",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Kritisch",
|
||||
logSerial: "Guru Meditation Error: Core 1 panic'ed (Unhandled debug exception).\nDebug exception reason: Stack canary watchpoint triggered (my_task)",
|
||||
resumo: "The task consumed more stack memory than allocated upon creation, corrupting the RTOS protection canary.",
|
||||
causaRaiz:
|
||||
"Each FreeRTOS task is allocated a fixed contiguous memory block for local variables, function arguments, and return addresses. Declaring large arrays on the stack (e.g., char buffer[2048];), heavy JSON documents, or deep call recursions within a default 2048-byte stack overflows the boundary and overwrites adjacent memory.",
|
||||
gambiarra: {
|
||||
titulo: "Assigning 64KB stack blindly to every task",
|
||||
descricao: "Inflating task stack sizes indiscriminately to avoid overflow crashes.",
|
||||
consequencia: "The ~320 KB usable SRAM of the ESP32 is quickly exhausted, leading to out-of-memory errors in Wi-Fi and TLS allocations.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Deliberate stack sizing and HighWaterMark monitoring",
|
||||
passos: [
|
||||
"Measure actual stack consumption using uxTaskGetStackHighWaterMark(). It returns the minimum free stack remaining since task creation.",
|
||||
"Move large buffers from the stack to the heap (using malloc/free) or declare them static outside function scope if reused.",
|
||||
"Tasks running secure TLS/HTTPS or MQTT over SSL connections require at least 6 KB to 8 KB of stack due to MbedTLS cryptographic frame complexity.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// MONITORING TASK STACK IN ARDUINO:
|
||||
void sensorTask(void *pvParameters) {
|
||||
for (;;) {
|
||||
// Task workload...
|
||||
|
||||
UBaseType_t freeStack = uxTaskGetStackHighWaterMark(NULL);
|
||||
Serial.printf("[STACK] Remaining free stack: %d bytes\\n", (int)freeStack);
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(5000));
|
||||
}
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
// Allocate 4096 bytes (4KB) with safety margin:
|
||||
xTaskCreatePinnedToCore(sensorTask, "sensorTask", 4096, NULL, 1, NULL, 1);
|
||||
}`,
|
||||
codigoEspIdf: `// Enable double stack checking in menuconfig:
|
||||
// Component config -> FreeRTOS -> Set a end of stack check -> Option 2 (Check by Stack Canary)
|
||||
// This catches overflows BEFORE memory structures become silently corrupted at runtime.`,
|
||||
codigoMicroPython: `# Memory and stack inspection in MicroPython:
|
||||
import gc
|
||||
import micropython
|
||||
|
||||
micropython.mem_info()
|
||||
|
||||
gc.collect()
|
||||
print("Free Heap:", gc.mem_free(), "bytes")
|
||||
print("Allocated Heap:", gc.mem_alloc(), "bytes")`,
|
||||
dicaPro: "If a function only processes an HTTP or JSON payload occasionally, allocate the buffer dynamically on the heap during the transaction and free it immediately, rather than permanently inflating task stack.",
|
||||
},
|
||||
{
|
||||
id: "memoria-fragmentacao-heap",
|
||||
titulo: "Heap-Fragmentierung und Speicherlecks (Memory Leaks)",
|
||||
categoria: "memoria",
|
||||
sintomas: ["random-freeze", "tls-fail"],
|
||||
gravidade: "Hoch",
|
||||
logSerial: "E (45892) mbedtls: mbedtls_ssl_setup returned -0x7f00\nE (45892) esp-tls: create_ssl_handle failed\nE (45893) HTTP_CLIENT: Connection failed, out of memory",
|
||||
resumo: "The ESP32 fails to allocate memory despite reporting a seemingly adequate total free heap size.",
|
||||
causaRaiz:
|
||||
"Heap memory becomes fragmented after thousands of allocations and deallocations of varying sizes over time (common when repeatedly concatenating Arduino String objects in loops). Free heap becomes split into tiny isolated chunks. When Wi-Fi or TLS libraries request a single contiguous 40 KB block for an SSL certificate buffer, malloc fails even if 100 KB total free memory exists across disconnected fragments.",
|
||||
gambiarra: {
|
||||
titulo: "Scheduling periodic ESP.restart() every few hours",
|
||||
descricao: "Triggering a daily reboot to reset fragmented memory.",
|
||||
consequencia: "Merely conceals the bug: during traffic spikes the device crashes well ahead of the scheduled reboot.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Eliminate dynamic strings and use pre-allocated static buffers",
|
||||
passos: [
|
||||
"In Arduino, avoid the String class. Use standard C-style character arrays (char buffer[128];) with safe snprintf().",
|
||||
"Monitor fragmentation by comparing total free memory (heap_caps_get_free_size) with the largest contiguous free block (heap_caps_get_largest_free_block).",
|
||||
"In complex ESP-IDF firmware, enable Heap Memory Tracing (CONFIG_HEAP_TRACING) to locate missing free() calls.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// COMPARISON:
|
||||
// ❌ AVOID (Causes severe heap fragmentation):
|
||||
// String json = "{\\"temp\\":";
|
||||
// json += String(temperature) + "}";
|
||||
|
||||
// ✅ RECOMMENDED (Zero heap allocations):
|
||||
char payload[64];
|
||||
snprintf(payload, sizeof(payload), "{\\"temp\\":%.2f,\\"hum\\":%.2f}", temperature, humidity);
|
||||
|
||||
// Health check:
|
||||
Serial.printf("Free Heap: %u | Largest Block: %u\\n",
|
||||
ESP.getFreeHeap(),
|
||||
ESP.getMaxAllocHeap());`,
|
||||
codigoEspIdf: `// Heap monitoring in ESP-IDF:
|
||||
#include "esp_heap_caps.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void inspect_memory(void) {
|
||||
size_t total_free = heap_caps_get_free_size(MALLOC_CAP_8BIT);
|
||||
size_t largest_block = heap_caps_get_largest_free_block(MALLOC_CAP_8BIT);
|
||||
|
||||
ESP_LOGI("HEAP", "Total free: %d bytes | Largest contiguous: %d bytes", total_free, largest_block);
|
||||
}`,
|
||||
codigoMicroPython: `# Preventing heap fragmentation in MicroPython:
|
||||
import gc
|
||||
|
||||
gc.enable()
|
||||
|
||||
# Pre-allocate reusable bytearrays instead of instantiating new strings:
|
||||
rx_buffer = bytearray(256)
|
||||
|
||||
def read_sensor_zero_alloc(stream):
|
||||
bytes_read = stream.readinto(rx_buffer)
|
||||
return rx_buffer[:bytes_read]
|
||||
|
||||
gc.collect()
|
||||
print(f"Free Heap: {gc.mem_free()} B | Allocated: {gc.mem_alloc()} B")`,
|
||||
dicaPro: "If the largest contiguous free block drops below 35 KB to 40 KB, modern HTTPS/TLS connections will fail during the cryptographic handshake.",
|
||||
},
|
||||
{
|
||||
id: "memoria-dma-psram",
|
||||
titulo: "Fehler bei DMA-Allokationen im externen Speicher (PSRAM)",
|
||||
categoria: "memoria",
|
||||
sintomas: ["bootloop", "random-freeze"],
|
||||
gravidade: "Hoch",
|
||||
logSerial: "E (1204) spi_master: spi_bus_initialize: DMA channel not compatible with external RAM buffer\nESP_ERROR_CHECK failed: esp_err_t 0x102 (ESP_ERR_INVALID_ARG)",
|
||||
resumo: "Firmware attempted to pass a buffer allocated in external PSRAM to a DMA-driven peripheral (SPI, I2S, LCD, SDMMC) that can only access internal SRAM.",
|
||||
causaRaiz:
|
||||
"On ESP32 family chips (especially classic ESP32, ESP32-S2, and ESP32-S3 standard bus), the peripheral DMA engine has no direct physical access to external SPI/QSPI PSRAM. DMA transfers strictly require source and destination buffers to reside in internal SRAM.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling DMA on peripherals",
|
||||
descricao: "Switching SPI/I2S buses to polled CPU transfer mode without DMA.",
|
||||
consequencia: "Throughput plummets and the CPU core stays 100% occupied during display updates or audio streaming.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Explicit allocation with MALLOC_CAP_DMA and MALLOC_CAP_INTERNAL",
|
||||
passos: [
|
||||
"Always allocate DMA buffers using heap_caps_malloc(size, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL).",
|
||||
"Keep heavy non-DMA assets (decoded images, machine learning weights, inactive audio) in PSRAM, copying small frames to internal DMA buffers on demand (ping-pong buffering).",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Allocating DMA buffers in Arduino ESP32:
|
||||
#include <esp_heap_caps.h>
|
||||
|
||||
uint8_t* dmaBuffer = nullptr;
|
||||
|
||||
void setup() {
|
||||
size_t size = 4096;
|
||||
// Guarantees buffer is allocated in DMA-accessible internal SRAM:
|
||||
dmaBuffer = (uint8_t*) heap_caps_malloc(size, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL);
|
||||
|
||||
if (dmaBuffer == nullptr) {
|
||||
Serial.println("[ERROR] Failed to allocate internal DMA buffer!");
|
||||
}
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF:
|
||||
#include "esp_heap_caps.h"
|
||||
|
||||
uint8_t* allocate_spi_buffer(size_t len) {
|
||||
return (uint8_t*) heap_caps_aligned_alloc(4, len, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL);
|
||||
}`,
|
||||
codigoMicroPython: `# In MicroPython, inspect available PSRAM:
|
||||
import gc
|
||||
import esp32
|
||||
|
||||
print("Total accessible memory in MicroPython:", gc.mem_free() + gc.mem_alloc(), "bytes")
|
||||
buffer_spi = bytearray(1024)`,
|
||||
dicaPro: "On the ESP32-P4, the advanced AXI bus matrix enables DMA into specific external memory regions, but for the ESP32/S2/S3/C3 lines, internal SRAM placement is mandatory.",
|
||||
},
|
||||
{
|
||||
id: "boot-failed-connect",
|
||||
titulo: "Serieller Verbindungsfehler beim Flashen (Timed out waiting for packet header)",
|
||||
categoria: "boot-flash",
|
||||
sintomas: ["upload-fail"],
|
||||
gravidade: "Mittel",
|
||||
logSerial: "A fatal error occurred: Failed to connect to ESP32: Timed out waiting for packet header\nesptool.py v4.6\nConnecting...................",
|
||||
resumo: "The programming tool (esptool / Arduino IDE / PlatformIO) was unable to place the microcontroller into UART bootloader mode.",
|
||||
causaRaiz:
|
||||
"To initiate flashing, the USB-UART bridge (CH340, CP2102, FTDI) toggles DTR and RTS lines to pull GPIO 0 LOW while pulsing EN/RST LOW then HIGH. On many third-party development boards, the RC timing circuit on EN lacks adequate capacitance to hold the reset state during the DTR transition.",
|
||||
gambiarra: {
|
||||
titulo: "Holding the physical BOOT button with your finger at every upload",
|
||||
descricao: "Pressing BOOT/GPIO 0 manually each time the compiler finishes generating binaries.",
|
||||
consequencia: "Inconvenient during rapid prototyping and impossible on sealed boards enclosed in enclosures.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Add a 10 µF capacitor on EN or verify USB data cable",
|
||||
passos: [
|
||||
"Solder a 10 µF (or 1 µF to 10 µF) ceramic or electrolytic capacitor between the EN (RST) and GND pins. This stabilizes the automatic reset ramp.",
|
||||
"Ensure the USB cable has active data lines (D+ and D-). Many cheap charging cables contain only power wires.",
|
||||
"On Linux, confirm your user belongs to the 'dialout' group (sudo usermod -a -G dialout $USER) and that the 'brltty' service is not holding the serial port.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Command-line verification with esptool:
|
||||
// python -m esptool --port /dev/ttyUSB0 chip_id
|
||||
// If it prints the MAC and chip model, physical communication is working.`,
|
||||
codigoEspIdf: `// In ESP-IDF:
|
||||
// idf.py -p /dev/ttyUSB0 -b 460800 flash
|
||||
// If flashing fails at high speeds, reduce baud rate:
|
||||
// idf.py -p /dev/ttyUSB0 -b 115200 flash`,
|
||||
codigoMicroPython: `# Flashing official MicroPython firmware via terminal:
|
||||
# 1. Erase flash:
|
||||
# esptool.py --port /dev/ttyUSB0 erase_flash
|
||||
|
||||
# 2. Flash binary at safe baud rate:
|
||||
# esptool.py --chip esp32 --port /dev/ttyUSB0 --baud 460800 write_flash -z 0x1000 ESP32_GENERIC-*.bin`,
|
||||
dicaPro: "When using ESP32-S3 or C3 modules with native USB (Direct USB-JTAG), verify that your tooling is configured for the USB CDC/JTAG port rather than a legacy UART bridge.",
|
||||
},
|
||||
{
|
||||
id: "tls-sntp-clock-fail",
|
||||
titulo: "Fehlgeschlagener TLS/HTTPS-Handshake wegen nicht synchronisierter Uhrzeit (Jahr 1970)",
|
||||
categoria: "conectividade",
|
||||
sintomas: ["tls-fail", "random-freeze"],
|
||||
gravidade: "Hoch",
|
||||
logSerial: "E (15420) esp-tls-mbedtls: mbedtls_ssl_handshake returned -0x2700\nE (15420) esp-tls: Failed to verify peer certificate!\nE (15421) esp-tls: Verification info: The certificate is not yet valid (or has expired)",
|
||||
resumo: "Secure HTTPS, AWS IoT, MQTT over TLS, or Web API requests fail because the internal ESP32 RTC defaults to 01/01/1970.",
|
||||
causaRaiz:
|
||||
"Digital certificates (X.509 SSL/TLS) include strict validity windows (Not Before and Not After). Because typical ESP32 boards lack an external RTC battery, the internal clock resets to the Unix epoch (1970) on every cold boot. When MbedTLS checks the server certificate date, it deems it 'not yet valid' (since current dates are decades ahead of 1970), aborting the handshake with error -0x2700 (MBEDTLS_ERR_X509_CERT_VERIFY_FAILED).",
|
||||
gambiarra: {
|
||||
titulo: "Disabling SSL certificate verification (Insecure / No-Verify)",
|
||||
descricao: "Using client.setInsecure() in Arduino or turning off CA validation in ESP-IDF.",
|
||||
consequencia: "Creates a critical security vulnerability: the device is completely exposed to Man-in-the-Middle (MitM) attacks, allowing credentials and firmware to be intercepted.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Mandatory SNTP time synchronization prior to opening TLS sockets",
|
||||
passos: [
|
||||
"Immediately after acquiring an IP address, start the SNTP client querying reliable NTP servers (e.g. pool.ntp.org, time.google.com).",
|
||||
"Block outbound HTTPS/MQTT connections until system time is confirmed synchronized.",
|
||||
"Set the correct timezone string so log timestamps match local operational time.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// SNTP SYNCHRONIZATION BEFORE HTTPS IN ARDUINO:
|
||||
#include <WiFi.h>
|
||||
#include <time.h>
|
||||
|
||||
void syncClock() {
|
||||
configTime(0, 0, "pool.ntp.org", "time.google.com");
|
||||
|
||||
Serial.print("Waiting for NTP time sync");
|
||||
time_t now = time(nullptr);
|
||||
// Year 2024 in Unix timestamp is > 1700000000. If smaller, clock is still in 1970:
|
||||
while (now < 1700000000) {
|
||||
delay(500);
|
||||
Serial.print(".");
|
||||
now = time(nullptr);
|
||||
}
|
||||
Serial.println("\\n[OK] Clock synchronized! TLS handshakes enabled.");
|
||||
}`,
|
||||
codigoEspIdf: `// SNTP in ESP-IDF:
|
||||
#include "esp_sntp.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void initialize_sntp(void) {
|
||||
ESP_LOGI("SNTP", "Starting SNTP client...");
|
||||
esp_sntp_setoperatingmode(SNTP_OPMODE_POLL);
|
||||
esp_sntp_setservername(0, "pool.ntp.org");
|
||||
esp_sntp_init();
|
||||
}`,
|
||||
codigoMicroPython: `# SNTP synchronization and HTTPS requests in MicroPython:
|
||||
import ntptime
|
||||
import time
|
||||
import urequests
|
||||
|
||||
def sync_and_request():
|
||||
try:
|
||||
print("Synchronizing clock via NTP...")
|
||||
ntptime.host = "pool.ntp.org"
|
||||
ntptime.settime()
|
||||
print("UTC Time synchronized:", time.localtime())
|
||||
|
||||
response = urequests.get("https://api.github.com")
|
||||
print("HTTPS Response:", response.status_code)
|
||||
response.close()
|
||||
except Exception as e:
|
||||
print("[TLS/NTP ERROR]:", e)`,
|
||||
dicaPro: "If operating in isolated local networks without internet access, configure a local NTP server on the gateway router or add a physical DS3231 RTC module over I2C.",
|
||||
},
|
||||
];
|
||||
|
||||
export const regrasDecodificadorLog = [
|
||||
{
|
||||
padrao: /Brownout detector was triggered/i,
|
||||
titulo: "Brownout-Detektor (Kritische Unterspannung)",
|
||||
tipo: "Stromversorgung / Hardware",
|
||||
explicacao:
|
||||
"Die Spannung an der 3.3V-Schiene fiel unter die sichere Betriebsgrenze (typischerweise verursacht durch Wi-Fi/BLE-Sendeimpulse oder ein zu schwaches Netzteil).",
|
||||
acaoRecomendada:
|
||||
"Fügen Sie einen 10-µF- bis 100-µF-Low-ESR-Kondensator an der VCC-Leitung hinzu, prüfen Sie die Stromkabel und stellen Sie sicher, dass der LDO-Regler ausreichend Strom liefert.",
|
||||
},
|
||||
{
|
||||
padrao: /LoadProhibited|StoreProhibited/i,
|
||||
titulo: "Guru Meditation: Load/StoreProhibited (Null- oder ungültiger Zeiger)",
|
||||
tipo: "CPU-Panic / Exception",
|
||||
explicacao:
|
||||
"Es wurde versucht, auf eine ungültige Speicheradresse zuzugreifen (meist Dereferenzierung eines Nullzeigers oder Feldgrenzenüberschreitung).",
|
||||
acaoRecomendada:
|
||||
"Dekodieren Sie den Backtrace mit Exception Decoder oder 'addr2line', um die genaue Zeile zu finden. Fügen Sie defensive Prüfungen 'if (ptr != NULL)' ein.",
|
||||
},
|
||||
{
|
||||
padrao: /Cache disabled but cached memory region accessed|InstructionFetchError/i,
|
||||
titulo: "Interrupt-Cache-Fehler (ISR außerhalb des IRAM)",
|
||||
tipo: "CPU-Panic / Flash",
|
||||
explicacao:
|
||||
"Eine Interrupt-Serviceroutine (ISR) versuchte, Code aus dem externen Flash auszuführen, während der SPI-Flash-Cache für Schreib-/Löschvorgänge deaktiviert war.",
|
||||
acaoRecomendada:
|
||||
"Versehen Sie die Interrupt-Routine mit dem IRAM_ATTR-Attribut und alle in der ISR verwendeten Konstanten/Strings mit DRAM_ATTR.",
|
||||
},
|
||||
{
|
||||
padrao: /Task watchdog got triggered|TWDT/i,
|
||||
titulo: "Task-Watchdog-Timeout (Blockierte FreeRTOS-Task)",
|
||||
tipo: "FreeRTOS / Watchdog",
|
||||
explicacao:
|
||||
"Eine hochpriorisierte Task belegt die CPU dauerhaft, sodass die IDLE-Task nicht zur Ausführung kommt und den Watchdog nicht zurücksetzen kann.",
|
||||
acaoRecomendada:
|
||||
"Fügen Sie vTaskDelay(1) oder delay(1) in rechenintensive Endlosschleifen ein, oder nutzen Sie Queues und Semaphore statt aktiver Warteschleifen.",
|
||||
},
|
||||
{
|
||||
padrao: /Stack canary watchpoint got triggered|Stack overflow/i,
|
||||
titulo: "Task-Stack-Überlauf (Stack Overflow)",
|
||||
tipo: "FreeRTOS / Task-Speicher",
|
||||
explicacao:
|
||||
"Die Task hat den bei ihrer Erstellung reservierten Stack-Speicher aufgebraucht und die Sicherheitsmarkierung (Stack Canary) überschrieben.",
|
||||
acaoRecomendada:
|
||||
"Erhöhen Sie den Stack in xTaskCreate (z. B. von 2048 auf 4096 Bytes) und verlagern Sie große lokale Arrays auf den Heap.",
|
||||
},
|
||||
{
|
||||
padrao: /Timed out waiting for packet header|Failed to connect to ESP32/i,
|
||||
titulo: "Serieller Verbindungsfehler beim Flashen",
|
||||
tipo: "Bootloader / Verbindung",
|
||||
explicacao:
|
||||
"Der Computer konnte den ESP32 über die DTR/RTS-Signale der seriellen Schnittstelle nicht in den Download-Modus versetzen.",
|
||||
acaoRecomendada:
|
||||
"Schließen Sie einen 10-µF-Kondensator zwischen EN und GND an, prüfen Sie das USB-Datenkabel oder halten Sie die BOOT-Taste beim Einstecken gedrückt.",
|
||||
},
|
||||
{
|
||||
padrao: /The certificate is not yet valid|-0x2700/i,
|
||||
titulo: "TLS/HTTPS-Zertifikatsfehler (Systemzeit im Jahr 1970)",
|
||||
tipo: "Konnektivität / TLS",
|
||||
explicacao:
|
||||
"Der ESP32 versuchte, ein HTTPS/TLS-Zertifikat mit nicht synchronisierter interner Uhrzeit (Unix-Epoche 1970) zu validieren.",
|
||||
acaoRecomendada:
|
||||
"Synchronisieren Sie die Uhrzeit über SNTP (configTime in Arduino oder ntptime in MicroPython) vor dem Aufbau von TLS-Verbindungen.",
|
||||
},
|
||||
{
|
||||
padrao: /rst:0x1 \(POWERON_RESET\),boot:0x[0-9a-fA-F]+/i,
|
||||
titulo: "Power-On-Reset / Abtastung der Strapping-Pins",
|
||||
tipo: "Hardware / Boot",
|
||||
explicacao:
|
||||
"Der Mikrocontroller wurde neu gestartet und hat seine Boot-Pins abgetastet. Friert er sofort ein, liegt an einem Strapping-Pin ein falscher Pegel an.",
|
||||
acaoRecomendada:
|
||||
"Stellen Sie sicher, dass die GPIO-Strapping-Pins beim Einschalten nicht durch externe Schaltungen auf unzulässige Pegel gezwungen werden.",
|
||||
},
|
||||
];
|
||||
export const analisarLogSerial = regrasDecodificadorLog;
|
||||
export const ERROS_COMUNS = errosCatalogo;
|
||||
@@ -0,0 +1,408 @@
|
||||
/**
|
||||
* Strukturierte und umfassende Datenbank technischer Begriffe des ESP32-Glossars auf Deutsch.
|
||||
* Umfasst alle Espressif-Chipserien (ESP32, S2, S3, S31, C2, C3, C5, C6, C61, H2, H4, P4)
|
||||
* und deren Hardwarefunktionen, Peripheriegeräte, Funk-, Sicherheits- und Softwaremerkmale.
|
||||
*/
|
||||
|
||||
export const categoriasGlossario = [
|
||||
{
|
||||
"id": "processamento",
|
||||
"nome": "Verarbeitung, CPU & Silizium",
|
||||
"icone": "Cpu",
|
||||
"emoji": "🧠",
|
||||
"cor": "blue",
|
||||
"descricao": "Xtensa- und RISC-V-Architekturen, Rechenkerne, ULP-Coprocessoren, KI-Vektorbeschleuniger und Gleitkommaeinheiten.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Xtensa- vs. RISC-V-Architektur",
|
||||
"definicao": "Basisbefehlssatz des Prozessors. Die klassischen ESP32-, S2- und S3-Modelle nutzen proprietäre Tensilica-Xtensa-Kerne (LX6/LX7). Die modernen Serien C (C2, C3, C5, C6, C61), H (H2, H4) und P (P4) setzen auf die offene, modulare und effiziente 32-Bit-RISC-V-Architektur.",
|
||||
"exemplo": "Der ESP32-S3 nutzt Xtensa LX7 Dual-Core, während der ESP32-C6 einen RISC-V Single-Core und der ESP32-P4 einen RISC-V Dual-Core mit 400 MHz verwendet."
|
||||
},
|
||||
{
|
||||
"termo": "CPU-Kerne (Dual-Core vs. Single-Core)",
|
||||
"definicao": "Unabhängige zentrale Verarbeitungseinheiten. Dual-Core-Chips ermöglichen es, einen Kern (Core 0) ausschließlich für Wi-Fi-/Bluetooth-Funk und FreeRTOS-Scheduling zu reservieren, während der zweite Kern (Core 1) vollständig für Benutzeranwendungen frei bleibt.",
|
||||
"exemplo": "ESP32, ESP32-S3 und ESP32-P4 sind Dual-Core; ESP32-S2, C2, C3, C6 und H2 sind Single-Core."
|
||||
},
|
||||
{
|
||||
"termo": "Taktfrequenz (MHz)",
|
||||
"definicao": "Verarbeitungsgeschwindigkeit in Megahertz (MHz). ESP-IDF passt die Taktfrequenz im Betrieb dynamisch an (Dynamic Frequency Scaling - DFS), um in Leerlaufphasen Energie zu sparen.",
|
||||
"exemplo": "Der ESP32-C2 arbeitet mit bis zu 120 MHz; ESP32, S2, S3 und C6 erreichen 160/240 MHz; und der ESP32-P4 erreicht 400 MHz."
|
||||
},
|
||||
{
|
||||
"termo": "ULP (Ultra-Low-Power-Coprozessor)",
|
||||
"definicao": "Unabhängiger stromsparender Sekundärprozessor, der Befehle ausführen, analoge Sensoren (ADC), I2C und GPIOs abfragen kann, während die Hauptkerne im Deep Sleep vollständig abgeschaltet bleiben.",
|
||||
"exemplo": "Der Ur-ESP32 enthält einen ULP-FSM; ESP32-S2, S3 und C6 verfügen über einen in C programmierbaren ULP-RISC-V; der ESP32-P4 bietet einen dedizierten Low-Power-ULP."
|
||||
},
|
||||
{
|
||||
"termo": "KI-Vektorerweiterungen (Vector Extension / ESP-NN)",
|
||||
"definicao": "Spezialisierte Silizium-Befehlssatzerweiterungen, die mathematische Vektor- und Matrixoperationen mit Ganzzahlen (int8/int16) parallel verarbeiten und so Faltungsnetze (CNNs) und Signalverarbeitung beschleunigen.",
|
||||
"exemplo": "ESP32-S3 und ESP32-P4 beschleunigen Inferenzmodelle für Gesichtserkennung, Spracherkennung und TensorFlow Lite for Microcontrollers."
|
||||
},
|
||||
{
|
||||
"termo": "FPU (Gleitkommaeinheit)",
|
||||
"definicao": "Hardware-Recheneinheit für Gleitkommaoperationen, die Additionen, Multiplikationen und Divisionen von Dezimalzahlen (float) in einem einzigen Taktzyklus ohne Software-Emulation ausführt.",
|
||||
"exemplo": "Integriert in den Xtensa-Kernen des ESP32 und ESP32-S3 sowie in den Hochleistungs-RISC-V-Kernen des ESP32-P4."
|
||||
},
|
||||
{
|
||||
"termo": "PPA (Pixel Processing Accelerator)",
|
||||
"definicao": "Exklusiver 2D-Grafikbeschleuniger des ESP32-P4 für beschleunigte Bildverarbeitung: Frame-Rotation, Skalierung (Scaling), Alpha-Blending und Farbraumkonvertierung (RGB565, ARGB8888, YUV420).",
|
||||
"exemplo": "Ermöglicht das Rendering komplexer Benutzeroberflächen (LVGL) bei 60 FPS ohne Belastung der Haupt-CPU-Kerne."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "seguranca",
|
||||
"nome": "Sicherheit, Kryptografie & eFuses",
|
||||
"icone": "ShieldCheck",
|
||||
"emoji": "🔒",
|
||||
"cor": "red",
|
||||
"descricao": "Secure Boot v2, hardwarebasierte Flash-Verschlüsselung, irreversible eFuses, digitale Signaturen und TEE-Isolation.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "eFuse (Elektronische Sicherungen)",
|
||||
"definicao": "Einmalig programmierbare mikroskopische Sicherungen (One-Time Programmable - OTP) im Silizium. Dienen zur dauerhaften Speicherung von kryptografischen Hardware-Schlüsseln, MAC-Adressen und Sicherheitsparametern.",
|
||||
"exemplo": "Das Setzen der Schutz-eFuses sperrt unsichere Boot-Modi dauerhaft und schützt den Flash-Verschlüsselungsschlüssel."
|
||||
},
|
||||
{
|
||||
"termo": "Secure Boot (V1 und V2)",
|
||||
"definicao": "Hardwarebasierter Sicherheitsmechanismus, der sicherstellt, dass nur mit einem vertrauenswürdigen privaten Schlüssel (RSA-3072 oder ECDSA-V2) signierte Firmware gestartet werden kann. Verhindert das Ausführen unautorisierter Binärdateien.",
|
||||
"exemplo": "ESP32 unterstützt Secure Boot v1/v2; ESP32-S2, S3, C3, C6, H2 und P4 nutzen ausschließlich Secure Boot v2 basierend auf RSA-3072 / ECDSA."
|
||||
},
|
||||
{
|
||||
"termo": "Flash-Verschlüsselung (Flash Encryption)",
|
||||
"definicao": "Transparente Echtzeitverschlüsselung der Inhalte des externen Flash-Speichers mittels AES-XTS (128 oder 256 Bit). Der kryptografische Schlüssel wird in eFuses abgelegt und kann per Software nicht ausgelesen werden.",
|
||||
"exemplo": "Das direkte physische Auslesen des Flash-Chips mit externen Programmiergeräten liefert lediglich unlesbare Chiffredaten."
|
||||
},
|
||||
{
|
||||
"termo": "Key Manager",
|
||||
"definicao": "Dedizierte Hardware-Sicherheitsperipherie auf modernen ESP32-SoCs (ESP32-C6, C61, P4) zur sicheren Speicherung, Ableitung und Zugriffskontrolle kryptografischer Schlüssel ohne Offenlegung im CPU-RAM.",
|
||||
"exemplo": "Sichere Schlüsselableitung für TLS-Verbindungen und Datenspeicherung mit Hardware-Schutz gegen Speicher-Dumps."
|
||||
},
|
||||
{
|
||||
"termo": "Hardware-ECC und ECDSA",
|
||||
"definicao": "Hardware-Beschleuniger für elliptische Kurven-Kryptografie (ECC) und digitale Signaturen (ECDSA) auf P-192- und P-256-Kurven. Beschleunigt TLS/DTLS-Verbindungsaufbauten und das Matter-Protokoll signifikant.",
|
||||
"exemplo": "Authentifizierung von Matter-Geräten und Erstellung digitaler Signaturen ohne nennenswerte CPU-Auslastung."
|
||||
},
|
||||
{
|
||||
"termo": "HMAC und digitale Signatur (DS)",
|
||||
"definicao": "Hardware-Blöcke zur Berechnung von HMAC-Hashes und RSA-Signaturen, ohne dass der geheime private Schlüssel jemals in den RAM-Speicher der CPU geladen werden muss.",
|
||||
"exemplo": "Sichere Geräteauthentifizierung bei Cloud-Plattformen per mTLS ohne Risiko des Schlüsselabflusses."
|
||||
},
|
||||
{
|
||||
"termo": "TRNG (Echter Zufallszahlengenerator)",
|
||||
"definicao": "Hardwarebasierter Zufallszahlengenerator basierend auf thermischem Rauschen und HF-Signalen des Funkempfängers. Liefert unverzichtbare physikalische Entropie für kryptografische Operationen.",
|
||||
"exemplo": "Erzeugung sicherer Session-Keys, Initialisierungsvektoren (IV) und Nonces für TLS und WPA3."
|
||||
},
|
||||
{
|
||||
"termo": "DPA-Schutz (Differential Power Analysis)",
|
||||
"definicao": "Hardware-Gegenmaßnahmen in Kryptografie-Engines (AES/RSA) zur Verschleierung von Stromverbrauchsprofilen, um Seitenkanalangriffe bei Berechnungen zu unterbinden.",
|
||||
"exemplo": "Integriert auf ESP32-S3, C3, C6, H2 und P4 zum Schutz gegen physische Laborangriffe."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "memoria",
|
||||
"nome": "Speicher, Busse & Massenspeicher",
|
||||
"icone": "Database",
|
||||
"emoji": "💾",
|
||||
"cor": "purple",
|
||||
"descricao": "Interner SRAM, SPI- und Octal-Busse für externen Flash, High-Speed-PSRAM, Cache-Speicher und MMU-Adressabbildung.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Interner SRAM (Static RAM)",
|
||||
"definicao": "Ultraschneller statischer Arbeitsspeicher direkt auf dem Chip, der in einem CPU-Taktzyklus für Befehlsausführung (IRAM) und dynamische Datenablage (DRAM) adressierbar ist.",
|
||||
"exemplo": "ESP32 bietet 520 KB SRAM; ESP32-S3 512 KB; ESP32-C3 400 KB; ESP32-C6 512 KB; und ESP32-P4 768 KB."
|
||||
},
|
||||
{
|
||||
"termo": "Boot-ROM",
|
||||
"definicao": "Im Werk fest ins Silizium geschriebener Festspeicher mit dem First-Stage-Bootloader. Initialisiert grundlegende Takte, liest eFuses und lädt den sekundären Bootloader aus dem Flash-Speicher.",
|
||||
"exemplo": "Unterstützt den seriellen Download-Modus über UART oder USB zur Erstprogrammierung von Firmware."
|
||||
},
|
||||
{
|
||||
"termo": "SPI-Flash (Quad-SPI vs. Octal-SPI)",
|
||||
"definicao": "Nichtflüchtiger externer oder In-Package-Speicher für Firmware, Partitionstabellen und Anwendungsdaten. Quad-SPI nutzt 4 Datenleitungen, Octal-SPI nutzt 8 Datenleitungen bei doppelter Bandbreite.",
|
||||
"exemplo": "ESP32-S3 und ESP32-P4 unterstützen Octal-SPI-Flash mit bis zu 120 MHz im OPI-DDR-Modus."
|
||||
},
|
||||
{
|
||||
"termo": "PSRAM (Externer Pseudo-Static RAM)",
|
||||
"definicao": "Externer dynamischer RAM über SPI/QPI/OPI-Busse, der sich durch interne Refresh-Logik wie statischer SRAM verhält. Erforderlich für Audiostreaming, Bildverarbeitung und grafische Oberflächen.",
|
||||
"exemplo": "ESP32-WROVER-Module (4/8 MB Quad-PSRAM) und ESP32-S3-WROOM-1 (bis zu 16 MB Octal-PSRAM)."
|
||||
},
|
||||
{
|
||||
"termo": "RTC-SRAM (Fast und Slow)",
|
||||
"definicao": "SRAM-Speicherbereiche in der batteriegepufferten RTC-Domäne (Real-Time Clock), die während des Deep-Sleep-Modus mit Strom versorgt werden und ihren Inhalt behalten.",
|
||||
"exemplo": "RTC Fast (8 KB) ermöglicht schnelle Befehlsausführung durch den ULP-Coprozessor; RTC Slow (8 KB) speichert Zustandsdaten und Messwerte."
|
||||
},
|
||||
{
|
||||
"termo": "DMA-Speicherallokation (MALLOC_CAP_DMA)",
|
||||
"definicao": "Speicherreservierung in physischen SRAM-Bereichen, die direkt für Direct Memory Access (DMA) von Peripheriegeräten (SPI, I2S, LCD, ADC) ohne CPU-Beteiligung zugänglich sind.",
|
||||
"exemplo": "Nutzung von heap_caps_malloc(groesse, MALLOC_CAP_DMA) für Bildschirmpuffer bei schnellen SPI-Displays."
|
||||
},
|
||||
{
|
||||
"termo": "Heap-Fragmentierung",
|
||||
"definicao": "Zustand, in dem freier RAM-Speicher in viele kleine, nicht zusammenhängende Blöcke zerfällt, sodass größere zusammenhängende Speicheranforderungen fehlschlagen, obwohl insgesamt genug RAM frei ist.",
|
||||
"exemplo": "Vermeiden Sie dynamische String-Operationen in Schleifen; nutzen Sie statisch vorallokierte Puffer."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "conectividade",
|
||||
"nome": "Drahtlose Konnektivität & Protokolle",
|
||||
"icone": "Wifi",
|
||||
"emoji": "📡",
|
||||
"cor": "emerald",
|
||||
"descricao": "Wi-Fi 4/6, Bluetooth 5.x BLE, IEEE 802.15.4-Funk (Zigbee / Thread), Matter-Standard und routerloses ESP-NOW.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Wi-Fi 6 (802.11ax)",
|
||||
"definicao": "Moderner Wi-Fi-Standard mit wesentlichen Verbesserungen bei spektraler Effizienz, Latenz und Energieverbrauch in dichten IoT-Netzwerken durch OFDMA und Target Wake Time (TWT).",
|
||||
"exemplo": "Nativ unterstützt auf den SoCs ESP32-C6 und ESP32-C5 (2.4 GHz und 5 GHz)."
|
||||
},
|
||||
{
|
||||
"termo": "Wi-Fi Dual-Band (2.4 GHz und 5 GHz)",
|
||||
"definicao": "Fähigkeit des Funkteils, sowohl im etablierten 2.4-GHz-Band (höhere Reichweite) als auch im 5-GHz-Band (höhere Datenrate, weniger Störungen) zu kommunizieren.",
|
||||
"exemplo": "Der ESP32-C5 ist Espressifs erster SoC mit vollständigem Dual-Band-Wi-Fi 6."
|
||||
},
|
||||
{
|
||||
"termo": "OFDMA (Orthogonal Frequency Division Multiple Access)",
|
||||
"definicao": "Kerntechnologie von Wi-Fi 6, die Funkkanäle in Unterkanäle (Resource Units - RUs) aufteilt, sodass ein Router gleichzeitig mit mehreren IoT-Geräten ohne Paketkollisionen Daten austauschen kann.",
|
||||
"exemplo": "Reduziert Netzwerklatenzen in Smart-Home-Umgebungen mit Dutzenden vernetzten ESP32-C6-Knoten erheblich."
|
||||
},
|
||||
{
|
||||
"termo": "TWT (Target Wake Time)",
|
||||
"definicao": "Stromsparfunktion von Wi-Fi 6, bei der IoT-Gerät und Access Point feste Aufwachzeiten aushandeln, wodurch das Funkmodul über lange Zeiträume im Tiefschlaf bleiben kann.",
|
||||
"exemplo": "Ermöglicht batteriebetriebenen ESP32-C6-Sensoren mehrjährige Laufzeiten mit einer Batterieladung."
|
||||
},
|
||||
{
|
||||
"termo": "Klassisches Bluetooth (BR/EDR)",
|
||||
"definicao": "Ursprünglicher Bluetooth-Standard für kontinuierliche Datenübertragungen mit mittlerer Bandbreite und drahtloses Audiostreaming über das A2DP-Profil.",
|
||||
"exemplo": "Verfügbar auf dem klassischen ESP32 für Bluetooth-Lautsprecher und serielle SPP-Verbindungen."
|
||||
},
|
||||
{
|
||||
"termo": "Bluetooth Low Energy (BLE 5.0 bis 5.4)",
|
||||
"definicao": "Extrem stromsparendes Funkprotokoll für autonome IoT-Geräte. Versionen ab 5.0 bieten 2-Mbps-Datenraten, Coded PHY für hohe Reichweite und Extended Advertising.",
|
||||
"exemplo": "Unterstützt auf allen modernen Serien wie ESP32-S3, C3, C6, H2 und C5."
|
||||
},
|
||||
{
|
||||
"termo": "Bluetooth LE Audio und Auracast",
|
||||
"definicao": "Moderne Bluetooth-Audiogeneration basierend auf dem LC3-Codec über BLE, mit verbesserter Klangqualität, geringerem Stromverbrauch und Auracast-Broadcast-Audio.",
|
||||
"exemplo": "Unterstützt auf dem ESP32-H4 für Audioempfänger und Hörassistenzgeräte."
|
||||
},
|
||||
{
|
||||
"termo": "IEEE 802.15.4 (Zigbee 3.0 und Thread)",
|
||||
"definicao": "Energiesparender Funkstandard für Mesh-Netzwerke. Dient als physikalische Basis für Zigbee 3.0 und Thread zur herstellerübergreifenden Gebäudeautomation ohne Wi-Fi-Abhängigkeit.",
|
||||
"exemplo": "Nativ integriert in den SoCs ESP32-H2 und ESP32-C6."
|
||||
},
|
||||
{
|
||||
"termo": "Matter (Einheitlicher Smart-Home-Standard)",
|
||||
"definicao": "Offener Smart-Home-Anwendungsstandard der Connectivity Standards Alliance (CSA), der herstellerübergreifende Interoperabilität mit Apple Home, Google Home, Alexa und SmartThings ermöglicht.",
|
||||
"exemplo": "Läuft über Matter over Wi-Fi (ESP32, S3, C3, C6) und Matter over Thread (ESP32-H2, C6)."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "perifericos",
|
||||
"nome": "Ein-/Ausgänge & Peripheriegeräte",
|
||||
"icone": "Sliders",
|
||||
"emoji": "🔌",
|
||||
"cor": "amber",
|
||||
"descricao": "GPIO-Pins, GPIO-Matrix, ADC- und DAC-Wandler, kapazitive Touch-Sensoren, UART, SPI, I2C, I2S und PWM.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "GPIO (Allgemeine digitale Ein-/Ausgänge)",
|
||||
"definicao": "Physische Pins des Mikrocontrollers, die individuell als digitale Ein- oder Ausgänge konfiguriert werden können, inklusive interner Pull-up/Pull-down-Widerstände und Hardware-Interrupts.",
|
||||
"exemplo": "Abfrage von Tastern, Schalten von Relais und Statusanzeigen über LEDs."
|
||||
},
|
||||
{
|
||||
"termo": "Strapping-Pins (Boot-Pins)",
|
||||
"definicao": "Spezielle Pins, deren logischer Pegel beim Hardware-Reset vom ROM abgetastet wird, um den Betriebsmodus zu bestimmen: normaler Flash-Boot, serieller Download-Modus oder VDD_SDIO-Spannungswahl.",
|
||||
"exemplo": "GPIO0 muss auf Low (0) liegen, um den Programmiermodus zu aktivieren, oder auf High (1) für normalen Boot."
|
||||
},
|
||||
{
|
||||
"termo": "ADC (Analog-Digital-Wandler)",
|
||||
"definicao": "Hardware-Peripherie zur Umwandlung kontinuierlicher analoger Spannungen in diskrete 12-Bit-Digitalwerte (0 bis 4095). Aufgeteilt auf zwei Blöcke: ADC1 und ADC2.",
|
||||
"exemplo": "Messung von Batteriespannungen, Helligkeitssensoren (LDR) und Potentiometern."
|
||||
},
|
||||
{
|
||||
"termo": "DAC (Digital-Analog-Wandler)",
|
||||
"definicao": "Hardware-Wandler zur Ausgabe einer analogen Spannung proportional zu einem 8-Bit-Digitalwert an dedizierten Pins.",
|
||||
"exemplo": "Verfügbar an GPIO25 und GPIO26 des Ur-ESP32 zur Erzeugung von Audiosignalen und analogen Spannungskurven."
|
||||
},
|
||||
{
|
||||
"termo": "LEDC (LED-PWM-Controller)",
|
||||
"definicao": "Hardware-PWM-Generator mit bis zu 16 Bit Auflösung, unabhängigen Kanälen und automatischer Hardware-Überblendung (Fading) ohne CPU-Last.",
|
||||
"exemplo": "Helligkeitssteuerung von LED-Streifen (RGB/RGBW) und Ansteuerung von Standard-Servos."
|
||||
},
|
||||
{
|
||||
"termo": "MCPWM (Motorsteuerungs-PWM)",
|
||||
"definicao": "Spezialisierte PWM-Peripherie für Elektromotoren, Wechselrichter und H-Brücken mit automatischer Totzeit-Generierung (Dead-Time) und Fehlerschutzabschaltung.",
|
||||
"exemplo": "Präzise Ansteuerung bürstenloser Gleichstrommotoren (BLDC) auf ESP32 und ESP32-S3."
|
||||
},
|
||||
{
|
||||
"termo": "RMT (Fernbedienungs-Peripherie)",
|
||||
"definicao": "Hardware-Sende- und Empfangsmodul für Infrarot- und Digitalimpulsfolgen mit Nanosekunden-Präzision ohne CPU-Beteiligung.",
|
||||
"exemplo": "Ideal zur Ansteuerung adressierbarer LED-Streifen (WS2812B/NeoPixel) und Dekodierung von Infrarot-Fernbedienungen."
|
||||
},
|
||||
{
|
||||
"termo": "PCNT (Impulszähler)",
|
||||
"definicao": "Eigenständiger Hardware-Zähler zur Erfassung steigender und fallender Signalflanken externer Impulse, inklusive Entprellfiltern und Quadratur-Dekodierung.",
|
||||
"exemplo": "Auswertung von Drehgebern und Durchflusssensoren ohne Generierung ständiger CPU-Interrupts."
|
||||
},
|
||||
{
|
||||
"termo": "TWAI® (Two-Wire Automotive Interface / CAN-Bus)",
|
||||
"definicao": "CAN 2.0B-kompatibler Hardware-Controller für robuste differentielle Datenübertragungen im Fahrzeug- und industriellen Bereich.",
|
||||
"exemplo": "Auslesen von Kfz-OBD-II-Schnittstellen und Kommunikation mit Industriesteuerungen (SPS)."
|
||||
},
|
||||
{
|
||||
"termo": "Kapazitive Touch-Pins",
|
||||
"definicao": "Eingangspins mit kapazitiver Messschaltung zur Erkennung von Berührung oder Annäherung ohne externe Bauteile.",
|
||||
"exemplo": "Vandalismussichere Folientaster und berührungsempfindliche Oberflächen hinter Kunststoffgehäusen."
|
||||
},
|
||||
{
|
||||
"termo": "PARLIO (Paralleler E/A-Controller)",
|
||||
"definicao": "Schnelle parallele E/A-Schnittstelle auf neueren SoCs (ESP32-C6, P4) zur getakteten Mehrbit-Datenübertragung mit dediziertem Taktsignal.",
|
||||
"exemplo": "Anbindung schneller externer Sensoren, Spezialdisplays und proprietärer Funkmodule."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "multimidia",
|
||||
"nome": "Multimedia, USB & Erweiterte Schnittstellen",
|
||||
"icone": "Sparkles",
|
||||
"emoji": "✨",
|
||||
"cor": "pink",
|
||||
"descricao": "Natives USB OTG, USB Serial/JTAG, MIPI-DSI- und CSI-Schnittstellen für Displays und Kameras, PPA-Grafikbeschleuniger und Ethernet-MAC.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Natives USB OTG (On-The-Go)",
|
||||
"definicao": "Integrierter USB-Hardware-Controller, der sowohl im Device-Modus (Tastatur, Maus, Massenspeicher) als auch im Host-Modus (Auslesen von USB-Sticks) betrieben werden kann.",
|
||||
"exemplo": "Verfügbar auf ESP32-S2 und ESP32-S3 (Full-Speed 12 Mbps) sowie ESP32-P4 (High-Speed 480 Mbps)."
|
||||
},
|
||||
{
|
||||
"termo": "Natives USB Serial/JTAG",
|
||||
"definicao": "Direkt ins Silizium integrierte Hardware-Schnittstelle, die einen virtuellen COM-Port (CDC) und JTAG-Debugging ohne externe Brückenchips (wie CP2102 oder CH340) bereitstellt.",
|
||||
"exemplo": "Firmware-Upload und Einzelschritt-Debugging in VS Code auf ESP32-C3, S3, C6, H2 und P4."
|
||||
},
|
||||
{
|
||||
"termo": "USB 2.0 High-Speed (480 Mbps)",
|
||||
"definicao": "Schnelle USB-Schnittstelle mit bis zu 480 Mbit/s Datenübertragungsrate für Videoerfassung, UVC-Kameras und große Datenmengen.",
|
||||
"exemplo": "Nativ mit integriertem physikalischem Transceiver (PHY) im ESP32-P4-SoC enthalten."
|
||||
},
|
||||
{
|
||||
"termo": "MIPI CSI und MIPI DSI",
|
||||
"definicao": "Standardisierte serielle Hochgeschwindigkeits-Differenzialbusse der Mobile Industry Processor Interface für Kamerasensoren (CSI) und hochauflösende Displays (DSI).",
|
||||
"exemplo": "ESP32-P4 bietet MIPI CSI mit 2 Lanes (HD-Kameras) und MIPI DSI mit 2 Lanes (1080p-Touchscreens)."
|
||||
},
|
||||
{
|
||||
"termo": "Hardwarebasierter H.264-Video-Encoder",
|
||||
"definicao": "Dedizierte Hardware-Einheit zur Echtzeitkompression von Videodaten nach dem H.264-Standard (AVC) bei minimaler CPU-Auslastung.",
|
||||
"exemplo": "Ermöglicht Videocodierung bis zu 1080p bei 30 FPS auf dem Multimedia-Prozessor ESP32-P4."
|
||||
},
|
||||
{
|
||||
"termo": "Ethernet MAC 10/100 Mbps",
|
||||
"definicao": "Integrierter IEEE 802.3-Netzwerkcontroller, der lediglich einen externen RMII-PHY-Transceiver (z. B. LAN8720 oder IP101) für kabelgebundene Netzwerkverbindungen benötigt.",
|
||||
"exemplo": "Verfügbar auf dem klassischen ESP32 und ESP32-P4 für ausfallsichere industrielle Netzwerkanbindungen."
|
||||
},
|
||||
{
|
||||
"termo": "DVP-Kameraschnittstelle (8 Bit / 16 Bit)",
|
||||
"definicao": "Parallele digitale Videoschnittstelle (Digital Video Port) mit 8 oder 16 Datenleitungen und Pixeltakt (PCLK) zur Bildeingabe von Standard-Kamerasensoren.",
|
||||
"exemplo": "Anschluss gängiger Kameramodule (OV2640, OV5640) auf ESP32-CAM- und ESP32-S3-Entwicklungsboards."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "energia",
|
||||
"nome": "Energiemanagement & Schlafmodi",
|
||||
"icone": "BatteryCharging",
|
||||
"emoji": "🔋",
|
||||
"cor": "teal",
|
||||
"descricao": "Deep Sleep, Light Sleep, Low-Power-RTC-Domäne, dynamische Frequenzskalierung (DFS) und Brownout-Schutzschaltung.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Aktiver Modus (Active Mode)",
|
||||
"definicao": "Voll funktionsfähiger Betriebszustand, bei dem CPU-Kerne, Peripherie und Funkmodule aktiv sind. Der Stromverbrauch liegt je nach Funkaktivität typischerweise zwischen 40 mA und 240 mA.",
|
||||
"exemplo": "Laufende Datenübertragungen über Wi-Fi oder rechenintensive Bildverarbeitung."
|
||||
},
|
||||
{
|
||||
"termo": "Modem Sleep",
|
||||
"definicao": "Betriebsmodus, bei dem die CPU normal weiterarbeitet, während das Funkmodul (Wi-Fi oder Bluetooth) zwischen den DTIM-Beacon-Intervallen abgeschaltet wird.",
|
||||
"exemplo": "Der Stromverbrauch sinkt auf etwa 15 bis 30 mA bei bestehender WLAN-Verbindung."
|
||||
},
|
||||
{
|
||||
"termo": "Light Sleep",
|
||||
"definicao": "Zwischenschlafmodus, bei dem Takte und CPU angehalten werden, der SRAM-Inhalt jedoch vollständig erhalten bleibt. Die Aufwachzeit liegt unter einer Millisekunde.",
|
||||
"exemplo": "Stromverbrauch unter 1 bis 2 mA mit schnellem Aufwachen durch Timer, GPIO oder serielle Aktivität."
|
||||
},
|
||||
{
|
||||
"termo": "Deep Sleep",
|
||||
"definicao": "Tiefschlafmodus, bei dem CPU, Funk und der Großteil des SRAMs abgeschaltet sind. Nur die stromsparende RTC-Domäne bleibt aktiv, um Aufwachereignisse zu überwachen.",
|
||||
"exemplo": "Extrem geringer Stromverbrauch von 5 bis 150 µA – ideal für batteriebetriebene Wetterstationen und Sensoren."
|
||||
},
|
||||
{
|
||||
"termo": "Ruhezustand (Hibernation Mode)",
|
||||
"definicao": "Modus mit absolut minimalem Energieverbrauch, bei dem auch Hauptquarz und RTC Fast SRAM stromlos geschaltet werden. Nur der langsame RTC-Timer oder ein externer Pin können aufwecken.",
|
||||
"exemplo": "Minimaler Reststrom von unter 5 µA auf dem Ur-ESP32 und ESP32-C3."
|
||||
},
|
||||
{
|
||||
"termo": "Aufwachquellen (Wakeup Sources)",
|
||||
"definicao": "Konfigurierbare Hardware-Ereignisse zum Aufwecken des SoCs aus dem Schlafmodus (Light Sleep oder Deep Sleep): RTC-Timer, GPIO-Pegelwechsel (ext0/ext1), Touch-Sensor oder ULP-Coprozessor.",
|
||||
"exemplo": "Periodisches Aufwachen alle 15 Minuten zur Sensordatenübermittlung mit sofortiger Rückkehr in den Tiefschlaf."
|
||||
},
|
||||
{
|
||||
"termo": "Brownout-Detektor (Unterspannungserkennung)",
|
||||
"definicao": "Interne Überwachungsschaltung für die Versorgungsspannung, die bei gefährlichen Spannungseinbrüchen einen kontrollierten Reset auslöst, um Flash-Datenkorruption zu verhindern.",
|
||||
"exemplo": "Löst die Fehlermeldung 'Brownout detector was triggered' aus, wenn die Stromversorgung bei Wi-Fi-Sendeimpulsen einbricht."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "desenvolvimento",
|
||||
"nome": "Firmware, Boot & Betriebssystem",
|
||||
"icone": "Code2",
|
||||
"emoji": "🚀",
|
||||
"cor": "rose",
|
||||
"descricao": "Bootloader-Ablauf, Strapping-Pins, Partitionstabellen, OTA-Updates mit Rollback, FreeRTOS SMP und ESP Component Registry.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Bootloader (Erste und zweite Stufe)",
|
||||
"definicao": "Startkette der Firmware: Das interne ROM (1. Stufe) initialisiert Basishardware und lädt den sekundären Bootloader aus dem Flash, der die Partitionstabelle liest und die Applikation startet.",
|
||||
"exemplo": "Prüft kryptografische Signaturen bei aktivem Secure Boot vor dem Programmstart."
|
||||
},
|
||||
{
|
||||
"termo": "FreeRTOS (Echtzeitbetriebssystem)",
|
||||
"definicao": "Präemptives Echtzeitbetriebssystem, von Espressif für symmetrisches Multiprocessing (SMP) erweitert, das Tasks, Queues, Semaphoren und Software-Timer verwaltet.",
|
||||
"exemplo": "Ermöglicht die parallele Ausführung einer Sensor-Task auf Core 1 und des Netzwerk-Stacks auf Core 0."
|
||||
},
|
||||
{
|
||||
"termo": "Attribute IRAM_ATTR und DRAM_ATTR",
|
||||
"definicao": "Compiler-Makros, die Funktionen im schnellen Befehls-RAM (IRAM) oder Konstanten im Daten-RAM (DRAM) statt im externen SPI-Flash platzieren.",
|
||||
"exemplo": "Zwingend erforderlich für Interrupt-Serviceroutinen (ISRs), die während laufender Flash-Schreibvorgänge ausgeführt werden."
|
||||
},
|
||||
{
|
||||
"termo": "Partitionstabelle (partitions.csv)",
|
||||
"definicao": "Konfigurationsdatei zur Aufteilung des Flash-Speichers: Bereiche für Bootloader, NVS-Speicher, App-Binärdateien (ota_0, ota_1) und Dateisysteme (LittleFS).",
|
||||
"exemplo": "Ermöglicht zwei getrennte Firmware-Partitionen für ausfallsichere OTA-Updates mit Rollback-Funktion."
|
||||
},
|
||||
{
|
||||
"termo": "OTA-Updates mit Rollback-Funktion",
|
||||
"definicao": "Drahtlose Firmware-Aktualisierung über Wi-Fi oder Ethernet. Stürzt die neue Version ab oder bestätigt sie ihren Zustand nicht rechtzeitig, schaltet das System automatisch auf die vorherige funktionierende Firmware zurück.",
|
||||
"exemplo": "Verhindert, dass entfernt installierte IoT-Geräte durch fehlerhafte Software-Updates unbrauchbar werden."
|
||||
},
|
||||
{
|
||||
"termo": "NVS (Nichtflüchtiger Speicher) und NVS-Verschlüsselung",
|
||||
"definicao": "Schlüssel-Wert-Speicherbibliothek in einer dedizierten Flash-Partition zum dauerhaften Speichern von Wi-Fi-Zugangsdaten und Geräteeinstellungen mit optionaler Hardware-Verschlüsselung.",
|
||||
"exemplo": "Sichere Ablage von WLAN-Passwörtern und Authentifizierungszertifikaten."
|
||||
},
|
||||
{
|
||||
"termo": "Dateisysteme (LittleFS und SPIFFS)",
|
||||
"definicao": "Integrierte Dateisysteme für NOR-Flash-Speicher mit Wear-Leveling-Schutz vor vorzeitiger Speicherabnutzung. LittleFS ist moderner, stromausfallsicherer und deutlich schneller als SPIFFS.",
|
||||
"exemplo": "Speicherung von HTML-, CSS- und JavaScript-Dateien für lokale Weboberflächen auf dem ESP32."
|
||||
},
|
||||
{
|
||||
"termo": "JTAG und OpenOCD",
|
||||
"definicao": "Hardware- und Software-Debugging-Schnittstelle zum Setzen von Hardware-Breakpoints, Inspizieren von Variablen und Verfolgen der Programmausführung in Echtzeit.",
|
||||
"exemplo": "Direktes Hardware-Debugging über den internen USB-Serial/JTAG-Port in VS Code auf modernen SoCs (ESP32-S3, C3, C6, P4)."
|
||||
}
|
||||
]
|
||||
}
|
||||
];
|
||||
@@ -0,0 +1,177 @@
|
||||
/**
|
||||
* Domänenwissen für die intelligente Suche auf Deutsch.
|
||||
*
|
||||
* Ohne Abhängigkeiten oder Import-Aliase: läuft auf dem Server (Indexaufbau),
|
||||
* im Browser (Suchanfragen-Parsing) und in Node-Testskripten.
|
||||
*
|
||||
* Alle Texte in `termos` sind normalisiert (Kleinschreibung, ohne Umlaute/Akzente).
|
||||
*/
|
||||
|
||||
export const normalizar = (s = "") =>
|
||||
String(s)
|
||||
.toLowerCase()
|
||||
.replace(/ß/g, "ss")
|
||||
.replace(/ä/g, "ae")
|
||||
.replace(/ö/g, "oe")
|
||||
.replace(/ü/g, "ue")
|
||||
.normalize("NFD")
|
||||
.replace(/[\u0300-\u036f]/g, "");
|
||||
|
||||
/**
|
||||
* Erkennt durch Flash/PSRAM belegte Pins anhand der Diagrammbeschreibung.
|
||||
* "forte": Pin wird durch den Speicher belegt (oder ist dessen Stromversorgung).
|
||||
* "fraco": nur in bestimmten Betriebsmodi betroffen (z. B. 8-Leitungs-/Octal-SPI).
|
||||
*/
|
||||
const nivelMemoria = (palavra) => (p) => {
|
||||
const citam = p._avs.filter((a) => a.includes(palavra) && !/^fuer chips (mit|ohne)/i.test(a));
|
||||
if (citam.some((a) => /(belegt|dediziert|verbunden)/i.test(a) && !/ausser/i.test(a))) return "forte";
|
||||
if (p._fn.some((f) => /versorgung|stromversorgung/i.test(f) && f.includes(palavra))) return "forte";
|
||||
if (citam.length) return "fraco";
|
||||
return null;
|
||||
};
|
||||
|
||||
/**
|
||||
* Themenbereiche, die Benutzer auf Deutsch abfragen können.
|
||||
*/
|
||||
export const TOPICOS = [
|
||||
{ id: "flash", nome: "Flash", termos: ["flash", "flash-speicher", "flashspeicher", "spi flash", "speicher", "firmware", "externer rom"], pinoNivel: nivelMemoria("flash"), pinoRotulo: "mit Flash-Speicher verbunden" },
|
||||
{ id: "psram", nome: "PSRAM", termos: ["psram", "externes ram", "spiram"], pinoNivel: nivelMemoria("psram"), pinoRotulo: "mit PSRAM verbunden" },
|
||||
{ id: "memoria", nome: "Speicher", termos: ["speicher", "sram", "heap", "rtc ram", "kb ram", "interner speicher", "ram", "memory"], pinoRotulo: "" },
|
||||
{ id: "wifi", nome: "Wi-Fi", termos: ["wifi", "wi-fi", "wlan", "kabellos", "wireless", "802.11", "wifi6", "wifi 6"], pinoCats: ["Antenne"], pinoRotulo: "Antennen- und Funk-Pins" },
|
||||
{ id: "bluetooth", nome: "Bluetooth", termos: ["bluetooth", "ble", "bt", "bluetooth le", "mesh"], pinoCats: ["Antenne"], pinoRotulo: "Antennen- und Funk-Pins" },
|
||||
{ id: "zigbee", nome: "Zigbee/Thread", termos: ["zigbee", "thread", "802.15.4", "ieee 802.15.4"], pinoRotulo: "" },
|
||||
{ id: "matter", nome: "Matter", termos: ["matter", "smart home", "gebaeudeautomation", "heimvernetzung"], pinoRotulo: "" },
|
||||
{ id: "ethernet", nome: "Ethernet", termos: ["ethernet", "rmii", "netzwerkkabel", "lan"], pinoCats: ["Ethernet"], pinoRotulo: "Ethernet-Pins" },
|
||||
{ id: "can", nome: "CAN / TWAI", termos: ["can", "twai", "can bus", "canbus", "can fd"], pinoRe: /twai|\bcan\b/, pinoRotulo: "CAN/TWAI-Pins" },
|
||||
{ id: "usb", nome: "USB", termos: ["usb", "otg", "usb serial", "usb otg", "hid", "cdc"], pinoCats: ["USB"], pinoRotulo: "USB-Pins" },
|
||||
{ id: "jtag", nome: "JTAG / Debug", termos: ["jtag", "debug", "debugging", "openocd", "gdb", "fehlersuche"], pinoCats: ["JTAG"], pinoRotulo: "JTAG-Pins" },
|
||||
{ id: "adc", nome: "ADC", termos: ["adc", "analog", "analogeingang", "analog-digital-wandler", "analogread", "saradc"], pinoCats: ["ADC"], pinoRotulo: "mit ADC" },
|
||||
{ id: "dac", nome: "DAC", termos: ["dac", "analogausgang", "digital-analog-wandler"], pinoCats: ["DAC"], pinoRotulo: "mit DAC" },
|
||||
{ id: "touch", nome: "Kapazitiver Touch", termos: ["touch", "kapazitiv", "beruehrung", "touchpad", "beruehrungssensor"], pinoCats: ["Touch"], pinoRotulo: "kapazitive Touch-Pins" },
|
||||
{ id: "uart", nome: "UART", termos: ["uart", "seriell", "serial", "tx", "rx", "txd", "rxd", "serielle schnittstelle"], pinoCats: ["UART"], pinoRotulo: "UART-Pins" },
|
||||
{ id: "spi", nome: "SPI", termos: ["spi", "mosi", "miso", "sclk", "spi bus"], pinoCats: ["SPI"], pinoRotulo: "SPI-Pins" },
|
||||
{ id: "i2c", nome: "I2C", termos: ["i2c", "sda", "scl", "twi", "iic"], pinoCats: ["I2C"], pinoRotulo: "I2C-Pins" },
|
||||
{ id: "i2s", nome: "I2S", termos: ["i2s", "audio", "ton", "mikrofon", "pdm", "codec"], pinoRe: /i2s|\bpdm\b/, pinoRotulo: "I2S-/Audio-Pins" },
|
||||
{ id: "pwm", nome: "PWM", termos: ["pwm", "ledc", "mcpwm", "servo", "dimmer"], pinoRe: /ledc|pwm/, pinoRotulo: "PWM-Pins" },
|
||||
{ id: "sd", nome: "SD-Karte / SDIO", termos: ["sd", "sdio", "sd card", "sd-karte", "sdkarte", "microsd", "sdmmc", "mmc"], pinoCats: ["SD"], pinoRe: /sdio|sdmmc|\bsd\b/, pinoRotulo: "SD-Karten-/SDIO-Pins" },
|
||||
{ id: "camera", nome: "Kamera", termos: ["kamera", "camera", "cam", "dvp", "csi", "mipi csi", "ov2640", "video"], pinoCats: ["CSI"], pinoRe: /\bcam\b|dvp|cam_/, pinoRotulo: "Kamera-Pins" },
|
||||
{ id: "lcd", nome: "Display / LCD", termos: ["lcd", "display", "bildschirm", "dsi", "mipi dsi", "oled", "tft", "lvgl", "rgb"], pinoCats: ["DSI"], pinoRe: /lcd/, pinoRotulo: "Display-/LCD-Pins" },
|
||||
{ id: "strapping", nome: "Boot / Strapping", termos: ["strapping", "boot", "bootstrap", "boot-modus", "bootmodus", "download-modus", "startmodus"], pinoCats: ["Strapping"], pinoRotulo: "Strapping-Pins (Boot-Modus)" },
|
||||
{ id: "energia_pinos", nome: "Stromversorgung", termos: ["stromversorgung", "versorgung", "vdd", "3v3", "3.3v", "spannung", "regler", "ldo", "netzteil"], pinoCats: ["Power"], pinoRotulo: "Stromversorgungs-Pins" },
|
||||
{ id: "clock", nome: "Takt / Quarz", termos: ["clock", "takt", "taktfrequenz", "xtal", "quarz", "oszillator", "32khz", "40mhz"], pinoCats: ["Clock"], pinoRotulo: "Takt-/Quarz-Pins" },
|
||||
{ id: "gpio", nome: "GPIO", termos: ["gpio", "ein- und ausgaenge", "pins", "anschluesse"], pinoCats: ["GPIO"], pinoRotulo: "GPIO-Pins" },
|
||||
{ id: "baixo_consumo", nome: "Low Power / ULP", termos: ["ulp", "lp core", "lp cpu", "coprozessor", "lp gpio", "low power", "rtc gpio", "stromsparmodus", "niedriger verbrauch"], pinoCats: ["Low Power"], pinoRotulo: "Low-Power-Pins (LP/RTC)" },
|
||||
{ id: "antena", nome: "Antenne / HF", termos: ["antenne", "rf", "hf", "hochfrequenz", "funk", "ipex"], pinoCats: ["Antenne"], pinoRotulo: "Antennen-/HF-Pins" },
|
||||
{ id: "seguranca", nome: "Sicherheit", termos: ["sicherheit", "security", "secure boot", "kryptografie", "verschluesselung", "aes", "sha", "rsa", "hmac", "ecdsa", "efuse", "tee", "trng", "rng", "hsm", "schutz"], pinoRotulo: "" },
|
||||
{ id: "consumo", nome: "Energieverbrauch", termos: ["energieverbrauch", "stromverbrauch", "batterie", "deep sleep", "light sleep", "sleep", "modem sleep", "strom", "milliampere", "laufzeit", "energiesparmodus"], pinoRotulo: "" },
|
||||
{ id: "temperatura", nome: "Temperatur", termos: ["temperatur", "waerme", "grad", "temperaturbereich", "industriell"], pinoRotulo: "" },
|
||||
{ id: "ia", nome: "KI / Beschleunigung", termos: ["ki", "ia", "ai", "machine learning", "ml", "tinyml", "vektoriell", "kuenstliche intelligenz", "neuronales netz", "esp-nn", "esp-dl"], pinoRotulo: "" },
|
||||
{ id: "processador", nome: "Prozessor", termos: ["prozessor", "cpu", "kern", "kerne", "core", "dual core", "single core", "architektur", "xtensa", "risc-v", "riscv"], pinoRotulo: "" },
|
||||
{ id: "frequencia", nome: "Taktfrequenz", termos: ["frequenz", "taktfrequenz", "mhz", "geschwindigkeit", "leistung", "performance"], pinoRotulo: "" },
|
||||
{ id: "ferramentas", nome: "Werkzeuge / SDK", termos: ["esp-idf", "idf", "arduino", "sdk", "toolchain", "entwicklungsumgebung", "idf-version"], pinoRotulo: "" },
|
||||
{ id: "encapsulamento", nome: "Module & Gehäuse", termos: ["modul", "module", "gehaeuse", "package", "qfn", "wroom", "wrover", "mini-1"], pinoRotulo: "" },
|
||||
];
|
||||
|
||||
/**
|
||||
* Technische Spezifikationsfelder auf Deutsch.
|
||||
*/
|
||||
export const SPEC_CAMPOS = [
|
||||
{ campo: "arquitetura", label: "Architektur", secao: "processador", topicos: ["processador"] },
|
||||
{ campo: "nucleos", label: "Kerne", secao: "processador", topicos: ["processador"] },
|
||||
{ campo: "frequencia", label: "Taktfrequenz", secao: "processador", topicos: ["frequencia", "processador"] },
|
||||
{ campo: "coprocessador_ulp", label: "ULP-Coprozessor", secao: "processador", topicos: ["baixo_consumo"] },
|
||||
{ campo: "aceleradores_ia", label: "KI-Beschleuniger", secao: "processador", topicos: ["ia"] },
|
||||
|
||||
{ campo: "wifi", label: "Wi-Fi", secao: "conectividade", topicos: ["wifi"] },
|
||||
{ campo: "bluetooth", label: "Bluetooth", secao: "conectividade", topicos: ["bluetooth"] },
|
||||
{ campo: "zigbee_thread", label: "Zigbee/Thread", secao: "conectividade", topicos: ["zigbee"] },
|
||||
{ campo: "matter", label: "Matter", secao: "conectividade", topicos: ["matter"] },
|
||||
{ campo: "ethernet", label: "Ethernet", secao: "conectividade", topicos: ["ethernet"] },
|
||||
{ campo: "ethernet_mac", label: "Ethernet MAC", secao: "conectividade", topicos: ["ethernet"] },
|
||||
{ campo: "can", label: "CAN", secao: "conectividade", topicos: ["can"] },
|
||||
|
||||
{ campo: "memoria_sram", label: "SRAM", secao: "memoria", topicos: ["memoria"] },
|
||||
{ campo: "memoria_sram_rtc", label: "RTC-SRAM", secao: "memoria", topicos: ["memoria", "baixo_consumo"] },
|
||||
{ campo: "memoria_rom", label: "ROM", secao: "memoria", topicos: ["memoria"] },
|
||||
{ campo: "flash_externa", label: "Externer Flash", secao: "memoria", topicos: ["flash", "memoria"] },
|
||||
{ campo: "psram_externa", label: "Externes PSRAM", secao: "memoria", topicos: ["psram", "memoria"] },
|
||||
|
||||
{ campo: "gpio", label: "GPIO", secao: "perifericos", topicos: ["gpio"] },
|
||||
{ campo: "adc", label: "ADC", secao: "perifericos", topicos: ["adc"] },
|
||||
{ campo: "dac", label: "DAC", secao: "perifericos", topicos: ["dac"] },
|
||||
{ campo: "touch", label: "Kapazitiver Touch", secao: "perifericos", topicos: ["touch"] },
|
||||
{ campo: "uart", label: "UART", secao: "perifericos", topicos: ["uart"] },
|
||||
{ campo: "spi", label: "SPI", secao: "perifericos", topicos: ["spi", "flash"] },
|
||||
{ campo: "i2c", label: "I2C", secao: "perifericos", topicos: ["i2c"] },
|
||||
{ campo: "i2s", label: "I2S", secao: "perifericos", topicos: ["i2s"] },
|
||||
{ campo: "pwm", label: "PWM", secao: "perifericos", topicos: ["pwm"] },
|
||||
{ campo: "usb", label: "USB", secao: "perifericos", topicos: ["usb"] },
|
||||
{ campo: "lcd", label: "LCD", secao: "interfaces", topicos: ["lcd"] },
|
||||
{ campo: "camera", label: "Kamera", secao: "interfaces", topicos: ["camera"] },
|
||||
{ campo: "mipi_csi", label: "MIPI CSI", secao: "interfaces", topicos: ["camera"] },
|
||||
{ campo: "mipi_dsi", label: "MIPI DSI", secao: "interfaces", topicos: ["lcd"] },
|
||||
{ campo: "sdio", label: "SDIO", secao: "interfaces", topicos: ["sd"] },
|
||||
{ campo: "sensor_temperatura", label: "Temperatursensor", secao: "interfaces", topicos: ["temperatura"] },
|
||||
|
||||
{ campo: "seguranca.aes", label: "AES", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.sha", label: "SHA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.rsa", label: "RSA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.ecc", label: "ECC", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.ecdsa", label: "ECDSA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.hmac", label: "HMAC", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.assinatura_digital", label: "Digitale Signatur", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.rng", label: "Zufallszahlengenerator", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.criptografia_flash", label: "Flash-Verschlüsselung", secao: "seguranca", topicos: ["seguranca", "flash"] },
|
||||
{ campo: "seguranca.secure_boot", label: "Secure Boot", secao: "seguranca", topicos: ["seguranca", "strapping"] },
|
||||
|
||||
{ campo: "temperatura_operacao", label: "Betriebstemperatur", secao: "temperatura", topicos: ["temperatura"] },
|
||||
{ campo: "temperatura_armazenamento", label: "Lagertemperatur", secao: "temperatura", topicos: ["temperatura"] },
|
||||
|
||||
{ campo: "esp_idf_minimo", label: "Minimales ESP-IDF", secao: "ferramentas", topicos: ["ferramentas"] },
|
||||
{ campo: "arduino_core", label: "Arduino Core", secao: "ferramentas", topicos: ["ferramentas"] },
|
||||
{ campo: "depuracao", label: "Debugging", secao: "ferramentas", topicos: ["jtag", "ferramentas"] },
|
||||
{ campo: "encapsulamento", label: "Gehäuse", secao: "ferramentas", topicos: ["encapsulamento"] },
|
||||
{ campo: "modulos", label: "Module", secao: "ferramentas", topicos: ["encapsulamento"] },
|
||||
];
|
||||
|
||||
const ROTULOS_ENERGIA = {
|
||||
active: "Aktiv",
|
||||
modem_sleep: "Modem Sleep",
|
||||
light_sleep: "Light Sleep",
|
||||
deep_sleep: "Deep Sleep",
|
||||
hibernation: "Ruhezustand (Hibernation)",
|
||||
};
|
||||
|
||||
const pegar = (obj, caminho) => caminho.split(".").reduce((o, k) => (o == null ? o : o[k]), obj);
|
||||
|
||||
/**
|
||||
* Baut die Spezifikationsliste für jede Serie auf Deutsch auf.
|
||||
*/
|
||||
export function montarConhecimento(series, conexoes) {
|
||||
const saida = {};
|
||||
for (const [chave, s] of Object.entries(series)) {
|
||||
const specs = [];
|
||||
for (const c of SPEC_CAMPOS) {
|
||||
const valor = pegar(s, c.campo);
|
||||
if (valor == null || valor === "") continue;
|
||||
specs.push({ label: c.label, valor: String(valor), secao: c.secao, topicos: c.topicos });
|
||||
}
|
||||
for (const [modo, valor] of Object.entries(s.consumo_energia ?? {})) {
|
||||
const base = modo.replace(/_cpu.*|_wifi.*/, "");
|
||||
const label = ROTULOS_ENERGIA[modo] ?? ROTULOS_ENERGIA[base] ?? modo.replace(/_/g, " ");
|
||||
specs.push({ label: `Verbrauch: ${label}`, valor: String(valor), secao: "energia", topicos: ["consumo"] });
|
||||
}
|
||||
saida[chave] = {
|
||||
nome: s.nome_completo ?? chave,
|
||||
specs,
|
||||
pinos: (conexoes[chave] ?? []).map((p) => ({
|
||||
n: String(p.numero),
|
||||
nome: p.nome,
|
||||
f: p.funcoes ?? [],
|
||||
c: p.categorias ?? [],
|
||||
a: p.avisos ?? [],
|
||||
})),
|
||||
};
|
||||
}
|
||||
return saida;
|
||||
}
|
||||
File diff suppressed because it is too large.
Load diff
@@ -0,0 +1,724 @@
|
||||
/**
|
||||
* Base de données structurée pour le guide de diagnostic, erreurs fréquentes et dépannage sur ESP32.
|
||||
* Couvre 6 catégories techniques avec causes racines, comparaison bonnes pratiques vs contournements temporaires et exemples de code
|
||||
* en Arduino C++, ESP-IDF (C) et MicroPython.
|
||||
*/
|
||||
|
||||
export const categoriasDiagnostico = [
|
||||
{
|
||||
id: "alimentacao",
|
||||
nome: "Alimentation et Matériel",
|
||||
icone: "Zap",
|
||||
cor: "amber",
|
||||
descricao: "Chutes de tension causées par les pics de radio Wi-Fi/BLE, conflits sur broches de strapping, bruit électromagnétique et régulateurs LDO.",
|
||||
},
|
||||
{
|
||||
id: "cpu-panics",
|
||||
nome: "Paniques CPU et Guru Meditation",
|
||||
icone: "Cpu",
|
||||
cor: "red",
|
||||
descricao: "Pointeurs nuls, violations d'accès mémoire (Load/StoreProhibited), instructions illégales et paniques de cache dans les ISRs.",
|
||||
},
|
||||
{
|
||||
id: "freertos",
|
||||
nome: "FreeRTOS et Multitâche",
|
||||
icone: "Layers",
|
||||
cor: "purple",
|
||||
descricao: "Task Watchdog (TWDT), Interrupt Watchdog (IWDT), dépassement de pile (Stack Overflow) et blocages de l'ordonnanceur.",
|
||||
},
|
||||
{
|
||||
id: "memoria",
|
||||
nome: "Mémoire, Tas et PSRAM",
|
||||
icone: "Activity",
|
||||
cor: "blue",
|
||||
descricao: "Fragmentation du tas (heap), fuites de mémoire (Memory Leaks), allocations DMA et restrictions d'alignement de la PSRAM.",
|
||||
},
|
||||
{
|
||||
id: "boot-flash",
|
||||
nome: "Bootloader et Programmation",
|
||||
icone: "Terminal",
|
||||
cor: "emerald",
|
||||
descricao: "Pannes de communication série (DTR/RTS), erreurs de lecture en Flash SPI, décalages d'horloge et partitions corrompues.",
|
||||
},
|
||||
{
|
||||
id: "conectividade",
|
||||
nome: "Connectivité et Protocoles",
|
||||
icone: "Wifi",
|
||||
cor: "cyan",
|
||||
descricao: "Timeouts de balises Wi-Fi, échecs de négociation TLS/HTTPS dus à l'absence de synchronisation SNTP et signaux instables.",
|
||||
},
|
||||
];
|
||||
|
||||
export const sintomasRapidos = [
|
||||
{ id: "bootloop", rotulo: "🔄 Boucle de redémarrage (Crash loop)", categoria: "todos" },
|
||||
{ id: "wifi-crash", rotulo: "📶 Redémarre à l'activation du Wi-Fi/BLE", categoria: "alimentacao" },
|
||||
{ id: "upload-fail", rotulo: "🔌 Échec de téléversement (Erreur de flash)", categoria: "boot-flash" },
|
||||
{ id: "random-freeze", rotulo: "⏱️ Se fige après quelques minutes ou heures", categoria: "memoria" },
|
||||
{ id: "null-pointer", rotulo: "💥 Guru Meditation (Crash CPU)", categoria: "cpu-panics" },
|
||||
{ id: "wdt-reset", rotulo: "🐕 Watchdog déclenché (Reset TWDT)", categoria: "freertos" },
|
||||
{ id: "tls-fail", rotulo: "🔒 Échec de connexion HTTPS / SSL", categoria: "conectividade" },
|
||||
];
|
||||
|
||||
export const errosCatalogo = [
|
||||
{
|
||||
id: "brownout-reset",
|
||||
titulo: "Réinitialisation par le détecteur de sous-tension (Brownout Reset)",
|
||||
categoria: "alimentacao",
|
||||
sintomas: ["bootloop", "wifi-crash"],
|
||||
gravidade: "Haute",
|
||||
logSerial: "Brownout detector was triggered\n\nrst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)",
|
||||
resumo: "La tension d'alimentation de l'ESP32 a chuté sous le seuil critique de fonctionnement sécurisé (environ 2.8V ~ 2.43V).",
|
||||
causaRaiz:
|
||||
"Lors de l'initialisation des radios Wi-Fi ou BLE, l'amplificateur de puissance (PA) génère des pics de courant instantanés dépassant 500 mA en moins d'une milliseconde. Si l'alimentation, des câbles USB trop longs/fins, les pistes de plaque d'essai ou le régulateur LDO ne peuvent fournir ce courant transitoire à faible impédance, la tension sur le rail 3.3V s'effondre brièvement, déclenchant le comparateur interne de Brownout pour éviter la corruption de la Flash.",
|
||||
gambiarra: {
|
||||
titulo: "Désactiver le détecteur de Brownout par logiciel",
|
||||
descricao: "Appeler WRITE_PERI_REG(RTC_CNTL_BROWN_OUT_REG, 0) pour masquer l'erreur dans le code.",
|
||||
consequencia: "Extrêmement dangereux : l'ESP32 continue d'exécuter des instructions en sous-tension, corrompant la mémoire Flash SPI, bloquant les registres périphériques et provoquant des pannes imprévisibles sur le terrain.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Dimensionnement matériel correct et condensateurs de découplage",
|
||||
passos: [
|
||||
"Ajoutez un condensateur céramique ou tantale à faible ESR de 10 µF à 100 µF en parallèle avec un condensateur céramique de 100 nF au plus près des broches 3V3 et GND de l'ESP32.",
|
||||
"Utilisez des régulateurs LDO calibrés pour des pics d'au moins 600 mA à 1 A avec une excellente réponse transitoire (ex. : AP2112K, ME6211, TPS73733). Évitez les clones bas de gamme de l'AMS1117.",
|
||||
"Évitez d'alimenter l'ESP32 à travers les pistes d'une plaque d'essai avec de fins câbles dupont lorsque le Wi-Fi émet à pleine puissance.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Do NOT disable the Brownout detector! If you need to reduce current peaks in bench testing:
|
||||
#include <WiFi.h>
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
|
||||
// Optional: Slightly reducing maximum Wi-Fi TX power from 20dBm to 17dBm cuts current spikes by ~20%
|
||||
WiFi.setTxPower(WIFI_POWER_17dBm);
|
||||
WiFi.begin("SSID", "PASSWORD");
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF configuration:
|
||||
#include "esp_wifi.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void app_main(void) {
|
||||
// In menuconfig: Component config -> ESP32-specific -> Hardware Brownout Reset (Keep ENABLED)
|
||||
// To mitigate transient peaks in power-constrained designs:
|
||||
esp_wifi_set_max_tx_power(68); // 68 = 17dBm (units of 0.25dBm)
|
||||
}`,
|
||||
codigoMicroPython: `# Safe Wi-Fi connection in MicroPython with supply stabilization:
|
||||
import network
|
||||
import time
|
||||
|
||||
wlan = network.WLAN(network.STA_IF)
|
||||
wlan.active(True)
|
||||
|
||||
# Wait for supply rails to settle before turning on transmitter
|
||||
time.sleep_ms(200)
|
||||
wlan.connect("SSID", "PASSWORD")
|
||||
|
||||
attempts = 0
|
||||
while not wlan.isconnected() and attempts < 30:
|
||||
time.sleep_ms(200)
|
||||
attempts += 1
|
||||
|
||||
if wlan.isconnected():
|
||||
print("Wi-Fi Connected! IP:", wlan.ifconfig()[0])
|
||||
else:
|
||||
print("[ERROR] Failed to connect Wi-Fi")`,
|
||||
dicaPro: "Sur les circuits imprimés personnalisés, routez un plan de masse solide directement sous le module et dimensionnez les pistes d'alimentation 3.3V à 0.5 mm - 1 mm minimum pour éviter les chutes de tension résistives lors des salves RF.",
|
||||
},
|
||||
{
|
||||
id: "strapping-pins",
|
||||
titulo: "Conflit sur les broches de strapping au démarrage",
|
||||
categoria: "alimentacao",
|
||||
sintomas: ["bootloop", "upload-fail"],
|
||||
gravidade: "Critique",
|
||||
logSerial: "rst:0x1 (POWERON_RESET),boot:0x12 (SPI_FAST_FLASH_BOOT)\nflash read err, 1000\nwaiting for download",
|
||||
resumo: "The ESP32 fails to boot firmware from Flash or enters download mode unintentionally because a strapping pin was pulled to an incorrect logic level during reset.",
|
||||
causaRaiz:
|
||||
"The instant EN/CHIP_PU rises (Power-On Reset), the CPU latches the electrical logic level on specific strapping pins to configure Flash voltage (1.8V vs 3.3V), boot mode (UART Download vs SPI Flash Boot), and clock output. Connecting external sensors, relays, or LEDs with pull-up/pull-down resistors to these pins forces invalid strapping states, halting the bootloader.",
|
||||
gambiarra: {
|
||||
titulo: "Adding delays in code or manually disconnecting cables at each boot",
|
||||
descricao: "Attempting to fix the problem in setup() or manually unplugging wires before every reset.",
|
||||
consequencia: "Useless: Strapping pins are sampled by silicon hardware before the CPU executes a single line of application code or the second-stage bootloader.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Safe GPIO allocation and reset isolation",
|
||||
passos: [
|
||||
"ESP32 (Classic): Avoid using GPIO 0 (Boot mode), GPIO 2 (must be LOW or floating during flashing), GPIO 12 (selects Flash voltage: pulling HIGH at reset burns/locks 3.3V flash), and GPIO 15 (suppresses boot log output if LOW).",
|
||||
"ESP32-C3: Avoid pulling GPIO 8 LOW or GPIO 9 LOW during reset.",
|
||||
"ESP32-S3: Watch GPIO 0, GPIO 45 (VDD_SPI voltage level), and GPIO 46.",
|
||||
"If these pins must interface with peripherals, use transistors or digital bus switches to isolate them until the EN pin has completely risen and stabilized.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// SAFE PINOUT RECOMMENDATIONS (ESP32 Classic):
|
||||
// Preferred pins for I2C / SPI / General Sensors:
|
||||
// SDA: GPIO 21 | SCL: GPIO 22
|
||||
// SPI: MOSI 23 | MISO 19 | SCK 18 | CS 5
|
||||
|
||||
// WARNING: GPIOs 34, 35, 36 (VP), 39 (VN) are INPUT-ONLY (no internal pull-up/pull-down).
|
||||
// Never configure them as pinMode(..., OUTPUT); nor for I2C/SPI buses.`,
|
||||
codigoEspIdf: `// In ESP-IDF, lock Flash voltage via eFuse to free GPIO 12 (WARNING: IRREVERSIBLE):
|
||||
// If using classic ESP32 and GPIO 12 is needed for peripherals:
|
||||
// espefuse.py --port /dev/ttyUSB0 set_flash_voltage 3.3V
|
||||
// This permanently disables hardware strapping sampling on GPIO 12.`,
|
||||
codigoMicroPython: `# Safe pin setup in MicroPython:
|
||||
from machine import Pin
|
||||
|
||||
# Safe pins for outputs and buttons with internal pull-up:
|
||||
led = Pin(2, Pin.OUT) # GPIO 2
|
||||
button = Pin(4, Pin.IN, Pin.PULL_UP) # GPIO 4 (safe)
|
||||
|
||||
# Pins 34, 35, 36, 39 are INPUT-ONLY with no internal pull-ups:
|
||||
analog_sensor = Pin(36, Pin.IN) # Correct (requires external pull-up if used as a digital input)`,
|
||||
dicaPro: "Remember: Input-only pins (GPI 34 to 39 on classic ESP32) have neither internal silicon pull-up/pull-down circuits nor output drivers. External resistors are mandatory.",
|
||||
},
|
||||
{
|
||||
id: "guru-load-prohibited",
|
||||
titulo: "Guru Meditation: LoadProhibited / StoreProhibited (Pointeur nul ou invalide)",
|
||||
categoria: "cpu-panics",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Critique",
|
||||
logSerial: "Guru Meditation Error: Core 0 panic'ed (LoadProhibited). Exception was unhandled.\nCore 0 register dump:\nPC : 0x400d14bc PS : 0x00060830 A0 : 0x800d1512 A1 : 0x3ffb1f20 \nEXCVADDR: 0x00000000",
|
||||
resumo: "The CPU attempted to read (Load) or write (Store) to an inaccessible or invalid memory address, typically null pointer 0x00000000.",
|
||||
causaRaiz:
|
||||
"This is the classic null pointer dereference or dangling pointer access. The EXCVADDR register shows the faulty memory address: if EXCVADDR is 0x00000000 or near zero (e.g. 0x00000008, a struct offset), code attempted to access members of an uninitialized object or a failed malloc allocation.",
|
||||
gambiarra: {
|
||||
titulo: "Inserting random delays or rebooting in loop without fixing root cause",
|
||||
descricao: "Assuming it is a timing glitch and scattering delay() calls or masking reboots.",
|
||||
consequencia: "The firmware continues crashing intermittently in production whenever the null pointer condition recurs.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Defensive validation and Backtrace decoding",
|
||||
passos: [
|
||||
"Always verify that pointers returned by allocation or lookup functions (malloc, WiFi.client(), JSON parsing, xQueueReceive) are non-NULL before accessing their fields.",
|
||||
"Install 'Espressif Exception Decoder' in your IDE (Arduino IDE / PlatformIO) or run 'xtensa-esp32-elf-addr2line -pfia -e firmware.elf 0x400d14bc' to pinpoint the exact line of code that triggered the crash.",
|
||||
"In ESP-IDF, run 'idf.py monitor' which decodes the call backtrace in real-time.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// DEFENSIVE CODING:
|
||||
struct SensorData {
|
||||
float temperature;
|
||||
float humidity;
|
||||
};
|
||||
|
||||
void processSensor(SensorData* sensor) {
|
||||
// Mandatory check against LoadProhibited:
|
||||
if (sensor == nullptr) {
|
||||
Serial.println("[ERROR] Null sensor pointer!");
|
||||
return;
|
||||
}
|
||||
|
||||
Serial.printf("Temp: %.1f C\\n", sensor->temperature);
|
||||
}`,
|
||||
codigoEspIdf: `// In ESP-IDF, use ESP_RETURN_ON_FALSE or explicit assertions:
|
||||
#include "esp_log.h"
|
||||
#include "esp_check.h"
|
||||
|
||||
static const char* TAG = "SENSOR";
|
||||
|
||||
esp_err_t read_data(char* buffer, size_t max_len) {
|
||||
ESP_RETURN_ON_FALSE(buffer != NULL, ESP_ERR_INVALID_ARG, TAG, "Null buffer supplied!");
|
||||
// Safe operation...
|
||||
return ESP_OK;
|
||||
}`,
|
||||
codigoMicroPython: `# Preventing NoneType exceptions in MicroPython:
|
||||
import json
|
||||
|
||||
def process_sensor(raw_data):
|
||||
if raw_data is None:
|
||||
print("[ERROR] Null data received!")
|
||||
return None
|
||||
|
||||
try:
|
||||
obj = json.loads(raw_data)
|
||||
# Safe lookup with fallback default
|
||||
temperature = obj.get("temp", 0.0)
|
||||
return temperature
|
||||
except (ValueError, AttributeError) as e:
|
||||
print("Error processing payload:", e)
|
||||
return None`,
|
||||
dicaPro: "If EXCVADDR is 0x3fxxxxxx or 0x40xxxxxx but the code crashes, you likely experienced a buffer overflow that corrupted adjacent pointers in RAM.",
|
||||
},
|
||||
{
|
||||
id: "guru-iram-cache",
|
||||
titulo: "Erreur de cache et InstructionFetchError dans les routines d'interruption (ISRs)",
|
||||
categoria: "cpu-panics",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Haute",
|
||||
logSerial: "Guru Meditation Error: Core 0 panic'ed (Cache disabled but cached memory region accessed)\nGuru Meditation Error: Core 0 panic'ed (InstructionFetchError)",
|
||||
resumo: "An interrupt service routine (ISR) tried to execute code or read constants from SPI Flash while the Flash memory controller was disabled for a write or erase operation.",
|
||||
causaRaiz:
|
||||
"By default, ESP32 application code resides in external SPI Flash and is fetched into CPU execution pipeline via internal Instruction Cache. When the ESP32 writes to Flash (such as NVS commits, LittleFS, SPIFFS, or OTA updates), the hardware cache is momentarily disabled. If an ISR fires during this window and its function body resides in Flash, the CPU cannot fetch the instruction and enters an immediate panic.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling all interrupts before writing to Flash",
|
||||
descricao: "Wrapping Flash file operations in indiscriminate noInterrupts() blocks.",
|
||||
consequencia: "Causes dropped sensor pulses, jitter on system timers, and potential watchdog resets.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Allocating ISRs and callback constants in IRAM / DRAM",
|
||||
passos: [
|
||||
"Decorate EVERY hardware interrupt handler with the IRAM_ATTR attribute (e.g., void IRAM_ATTR isrHandler()).",
|
||||
"Ensure any variables or constant strings accessed inside the ISR reside in DRAM (avoid inline string literals in ISR without DRAM_ATTR in ESP-IDF).",
|
||||
"Never call heavy library functions (such as Serial.print or floating-point formatting) inside an interrupt handler.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// ISR properly placed in internal IRAM:
|
||||
volatile uint32_t pulseCount = 0;
|
||||
|
||||
void IRAM_ATTR handleGpioInterrupt() {
|
||||
pulseCount++;
|
||||
}
|
||||
|
||||
void setup() {
|
||||
pinMode(4, INPUT_PULLUP);
|
||||
attachInterrupt(digitalPinToInterrupt(4), handleGpioInterrupt, FALLING);
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF:
|
||||
#include "esp_attr.h"
|
||||
#include "driver/gpio.h"
|
||||
|
||||
static volatile uint32_t pulses = 0;
|
||||
|
||||
// Placed explicitly in IRAM:
|
||||
static void IRAM_ATTR gpio_isr_handler(void* arg) {
|
||||
pulses++;
|
||||
}
|
||||
|
||||
void app_main(void) {
|
||||
gpio_install_isr_service(ESP_INTR_FLAG_IRAM);
|
||||
gpio_isr_handler_add(GPIO_NUM_4, gpio_isr_handler, NULL);
|
||||
}`,
|
||||
codigoMicroPython: `# Safe interrupt handling (ISR) in MicroPython:
|
||||
import micropython
|
||||
from machine import Pin
|
||||
|
||||
# Pre-allocate emergency exception buffer for ISR debugging:
|
||||
micropython.alloc_emergency_exception_buf(100)
|
||||
|
||||
pulse_count = 0
|
||||
|
||||
# Interrupt callback: do NOT allocate memory (no new strings, no new floats)
|
||||
def handle_pulse(pin):
|
||||
global pulse_count
|
||||
pulse_count += 1
|
||||
|
||||
sensor = Pin(4, Pin.IN, Pin.PULL_UP)
|
||||
sensor.irq(trigger=Pin.IRQ_FALLING, handler=handle_pulse)`,
|
||||
dicaPro: "When passing ESP_INTR_FLAG_IRAM in ESP-IDF, every function invoked by the ISR (including FreeRTOS API calls) MUST support IRAM (e.g. xQueueSendFromISR).",
|
||||
},
|
||||
{
|
||||
id: "freertos-twdt",
|
||||
titulo: "Timeout du Task Watchdog Timer (TWDT sur Core 0 ou Core 1)",
|
||||
categoria: "freertos",
|
||||
sintomas: ["bootloop", "wdt-reset"],
|
||||
gravidade: "Critique",
|
||||
logSerial: "E (10532) task_wdt: Task watchdog got triggered. The following tasks/users did not reset the watchdog in time:\nE (10532) task_wdt: - IDLE0 (CPU 0)\nTask watchdog got triggered. System will be reset.",
|
||||
resumo: "A high-priority task entered a busy loop without yielding CPU time, preventing the FreeRTOS IDLE task from feeding the watchdog.",
|
||||
causaRaiz:
|
||||
"FreeRTOS runs an essential priority-0 task called IDLE on each CPU core. The Task Watchdog monitors whether the IDLE task executes periodically (by default, within 5 seconds). If a task with priority >= 1 runs a tight while(1) loop without blocking calls (vTaskDelay, queue reads, semaphores), it starves the IDLE task, triggering an emergency hardware reset.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling Task Watchdog in menuconfig or increasing timeout to 60s",
|
||||
descricao: "Turning off the TWDT to prevent the board from rebooting.",
|
||||
consequencia: "If the firmware encounters an unexpected deadlock or infinite loop, the device freezes permanently and requires manual power cycling.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Event-driven architecture and periodic CPU yield",
|
||||
passos: [
|
||||
"Never write empty busy-wait loops like while(!condition); in FreeRTOS tasks.",
|
||||
"Always insert vTaskDelay(pdMS_TO_TICKS(10)) or wait for events with xQueueReceive(), ulTaskNotifyTake(), or xSemaphoreTake() with a timeout.",
|
||||
"If heavy compute tasks must run continuously, feed the watchdog explicitly via esp_task_wdt_reset().",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// CORRECT ARDUINO FREERTOS PATTERN:
|
||||
void myTask(void *pvParameters) {
|
||||
for (;;) {
|
||||
float sensorValue = analogRead(36);
|
||||
|
||||
// YIELD CPU to FreeRTOS scheduler and IDLE task:
|
||||
vTaskDelay(pdMS_TO_TICKS(100)); // Non-blocking 100ms pause
|
||||
}
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF Task Watchdog pattern:
|
||||
#include "esp_task_wdt.h"
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
|
||||
void compute_task(void *pvParameters) {
|
||||
esp_task_wdt_add(NULL);
|
||||
|
||||
while (1) {
|
||||
// Compute...
|
||||
|
||||
// Feed watchdog during long processing cycles:
|
||||
esp_task_wdt_reset();
|
||||
vTaskDelay(pdMS_TO_TICKS(50));
|
||||
}
|
||||
}`,
|
||||
codigoMicroPython: `# Watchdog and non-blocking tasks with uasyncio in MicroPython:
|
||||
from machine import WDT
|
||||
import uasyncio as asyncio
|
||||
|
||||
wdt = WDT(timeout=5000)
|
||||
|
||||
async def sensor_task():
|
||||
while True:
|
||||
wdt.feed()
|
||||
await asyncio.sleep_ms(100)
|
||||
|
||||
async def main():
|
||||
asyncio.create_task(sensor_task())
|
||||
while True:
|
||||
await asyncio.sleep(1)
|
||||
|
||||
asyncio.run(main())`,
|
||||
dicaPro: "In Arduino, delay(ms) internally calls vTaskDelay. However, delayMicroseconds() or raw compute loops do not yield CPU time and will trigger the TWDT if held for more than a few seconds.",
|
||||
},
|
||||
{
|
||||
id: "freertos-stack-overflow",
|
||||
titulo: "Dépassement de pile de tâche FreeRTOS (Stack Overflow)",
|
||||
categoria: "freertos",
|
||||
sintomas: ["bootloop", "null-pointer"],
|
||||
gravidade: "Critique",
|
||||
logSerial: "Guru Meditation Error: Core 1 panic'ed (Unhandled debug exception).\nDebug exception reason: Stack canary watchpoint triggered (my_task)",
|
||||
resumo: "The task consumed more stack memory than allocated upon creation, corrupting the RTOS protection canary.",
|
||||
causaRaiz:
|
||||
"Each FreeRTOS task is allocated a fixed contiguous memory block for local variables, function arguments, and return addresses. Declaring large arrays on the stack (e.g., char buffer[2048];), heavy JSON documents, or deep call recursions within a default 2048-byte stack overflows the boundary and overwrites adjacent memory.",
|
||||
gambiarra: {
|
||||
titulo: "Assigning 64KB stack blindly to every task",
|
||||
descricao: "Inflating task stack sizes indiscriminately to avoid overflow crashes.",
|
||||
consequencia: "The ~320 KB usable SRAM of the ESP32 is quickly exhausted, leading to out-of-memory errors in Wi-Fi and TLS allocations.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Deliberate stack sizing and HighWaterMark monitoring",
|
||||
passos: [
|
||||
"Measure actual stack consumption using uxTaskGetStackHighWaterMark(). It returns the minimum free stack remaining since task creation.",
|
||||
"Move large buffers from the stack to the heap (using malloc/free) or declare them static outside function scope if reused.",
|
||||
"Tasks running secure TLS/HTTPS or MQTT over SSL connections require at least 6 KB to 8 KB of stack due to MbedTLS cryptographic frame complexity.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// MONITORING TASK STACK IN ARDUINO:
|
||||
void sensorTask(void *pvParameters) {
|
||||
for (;;) {
|
||||
// Task workload...
|
||||
|
||||
UBaseType_t freeStack = uxTaskGetStackHighWaterMark(NULL);
|
||||
Serial.printf("[STACK] Remaining free stack: %d bytes\\n", (int)freeStack);
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(5000));
|
||||
}
|
||||
}
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
// Allocate 4096 bytes (4KB) with safety margin:
|
||||
xTaskCreatePinnedToCore(sensorTask, "sensorTask", 4096, NULL, 1, NULL, 1);
|
||||
}`,
|
||||
codigoEspIdf: `// Enable double stack checking in menuconfig:
|
||||
// Component config -> FreeRTOS -> Set a end of stack check -> Option 2 (Check by Stack Canary)
|
||||
// This catches overflows BEFORE memory structures become silently corrupted at runtime.`,
|
||||
codigoMicroPython: `# Memory and stack inspection in MicroPython:
|
||||
import gc
|
||||
import micropython
|
||||
|
||||
micropython.mem_info()
|
||||
|
||||
gc.collect()
|
||||
print("Free Heap:", gc.mem_free(), "bytes")
|
||||
print("Allocated Heap:", gc.mem_alloc(), "bytes")`,
|
||||
dicaPro: "If a function only processes an HTTP or JSON payload occasionally, allocate the buffer dynamically on the heap during the transaction and free it immediately, rather than permanently inflating task stack.",
|
||||
},
|
||||
{
|
||||
id: "memoria-fragmentacao-heap",
|
||||
titulo: "Fragmentation du tas (Heap Fragmentation) et fuites de mémoire (Memory Leaks)",
|
||||
categoria: "memoria",
|
||||
sintomas: ["random-freeze", "tls-fail"],
|
||||
gravidade: "Haute",
|
||||
logSerial: "E (45892) mbedtls: mbedtls_ssl_setup returned -0x7f00\nE (45892) esp-tls: create_ssl_handle failed\nE (45893) HTTP_CLIENT: Connection failed, out of memory",
|
||||
resumo: "The ESP32 fails to allocate memory despite reporting a seemingly adequate total free heap size.",
|
||||
causaRaiz:
|
||||
"Heap memory becomes fragmented after thousands of allocations and deallocations of varying sizes over time (common when repeatedly concatenating Arduino String objects in loops). Free heap becomes split into tiny isolated chunks. When Wi-Fi or TLS libraries request a single contiguous 40 KB block for an SSL certificate buffer, malloc fails even if 100 KB total free memory exists across disconnected fragments.",
|
||||
gambiarra: {
|
||||
titulo: "Scheduling periodic ESP.restart() every few hours",
|
||||
descricao: "Triggering a daily reboot to reset fragmented memory.",
|
||||
consequencia: "Merely conceals the bug: during traffic spikes the device crashes well ahead of the scheduled reboot.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Eliminate dynamic strings and use pre-allocated static buffers",
|
||||
passos: [
|
||||
"In Arduino, avoid the String class. Use standard C-style character arrays (char buffer[128];) with safe snprintf().",
|
||||
"Monitor fragmentation by comparing total free memory (heap_caps_get_free_size) with the largest contiguous free block (heap_caps_get_largest_free_block).",
|
||||
"In complex ESP-IDF firmware, enable Heap Memory Tracing (CONFIG_HEAP_TRACING) to locate missing free() calls.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// COMPARISON:
|
||||
// ❌ AVOID (Causes severe heap fragmentation):
|
||||
// String json = "{\\"temp\\":";
|
||||
// json += String(temperature) + "}";
|
||||
|
||||
// ✅ RECOMMENDED (Zero heap allocations):
|
||||
char payload[64];
|
||||
snprintf(payload, sizeof(payload), "{\\"temp\\":%.2f,\\"hum\\":%.2f}", temperature, humidity);
|
||||
|
||||
// Health check:
|
||||
Serial.printf("Free Heap: %u | Largest Block: %u\\n",
|
||||
ESP.getFreeHeap(),
|
||||
ESP.getMaxAllocHeap());`,
|
||||
codigoEspIdf: `// Heap monitoring in ESP-IDF:
|
||||
#include "esp_heap_caps.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void inspect_memory(void) {
|
||||
size_t total_free = heap_caps_get_free_size(MALLOC_CAP_8BIT);
|
||||
size_t largest_block = heap_caps_get_largest_free_block(MALLOC_CAP_8BIT);
|
||||
|
||||
ESP_LOGI("HEAP", "Total free: %d bytes | Largest contiguous: %d bytes", total_free, largest_block);
|
||||
}`,
|
||||
codigoMicroPython: `# Preventing heap fragmentation in MicroPython:
|
||||
import gc
|
||||
|
||||
gc.enable()
|
||||
|
||||
# Pre-allocate reusable bytearrays instead of instantiating new strings:
|
||||
rx_buffer = bytearray(256)
|
||||
|
||||
def read_sensor_zero_alloc(stream):
|
||||
bytes_read = stream.readinto(rx_buffer)
|
||||
return rx_buffer[:bytes_read]
|
||||
|
||||
gc.collect()
|
||||
print(f"Free Heap: {gc.mem_free()} B | Allocated: {gc.mem_alloc()} B")`,
|
||||
dicaPro: "If the largest contiguous free block drops below 35 KB to 40 KB, modern HTTPS/TLS connections will fail during the cryptographic handshake.",
|
||||
},
|
||||
{
|
||||
id: "memoria-dma-psram",
|
||||
titulo: "Échec d'allocation DMA en mémoire externe (PSRAM)",
|
||||
categoria: "memoria",
|
||||
sintomas: ["bootloop", "random-freeze"],
|
||||
gravidade: "Haute",
|
||||
logSerial: "E (1204) spi_master: spi_bus_initialize: DMA channel not compatible with external RAM buffer\nESP_ERROR_CHECK failed: esp_err_t 0x102 (ESP_ERR_INVALID_ARG)",
|
||||
resumo: "Firmware attempted to pass a buffer allocated in external PSRAM to a DMA-driven peripheral (SPI, I2S, LCD, SDMMC) that can only access internal SRAM.",
|
||||
causaRaiz:
|
||||
"On ESP32 family chips (especially classic ESP32, ESP32-S2, and ESP32-S3 standard bus), the peripheral DMA engine has no direct physical access to external SPI/QSPI PSRAM. DMA transfers strictly require source and destination buffers to reside in internal SRAM.",
|
||||
gambiarra: {
|
||||
titulo: "Disabling DMA on peripherals",
|
||||
descricao: "Switching SPI/I2S buses to polled CPU transfer mode without DMA.",
|
||||
consequencia: "Throughput plummets and the CPU core stays 100% occupied during display updates or audio streaming.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Explicit allocation with MALLOC_CAP_DMA and MALLOC_CAP_INTERNAL",
|
||||
passos: [
|
||||
"Always allocate DMA buffers using heap_caps_malloc(size, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL).",
|
||||
"Keep heavy non-DMA assets (decoded images, machine learning weights, inactive audio) in PSRAM, copying small frames to internal DMA buffers on demand (ping-pong buffering).",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Allocating DMA buffers in Arduino ESP32:
|
||||
#include <esp_heap_caps.h>
|
||||
|
||||
uint8_t* dmaBuffer = nullptr;
|
||||
|
||||
void setup() {
|
||||
size_t size = 4096;
|
||||
// Guarantees buffer is allocated in DMA-accessible internal SRAM:
|
||||
dmaBuffer = (uint8_t*) heap_caps_malloc(size, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL);
|
||||
|
||||
if (dmaBuffer == nullptr) {
|
||||
Serial.println("[ERROR] Failed to allocate internal DMA buffer!");
|
||||
}
|
||||
}`,
|
||||
codigoEspIdf: `// ESP-IDF:
|
||||
#include "esp_heap_caps.h"
|
||||
|
||||
uint8_t* allocate_spi_buffer(size_t len) {
|
||||
return (uint8_t*) heap_caps_aligned_alloc(4, len, MALLOC_CAP_DMA | MALLOC_CAP_INTERNAL);
|
||||
}`,
|
||||
codigoMicroPython: `# In MicroPython, inspect available PSRAM:
|
||||
import gc
|
||||
import esp32
|
||||
|
||||
print("Total accessible memory in MicroPython:", gc.mem_free() + gc.mem_alloc(), "bytes")
|
||||
buffer_spi = bytearray(1024)`,
|
||||
dicaPro: "On the ESP32-P4, the advanced AXI bus matrix enables DMA into specific external memory regions, but for the ESP32/S2/S3/C3 lines, internal SRAM placement is mandatory.",
|
||||
},
|
||||
{
|
||||
id: "boot-failed-connect",
|
||||
titulo: "Échec de connexion série lors du téléversement (Timed out waiting for packet header)",
|
||||
categoria: "boot-flash",
|
||||
sintomas: ["upload-fail"],
|
||||
gravidade: "Moyenne",
|
||||
logSerial: "A fatal error occurred: Failed to connect to ESP32: Timed out waiting for packet header\nesptool.py v4.6\nConnecting...................",
|
||||
resumo: "The programming tool (esptool / Arduino IDE / PlatformIO) was unable to place the microcontroller into UART bootloader mode.",
|
||||
causaRaiz:
|
||||
"To initiate flashing, the USB-UART bridge (CH340, CP2102, FTDI) toggles DTR and RTS lines to pull GPIO 0 LOW while pulsing EN/RST LOW then HIGH. On many third-party development boards, the RC timing circuit on EN lacks adequate capacitance to hold the reset state during the DTR transition.",
|
||||
gambiarra: {
|
||||
titulo: "Holding the physical BOOT button with your finger at every upload",
|
||||
descricao: "Pressing BOOT/GPIO 0 manually each time the compiler finishes generating binaries.",
|
||||
consequencia: "Inconvenient during rapid prototyping and impossible on sealed boards enclosed in enclosures.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Add a 10 µF capacitor on EN or verify USB data cable",
|
||||
passos: [
|
||||
"Solder a 10 µF (or 1 µF to 10 µF) ceramic or electrolytic capacitor between the EN (RST) and GND pins. This stabilizes the automatic reset ramp.",
|
||||
"Ensure the USB cable has active data lines (D+ and D-). Many cheap charging cables contain only power wires.",
|
||||
"On Linux, confirm your user belongs to the 'dialout' group (sudo usermod -a -G dialout $USER) and that the 'brltty' service is not holding the serial port.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// Command-line verification with esptool:
|
||||
// python -m esptool --port /dev/ttyUSB0 chip_id
|
||||
// If it prints the MAC and chip model, physical communication is working.`,
|
||||
codigoEspIdf: `// In ESP-IDF:
|
||||
// idf.py -p /dev/ttyUSB0 -b 460800 flash
|
||||
// If flashing fails at high speeds, reduce baud rate:
|
||||
// idf.py -p /dev/ttyUSB0 -b 115200 flash`,
|
||||
codigoMicroPython: `# Flashing official MicroPython firmware via terminal:
|
||||
# 1. Erase flash:
|
||||
# esptool.py --port /dev/ttyUSB0 erase_flash
|
||||
|
||||
# 2. Flash binary at safe baud rate:
|
||||
# esptool.py --chip esp32 --port /dev/ttyUSB0 --baud 460800 write_flash -z 0x1000 ESP32_GENERIC-*.bin`,
|
||||
dicaPro: "When using ESP32-S3 or C3 modules with native USB (Direct USB-JTAG), verify that your tooling is configured for the USB CDC/JTAG port rather than a legacy UART bridge.",
|
||||
},
|
||||
{
|
||||
id: "tls-sntp-clock-fail",
|
||||
titulo: "Échec de négociation TLS/HTTPS pour cause d'horloge non synchronisée (Année 1970)",
|
||||
categoria: "conectividade",
|
||||
sintomas: ["tls-fail", "random-freeze"],
|
||||
gravidade: "Haute",
|
||||
logSerial: "E (15420) esp-tls-mbedtls: mbedtls_ssl_handshake returned -0x2700\nE (15420) esp-tls: Failed to verify peer certificate!\nE (15421) esp-tls: Verification info: The certificate is not yet valid (or has expired)",
|
||||
resumo: "Secure HTTPS, AWS IoT, MQTT over TLS, or Web API requests fail because the internal ESP32 RTC defaults to 01/01/1970.",
|
||||
causaRaiz:
|
||||
"Digital certificates (X.509 SSL/TLS) include strict validity windows (Not Before and Not After). Because typical ESP32 boards lack an external RTC battery, the internal clock resets to the Unix epoch (1970) on every cold boot. When MbedTLS checks the server certificate date, it deems it 'not yet valid' (since current dates are decades ahead of 1970), aborting the handshake with error -0x2700 (MBEDTLS_ERR_X509_CERT_VERIFY_FAILED).",
|
||||
gambiarra: {
|
||||
titulo: "Disabling SSL certificate verification (Insecure / No-Verify)",
|
||||
descricao: "Using client.setInsecure() in Arduino or turning off CA validation in ESP-IDF.",
|
||||
consequencia: "Creates a critical security vulnerability: the device is completely exposed to Man-in-the-Middle (MitM) attacks, allowing credentials and firmware to be intercepted.",
|
||||
},
|
||||
solucaoEngenharia: {
|
||||
titulo: "Mandatory SNTP time synchronization prior to opening TLS sockets",
|
||||
passos: [
|
||||
"Immediately after acquiring an IP address, start the SNTP client querying reliable NTP servers (e.g. pool.ntp.org, time.google.com).",
|
||||
"Block outbound HTTPS/MQTT connections until system time is confirmed synchronized.",
|
||||
"Set the correct timezone string so log timestamps match local operational time.",
|
||||
],
|
||||
},
|
||||
codigoArduino: `// SNTP SYNCHRONIZATION BEFORE HTTPS IN ARDUINO:
|
||||
#include <WiFi.h>
|
||||
#include <time.h>
|
||||
|
||||
void syncClock() {
|
||||
configTime(0, 0, "pool.ntp.org", "time.google.com");
|
||||
|
||||
Serial.print("Waiting for NTP time sync");
|
||||
time_t now = time(nullptr);
|
||||
// Year 2024 in Unix timestamp is > 1700000000. If smaller, clock is still in 1970:
|
||||
while (now < 1700000000) {
|
||||
delay(500);
|
||||
Serial.print(".");
|
||||
now = time(nullptr);
|
||||
}
|
||||
Serial.println("\\n[OK] Clock synchronized! TLS handshakes enabled.");
|
||||
}`,
|
||||
codigoEspIdf: `// SNTP in ESP-IDF:
|
||||
#include "esp_sntp.h"
|
||||
#include "esp_log.h"
|
||||
|
||||
void initialize_sntp(void) {
|
||||
ESP_LOGI("SNTP", "Starting SNTP client...");
|
||||
esp_sntp_setoperatingmode(SNTP_OPMODE_POLL);
|
||||
esp_sntp_setservername(0, "pool.ntp.org");
|
||||
esp_sntp_init();
|
||||
}`,
|
||||
codigoMicroPython: `# SNTP synchronization and HTTPS requests in MicroPython:
|
||||
import ntptime
|
||||
import time
|
||||
import urequests
|
||||
|
||||
def sync_and_request():
|
||||
try:
|
||||
print("Synchronizing clock via NTP...")
|
||||
ntptime.host = "pool.ntp.org"
|
||||
ntptime.settime()
|
||||
print("UTC Time synchronized:", time.localtime())
|
||||
|
||||
response = urequests.get("https://api.github.com")
|
||||
print("HTTPS Response:", response.status_code)
|
||||
response.close()
|
||||
except Exception as e:
|
||||
print("[TLS/NTP ERROR]:", e)`,
|
||||
dicaPro: "If operating in isolated local networks without internet access, configure a local NTP server on the gateway router or add a physical DS3231 RTC module over I2C.",
|
||||
},
|
||||
];
|
||||
|
||||
export const regrasDecodificadorLog = [
|
||||
{
|
||||
padrao: /Brownout detector was triggered/i,
|
||||
titulo: "Détecteur de sous-tension (Brownout critique)",
|
||||
tipo: "Alimentation / Matériel",
|
||||
explicacao:
|
||||
"La tension sur le rail 3.3V a chuté sous les limites sécurisées (généralement causé par les pics d'émission RF Wi-Fi/BLE ou une alimentation insuffisante).",
|
||||
acaoRecomendada:
|
||||
"Ajoutez un condensateur à faible ESR de 10 µF à 100 µF sur le rail VCC, vérifiez les câbles d'alimentation et assurez-vous que le régulateur LDO fournit un courant suffisant.",
|
||||
},
|
||||
{
|
||||
padrao: /LoadProhibited|StoreProhibited/i,
|
||||
titulo: "Guru Meditation: Load/StoreProhibited (Pointeur nul ou invalide)",
|
||||
tipo: "Panique CPU / Exception",
|
||||
explicacao:
|
||||
"Tentative de lecture ou d'écriture à une adresse mémoire invalide (généralement déréférencement d'un pointeur nul ou dépassement de tableau).",
|
||||
acaoRecomendada:
|
||||
"Décodez la pile d'appels (Backtrace) avec Exception Decoder ou 'addr2line' pour trouver la ligne exacte. Ajoutez des vérifications défensives 'if (ptr != NULL)'.",
|
||||
},
|
||||
{
|
||||
padrao: /Cache disabled but cached memory region accessed|InstructionFetchError/i,
|
||||
titulo: "Erreur de cache d'interruption (ISR hors IRAM)",
|
||||
tipo: "Panique CPU / Flash",
|
||||
explicacao:
|
||||
"Une routine d'interruption (ISR) a tenté d'exécuter du code depuis la Flash externe pendant que le cache SPI Flash était désactivé pour écriture/effacement.",
|
||||
acaoRecomendada:
|
||||
"Ajoutez le modificateur IRAM_ATTR à la fonction d'interruption et DRAM_ATTR aux constantes/chaînes accédées dans l'ISR.",
|
||||
},
|
||||
{
|
||||
padrao: /Task watchdog got triggered|TWDT/i,
|
||||
titulo: "Timeout du Task Watchdog (Blocage de tâche FreeRTOS)",
|
||||
tipo: "FreeRTOS / Watchdog",
|
||||
explicacao:
|
||||
"Une tâche de haute priorité accapare le processeur sans céder le contrôle, affamant la tâche système IDLE qui réinitialise le watchdog.",
|
||||
acaoRecomendada:
|
||||
"Insérez vTaskDelay(1) ou delay(1) dans les boucles infinies intensives, ou utilisez des files de messages (queues) et sémaphores au lieu de l'attente active.",
|
||||
},
|
||||
{
|
||||
padrao: /Stack canary watchpoint got triggered|Stack overflow/i,
|
||||
titulo: "Dépassement de pile de tâche (Stack Overflow)",
|
||||
tipo: "FreeRTOS / Mémoire de tâche",
|
||||
explicacao:
|
||||
"La tâche a épuisé l'espace de pile alloué lors de sa création, écrasant le marqueur de sécurité (canary).",
|
||||
acaoRecomendada:
|
||||
"Augmentez la taille de pile dans xTaskCreate (ex. : de 2048 à 4096 octets) et déplacez les grands tableaux locaux vers le tas (heap).",
|
||||
},
|
||||
{
|
||||
padrao: /Timed out waiting for packet header|Failed to connect to ESP32/i,
|
||||
titulo: "Échec de connexion série lors du flashage",
|
||||
tipo: "Bootloader / Connexion",
|
||||
explicacao:
|
||||
"L'ordinateur n'a pas réussi à faire passer l'ESP32 en mode programmation (download mode) via les lignes DTR/RTS du port série.",
|
||||
acaoRecomendada:
|
||||
"Connectez un condensateur de 10 µF entre EN et GND, vérifiez que le câble USB transporte les données ou maintenez le bouton BOOT enfoncé lors du branchement.",
|
||||
},
|
||||
{
|
||||
padrao: /The certificate is not yet valid|-0x2700/i,
|
||||
titulo: "Échec de certificat TLS/HTTPS (Horloge en 1970)",
|
||||
tipo: "Connectivité / TLS",
|
||||
explicacao:
|
||||
"L'ESP32 a tenté de valider un certificat HTTPS/TLS avec une horloge interne non synchronisée (époque de 1970).",
|
||||
acaoRecomendada:
|
||||
"Synchronisez l'horloge via le protocole SNTP (configTime sous Arduino ou ntptime sous MicroPython) avant d'initier des requêtes TLS.",
|
||||
},
|
||||
{
|
||||
padrao: /rst:0x1 \(POWERON_RESET\),boot:0x[0-9a-fA-F]+/i,
|
||||
titulo: "Redémarrage sous tension / Échantillonnage des broches de strapping",
|
||||
tipo: "Matériel / Démarrage",
|
||||
explicacao:
|
||||
"Le microcontrôleur a redémarré et échantillonné ses broches de démarrage. S'il se bloque immédiatement, une broche de strapping est tirée au mauvais niveau.",
|
||||
acaoRecomendada:
|
||||
"Vérifiez que les broches de strapping GPIO ne sont pas forcées à des niveaux incorrects par des circuits externes lors de la mise sous tension.",
|
||||
},
|
||||
];
|
||||
export const analisarLogSerial = regrasDecodificadorLog;
|
||||
export const ERROS_COMUNS = errosCatalogo;
|
||||
@@ -0,0 +1,408 @@
|
||||
/**
|
||||
* Base de données structurée et complète des termes techniques du Glossaire ESP32 en français.
|
||||
* Couvre toutes les séries de puces Espressif (ESP32, S2, S3, S31, C2, C3, C5, C6, C61, H2, H4, P4)
|
||||
* et leurs fonctions matérielles, périphériques, radio, sécurité et logicielles.
|
||||
*/
|
||||
|
||||
export const categoriasGlossario = [
|
||||
{
|
||||
"id": "processamento",
|
||||
"nome": "Traitement, CPU & Silicium",
|
||||
"icone": "Cpu",
|
||||
"emoji": "🧠",
|
||||
"cor": "blue",
|
||||
"descricao": "Architectures Xtensa et RISC-V, cœurs, coprocesseurs ULP, accélérateurs vectoriels d'IA et unités à virgule flottante.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Architecture Xtensa vs RISC-V",
|
||||
"definicao": "Jeu d'instructions de base du processeur. L'ESP32 classique, le S2 et le S3 utilisent des cœurs propriétaires Tensilica Xtensa (LX6/LX7). Les séries modernes C (C2, C3, C5, C6, C61), H (H2, H4) et P (P4) adoptent l'architecture ouverte, modulaire et efficace RISC-V (32 bits).",
|
||||
"exemplo": "L'ESP32-S3 utilise Xtensa LX7 dual-core, tandis que l'ESP32-C6 utilise RISC-V single-core et l'ESP32-P4 utilise RISC-V dual-core à 400 MHz."
|
||||
},
|
||||
{
|
||||
"termo": "Cœurs de processeur (Dual-Core vs Single-Core)",
|
||||
"definicao": "Unités centrales de traitement indépendantes. Les puces double cœur permettent de dédier un cœur (Core 0) exclusivement à la radio Wi-Fi/Bluetooth et à l'ordonnancement de FreeRTOS, laissant le second cœur (Core 1) 100% disponible pour l'application et les calculs de l'utilisateur.",
|
||||
"exemplo": "ESP32, ESP32-S3 et ESP32-P4 sont dual-core ; ESP32-S2, C2, C3, C6 et H2 sont single-core."
|
||||
},
|
||||
{
|
||||
"termo": "Fréquence d'horloge (MHz)",
|
||||
"definicao": "Vitesse de traitement mesurée en mégahertz (MHz). L'ESP-IDF ajuste dynamiquement la fréquence (Dynamic Frequency Scaling - DFS) pour économiser l'énergie lors des périodes d'inactivité.",
|
||||
"exemplo": "L'ESP32-C2 fonctionne jusqu'à 120 MHz ; ESP32, S2, S3 et C6 atteignent 160/240 MHz ; et l'ESP32-P4 atteint 400 MHz."
|
||||
},
|
||||
{
|
||||
"termo": "ULP (Coprocesseur à ultra basse consommation)",
|
||||
"definicao": "Processeur secondaire indépendant à ultra basse consommation capable de continuer à exécuter des instructions, lire des capteurs analogiques (ADC), I2C et broches GPIO pendant que les cœurs principaux restent éteints en Deep Sleep.",
|
||||
"exemplo": "L'ESP32 classique intègre un ULP FSM ; ESP32-S2, S3 et C6 disposent d'un ULP RISC-V programmable en C ; l'ESP32-P4 dispose d'un ULP basse consommation dédié."
|
||||
},
|
||||
{
|
||||
"termo": "Extensions vectorielles d'IA (Vector Extension / ESP-NN)",
|
||||
"definicao": "Instructions matérielles spécialisées exécutant des opérations mathématiques vectorielles et matricielles sur des entiers (int8/int16) en parallèle, accélérant les réseaux neuronaux convolutifs (CNN) et le traitement du signal.",
|
||||
"exemplo": "ESP32-S3 et ESP32-P4 accélèrent les inférences de reconnaissance faciale, la détection vocale et les modèles TensorFlow Lite for Microcontrollers."
|
||||
},
|
||||
{
|
||||
"termo": "FPU (Unité à virgule flottante)",
|
||||
"definicao": "Unité de traitement à virgule flottante matérielle effectuant des additions, multiplications et divisions sur nombres décimaux (float) en un cycle d'horloge unique, sans pénalité d'émulation logicielle.",
|
||||
"exemplo": "Présente sur les cœurs Xtensa des ESP32 et ESP32-S3, ainsi que sur les cœurs RISC-V haute performance de l'ESP32-P4."
|
||||
},
|
||||
{
|
||||
"termo": "PPA (Pixel Processing Accelerator)",
|
||||
"definicao": "Accélérateur graphique 2D matériel exclusif à l'ESP32-P4 pour la manipulation accélérée d'images : rotation de trames, mise à l'échelle (scaling), fusion alpha (alpha blending) et conversion d'espaces colorimétriques (RGB565, ARGB8888, YUV420).",
|
||||
"exemplo": "Rendu d'interfaces graphiques complexes (LVGL) à 60 FPS sans surcharger les cœurs de processeur principaux."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "seguranca",
|
||||
"nome": "Sécurité, Cryptographie & eFuses",
|
||||
"icone": "ShieldCheck",
|
||||
"emoji": "🔒",
|
||||
"cor": "red",
|
||||
"descricao": "Secure Boot v2, chiffrement Flash sur silicium, eFuses irréversibles, signature numérique matérielle et isolation TEE.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "eFuse (Fusibles électroniques)",
|
||||
"definicao": "Fusibles microscopiques programmables une seule fois (One-Time Programmable - OTP) gravés dans le silicium. Utilisés pour stocker de façon irréversible les clés de chiffrement matérielles, adresses MAC d'usine et réglages de sécurité.",
|
||||
"exemplo": "Le verrouillage des eFuses désactive définitivement le téléchargement ROM non sécurisé et protège la clé de chiffrement Flash."
|
||||
},
|
||||
{
|
||||
"termo": "Secure Boot (V1 et V2)",
|
||||
"definicao": "Mécanisme matériel garantissant que seul un micrologiciel signé avec une clé cryptographique privée approuvée (RSA-3072 ou ECDSA-V2) peut démarrer sur le SoC. Empêche l'exécution de code malveillant ou non autorisé.",
|
||||
"exemplo": "ESP32 prend en charge Secure Boot v1/v2 ; ESP32-S2, S3, C3, C6, H2 et P4 utilisent exclusivement Secure Boot v2 basé sur RSA-3072 / ECDSA."
|
||||
},
|
||||
{
|
||||
"termo": "Chiffrement Flash (Flash Encryption)",
|
||||
"definicao": "Chiffrement transparent au vol (on-the-fly) du contenu de la mémoire Flash externe utilisant l'algorithme AES-XTS (128 ou 256 bits). La clé de chiffrement est stockée dans les eFuses et protégée contre toute lecture logicielle.",
|
||||
"exemplo": "La lecture physique de la puce Flash avec un programmateur externe ne révèle que des données chiffrées indéchiffrables."
|
||||
},
|
||||
{
|
||||
"termo": "Key Manager",
|
||||
"definicao": "Périphérique matériel de gestion de clés sur les SoCs ESP32 récents (ESP32-C6, C61, P4) permettant de stocker, dériver et contrôler l'accès aux clés cryptographiques de manière sécurisée sans exposition dans la mémoire vive accessible au CPU.",
|
||||
"exemplo": "Dérivation de clés de session pour TLS et chiffrement de données avec protection matérielle contre l'extraction en mémoire."
|
||||
},
|
||||
{
|
||||
"termo": "ECC et ECDSA matériels",
|
||||
"definicao": "Accélérateur matériel pour la cryptographie sur courbes elliptiques (ECC) et les signatures numériques (ECDSA) sur les courbes P-192 et P-256. Accélère drastiquement les poignées de main sécurisées (TLS / DTLS) et le protocole Matter.",
|
||||
"exemplo": "Authentification des nœuds Matter et génération de signatures cryptographiques sans ralentir le CPU principal."
|
||||
},
|
||||
{
|
||||
"termo": "HMAC et Signature Numérique (DS)",
|
||||
"definicao": "Blocs matériels permettant d'effectuer des calculs HMAC et des signatures numériques RSA sans que la clé secrète ne soit jamais chargée dans la RAM du processeur.",
|
||||
"exemplo": "Authentification sécurisée avec les plateformes cloud via mTLS sans risque de fuite de clé privée."
|
||||
},
|
||||
{
|
||||
"termo": "TRNG (Générateur de nombres aléatoires véritables)",
|
||||
"definicao": "Générateur matériel de nombres aléatoires basé sur le bruit thermique et les signaux radio du récepteur Wi-Fi/Bluetooth. Fournit une entropie physique indispensable pour les protocoles cryptographiques sécurisés.",
|
||||
"exemplo": "Génération de clés de session, vecteurs d'initialisation (IV) et nonces pour TLS et WPA3."
|
||||
},
|
||||
{
|
||||
"termo": "Protection contre le DPA (Differential Power Analysis)",
|
||||
"definicao": "Contre-mesures matérielles intégrées dans les moteurs cryptographiques (AES/RSA) pour masquer les variations de consommation électrique et éviter les attaques par canaux auxiliaires lors des calculs.",
|
||||
"exemplo": "Présente sur les SoCs ESP32-S3, C3, C6, H2 et P4 pour résister aux attaques matérielles en laboratoire."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "memoria",
|
||||
"nome": "Mémoire, Bus & Stockage",
|
||||
"icone": "Database",
|
||||
"emoji": "💾",
|
||||
"cor": "purple",
|
||||
"descricao": "SRAM interne, bus SPI et octal pour Flash externe, PSRAM haute vitesse, mémoire cache et mappage MMU.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "SRAM interne (Static RAM)",
|
||||
"definicao": "Mémoire vive statique ultra-rapide intégrée directement au silicium de la puce, accessible en un cycle de processeur pour l'exécution des instructions (IRAM) et le stockage des données dynamiques (DRAM).",
|
||||
"exemplo": "ESP32 dispose de 520 Ko de SRAM ; ESP32-S3 de 512 Ko ; ESP32-C3 de 400 Ko ; ESP32-C6 de 512 Ko ; et ESP32-P4 de 768 Ko."
|
||||
},
|
||||
{
|
||||
"termo": "ROM de démarrage (Boot ROM)",
|
||||
"definicao": "Mémoire morte gravée d'usine dans le silicium contenant le code initial de premier niveau (First-Stage Bootloader). Elle initialise les horloges minimales, lit les eFuses et charge le bootloader secondaire depuis la mémoire Flash.",
|
||||
"exemplo": "Prend en charge le mode téléchargement (Download Mode) via UART ou USB pour la programmation initiale du firmware."
|
||||
},
|
||||
{
|
||||
"termo": "Flash SPI (Quad-SPI vs Octal-SPI)",
|
||||
"definicao": "Mémoire de stockage non volatile externe ou intégrée dans le boîtier où résident le micrologiciel, les tables de partitions et les données de l'application. Quad-SPI utilise 4 lignes de données, tandis qu'Octal-SPI en utilise 8, doublant le débit.",
|
||||
"exemplo": "L'ESP32-S3 et l'ESP32-P4 prennent en charge la Flash Octal-SPI à 120 MHz en mode OPI DDR."
|
||||
},
|
||||
{
|
||||
"termo": "PSRAM (Pseudo-Static RAM externe)",
|
||||
"definicao": "Mémoire RAM dynamique externe interfacée via bus SPI/QPI/OPI qui se comporte logiquement comme de la SRAM statique grâce à des contrôleurs de rafraîchissement internes. Indispensable pour le streaming audio, le traitement d'images et les interfaces graphiques.",
|
||||
"exemplo": "Modules ESP32-WROVER (4/8 Mo de PSRAM Quad) et ESP32-S3-WROOM-1 (jusqu'à 16 Mo de PSRAM Octal)."
|
||||
},
|
||||
{
|
||||
"termo": "SRAM RTC Fast et Slow",
|
||||
"definicao": "Zones de mémoire SRAM situées dans le domaine d'alimentation RTC (Real-Time Clock) qui restent sous tension et conservent leurs données pendant les modes de veille profonde (Deep Sleep).",
|
||||
"exemplo": "RTC Fast (8 Ko) permet l'exécution rapide de code par le coprocesseur ULP ; RTC Slow (8 Ko) conserve des variables d'état et des compteurs."
|
||||
},
|
||||
{
|
||||
"termo": "Allocation DMA (MALLOC_CAP_DMA)",
|
||||
"definicao": "Capacité d'allocation de mémoire dans une région SRAM physique compatible avec l'accès direct en mémoire (DMA) des périphériques (SPI, I2S, LCD, ADC) sans faire transiter les octets par le processeur.",
|
||||
"exemplo": "Utilisation de heap_caps_malloc(taille, MALLOC_CAP_DMA) pour transférer des tampons graphiques vers un écran SPI à haute vitesse."
|
||||
},
|
||||
{
|
||||
"termo": "Fragmentation du tas (Heap Fragmentation)",
|
||||
"definicao": "Phénomène où la mémoire vive libre disponible est divisée en de multiples petits blocs discontinus, rendant impossible l'allocation d'un bloc contigu de taille moyenne malgré une mémoire totale apparemment suffisante.",
|
||||
"exemplo": "Évitez les allocations/désallocations répétées de chaînes en boucle ; privilégiez des tampons pré-alloués de taille fixe."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "conectividade",
|
||||
"nome": "Connectivité Sans Fil & Protocoles",
|
||||
"icone": "Wifi",
|
||||
"emoji": "📡",
|
||||
"cor": "emerald",
|
||||
"descricao": "Wi-Fi 4/6, Bluetooth 5.x BLE, radio IEEE 802.15.4 (Zigbee / Thread), standard Matter et ESP-NOW sans routeur.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Wi-Fi 6 (802.11ax)",
|
||||
"definicao": "Norme Wi-Fi moderne apportant des améliorations majeures en efficacité spectrale, latence et autonomie énergétique dans les environnements à forte densité d'objets connectés grâce aux technologies OFDMA et Target Wake Time (TWT).",
|
||||
"exemplo": "Pris en charge nativement sur les SoCs ESP32-C6 et ESP32-C5 (2.4 GHz et 5 GHz)."
|
||||
},
|
||||
{
|
||||
"termo": "Wi-Fi Dual-Band (2.4 GHz et 5 GHz)",
|
||||
"definicao": "Capacité radio à fonctionner à la fois sur la bande classique de 2.4 GHz (plus longue portée) et sur la bande de 5 GHz (débit supérieur et moins encombrée par les interférences).",
|
||||
"exemplo": "L'ESP32-C5 est le premier SoC d'Espressif à intégrer une radio Wi-Fi 6 Dual-Band complète."
|
||||
},
|
||||
{
|
||||
"termo": "OFDMA (Accès multiple par répartition en fréquences orthogonales)",
|
||||
"definicao": "Technologie clé du Wi-Fi 6 qui divise un canal radio en sous-canaux appelés Resource Units (RU), permettant à un point d'accès de communiquer simultanément avec plusieurs dispositifs IoT sans collision de trames.",
|
||||
"exemplo": "Réduit considérablement la latence réseau sur les réseaux domotiques comptant des dizaines de capteurs ESP32-C6."
|
||||
},
|
||||
{
|
||||
"termo": "TWT (Target Wake Time)",
|
||||
"definicao": "Fonctionnalité d'économie d'énergie de la norme Wi-Fi 6 permettant au dispositif IoT et au routeur de convenir d'heures précises de réveil pour échanger des données, permettant à la radio de rester éteinte pendant de longues périodes.",
|
||||
"exemplo": "Permet à des capteurs ESP32-C6 alimentés par pile de fonctionner pendant plusieurs années sur une seule charge."
|
||||
},
|
||||
{
|
||||
"termo": "Bluetooth Classic (BR/EDR)",
|
||||
"definicao": "Standard Bluetooth d'origine optimisé pour les transmissions continues de données à débit moyen et le streaming audio sans fil via le profil A2DP.",
|
||||
"exemplo": "Présent sur l'ESP32 d'origine pour les enceintes audio Bluetooth et les communications série SPP."
|
||||
},
|
||||
{
|
||||
"termo": "Bluetooth Low Energy (BLE 5.0 à 5.4)",
|
||||
"definicao": "Protocole sans fil ultra basse consommation conçu pour les objets connectés autonomes. Les révisions 5.0+ introduisent le débit 2 Mbps, la longue portée (Coded PHY) et les annonces étendues.",
|
||||
"exemplo": "Pris en charge sur toutes les séries modernes ESP32-S3, C3, C6, H2 et C5."
|
||||
},
|
||||
{
|
||||
"termo": "Bluetooth LE Audio et Auracast",
|
||||
"definicao": "Nouvelle génération audio Bluetooth basée sur le codec LC3 et le transport BLE, apportant une qualité audio supérieure, une consommation réduite et la diffusion broadcast Auracast.",
|
||||
"exemplo": "Pris en charge sur l'ESP32-H4 pour les récepteurs audio et dispositifs d'assistance d'écoute."
|
||||
},
|
||||
{
|
||||
"termo": "IEEE 802.15.4 (Zigbee 3.0 et Thread)",
|
||||
"definicao": "Standard radio basse consommation pour réseaux maillés (Mesh). Sert de couche physique aux protocoles Zigbee 3.0 et Thread, assurant l'interopérabilité domotique sans dépendance au Wi-Fi.",
|
||||
"exemplo": "Pris en charge nativement sur les SoCs ESP32-H2 et ESP32-C6."
|
||||
},
|
||||
{
|
||||
"termo": "Matter (Standard unifié pour maison connectée)",
|
||||
"definicao": "Protocole d'application domotique ouvert soutenu par la Connectivity Standards Alliance (CSA), permettant l'interopérabilité directe entre Apple Home, Google Home, Alexa et SmartThings.",
|
||||
"exemplo": "Fonctionne sur Matter over Wi-Fi (ESP32, S3, C3, C6) et Matter over Thread (ESP32-H2, C6)."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "perifericos",
|
||||
"nome": "Entrées, Sorties & Périphériques",
|
||||
"icone": "Sliders",
|
||||
"emoji": "🔌",
|
||||
"cor": "amber",
|
||||
"descricao": "Broches GPIO, matrice GPIO Matrix, convertisseurs ADC et DAC, capteurs tactiles capacitifs, UART, SPI, I2C, I2S et PWM.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "GPIO (Entrées et sorties à usage général)",
|
||||
"definicao": "Broches physiques du microcontrôleur configurables individuellement comme entrées ou sorties numériques, avec résistances de pull-up/pull-down internes et interruptions matérielles.",
|
||||
"exemplo": "Lecture de boutons-poussoirs, commande de relais et signalisation d'état par LED."
|
||||
},
|
||||
{
|
||||
"termo": "Broches de strapping (Strapping Pins)",
|
||||
"definicao": "Broches spéciales échantillonnées par la ROM matérielle lors du reset pour déterminer le mode de démarrage : boot Flash SPI normal, téléchargement UART/USB ou réglage de la tension VDD_SDIO.",
|
||||
"exemplo": "GPIO0 doit être tiré à la masse (0) pour entrer en mode programmation, ou maintenu au niveau haut (1) pour un démarrage normal."
|
||||
},
|
||||
{
|
||||
"termo": "ADC (Convertisseur analogique-numérique)",
|
||||
"definicao": "Périphérique matériel convertissant une tension analogique continue en valeur numérique discrète sur 12 bits (0 à 4095). Dispose de canaux répartis sur deux blocs : ADC1 et ADC2.",
|
||||
"exemplo": "Mesure de tensions de batteries, capteurs de lumière (LDR) et potentiomètres."
|
||||
},
|
||||
{
|
||||
"termo": "DAC (Convertisseur numérique-analogique)",
|
||||
"definicao": "Convertisseur matériel transformant une valeur numérique de 8 bits en une tension analogique correspondante sur une broche de sortie dédiée.",
|
||||
"exemplo": "Disponible sur les broches GPIO25 et GPIO26 de l'ESP32 d'origine pour générer des signaux sonores simples et des formes d'onde."
|
||||
},
|
||||
{
|
||||
"termo": "LEDC (Contrôleur LED PWM)",
|
||||
"definicao": "Générateur PWM matériel à haute résolution (jusqu'à 16 bits) doté de canaux indépendants et d'un contrôle automatique de fondu progressif de luminosité (fade hardware).",
|
||||
"exemplo": "Variateurs d'intensité lumineuse pour rubans LED RGB/RGBW et servomoteurs standards."
|
||||
},
|
||||
{
|
||||
"termo": "MCPWM (PWM pour contrôle moteur)",
|
||||
"definicao": "Périphérique PWM spécialisé pour le contrôle de moteurs électriques, d'onduleurs de puissance et de ponts en H avec insertion automatique de temps mort (dead-time) et entrées de capture de fautes.",
|
||||
"exemplo": "Pilotage précis de moteurs brushless (BLDC) et servomoteurs industriels sur ESP32 et ESP32-S3."
|
||||
},
|
||||
{
|
||||
"termo": "RMT (Périphérique de télécommande)",
|
||||
"definicao": "Transmetteur et récepteur de signaux d'impulsions infrarouges ou numériques de précision nanoseconde sans solliciter le processeur.",
|
||||
"exemplo": "Idéal pour contrôler des rubans LED adressables WS2812B/NeoPixel et décoder les télécommandes infrarouges NEC/RC-5."
|
||||
},
|
||||
{
|
||||
"termo": "PCNT (Compteur d'impulsions)",
|
||||
"definicao": "Compteur matériel indépendant surveillant les fronts montants et descendants de signaux externes, avec filtrage des rebonds et décodage en quadrature.",
|
||||
"exemplo": "Lecture d'encodeurs rotatifs optiques et capteurs de débit d'eau sans générer d'interruptions CPU récurrentes."
|
||||
},
|
||||
{
|
||||
"termo": "TWAI® (Two-Wire Automotive Interface / Bus CAN)",
|
||||
"definicao": "Contrôleur matériel conforme au standard CAN 2.0B (Controller Area Network) pour les communications différentielles robustes en milieu automobile et industriel.",
|
||||
"exemplo": "Lecture de la prise de diagnostic OBD-II de véhicules et communication avec automates industriels."
|
||||
},
|
||||
{
|
||||
"termo": "Broches tactiles capacitives (Touch)",
|
||||
"definicao": "Broches physiques intégrant des circuits de mesure capacitive pour détecter le contact ou l'approche du doigt humain sans composants externes.",
|
||||
"exemplo": "Touches sensitives étanches et curseurs tactiles intégrés dans des boîtiers plastiques."
|
||||
},
|
||||
{
|
||||
"termo": "PARLIO (Contrôleur d'E/S parallèles)",
|
||||
"definicao": "Périphérique d'E/S parallèle à haute vitesse présent sur les séries récentes (ESP32-C6, P4) permettant l'émission et la réception cadencées de données numériques sur plusieurs bits avec horloge dédiée.",
|
||||
"exemplo": "Interfaçage de capteurs rapides, écrans spécifiques et modems propriétaires."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "multimidia",
|
||||
"nome": "Multimédia, USB & Interfaces Avancées",
|
||||
"icone": "Sparkles",
|
||||
"emoji": "✨",
|
||||
"cor": "pink",
|
||||
"descricao": "USB OTG natif, USB Serial/JTAG, interfaces MIPI DSI et CSI pour écrans et caméras, accélérateur graphique PPA et Ethernet MAC.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "USB OTG (On-The-Go) natif",
|
||||
"definicao": "Contrôleur USB matériel intégré permettant au SoC de fonctionner aussi bien en tant que périphérique (Device : clavier, souris, stockage) qu'en tant qu'hôte (Host : lecture de clés USB ou manettes).",
|
||||
"exemplo": "Présent sur ESP32-S2 et ESP32-S3 (Full-Speed 12 Mbps) et ESP32-P4 (High-Speed 480 Mbps)."
|
||||
},
|
||||
{
|
||||
"termo": "USB Série/JTAG natif",
|
||||
"definicao": "Périphérique matériel dédié intégré au silicium fournissant un port série virtuel (CDC) et une interface de débogage JTAG complète directement sur les broches D+/D- sans convertisseur externe (type CP2102 ou CH340).",
|
||||
"exemplo": "Téléversement de firmware et débogage pas à pas dans VS Code sur ESP32-C3, S3, C6, H2 et P4."
|
||||
},
|
||||
{
|
||||
"termo": "USB 2.0 High-Speed (480 Mbps)",
|
||||
"definicao": "Interface USB haute vitesse offrant un débit de transfert de données jusqu'à 480 Mbit/s, indispensable pour la capture vidéo, les caméras UVC et les transferts massifs de données.",
|
||||
"exemplo": "Présente nativement avec couche physique intégrée (PHY) sur le SoC ESP32-P4."
|
||||
},
|
||||
{
|
||||
"termo": "MIPI CSI et MIPI DSI",
|
||||
"definicao": "Interfaces de bus différentiels série haute vitesse normalisées par la Mobile Industry Processor Interface pour relier des capteurs de caméra (CSI) et des écrans graphiques haute résolution (DSI).",
|
||||
"exemplo": "ESP32-P4 intègre MIPI CSI 2 lignes (caméras haute définition) et MIPI DSI 2 lignes (écrans tactiles 1080p)."
|
||||
},
|
||||
{
|
||||
"termo": "Encodeur vidéo matériel H.264",
|
||||
"definicao": "Moteur matériel dédié capable de compresser des flux vidéo bruts au format standard H.264 (AVC) en temps réel avec un minimum de charge processeur.",
|
||||
"exemplo": "Encodage vidéo jusqu'à 1080p à 30 FPS sur le processeur multimédia ESP32-P4."
|
||||
},
|
||||
{
|
||||
"termo": "Ethernet MAC 10/100 Mbps",
|
||||
"definicao": "Contrôleur de couche d'accès réseau (MAC) intégré conforme IEEE 802.3, nécessitant seulement un émetteur-récepteur physique externe (PHY RMII comme LAN8720 ou IP101) pour une connexion réseau filaire.",
|
||||
"exemplo": "Présent sur l'ESP32 d'origine et l'ESP32-P4 pour des passerelles réseau professionnelles et installations industrielles."
|
||||
},
|
||||
{
|
||||
"termo": "Interface caméra DVP (8 bits / 16 bits)",
|
||||
"definicao": "Interface parallèle de vision numérique (Digital Video Port) utilisant un bus de données 8 ou 16 bits cadencé par une horloge pixel (PCLK) pour capturer des images depuis des capteurs optiques standard.",
|
||||
"exemplo": "Connexion des capteurs OV2640 et OV5640 sur cartes ESP32-CAM et ESP32-S3."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "energia",
|
||||
"nome": "Gestion de l'Énergie & Modes de Veille",
|
||||
"icone": "BatteryCharging",
|
||||
"emoji": "🔋",
|
||||
"cor": "teal",
|
||||
"descricao": "Modes Deep Sleep, Light Sleep, domaine RTC basse consommation, DFS (Dynamic Frequency Scaling) et circuit Brownout.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Mode actif (Active Mode)",
|
||||
"definicao": "État de fonctionnement nominal où tous les cœurs de processeur, périphériques et radios sont allumés. La consommation varie généralement entre 40 mA et 240 mA selon les émetteurs radio activés.",
|
||||
"exemplo": "Transmission active de données via Wi-Fi ou traitement d'images haute performance."
|
||||
},
|
||||
{
|
||||
"termo": "Modem Sleep",
|
||||
"definicao": "Mode où le processeur reste actif et exécute le programme utilisateur, mais où la radio Wi-Fi ou Bluetooth est coupée entre les intervalles de communication DTIM.",
|
||||
"exemplo": "La consommation baisse à environ 15 à 30 mA tout en maintenant la connexion au routeur Wi-Fi."
|
||||
},
|
||||
{
|
||||
"termo": "Light Sleep",
|
||||
"definicao": "Mode de veille intermédiaire où la plupart des horloges numériques et le CPU sont suspendus, mais où la mémoire SRAM reste alimentée. Le réveil est quasi instantané (moins d'une milliseconde).",
|
||||
"exemplo": "Consommation réduite à moins de 1 à 2 mA avec réveil sur minuteur, broche GPIO ou activité UART."
|
||||
},
|
||||
{
|
||||
"termo": "Deep Sleep",
|
||||
"definicao": "Mode de veille profonde où la CPU, la radio et la majeure partie de la SRAM sont éteintes. Seul le domaine RTC reste alimenté pour surveiller les sources de réveil.",
|
||||
"exemplo": "Consommation ultra faible de 5 à 150 µA, idéale pour les stations météo et capteurs IoT sur pile."
|
||||
},
|
||||
{
|
||||
"termo": "Hibernation (Hibernation Mode)",
|
||||
"definicao": "Mode de consommation minimale absolue où même le quartz et la SRAM RTC Fast sont coupés. Seul le minuteur RTC Slow ou une broche d'activation externe peut réveiller le microcontrôleur.",
|
||||
"exemplo": "Consommation descendant jusqu'à moins de 5 µA sur l'ESP32 d'origine et l'ESP32-C3."
|
||||
},
|
||||
{
|
||||
"termo": "Sources de réveil (Wakeup Sources)",
|
||||
"definicao": "Événements matériels configurés pour réveiller le SoC d'un mode de veille (Light Sleep ou Deep Sleep) : minuteur RTC, changement de niveau sur broche GPIO (ext0/ext1), capteur tactile capacitif ou coprocesseur ULP.",
|
||||
"exemplo": "Réveil automatique toutes les 15 minutes pour transmettre un relevé de température, puis retour immédiat en veille."
|
||||
},
|
||||
{
|
||||
"termo": "Détecteur de sous-tension (Brownout Detector)",
|
||||
"definicao": "Circuit matériel de surveillance de la tension d'alimentation interne qui déclenche une réinitialisation propre si la tension chute sous un seuil critique, protégeant la Flash contre la corruption de données.",
|
||||
"exemplo": "Déclenche le message d'erreur 'Brownout detector was triggered' lors d'un appel de courant trop important sur une alimentation insuffisante."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "desenvolvimento",
|
||||
"nome": "Firmware, Démarrage & Système d'Exploitation",
|
||||
"icone": "Code2",
|
||||
"emoji": "🚀",
|
||||
"cor": "rose",
|
||||
"descricao": "Séquence de boot, broches de strapping, système de partitionnement, mises à jour OTA avec rollback, FreeRTOS SMP et ESP Component Registry.",
|
||||
"termos": [
|
||||
{
|
||||
"termo": "Bootloader (Premier et second niveau)",
|
||||
"definicao": "Chaîne logicielle de démarrage : la ROM interne (1er niveau) initialise le matériel de base puis charge le bootloader secondaire depuis la Flash, qui analyse la table de partitions et lance l'application sélectionnée.",
|
||||
"exemplo": "Prend en charge la vérification cryptographique des images lors de l'activation du Secure Boot."
|
||||
},
|
||||
{
|
||||
"termo": "FreeRTOS (Système d'exploitation temps réel)",
|
||||
"definicao": "Noyau temps réel préemptif adapté par Espressif pour la gestion multi-cœur symétrique (SMP), ordonnançant les tâches, files d'attente (queues), sémaphores et minuteurs logiciels.",
|
||||
"exemplo": "Permet d'exécuter simultanément une tâche de lecture de capteurs sur le Core 1 et la pile réseau Wi-Fi sur le Core 0."
|
||||
},
|
||||
{
|
||||
"termo": "Attributs IRAM_ATTR et DRAM_ATTR",
|
||||
"definicao": "Directives de compilation forçant le placement d'une fonction dans la mémoire d'instructions rapide (IRAM) ou d'une constante dans la mémoire de données (DRAM) plutôt que dans la Flash externe.",
|
||||
"exemplo": "Obligatoire pour les routines de service d'interruption (ISR) exécutées pendant les opérations d'écriture en Flash SPI."
|
||||
},
|
||||
{
|
||||
"termo": "Table de partitions (partitions.csv)",
|
||||
"definicao": "Fichier de configuration décrivant la disposition de la mémoire Flash externe : partitions pour le bootloader, les données NVS, les images d'application (ota_0, ota_1) et les systèmes de fichiers (LittleFS).",
|
||||
"exemplo": "Permet de configurer deux banques d'application pour des mises à jour OTA sécurisées avec possibilité de retour arrière."
|
||||
},
|
||||
{
|
||||
"termo": "Mises à jour OTA avec retour arrière (Rollback)",
|
||||
"definicao": "Mise à niveau du firmware à distance par Wi-Fi ou Ethernet. Si la nouvelle version plante ou échoue à valider son état fonctionnel (esp_ota_mark_app_valid_cancel_rollback), le système bascule automatiquement sur la version précédente saine.",
|
||||
"exemplo": "Évite de rendre un dispositif inaccessible sur le terrain lors d'une mise à jour logicielle défectueuse."
|
||||
},
|
||||
{
|
||||
"termo": "NVS (Non-Volatile Storage) et chiffrement NVS",
|
||||
"definicao": "Bibliothèque intégrée de stockage clé-valeur dans une partition Flash dédiée pour conserver les identifiants Wi-Fi, calibrages et réglages utilisateur, avec prise en charge du chiffrement par clé matérielle.",
|
||||
"exemplo": "Stockage sécurisé des identifiants réseau et certificats de connexion cloud d'un objet connecté."
|
||||
},
|
||||
{
|
||||
"termo": "Systèmes de fichiers (LittleFS et SPIFFS)",
|
||||
"definicao": "Systèmes de fichiers embarqués optimisés pour mémoires Flash NOR avec mécanismes d'égalisation d'usure (wear leveling). LittleFS est plus moderne, plus résilient aux coupures de courant et nettement plus rapide que SPIFFS.",
|
||||
"exemplo": "Stockage de fichiers HTML, CSS et JavaScript pour servir une interface web locale depuis l'ESP32."
|
||||
},
|
||||
{
|
||||
"termo": "JTAG et OpenOCD",
|
||||
"definicao": "Protocole matériel et logiciel de débogage sur puce permettant d'insérer des points d'arrêt matériels (breakpoints), d'inspecter les variables en temps réel et de tracer l'exécution du code dans VS Code.",
|
||||
"exemplo": "Débogage matériel direct via le port USB Série/JTAG interne sur les SoCs récents (ESP32-S3, C3, C6, P4)."
|
||||
}
|
||||
]
|
||||
}
|
||||
];
|
||||
@@ -0,0 +1,176 @@
|
||||
/**
|
||||
* Connaissances métier pour la recherche intelligente en français.
|
||||
*
|
||||
* Sans dépendances ni alias d'importation : s'exécute côté serveur (construction de l'index),
|
||||
* dans le navigateur (interprétation de la requête) et dans les scripts de test Node.
|
||||
*
|
||||
* Tous les termes de `termos` sont déjà normalisés (minuscules, sans accents).
|
||||
*/
|
||||
|
||||
export const normalizar = (s = "") =>
|
||||
String(s)
|
||||
.toLowerCase()
|
||||
.replace(/œ/g, "oe")
|
||||
.replace(/æ/g, "ae")
|
||||
.replace(/['’]/g, "'")
|
||||
.normalize("NFD")
|
||||
.replace(/[\u0300-\u036f]/g, "");
|
||||
|
||||
/**
|
||||
* Reconnaît les broches occupées par la flash/PSRAM selon la description du schéma.
|
||||
* "forte": la broche est consommée par la mémoire (ou constitue son alimentation).
|
||||
* "fraco": seulement affectée dans certains modes (ex. : SPI octal 8 lignes).
|
||||
*/
|
||||
const nivelMemoria = (palavra) => (p) => {
|
||||
const citam = p._avs.filter((a) => a.includes(palavra) && !/^pour les puces (avec|sans)/i.test(a));
|
||||
if (citam.some((a) => /(utilise|dedie|connecte)/i.test(a) && !/sauf si/i.test(a))) return "forte";
|
||||
if (p._fn.some((f) => /alimentation/i.test(f) && f.includes(palavra))) return "forte";
|
||||
if (citam.length) return "fraco";
|
||||
return null;
|
||||
};
|
||||
|
||||
/**
|
||||
* Sujets qu'un utilisateur peut consulter en français.
|
||||
*/
|
||||
export const TOPICOS = [
|
||||
{ id: "flash", nome: "Flash", termos: ["flash", "memoire flash", "spi flash", "stockage", "firmware", "rom externe"], pinoNivel: nivelMemoria("flash"), pinoRotulo: "reliées à la mémoire flash" },
|
||||
{ id: "psram", nome: "PSRAM", termos: ["psram", "ram externe", "spiram"], pinoNivel: nivelMemoria("psram"), pinoRotulo: "reliées à la PSRAM" },
|
||||
{ id: "memoria", nome: "Mémoire", termos: ["memoire", "sram", "heap", "rtc ram", "ko de ram", "memoire interne", "ram", "memory"], pinoRotulo: "" },
|
||||
{ id: "wifi", nome: "Wi-Fi", termos: ["wifi", "wi-fi", "sans fil", "wireless", "802.11", "wifi6", "wifi 6", "wi-fi 6"], pinoCats: ["Antenne"], pinoRotulo: "d'antenne et radio" },
|
||||
{ id: "bluetooth", nome: "Bluetooth", termos: ["bluetooth", "ble", "bt", "bluetooth le", "mesh"], pinoCats: ["Antenne"], pinoRotulo: "d'antenne et radio" },
|
||||
{ id: "zigbee", nome: "Zigbee/Thread", termos: ["zigbee", "thread", "802.15.4", "ieee 802.15.4"], pinoRotulo: "" },
|
||||
{ id: "matter", nome: "Matter", termos: ["matter", "maison intelligente", "smart home", "domotique"], pinoRotulo: "" },
|
||||
{ id: "ethernet", nome: "Ethernet", termos: ["ethernet", "rmii", "cable reseau", "lan"], pinoCats: ["Ethernet"], pinoRotulo: "d'Ethernet" },
|
||||
{ id: "can", nome: "CAN / TWAI", termos: ["can", "twai", "can bus", "canbus", "can fd"], pinoRe: /twai|\bcan\b/, pinoRotulo: "de CAN/TWAI" },
|
||||
{ id: "usb", nome: "USB", termos: ["usb", "otg", "usb serie", "usb serial", "usb otg", "hid", "cdc"], pinoCats: ["USB"], pinoRotulo: "d'USB" },
|
||||
{ id: "jtag", nome: "JTAG / Débogage", termos: ["jtag", "debug", "debogage", "deboguer", "openocd", "gdb"], pinoCats: ["JTAG"], pinoRotulo: "de JTAG" },
|
||||
{ id: "adc", nome: "ADC", termos: ["adc", "analogique", "entree analogique", "convertisseur analogique", "analogread", "saradc"], pinoCats: ["ADC"], pinoRotulo: "avec ADC" },
|
||||
{ id: "dac", nome: "DAC", termos: ["dac", "sortie analogique", "convertisseur numerique"], pinoCats: ["DAC"], pinoRotulo: "avec DAC" },
|
||||
{ id: "touch", nome: "Tactile capacitif", termos: ["touch", "capacitif", "tactile", "touchpad", "capteur tactile"], pinoCats: ["Touch"], pinoRotulo: "tactiles capacitives" },
|
||||
{ id: "uart", nome: "UART", termos: ["uart", "serie", "serial", "tx", "rx", "txd", "rxd", "port serie"], pinoCats: ["UART"], pinoRotulo: "d'UART" },
|
||||
{ id: "spi", nome: "SPI", termos: ["spi", "mosi", "miso", "sclk", "bus spi"], pinoCats: ["SPI"], pinoRotulo: "de SPI" },
|
||||
{ id: "i2c", nome: "I2C", termos: ["i2c", "sda", "scl", "twi", "iic"], pinoCats: ["I2C"], pinoRotulo: "d'I2C" },
|
||||
{ id: "i2s", nome: "I2S", termos: ["i2s", "audio", "son", "microphone", "pdm", "codec"], pinoRe: /i2s|\bpdm\b/, pinoRotulo: "d'I2S / audio" },
|
||||
{ id: "pwm", nome: "PWM", termos: ["pwm", "ledc", "mcpwm", "servo", "variateur"], pinoRe: /ledc|pwm/, pinoRotulo: "de PWM" },
|
||||
{ id: "sd", nome: "Carte SD / SDIO", termos: ["sd", "sdio", "carte sd", "sd card", "microsd", "sdmmc", "mmc"], pinoCats: ["SD"], pinoRe: /sdio|sdmmc|\bsd\b/, pinoRotulo: "de carte SD/SDIO" },
|
||||
{ id: "camera", nome: "Caméra", termos: ["camera", "cam", "dvp", "csi", "mipi csi", "ov2640", "video"], pinoCats: ["CSI"], pinoRe: /\bcam\b|dvp|cam_/, pinoRotulo: "de caméra" },
|
||||
{ id: "lcd", nome: "Écran / LCD", termos: ["lcd", "display", "ecran", "dsi", "mipi dsi", "oled", "tft", "lvgl", "rgb"], pinoCats: ["DSI"], pinoRe: /lcd/, pinoRotulo: "d'écran/LCD" },
|
||||
{ id: "strapping", nome: "Démarrage / Strapping", termos: ["strapping", "boot", "bootstrap", "mode boot", "mode demarrage", "download mode", "demarrage"], pinoCats: ["Strapping"], pinoRotulo: "de strapping (mode de démarrage)" },
|
||||
{ id: "energia_pinos", nome: "Alimentation", termos: ["alimentation", "vdd", "3v3", "3.3v", "tension", "regulateur", "ldo", "source"], pinoCats: ["Power"], pinoRotulo: "d'alimentation" },
|
||||
{ id: "clock", nome: "Horloge / Quartz", termos: ["clock", "horloge", "xtal", "quartz", "oscillateur", "32khz", "40mhz"], pinoCats: ["Clock"], pinoRotulo: "d'horloge/quartz" },
|
||||
{ id: "gpio", nome: "GPIO", termos: ["gpio", "entrees sorties", "broches"], pinoCats: ["GPIO"], pinoRotulo: "de GPIO" },
|
||||
{ id: "baixo_consumo", nome: "Basse consommation / ULP", termos: ["ulp", "lp core", "lp cpu", "coprocesseur", "lp gpio", "low power", "rtc gpio", "basse consommation"], pinoCats: ["Low Power"], pinoRotulo: "basse consommation (LP/RTC)" },
|
||||
{ id: "antena", nome: "Antenne / RF", termos: ["antenne", "rf", "radiofrequence", "ipex"], pinoCats: ["Antenne"], pinoRotulo: "d'antenne/RF" },
|
||||
{ id: "seguranca", nome: "Sécurité", termos: ["securite", "secure boot", "cryptographie", "chiffrement", "aes", "sha", "rsa", "hmac", "ecdsa", "efuse", "tee", "trng", "rng", "hsm", "protection"], pinoRotulo: "" },
|
||||
{ id: "consumo", nome: "Consommation d'énergie", termos: ["consommation", "batterie", "deep sleep", "light sleep", "sleep", "modem sleep", "courant", "milliampere", "autonomie", "economie d energie", "mode veille"], pinoRotulo: "" },
|
||||
{ id: "temperatura", nome: "Température", termos: ["temperature", "chaleur", "degres", "plage de temperature", "industriel"], pinoRotulo: "" },
|
||||
{ id: "ia", nome: "IA / Accélération", termos: ["ia", "ai", "machine learning", "ml", "tinyml", "vectoriel", "intelligence artificielle", "reseau neuronal", "esp-nn", "esp-dl"], pinoRotulo: "" },
|
||||
{ id: "processador", nome: "Processeur", termos: ["processeur", "cpu", "coeur", "coeurs", "core", "dual core", "single core", "architecture", "xtensa", "risc-v", "riscv"], pinoRotulo: "" },
|
||||
{ id: "frequencia", nome: "Fréquence", termos: ["frequence", "mhz", "vitesse", "performance", "rendement"], pinoRotulo: "" },
|
||||
{ id: "ferramentas", nome: "Outils / SDK", termos: ["esp-idf", "idf", "arduino", "sdk", "toolchain", "chaine d outils", "version d idf"], pinoRotulo: "" },
|
||||
{ id: "encapsulamento", nome: "Modules et boîtier", termos: ["module", "modules", "boitier", "encapsulation", "package", "qfn", "wroom", "wrover", "mini-1"], pinoRotulo: "" },
|
||||
];
|
||||
|
||||
/**
|
||||
* Champs de données techniques en français.
|
||||
*/
|
||||
export const SPEC_CAMPOS = [
|
||||
{ campo: "arquitetura", label: "Architecture", secao: "processador", topicos: ["processador"] },
|
||||
{ campo: "nucleos", label: "Cœurs", secao: "processador", topicos: ["processador"] },
|
||||
{ campo: "frequencia", label: "Fréquence", secao: "processador", topicos: ["frequencia", "processador"] },
|
||||
{ campo: "coprocessador_ulp", label: "Coprocesseur ULP", secao: "processador", topicos: ["baixo_consumo"] },
|
||||
{ campo: "aceleradores_ia", label: "Accélérateurs IA", secao: "processador", topicos: ["ia"] },
|
||||
|
||||
{ campo: "wifi", label: "Wi-Fi", secao: "conectividade", topicos: ["wifi"] },
|
||||
{ campo: "bluetooth", label: "Bluetooth", secao: "conectividade", topicos: ["bluetooth"] },
|
||||
{ campo: "zigbee_thread", label: "Zigbee/Thread", secao: "conectividade", topicos: ["zigbee"] },
|
||||
{ campo: "matter", label: "Matter", secao: "conectividade", topicos: ["matter"] },
|
||||
{ campo: "ethernet", label: "Ethernet", secao: "conectividade", topicos: ["ethernet"] },
|
||||
{ campo: "ethernet_mac", label: "Ethernet MAC", secao: "conectividade", topicos: ["ethernet"] },
|
||||
{ campo: "can", label: "CAN", secao: "conectividade", topicos: ["can"] },
|
||||
|
||||
{ campo: "memoria_sram", label: "SRAM", secao: "memoria", topicos: ["memoria"] },
|
||||
{ campo: "memoria_sram_rtc", label: "SRAM RTC", secao: "memoria", topicos: ["memoria", "baixo_consumo"] },
|
||||
{ campo: "memoria_rom", label: "ROM", secao: "memoria", topicos: ["memoria"] },
|
||||
{ campo: "flash_externa", label: "Flash externe", secao: "memoria", topicos: ["flash", "memoria"] },
|
||||
{ campo: "psram_externa", label: "PSRAM externe", secao: "memoria", topicos: ["psram", "memoria"] },
|
||||
|
||||
{ campo: "gpio", label: "GPIO", secao: "perifericos", topicos: ["gpio"] },
|
||||
{ campo: "adc", label: "ADC", secao: "perifericos", topicos: ["adc"] },
|
||||
{ campo: "dac", label: "DAC", secao: "perifericos", topicos: ["dac"] },
|
||||
{ campo: "touch", label: "Tactile capacitif", secao: "perifericos", topicos: ["touch"] },
|
||||
{ campo: "uart", label: "UART", secao: "perifericos", topicos: ["uart"] },
|
||||
{ campo: "spi", label: "SPI", secao: "perifericos", topicos: ["spi", "flash"] },
|
||||
{ campo: "i2c", label: "I2C", secao: "perifericos", topicos: ["i2c"] },
|
||||
{ campo: "i2s", label: "I2S", secao: "perifericos", topicos: ["i2s"] },
|
||||
{ campo: "pwm", label: "PWM", secao: "perifericos", topicos: ["pwm"] },
|
||||
{ campo: "usb", label: "USB", secao: "perifericos", topicos: ["usb"] },
|
||||
{ campo: "lcd", label: "LCD", secao: "interfaces", topicos: ["lcd"] },
|
||||
{ campo: "camera", label: "Caméra", secao: "interfaces", topicos: ["camera"] },
|
||||
{ campo: "mipi_csi", label: "MIPI CSI", secao: "interfaces", topicos: ["camera"] },
|
||||
{ campo: "mipi_dsi", label: "MIPI DSI", secao: "interfaces", topicos: ["lcd"] },
|
||||
{ campo: "sdio", label: "SDIO", secao: "interfaces", topicos: ["sd"] },
|
||||
{ campo: "sensor_temperatura", label: "Capteur de température", secao: "interfaces", topicos: ["temperatura"] },
|
||||
|
||||
{ campo: "seguranca.aes", label: "AES", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.sha", label: "SHA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.rsa", label: "RSA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.ecc", label: "ECC", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.ecdsa", label: "ECDSA", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.hmac", label: "HMAC", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.assinatura_digital", label: "Signature numérique", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.rng", label: "Générateur de nombres aléatoires", secao: "seguranca", topicos: ["seguranca"] },
|
||||
{ campo: "seguranca.criptografia_flash", label: "Chiffrement Flash", secao: "seguranca", topicos: ["seguranca", "flash"] },
|
||||
{ campo: "seguranca.secure_boot", label: "Secure Boot", secao: "seguranca", topicos: ["seguranca", "strapping"] },
|
||||
|
||||
{ campo: "temperatura_operacao", label: "Température de fonctionnement", secao: "temperatura", topicos: ["temperatura"] },
|
||||
{ campo: "temperatura_armazenamento", label: "Température de stockage", secao: "temperatura", topicos: ["temperatura"] },
|
||||
|
||||
{ campo: "esp_idf_minimo", label: "ESP-IDF minimum", secao: "ferramentas", topicos: ["ferramentas"] },
|
||||
{ campo: "arduino_core", label: "Arduino Core", secao: "ferramentas", topicos: ["ferramentas"] },
|
||||
{ campo: "depuracao", label: "Débogage", secao: "ferramentas", topicos: ["jtag", "ferramentas"] },
|
||||
{ campo: "encapsulamento", label: "Boîtier", secao: "ferramentas", topicos: ["encapsulamento"] },
|
||||
{ campo: "modulos", label: "Modules", secao: "ferramentas", topicos: ["encapsulamento"] },
|
||||
];
|
||||
|
||||
const ROTULOS_ENERGIA = {
|
||||
active: "Actif",
|
||||
modem_sleep: "Modem Sleep",
|
||||
light_sleep: "Light Sleep",
|
||||
deep_sleep: "Deep Sleep",
|
||||
hibernation: "Hibernation",
|
||||
};
|
||||
|
||||
const pegar = (obj, caminho) => caminho.split(".").reduce((o, k) => (o == null ? o : o[k]), obj);
|
||||
|
||||
/**
|
||||
* Monte la liste à plat des spécifications pour chaque série en français.
|
||||
*/
|
||||
export function montarConhecimento(series, conexoes) {
|
||||
const saida = {};
|
||||
for (const [chave, s] of Object.entries(series)) {
|
||||
const specs = [];
|
||||
for (const c of SPEC_CAMPOS) {
|
||||
const valor = pegar(s, c.campo);
|
||||
if (valor == null || valor === "") continue;
|
||||
specs.push({ label: c.label, valor: String(valor), secao: c.secao, topicos: c.topicos });
|
||||
}
|
||||
for (const [modo, valor] of Object.entries(s.consumo_energia ?? {})) {
|
||||
const base = modo.replace(/_cpu.*|_wifi.*/, "");
|
||||
const label = ROTULOS_ENERGIA[modo] ?? ROTULOS_ENERGIA[base] ?? modo.replace(/_/g, " ");
|
||||
specs.push({ label: `Consommation : ${label}`, valor: String(valor), secao: "energia", topicos: ["consumo"] });
|
||||
}
|
||||
saida[chave] = {
|
||||
nome: s.nome_completo ?? chave,
|
||||
specs,
|
||||
pinos: (conexoes[chave] ?? []).map((p) => ({
|
||||
n: String(p.numero),
|
||||
nome: p.nome,
|
||||
f: p.funcoes ?? [],
|
||||
c: p.categorias ?? [],
|
||||
a: p.avisos ?? [],
|
||||
})),
|
||||
};
|
||||
}
|
||||
return saida;
|
||||
}
|
||||
+68
-7
@@ -19,6 +19,20 @@ import { errosCatalogo as errosEs } from "@/lib/data/es/diagnostico";
|
||||
import { COMPONENTES_REGISTRY as componentesEs } from "@/lib/data/es/componentes";
|
||||
import { montarConhecimento as montarConhecimentoEs } from "@/lib/data/es/topicos";
|
||||
|
||||
import seriesDataFr from "@/data/fr/series.json";
|
||||
import frameworksDataFr from "@/data/fr/frameworks.json";
|
||||
import { categoriasGlossario as glossarioFr } from "@/lib/data/fr/glossario";
|
||||
import { errosCatalogo as errosFr } from "@/lib/data/fr/diagnostico";
|
||||
import { COMPONENTES_REGISTRY as componentesFr } from "@/lib/data/fr/componentes";
|
||||
import { montarConhecimento as montarConhecimentoFr } from "@/lib/data/fr/topicos";
|
||||
|
||||
import seriesDataDe from "@/data/de/series.json";
|
||||
import frameworksDataDe from "@/data/de/frameworks.json";
|
||||
import { categoriasGlossario as glossarioDe } from "@/lib/data/de/glossario";
|
||||
import { errosCatalogo as errosDe } from "@/lib/data/de/diagnostico";
|
||||
import { COMPONENTES_REGISTRY as componentesDe } from "@/lib/data/de/componentes";
|
||||
import { montarConhecimento as montarConhecimentoDe } from "@/lib/data/de/topicos";
|
||||
|
||||
import { readFileSync, existsSync } from "node:fs";
|
||||
import path from "node:path";
|
||||
|
||||
@@ -66,15 +80,43 @@ const PAGINAS_ES = [
|
||||
{ titulo: "Diagnóstico de Errores", descricao: "Solucione brownout, bucles de arranque, WDT y fallos", href: "/es/diagnostico", keywords: "error problema fallo crash" },
|
||||
{ titulo: "Frameworks y SDKs", descricao: "ESP-IDF, Arduino, Rust, RainMaker y más", href: "/es/frameworks", keywords: "sdk" },
|
||||
{ titulo: "Component Registry", descricao: "Catálogo de controladores y generador de idf_component.yml", href: "/es/componentes", keywords: "bibliotecas controladores drivers yml" },
|
||||
{ titulo: "Glosario Técnico", descricao: "Conceptos esenciales de hardware y software", href: "/es/glosario", keywords: "términos diccionario significado" },
|
||||
{ titulo: "Glosario Técnico", descricao: "Conceptos esenciales de hardware e software", href: "/es/glosario", keywords: "términos diccionario significado" },
|
||||
{ titulo: "Acerca del Proyecto", descricao: "Historia, autor y código abierto", href: "/es/acerca", keywords: "autor contacto código abierto" },
|
||||
];
|
||||
|
||||
const PAGINAS_FR = [
|
||||
{ titulo: "Accueil", descricao: "Page d'accueil d'ESPDocs", href: "/fr", keywords: "accueil home" },
|
||||
{ titulo: "Toutes les Séries", descricao: "Brochages, spécifications et restrictions pour chaque série ESP32", href: "/fr/series", keywords: "puces brochage specifications pinout" },
|
||||
{ titulo: "Comparateur de Séries", descricao: "Comparez jusqu'à 4 modèles côte à côte", href: "/fr/comparaison", keywords: "comparer comparaison versus" },
|
||||
{ titulo: "Catalogue de Cartes", descricao: "Cartes de développement, brochages et achat", href: "/fr/catalogue", keywords: "cartes dev boards devkit acheter" },
|
||||
{ titulo: "Sélecteur Intelligent", descricao: "Trouvez la puce idéale pour votre projet", href: "/fr/selecteur", keywords: "quiz choisir recommander selecteur" },
|
||||
{ titulo: "Diagnostic d'Erreurs", descricao: "Résolvez brownout, boucles de démarrage, WDT et crashs", href: "/fr/diagnostic", keywords: "erreur probleme panne crash bug" },
|
||||
{ titulo: "Frameworks et SDKs", descricao: "ESP-IDF, Arduino, Rust, RainMaker et plus", href: "/fr/frameworks", keywords: "sdk" },
|
||||
{ titulo: "Component Registry", descricao: "Catalogue de pilotes et générateur idf_component.yml", href: "/fr/composants", keywords: "bibliotheques pilotes drivers yml composants" },
|
||||
{ titulo: "Glossaire Technique", descricao: "Concepts essentiels de matériel et de logiciel", href: "/fr/glossaire", keywords: "termes dictionnaire definition signification" },
|
||||
{ titulo: "À Propos du Projet", descricao: "Histoire, auteur et open source", href: "/fr/a-propos", keywords: "auteur contact open source" },
|
||||
];
|
||||
|
||||
const PAGINAS_DE = [
|
||||
{ titulo: "Startseite", descricao: "ESPDocs Startseite", href: "/de", keywords: "startseite home" },
|
||||
{ titulo: "Alle Serien", descricao: "Pinbelegungen, Spezifikationen und Einschränkungen für jede ESP32-Serie", href: "/de/serien", keywords: "chips pinbelegung spezifikationen pinout" },
|
||||
{ titulo: "Serienvergleich", descricao: "Vergleichen Sie bis zu 4 Modelle nebeneinander", href: "/de/vergleich", keywords: "vergleichen vergleich versus" },
|
||||
{ titulo: "Board-Katalog", descricao: "Entwicklungsboards, Pinbelegungen und Kauf", href: "/de/katalog", keywords: "boards dev boards devkit kaufen" },
|
||||
{ titulo: "Intelligente Auswahl", descricao: "Finden Sie den idealen Chip für Ihr Projekt", href: "/de/auswahl", keywords: "quiz waehlen empfehlen auswahl" },
|
||||
{ titulo: "Fehlerdiagnose", descricao: "Beheben Sie Brownout, Bootloops, WDT und Abstürze", href: "/de/diagnose", keywords: "fehler problem absturz crash bug" },
|
||||
{ titulo: "Frameworks & SDKs", descricao: "ESP-IDF, Arduino, Rust, RainMaker und mehr", href: "/de/frameworks", keywords: "sdk" },
|
||||
{ titulo: "Component Registry", descricao: "Treiberkatalog und idf_component.yml-Generator", href: "/de/komponenten", keywords: "bibliotheken treiber drivers yml komponenten" },
|
||||
{ titulo: "Technisches Glossar", descricao: "Wesentliche Hardware- und Softwarekonzepte", href: "/de/glossar", keywords: "begriffe woerterbuch definition bedeutung" },
|
||||
{ titulo: "Über das Projekt", descricao: "Geschichte, Autor und Open Source", href: "/de/ueber-uns", keywords: "autor kontakt open source" },
|
||||
];
|
||||
|
||||
const cortar = (texto = "", max = 140) => (texto.length > max ? `${texto.slice(0, max - 1).trimEnd()}…` : texto);
|
||||
|
||||
export function construirIndiceBusca(locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
|
||||
let paginas = PAGINAS_PT;
|
||||
let seriesData = seriesDataPt;
|
||||
@@ -100,14 +142,29 @@ export function construirIndiceBusca(locale = "pt") {
|
||||
errosCatalogo = errosEs;
|
||||
componentes = componentesEs;
|
||||
montarConhecimento = montarConhecimentoEs;
|
||||
} else if (isFr) {
|
||||
paginas = PAGINAS_FR;
|
||||
seriesData = seriesDataFr;
|
||||
frameworksData = frameworksDataFr;
|
||||
categoriasGlossario = glossarioFr;
|
||||
errosCatalogo = errosFr;
|
||||
componentes = componentesFr;
|
||||
montarConhecimento = montarConhecimentoFr;
|
||||
} else if (isDe) {
|
||||
paginas = PAGINAS_DE;
|
||||
seriesData = seriesDataDe;
|
||||
frameworksData = frameworksDataDe;
|
||||
categoriasGlossario = glossarioDe;
|
||||
errosCatalogo = errosDe;
|
||||
componentes = componentesDe;
|
||||
montarConhecimento = montarConhecimentoDe;
|
||||
}
|
||||
|
||||
const prefixo = isEn ? "/en" : isEs ? "/es" : "";
|
||||
const slugSeries = `${prefixo}/series`;
|
||||
const slugFrameworks = `${prefixo}/frameworks`;
|
||||
const slugGlossario = isEn ? "/en/glossary" : isEs ? "/es/glosario" : "/glossario";
|
||||
const slugDiagnostico = isEn ? "/en/diagnostics" : isEs ? "/es/diagnostico" : "/diagnostico";
|
||||
const slugComponentes = isEn ? "/en/components" : isEs ? "/es/componentes" : "/componentes";
|
||||
const slugSeries = isDe ? "/de/serien" : isFr ? "/fr/series" : isEn ? "/en/series" : isEs ? "/es/series" : "/series";
|
||||
const slugFrameworks = isDe ? "/de/frameworks" : isFr ? "/fr/frameworks" : isEn ? "/en/frameworks" : isEs ? "/es/frameworks" : "/frameworks";
|
||||
const slugGlossario = isDe ? "/de/glossar" : isFr ? "/fr/glossaire" : isEn ? "/en/glossary" : isEs ? "/es/glosario" : "/glossario";
|
||||
const slugDiagnostico = isDe ? "/de/diagnose" : isFr ? "/fr/diagnostic" : isEn ? "/en/diagnostics" : isEs ? "/es/diagnostico" : "/diagnostico";
|
||||
const slugComponentes = isDe ? "/de/komponenten" : isFr ? "/fr/composants" : isEn ? "/en/components" : isEs ? "/es/componentes" : "/componentes";
|
||||
|
||||
const itens = [];
|
||||
|
||||
@@ -174,6 +231,10 @@ export function construirIndiceBusca(locale = "pt") {
|
||||
? path.join(process.cwd(), "data", "en", "conexoes")
|
||||
: isEs
|
||||
? path.join(process.cwd(), "data", "es", "conexoes")
|
||||
: isFr
|
||||
? path.join(process.cwd(), "data", "fr", "conexoes")
|
||||
: isDe
|
||||
? path.join(process.cwd(), "data", "de", "conexoes")
|
||||
: path.join(process.cwd(), "public", "conexoes");
|
||||
const arquivo = path.join(pastaConexoes, `${chave}.json`);
|
||||
if (existsSync(arquivo)) {
|
||||
|
||||
+68
-26
@@ -95,8 +95,11 @@ export const jsonLd = {
|
||||
siteESociedade(locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const orgAnchor = isEn ? "organization" : isEs ? "organizacion" : "organizacao";
|
||||
const authorAnchor = isEn ? "author" : "autor";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const orgAnchor = isEn ? "organization" : isEs ? "organizacion" : (isFr || isDe) ? "organisation" : "organizacao";
|
||||
const authorAnchor = isEn ? "author" : isFr ? "auteur" : "autor";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
"@graph": [
|
||||
@@ -105,11 +108,15 @@ export const jsonLd = {
|
||||
"@id": `${SITE.url}/#site`,
|
||||
url: `${SITE.url}/${locale}`,
|
||||
name: SITE.nome,
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
inLanguage: inLang,
|
||||
description: isEn
|
||||
? "ESP32 ecosystem documentation: specifications, pinouts, comparison, and series selection."
|
||||
: isEs
|
||||
? "Documentación del ecosistema ESP32: especificaciones, patillaje, comparación y selección de series."
|
||||
: isFr
|
||||
? "Documentation de l'écosystème ESP32 : spécifications, brochages, comparaison et sélection de séries."
|
||||
: isDe
|
||||
? "Dokumentation des ESP32-Ökosystems: Spezifikationen, Pinbelegung, Vergleich und Serienauswahl."
|
||||
: "Documentação do ecossistema ESP32 em português brasileiro: especificações, pinagem, comparação e seleção de séries.",
|
||||
publisher: { "@id": `${SITE.url}/#${orgAnchor}` },
|
||||
},
|
||||
@@ -157,32 +164,35 @@ export const jsonLd = {
|
||||
serie(chave, serie, locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const prop = (nome, valor) =>
|
||||
valor ? { "@type": "PropertyValue", name: nome, value: String(valor) } : null;
|
||||
|
||||
const propriedades = [
|
||||
prop(isEn ? "Manufacturer" : isEs ? "Fabricante" : "Fabricante", "Espressif Systems"),
|
||||
prop(isEn ? "Architecture" : isEs ? "Arquitectura" : "Arquitetura", serie.arquitetura),
|
||||
prop(isEn ? "Cores" : isEs ? "Núcleos" : "Núcleos", serie.nucleos),
|
||||
prop(isEn ? "Max frequency" : isEs ? "Frecuencia máxima" : "Frequência máxima", serie.frequencia),
|
||||
prop(isEn ? "Manufacturer" : isEs ? "Fabricante" : isFr ? "Fabricant" : isDe ? "Hersteller" : "Fabricante", "Espressif Systems"),
|
||||
prop(isEn ? "Architecture" : isEs ? "Arquitectura" : isFr ? "Architecture" : isDe ? "Architektur" : "Arquitetura"),
|
||||
prop(isEn ? "Cores" : isEs ? "Núcleos" : isFr ? "Cœurs" : isDe ? "Kerne" : "Núcleos", serie.nucleos),
|
||||
prop(isEn ? "Max frequency" : isEs ? "Frecuencia máxima" : isFr ? "Fréquence maximale" : isDe ? "Maximale Frequenz" : "Frequência máxima", serie.frequencia),
|
||||
prop("SRAM", serie.memoria_sram),
|
||||
prop("RTC SRAM", serie.memoria_sram_rtc),
|
||||
prop(isEn ? "Supported Flash" : isEs ? "Flash soportada" : "Flash suportada", serie.flash_suportada),
|
||||
prop(isEn ? "Supported PSRAM" : isEs ? "PSRAM soportada" : "PSRAM suportada", serie.psram_suportada),
|
||||
prop(isEn ? "Supported Flash" : isEs ? "Flash soportada" : isFr ? "Flash prise en charge" : isDe ? "Unterstützter Flash" : "Flash suportada", serie.flash_suportada),
|
||||
prop(isEn ? "Supported PSRAM" : isEs ? "PSRAM soportada" : isFr ? "PSRAM prise en charge" : isDe ? "Unterstütztes PSRAM" : "PSRAM suportada", serie.psram_suportada),
|
||||
prop("GPIO", serie.gpio),
|
||||
prop("Wi-Fi", serie.wifi),
|
||||
prop("Bluetooth", serie.bluetooth),
|
||||
prop("Zigbee / Thread / 802.15.4", serie.zigbee_thread),
|
||||
prop(isEn ? "Package" : isEs ? "Encapsulado" : "Encapsulamento", serie.encapsulamento),
|
||||
prop(isEn ? "Minimum ESP-IDF" : isEs ? "ESP-IDF mínimo" : "ESP-IDF mínimo", serie.esp_idf_minimo),
|
||||
prop(isEn ? "Package" : isEs ? "Encapsulado" : isFr ? "Boîtier" : isDe ? "Gehäuse" : "Encapsulamento", serie.encapsulamento),
|
||||
prop(isEn ? "Minimum ESP-IDF" : isEs ? "ESP-IDF mínimo" : isFr ? "ESP-IDF minimum" : isDe ? "Mindestens ESP-IDF" : "ESP-IDF mínimo", serie.esp_idf_minimo),
|
||||
].filter(Boolean);
|
||||
|
||||
const imagem = serie.placa
|
||||
? `${SITE.url}${serie.placa}`
|
||||
: `${SITE.url}/opengraph-image.png`;
|
||||
|
||||
const basePath = isEn ? `/en/series/${chave}` : isEs ? `/es/series/${chave}` : `/series/${chave}`;
|
||||
const anchor = isEn ? "article" : isEs ? "articulo" : "artigo";
|
||||
const basePath = isDe ? `/de/serien/${chave}` : isFr ? `/fr/series/${chave}` : isEn ? `/en/series/${chave}` : isEs ? `/es/series/${chave}` : `/series/${chave}`;
|
||||
const anchor = isEn ? "article" : isEs ? "articulo" : isFr ? "article" : isDe ? "artikel" : "artigo";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
@@ -192,15 +202,23 @@ export const jsonLd = {
|
||||
? `${serie.nome_completo || chave}: specifications and pinout`
|
||||
: isEs
|
||||
? `${serie.nome_completo || chave}: especificaciones y patillaje`
|
||||
: isFr
|
||||
? `${serie.nome_completo || chave} : spécifications et brochage`
|
||||
: isDe
|
||||
? `${serie.nome_completo || chave}: Spezifikationen und Pinbelegung`
|
||||
: `${serie.nome_completo || chave}: especificações e pinagem`,
|
||||
name: isEn
|
||||
? `${serie.nome_completo || chave} - Technical Documentation and Specifications`
|
||||
: isEs
|
||||
? `${serie.nome_completo || chave} - Documentación técnica y especificaciones`
|
||||
: isFr
|
||||
? `${serie.nome_completo || chave} - Documentation technique et spécifications`
|
||||
: isDe
|
||||
? `${serie.nome_completo || chave} - Technische Dokumentation und Spezifikationen`
|
||||
: `${serie.nome_completo || chave} - Documentação Técnica e Especificações`,
|
||||
description: serie.descricao,
|
||||
image: [imagem],
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
inLanguage: inLang,
|
||||
datePublished: "2026-08-25T00:00:00.000Z",
|
||||
dateModified: new Date().toISOString(),
|
||||
mainEntityOfPage: `${SITE.url}${basePath}`,
|
||||
@@ -234,8 +252,11 @@ export const jsonLd = {
|
||||
framework(chave, framework, locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const basePath = isEn ? `/en/frameworks/${encodeURIComponent(chave)}` : isEs ? `/es/frameworks/${encodeURIComponent(chave)}` : `/frameworks/${encodeURIComponent(chave)}`;
|
||||
const anchor = isEn ? "article" : isEs ? "articulo" : "artigo";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const basePath = isDe ? `/de/frameworks/${encodeURIComponent(chave)}` : isFr ? `/fr/frameworks/${encodeURIComponent(chave)}` : isEn ? `/en/frameworks/${encodeURIComponent(chave)}` : isEs ? `/es/frameworks/${encodeURIComponent(chave)}` : `/frameworks/${encodeURIComponent(chave)}`;
|
||||
const anchor = isEn ? "article" : isEs ? "articulo" : isFr ? "article" : isDe ? "artikel" : "artigo";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
"@type": "TechArticle",
|
||||
@@ -244,13 +265,21 @@ export const jsonLd = {
|
||||
? `${framework.nome} for ESP32: Guide and Documentation`
|
||||
: isEs
|
||||
? `${framework.nome} para ESP32: Guía y documentación`
|
||||
: isFr
|
||||
? `${framework.nome} pour ESP32 : Guide et documentation`
|
||||
: isDe
|
||||
? `${framework.nome} für ESP32: Leitfaden und Dokumentation`
|
||||
: `${framework.nome} para ESP32: Guia e Documentação`,
|
||||
name: isEn
|
||||
? `${framework.nome_completo || framework.nome} for ESP32`
|
||||
: isFr
|
||||
? `${framework.nome_completo || framework.nome} pour ESP32`
|
||||
: isDe
|
||||
? `${framework.nome_completo || framework.nome} für ESP32`
|
||||
: `${framework.nome_completo || framework.nome} para ESP32`,
|
||||
description: framework.descricao,
|
||||
image: [`${SITE.url}/opengraph-image.png`],
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
inLanguage: inLang,
|
||||
datePublished: "2026-08-25T00:00:00.000Z",
|
||||
dateModified: new Date().toISOString(),
|
||||
mainEntityOfPage: `${SITE.url}${basePath}`,
|
||||
@@ -286,14 +315,17 @@ export const jsonLd = {
|
||||
glossario(categorias, locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const basePath = isEn ? "/en/glossary" : isEs ? "/es/glosario" : "/glossario";
|
||||
const anchor = isEn ? "glossary" : isEs ? "glosario" : "glossario";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const basePath = isDe ? "/de/glossar" : isFr ? "/fr/glossaire" : isEn ? "/en/glossary" : isEs ? "/es/glosario" : "/glossario";
|
||||
const anchor = isDe ? "glossar" : isFr ? "glossaire" : isEn ? "glossary" : isEs ? "glosario" : "glossario";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
"@type": "DefinedTermSet",
|
||||
"@id": `${SITE.url}${basePath}#${anchor}`,
|
||||
name: isEn ? "ESP32 Technical Glossary" : isEs ? "Glosario técnico de ESP32" : "Glossário Técnico do ESP32",
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
name: isEn ? "ESP32 Technical Glossary" : isEs ? "Glosario técnico de ESP32" : isFr ? "Glossaire technique de l'ESP32" : isDe ? "Technisches Glossar für ESP32" : "Glossário Técnico do ESP32",
|
||||
inLanguage: inLang,
|
||||
hasDefinedTerm: categorias.flatMap((cat) =>
|
||||
cat.termos.map((t) => ({
|
||||
"@type": "DefinedTerm",
|
||||
@@ -322,6 +354,9 @@ export const jsonLd = {
|
||||
aplicacaoWeb({ nome, descricao, caminho, locale = "pt" }) {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
"@type": "WebApplication",
|
||||
@@ -332,7 +367,7 @@ export const jsonLd = {
|
||||
applicationCategory: "DeveloperApplication",
|
||||
operatingSystem: "All",
|
||||
browserRequirements: "Requires JavaScript",
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
inLanguage: inLang,
|
||||
author: {
|
||||
"@type": "Person",
|
||||
name: SITE.autor,
|
||||
@@ -415,20 +450,27 @@ export const jsonLd = {
|
||||
paginaSobre(locale = "pt") {
|
||||
const isEn = locale === "en";
|
||||
const isEs = locale === "es";
|
||||
const basePath = isEn ? "/en/about" : isEs ? "/es/acerca" : "/sobre";
|
||||
const anchor = isEn ? "about" : isEs ? "acerca" : "sobre";
|
||||
const isFr = locale === "fr";
|
||||
const isDe = locale === "de";
|
||||
const basePath = isDe ? "/de/ueber-uns" : isFr ? "/fr/a-propos" : isEn ? "/en/about" : isEs ? "/es/acerca" : "/sobre";
|
||||
const anchor = isDe ? "ueber-uns" : isFr ? "a-propos" : isEn ? "about" : isEs ? "acerca" : "sobre";
|
||||
const inLang = isEn ? "en" : isEs ? "es-419" : isFr ? "fr" : isDe ? "de" : "pt-BR";
|
||||
return {
|
||||
"@context": "https://schema.org",
|
||||
"@type": "AboutPage",
|
||||
"@id": `${SITE.url}${basePath}#${anchor}`,
|
||||
name: isEn ? "About ESPDocs" : isEs ? "Acerca de ESPDocs" : "Sobre o ESPDocs",
|
||||
name: isEn ? "About ESPDocs" : isEs ? "Acerca de ESPDocs" : isFr ? "À propos d'ESPDocs" : isDe ? "Über ESPDocs" : "Sobre o ESPDocs",
|
||||
description: isEn
|
||||
? "ESPDocs is an independent platform organizing technical documentation of the ESP32 ecosystem."
|
||||
: isEs
|
||||
? "ESPDocs es una plataforma independiente que reúne la documentación técnica del ecosistema ESP32."
|
||||
: isFr
|
||||
? "ESPDocs est une plateforme indépendante qui rassemble la documentation technique de l'écosystème ESP32."
|
||||
: isDe
|
||||
? "ESPDocs ist eine unabhängige Plattform, die die technische Dokumentation des ESP32-Ökosystems zusammenführt."
|
||||
: "O ESPDocs é uma plataforma independente que reúne a documentação do ecossistema ESP32 em português brasileiro.",
|
||||
url: `${SITE.url}${basePath}`,
|
||||
inLanguage: isEn ? "en" : isEs ? "es-419" : "pt-BR",
|
||||
inLanguage: inLang,
|
||||
mainEntity: {
|
||||
"@type": "Person",
|
||||
name: SITE.autor,
|
||||
|
||||
@@ -0,0 +1,152 @@
|
||||
{
|
||||
"Common": {
|
||||
"siteName": "ESPDocs",
|
||||
"author": "Lucas Rayan Guerra",
|
||||
"organization": "Ciência Embarcada",
|
||||
"skipToContent": "Zum Inhalt springen",
|
||||
"allRightsReserved": "Inhalte unter MIT-Lizenz. Erstellt für die Embedded-Systems-Community.",
|
||||
"backToHome": "Zurück zur Startseite",
|
||||
"explore": "Erkunden",
|
||||
"tools": "Werkzeuge",
|
||||
"project": "Projekt",
|
||||
"loading": "Wird geladen...",
|
||||
"search": "Suchen...",
|
||||
"officialDocumentation": "Offizielle Dokumentation",
|
||||
"community": "Community",
|
||||
"mitLicense": "MIT-Lizenz"
|
||||
},
|
||||
"Header": {
|
||||
"brand": "ESPDocs",
|
||||
"homeAria": "ESPDocs, Startseite",
|
||||
"navAria": "Hauptnavigation",
|
||||
"mobileNavAria": "Mobile Navigation",
|
||||
"openMenu": "Navigationsmenü öffnen",
|
||||
"closeMenu": "Menü schließen",
|
||||
"navigationTitle": "Navigation",
|
||||
"whereToGo": "Wohin möchten Sie gehen",
|
||||
"selectChip": "Chip auswählen",
|
||||
"selectMyChip": "Meinen Chip auswählen",
|
||||
"hardware": "Hardware",
|
||||
"hardwareDesc": "12 Chips, Pinbelegungen und Spezifikationen",
|
||||
"series": "ESP32-Serien",
|
||||
"seriesDesc": "12 Chips, Pinbelegungen und Spezifikationen",
|
||||
"comparator": "Vergleich",
|
||||
"comparatorDesc": "Bis zu vier Serien nebeneinander",
|
||||
"catalog": "Board-Katalog",
|
||||
"catalogDesc": "DevKits, Pinbelegungen und Bezugsquellen",
|
||||
"tools": "Werkzeuge",
|
||||
"selector": "Intelligente Auswahl",
|
||||
"selectorDesc": "Der passende Chip für Ihr Projekt",
|
||||
"diagnostics": "Diagnose",
|
||||
"diagnosticsDesc": "Brownout, Bootloops, WDT und mehr",
|
||||
"components": "ESP Component Registry",
|
||||
"componentsDesc": "Treiber und idf_component.yml-Manifeste",
|
||||
"library": "Bibliothek",
|
||||
"frameworks": "Frameworks und SDKs",
|
||||
"frameworksDesc": "ESP-IDF, Arduino, Rust und Matter",
|
||||
"glossary": "Technisches Glossar",
|
||||
"glossaryDesc": "Begriffe aus den Datenblättern",
|
||||
"about": "Über das Projekt",
|
||||
"aboutDesc": "Autor, Methodik und Open Source"
|
||||
},
|
||||
"Footer": {
|
||||
"ariaLabel": "ESPDocs Fußzeile",
|
||||
"description": "Unabhängige Dokumentation des ESP32-Ökosystems. Offene Daten, redaktionelle Aufbereitung und Links zu offiziellen Quellen.",
|
||||
"exploreTitle": "Erkunden",
|
||||
"toolsTitle": "Werkzeuge",
|
||||
"projectTitle": "Projekt",
|
||||
"authorTitle": "Autor",
|
||||
"reportIssue": "Problem melden",
|
||||
"repository": "Repository",
|
||||
"personalSite": "Persönliche Website",
|
||||
"linkedin": "LinkedIn"
|
||||
},
|
||||
"Home": {
|
||||
"badge": "Offene ESP32-Dokumentation",
|
||||
"titleLine1": "Der ESP32,",
|
||||
"titleLine2": " auf den Punkt gebracht.",
|
||||
"lede": "Spezifikationen, Pinbelegungen, Vergleiche und Diagnose auf einen Blick. Weniger Datenblatt-Recherche, mehr Zeit an der Werkbank.",
|
||||
"chooseMyChip": "Meinen Chip auswählen",
|
||||
"exploreSeries": "Die {count} Serien erkunden",
|
||||
"seriesCount": "{count} Serien",
|
||||
"frameworkCount": "{count} Frameworks",
|
||||
"portugueseFlag": "100 % auf Deutsch",
|
||||
"featuredSeries": "Vorgestellte Serien",
|
||||
"featuredDesc": "Das Wesentliche jeder Familie, bevor Sie das Datenblatt öffnen.",
|
||||
"fullIndex": "Vollständiger Index",
|
||||
"toolsTitle": "Beginnen Sie beim Problem.",
|
||||
"toolsEyebrow": "Werkzeuge",
|
||||
"toolsDesc": "Werkzeuge zur Auswahl des richtigen Chips, zur Diagnose von Hardwarefehlern und zur Beschleunigung der Entwicklung."
|
||||
},
|
||||
"NotFound": {
|
||||
"eyebrow": "Fehler 404",
|
||||
"title": "Diese Seite existiert nicht.",
|
||||
"lede": "Die URL wurde möglicherweise geändert oder falsch eingegeben. Wählen Sie einen dieser Wege, um fortzufahren.",
|
||||
"backToHome": "Zurück zur Startseite",
|
||||
"seriesTitle": "ESP32-Serien",
|
||||
"seriesDesc": "12 Familien mit Pinbelegungen und Spezifikationen.",
|
||||
"selectorTitle": "Chip-Auswahl",
|
||||
"selectorDesc": "Beantworten Sie acht Fragen und finden Sie empfohlene Modelle.",
|
||||
"comparatorTitle": "Vergleich",
|
||||
"comparatorDesc": "Bis zu vier Serien nebeneinander.",
|
||||
"glossaryTitle": "Glossar",
|
||||
"glossaryDesc": "Hardwarebegriffe verständlich erklärt."
|
||||
},
|
||||
"Sobre": {
|
||||
"label": "Unabhängiges Projekt",
|
||||
"title": "Über ESPDocs",
|
||||
"lede": "Eine inoffizielle Plattform, die technische Informationen über den ESP32 strukturiert und direkt mit der offiziellen Espressif-Dokumentation verknüpft. Entwickelt für die Open-Hardware-Community.",
|
||||
"viewRepository": "Repository ansehen",
|
||||
"features": {
|
||||
"portugueseTitle": "Kuratierte Inhalte",
|
||||
"portugueseDesc": "Strukturierte technische Daten, klar aufbereitet ohne Datenblatt-Ballast.",
|
||||
"visualCompareTitle": "Visuelle Vergleiche",
|
||||
"visualCompareDesc": "Tabellen und Diagramme zur Auswahl der passenden Serie, ohne zehn Datenblätter öffnen zu müssen.",
|
||||
"centralizedAccessTitle": "Zentraler Zugang",
|
||||
"centralizedAccessDesc": "Direkte Links zu offizieller Dokumentation, Repositories und Beispielen.",
|
||||
"openSourceTitle": "Open Source",
|
||||
"openSourceDesc": "Beiträge auf Gitea sind herzlich willkommen."
|
||||
}
|
||||
},
|
||||
"Series": {
|
||||
"title": "ESP32-Serien",
|
||||
"description": "12 ESP32-Serien im Überblick: ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 und H4. Architektur, Speicher, Funk, Peripherie und Pinbelegung für jede Serie.",
|
||||
"pinout": "Pinbelegung",
|
||||
"specifications": "Spezifikationen",
|
||||
"peripherals": "Peripherie",
|
||||
"architecture": "Architektur",
|
||||
"memory": "Speicher",
|
||||
"radio": "Funk",
|
||||
"security": "Hardware-Sicherheit"
|
||||
},
|
||||
"Catalogo": {
|
||||
"title": "Board-Katalog",
|
||||
"description": "Offizielle und Drittanbieter-DevKits mit Pinbelegungen, Schnittstellen und Bezugsquellen.",
|
||||
"filterBySeries": "Nach Serie filtern",
|
||||
"searchBoards": "Boards suchen..."
|
||||
},
|
||||
"Comparacao": {
|
||||
"title": "ESP32-Serien-Vergleich",
|
||||
"description": "Vergleichen Sie bis zu 4 Serien nebeneinander mit vollständigen Angaben zu Rechenleistung, Funk, Speicher und Pinbelegung."
|
||||
},
|
||||
"Componentes": {
|
||||
"title": "ESP Component Registry",
|
||||
"description": "Treiber, Bibliotheken und einsatzbereite idf_component.yml-Manifeste für ESP-IDF."
|
||||
},
|
||||
"Diagnostico": {
|
||||
"title": "Diagnose und Fehlersuche",
|
||||
"description": "Brownout, Bootloops, CPU-Panics, FreeRTOS und Hardware-Best-Practices."
|
||||
},
|
||||
"Frameworks": {
|
||||
"title": "Frameworks und SDKs",
|
||||
"description": "Leitfäden und Übersichten zu den wichtigsten Entwicklungsumgebungen: ESP-IDF, Arduino, MicroPython, Rust und ESP-Matter."
|
||||
},
|
||||
"Glossario": {
|
||||
"title": "Technisches Glossar",
|
||||
"description": "Praxisnahe Erklärungen zu Hardwarekonzepten, Peripherie, Funk und Architektur aus den Datenblättern."
|
||||
},
|
||||
"Seletor": {
|
||||
"title": "Intelligente ESP32-Auswahl",
|
||||
"description": "Beantworten Sie gezielte Fragen zu Ihrem Projekt und finden Sie die ideale Serie anhand technischer Kriterien."
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,152 @@
|
||||
{
|
||||
"Common": {
|
||||
"siteName": "ESPDocs",
|
||||
"author": "Lucas Rayan Guerra",
|
||||
"organization": "Ciência Embarcada",
|
||||
"skipToContent": "Passer au contenu",
|
||||
"allRightsReserved": "Contenu sous licence MIT. Conçu pour la communauté des systèmes embarqués.",
|
||||
"backToHome": "Retour à l'accueil",
|
||||
"explore": "Explorer",
|
||||
"tools": "Outils",
|
||||
"project": "Projet",
|
||||
"loading": "Chargement...",
|
||||
"search": "Rechercher...",
|
||||
"officialDocumentation": "Documentation officielle",
|
||||
"community": "Communauté",
|
||||
"mitLicense": "Licence MIT"
|
||||
},
|
||||
"Header": {
|
||||
"brand": "ESPDocs",
|
||||
"homeAria": "ESPDocs, page d'accueil",
|
||||
"navAria": "Navigation principale",
|
||||
"mobileNavAria": "Navigation mobile",
|
||||
"openMenu": "Ouvrir le menu de navigation",
|
||||
"closeMenu": "Fermer le menu",
|
||||
"navigationTitle": "Navigation",
|
||||
"whereToGo": "Où aller",
|
||||
"selectChip": "Sélectionner la puce",
|
||||
"selectMyChip": "Choisir ma puce",
|
||||
"hardware": "Matériel",
|
||||
"hardwareDesc": "12 puces, brochages et spécifications",
|
||||
"series": "Séries ESP32",
|
||||
"seriesDesc": "12 puces, brochages et spécifications",
|
||||
"comparator": "Comparateur",
|
||||
"comparatorDesc": "Jusqu'à quatre séries côte à côte",
|
||||
"catalog": "Catalogue de cartes",
|
||||
"catalogDesc": "DevKits, brochages et points de vente",
|
||||
"tools": "Outils",
|
||||
"selector": "Sélecteur intelligent",
|
||||
"selectorDesc": "La bonne puce pour votre projet",
|
||||
"diagnostics": "Diagnostic",
|
||||
"diagnosticsDesc": "Brownout, bootloops, WDT et plus",
|
||||
"components": "ESP Component Registry",
|
||||
"componentsDesc": "Pilotes et manifestes idf_component.yml",
|
||||
"library": "Bibliothèque",
|
||||
"frameworks": "Frameworks et SDKs",
|
||||
"frameworksDesc": "ESP-IDF, Arduino, Rust et Matter",
|
||||
"glossary": "Glossaire technique",
|
||||
"glossaryDesc": "Termes figurant dans les fiches techniques",
|
||||
"about": "À propos du projet",
|
||||
"aboutDesc": "Auteur, méthode et open source"
|
||||
},
|
||||
"Footer": {
|
||||
"ariaLabel": "Pied de page ESPDocs",
|
||||
"description": "Documentation indépendante de l'écosystème ESP32. Données ouvertes, curation éditoriale et liens vers les sources officielles.",
|
||||
"exploreTitle": "Explorer",
|
||||
"toolsTitle": "Outils",
|
||||
"projectTitle": "Projet",
|
||||
"authorTitle": "Auteur",
|
||||
"reportIssue": "Signaler un problème",
|
||||
"repository": "Dépôt",
|
||||
"personalSite": "Site personnel",
|
||||
"linkedin": "LinkedIn"
|
||||
},
|
||||
"Home": {
|
||||
"badge": "Documentation ouverte ESP32",
|
||||
"titleLine1": "L'ESP32,",
|
||||
"titleLine2": " sans artifice.",
|
||||
"lede": "Spécifications, brochages, comparatifs et diagnostics en une seule lecture. Moins d'allers-retours dans les fiches techniques, plus de temps à l'établi.",
|
||||
"chooseMyChip": "Choisir ma puce",
|
||||
"exploreSeries": "Explorer les {count} séries",
|
||||
"seriesCount": "{count} séries de puces",
|
||||
"frameworkCount": "{count} frameworks",
|
||||
"portugueseFlag": "100 % en français",
|
||||
"featuredSeries": "Séries en vedette",
|
||||
"featuredDesc": "L'essentiel de chaque famille avant d'ouvrir la fiche technique.",
|
||||
"fullIndex": "Index complet",
|
||||
"toolsTitle": "Commencez par le problème.",
|
||||
"toolsEyebrow": "Outils",
|
||||
"toolsDesc": "Des outils pour sélectionner la bonne puce, diagnostiquer les erreurs matérielles et accélérer le développement."
|
||||
},
|
||||
"NotFound": {
|
||||
"eyebrow": "Erreur 404",
|
||||
"title": "Cette page n'existe pas.",
|
||||
"lede": "L'URL a peut-être changé ou a été mal saisie. Choisissez l'un de ces chemins pour continuer.",
|
||||
"backToHome": "Retour à l'accueil",
|
||||
"seriesTitle": "Séries ESP32",
|
||||
"seriesDesc": "12 familles, avec brochages et spécifications.",
|
||||
"selectorTitle": "Sélecteur de puces",
|
||||
"selectorDesc": "Répondez à huit questions et trouvez les modèles recommandés.",
|
||||
"comparatorTitle": "Comparateur",
|
||||
"comparatorDesc": "Jusqu'à quatre séries côte à côte.",
|
||||
"glossaryTitle": "Glossaire",
|
||||
"glossaryDesc": "Termes matériels expliqués clairement."
|
||||
},
|
||||
"Sobre": {
|
||||
"label": "Projet indépendant",
|
||||
"title": "À propos d'ESPDocs",
|
||||
"lede": "Une plateforme non officielle organisant les informations techniques sur l'ESP32 et reliant directement à la documentation officielle d'Espressif. Conçue pour la communauté du matériel open source.",
|
||||
"viewRepository": "Voir le dépôt",
|
||||
"features": {
|
||||
"portugueseTitle": "Contenu soigné",
|
||||
"portugueseDesc": "Des données techniques structurées et présentées clairement, sans le bruit des fiches techniques.",
|
||||
"visualCompareTitle": "Comparaisons visuelles",
|
||||
"visualCompareDesc": "Tableaux et diagrammes pour sélectionner la bonne série sans ouvrir dix fiches techniques.",
|
||||
"centralizedAccessTitle": "Accès centralisé",
|
||||
"centralizedAccessDesc": "Liens directs vers la documentation officielle, les dépôts et les exemples.",
|
||||
"openSourceTitle": "Open source",
|
||||
"openSourceDesc": "Les contributions sont les bienvenues sur Gitea."
|
||||
}
|
||||
},
|
||||
"Series": {
|
||||
"title": "Séries ESP32",
|
||||
"description": "12 séries ESP32 côte à côte : ESP32, S2, S3, S31, C2, C3, C5, C6, C61, P4, H2 et H4. Architecture, mémoire, radio, périphériques et brochages de chacune.",
|
||||
"pinout": "Brochage",
|
||||
"specifications": "Spécifications",
|
||||
"peripherals": "Périphériques",
|
||||
"architecture": "Architecture",
|
||||
"memory": "Mémoire",
|
||||
"radio": "Radio",
|
||||
"security": "Sécurité matérielle"
|
||||
},
|
||||
"Catalogo": {
|
||||
"title": "Catalogue de cartes de développement",
|
||||
"description": "DevKits officiels et tiers avec brochages, interfaces et liens d'achat.",
|
||||
"filterBySeries": "Filtrer par série",
|
||||
"searchBoards": "Rechercher des cartes..."
|
||||
},
|
||||
"Comparacao": {
|
||||
"title": "Comparateur de séries ESP32",
|
||||
"description": "Comparez jusqu'à 4 séries côte à côte avec les spécifications complètes de traitement, radio, mémoire et brochages."
|
||||
},
|
||||
"Componentes": {
|
||||
"title": "ESP Component Registry",
|
||||
"description": "Pilotes, bibliothèques et manifestes idf_component.yml prêts à l'emploi pour ESP-IDF."
|
||||
},
|
||||
"Diagnostico": {
|
||||
"title": "Diagnostic et dépannage",
|
||||
"description": "Brownout, bootloops, paniques de CPU, FreeRTOS et bonnes pratiques matérielles."
|
||||
},
|
||||
"Frameworks": {
|
||||
"title": "Frameworks et SDKs",
|
||||
"description": "Guides et aperçus des principaux environnements de développement : ESP-IDF, Arduino, MicroPython, Rust et ESP-Matter."
|
||||
},
|
||||
"Glossario": {
|
||||
"title": "Glossaire technique",
|
||||
"description": "Explications pratiques des concepts matériels, périphériques, radio et architecture présents dans les fiches techniques."
|
||||
},
|
||||
"Seletor": {
|
||||
"title": "Sélecteur intelligent d'ESP32",
|
||||
"description": "Répondez à des questions objectives sur votre projet et trouvez la série idéale selon des critères techniques."
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
#include <WiFi.h>
|
||||
|
||||
// Ersetzen Sie dies durch Ihre Wi-Fi-Zugangsdaten
|
||||
const char* ssid = "NAME_IHRES_WIFI_NETZWERKS";
|
||||
const char* password = "PASSWORT_IHRES_WIFI_NETZWERKS";
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
delay(1000);
|
||||
|
||||
Serial.println("Verbindung zum Wi-Fi wird aufgebaut...");
|
||||
WiFi.begin(ssid, password);
|
||||
|
||||
// Verbindung wird abgewartet
|
||||
while (WiFi.status() != WL_CONNECTED) {
|
||||
delay(500);
|
||||
Serial.print(".");
|
||||
}
|
||||
|
||||
Serial.println("");
|
||||
Serial.println("Wi-Fi erfolgreich verbunden!");
|
||||
Serial.print("IP-Adresse: ");
|
||||
Serial.println(WiFi.localIP());
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// Aqui você pode colocar o código principal do seu programa
|
||||
delay(1000);
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
#include "esp_log.h"
|
||||
#include "audio_pipeline.h"
|
||||
#include "audio_element.h"
|
||||
#include "audio_event_iface.h"
|
||||
#include "audio_common.h"
|
||||
#include "i2s_stream.h"
|
||||
#include "mp3_decoder.h"
|
||||
#include "fatfs_stream.h"
|
||||
#include "esp_peripherals.h"
|
||||
#include "periph_sdcard.h"
|
||||
|
||||
static const char *TAG = "HELLO_ADF";
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa periféricos (como o SD card)
|
||||
esp_periph_config_t periph_cfg = DEFAULT_ESP_PERIPH_SET_CONFIG();
|
||||
esp_periph_set_handle_t set = esp_periph_set_init(&periph_cfg);
|
||||
periph_sdcard_cfg_t sd_cfg = {
|
||||
.root = "/sdcard",
|
||||
};
|
||||
esp_periph_handle_t sdcard_handle = periph_sdcard_init(&sd_cfg);
|
||||
esp_periph_start(set, sdcard_handle);
|
||||
|
||||
// Espera o SD card montar
|
||||
periph_sdcard_wait_for_ready(sdcard_handle, portMAX_DELAY);
|
||||
|
||||
ESP_LOGI(TAG, "SD card montado!");
|
||||
|
||||
// Cria o pipeline
|
||||
audio_pipeline_handle_t pipeline;
|
||||
audio_pipeline_cfg_t pipeline_cfg = DEFAULT_AUDIO_PIPELINE_CONFIG();
|
||||
pipeline = audio_pipeline_init(&pipeline_cfg);
|
||||
|
||||
// Elementos: arquivo (fatfs), decodificador (mp3) e saída (i2s)
|
||||
audio_element_handle_t fatfs_stream_reader, i2s_stream_writer, mp3_decoder;
|
||||
|
||||
fatfs_stream_cfg_t fatfs_cfg = FATFS_STREAM_CFG_DEFAULT();
|
||||
fatfs_cfg.type = AUDIO_STREAM_READER;
|
||||
fatfs_stream_reader = fatfs_stream_init(&fatfs_cfg);
|
||||
|
||||
mp3_decoder_cfg_t mp3_cfg = DEFAULT_MP3_DECODER_CONFIG();
|
||||
mp3_decoder = mp3_decoder_init(&mp3_cfg);
|
||||
|
||||
i2s_stream_cfg_t i2s_cfg = I2S_STREAM_CFG_DEFAULT();
|
||||
i2s_cfg.type = AUDIO_STREAM_WRITER;
|
||||
i2s_stream_writer = i2s_stream_init(&i2s_cfg);
|
||||
|
||||
// Registra e conecta elementos
|
||||
audio_pipeline_register(pipeline, fatfs_stream_reader, "file");
|
||||
audio_pipeline_register(pipeline, mp3_decoder, "mp3");
|
||||
audio_pipeline_register(pipeline, i2s_stream_writer, "i2s");
|
||||
|
||||
audio_pipeline_link(pipeline, (const char *[]) {"file", "mp3", "i2s"}, 3);
|
||||
|
||||
// Define o arquivo MP3 a ser tocado
|
||||
audio_element_set_uri(fatfs_stream_reader, "/sdcard/test.mp3");
|
||||
|
||||
// Inicia o pipeline
|
||||
ESP_LOGI(TAG, "Iniciando pipeline...");
|
||||
audio_pipeline_run(pipeline);
|
||||
|
||||
// Mantém o pipeline rodando
|
||||
while (1) {
|
||||
vTaskDelay(1000 / portTICK_PERIOD_MS);
|
||||
}
|
||||
|
||||
// (Nunca chega aqui, mas seria o cleanup)
|
||||
audio_pipeline_stop(pipeline);
|
||||
audio_pipeline_wait_for_stop(pipeline);
|
||||
audio_pipeline_terminate(pipeline);
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_dsp.h"
|
||||
|
||||
#define N 8 // Tamanho do vetor
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Vetor de entrada (exemplo de sinal)
|
||||
float x[N] = {1.0, -2.0, 3.0, -4.0, 2.5, -1.5, 0.0, 4.5};
|
||||
float y[N]; // Vetor de saída
|
||||
|
||||
// Inicializa o ESP-DSP
|
||||
esp_err_t ret = dsps_fft2r_init_fc32(NULL, CONFIG_DSP_MAX_FFT_SIZE);
|
||||
if (ret != ESP_OK) {
|
||||
printf("Erro ao inicializar o ESP-DSP!\n");
|
||||
return;
|
||||
}
|
||||
|
||||
printf("Sinal de entrada:\n");
|
||||
for (int i = 0; i < N; i++) {
|
||||
printf("%f ", x[i]);
|
||||
}
|
||||
printf("\n");
|
||||
|
||||
// Calcula o quadrado de cada valor
|
||||
dsps_mulc_f32(x, y, N, 1.0f);
|
||||
dsps_mul_f32(y, y, y, N, 1, 1, 1);
|
||||
|
||||
// Soma todos os quadrados
|
||||
float soma = 0;
|
||||
dsps_sum_f32(y, N, &soma, 1);
|
||||
|
||||
// Calcula a magnitude (raiz da soma dos quadrados)
|
||||
float magnitude = sqrtf(soma);
|
||||
|
||||
printf("Magnitude do vetor: %f\n", magnitude);
|
||||
}
|
||||
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* ESP-IDF v5.x+ Beispiel für ESP32
|
||||
* Demonstration von Systeminitialisierung, FreeRTOS-Task-Management und einheitlichem Logging
|
||||
*
|
||||
* Komponentenverwaltung (main/idf_component.yml):
|
||||
* dependencies:
|
||||
* espressif/led_strip: "^2.5.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_chip_info.h"
|
||||
|
||||
static const char *TAG = "main_app";
|
||||
|
||||
#define BLINK_GPIO GPIO_NUM_2 // Passen Sie dies an den LED-Pin Ihres Boards an
|
||||
|
||||
static void blink_task(void *pvParameters)
|
||||
{
|
||||
// Konfiguriert den GPIO-Pin mit der neuen ESP-IDF-API
|
||||
gpio_reset_pin(BLINK_GPIO);
|
||||
gpio_set_direction(BLINK_GPIO, GPIO_MODE_OUTPUT);
|
||||
|
||||
bool led_state = false;
|
||||
|
||||
while (1) {
|
||||
led_state = !led_state;
|
||||
gpio_set_level(BLINK_GPIO, led_state);
|
||||
|
||||
ESP_LOGI(TAG, "LED %s | Freier Heap: %lu Bytes",
|
||||
led_state ? "EIN" : "AUS",
|
||||
(unsigned long)esp_get_free_heap_size());
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(1000));
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Informações do chip SoC
|
||||
esp_chip_info_t chip_info;
|
||||
esp_chip_info(&chip_info);
|
||||
|
||||
ESP_LOGI(TAG, "===========================================");
|
||||
ESP_LOGI(TAG, " Iniciando ESP-IDF v5.x Modern Application ");
|
||||
ESP_LOGI(TAG, " Modelo do Chip: %d | Núcleos: %d | Rev: %d",
|
||||
chip_info.model, chip_info.cores, chip_info.revision);
|
||||
ESP_LOGI(TAG, "===========================================");
|
||||
|
||||
// Cria uma tarefa FreeRTOS dedicada
|
||||
xTaskCreate(blink_task, "blink_task", 3072, NULL, 5, NULL);
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
* Exemplo ESP-IoT-Solution para ESP32
|
||||
* Inicialização de Botão Inteligente com Callbacks e Driver de Display/Sensores
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/button: "^3.3.0"
|
||||
* espressif/led_indicator: "^1.2.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "iot_button.h"
|
||||
#include "led_indicator.h"
|
||||
|
||||
static const char *TAG = "iot_solution_app";
|
||||
|
||||
#define BUTTON_GPIO_NUM 0 // Botão BOOT nativo
|
||||
#define LED_INDICATOR_GPIO 2 // LED indicador
|
||||
|
||||
static led_indicator_handle_t led_handle = NULL;
|
||||
|
||||
/* Callback para clique único do botão */
|
||||
static void button_single_click_cb(void *arg, void *data)
|
||||
{
|
||||
ESP_LOGI(TAG, "Evento: Clique Único detectado!");
|
||||
led_indicator_start(led_handle, BLINK_DOUBLE_FAST);
|
||||
}
|
||||
|
||||
/* Callback para clique longo (> 3 segundos) */
|
||||
static void button_long_press_cb(void *arg, void *data)
|
||||
{
|
||||
ESP_LOGW(TAG, "Evento: Pressionamento Longo! Acionando modo de reset de fábrica.");
|
||||
led_indicator_start(led_handle, BLINK_BREATHE_FAST);
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_LOGI(TAG, "Iniciando ESP-IoT-Solution Component Suite");
|
||||
|
||||
// 1. Configuração do LED Indicator
|
||||
led_indicator_gpio_config_t led_cfg = {
|
||||
.is_active_level_high = true,
|
||||
.gpio_num = LED_INDICATOR_GPIO,
|
||||
};
|
||||
led_handle = led_indicator_create(&led_cfg);
|
||||
|
||||
// 2. Configuração do Botão com debounce de hardware/software automático
|
||||
button_config_t btn_cfg = {
|
||||
.type = BUTTON_TYPE_GPIO,
|
||||
.long_press_time = 3000,
|
||||
.short_press_time = 180,
|
||||
.gpio_button_config = {
|
||||
.gpio_num = BUTTON_GPIO_NUM,
|
||||
.active_level = 0,
|
||||
},
|
||||
};
|
||||
|
||||
button_handle_t btn_handle = iot_button_create(&btn_cfg);
|
||||
assert(btn_handle != NULL);
|
||||
|
||||
// Registra callbacks para diferentes gestos
|
||||
iot_button_register_cb(btn_handle, BUTTON_SINGLE_CLICK, button_single_click_cb, NULL);
|
||||
iot_button_register_cb(btn_handle, BUTTON_LONG_PRESS_START, button_long_press_cb, NULL);
|
||||
|
||||
ESP_LOGI(TAG, "Drivers inicializados com sucesso! Pressione o botão GPIO 0.");
|
||||
|
||||
while (1) {
|
||||
vTaskDelay(pdMS_TO_TICKS(1000));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_log.h"
|
||||
#include "esp_matter.h"
|
||||
#include "esp_matter_controller.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
static const char *TAG = "esp-matter-example";
|
||||
|
||||
void app_event_cb(const esp_matter_event_t *event)
|
||||
{
|
||||
switch (event->event_id) {
|
||||
case ESP_MATTER_EVENT_ATTRIBUTE_UPDATE: {
|
||||
const esp_matter_attr_update_t *attr_update = &event->data.attr_update;
|
||||
if (attr_update->endpoint_id == 1 && attr_update->cluster_id == ESP_MATTER_ON_OFF_CLUSTER_ID) {
|
||||
bool on = false;
|
||||
esp_matter_attribute_get(attr_update->endpoint_id, attr_update->cluster_id,
|
||||
attr_update->attribute_id, &on);
|
||||
ESP_LOGI(TAG, "Lâmpada %s", on ? "ligada" : "desligada");
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa NVS
|
||||
esp_err_t err = nvs_flash_init();
|
||||
if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
|
||||
ESP_ERROR_CHECK(nvs_flash_erase());
|
||||
ESP_ERROR_CHECK(nvs_flash_init());
|
||||
}
|
||||
|
||||
// Inicializa o Matter node
|
||||
esp_matter::node_t *node = esp_matter::node::create(NULL, app_event_cb);
|
||||
esp_matter::endpoint_t *endpoint = esp_matter::endpoint::create(node, ESP_MATTER_ENDPOINT_TYPE_ON_OFF_LIGHT);
|
||||
|
||||
// Inicia o stack Matter
|
||||
ESP_ERROR_CHECK(esp_matter::start(node));
|
||||
|
||||
ESP_LOGI(TAG, "Dispositivo Matter iniciado. Aguardando comissionamento...");
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_nn.h"
|
||||
#include "esp_nn_defs.h"
|
||||
|
||||
#define INPUT_SIZE 4
|
||||
#define OUTPUT_SIZE 3
|
||||
|
||||
void print_array(const char *label, int16_t *array, int size) {
|
||||
printf("%s: ", label);
|
||||
for (int i = 0; i < size; i++) {
|
||||
printf("%d ", array[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Vetor de entrada (ex: saída de uma camada anterior)
|
||||
int16_t input[INPUT_SIZE] = {1, 2, 3, 4};
|
||||
|
||||
// Pesos da camada densa (3x4)
|
||||
int8_t weights[OUTPUT_SIZE * INPUT_SIZE] = {
|
||||
1, -1, 2, 0,
|
||||
0, 1, -1, 1,
|
||||
2, 0, 1, -2
|
||||
};
|
||||
|
||||
// Bias de cada neurônio
|
||||
int16_t bias[OUTPUT_SIZE] = {10, -5, 0};
|
||||
|
||||
// Saída
|
||||
int16_t output[OUTPUT_SIZE];
|
||||
|
||||
// Multiplicação da matriz: output = weights * input + bias
|
||||
esp_nn_mul_mat_16x8_16(weights, input, bias, output,
|
||||
OUTPUT_SIZE, INPUT_SIZE, /*shift=*/0);
|
||||
|
||||
print_array("Antes da ReLU", output, OUTPUT_SIZE);
|
||||
|
||||
// Aplicar função de ativação ReLU
|
||||
esp_nn_relu_16(output, OUTPUT_SIZE);
|
||||
|
||||
print_array("Depois da ReLU", output, OUTPUT_SIZE);
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Exemplo ESP-NOW para ESP32
|
||||
* Comunicação Sem Fio Ponto-a-Ponto e Broadcast sem roteador Wi-Fi
|
||||
*
|
||||
* Protocolo nativo integrado no ESP-IDF
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_wifi.h"
|
||||
#include "esp_now.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
static const char *TAG = "esp_now_demo";
|
||||
|
||||
// Estrutura de dados enviada no pacote
|
||||
typedef struct {
|
||||
uint32_t sensor_id;
|
||||
float temperatura;
|
||||
float umidade;
|
||||
uint32_t tempo_ms;
|
||||
} __attribute__((packed)) dados_pacote_t;
|
||||
|
||||
// Endereço MAC de Broadcast (envia para todos os nós ESP-NOW por perto)
|
||||
static const uint8_t broadcast_mac[ESP_NOW_ETH_ALEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
|
||||
|
||||
/* Callback executado ao enviar um pacote */
|
||||
static void on_data_sent(const uint8_t *mac_addr, esp_now_send_status_t status)
|
||||
{
|
||||
ESP_LOGI(TAG, "Envio concluído: %s", status == ESP_NOW_SEND_SUCCESS ? "SUCESSO (ACK)" : "FALHA");
|
||||
}
|
||||
|
||||
/* Callback executado ao receber um pacote de outro ESP32 */
|
||||
static void on_data_recv(const esp_now_recv_info_t *recv_info, const uint8_t *data, int len)
|
||||
{
|
||||
if (len == sizeof(dados_pacote_t)) {
|
||||
dados_pacote_t *pct = (dados_pacote_t *)data;
|
||||
ESP_LOGI(TAG, "Pacote recebido de [%02X:%02X:%02X:%02X:%02X:%02X]: Sensor #%ld | Temp: %.1f C | Umid: %.1f %%",
|
||||
recv_info->src_addr[0], recv_info->src_addr[1], recv_info->src_addr[2],
|
||||
recv_info->src_addr[3], recv_info->src_addr[4], recv_info->src_addr[5],
|
||||
pct->sensor_id, pct->temperatura, pct->umidade);
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa NVS e Wi-Fi em modo Station
|
||||
nvs_flash_init();
|
||||
esp_netif_init();
|
||||
esp_event_loop_create_default();
|
||||
wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT();
|
||||
esp_wifi_init(&cfg);
|
||||
esp_wifi_set_mode(WIFI_MODE_STA);
|
||||
esp_wifi_start();
|
||||
|
||||
// Inicializa o protocolo ESP-NOW
|
||||
ESP_ERROR_CHECK(esp_now_init());
|
||||
esp_now_register_send_cb(on_data_sent);
|
||||
esp_now_register_recv_cb(on_data_recv);
|
||||
|
||||
// Registra o peer de Broadcast
|
||||
esp_now_peer_info_t peer_info = {
|
||||
.channel = 1,
|
||||
.ifidx = WIFI_IF_STA,
|
||||
.encrypt = false,
|
||||
};
|
||||
memcpy(peer_info.peer_addr, broadcast_mac, ESP_NOW_ETH_ALEN);
|
||||
ESP_ERROR_CHECK(esp_now_add_peer(&peer_info));
|
||||
|
||||
ESP_LOGI(TAG, "ESP-NOW pronto! Enviando telemetria a cada 3 segundos...");
|
||||
|
||||
dados_pacote_t telemetria = {
|
||||
.sensor_id = 101,
|
||||
.temperatura = 24.8f,
|
||||
.umidade = 58.2f,
|
||||
};
|
||||
|
||||
while (1) {
|
||||
telemetria.tempo_ms = esp_log_timestamp();
|
||||
telemetria.temperatura += ((float)(rand() % 10) - 5.0f) / 10.0f;
|
||||
|
||||
esp_err_t res = esp_now_send(broadcast_mac, (uint8_t *)&telemetria, sizeof(telemetria));
|
||||
if (res != ESP_OK) {
|
||||
ESP_LOGE(TAG, "Erro ao disparar envio ESP-NOW: %d", res);
|
||||
}
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(3000));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* Exemplo ESP-RainMaker para ESP32
|
||||
* Dispositivo: Interruptor Inteligente com controle via App e Nuvem
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp_rainmaker: "^1.4.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
#include <esp_rmaker_core.h>
|
||||
#include <esp_rmaker_standard_params.h>
|
||||
#include <esp_rmaker_standard_devices.h>
|
||||
#include <app_wifi.h>
|
||||
|
||||
static const char *TAG = "app_rainmaker";
|
||||
static esp_rmaker_device_t *switch_device;
|
||||
|
||||
/* Callback acionado quando o usuário altera o estado no App móvel */
|
||||
static esp_err_t write_cb(const esp_rmaker_device_t *dev, const esp_rmaker_param_val_t val, void *priv_data, esp_rmaker_write_ctx_t *ctx)
|
||||
{
|
||||
if (ctx) {
|
||||
ESP_LOGI(TAG, "Comando recebido via %s", esp_rmaker_device_cb_src_to_str(ctx->src));
|
||||
}
|
||||
|
||||
bool state = val.val.b;
|
||||
ESP_LOGI(TAG, "Schalterzustand geändert auf: %s", state ? "EIN" : "AUS");
|
||||
|
||||
// Aktualisiert den Parameter in Cloud und App
|
||||
esp_rmaker_param_update_and_report(priv_data, val);
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicialização da memória não-volátil (NVS)
|
||||
esp_err_t err = nvs_flash_init();
|
||||
if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
|
||||
ESP_ERROR_CHECK(nvs_flash_erase());
|
||||
err = nvs_flash_init();
|
||||
}
|
||||
ESP_ERROR_CHECK(err);
|
||||
|
||||
// Inicializa o provisionamento Wi-Fi
|
||||
app_wifi_init();
|
||||
|
||||
// Configura o nó RainMaker
|
||||
esp_rmaker_config_t rainmaker_cfg = {
|
||||
.enable_time_sync = true,
|
||||
};
|
||||
esp_rmaker_node_t *node = esp_rmaker_node_init(&rainmaker_cfg, "ESP32_SmartSwitch", "Switch");
|
||||
|
||||
// Cria o dispositivo padrão 'Switch'
|
||||
switch_device = esp_rmaker_switch_device_create("Luz Sala", NULL, true);
|
||||
|
||||
// Registra callback de escrita
|
||||
esp_rmaker_device_add_cb(switch_device, write_cb, NULL);
|
||||
esp_rmaker_node_add_device(node, switch_device);
|
||||
|
||||
// Habilita serviços adicionais (OTA e Timezone)
|
||||
esp_rmaker_ota_enable_default();
|
||||
esp_rmaker_timezone_service_enable();
|
||||
|
||||
// Inicia o agente RainMaker
|
||||
esp_rmaker_start();
|
||||
|
||||
// Inicia o provisionamento Wi-Fi via BLE (abre no app oficial RainMaker)
|
||||
app_wifi_start(POP_TYPE_RANDOM);
|
||||
|
||||
ESP_LOGI(TAG, "Nó RainMaker pronto! Escaneie o QR Code no app ESP RainMaker.");
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
* Exemplo ESP-SR para ESP32-S3 / ESP32-P4
|
||||
* Reconhecimento de Fala Local Offline (WakeNet + MultiNet)
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp-sr: "^1.5.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_wn_iface.h"
|
||||
#include "esp_wn_models.h"
|
||||
#include "esp_mn_iface.h"
|
||||
#include "esp_mn_models.h"
|
||||
#include "esp_afe_sr_iface.h"
|
||||
#include "esp_afe_sr_models.h"
|
||||
|
||||
static const char *TAG = "app_voice_sr";
|
||||
|
||||
void feed_audio_task(void *arg)
|
||||
{
|
||||
esp_afe_sr_data_t *afe_data = (esp_afe_sr_data_t *)arg;
|
||||
int audio_chunksize = afe_handle->get_feed_chunksize(afe_data);
|
||||
int16_t *feed_buff = (int16_t *)malloc(audio_chunksize * sizeof(int16_t) * 2);
|
||||
|
||||
while (1) {
|
||||
// Leitura de áudio I2S dos microfones da placa
|
||||
// i2s_read(I2S_NUM_0, feed_buff, ...);
|
||||
|
||||
afe_handle->feed(afe_data, feed_buff);
|
||||
vTaskDelay(pdMS_TO_TICKS(10));
|
||||
}
|
||||
free(feed_buff);
|
||||
vTaskDelete(NULL);
|
||||
}
|
||||
|
||||
void speech_recognition_task(void *arg)
|
||||
{
|
||||
esp_afe_sr_data_t *afe_data = (esp_afe_sr_data_t *)arg;
|
||||
const esp_afe_sr_iface_t *afe_handle = &ESP_AFE_SR_HANDLE;
|
||||
|
||||
// Inicializa o modelo de comandos de fala (MultiNet)
|
||||
const esp_mn_iface_t *multinet = &ESP_MN_HANDLE;
|
||||
model_iface_data_t *model_data = multinet->create(&MULTINET_MODEL, 6000);
|
||||
|
||||
ESP_LOGI(TAG, "Aguardando palavra-chave de ativação (ex: 'Hi, ESP')...");
|
||||
|
||||
while (1) {
|
||||
afe_fetch_result_t *res = afe_handle->fetch(afe_data);
|
||||
if (!res || res->ret_value == ESP_FAIL) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// 1. Verificação de Wake Word (Palavra de ativação)
|
||||
if (res->wake_word_detected == WAKENET_DETECTED) {
|
||||
ESP_LOGW(TAG, ">>> PALAVRA-CHAVE DETECTADA! Canal de escuta aberto.");
|
||||
}
|
||||
|
||||
// 2. Reconhecimento de comando local
|
||||
if (res->raw_data_size > 0) {
|
||||
esp_mn_state_t mn_state = multinet->detect(model_data, res->data);
|
||||
|
||||
if (mn_state == ESP_MN_STATE_DETECTED) {
|
||||
esp_mn_results_t *mn_res = multinet->get_results(model_data);
|
||||
ESP_LOGI(TAG, ">>> COMANDO RECONHECIDO: ID #%d (Frase correspondente)", mn_res->command_id[0]);
|
||||
|
||||
// Exemplo de ação
|
||||
if (mn_res->command_id[0] == 1) {
|
||||
ESP_LOGI(TAG, "Ação: Ligar Luz da Sala");
|
||||
} else if (mn_res->command_id[0] == 2) {
|
||||
ESP_LOGI(TAG, "Ação: Desligar Luz da Sala");
|
||||
}
|
||||
} else if (mn_state == ESP_MN_STATE_TIMEOUT) {
|
||||
ESP_LOGI(TAG, "Tempo esgotado. Retornando ao modo de escuta de Wake Word.");
|
||||
}
|
||||
}
|
||||
}
|
||||
vTaskDelete(NULL);
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_LOGI(TAG, "Iniciando ESP-SR Speech Recognition Engine");
|
||||
|
||||
// Configura o pipeline de Audio Front-End (AEC, BSS, VAD, WakeNet)
|
||||
afe_config_t afe_config = AFE_CONFIG_DEFAULT();
|
||||
afe_config.wakenet_init = true;
|
||||
afe_config.voice_communication_init = false;
|
||||
|
||||
esp_afe_sr_data_t *afe_data = ESP_AFE_SR_HANDLE.create_from_config(&afe_config);
|
||||
|
||||
// Cria as tarefas de alimentação de áudio e reconhecimento
|
||||
xTaskCreatePinnedToCore(feed_audio_task, "feed_task", 4096, afe_data, 5, NULL, 0);
|
||||
xTaskCreatePinnedToCore(speech_recognition_task, "sr_task", 8192, afe_data, 5, NULL, 1);
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
#include "esp_camera.h"
|
||||
#include "fd_forward.h" // Face Detection
|
||||
#include "fr_forward.h" // Face Recognition
|
||||
#include "human_face_detect_msr01.hpp"
|
||||
#include "human_face_detect_mnp01.hpp"
|
||||
|
||||
#define CAMERA_MODEL_AI_THINKER // ou o modelo da sua placa
|
||||
|
||||
#include "camera_pins.h"
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
Serial.setDebugOutput(true);
|
||||
Serial.println("Iniciando câmera...");
|
||||
|
||||
camera_config_t config;
|
||||
config.ledc_channel = LEDC_CHANNEL_0;
|
||||
config.ledc_timer = LEDC_TIMER_0;
|
||||
config.pin_d0 = Y2_GPIO_NUM;
|
||||
config.pin_d1 = Y3_GPIO_NUM;
|
||||
config.pin_d2 = Y4_GPIO_NUM;
|
||||
config.pin_d3 = Y5_GPIO_NUM;
|
||||
config.pin_d4 = Y6_GPIO_NUM;
|
||||
config.pin_d5 = Y7_GPIO_NUM;
|
||||
config.pin_d6 = Y8_GPIO_NUM;
|
||||
config.pin_d7 = Y9_GPIO_NUM;
|
||||
config.pin_xclk = XCLK_GPIO_NUM;
|
||||
config.pin_pclk = PCLK_GPIO_NUM;
|
||||
config.pin_vsync = VSYNC_GPIO_NUM;
|
||||
config.pin_href = HREF_GPIO_NUM;
|
||||
config.pin_sscb_sda = SIOD_GPIO_NUM;
|
||||
config.pin_sscb_scl = SIOC_GPIO_NUM;
|
||||
config.pin_pwdn = PWDN_GPIO_NUM;
|
||||
config.pin_reset = RESET_GPIO_NUM;
|
||||
config.xclk_freq_hz = 20000000;
|
||||
config.pixel_format = PIXFORMAT_RGB565;
|
||||
config.frame_size = FRAMESIZE_QVGA;
|
||||
config.fb_count = 1;
|
||||
|
||||
if (esp_camera_init(&config) != ESP_OK) {
|
||||
Serial.println("Falha ao iniciar a câmera!");
|
||||
return;
|
||||
}
|
||||
|
||||
Serial.println("Câmera inicializada com sucesso!");
|
||||
}
|
||||
|
||||
void loop() {
|
||||
camera_fb_t *fb = esp_camera_fb_get();
|
||||
if (!fb) {
|
||||
Serial.println("Falha ao capturar imagem!");
|
||||
return;
|
||||
}
|
||||
|
||||
// Detecta rostos na imagem
|
||||
box_array_t *faces = face_detect_msr01(fb->buf, fb->width, fb->height, fb->format);
|
||||
if (faces) {
|
||||
Serial.printf("Rostos detectados: %d\n", faces->len);
|
||||
for (int i = 0; i < faces->len; i++) {
|
||||
box_t *box = &faces->box[i];
|
||||
Serial.printf("Face %d - x:%d y:%d w:%d h:%d\n", i, box->box_p[0], box->box_p[1],
|
||||
box->box_p[2] - box->box_p[0], box->box_p[3] - box->box_p[1]);
|
||||
}
|
||||
dl_lib_free(faces);
|
||||
} else {
|
||||
Serial.println("Nenhum rosto detectado.");
|
||||
}
|
||||
|
||||
esp_camera_fb_return(fb);
|
||||
delay(1000);
|
||||
}
|
||||
@@ -0,0 +1,97 @@
|
||||
/*
|
||||
* Exemplo ESP-Zigbee-SDK para ESP32-H2 e ESP32-C6 (IEEE 802.15.4)
|
||||
* Dispositivo: Lâmpada Inteligente Zigbee 3.0 (Home Automation End Device)
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp-zigbee-lib: "^1.6.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
#include "esp_zigbee_core.h"
|
||||
|
||||
static const char *TAG = "zigbee_light_device";
|
||||
|
||||
#define HA_ESP_LIGHT_ENDPOINT 1
|
||||
#define ESP_ZB_PRIMARY_CHANNEL_MASK (1l << 15) // Canal 15 padrão Zigbee
|
||||
|
||||
/* Callback de escrita em atributos Zigbee (ex: Liga/Desliga via Home Assistant) */
|
||||
static esp_err_t zb_attribute_handler(const esp_zb_zcl_set_attr_value_message_t *message)
|
||||
{
|
||||
if (message->info.cluster == ESP_ZB_ZCL_CLUSTER_ID_ON_OFF) {
|
||||
if (message->attribute.id == ESP_ZB_ZCL_ATTR_ON_OFF_ON_OFF_ID &&
|
||||
message->attribute.data.type == ESP_ZB_ZCL_ATTR_TYPE_BOOL) {
|
||||
bool on_off_state = message->attribute.data.value ? *(bool *)message->attribute.data.value : false;
|
||||
ESP_LOGW(TAG, ">>> COMANDO ZIGBEE RECEBIDO: Lâmpada %s", on_off_state ? "LIGADA" : "DESLIGADA");
|
||||
}
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
/* Callback de eventos da pilha Zigbee */
|
||||
void esp_zb_app_signal_handler(esp_zb_app_signal_msg_t *signal_msg)
|
||||
{
|
||||
uint32_t *p_sg_p = signal_msg->p_app_signal;
|
||||
esp_err_t err_status = signal_msg->esp_err_status;
|
||||
esp_zb_app_signal_type_t sig_type = *p_sg_p;
|
||||
|
||||
switch (sig_type) {
|
||||
case ESP_ZB_ZDO_SIGNAL_SKIP_STARTUP:
|
||||
ESP_LOGI(TAG, "Iniciando comissionamento na rede Zigbee...");
|
||||
esp_zb_bdb_start_top_level_commissioning(ESP_ZB_BDB_MODE_NETWORK_STEERING);
|
||||
break;
|
||||
case ESP_ZB_BDB_SIGNAL_STEERING:
|
||||
if (err_status == ESP_OK) {
|
||||
ESP_LOGI(TAG, "Conectado com sucesso à rede Zigbee 3.0!");
|
||||
} else {
|
||||
ESP_LOGW(TAG, "Buscando coordenador Zigbee novamente...");
|
||||
esp_zb_scheduler_alarm((esp_zb_callback_t)esp_zb_bdb_start_top_level_commissioning, ESP_ZB_BDB_MODE_NETWORK_STEERING, 1000);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void esp_zb_task(void *pvParameters)
|
||||
{
|
||||
// Configura nó Zigbee como End Device
|
||||
esp_zb_cfg_t zb_nwk_cfg = {
|
||||
.esp_zb_role = ESP_ZB_DEVICE_TYPE_ED,
|
||||
.install_code_policy = false,
|
||||
.nwk_cfg.zed_cfg = {
|
||||
.ed_timeout = ESP_ZB_ED_0_5_MIN,
|
||||
.keep_alive = 3000,
|
||||
},
|
||||
};
|
||||
esp_zb_init(&zb_nwk_cfg);
|
||||
|
||||
// Cria o cluster de On/Off de iluminação residencial
|
||||
esp_zb_on_off_light_cfg_t light_cfg = ESP_ZB_DEFAULT_ON_OFF_LIGHT_CONFIG();
|
||||
esp_zb_ep_list_t *ep_list = esp_zb_on_off_light_ep_create(HA_ESP_LIGHT_ENDPOINT, &light_cfg);
|
||||
|
||||
// Registra endpoint e manipulador de atributos
|
||||
esp_zb_device_register(ep_list);
|
||||
esp_zb_core_action_handler_register(zb_attribute_handler);
|
||||
|
||||
esp_zb_set_primary_network_channel_set(ESP_ZB_PRIMARY_CHANNEL_MASK);
|
||||
ESP_ERROR_CHECK(esp_zb_start(false));
|
||||
esp_zb_main_loop_iteration();
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_ERROR_CHECK(nvs_flash_init());
|
||||
|
||||
// Inicializa a pilha de rádio IEEE 802.15.4
|
||||
esp_zb_platform_config_t config = {
|
||||
.radio_config = { .radio_mode = ZB_RADIO_MODE_NATIVE },
|
||||
.host_config = { .host_connection_mode = ZB_HOST_CONNECTION_MODE_NONE },
|
||||
};
|
||||
ESP_ERROR_CHECK(esp_zb_platform_config(&config));
|
||||
|
||||
xTaskCreate(esp_zb_task, "Zigbee_main", 4096, NULL, 5, NULL);
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
from machine import Pin
|
||||
from time import sleep
|
||||
|
||||
# Definiert Pin 2 als Ausgang (üblicherweise die integrierte LED)
|
||||
led = Pin(2, Pin.OUT)
|
||||
|
||||
while True:
|
||||
led.value(1) # Schaltet die LED ein
|
||||
sleep(0.5) # Wartet 0,5 Sekunden
|
||||
led.value(0) # Schaltet die LED aus
|
||||
sleep(0.5) # Wartet 0,5 Sekunden
|
||||
@@ -0,0 +1,48 @@
|
||||
//! Exemplo Rust no ESP32 usando `esp-hal` (Modo Bare-Metal / no_std)
|
||||
//! Pisca um LED e envia mensagens via UART Serial com segurança de memória garantida.
|
||||
//!
|
||||
//! Cargo.toml:
|
||||
//! esp-hal = { version = "0.22", features = ["esp32s3"] }
|
||||
//! esp-println = { version = "0.12", features = ["esp32s3", "log"] }
|
||||
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
|
||||
use esp_backtrace as _;
|
||||
use esp_hal::{
|
||||
clock::ClockControl,
|
||||
gpio::{Io, Level, Output},
|
||||
peripherals::Peripherals,
|
||||
system::SystemControl,
|
||||
timer::timg::TimerGroup,
|
||||
delay::Delay,
|
||||
prelude::*,
|
||||
};
|
||||
use esp_println::println;
|
||||
|
||||
#[entry]
|
||||
fn main() -> ! {
|
||||
// Inicializa periféricos do SoC com verificação em tempo de compilação
|
||||
let peripherals = Peripherals::take();
|
||||
let system = SystemControl::new(peripherals.SYSTEM);
|
||||
let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
|
||||
|
||||
// Configura os pinos de E/S
|
||||
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
|
||||
let mut led = Output::new(io.pins.gpio2, Level::Low);
|
||||
|
||||
let delay = Delay::new(&clocks);
|
||||
|
||||
println!("🦀 Firmware Rust Bare-Metal inicializado no ESP32!");
|
||||
|
||||
let mut counter: u32 = 0;
|
||||
|
||||
loop {
|
||||
// Inverte estado do LED com garantia de exclusão mútua
|
||||
led.toggle();
|
||||
counter += 1;
|
||||
|
||||
println!("Ciclo Rust #{}: LED está {:?}", counter, led.is_set_high());
|
||||
delay.delay_millis(500);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
#include <WiFi.h>
|
||||
|
||||
// Remplacez par les identifiants de votre réseau Wi-Fi
|
||||
const char* ssid = "NOM_DE_VOTRE_RESEAU";
|
||||
const char* password = "MOT_DE_PASSE_RESEAU";
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
delay(1000);
|
||||
|
||||
Serial.println("Connexion au Wi-Fi...");
|
||||
WiFi.begin(ssid, password);
|
||||
|
||||
// En attente de la connexion
|
||||
while (WiFi.status() != WL_CONNECTED) {
|
||||
delay(500);
|
||||
Serial.print(".");
|
||||
}
|
||||
|
||||
Serial.println("");
|
||||
Serial.println("Wi-Fi connecté avec succès !");
|
||||
Serial.print("Adresse IP : ");
|
||||
Serial.println(WiFi.localIP());
|
||||
}
|
||||
|
||||
void loop() {
|
||||
// Aqui você pode colocar o código principal do seu programa
|
||||
delay(1000);
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
#include "esp_log.h"
|
||||
#include "audio_pipeline.h"
|
||||
#include "audio_element.h"
|
||||
#include "audio_event_iface.h"
|
||||
#include "audio_common.h"
|
||||
#include "i2s_stream.h"
|
||||
#include "mp3_decoder.h"
|
||||
#include "fatfs_stream.h"
|
||||
#include "esp_peripherals.h"
|
||||
#include "periph_sdcard.h"
|
||||
|
||||
static const char *TAG = "HELLO_ADF";
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa periféricos (como o SD card)
|
||||
esp_periph_config_t periph_cfg = DEFAULT_ESP_PERIPH_SET_CONFIG();
|
||||
esp_periph_set_handle_t set = esp_periph_set_init(&periph_cfg);
|
||||
periph_sdcard_cfg_t sd_cfg = {
|
||||
.root = "/sdcard",
|
||||
};
|
||||
esp_periph_handle_t sdcard_handle = periph_sdcard_init(&sd_cfg);
|
||||
esp_periph_start(set, sdcard_handle);
|
||||
|
||||
// Espera o SD card montar
|
||||
periph_sdcard_wait_for_ready(sdcard_handle, portMAX_DELAY);
|
||||
|
||||
ESP_LOGI(TAG, "SD card montado!");
|
||||
|
||||
// Cria o pipeline
|
||||
audio_pipeline_handle_t pipeline;
|
||||
audio_pipeline_cfg_t pipeline_cfg = DEFAULT_AUDIO_PIPELINE_CONFIG();
|
||||
pipeline = audio_pipeline_init(&pipeline_cfg);
|
||||
|
||||
// Elementos: arquivo (fatfs), decodificador (mp3) e saída (i2s)
|
||||
audio_element_handle_t fatfs_stream_reader, i2s_stream_writer, mp3_decoder;
|
||||
|
||||
fatfs_stream_cfg_t fatfs_cfg = FATFS_STREAM_CFG_DEFAULT();
|
||||
fatfs_cfg.type = AUDIO_STREAM_READER;
|
||||
fatfs_stream_reader = fatfs_stream_init(&fatfs_cfg);
|
||||
|
||||
mp3_decoder_cfg_t mp3_cfg = DEFAULT_MP3_DECODER_CONFIG();
|
||||
mp3_decoder = mp3_decoder_init(&mp3_cfg);
|
||||
|
||||
i2s_stream_cfg_t i2s_cfg = I2S_STREAM_CFG_DEFAULT();
|
||||
i2s_cfg.type = AUDIO_STREAM_WRITER;
|
||||
i2s_stream_writer = i2s_stream_init(&i2s_cfg);
|
||||
|
||||
// Registra e conecta elementos
|
||||
audio_pipeline_register(pipeline, fatfs_stream_reader, "file");
|
||||
audio_pipeline_register(pipeline, mp3_decoder, "mp3");
|
||||
audio_pipeline_register(pipeline, i2s_stream_writer, "i2s");
|
||||
|
||||
audio_pipeline_link(pipeline, (const char *[]) {"file", "mp3", "i2s"}, 3);
|
||||
|
||||
// Define o arquivo MP3 a ser tocado
|
||||
audio_element_set_uri(fatfs_stream_reader, "/sdcard/test.mp3");
|
||||
|
||||
// Inicia o pipeline
|
||||
ESP_LOGI(TAG, "Iniciando pipeline...");
|
||||
audio_pipeline_run(pipeline);
|
||||
|
||||
// Mantém o pipeline rodando
|
||||
while (1) {
|
||||
vTaskDelay(1000 / portTICK_PERIOD_MS);
|
||||
}
|
||||
|
||||
// (Nunca chega aqui, mas seria o cleanup)
|
||||
audio_pipeline_stop(pipeline);
|
||||
audio_pipeline_wait_for_stop(pipeline);
|
||||
audio_pipeline_terminate(pipeline);
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_dsp.h"
|
||||
|
||||
#define N 8 // Tamanho do vetor
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Vetor de entrada (exemplo de sinal)
|
||||
float x[N] = {1.0, -2.0, 3.0, -4.0, 2.5, -1.5, 0.0, 4.5};
|
||||
float y[N]; // Vetor de saída
|
||||
|
||||
// Inicializa o ESP-DSP
|
||||
esp_err_t ret = dsps_fft2r_init_fc32(NULL, CONFIG_DSP_MAX_FFT_SIZE);
|
||||
if (ret != ESP_OK) {
|
||||
printf("Erro ao inicializar o ESP-DSP!\n");
|
||||
return;
|
||||
}
|
||||
|
||||
printf("Sinal de entrada:\n");
|
||||
for (int i = 0; i < N; i++) {
|
||||
printf("%f ", x[i]);
|
||||
}
|
||||
printf("\n");
|
||||
|
||||
// Calcula o quadrado de cada valor
|
||||
dsps_mulc_f32(x, y, N, 1.0f);
|
||||
dsps_mul_f32(y, y, y, N, 1, 1, 1);
|
||||
|
||||
// Soma todos os quadrados
|
||||
float soma = 0;
|
||||
dsps_sum_f32(y, N, &soma, 1);
|
||||
|
||||
// Calcula a magnitude (raiz da soma dos quadrados)
|
||||
float magnitude = sqrtf(soma);
|
||||
|
||||
printf("Magnitude do vetor: %f\n", magnitude);
|
||||
}
|
||||
@@ -0,0 +1,56 @@
|
||||
/*
|
||||
* Exemple ESP-IDF v5.x+ pour ESP32
|
||||
* Démonstration d'initialisation système, gestion des tâches FreeRTOS et journalisation unifiée
|
||||
*
|
||||
* Gestion des composants (main/idf_component.yml) :
|
||||
* dependencies:
|
||||
* espressif/led_strip: "^2.5.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_chip_info.h"
|
||||
|
||||
static const char *TAG = "main_app";
|
||||
|
||||
#define BLINK_GPIO GPIO_NUM_2 // Ajustez selon la broche de la LED de votre carte
|
||||
|
||||
static void blink_task(void *pvParameters)
|
||||
{
|
||||
// Configure la broche GPIO avec la nouvelle API ESP-IDF
|
||||
gpio_reset_pin(BLINK_GPIO);
|
||||
gpio_set_direction(BLINK_GPIO, GPIO_MODE_OUTPUT);
|
||||
|
||||
bool led_state = false;
|
||||
|
||||
while (1) {
|
||||
led_state = !led_state;
|
||||
gpio_set_level(BLINK_GPIO, led_state);
|
||||
|
||||
ESP_LOGI(TAG, "LED %s | Tas libre : %lu octets",
|
||||
led_state ? "ALLUMÉ" : "ÉTEINT",
|
||||
(unsigned long)esp_get_free_heap_size());
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(1000));
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Informações do chip SoC
|
||||
esp_chip_info_t chip_info;
|
||||
esp_chip_info(&chip_info);
|
||||
|
||||
ESP_LOGI(TAG, "===========================================");
|
||||
ESP_LOGI(TAG, " Iniciando ESP-IDF v5.x Modern Application ");
|
||||
ESP_LOGI(TAG, " Modelo do Chip: %d | Núcleos: %d | Rev: %d",
|
||||
chip_info.model, chip_info.cores, chip_info.revision);
|
||||
ESP_LOGI(TAG, "===========================================");
|
||||
|
||||
// Cria uma tarefa FreeRTOS dedicada
|
||||
xTaskCreate(blink_task, "blink_task", 3072, NULL, 5, NULL);
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
* Exemplo ESP-IoT-Solution para ESP32
|
||||
* Inicialização de Botão Inteligente com Callbacks e Driver de Display/Sensores
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/button: "^3.3.0"
|
||||
* espressif/led_indicator: "^1.2.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "iot_button.h"
|
||||
#include "led_indicator.h"
|
||||
|
||||
static const char *TAG = "iot_solution_app";
|
||||
|
||||
#define BUTTON_GPIO_NUM 0 // Botão BOOT nativo
|
||||
#define LED_INDICATOR_GPIO 2 // LED indicador
|
||||
|
||||
static led_indicator_handle_t led_handle = NULL;
|
||||
|
||||
/* Callback para clique único do botão */
|
||||
static void button_single_click_cb(void *arg, void *data)
|
||||
{
|
||||
ESP_LOGI(TAG, "Evento: Clique Único detectado!");
|
||||
led_indicator_start(led_handle, BLINK_DOUBLE_FAST);
|
||||
}
|
||||
|
||||
/* Callback para clique longo (> 3 segundos) */
|
||||
static void button_long_press_cb(void *arg, void *data)
|
||||
{
|
||||
ESP_LOGW(TAG, "Evento: Pressionamento Longo! Acionando modo de reset de fábrica.");
|
||||
led_indicator_start(led_handle, BLINK_BREATHE_FAST);
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_LOGI(TAG, "Iniciando ESP-IoT-Solution Component Suite");
|
||||
|
||||
// 1. Configuração do LED Indicator
|
||||
led_indicator_gpio_config_t led_cfg = {
|
||||
.is_active_level_high = true,
|
||||
.gpio_num = LED_INDICATOR_GPIO,
|
||||
};
|
||||
led_handle = led_indicator_create(&led_cfg);
|
||||
|
||||
// 2. Configuração do Botão com debounce de hardware/software automático
|
||||
button_config_t btn_cfg = {
|
||||
.type = BUTTON_TYPE_GPIO,
|
||||
.long_press_time = 3000,
|
||||
.short_press_time = 180,
|
||||
.gpio_button_config = {
|
||||
.gpio_num = BUTTON_GPIO_NUM,
|
||||
.active_level = 0,
|
||||
},
|
||||
};
|
||||
|
||||
button_handle_t btn_handle = iot_button_create(&btn_cfg);
|
||||
assert(btn_handle != NULL);
|
||||
|
||||
// Registra callbacks para diferentes gestos
|
||||
iot_button_register_cb(btn_handle, BUTTON_SINGLE_CLICK, button_single_click_cb, NULL);
|
||||
iot_button_register_cb(btn_handle, BUTTON_LONG_PRESS_START, button_long_press_cb, NULL);
|
||||
|
||||
ESP_LOGI(TAG, "Drivers inicializados com sucesso! Pressione o botão GPIO 0.");
|
||||
|
||||
while (1) {
|
||||
vTaskDelay(pdMS_TO_TICKS(1000));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_log.h"
|
||||
#include "esp_matter.h"
|
||||
#include "esp_matter_controller.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
static const char *TAG = "esp-matter-example";
|
||||
|
||||
void app_event_cb(const esp_matter_event_t *event)
|
||||
{
|
||||
switch (event->event_id) {
|
||||
case ESP_MATTER_EVENT_ATTRIBUTE_UPDATE: {
|
||||
const esp_matter_attr_update_t *attr_update = &event->data.attr_update;
|
||||
if (attr_update->endpoint_id == 1 && attr_update->cluster_id == ESP_MATTER_ON_OFF_CLUSTER_ID) {
|
||||
bool on = false;
|
||||
esp_matter_attribute_get(attr_update->endpoint_id, attr_update->cluster_id,
|
||||
attr_update->attribute_id, &on);
|
||||
ESP_LOGI(TAG, "Lâmpada %s", on ? "ligada" : "desligada");
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa NVS
|
||||
esp_err_t err = nvs_flash_init();
|
||||
if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
|
||||
ESP_ERROR_CHECK(nvs_flash_erase());
|
||||
ESP_ERROR_CHECK(nvs_flash_init());
|
||||
}
|
||||
|
||||
// Inicializa o Matter node
|
||||
esp_matter::node_t *node = esp_matter::node::create(NULL, app_event_cb);
|
||||
esp_matter::endpoint_t *endpoint = esp_matter::endpoint::create(node, ESP_MATTER_ENDPOINT_TYPE_ON_OFF_LIGHT);
|
||||
|
||||
// Inicia o stack Matter
|
||||
ESP_ERROR_CHECK(esp_matter::start(node));
|
||||
|
||||
ESP_LOGI(TAG, "Dispositivo Matter iniciado. Aguardando comissionamento...");
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
#include <stdio.h>
|
||||
#include "esp_nn.h"
|
||||
#include "esp_nn_defs.h"
|
||||
|
||||
#define INPUT_SIZE 4
|
||||
#define OUTPUT_SIZE 3
|
||||
|
||||
void print_array(const char *label, int16_t *array, int size) {
|
||||
printf("%s: ", label);
|
||||
for (int i = 0; i < size; i++) {
|
||||
printf("%d ", array[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Vetor de entrada (ex: saída de uma camada anterior)
|
||||
int16_t input[INPUT_SIZE] = {1, 2, 3, 4};
|
||||
|
||||
// Pesos da camada densa (3x4)
|
||||
int8_t weights[OUTPUT_SIZE * INPUT_SIZE] = {
|
||||
1, -1, 2, 0,
|
||||
0, 1, -1, 1,
|
||||
2, 0, 1, -2
|
||||
};
|
||||
|
||||
// Bias de cada neurônio
|
||||
int16_t bias[OUTPUT_SIZE] = {10, -5, 0};
|
||||
|
||||
// Saída
|
||||
int16_t output[OUTPUT_SIZE];
|
||||
|
||||
// Multiplicação da matriz: output = weights * input + bias
|
||||
esp_nn_mul_mat_16x8_16(weights, input, bias, output,
|
||||
OUTPUT_SIZE, INPUT_SIZE, /*shift=*/0);
|
||||
|
||||
print_array("Antes da ReLU", output, OUTPUT_SIZE);
|
||||
|
||||
// Aplicar função de ativação ReLU
|
||||
esp_nn_relu_16(output, OUTPUT_SIZE);
|
||||
|
||||
print_array("Depois da ReLU", output, OUTPUT_SIZE);
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Exemplo ESP-NOW para ESP32
|
||||
* Comunicação Sem Fio Ponto-a-Ponto e Broadcast sem roteador Wi-Fi
|
||||
*
|
||||
* Protocolo nativo integrado no ESP-IDF
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_wifi.h"
|
||||
#include "esp_now.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
static const char *TAG = "esp_now_demo";
|
||||
|
||||
// Estrutura de dados enviada no pacote
|
||||
typedef struct {
|
||||
uint32_t sensor_id;
|
||||
float temperatura;
|
||||
float umidade;
|
||||
uint32_t tempo_ms;
|
||||
} __attribute__((packed)) dados_pacote_t;
|
||||
|
||||
// Endereço MAC de Broadcast (envia para todos os nós ESP-NOW por perto)
|
||||
static const uint8_t broadcast_mac[ESP_NOW_ETH_ALEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
|
||||
|
||||
/* Callback executado ao enviar um pacote */
|
||||
static void on_data_sent(const uint8_t *mac_addr, esp_now_send_status_t status)
|
||||
{
|
||||
ESP_LOGI(TAG, "Envio concluído: %s", status == ESP_NOW_SEND_SUCCESS ? "SUCESSO (ACK)" : "FALHA");
|
||||
}
|
||||
|
||||
/* Callback executado ao receber um pacote de outro ESP32 */
|
||||
static void on_data_recv(const esp_now_recv_info_t *recv_info, const uint8_t *data, int len)
|
||||
{
|
||||
if (len == sizeof(dados_pacote_t)) {
|
||||
dados_pacote_t *pct = (dados_pacote_t *)data;
|
||||
ESP_LOGI(TAG, "Pacote recebido de [%02X:%02X:%02X:%02X:%02X:%02X]: Sensor #%ld | Temp: %.1f C | Umid: %.1f %%",
|
||||
recv_info->src_addr[0], recv_info->src_addr[1], recv_info->src_addr[2],
|
||||
recv_info->src_addr[3], recv_info->src_addr[4], recv_info->src_addr[5],
|
||||
pct->sensor_id, pct->temperatura, pct->umidade);
|
||||
}
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicializa NVS e Wi-Fi em modo Station
|
||||
nvs_flash_init();
|
||||
esp_netif_init();
|
||||
esp_event_loop_create_default();
|
||||
wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT();
|
||||
esp_wifi_init(&cfg);
|
||||
esp_wifi_set_mode(WIFI_MODE_STA);
|
||||
esp_wifi_start();
|
||||
|
||||
// Inicializa o protocolo ESP-NOW
|
||||
ESP_ERROR_CHECK(esp_now_init());
|
||||
esp_now_register_send_cb(on_data_sent);
|
||||
esp_now_register_recv_cb(on_data_recv);
|
||||
|
||||
// Registra o peer de Broadcast
|
||||
esp_now_peer_info_t peer_info = {
|
||||
.channel = 1,
|
||||
.ifidx = WIFI_IF_STA,
|
||||
.encrypt = false,
|
||||
};
|
||||
memcpy(peer_info.peer_addr, broadcast_mac, ESP_NOW_ETH_ALEN);
|
||||
ESP_ERROR_CHECK(esp_now_add_peer(&peer_info));
|
||||
|
||||
ESP_LOGI(TAG, "ESP-NOW pronto! Enviando telemetria a cada 3 segundos...");
|
||||
|
||||
dados_pacote_t telemetria = {
|
||||
.sensor_id = 101,
|
||||
.temperatura = 24.8f,
|
||||
.umidade = 58.2f,
|
||||
};
|
||||
|
||||
while (1) {
|
||||
telemetria.tempo_ms = esp_log_timestamp();
|
||||
telemetria.temperatura += ((float)(rand() % 10) - 5.0f) / 10.0f;
|
||||
|
||||
esp_err_t res = esp_now_send(broadcast_mac, (uint8_t *)&telemetria, sizeof(telemetria));
|
||||
if (res != ESP_OK) {
|
||||
ESP_LOGE(TAG, "Erro ao disparar envio ESP-NOW: %d", res);
|
||||
}
|
||||
|
||||
vTaskDelay(pdMS_TO_TICKS(3000));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* Exemplo ESP-RainMaker para ESP32
|
||||
* Dispositivo: Interruptor Inteligente com controle via App e Nuvem
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp_rainmaker: "^1.4.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
#include <esp_rmaker_core.h>
|
||||
#include <esp_rmaker_standard_params.h>
|
||||
#include <esp_rmaker_standard_devices.h>
|
||||
#include <app_wifi.h>
|
||||
|
||||
static const char *TAG = "app_rainmaker";
|
||||
static esp_rmaker_device_t *switch_device;
|
||||
|
||||
/* Callback acionado quando o usuário altera o estado no App móvel */
|
||||
static esp_err_t write_cb(const esp_rmaker_device_t *dev, const esp_rmaker_param_val_t val, void *priv_data, esp_rmaker_write_ctx_t *ctx)
|
||||
{
|
||||
if (ctx) {
|
||||
ESP_LOGI(TAG, "Comando recebido via %s", esp_rmaker_device_cb_src_to_str(ctx->src));
|
||||
}
|
||||
|
||||
bool state = val.val.b;
|
||||
ESP_LOGI(TAG, "État de l'interrupteur modifié en : %s", state ? "ALLUMÉ" : "ÉTEINT");
|
||||
|
||||
// Met à jour le paramètre dans le cloud et l'application
|
||||
esp_rmaker_param_update_and_report(priv_data, val);
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
// Inicialização da memória não-volátil (NVS)
|
||||
esp_err_t err = nvs_flash_init();
|
||||
if (err == ESP_ERR_NVS_NO_FREE_PAGES || err == ESP_ERR_NVS_NEW_VERSION_FOUND) {
|
||||
ESP_ERROR_CHECK(nvs_flash_erase());
|
||||
err = nvs_flash_init();
|
||||
}
|
||||
ESP_ERROR_CHECK(err);
|
||||
|
||||
// Inicializa o provisionamento Wi-Fi
|
||||
app_wifi_init();
|
||||
|
||||
// Configura o nó RainMaker
|
||||
esp_rmaker_config_t rainmaker_cfg = {
|
||||
.enable_time_sync = true,
|
||||
};
|
||||
esp_rmaker_node_t *node = esp_rmaker_node_init(&rainmaker_cfg, "ESP32_SmartSwitch", "Switch");
|
||||
|
||||
// Cria o dispositivo padrão 'Switch'
|
||||
switch_device = esp_rmaker_switch_device_create("Luz Sala", NULL, true);
|
||||
|
||||
// Registra callback de escrita
|
||||
esp_rmaker_device_add_cb(switch_device, write_cb, NULL);
|
||||
esp_rmaker_node_add_device(node, switch_device);
|
||||
|
||||
// Habilita serviços adicionais (OTA e Timezone)
|
||||
esp_rmaker_ota_enable_default();
|
||||
esp_rmaker_timezone_service_enable();
|
||||
|
||||
// Inicia o agente RainMaker
|
||||
esp_rmaker_start();
|
||||
|
||||
// Inicia o provisionamento Wi-Fi via BLE (abre no app oficial RainMaker)
|
||||
app_wifi_start(POP_TYPE_RANDOM);
|
||||
|
||||
ESP_LOGI(TAG, "Nó RainMaker pronto! Escaneie o QR Code no app ESP RainMaker.");
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
* Exemplo ESP-SR para ESP32-S3 / ESP32-P4
|
||||
* Reconhecimento de Fala Local Offline (WakeNet + MultiNet)
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp-sr: "^1.5.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_wn_iface.h"
|
||||
#include "esp_wn_models.h"
|
||||
#include "esp_mn_iface.h"
|
||||
#include "esp_mn_models.h"
|
||||
#include "esp_afe_sr_iface.h"
|
||||
#include "esp_afe_sr_models.h"
|
||||
|
||||
static const char *TAG = "app_voice_sr";
|
||||
|
||||
void feed_audio_task(void *arg)
|
||||
{
|
||||
esp_afe_sr_data_t *afe_data = (esp_afe_sr_data_t *)arg;
|
||||
int audio_chunksize = afe_handle->get_feed_chunksize(afe_data);
|
||||
int16_t *feed_buff = (int16_t *)malloc(audio_chunksize * sizeof(int16_t) * 2);
|
||||
|
||||
while (1) {
|
||||
// Leitura de áudio I2S dos microfones da placa
|
||||
// i2s_read(I2S_NUM_0, feed_buff, ...);
|
||||
|
||||
afe_handle->feed(afe_data, feed_buff);
|
||||
vTaskDelay(pdMS_TO_TICKS(10));
|
||||
}
|
||||
free(feed_buff);
|
||||
vTaskDelete(NULL);
|
||||
}
|
||||
|
||||
void speech_recognition_task(void *arg)
|
||||
{
|
||||
esp_afe_sr_data_t *afe_data = (esp_afe_sr_data_t *)arg;
|
||||
const esp_afe_sr_iface_t *afe_handle = &ESP_AFE_SR_HANDLE;
|
||||
|
||||
// Inicializa o modelo de comandos de fala (MultiNet)
|
||||
const esp_mn_iface_t *multinet = &ESP_MN_HANDLE;
|
||||
model_iface_data_t *model_data = multinet->create(&MULTINET_MODEL, 6000);
|
||||
|
||||
ESP_LOGI(TAG, "Aguardando palavra-chave de ativação (ex: 'Hi, ESP')...");
|
||||
|
||||
while (1) {
|
||||
afe_fetch_result_t *res = afe_handle->fetch(afe_data);
|
||||
if (!res || res->ret_value == ESP_FAIL) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// 1. Verificação de Wake Word (Palavra de ativação)
|
||||
if (res->wake_word_detected == WAKENET_DETECTED) {
|
||||
ESP_LOGW(TAG, ">>> PALAVRA-CHAVE DETECTADA! Canal de escuta aberto.");
|
||||
}
|
||||
|
||||
// 2. Reconhecimento de comando local
|
||||
if (res->raw_data_size > 0) {
|
||||
esp_mn_state_t mn_state = multinet->detect(model_data, res->data);
|
||||
|
||||
if (mn_state == ESP_MN_STATE_DETECTED) {
|
||||
esp_mn_results_t *mn_res = multinet->get_results(model_data);
|
||||
ESP_LOGI(TAG, ">>> COMANDO RECONHECIDO: ID #%d (Frase correspondente)", mn_res->command_id[0]);
|
||||
|
||||
// Exemplo de ação
|
||||
if (mn_res->command_id[0] == 1) {
|
||||
ESP_LOGI(TAG, "Ação: Ligar Luz da Sala");
|
||||
} else if (mn_res->command_id[0] == 2) {
|
||||
ESP_LOGI(TAG, "Ação: Desligar Luz da Sala");
|
||||
}
|
||||
} else if (mn_state == ESP_MN_STATE_TIMEOUT) {
|
||||
ESP_LOGI(TAG, "Tempo esgotado. Retornando ao modo de escuta de Wake Word.");
|
||||
}
|
||||
}
|
||||
}
|
||||
vTaskDelete(NULL);
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_LOGI(TAG, "Iniciando ESP-SR Speech Recognition Engine");
|
||||
|
||||
// Configura o pipeline de Audio Front-End (AEC, BSS, VAD, WakeNet)
|
||||
afe_config_t afe_config = AFE_CONFIG_DEFAULT();
|
||||
afe_config.wakenet_init = true;
|
||||
afe_config.voice_communication_init = false;
|
||||
|
||||
esp_afe_sr_data_t *afe_data = ESP_AFE_SR_HANDLE.create_from_config(&afe_config);
|
||||
|
||||
// Cria as tarefas de alimentação de áudio e reconhecimento
|
||||
xTaskCreatePinnedToCore(feed_audio_task, "feed_task", 4096, afe_data, 5, NULL, 0);
|
||||
xTaskCreatePinnedToCore(speech_recognition_task, "sr_task", 8192, afe_data, 5, NULL, 1);
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
#include "esp_camera.h"
|
||||
#include "fd_forward.h" // Face Detection
|
||||
#include "fr_forward.h" // Face Recognition
|
||||
#include "human_face_detect_msr01.hpp"
|
||||
#include "human_face_detect_mnp01.hpp"
|
||||
|
||||
#define CAMERA_MODEL_AI_THINKER // ou o modelo da sua placa
|
||||
|
||||
#include "camera_pins.h"
|
||||
|
||||
void setup() {
|
||||
Serial.begin(115200);
|
||||
Serial.setDebugOutput(true);
|
||||
Serial.println("Iniciando câmera...");
|
||||
|
||||
camera_config_t config;
|
||||
config.ledc_channel = LEDC_CHANNEL_0;
|
||||
config.ledc_timer = LEDC_TIMER_0;
|
||||
config.pin_d0 = Y2_GPIO_NUM;
|
||||
config.pin_d1 = Y3_GPIO_NUM;
|
||||
config.pin_d2 = Y4_GPIO_NUM;
|
||||
config.pin_d3 = Y5_GPIO_NUM;
|
||||
config.pin_d4 = Y6_GPIO_NUM;
|
||||
config.pin_d5 = Y7_GPIO_NUM;
|
||||
config.pin_d6 = Y8_GPIO_NUM;
|
||||
config.pin_d7 = Y9_GPIO_NUM;
|
||||
config.pin_xclk = XCLK_GPIO_NUM;
|
||||
config.pin_pclk = PCLK_GPIO_NUM;
|
||||
config.pin_vsync = VSYNC_GPIO_NUM;
|
||||
config.pin_href = HREF_GPIO_NUM;
|
||||
config.pin_sscb_sda = SIOD_GPIO_NUM;
|
||||
config.pin_sscb_scl = SIOC_GPIO_NUM;
|
||||
config.pin_pwdn = PWDN_GPIO_NUM;
|
||||
config.pin_reset = RESET_GPIO_NUM;
|
||||
config.xclk_freq_hz = 20000000;
|
||||
config.pixel_format = PIXFORMAT_RGB565;
|
||||
config.frame_size = FRAMESIZE_QVGA;
|
||||
config.fb_count = 1;
|
||||
|
||||
if (esp_camera_init(&config) != ESP_OK) {
|
||||
Serial.println("Falha ao iniciar a câmera!");
|
||||
return;
|
||||
}
|
||||
|
||||
Serial.println("Câmera inicializada com sucesso!");
|
||||
}
|
||||
|
||||
void loop() {
|
||||
camera_fb_t *fb = esp_camera_fb_get();
|
||||
if (!fb) {
|
||||
Serial.println("Falha ao capturar imagem!");
|
||||
return;
|
||||
}
|
||||
|
||||
// Detecta rostos na imagem
|
||||
box_array_t *faces = face_detect_msr01(fb->buf, fb->width, fb->height, fb->format);
|
||||
if (faces) {
|
||||
Serial.printf("Rostos detectados: %d\n", faces->len);
|
||||
for (int i = 0; i < faces->len; i++) {
|
||||
box_t *box = &faces->box[i];
|
||||
Serial.printf("Face %d - x:%d y:%d w:%d h:%d\n", i, box->box_p[0], box->box_p[1],
|
||||
box->box_p[2] - box->box_p[0], box->box_p[3] - box->box_p[1]);
|
||||
}
|
||||
dl_lib_free(faces);
|
||||
} else {
|
||||
Serial.println("Nenhum rosto detectado.");
|
||||
}
|
||||
|
||||
esp_camera_fb_return(fb);
|
||||
delay(1000);
|
||||
}
|
||||
@@ -0,0 +1,97 @@
|
||||
/*
|
||||
* Exemplo ESP-Zigbee-SDK para ESP32-H2 e ESP32-C6 (IEEE 802.15.4)
|
||||
* Dispositivo: Lâmpada Inteligente Zigbee 3.0 (Home Automation End Device)
|
||||
*
|
||||
* Dependência (idf_component.yml):
|
||||
* espressif/esp-zigbee-lib: "^1.6.0"
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
#include "esp_zigbee_core.h"
|
||||
|
||||
static const char *TAG = "zigbee_light_device";
|
||||
|
||||
#define HA_ESP_LIGHT_ENDPOINT 1
|
||||
#define ESP_ZB_PRIMARY_CHANNEL_MASK (1l << 15) // Canal 15 padrão Zigbee
|
||||
|
||||
/* Callback de escrita em atributos Zigbee (ex: Liga/Desliga via Home Assistant) */
|
||||
static esp_err_t zb_attribute_handler(const esp_zb_zcl_set_attr_value_message_t *message)
|
||||
{
|
||||
if (message->info.cluster == ESP_ZB_ZCL_CLUSTER_ID_ON_OFF) {
|
||||
if (message->attribute.id == ESP_ZB_ZCL_ATTR_ON_OFF_ON_OFF_ID &&
|
||||
message->attribute.data.type == ESP_ZB_ZCL_ATTR_TYPE_BOOL) {
|
||||
bool on_off_state = message->attribute.data.value ? *(bool *)message->attribute.data.value : false;
|
||||
ESP_LOGW(TAG, ">>> COMANDO ZIGBEE RECEBIDO: Lâmpada %s", on_off_state ? "LIGADA" : "DESLIGADA");
|
||||
}
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
/* Callback de eventos da pilha Zigbee */
|
||||
void esp_zb_app_signal_handler(esp_zb_app_signal_msg_t *signal_msg)
|
||||
{
|
||||
uint32_t *p_sg_p = signal_msg->p_app_signal;
|
||||
esp_err_t err_status = signal_msg->esp_err_status;
|
||||
esp_zb_app_signal_type_t sig_type = *p_sg_p;
|
||||
|
||||
switch (sig_type) {
|
||||
case ESP_ZB_ZDO_SIGNAL_SKIP_STARTUP:
|
||||
ESP_LOGI(TAG, "Iniciando comissionamento na rede Zigbee...");
|
||||
esp_zb_bdb_start_top_level_commissioning(ESP_ZB_BDB_MODE_NETWORK_STEERING);
|
||||
break;
|
||||
case ESP_ZB_BDB_SIGNAL_STEERING:
|
||||
if (err_status == ESP_OK) {
|
||||
ESP_LOGI(TAG, "Conectado com sucesso à rede Zigbee 3.0!");
|
||||
} else {
|
||||
ESP_LOGW(TAG, "Buscando coordenador Zigbee novamente...");
|
||||
esp_zb_scheduler_alarm((esp_zb_callback_t)esp_zb_bdb_start_top_level_commissioning, ESP_ZB_BDB_MODE_NETWORK_STEERING, 1000);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void esp_zb_task(void *pvParameters)
|
||||
{
|
||||
// Configura nó Zigbee como End Device
|
||||
esp_zb_cfg_t zb_nwk_cfg = {
|
||||
.esp_zb_role = ESP_ZB_DEVICE_TYPE_ED,
|
||||
.install_code_policy = false,
|
||||
.nwk_cfg.zed_cfg = {
|
||||
.ed_timeout = ESP_ZB_ED_0_5_MIN,
|
||||
.keep_alive = 3000,
|
||||
},
|
||||
};
|
||||
esp_zb_init(&zb_nwk_cfg);
|
||||
|
||||
// Cria o cluster de On/Off de iluminação residencial
|
||||
esp_zb_on_off_light_cfg_t light_cfg = ESP_ZB_DEFAULT_ON_OFF_LIGHT_CONFIG();
|
||||
esp_zb_ep_list_t *ep_list = esp_zb_on_off_light_ep_create(HA_ESP_LIGHT_ENDPOINT, &light_cfg);
|
||||
|
||||
// Registra endpoint e manipulador de atributos
|
||||
esp_zb_device_register(ep_list);
|
||||
esp_zb_core_action_handler_register(zb_attribute_handler);
|
||||
|
||||
esp_zb_set_primary_network_channel_set(ESP_ZB_PRIMARY_CHANNEL_MASK);
|
||||
ESP_ERROR_CHECK(esp_zb_start(false));
|
||||
esp_zb_main_loop_iteration();
|
||||
}
|
||||
|
||||
void app_main(void)
|
||||
{
|
||||
ESP_ERROR_CHECK(nvs_flash_init());
|
||||
|
||||
// Inicializa a pilha de rádio IEEE 802.15.4
|
||||
esp_zb_platform_config_t config = {
|
||||
.radio_config = { .radio_mode = ZB_RADIO_MODE_NATIVE },
|
||||
.host_config = { .host_connection_mode = ZB_HOST_CONNECTION_MODE_NONE },
|
||||
};
|
||||
ESP_ERROR_CHECK(esp_zb_platform_config(&config));
|
||||
|
||||
xTaskCreate(esp_zb_task, "Zigbee_main", 4096, NULL, 5, NULL);
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
from machine import Pin
|
||||
from time import sleep
|
||||
|
||||
# Définit la broche 2 en sortie (généralement la LED intégrée)
|
||||
led = Pin(2, Pin.OUT)
|
||||
|
||||
while True:
|
||||
led.value(1) # Allume la LED
|
||||
sleep(0.5) # Attend 0,5 seconde
|
||||
led.value(0) # Éteint la LED
|
||||
sleep(0.5) # Attend 0,5 seconde
|
||||
Loaded 100 of 104 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user