Trasformare lo spazio delle coordinate: rotazione, ridimensionamento, inclinazione e ribaltamento
In breve
Sezione intitolata “In breve”Trasformare lo spazio delle coordinate di disegno attorno a un perno scelto. Questa ricetta illustra rotazione, ridimensionamento, inclinazione e ribaltamento. Ogni trasformazione resta isolata in un blocco di stato grafico salvato, perciò non influisce sul contenuto successivo. La struttura segue examples/21-transforms.php.
Installazione
Sezione intitolata “Installazione”composer require nextpdf/core:^3Non è richiesto un pacchetto Pro o Enterprise. L’API di trasformazione è inclusa in Core e funziona da PHP 8.1 a 8.4.
Panoramica concettuale
Sezione intitolata “Panoramica concettuale”Il contenuto PDF viene disegnato nello spazio utente. Per impostazione predefinita, lo spazio utente ha l’origine in basso a sinistra della pagina e un’unità equivale a 1/72 di pollice (ISO 32000-2 §8.3.2). Una trasformazione moltiplica la matrice di trasformazione corrente (CTM) per una nuova matrice tramite l’operatore cm (§8.3.4). Le trasformazioni si compongono per concatenazione di matrici, perciò l’ordine è significativo.
NextPDF espone un sistema di coordinate autore con origine in alto a sinistra. Internamente lo converte nello spazio utente nativo con origine in basso a sinistra tramite la proiezione toY() nei metodi di trasformazione. Le posizioni usano le unità dello spazio utente, ovvero i punti PDF, dove 1 pt equivale a 1/72 di pollice. Per mantenere una trasformazione locale, racchiuderla tra startTransform() e stopTransform(). Questi metodi emettono gli operatori di stato grafico q (salva) e Q (ripristina) (§8.4.2). Tutto ciò che viene disegnato tra i due metodi eredita la trasformazione. Tutto ciò che segue stopTransform() torna alla CTM precedente. Ogni chiamata a rotate()/scale()/skewX()/mirrorH() accetta un perno esplicito, perciò la trasformazione si ancora al punto previsto anziché all’origine della pagina.
Superficie dell’API
Sezione intitolata “Superficie dell’API”La superficie dell’API è generata da PHPDoc. I principali punti di ingresso provengono dal trait \NextPDF\Core\Concerns\HasTransforms:
Document::startTransform(): static— emetteqe apre un blocco di stato graficoDocument::stopTransform(): static— emetteQe chiude il bloccoDocument::rotate(float $angle, float $x = 0, float $y = 0): staticDocument::scale(float $sx, float $sy, float $x = 0, float $y = 0): staticDocument::skewX(float $angle, float $x = 0, float $y = 0): static/skewY(...)Document::mirrorH(float $x = 0): static/mirrorV(float $y = 0): staticDocument::translateCtm(float $dx, float $dy): static
Esempio di codice — Guida rapida
Sezione intitolata “Esempio di codice — Guida rapida”<?php
declare(strict_types=1);
require_once __DIR__ . '/vendor/autoload.php';
use NextPDF\Core\Document;
$doc = Document::createStandalone();$doc->setTitle('Coordinate Transforms');$doc->addPage();
$cx = 60.0;$cy = 60.0;
// Rotate 30° around (cx, cy). The transform is scoped to this block.$doc->startTransform();$doc->rotate(30, $cx, $cy);$doc->setFont('helvetica', '', 14);$doc->text($cx, $cy, 'Rotated 30 degrees');$doc->stopTransform();
// Back to the untransformed CTM — this text is upright.$doc->setFont('helvetica', '', 10);$doc->text($cx, $cy + 20, 'Not rotated');
$doc->save(__DIR__ . '/transforms.pdf');
echo "Created: transforms.pdf\n";Esempio di codice — Produzione
Sezione intitolata “Esempio di codice — Produzione”Questo programma autonomo è eseguibile dall’harness. Rispecchia la sezione di ridimensionamento di examples/21-transforms.php. Ogni trasformazione è isolata in un blocco di stato grafico salvato con un perno esplicito. Lo stato del colore e della linea viene reimpostato alla fine, perciò nulla si propaga a una pagina successiva.
<?php
declare(strict_types=1);
require_once __DIR__ . '/vendor/autoload.php';
use NextPDF\Core\Document;
$doc = Document::createStandalone();$doc->setTitle('Coordinate Transforms');$doc->addPage();
$doc->setFont('helvetica', 'B', 13);$doc->cell(0, 8, 'Scaling a reference square at 0.5x, 1.0x, 1.5x, 2.0x', newLine: true);$doc->ln(6);
$scaleBaseY = $doc->getY();$scaleFactors = [0.5, 1.0, 1.5, 2.0];
$doc->setDrawColor(30, 58, 138);$doc->setLineWidth(0.4);
foreach ($scaleFactors as $idx => $factor) { $cx = 25.0 + $idx * 45; $cy = $scaleBaseY + 5;
$doc->startTransform(); $doc->scale($factor, $factor, $cx, $cy); // scale about (cx, cy)
$doc->setFillColor(220, 230, 241); $doc->rect($cx, $cy, 15, 15, 'DF'); $doc->line($cx, $cy, $cx + 15, $cy + 15);
$doc->stopTransform(); // CTM restored here
// Drawn AFTER the block — at the original scale, untransformed. $doc->setFont('helvetica', '', 8); $doc->setTextColor(0); $doc->text($cx, $scaleBaseY + 38, sprintf('%.1fx', $factor));}
// Explicit state reset so nothing carries into the next section.$doc->setTextColor(0);$doc->setFillColor(255);$doc->setDrawColor(0);
// The harness sets NEXTPDF_COOKBOOK_OUTPUT and runs this script twice under// the structural profile (the transform stream itself is deterministic).$out = getenv('NEXTPDF_COOKBOOK_OUTPUT');$doc->save($out !== false && $out !== '' ? $out : __DIR__ . '/transforms.pdf');
echo "Wrote transforms.pdf\n";STDOUT previsto:
Wrote transforms.pdfL’esempio completo copre tutte e quattro le famiglie di trasformazione: rotazione, ridimensionamento, inclinazione e ribaltamento. Eseguirlo con php examples/21-transforms.php, che scrive examples/output/21-transforms.pdf.
Casi limite e insidie
Sezione intitolata “Casi limite e insidie”- Chiudere sempre il blocco. Ogni
startTransform()richiede un corrispondentestopTransform(). Un bilanciamento errato diq/Qcorrompe lo stato grafico per il resto della pagina (ISO 32000-2 §8.4.2). NextPDF tiene traccia della profondità, ma il contratto a livello di ricetta è uno-a-uno. - L’ordine non è commutativo. Le trasformazioni si compongono per concatenazione di matrici, perciò
rotate()seguito dascale()non equivale ascale()seguito darotate(). Applicarle all’interno di un unico blocco nell’ordine desiderato. - Per impostazione predefinita, il perno è all’origine. Omettendo il perno, la trasformazione ruota attorno all’origine della pagina, non alla forma. Di solito non è il risultato desiderato, perciò passare il perno in modo esplicito.
- L’asse Y è nello spazio autore. La
ydel perno è la distanza dall’angolo in alto a sinistra dello spazio autore, che NextPDF proietta nello spazio utente nativo. Mescolare coordinate PDF grezze con l’API autore produce un risultato ribaltato. - Propagazione dello stato. Colore, font e spessore della linea impostati all’interno di un blocco di trasformazione persistono dopo
stopTransform(), perché in questa superficie dell’APIQripristina solo la CTM. Reimpostare questi valori in modo esplicito se una sezione successiva non deve ereditarli, come fa l’esempio di produzione.
Prestazioni
Sezione intitolata “Prestazioni”Una trasformazione è un singolo operatore cm più la coppia q/Q. Ogni elemento occupa pochi byte e non aggiunge alcun costo di runtime misurabile, perciò la ricetta rimane comodamente entro il budget di 1500 ms / 96 MB. Il profilo di riproducibilità è strutturale. L’output contiene un array /ID nel trailer e metadati di creazione che non sono stabili tra le esecuzioni, perciò è necessario normalizzarli prima del confronto. Il flusso di trasformazione in sé è deterministico.
Note sulla sicurezza
Sezione intitolata “Note sulla sicurezza”- Residenza dei dati e mitigazioni dei dati personali (PII). Non applicabile. Questa ricetta disegna primitive geometriche ed etichette brevi. Non elabora alcun dato esterno o personale.
- Telemetria sicura e pulizia dei log. La ricetta scrive una sola riga di avanzamento fissa. Nessun contenuto del documento viene registrato nei log.
- Modello di minaccia. Non applicabile. Non vi è alcuna analisi dell’input, alcuna crittografia, né alcun confine di attendibilità. Una trasformazione è pura emissione di content stream.
- Comportamento in modalità FIPS. Non applicabile. Non vi è alcuna operazione crittografica.
Conformità
Sezione intitolata “Conformità”| Dichiarazione | Specifica | Clausola | reference_id |
|---|---|---|---|
Una trasformazione concatena una matrice alla CTM tramite l’operatore cm. | ISO 32000-2 | §8.3.4 | |
| Le trasformazioni si compongono per concatenazione di matrici; l’ordine è significativo. | ISO 32000-2 | §8.3.4 | |
q salva e Q ripristina lo stato grafico, circoscrivendo la trasformazione. | ISO 32000-2 | §8.4.2 | |
| L’origine predefinita dello spazio utente è in basso a sinistra; un’unità è 1/72 di pollice. | ISO 32000-2 | §8.3.2 |
Questa ricetta implementa le clausole ISO 32000-2 citate relative allo stato grafico e alle trasformazioni. Non dichiara la conformità generale a ISO 32000-2; le clausole citate sono solo quelle che questa ricetta utilizza.