static function parse_msg($text, $show_smilies = true, $preview = false, $bbcode = true) { global $db, $futurebb_user, $futurebb_config; if ($bbcode && empty(self::$pattern)) { self::$pattern = array(); self::$replace = array(); self::add_bbcode('%\\[b\\](.*?)\\[/b\\]%ms', '<strong>$1</strong>'); self::add_bbcode('%\\[i\\](.*?)\\[/i\\]%ms', '<em>$1</em>'); self::add_bbcode('%\\[u\\](.*?)\\[/u\\]%ms', '<u>$1</u>'); self::add_bbcode('%\\[s\\](.*?)\\[/s\\]%ms', '<del>$1</del>'); self::add_bbcode('%\\[colou?r=(white|black|red|green|blue|orange|yellow|pink|gray|magenta|#[0-9a-fA-F]{6}|\\#[0-9a-fA-F]{3})\\](.*?)\\[/colou?r\\]%m', '<span style="color:$1">$2</span>'); } $text = htmlspecialchars($text); //clear out any funny business $text = preg_replace_callback('%\\s?\\[code\\](.*?)\\[/code\\]\\s?%msi', 'self::handle_code_tag_remove', $text); //remove content of code tags prior to parsing while (preg_match('%\\[quote(=.*?)?\\](.*?)\\[/quote\\]%ms', $text)) { $text = preg_replace_callback('%\\[quote\\](.*?)\\[/quote\\]%ms', 'self::handle_quote_tag', $text); $text = preg_replace_callback('%\\[quote=(.*?)\\](.*?)\\[/quote\\]%ms', 'self::handle_quote_tag', $text); } //links and images (these can't be grouped with the rest because they use a different function $text = preg_replace_callback('%\\[url=?(.*?)\\](.*?)\\[/url\\]%s', 'self::handle_url_tag', $text); $text = preg_replace_callback('%\\[img\\](.*?)\\[/img\\]%s', 'self::handle_img_tag', $text); // Format @username into tags if ($futurebb_config['allow_notifications'] == 1) { $text = preg_replace('%(\\s|^)@([a-zA-Z0-9_\\-]+)%', '$1<span class="usertag">@$2</span>', $text); } //run the bbcode parser with the items entered into the array at the beginning of this function if ($bbcode) { self::parse_bbcode($text); } if ($show_smilies) { // only parse similies if they were enabled by poster self::parse_smilies($text); } $text = self::add_line_breaks($text); //make the @username into links where applicable $at_usernames = array(); $text = preg_replace_callback('%<span class="usertag">@([a-zA-Z0-9_\\-]+)</span>%', function ($matches) use(&$at_usernames) { if (in_array($matches[1], $at_usernames)) { $return = array_search($matches[1], $at_usernames); } else { $at_usernames[] = $matches[1]; $return = sizeof($at_usernames) - 1; } return '<span class="usertag">' . $return . '</span>'; }, $text); if (!empty($at_usernames)) { $at_usernames_safe = array(); foreach ($at_usernames as $username) { $at_usernames_safe[] = '\'' . $db->escape(strtolower($username)) . '\''; } $returned_usernames = array(); $result = $db->query('SELECT LOWER(username) FROM `#^users` WHERE LOWER(username) IN(' . implode(',', $at_usernames_safe) . ')') or enhanced_error('Failed to validate usernames', true); while (list($username) = $db->fetch_row($result)) { $returned_usernames[] = $username; } $text = preg_replace_callback('%<span class="usertag">(\\d+)</span>%', function ($matches) use($at_usernames, $returned_usernames) { global $base_config; $req_username = $at_usernames[$matches[1]]; if (in_array(strtolower($req_username), $returned_usernames)) { $return = '<a href="' . $base_config['baseurl'] . '/users/' . $req_username . '">@' . $req_username . '</a>'; } else { $return = '@' . $req_username; } return '<span class="usertag">' . $return . '</span>'; }, $text); } //handle list and table tags last, they're weird $text = self::handle_list_tags($text); $text = self::handle_table_tags($text); $text = preg_replace_callback('%\\s?\\[code\\](.*?)\\[/code\\]\\s?%msi', 'self::handle_code_tag_replace', $text); //put [code] tags back $text = censor($text); return $text; }