En parcourant Internet pour m'inspirer, je suis tombé sur un composant intéressant.
Je pensais que le bloc avec l'illustration ASCII en cours d'exécution avait l'air cool, mais je n'arrivais pas à comprendre comment il était implémenté, alors j'ai commencé à regarder le code source.
J'ai trouvé le code qui semblait faire le travail, mais il a été minifié.
const { floor: ra, abs: KE, min: QE } = Math, O5 = ["reactive.network REACTIVE.NETWORK", "$@B%8&WM#*oahkbdpqwmZO0QLCJUYXzcvunxrjft/|()1{}[]?-_+~<>i!lI;:,^`'. .:â–‘â–’â–“â–ˆ"], G7 = Date.now() % 3 ? O5[1] : O5[0], V5 = G7.length, JE = { fps: 60 }; function eT(e, t, n, r) { const i = t.time * 8e-5, s = QE(t.cols, t.rows), o = t.metrics.aspect * 0.2, l = { x: ((4 * (e.x - t.cols / 6.25)) / s) * o, y: (5 * (e.y - t.rows / 4)) / s }, u = ra(KE(YE(l) - i) * V5 + (ra(e.x / 1) % 2) * 2) % V5; return G7[u]; } const tT = () => { const e = j.useRef(null), [t, n] = j.useState({ height: null, width: null }); return ( j.useEffect(() => { function r() { n({ height: window.innerHeight, width: window.innerWidth }); } if (typeof window < "u") return n({ height: window.innerHeight, width: window.innerWidth }), window.addEventListener("resize", r), () => window.removeEventListener("resize", r); }, []), j.useEffect(() => { const r = e.current; if (!r) return; const i = 12, s = ra(t.width / i) * 1.6, o = ra(t.height / i), l = { aspect: s / o }, u = setInterval(() => { let c = ""; for (let d = 0; d < o; d++) { for (let f = 0; f < s; f++) c += eT({ x: f, y: d }, { cols: s, rows: o, metrics: l, time: Date.now() }); c += ` `; } r.textContent = c; }, 1e3 / JE.fps); return () => clearInterval(u); }, [t]), a.jsx("div", { style: { position: "absolute", top: 0, left: 0, width: "100%", height: "100%" }, children: a.jsx("div", { ref: e, style: { width: "100%", height: "100%", whiteSpace: "pre", overflow: "hidden" } }) }) ); }; function nT(e) { return Math.cos(e.x * e.x - e.y * e.y); } const { floor: ia, abs: rT, min: iT } = Math, D5 = ["reactive.network REACTIVE.NETWORK", "$@B%8&WM#*oahkbdpqwmZO0QLCJUYXzcvunxrjft/|()1{}[]?-_+~<>i!lI;:,^`'. .:â–‘â–’â–“â–ˆ"], X7 = Date.now() % 3 ? D5[1] : D5[0], F5 = X7.length, sT = { fps: 60 }; function oT(e, t, n, r) { const i = t.time * 8e-5, s = iT(t.cols, t.rows), o = t.metrics.aspect * 0.2, l = { x: ((4 * (e.x - t.cols / 6.25)) / s) * o, y: (5 * (e.y - t.rows / 4)) / s }, u = ia(rT(nT(l) - i) * F5 + (ia(e.x / 1) % 2) * 2) % F5; return X7[u]; } const aT = () => { const e = j.useRef(null), [t, n] = j.useState({ height: null, width: null }); return ( j.useEffect(() => { function r() { n({ height: window.innerHeight, width: window.innerWidth }); } if (typeof window < "u") return n({ height: window.innerHeight, width: window.innerWidth }), window.addEventListener("resize", r), () => window.removeEventListener("resize", r); }, []), j.useEffect(() => { const r = e.current; if (!r) return; const i = 12, s = ia(t.width / i) * 1.6, o = ia(t.height / i), l = { aspect: s / o }, u = setInterval(() => { let c = ""; for (let d = 0; d < o; d++) { for (let f = 0; f < s; f++) c += oT({ x: f, y: d }, { cols: s, rows: o, metrics: l, time: Date.now() }); c += ` `; } r.textContent = c; }, 1e3 / sT.fps); return () => clearInterval(u); }, [t]), a.jsx("div", { style: { position: "absolute", top: 0, left: 0, width: "100%", height: "100%" }, children: a.jsx("div", { ref: e, style: { width: "100%", height: "100%", whiteSpace: "pre", overflow: "hidden" } }) }) ); },
Habituellement, je lisais simplement le code réduit pour comprendre l'implémentation (ou cherchais un fichier .map pour restaurer le code d'origine). Cependant, j'ai réalisé que je n'avais jamais essayé de demander à ChatGPT de le faire à ma place... J'ai donc copié tout le code ci-dessus et j'ai demandé à ChatGPT de "expliquer le code". Voici la réponse :
Le code fourni est assez complexe, mais je vais le décomposer dans un format plus compréhensible, en expliquant ses différentes parties et leurs fonctionnalités.
Aperçu
Le code définit plusieurs fonctions et composants utilisant JavaScript, notamment dans le cadre d'une application React. Il s'agit de générer du contenu textuel dynamique, vraisemblablement de l'art ASCII ou une sorte d'effet visuel utilisant des caractères d'un ensemble prédéfini. De plus, il comprend des fonctions utilitaires pour la gestion des événements, la synchronisation des performances et la conversion de contenu HTML.
Composants et fonctions clés
- Sélection du jeu de caractères :
``javascript
const { étage : ra, abs : KE, min : QE } = Math ;
const O5 = ["reactive.network REACTIVE.NETWORK", "$@B%8&WM#*oahkbdpqwmZO0QLCJUYXzcvunxrjft/|()1{}[]?-_+~<>i!lI;:,^'. . :â–'â–'â–«â–ˆ"];
const G7 = Date.now() % 3 ? O5[1] : O5[0];
const V5 = G7.longueur;- This part of the code imports some common Math functions (`floor`, `abs`, and `min`) and defines two sets of characters, stored in `O5`. - Based on the current time (`Date.now() % 3`), it selects one of these sets (`G7`) to use later. - The length of the selected character set is stored in `V5`. 2. **Dynamic Character Selection Function:** ```javascript function eT(e, t, n, r) { const i = t.time * 8e-5; const s = QE(t.cols, t.rows); const o = t.metrics.aspect * 0.2; const l = { x: ((4 * (e.x - t.cols / 6.25)) / s) * o, y: (5 * (e.y - t.rows / 4)) / s }; const u = ra(KE(YE(l) - i) * V5 + (ra(e.x / 1) % 2) * 2) % V5; return G7[u]; }Copier après la connexion
- La fonction eT génère un caractère basé sur la position d'entrée (e.x, e.y) et l'heure actuelle (t.time).
- Il ajuste la position à l'aide de certains calculs de rapport hauteur/largeur et sélectionne un caractère de G7 en fonction d'une combinaison de position et d'heure.
- Le but de la fonction YE n'est pas directement clair dans le code, mais il semble que ce soit une fonction personnalisée utilisée dans ce calcul.
- Composant React (tT) pour l'affichage de contenu dynamique :
```javascript
const tT = () => {
const e = j.useRef(null);
const [t, n] = j.useState({ hauteur : null, largeur : null });
j.useEffect(() => {
fonction r() {
n({ hauteur : window.innerHeight, largeur : window.innerWidth });
>
if (type de fenêtre < "u") {
n({ hauteur : window.innerHeight, largeur : window.innerWidth });
window.addEventListener("resize", r);
return () => window.removeEventListener("resize", r);
>
}, []);j.useEffect(() => { const r = e.current; if (!r) return; const i = 12; const s = ra(t.width / i) * 1.6; const o = ra(t.height / i); const l = { aspect: s / o }; const u = setInterval(() => { let c = ""; for (let d = 0; d < o; d++) { for (let f = 0; f < s; f++) c += eT({ x: f, y: d }, { cols: s, rows: o, metrics: l, time: Date.now() }); c += `Copier après la connexion`;
>
r.textContent = c;
}, 1e3 / JE.fps);
return () => clearInterval(u);
}, [t]);return a.jsx("div", { style: { position: "absolute", top: 0, left: 0, width: "100%", height: "100%" }, children: a.jsx("div", { ref: e, style: { width: "100%", height: "100%", whiteSpace: "pre", overflow: "hidden" } }) });Copier après la connexion};
- This is a React component that sets up an interval to periodically update the content of a `div` element (`e.current`) with dynamically generated characters. - It calculates the number of columns (`s`) and rows (`o`) based on the window size and then fills the `div` with characters generated by the `eT` function. - The effect runs at a specified frames per second (`JE.fps`).Copier après la connexion
J'ai ensuite demandé d'"implémenter un code équivalent dans TypeScript et de le rendre lisible par l'homme" et j'ai obtenu la réponse suivante :
import React, { useEffect, useRef, useState } from 'react'; const selectedCharacterSet = "$@B%8&WM#*oahkbdpqwmZO0QLCJUYXzcvunxrjft/|()1{}[]?-_+~<>i!lI;:,^`'. .:â–‘â–’â–“â–ˆ"; const characterSetLength = selectedCharacterSet.length; const calculateCharacter = ( x: number, y: number, cols: number, rows: number, aspect: number, time: number, ): string => { const timeFactor = time * 0.000_08; const size = Math.min(cols, rows); const aspectRatio = aspect * 0.2; const position = { x: ((4 * (x - cols / 6.25)) / size) * aspectRatio, y: (5 * (y - rows / 4)) / size, }; const index = Math.floor( Math.abs( Math.cos(position.x * position.x - position.y * position.y) - timeFactor, ) * characterSetLength + (Math.floor(x) % 2) * 2, ) % characterSetLength; return selectedCharacterSet[index]; }; type Size = { height: null | number; width: null | number; }; const AsciiArtGenerator: React.FC = () => { const textRef = useRef(null); const [size, setSize] = useState ({ height: null, width: null }); useEffect(() => { const handleResize = () => { setSize({ height: window.innerHeight, width: window.innerWidth }); }; // Initial size setting handleResize(); window.addEventListener('resize', handleResize); return () => { window.removeEventListener('resize', handleResize); }; }, []); useEffect(() => { const element = textRef.current; if (!element || !size.width || !size.height) return undefined; const cols = Math.floor(size.width / 12) * 1.6; const rows = Math.floor(size.height / 12); const aspectRatio = cols / rows; const intervalId = setInterval(() => { let content = ''; for (let y = 0; y < rows; y++) { for (let x = 0; x < cols; x++) { content += calculateCharacter( x, y, cols, rows, aspectRatio, Date.now(), ); } content += '\n'; } element.textContent = content; }, 1_000 / 60); // 60 fps return () => { clearInterval(intervalId); }; }, [size]); return ( ); }; export default () => { return ; };
À ma grande surprise, la réponse est non seulement assez bonne, mais elle est également très lisible.
Voici le composant ci-dessus en action.
En comparant les résultats, il semble que la réponse de LLM ait négligé quelques détails de mise en œuvre, mais il s'agit toujours d'une mise en œuvre suffisamment bonne pour en tirer des leçons. Certainement un cas d'utilisation intéressant auquel je n'avais jamais pensé auparavant !
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!