[ Index ] |
|
Code source de Serendipity 1.2 |
1 <?php 2 // $Id: List.php,v 1.1 2005/01/31 15:46:52 pmjones Exp $ 3 4 5 /** 6 * 7 * This class implements a Text_Wiki_Parse to find source text marked as 8 * a bulleted or numbered list. In short, if a line starts with '* ' then 9 * it is a bullet list item; if a line starts with '# ' then it is a 10 * number list item. Spaces in front of the * or # indicate an indented 11 * sub-list. The list items must be on sequential lines, and may be 12 * separated by blank lines to improve readability. Using a non-* non-# 13 * non-whitespace character at the beginning of a line ends the list. 14 * 15 * @author Paul M. Jones <pmjones@ciaweb.net> 16 * 17 * @package Text_Wiki 18 * 19 */ 20 21 class Text_Wiki_Parse_List extends Text_Wiki_Parse { 22 23 24 /** 25 * 26 * The regular expression used to parse the source text and find 27 * matches conforming to this rule. Used by the parse() method. 28 * 29 * @access public 30 * 31 * @var string 32 * 33 * @see parse() 34 * 35 */ 36 37 var $regex = '/\n((\*|#) .*\n)(?! {0,}(\* |# |\n))/Us'; 38 39 40 /** 41 * 42 * Generates a replacement for the matched text. Token options are: 43 * 44 * 'type' => 45 * 'bullet_start' : the start of a bullet list 46 * 'bullet_end' : the end of a bullet list 47 * 'number_start' : the start of a number list 48 * 'number_end' : the end of a number list 49 * 'item_start' : the start of item text (bullet or number) 50 * 'item_end' : the end of item text (bullet or number) 51 * 'unknown' : unknown type of list or item 52 * 53 * 'level' => the indent level (0 for the first level, 1 for the 54 * second, etc) 55 * 56 * 'count' => the list item number at this level. not needed for 57 * xhtml, but very useful for PDF and RTF. 58 * 59 * @access public 60 * 61 * @param array &$matches The array of matches from parse(). 62 * 63 * @return A series of text and delimited tokens marking the different 64 * list text and list elements. 65 * 66 */ 67 68 function process(&$matches) 69 { 70 // the replacement text we will return 71 $return = ''; 72 73 // the list of post-processing matches 74 $list = array(); 75 76 // a stack of list-start and list-end types; we keep this 77 // so that we know what kind of list we're working with 78 // (bullet or number) and what indent level we're at. 79 $stack = array(); 80 81 // the item count is the number of list items for any 82 // given list-type on the stack 83 $itemcount = array(); 84 85 // have we processed the very first list item? 86 $pastFirst = false; 87 88 // populate $list with this set of matches. $matches[1] is the 89 // text matched as a list set by parse(). 90 preg_match_all( 91 '=^( {0,})(\*|#) (.*)$=Ums', 92 $matches[1], 93 $list, 94 PREG_SET_ORDER 95 ); 96 97 // loop through each list-item element. 98 foreach ($list as $key => $val) { 99 100 // $val[0] is the full matched list-item line 101 // $val[1] is the number of initial spaces (indent level) 102 // $val[2] is the list item type (* or #) 103 // $val[3] is the list item text 104 105 // how many levels are we indented? (1 means the "root" 106 // list level, no indenting.) 107 $level = strlen($val[1]) + 1; 108 109 // get the list item type 110 if ($val[2] == '*') { 111 $type = 'bullet'; 112 } elseif ($val[2] == '#') { 113 $type = 'number'; 114 } else { 115 $type = 'unknown'; 116 } 117 118 // get the text of the list item 119 $text = $val[3]; 120 121 // add a level to the list? 122 if ($level > count($stack)) { 123 124 // the current indent level is greater than the 125 // number of stack elements, so we must be starting 126 // a new list. push the new list type onto the 127 // stack... 128 array_push($stack, $type); 129 130 // ...and add a list-start token to the return. 131 $return .= $this->wiki->addToken( 132 $this->rule, 133 array( 134 'type' => $type . '_list_start', 135 'level' => $level - 1 136 ) 137 ); 138 } 139 140 // remove a level from the list? 141 while (count($stack) > $level) { 142 143 // so we don't keep counting the stack, we set up a temp 144 // var for the count. -1 becuase we're going to pop the 145 // stack in the next command. $tmp will then equal the 146 // current level of indent. 147 $tmp = count($stack) - 1; 148 149 // as long as the stack count is greater than the 150 // current indent level, we need to end list types. 151 // continue adding end-list tokens until the stack count 152 // and the indent level are the same. 153 $return .= $this->wiki->addToken( 154 $this->rule, 155 array ( 156 'type' => array_pop($stack) . '_list_end', 157 'level' => $tmp 158 ) 159 ); 160 161 // reset to the current (previous) list type so that 162 // the new list item matches the proper list type. 163 $type = $stack[$tmp - 1]; 164 165 // reset the item count for the popped indent level 166 unset($itemcount[$tmp + 1]); 167 } 168 169 // add to the item count for this list (taking into account 170 // which level we are at). 171 if (! isset($itemcount[$level])) { 172 // first count 173 $itemcount[$level] = 0; 174 } else { 175 // increment count 176 $itemcount[$level]++; 177 } 178 179 // is this the very first item in the list? 180 if (! $pastFirst) { 181 $first = true; 182 $pastFirst = true; 183 } else { 184 $first = false; 185 } 186 187 // create a list-item starting token. 188 $start = $this->wiki->addToken( 189 $this->rule, 190 array( 191 'type' => $type . '_item_start', 192 'level' => $level, 193 'count' => $itemcount[$level], 194 'first' => $first 195 ) 196 ); 197 198 // create a list-item ending token. 199 $end = $this->wiki->addToken( 200 $this->rule, 201 array( 202 'type' => $type . '_item_end', 203 'level' => $level, 204 'count' => $itemcount[$level] 205 ) 206 ); 207 208 // add the starting token, list-item text, and ending token 209 // to the return. 210 $return .= $start . $val[3] . $end; 211 } 212 213 // the last list-item may have been indented. go through the 214 // list-type stack and create end-list tokens until the stack 215 // is empty. 216 while (count($stack) > 0) { 217 $return .= $this->wiki->addToken( 218 $this->rule, 219 array ( 220 'type' => array_pop($stack) . '_list_end', 221 'level' => count($stack) 222 ) 223 ); 224 } 225 226 // we're done! send back the replacement text. 227 return "\n" . $return . "\n\n"; 228 } 229 } 230 ?>
titre
Description
Corps
titre
Description
Corps
titre
Description
Corps
titre
Corps
Généré le : Sat Nov 24 09:00:37 2007 | par Balluche grâce à PHPXref 0.7 |
![]() |