Als ik het goed begrijp staan die links als plain URL (bijv. http://bladieblaenzo) in je db en wil je ze in je HTML outputten als <a href="http://bladieblaenzo">bladi..enzo</a>?
Zoals ik het ooit eens werkend heb gemaakt, ging ik eerst die URL's opsporen, door in een functie een regular expression te gebruiken. Op
http://nl.php.net/manual/en/function.preg-replace.php staan zeer aardige ideetjes daarvoor, maar de mooiste die ik had gevonden lijkt nu helaas weggehaald te zijn.

In mirrors van die manualpage is die code gelukkig echter nog wel terug te vinden:
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
| /*
cgamedude at yahoo dot com
15-Feb-2004 06:15
I wrote a function to convert URLs *that are not already in anchor tags* into hyperlinks. It works with both http://blah.com and www.blah.com and I tried to make it actually understandable by not using a single 200-char expression :)
It's used like:
$Text = InsertLinks( $Text );
Anyway here it is:
*/
function InsertLinks ( $Text )
{
// First match things beginning with http:// (or other protocols)
$NotAnchor = '(?<!"|href=|href\s=\s|href=\s|href\s=)';
$Protocol = '(http|ftp|https):\/\/';
$Domain = '[\w]+(.[\w]+)';
$Subdir = '([\w\-\.,@?^=%&:\/~\+#]*[\w\-\@?^=%&\/~\+#])?';
$Expr = '/' . $NotAnchor . $Protocol . $Domain . $Subdir . '/i';
$Result = preg_replace( $Expr, "<a href=\"$0\" title=\"$0\" target=\"_blank\">$0</a>", $Text );
// Now match things beginning with www.
$NotAnchor = '(?<!"|href=|href\s=\s|href=\s|href\s=)';
$NotHTTP = '(?<!:\/\/)';
$Domain = 'www(.[\w]+)';
$Subdir = '([\w\-\.,@?^=%&:\/~\+#]*[\w\-\@?^=%&\/~\+#])?';
$Expr = '/' . $NotAnchor . $NotHTTP . $Domain . $Subdir . '/i';
$Result2 = preg_replace( $Expr, "<a href=\"http://$0\" title=\"http://$0\" target=\"_blank\">$0</a>", $Result );
return $Result2;
} |
De bovenstaande code is sowieso uiterst interessant om eens goed te bekijken, omdat er minder efficiënt dan zou kunnen, maar des te duidelijker staat te lezen hoe zo'n reguliere expressie nu eigenlijk werkt. Er is heel veel uit te halen als je goed kijkt.

Maar goed, dan heb je dus alle plain linkjes omgezet naar keurige HTML-hrefs. Maar dan heb je nog niet wat je wilt, want dán moet je ze nog eens op de juiste lengte hebben, en het liefst een beetje netjes, met puntjes in 't midden ofzo.
Voor een aardig voorbeeld daarvoor kun je kijken naar
een functie die als modification kan worden toegevoegd aan UBB.
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
| // ---------------------------------------------------------
// Truncate the URL if it's too long - by JoshPet & Gardener
preg_match_all("/<a href=(\"|")([^\">]*?)(\"|")([^>]*?)>([^<]*?)<\/a>/i", $Body, $urlmatches, PREG_SET_ORDER);
$matchcount = count($urlmatches);
if ($matchcount) {
for ($i = 0; $i<$matchcount; $i++) {
$shorturl = $urlmatches[$i][5];
if ((preg_match("#^(http|https|ftp)://#i",$shorturl)) && (strlen($shorturl) > 100)) {
$shortenedurl = substr($shorturl, 0, 40) . "..." . substr($shorturl, -15);
$shorturl = preg_quote($shorturl, "#");
$Body = preg_replace("#>$shorturl</a>#i", ">$shortenedurl</a>", $Body, 1);
}
}
} |
(waarom de syntax highlighter hierover valt weet ik niet... want er zit voor zover ik kan zien geen syntactische fout in die reguliere expressie...)
Trek daar $Result2 doorheen (dus prop deze code gewoon erbij in die eerste functie, let wel even op dat je de juiste variabelen doorgeeft, dus hier $Result2 in deze functie stoppen ipv $Body natuurlijk

) en return dán pas wat je terugkrijgt .
Dan is je functie klaar en hoef je alleen nog maar je database-inhoud te voeren aan die functie en daarna het resultaat te echoën. Kind kan de was doen.

Ik zet dit hier zo uitgebreid neer, omdat ik zelf dagenlang aan 't zoeken en prutsen ben geweest voordat ik dit gevonden had.
Toen ik hiernaar op zoek was, had ik ook alleen maar wat basiskennis van PHP, maar toch wilde ik het voor elkaar krijgen. Zoiets als dit kon ik toen ook zelf volstrekt niet schrijven (zulke regexen nu waarschijnlijk nog niet trouwens

), dus ik was zielsgelukkig toen ik dit eenmaal bij elkaar gevonden had. Zeker iets als dat tweede scriptje is niet eenvoudig te vinden en zoiets bedenk je jammer genoeg ook niet zomaar zelf, wanneer je net begint.
Toch moet je zulk zoekwerk wel zelf kunnen verrichten vind ik. En als je het gevonden hebt, moet je zoiets als dit niet zomaar met je ogen dicht implementeren om nooit meer naar om te kijken als het werkt. Juist dit soort dingen zijn gigantisch leerzaam: jij had een probleem en had een paar ideeën hoe je dat op zou kunnen lossen; hier zie je dat het volledig anders kan. Bedenk dan voor jezelf waarom ze 't hier anders doen, wat het nut er van is dat ze het op deze manier doen. Zie je onbekende functies, pak dan de PHP-manual en ga kijken wat die functies precies doen en waarom ze hier gebruikt zijn. Zo leer je jezelf van zulk soort kleine dingetjes stukje bij beetje steeds meer... en nogmaals: vooral goed leren zoeken is erg belangrijk.
When I write my code, only God and I know what it means. One week later, only God knows.
Hell yes it's a Cuban Cigar, but I'm not supporting their economy, I'm burning their fields.