Forum Webscript.Ru

Программирование => PHP => Тема начата: Pr0Head от 01 Апреля 2002, 18:12:16

Название: Замена служебного символа.
Отправлено: Pr0Head от 01 Апреля 2002, 18:12:16
Приветствую!

Есть задача сделать подсветку РНР-кода в тексте.
Вот допустим пример:

Test message

echo $ttt;
if ($a = 1) {
$ret = \'rrr\';
}
?>";
$text = str_replace("\\$","\\\\$",$text);
highlight_string($text);
?>

tetsts

Как мне перед знаком $ подставить \\, а то получается, что он название переменной просто игнорирует.

Название: Замена служебного символа.
Отправлено: Dm от 01 Апреля 2002, 18:25:55
http://php.spb.ru/php/regexp.html
Название: Замена служебного символа.
Отправлено: Макс от 01 Апреля 2002, 22:17:06
Не Pr0Head, слеши нужно ставить в самом начале:

echo \\$ttt;
if (\\$a = 1) {
\\$ret = \'rrr\';
}
?>";

В твоем неправильном коде именно в этом месте происходит замена переменной на ее значение, поэтому слеши сразу прописывать нужно.

ИМХО, если код большой - то лучше выноси код который нужно подсвечивать в отдельный файл и используй highlight_file(); для него и слеши проставлять не нужно.
Название: Замена служебного символа.
Отправлено: Pr0Head от 02 Апреля 2002, 11:34:04
2 Макс: Может много хочу, но хочется все в одном файле, и текст и РНР-код.

Смысл такой: пользователь пишет статью с РНР-кодом, потом загружет этот файл на сервер. Так как я заранее не могу отследить правильность написания кода, хочется сделать это программно.

2 Dm: Спасибо, это похоже на правду, но почему-то код который написан на странице, у меня не работает. Будем копать. :)
Название: Замена служебного символа.
Отправлено: Dm от 02 Апреля 2002, 18:10:34
Pr0Head
можно взять заведомо рабочий вариант, к примеру, из этого форума :)
Название: Замена служебного символа.
Отправлено: Pr0Head от 03 Апреля 2002, 13:52:38
Цитировать
можно взять заведомо рабочий вариант, к примеру, из этого форума

Вот бы кто исходником форума поделился... :)

Может кто исходником поделится? Я не думаю, что я первопроходец.
Название: Замена служебного символа.
Отправлено: Dm от 03 Апреля 2002, 19:09:49
из файла vb/admin/functions.php:

