-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathtypogrify.php
77 lines (55 loc) · 2.84 KB
/
typogrify.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
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
<?php
class Typogrify {
/**
* Capitalizes a post title, per the rules by John Gruber from:
* http://daringfireball.net/2008/05/title_case
*
* PHP Implementation by Adam Nolley:
* http://nanovivid.com/stuff/wordpress/title-case/
*
* @param string $text The title to capitalize.
* @return string The properly capitalized title.
*/
public static function title_case ( $text ) {
// Edit this list to change what words should be lowercase
$small_words = "a an and as at but by en for if in of on or the to v[.]? via vs[.]?";
$small_re = str_replace(" ", "|", $small_words);
// Replace HTML entities for spaces and record their old positions
$htmlspaces = "/ | | /";
$oldspaces = array();
preg_match_all($htmlspaces, $text, $oldspaces, PREG_OFFSET_CAPTURE);
// Remove HTML space entities
$words = preg_replace($htmlspaces, " ", $text);
// Split around sentance divider-ish stuff
$words = preg_split('/( [:.;?!][ ] | (?:[ ]|^)["“])/x', $words, -1, PREG_SPLIT_DELIM_CAPTURE);
for ($i = 0; $i < count($words); $i++) {
// Skip words with dots in them like del.icio.us
$words[$i] = preg_replace_callback('/\b([[:alpha:]][[:lower:].\'’(&\#8217;)]*)\b/x', array( 'self', 'title_case_skip_dotted' ), $words[$i]);
// Lowercase our list of small words
$words[$i] = preg_replace("/\b($small_re)\b/ei", "strtolower(\"$1\")", $words[$i]);
// If the first word in the title is a small word, capitalize it
$words[$i] = preg_replace("/\A([[:punct:]]*)($small_re)\b/e", "\"$1\" . ucfirst(\"$2\")", $words[$i]);
// If the last word in the title is a small word, capitalize it
$words[$i] = preg_replace("/\b($small_re)([[:punct:]]*)\Z/e", "ucfirst(\"$1\") . \"$2\"", $words[$i]);
}
$words = join($words);
// Oddities
$words = preg_replace("/ V(s?)\. /i", " v$1. ", $words); // v, vs, v., and vs.
$words = preg_replace("/(['’]|’)S\b/i", "$1s", $words); // 's
$words = preg_replace("/\b(AT&T|Q&A)\b/ie", "strtoupper(\"$1\")", $words); // AT&T and Q&A
$words = preg_replace("/-ing\b/i", "-ing", $words); // -ing
$words = preg_replace("/(&[[:alpha:]]+;)/Ue", "strtolower(\"$1\")", $words); // html entities
// Put HTML space entities back
$offset = 0;
for ($i = 0; $i < count($oldspaces[0]); $i++) {
$offset = $oldspaces[0][$i][1];
$words = substr($words, 0, $offset) . $oldspaces[0][$i][0] . substr($words, $offset + 1);
$offset += strlen($oldspaces[0][$i][0]);
}
return $words;
}
private static function title_case_skip_dotted ( $matches ) {
return preg_match('/[[:alpha:]] [.] [[:alpha:]]/x', $matches[0]) ? $matches[0] : ucfirst($matches[0]);
}
}
?>