Enlaces y texto flotante

Este tutorial explica cómo incluir enlaces (internos y externos) y muestra una nueva manera de imprimir texto. También incluye un intérprete rudimentario de HTML.
<?php
require('fpdf.php');

class PDF extends FPDF
{
protected $B = 0;
protected $I = 0;
protected $U = 0;
protected $HREF = '';

function WriteHTML($html)
{
    // Intérprete de HTML
    $html = str_replace("\n",' ',$html);
    $a = preg_split('/<(.*)>/U',$html,-1,PREG_SPLIT_DELIM_CAPTURE);
    foreach($a as $i=>$e)
    {
        if($i%2==0)
        {
            // Text
            if($this->HREF)
                $this->PutLink($this->HREF,$e);
            else
                $this->Write(5,$e);
        }
        else
        {
            // Etiqueta
            if($e[0]=='/')
                $this->CloseTag(strtoupper(substr($e,1)));
            else
            {
                // Extraer atributos
                $a2 = explode(' ',$e);
                $tag = strtoupper(array_shift($a2));
                $attr = array();
                foreach($a2 as $v)
                {
                    if(preg_match('/([^=]*)=["\']?([^"\']*)/',$v,$a3))
                        $attr[strtoupper($a3[1])] = $a3[2];
                }
                $this->OpenTag($tag,$attr);
            }
        }
    }
}

function OpenTag($tag, $attr)
{
    // Etiqueta de apertura
    if($tag=='B' || $tag=='I' || $tag=='U')
        $this->SetStyle($tag,true);
    if($tag=='A')
        $this->HREF = $attr['HREF'];
    if($tag=='BR')
        $this->Ln(5);
}

function CloseTag($tag)
{
    // Etiqueta de cierre
    if($tag=='B' || $tag=='I' || $tag=='U')
        $this->SetStyle($tag,false);
    if($tag=='A')
        $this->HREF = '';
}

function SetStyle($tag, $enable)
{
    // Modificar estilo y escoger la fuente correspondiente
    $this->$tag += ($enable ? 1 : -1);
    $style = '';
    foreach(array('B', 'I', 'U') as $s)
    {
        if($this->$s>0)
            $style .= $s;
    }
    $this->SetFont('',$style);
}

function PutLink($URL, $txt)
{
    // Escribir un hiper-enlace
    $this->SetTextColor(0,0,255);
    $this->SetStyle('U',true);
    $this->Write(5,$txt,$URL);
    $this->SetStyle('U',false);
    $this->SetTextColor(0);
}
}

$html = 'Ahora puede imprimir fácilmente texto mezclando diferentes estilos: <b>negrita</b>, <i>itálica</i>,
<u>subrayado</u>, o ¡ <b><i><u>todos a la vez</u></i></b>!<br><br>También puede incluir enlaces en el
texto, como <a href="http://www.fpdf.org">www.fpdf.org</a>, o en una imagen: pulse en el logotipo.';

$pdf = new PDF();
// Primera página
$pdf->AddPage();
$pdf->SetFont('Arial','',20);
$pdf->Write(5,'Para saber qué hay de nuevo en este tutorial, pulse ');
$pdf->SetFont('','U');
$link = $pdf->AddLink();
$pdf->Write(5,'aquí',$link);
$pdf->SetFont('');
// Segunda página
$pdf->AddPage();
$pdf->SetLink($link);
$pdf->Image('logo.png',10,12,30,0,'','http://www.fpdf.org');
$pdf->SetLeftMargin(45);
$pdf->SetFontSize(14);
$pdf->WriteHTML($html);
$pdf->Output();
?>

[Demo]

El nuevo método para imprimir texto es Write(). Se parece mucho a MultiCell(); las diferencias son: Así que le permite escribir un texto, alterar el estilo de la fuente, y continuar en el punto exacto donde lo dejó. Sin embargo, no puede justificar el texto simultáneamente a derecha y a izquierda.

Este método se usa en la primera página para añadir un enlace que apunta a la segunda página. El principio de la frase se escribe en un estilo normal, después cambiamos a subrayado y la terminamos. El enlace se crea con AddLink(), que devuelve el identificador del enlace. El identificador se pasa como tercer parámetro a Write(). Una vez que la segunda página se ha creado, usamos SetLink() para hacer que el enlace apunte al principio de la página actual.

Deespués ponemos una imagen con un enlace en ella. Un enlace externo apunta a una URL. La URL se pasa como el último parámetro de Image().

Finalmente, el margen izquierdo se modifica después de la imagen con SetLeftMargin() y se escribe texto en formato HTML. Se utiliza un intérprete HTML para esto, basado en les expresiones regulares. Las etiquetas reconocidas son <b>, <i>, <u>, <a> y <br>; las demás se ignoran. El intérprete también usa el método Write(). Se pone un enlace externo de la misma manera que uno interno (como tercer parámetro de Write()). Observe que Cell() también permite incluir enlaces.