// ###################### Start phphighlite #######################
function phphighlite($code) {
  //PHP 4 only

  if (floor(phpversion())<4) {
    $buffer=$code;
  } else {
$code = str_replace("
", "", $code);
$code = str_replace("
", "", $code);
$code = str_replace(">", ">", $code);
$code = str_replace("<", "<", $code);

$code = str_replace("&", "&", $code);
$code = str_replace(\'$\', \'\\$\', $code);
$code = str_replace(\'\\n\', \'\\\\\\\\n\', $code);
$code = str_replace(\'\\r\', \'\\\\\\\\r\', $code);
$code = str_replace(\'\\t\', \'\\\\\\\\t\', $code);

$code = stripslashes($code);

if (!strpos($code," $code=""; // $addedtags=1;
}
ob_start();
$oldlevel=error_reporting(0);
highlight_string($code);
error_reporting($oldlevel);
$buffer = ob_get_contents();
ob_end_clean();
if ($addedtags) {
 $openingpos = strpos($buffer,\'<?\');
 $closingpos = strrpos($buffer, \'?\');
 $buffer=substr($buffer, 0, $openingpos).substr($buffer, $openingpos+5, $closingpos-($openingpos+5)).substr($buffer, $closingpos+5);
}
$buffer = str_replace(""", "\\"", $buffer);
  }

  return "
PHP:
$buffer
";
}
?>
Название: Замена служебного символа.
Отправлено: Pr0Head от 04 Апреля 2002, 17:48:39
Хм. Я попробовал и получается, что этот код высвечивает все, что было введено в textarea. Если брать на примере этого форума, то этот скрипт выдаст мне на экране:

РНР:
------------------------------------
здесь он выдаст ВСЕ, что я ввел в текстареа, а не только РНР-код.
------------------------------------

Вот мой код, на основе кода DM`a:



if ($code) {

        $code = str_replace("
", "", $code);
        $code = str_replace("
", "", $code);
        $code = str_replace(">", ">", $code);
        $code = str_replace("<", "<", $code);

        $code = str_replace("&", "&", $code);
        $code = str_replace(\'$\', \'\\$\', $code);
        $code = str_replace(\'\\n\', \'\\\\n\', $code);
        $code = str_replace(\'\\r\', \'\\\\r\', $code);
        $code = str_replace(\'\\t\', \'\\\\t\', $code);

        $code = stripslashes($code);

        if (!strpos($code,"            $code=""; //            $addedtags=1;
        }
        ob_start();
        $oldlevel=error_reporting(0);
        highlight_string($code);
        error_reporting($oldlevel);
        $buffer = ob_get_contents();
        ob_end_clean();
        if ($addedtags) {
          $openingpos = strpos($buffer,\'<?\');
          $closingpos = strrpos($buffer, \'?\');
          $buffer=substr($buffer, 0, $openingpos).substr($buffer, $openingpos+5, $closingpos-($openingpos+5)).substr($buffer, $closingpos+5);
        }
        $buffer = str_replace(""", "\\"", $buffer);

  echo "
PHP:
$buffer
";
}

else {
echo "

";
}

?>


Интересно, а как он отлавливает все что находится между [РНР] и [/РНР] и записывает в $code? Иными словами, может кто-нибудь знает, как сделано на этом форуме, текст сообщения сохраняет стиль (шрифт, размер), а код отдельно хайлайтом подсвечивается?
Название: Замена служебного символа.
Отправлено: Dm от 10 Апреля 2002, 00:41:09
из vb:
/admin/functions.php

// ###################### Start bbcodeparse #######################
function bbcodeparse($bbcode,$forumid=0,$allowsmilie=1) {

  global $allowhtml,$allowbbcode,$allowbbimagecode,$allowsmilies;

  if ($forumid == 0)
  {
    $dohtml=$allowhtml;
    $dobbcode=$allowbbcode;
    $dobbimagecode=$allowbbimagecode;
    $dosmilies=$allowsmilies;
  }
  else
  {
    $forum=getforuminfo($forumid);
    $dohtml=$forum[allowhtml];
    $dobbimagecode=$forum[allowimages];
    $dosmilies=$forum[allowsmilies];

    if ($allowsmilie!=1) {
      $dosmilies = $allowsmilie;
    }

    $dobbcode=$forum[allowbbcode];
  }

  return bbcodeparse2($bbcode,$dohtml,$dobbimagecode,$dosmilies,$dobbcode);
}

function bbcodeparse2($bbcode,$dohtml,$dobbimagecode,$dosmilies,$dobbcode)
{ // parses text for vB code, smilies and censoring

  global $DB_site,$wordwrap,$allowdynimg, $bbuserinfo;

  static $smilies,$bbcodes;
  global $regexcreated,$searcharray,$replacearray,$phpversionnum;

  if($wordwrap!=0) {
    $bbcode=dowordwrap($bbcode);
  }

  if(!$dohtml)  { // kill any rogue html code
    // $bbcode=str_replace("&","&",$bbcode);
    $bbcode=str_replace("<","&lt;",$bbcode);
    $bbcode=str_replace(">","&gt;",$bbcode);
    $bbcode=str_replace("<","<",$bbcode);
    $bbcode=str_replace(">",">",$bbcode);
  }
  $bbcode=nl2br($bbcode);

  //smilies
  if($dosmilies) {
    $bbcode=str_replace(">)", "> )", $bbcode);
    $bbcode=str_replace("<)", "< )", $bbcode);
    if(!isset($smilies)) {
      $smilies=$DB_site->query("SELECT smilietext,smiliepath FROM smilie");
    } else {
      $DB_site->data_seek(0,$smilies);
    }

    while ($smilie=$DB_site->fetch_array($smilies)) {
      if(trim($smilie[smilietext])!="") {
        $bbcode=str_replace(trim($smilie[smilietext]),"\\"\\"",$bbcode);
      }
    }
  }

  if($dobbcode and strpos($bbcode,"]")) {
    if (!isset($regexcreated)) {
      $regexcreated = 1;
      $phpversionnum = phpversion();

      if (floor($phpversionnum) < 4) {
        $searcharray = array(
          "/(\\[)(list)(=)([\'\\"]?)([^\\"\']*)(\\\\4])(.*)(\\[\\/list)(((=)(\\\\4)([^\\"\']*)(\\\\4]))|(\\]))/siU",
          "/(\\[)(list)(])(.*)(\\[\\/list\\])/siU",
          "/(\\[\\*\\])/siU",
          "/(\\[)(url)(=)([\'\\"]?)(www\\.)([^\\"\']*)(\\\\4)(.*)(\\[\\/url\\])/siU",
          "/(\\[)(url)(=)([\'\\"]?)([^\\"\']*)(\\\\4])(.*)(\\[\\/url\\])/siU",
          "/(\\[)(url)(])(www\\.)([^\\"]*)(\\[\\/url\\])/siU",
          "/(\\[)(url)(])([^\\"]*)(\\[\\/url\\])/siU",
          "/(\\[)(php)(])(\\r\\n)*(.*)(\\[\\/php\\])/siU",
          "/(\\[)(code)(])(\\r\\n)*(.*)(\\[\\/code\\])/siU",
          "/javascript:/si",
          "/about:/si",
          "/vbscript:/si"
        );

        $replacearray = array(
          "
    \\\\7
",
          "",
          "
  • ",
              "\\\\8",
              "\\\\7",
              "\\\\5",
              "\\\\4",
              "
    code:
    \\\\5
    ",
              "
    code:
    \\\\5
    ",
              "java script:",
              "about :",
              "vbscript :"
            );
          } else {
            $searcharray = array(
              "/(\\[)(list)(=)([\'\\"]?)([^\\"\']*)(\\\\4])(.*)(\\[\\/list)(((=)(\\\\4)([^\\"\']*)(\\\\4]))|(\\]))/esiU",
              "/(\\[)(list)(])(.*)(\\[\\/list\\])/esiU",
              "/(\\[)(url)(=)([\'\\"]?)([^\\"\']*)(\\\\4])(.*)(\\[\\/url\\])/esiU",
              "/(\\[)(url)(])([^\\"]*)(\\[\\/url\\])/esiU",
              "/(\\[)(code)(])(\\r\\n)*(.*)(\\[\\/code\\])/esiU",
              "/(\\[)(php)(])(\\r\\n)*(.*)(\\[\\/php\\])/esiU",
              "/javascript:/si",
              "/about:/si",
              "/vbscript:/si"
            );

            $replacearray = array(
              "createlists(\'\\\\7\', \'\\\\5\')",
              "createlists(\'\\\\4\')",
              "checkurl(\'\\\\5\', \'\\\\7\')",
              "checkurl(\'\\\\4\')",
              "stripbrsfromcode(\'\\\\5\')",
              "phphighlite(\'\\\\5\')",
              "java script:",
              "about :",
              "vbscript :"
            );
          }  // end version check

          $doubleRegex = "/(\\[)(%s)(=)([\'\\"]?)([^\\"\']*)(\\\\4])(.*)(\\[\\/%s\\])/siU";
          $singleRegex = "/(\\[)(%s)(])(.*)(\\[\\/%s\\])/siU";

          $bbcodes=$DB_site->query("SELECT bbcodetag,bbcodereplacement,twoparams FROM bbcode");

          while($bbregex=$DB_site->fetch_array($bbcodes)) {
            if ($bbregex[twoparams]) {
              $regex=sprintf($doubleRegex, $bbregex[bbcodetag], $bbregex[bbcodetag]);
            } else {
              $regex=sprintf($singleRegex, $bbregex[bbcodetag], $bbregex[bbcodetag]);
            }
            $searcharray[] = $regex;
            $replacearray[] = $bbregex[bbcodereplacement];
            // and get nested ones:
            $searcharray[] = $regex;
            $replacearray[] = $bbregex[bbcodereplacement];
            $searcharray[] = $regex;
            $replacearray[] = $bbregex[bbcodereplacement];
          }

        }

        if ($phpversionnum<"4.0.5") {
          $bbcode=str_replace("\'", "\\\'", $bbcode);
        }
        $bbcode=preg_replace($searcharray, $replacearray, $bbcode);

        if($dobbimagecode and ($bbuserinfo[userid]==0 or $bbuserinfo[showimages])) {
          // do [img]xxx[/img]
          $bbcode = preg_replace("/\\[img\\](\\r\\n|\\r|\\n)*((http|https):\\/\\/([^;<>\\*\\(\\)\\"".iif($allowdynimg,"","\\?\\&")."]+)|[a-z0-9\\/\\\\\\._\\- ]+)\\[\\/img\\]/siU", "\\"\\"", $bbcode);
        }
        $bbcode = preg_replace("/\\[img\\](\\r\\n|\\r|\\n)*((http|https):\\/\\/([^;<>\\*\\(\\)\\"]+)|[a-z0-9\\/\\\\\\._\\- ]+)\\[\\/img\\]/siU", "\\\\2", $bbcode);

        $bbcode=str_replace("\\\\\'", "\'", $bbcode);

        if (floor($phpversionnum) < 4) {
          // get rid of stray
     tags in the code - upsets older browsers (IE 4.72 reported problems)
          $codebits=explode("
    code:
    ",$bbcode);
          list($key,$bbcode)=each($codebits);

          while (list($key,$val)=each($codebits)) {
            $sbbits=explode("

    ",$val);
            $newbits=str_replace("
    ", "", $sbbits[0])."
    ".$sbbits[1];
            $bbcode.="
    code:
    ".$newbits;
          }
        }
      }

    $bbcode=str_replace("{", "{", $bbcode); // stop people posting replacements in their posts

      return censortext($bbcode);

    }

  • Название: Замена служебного символа.
    Отправлено: Britva от 10 Апреля 2002, 01:35:35
    Код vB - не opensource, а платный продукт, поэтому нежелательно выставлять в открытую его исходники...