1<?php 2/** 3 * HTML output functions 4 * 5 * @license GPL 2 (http://www.gnu.org/licenses/gpl.html) 6 * @author Andreas Gohr <andi@splitbrain.org> 7 */ 8 9 if(!defined('DOKU_INC')) define('DOKU_INC',realpath(dirname(__FILE__).'/../').'/'); 10 11 require_once(DOKU_INC.'inc/parserutils.php'); 12 13/** 14 * Convenience function to quickly build a wikilink 15 * 16 * @author Andreas Gohr <andi@splitbrain.org> 17 */ 18function html_wikilink($id,$name=NULL,$search=''){ 19 require_once(DOKU_INC.'inc/parser/xhtml.php'); 20 static $xhtml_renderer = NULL; 21 if(is_null($xhtml_renderer)){ 22 $xhtml_renderer = new Doku_Renderer_xhtml(); 23 } 24 25 return $xhtml_renderer->internallink($id,$name,$search,true); 26} 27 28/** 29 * Helps building long attribute lists 30 * 31 * @author Andreas Gohr <andi@splitbrain.org> 32 */ 33function html_attbuild($attributes){ 34 $ret = ''; 35 foreach ( $attributes as $key => $value ) { 36 $ret .= $key.'="'.formtext($value).'" '; 37 } 38 return trim($ret); 39} 40 41/** 42 * The loginform 43 * 44 * @author Andreas Gohr <andi@splitbrain.org> 45 */ 46function html_login(){ 47 global $lang; 48 global $conf; 49 global $ID; 50 51 print p_locale_xhtml('login'); 52 ?> 53 <div align="center"> 54 <form action="<?=script()?>" accept-charset="<?=$lang['encoding']?>" method="post"> 55 <fieldset> 56 <legend><?=$lang['btn_login']?></legend> 57 <input type="hidden" name="id" value="<?=$ID?>" /> 58 <input type="hidden" name="do" value="login" /> 59 <label> 60 <span><?=$lang['user']?></span> 61 <input type="text" name="u" value="<?=formText($_REQUEST['u'])?>" class="edit" /> 62 </label><br /> 63 <label> 64 <span><?=$lang['pass']?></span> 65 <input type="password" name="p" class="edit" /> 66 </label><br /> 67 <input type="submit" value="<?=$lang['btn_login']?>" class="button" /> 68 <label for="remember" class="simple"> 69 <input type="checkbox" name="r" id="remember" value="1" /> 70 <span><?=$lang['remember']?></span> 71 </label> 72 </fieldset> 73 </form> 74 <? 75 if($conf['openregister']){ 76 print '<p>'; 77 print $lang['reghere']; 78 print ': <a href="'.wl($ID,'do=register').'" class="wikilink1">'.$lang['register'].'</a>'; 79 print '</p>'; 80 } 81 ?> 82 </div> 83 <? 84/* 85 FIXME provide new hook 86 if(@file_exists('includes/login.txt')){ 87 print io_cacheParse('includes/login.txt'); 88 } 89*/ 90} 91 92/** 93 * shows the edit/source/show button dependent on current mode 94 * 95 * @author Andreas Gohr <andi@splitbrain.org> 96 */ 97function html_editbutton(){ 98 global $ID; 99 global $REV; 100 global $ACT; 101 global $INFO; 102 103 if($ACT == 'show' || $ACT == 'search'){ 104 if($INFO['writable']){ 105 if($INFO['exists']){ 106 $r = html_btn('edit',$ID,'e',array('do' => 'edit','rev' => $REV),'post'); 107 }else{ 108 $r = html_btn('create',$ID,'e',array('do' => 'edit','rev' => $REV),'post'); 109 } 110 }else{ 111 $r = html_btn('source',$ID,'v',array('do' => 'edit','rev' => $REV),'post'); 112 } 113 }else{ 114 $r = html_btn('show',$ID,'v',array('do' => 'show')); 115 } 116 return $r; 117} 118 119/** 120 * prints a section editing button 121 * 122 * @author Andreas Gohr <andi@splitbrain.org> 123 */ 124function html_secedit_button($section,$p){ 125 global $ID; 126 global $lang; 127 $secedit = ''; 128# if($p) $secedit .= "</p>\n"; 129 $secedit .= '<div class="secedit">'; 130 $secedit .= html_btn('secedit',$ID,'', 131 array('do' => 'edit', 132 'lines' => "$section"), 133 'post'); 134 $secedit .= '</div>'; 135# if($p) $secedit .= "\n<p>"; 136 return $secedit; 137} 138 139/** 140 * inserts section edit buttons if wanted or removes the markers 141 * 142 * @author Andreas Gohr <andi@splitbrain.org> 143 */ 144function html_secedit($text,$show=true){ 145 global $INFO; 146 if($INFO['writable'] && $show && !$INFO['rev']){ 147 $text = preg_replace('#<!-- SECTION \[(\d+-\d+)\] -->#e', 148 "html_secedit_button('\\1',true)", 149 $text); 150 $text = preg_replace('#<!-- SECTION \[(\d+-)\] -->#e', 151 "html_secedit_button('\\1',false)", 152 $text); 153 }else{ 154 $text = preg_replace('#<!-- SECTION \[(\d*-\d*)\] -->#e','',$text); 155 } 156 return $text; 157} 158 159/** 160 * Just the back to top button (in it's own form) 161 * 162 * @author Andreas Gohr <andi@splitbrain.org> 163 */ 164function html_topbtn(){ 165 global $lang; 166 167 $ret = ''; 168 $ret = '<a href="#top"><input type="button" class="button" value="Back to top" onclick="window.scrollTo(0, 0)" /></a>'; 169 170 return $ret; 171} 172 173/** 174 * Displays a button (using it's own form) 175 * 176 * @author Andreas Gohr <andi@splitbrain.org> 177 */ 178function html_btn($name,$id,$akey,$params,$method='get'){ 179 global $conf; 180 global $lang; 181 182 $label = $lang['btn_'.$name]; 183 184 $ret = ''; 185 186 //filter id (without urlencoding) 187 $id = idfilter($id,false); 188 189 //make nice URLs even for buttons 190 if(!$conf['userewrite']){ 191 $script = DOKU_BASE.DOKU_SCRIPT; 192 $params['id'] = $id; 193 }else{ 194 $script = DOKU_BASE.$id; 195 } 196 197 $ret .= '<form class="button" method="'.$method.'" action="'.$script.'" onsubmit="return svchk()">'; 198 199 reset($params); 200 while (list($key, $val) = each($params)) { 201 $ret .= '<input type="hidden" name="'.$key.'" '; 202 $ret .= 'value="'.htmlspecialchars($val).'" />'; 203 } 204 205 $ret .= '<input type="submit" value="'.htmlspecialchars($label).'" class="button" '; 206 if($akey){ 207 $ret .= 'title="ALT+'.strtoupper($akey).'" '; 208 $ret .= 'accesskey="'.$akey.'" '; 209 } 210 $ret .= '/>'; 211 $ret .= '</form>'; 212 213 return $ret; 214} 215 216/** 217 * Print the table of contents 218 * 219 * @author Andreas Gohr <andi@splitbrain.org> 220 */ 221function html_toc($toc){ 222 global $lang; 223 $ret = ''; 224 $ret .= '<div class="toc">'; 225 $ret .= '<div class="tocheader">'; 226 $ret .= $lang['toc']; 227 $ret .= ' <script type="text/javascript">'; 228 $ret .= 'showTocToggle("+","-")'; 229 $ret .= '</script>'; 230 $ret .= '</div>'; 231 $ret .= '<div id="tocinside">'; 232 $ret .= html_buildlist($toc,'toc','html_list_toc'); 233 $ret .= '</div>'; 234 $ret .= '</div>'; 235 return $ret; 236} 237 238/** 239 * TOC item formatter 240 * 241 * User function for html_buildlist() 242 * 243 * @author Andreas Gohr <andi@splitbrain.org> 244 */ 245function html_list_toc($item){ 246 $ret = ''; 247 $ret .= '<a href="#'.$item['id'].'" class="toc">'; 248 $ret .= $item['name']; 249 $ret .= '</a>'; 250 return $ret; 251} 252 253/** 254 * show a wiki page 255 * 256 * @author Andreas Gohr <andi@splitbrain.org> 257 */ 258function html_show($txt=''){ 259 global $ID; 260 global $REV; 261 global $HIGH; 262 //disable section editing for old revisions or in preview 263 if($text || $REV){ 264 $secedit = false; 265 }else{ 266 $secedit = true; 267 } 268 269 if ($txt){ 270 //PreviewHeader 271 print p_locale_xhtml('preview'); 272 print '<div class="preview">'; 273 print html_secedit(p_render('xhtml',p_get_instructions($txt)),$secedit); 274 print '</div>'; 275 276 }else{ 277 if ($REV) print p_locale_xhtml('showrev'); 278 $html = p_wiki_xhtml($ID,$REV,true); 279 $html = html_secedit($html,$secedit); 280 print html_hilight($html,$HIGH); 281 } 282} 283 284/** 285 * Highlights searchqueries in HTML code 286 * 287 * @author Andreas Gohr <andi@splitbrain.org> 288 */ 289function html_hilight($html,$query){ 290 $queries = preg_split ("/\s/",$query,-1,PREG_SPLIT_NO_EMPTY); 291 foreach ($queries as $q){ 292 $q = preg_quote($q,'/'); 293 $html = preg_replace("/((<[^>]*)|$q)/ie", '"\2"=="\1"? "\1":"<span class=\"search_hit\">\1</span>"', $html); 294 } 295 return $html; 296} 297 298/** 299 * Run a search and display the result 300 * 301 * @author Andreas Gohr <andi@splitbrain.org> 302 */ 303function html_search(){ 304 require_once(DOKU_INC.'inc/search.php'); 305 global $conf; 306 global $QUERY; 307 global $ID; 308 global $lang; 309 310 print p_locale_xhtml('searchpage'); 311 flush(); 312 313 //show progressbar 314 print '<div align="center">'; 315 print '<script language="JavaScript" type="text/javascript">'; 316 print 'showLoadBar();'; 317 print '</script>'; 318 print '<br /></div>'; 319 320 //do quick pagesearch 321 $data = array(); 322 search($data,$conf['datadir'],'search_pagename',array(query => cleanID($QUERY))); 323 if(count($data)){ 324 sort($data); 325 print '<div class="search_quickresult">'; 326 print '<b>'.$lang[quickhits].':</b><br />'; 327 foreach($data as $row){ 328 print '<div class="search_quickhits">'; 329 print html_wikilink(':'.$row['id'],$row['id']); 330 print '</div> '; 331 } 332 //clear float (see http://www.complexspiral.com/publications/containing-floats/) 333 print '<div class="clearer"> </div>'; 334 print '</div>'; 335 } 336 flush(); 337 338 //do fulltext search 339 $data = array(); 340 search($data,$conf['datadir'],'search_fulltext',array(query => utf8_strtolower($QUERY))); 341 if(count($data)){ 342 usort($data,'sort_search_fulltext'); 343 foreach($data as $row){ 344 print '<div class="search_result">'; 345 print html_wikilink(':'.$row['id'],$row['id'],$QUERY); 346 print ': <span class="search_cnt">'.$row['count'].' '.$lang['hits'].'</span><br />'; 347 print '<div class="search_snippet">'.$row['snippet'].'</div>'; 348 print '</div>'; 349 } 350 }else{ 351 print '<div class="nothing">'.$lang['nothingfound'].'</div>'; 352 } 353 354 //hide progressbar 355 print '<script language="JavaScript" type="text/javascript">'; 356 print 'hideLoadBar();'; 357 print '</script>'; 358} 359 360/** 361 * Display error on locked pages 362 * 363 * @author Andreas Gohr <andi@splitbrain.org> 364 */ 365function html_locked($ip){ 366 global $ID; 367 global $conf; 368 global $lang; 369 370 $locktime = filemtime(wikiFN($ID).'.lock'); 371 $expire = @date($conf['dformat'], $locktime + $conf['locktime'] ); 372 $min = round(($conf['locktime'] - (time() - $locktime) )/60); 373 374 print p_locale_xhtml('locked'); 375 print '<ul>'; 376 print '<li><b>'.$lang['lockedby'].':</b> '.$ip.'</li>'; 377 print '<li><b>'.$lang['lockexpire'].':</b> '.$expire.' ('.$min.' min)</li>'; 378 print '</ul>'; 379} 380 381/** 382 * list old revisions 383 * 384 * @author Andreas Gohr <andi@splitbrain.org> 385 */ 386function html_revisions(){ 387 global $ID; 388 global $INFO; 389 global $conf; 390 global $lang; 391 $revisions = getRevisions($ID); 392 $date = @date($conf['dformat'],$INFO['lastmod']); 393 394 print p_locale_xhtml('revisions'); 395 print '<ul>'; 396 if($INFO['exists']){ 397 print '<li>'; 398 print '<img src="'.DOKU_BASE.'images/blank.gif" border="0" width="15" height="11" alt="" /> '; 399 400 print $date.' <a class="wikilink1" href="'.wl($ID).'">'.$ID.'</a> '; 401 402 print $INFO['sum']; 403 print ' <span class="user">('; 404 print $INFO['ip']; 405 if($INFO['user']) print ' '.$INFO['user']; 406 print ')</span> '; 407 408 print '('.$lang['current'].')'; 409 print '</li>'; 410 } 411 412 foreach($revisions as $rev){ 413 $date = date($conf['dformat'],$rev); 414 $info = getRevisionInfo($ID,$rev); 415 416 print '<li>'; 417 print '<a href="'.wl($ID,"rev=$rev,do=diff").'">'; 418 print '<img src="'.DOKU_BASE.'images/diff.png" border="0" width="15" height="11" title="'.$lang['diff'].'" />'; 419 print '</a> '; 420 421 print $date.' <a class="wikilink1" href="'.wl($ID,"rev=$rev").'">'.$ID.'</a> '; 422 print htmlspecialchars($info['sum']); 423 print ' <span class="user">('; 424 print $info['ip']; 425 if($info['user']) print ' '.$info['user']; 426 print ')</span>'; 427 428 print '</li>'; 429 } 430 print '</ul>'; 431} 432 433/** 434 * display recent changes 435 * 436 * @author Andreas Gohr <andi@splitbrain.org> 437 */ 438function html_recent(){ 439 global $conf; 440 global $lang; 441 $recents = getRecents(0,true); 442 443 print p_locale_xhtml('recent'); 444 print '<ul>'; 445 foreach(array_keys($recents) as $id){ 446 $date = date($conf['dformat'],$recents[$id]['date']); 447 print '<li>'; 448 449 print '<a href="'.wl($id,"do=diff").'">'; 450 print '<img src="'.DOKU_BASE.'images/diff.png" border="0" width="15" height="11" title="'.$lang['diff'].'" />'; 451 print '</a> '; 452 453 print '<a href="'.wl($id,"do=revisions").'">'; 454 print '<img src="'.DOKU_BASE.'images/history.png" border="0" width="12" height="14" title="'.$lang['btn_revs'].'" />'; 455 print '</a> '; 456 457 458 print $date.' '.html_wikilink($id,$id); 459 print ' '.htmlspecialchars($recents[$id]['sum']); 460 print ' <span class="user">('; 461 print $recents[$id]['ip']; 462 if($recents[$id]['user']) print ' '.$recents[$id]['user']; 463 print ')</span>'; 464 465 print '</li>'; 466 } 467 print '</ul>'; 468} 469 470/** 471 * Display page index 472 * 473 * @author Andreas Gohr <andi@splitbrain.org> 474 */ 475function html_index($ns){ 476 require_once(DOKU_INC.'inc/search.php'); 477 global $conf; 478 global $ID; 479 $dir = $conf['datadir']; 480 $ns = cleanID($ns); 481 #fixme use appropriate function 482 if(empty($ns)){ 483 $ns = dirname(str_replace(':','/',$ID)); 484 if($ns == '.') $ns =''; 485 } 486 $ns = utf8_encodeFN(str_replace(':','/',$ns)); 487 488 print p_locale_xhtml('index'); 489 490 $data = array(); 491 search($data,$conf['datadir'],'search_index',array('ns' => $ns)); 492 print html_buildlist($data,'idx','html_list_index','html_li_index'); 493} 494 495/** 496 * Index item formatter 497 * 498 * User function for html_buildlist() 499 * 500 * @author Andreas Gohr <andi@splitbrain.org> 501 */ 502function html_list_index($item){ 503 $ret = ''; 504 $base = ':'.$item['id']; 505 $base = substr($base,strrpos($base,':')+1); 506 if($item['type']=='d'){ 507 $ret .= '<a href="'.wl($ID,'idx='.$item['id']).'" class="idx_dir">'; 508 $ret .= $base; 509 $ret .= '</a>'; 510 }else{ 511 $ret .= html_wikilink(':'.$item['id']); 512 } 513 return $ret; 514} 515 516/** 517 * Index List item 518 * 519 * This user function is used in html_build_lidt to build the 520 * <li> tags for namespaces when displaying the page index 521 * it gives different classes to opened or closed "folders" 522 * 523 * @author Andreas Gohr <andi@splitbrain.org> 524 */ 525function html_li_index($item){ 526 if($item['type'] == "f"){ 527 return '<li class="level'.$item['level'].'">'; 528 }elseif($item['open']){ 529 return '<li class="open">'; 530 }else{ 531 return '<li class="closed">'; 532 } 533} 534 535/** 536 * Default List item 537 * 538 * @author Andreas Gohr <andi@splitbrain.org> 539 */ 540function html_li_default($item){ 541 return '<li class="level'.$item['level'].'">'; 542} 543 544/** 545 * Build an unordered list 546 * 547 * Build an unordered list from the given $data array 548 * Each item in the array has to have a 'level' property 549 * the item itself gets printed by the given $func user 550 * function. The second and optional function is used to 551 * print the <li> tag. Both user function need to accept 552 * a single item. 553 * 554 * @author Andreas Gohr <andi@splitbrain.org> 555 */ 556function html_buildlist($data,$class,$func,$lifunc='html_li_default'){ 557 $level = 0; 558 $opens = 0; 559 $ret = ''; 560 561 foreach ($data as $item){ 562 563 if( $item['level'] > $level ){ 564 //open new list 565 for($i=0; $i<($item['level'] - $level); $i++){ 566 if ($i) $ret .= "<li class=\"clear\">\n"; 567 $ret .= "\n<ul class=\"$class\">\n"; 568 } 569 }elseif( $item['level'] < $level ){ 570 //close last item 571 $ret .= "</li>\n"; 572 for ($i=0; $i<($level - $item['level']); $i++){ 573 //close higher lists 574 $ret .= "</ul>\n</li>\n"; 575 } 576 }else{ 577 //close last item 578 $ret .= "</li>\n"; 579 } 580 581 //remember current level 582 $level = $item['level']; 583 584 //print item 585 $ret .= $lifunc($item); //user function 586 $ret .= '<span class="li">'; 587 $ret .= $func($item); //user function 588 $ret .= '</span>'; 589 } 590 591 //close remaining items and lists 592 for ($i=0; $i < $level; $i++){ 593 $ret .= "</li></ul>\n"; 594 } 595 596 return $ret; 597} 598 599/** 600 * display backlinks 601 * 602 * @author Andreas Gohr <andi@splitbrain.org> 603 */ 604function html_backlinks(){ 605 require_once(DOKU_INC.'inc/search.php'); 606 global $ID; 607 global $conf; 608 609 if(preg_match('#^(.*):(.*)$#',$ID,$matches)){ 610 $opts['ns'] = $matches[1]; 611 $opts['name'] = $matches[2]; 612 }else{ 613 $opts['ns'] = ''; 614 $opts['name'] = $ID; 615 } 616 617 print p_locale_xhtml('backlinks'); 618 619 $data = array(); 620 search($data,$conf['datadir'],'search_backlinks',$opts); 621 sort($data); 622 623 print '<ul class="idx">'; 624 foreach($data as $row){ 625 print '<li>'; 626 print html_wikilink(':'.$row['id'],$row['id']); 627 print '</li>'; 628 } 629 print '</ul>'; 630} 631 632/** 633 * show diff 634 * 635 * @author Andreas Gohr <andi@splitbrain.org> 636 */ 637function html_diff($text='',$intro=true){ 638 require_once(DOKU_INC.'inc/DifferenceEngine.php'); 639 global $ID; 640 global $REV; 641 global $lang; 642 global $conf; 643 if($text){ 644 $df = new Diff(split("\n",htmlspecialchars(rawWiki($ID,''))), 645 split("\n",htmlspecialchars(cleanText($text)))); 646 $left = '<a class="wikilink1" href="'.wl($ID).'">'. 647 $ID.' '.date($conf['dformat'],@filemtime(wikiFN($ID))).'</a>'. 648 $lang['current']; 649 $right = $lang['yours']; 650 }else{ 651 if($REV){ 652 $r = $REV; 653 }else{ 654 //use last revision if none given 655 $revs = getRevisions($ID); 656 $r = $revs[0]; 657 } 658 659 $df = new Diff(split("\n",htmlspecialchars(rawWiki($ID,$r))), 660 split("\n",htmlspecialchars(rawWiki($ID,'')))); 661 $left = '<a class="wikilink1" href="'.wl($ID,"rev=$r").'">'. 662 $ID.' '.date($conf['dformat'],$r).'</a>'; 663 $right = '<a class="wikilink1" href="'.wl($ID).'">'. 664 $ID.' '.date($conf['dformat'],@filemtime(wikiFN($ID))).'</a> '. 665 $lang['current']; 666 } 667 $tdf = new TableDiffFormatter(); 668 if($intro) print p_locale_xhtml('diff'); 669 ?> 670 <table class="diff" width="100%"> 671 <tr> 672 <td colspan="2" width="50%" class="diff-header"> 673 <?=$left?> 674 </td> 675 <td colspan="2" width="50%" class="diff-header"> 676 <?=$right?> 677 </td> 678 </tr> 679 <?=$tdf->format($df)?> 680 </table> 681 <? 682} 683 684/** 685 * show warning on conflict detection 686 * 687 * @author Andreas Gohr <andi@splitbrain.org> 688 */ 689function html_conflict($text,$summary){ 690 global $ID; 691 global $lang; 692 693 print p_locale_xhtml('conflict'); 694 ?> 695 <form name="editform" method="post" action="<?=script()?>" accept-charset="<?=$lang['encoding']?>"> 696 <input type="hidden" name="id" value="<?=$ID?>" /> 697 <input type="hidden" name="wikitext" value="<?=formText($text)?>" /> 698 <input type="hidden" name="summary" value="<?=formText($summary)?>" /> 699 700 <div align="center"> 701 <input class="button" type="submit" name="do" value="<?=$lang['btn_save']?>" accesskey="s" title="[ALT+S]" /> 702 <input class="button" type="submit" name="do" value="<?=$lang['btn_cancel']?>" /> 703 </div> 704 </form> 705 <br /><br /><br /><br /> 706 <? 707} 708 709/** 710 * Prints the global message array 711 * 712 * @author Andreas Gohr <andi@splitbrain.org> 713 */ 714function html_msgarea(){ 715 global $MSG; 716 717 if(!isset($MSG)) return; 718 719 foreach($MSG as $msg){ 720 print '<div class="'.$msg['lvl'].'">'; 721 print $msg['msg']; 722 print '</div>'; 723 } 724} 725 726/** 727 * Prints the registration form 728 * 729 * @author Andreas Gohr <andi@splitbrain.org> 730 */ 731function html_register(){ 732 global $lang; 733 global $ID; 734 735 print p_locale_xhtml('register'); 736?> 737 <div align="center"> 738 <form name="register" method="post" action="<?=wl($ID)?>" accept-charset="<?=$lang['encoding']?>"> 739 <input type="hidden" name="do" value="register" /> 740 <input type="hidden" name="save" value="1" /> 741 <fieldset> 742 <legend><?=$lang['register']?></legend> 743 <label> 744 <?=$lang['user']?> 745 <input type="text" name="login" class="edit" size="50" value="<?=formText($_POST['login'])?>" /> 746 </label><br /> 747 <label> 748 <?=$lang['fullname']?> 749 <input type="text" name="fullname" class="edit" size="50" value="<?=formText($_POST['fullname'])?>" /> 750 </label><br /> 751 <label> 752 <?=$lang['email']?> 753 <input type="text" name="email" class="edit" size="50" value="<?=formText($_POST['email'])?>" /> 754 </label><br /> 755 <input type="submit" class="button" value="<?=$lang['register']?>" /> 756 </fieldset> 757 </form> 758 </div> 759<? 760} 761 762/** 763 * This displays the edit form (lots of logic included) 764 * 765 * @author Andreas Gohr <andi@splitbrain.org> 766 */ 767function html_edit($text=null,$include='edit'){ //FIXME: include needed? 768 global $ID; 769 global $REV; 770 global $DATE; 771 global $RANGE; 772 global $PRE; 773 global $SUF; 774 global $INFO; 775 global $SUM; 776 global $lang; 777 global $conf; 778 779 //set summary default 780 if(!$SUM){ 781 if($REV){ 782 $SUM = $lang['restored']; 783 }elseif(!$INFO['exists']){ 784 $SUM = $lang['created']; 785 } 786 } 787 788 //no text? Load it! 789 if(!isset($text)){ 790 $pr = false; //no preview mode 791 if($RANGE){ 792 list($PRE,$text,$SUF) = rawWikiSlices($RANGE,$ID,$REV); 793 }else{ 794 $text = rawWiki($ID,$REV); 795 } 796 }else{ 797 $pr = true; //preview mode 798 } 799 800 $wr = $INFO['writable']; 801 if($wr){ 802 if ($REV) print p_locale_xhtml('editrev'); 803 print p_locale_xhtml($include); 804 }else{ 805 print p_locale_xhtml('read'); 806 $ro='readonly="readonly"'; 807 } 808 if(!$DATE) $DATE = $INFO['lastmod']; 809?> 810 <form name="editform" method="post" action="<?=script()?>" accept-charset="<?=$lang['encoding']?>" onsubmit="return svchk()"> 811 <input type="hidden" name="id" value="<?=$ID?>" /> 812 <input type="hidden" name="rev" value="<?=$REV?>" /> 813 <input type="hidden" name="date" value="<?=$DATE?>" /> 814 <input type="hidden" name="prefix" value="<?=formText($PRE)?>" /> 815 <input type="hidden" name="suffix" value="<?=formText($SUF)?>" /> 816 <table style="width:99%"> 817 <tr> 818 <td class="toolbar" colspan="3"> 819 <?if($wr){?> 820 <script language="JavaScript" type="text/javascript"> 821 <?/* sets changed to true when previewed */?> 822 textChanged = <? ($pr) ? print 'true' : print 'false' ?>; 823 824 formatButton('images/bold.png','<?=$lang['qb_bold']?>','**','**','<?=$lang['qb_bold']?>','b'); 825 formatButton('images/italic.png','<?=$lang['qb_italic']?>',"\/\/","\/\/",'<?=$lang['qb_italic']?>','i'); 826 formatButton('images/underline.png','<?=$lang['qb_underl']?>','__','__','<?=$lang['qb_underl']?>','u'); 827 formatButton('images/code.png','<?=$lang['qb_code']?>','\'\'','\'\'','<?=$lang['qb_code']?>','c'); 828 829 formatButton('images/fonth1.png','<?=$lang['qb_h1']?>','====== ',' ======\n','<?=$lang['qb_h1']?>','1'); 830 formatButton('images/fonth2.png','<?=$lang['qb_h2']?>','===== ',' =====\n','<?=$lang['qb_h2']?>','2'); 831 formatButton('images/fonth3.png','<?=$lang['qb_h3']?>','==== ',' ====\n','<?=$lang['qb_h3']?>','3'); 832 formatButton('images/fonth4.png','<?=$lang['qb_h4']?>','=== ',' ===\n','<?=$lang['qb_h4']?>','4'); 833 formatButton('images/fonth5.png','<?=$lang['qb_h5']?>','== ',' ==\n','<?=$lang['qb_h5']?>','5'); 834 835 formatButton('images/link.png','<?=$lang['qb_link']?>','[[',']]','<?=$lang['qb_link']?>','l'); 836 formatButton('images/extlink.png','<?=$lang['qb_extlink']?>','[[',']]','http://www.example.com|<?=$lang['qb_extlink']?>'); 837 838 formatButton('images/list.png','<?=$lang['qb_ol']?>',' - ','\n','<?=$lang['qb_ol']?>'); 839 formatButton('images/list_ul.png','<?=$lang['qb_ul']?>',' * ','\n','<?=$lang['qb_ul']?>'); 840 841 insertButton('images/rule.png','<?=$lang['qb_hr']?>','----\n'); 842 mediaButton('images/image.png','<?=$lang['qb_media']?>','m','<?=$INFO['namespace']?>'); 843 844 <? 845 if($conf['useacl'] && $_SERVER['REMOTE_USER']){ 846 echo "insertButton('images/sig.png','".$lang['qb_sig']."','".html_signature()."','y');"; 847 } 848 ?> 849 </script> 850 <?}?> 851 </td> 852 </tr> 853 <tr> 854 <td colspan="3"> 855 <textarea name="wikitext" id="wikitext" <?=$ro?> cols="80" rows="10" class="edit" onchange="textChanged = true;" onkeyup="summaryCheck();" tabindex="1"><?="\n".formText($text)?></textarea> 856 </td> 857 </tr> 858 <tr> 859 <td> 860 <?if($wr){?> 861 <input class="button" type="submit" name="do" value="<?=$lang['btn_save']?>" accesskey="s" title="[ALT+S]" onclick="textChanged=false" onkeypress="textChanged=false" tabindex="3" /> 862 <input class="button" type="submit" name="do" value="<?=$lang['btn_preview']?>" accesskey="p" title="[ALT+P]" onclick="textChanged=false" onkeypress="textChanged=false" tabindex="4" /> 863 <input class="button" type="submit" name="do" value="<?=$lang['btn_cancel']?>" tabindex="5" /> 864 <?}?> 865 </td> 866 <td> 867 <?if($wr){?> 868 <?=$lang['summary']?>: 869 <input type="text" class="edit" name="summary" id="summary" size="50" onkeyup="summaryCheck();" value="<?=formText($SUM)?>" tabindex="2" /> 870 <?}?> 871 </td> 872 <td align="right"> 873 <script type="text/javascript"> 874 showSizeCtl(); 875 <?if($wr){?> 876 init_locktimer(<?=$conf['locktime']-60?>,'<?=$lang['willexpire']?>'); 877 document.editform.wikitext.focus(); 878 <?}?> 879 </script> 880 </td> 881 </tr> 882 </table> 883 </form> 884<? 885} 886 887/** 888 * prepares the signature string as configured in the config 889 * 890 * @author Andreas Gohr <andi@splitbrain.org> 891 */ 892function html_signature(){ 893 global $conf; 894 global $INFO; 895 896 $sig = $conf['signature']; 897 $sig = strftime($sig); 898 $sig = str_replace('@USER@',$_SERVER['REMOTE_USER'],$sig); 899 $sig = str_replace('@NAME@',$INFO['userinfo']['name'],$sig); 900 $sig = str_replace('@MAIL@',$INFO['userinfo']['mail'],$sig); 901 $sig = str_replace('@DATE@',date($conf['dformat']),$sig); 902 return $sig; 903} 904 905/** 906 * prints some debug info 907 * 908 * @author Andreas Gohr <andi@splitbrain.org> 909 */ 910function html_debug(){ 911 global $conf; 912 global $lang; 913 //remove sensitive data 914 $cnf = $conf; 915 $cnf['auth']='***'; 916 $cnf['notify']='***'; 917 $cnf['ftp']='***'; 918 919 print '<html><body>'; 920 921 print '<p>When reporting bugs please send all the following '; 922 print 'output as a mail to andi@splitbrain.org '; 923 print 'The best way to do this is to save this page in your browser</p>'; 924 925 print '<b>$_SERVER:</b><pre>'; 926 print_r($_SERVER); 927 print '</pre>'; 928 929 print '<b>$conf:</b><pre>'; 930 print_r($cnf); 931 print '</pre>'; 932 933 print '<b>DOKU_BASE:</b><pre>'; 934 print DOKU_BASE; 935 print '</pre>'; 936 937 print '<b>abs DOKU_BASE:</b><pre>'; 938 print DOKU_URL; 939 print '</pre>'; 940 941 print '<b>rel DOKU_BASE:</b><pre>'; 942 print dirname($_SERVER['PHP_SELF']).'/'; 943 print '</pre>'; 944 945 print '<b>PHP Version:</b><pre>'; 946 print phpversion(); 947 print '</pre>'; 948 949 print '<b>locale:</b><pre>'; 950 print setlocale(LC_ALL,0); 951 print '</pre>'; 952 953 print '<b>encoding:</b><pre>'; 954 print $lang['encoding']; 955 print '</pre>'; 956 957 print '<b>Environment:</b><pre>'; 958 print_r($_ENV); 959 print '</pre>'; 960 961 print '<b>PHP settings:</b><pre>'; 962 $inis = ini_get_all(); 963 print_r($inis); 964 print '</pre>'; 965 966 print '</body></html>'; 967} 968 969/** 970 * Print the admin overview page 971 * 972 * @author Andreas Gohr <andi@splitbrain.org> 973 */ 974function html_admin(){ 975 global $ID; 976 global $lang; 977 978 print p_locale_xhtml('admin'); 979 980 ptln('<ul class="admin">'); 981 982 // currently ACL only - more to come 983 ptln('<li><a href="'.wl($ID,'do=admin&page=acl').'">'.$lang['admin_acl'].'</a></li>'); 984 985 ptln('</ul>'); 986} 987 988 989//Setup VIM: ex: et ts=2 enc=utf-8 : 990