Completed
Pull Request — development (#2316)
by Joshua
09:55
created

SmileyParser::getDefault()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 10
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 1

Importance

Changes 2
Bugs 0 Features 1
Metric Value
dl 0
loc 10
ccs 6
cts 6
cp 1
rs 9.4286
c 2
b 0
f 1
cc 1
eloc 6
nc 1
nop 0
crap 1
1
<?php
2
3
/**
4
 *
5
 * @name      ElkArte Forum
6
 * @copyright ElkArte Forum contributors
7
 * @license   BSD http://opensource.org/licenses/BSD-3-Clause
8
 *
9
 * This software is a derived product, based on:
10
 *
11
 * Simple Machines Forum (SMF)
12
 * copyright:	2011 Simple Machines (http://www.simplemachines.org)
13
 * license:		BSD, See included LICENSE.TXT for terms and conditions.
14
 *
15
 *
16
 */
17
18
namespace BBC;
19
20
class SmileyParser
21
{
22
	protected $enabled = true;
23
	protected $smileys = array();
24
	// This smiley regex makes sure it doesn't parse smileys within code tags (so [url=mailto:[email protected]] doesn't parse the :D smiley)
25
	protected $search = array();
26
	protected $replace = array();
27
	protected $marker = "\r";
28
	protected $path = '';
29
30 1
	public function __construct($path, array $smileys = array())
31
	{
32 1
		$this->setPath($path);
33
34 1
		if ($this->enabled)
35 1
		{
36 1
			$this->smileys = empty($smileys) ? $this->load() : $smileys;
37 1
		}
38 1
	}
39
40 1
	public function setEnabled($toggle)
41
	{
42 1
		$this->enabled = (bool) $toggle;
43 1
		return $this;
44
	}
45
46
	public function setMarker($marker)
47
	{
48
		$this->marker = $marker;
49
		return $this;
50
	}
51
52 1
	public function setPath($path)
53
	{
54 1
		$this->path = htmlspecialchars($path);
55 1
		return $this;
56
	}
57
58
	/**
59
	 * Parse smileys in the passed message.
60
	 *
61
	 * What it does:
62
	 * - The smiley parsing function which makes pretty faces appear :).
63
	 * - If custom smiley sets are turned off by smiley_enable, the default set of smileys will be used.
64
	 * - These are specifically not parsed in code tags [url=mailto:[email protected]]
65
	 * - Caches the smileys from the database or array in memory.
66
	 * - Doesn't return anything, but rather modifies message directly.
67
	 *
68
	 * @param string $message
69
	 */
70 1
	public function parseBlock(&$message)
71
	{
72
		// No smiley set at all?!
73 1
		if (!$this->enabled || $message === '' || trim($message) === '')
74 1
		{
75 1
			return;
76
		}
77
78
		// Replace away!
79 1
		$message = preg_replace_callback($this->search, array($this, 'parser_callback'), $message);
80 1
	}
81
82 1
	public function parse(&$message)
83
	{
84
		// Parse the smileys within the parts where it can be done safely.
85 1
		if ($this->enabled && trim($message) !== '')
86 1
		{
87 1
			$message_parts = explode($this->marker, $message);
88
89
			// first part (0) parse smileys. Then every other one after that parse smileys
90 1
			for ($i = 0, $n = count($message_parts); $i < $n; $i += 2)
91
			{
92 1
				$this->parseBlock($message_parts[$i]);
93 1
			}
94
95 1
			$message = implode('', $message_parts);
96 1
		}
97
		// No smileys, just get rid of the markers.
98
		else
99
		{
100
			$message = str_replace($this->marker, '', $message);
101
		}
102 1
	}
103
104
	public function add($from, $to, $description)
0 ignored issues
show
Unused Code introduced by
The parameter $from is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $to is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
Unused Code introduced by
The parameter $description is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
105
	{
106
107
	}
108
109
	protected function parser_callback(array $matches)
110
	{
111
		return $this->replace[$matches[0]];
112
	}
113
114 1
	protected function setSearchReplace($smileysfrom, $smileysto, $smileysdescs)
115
	{
116 1
		$searchParts = array();
117
118 1
		for ($i = 0, $n = count($smileysfrom); $i < $n; $i++)
119
		{
120 1
			$specialChars = htmlspecialchars($smileysfrom[$i], ENT_QUOTES);
121 1
			$smileyCode = '<img src="' . $this->path . $smileysto[$i] . '" alt="' . strtr($specialChars, array(':' => '&#58;', '(' => '&#40;', ')' => '&#41;', '$' => '&#36;', '[' => '&#091;')). '" title="' . strtr(htmlspecialchars($smileysdescs[$i]), array(':' => '&#58;', '(' => '&#40;', ')' => '&#41;', '$' => '&#36;', '[' => '&#091;')) . '" class="smiley" />';
122
123 1
			$this->replace[$smileysfrom[$i]] = $smileyCode;
124
125 1
			$searchParts[] = preg_quote($smileysfrom[$i], '~');
126 1
			if ($smileysfrom[$i] != $specialChars)
127 1
			{
128 1
				$this->replace[$specialChars] = $smileyCode;
129 1
				$searchParts[] = preg_quote($specialChars, '~');
130 1
			}
131 1
		}
132
133 1
		$this->search = '~(?<=[>:\?\.\s\x{A0}[\]()*\\\;]|^)(' . implode('|', $searchParts) . ')(?=[^[:alpha:]0-9]|$)~';
0 ignored issues
show
Documentation Bug introduced by
It seems like '~(?<=[>:\\?\\.\\s\\x{A0...(?=[^[:alpha:]0-9]|$)~' of type string is incompatible with the declared type array of property $search.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
134 1
	}
135
136 1
	protected function load()
137
	{
138 1
		global $modSettings;
139
140
		// Use the default smileys if it is disabled. (better for "portability" of smileys.)
141 1
		if (empty($modSettings['smiley_enable']))
142 1
		{
143 1
			list ($smileysfrom, $smileysto, $smileysdescs) = $this->getDefault();
144 1
		}
145
		else
146
		{
147
			list ($smileysfrom, $smileysto, $smileysdescs) = $this->getFromDB();
148
		}
149
150 1
		$this->setSearchReplace($smileysfrom, $smileysto, $smileysdescs);
151 1
	}
152
153 1
	protected function getDefault()
154
	{
155 1
		global $txt;
156
157 1
		$smileysfrom = array('>:D', ':D', '::)', '>:(', ':))', ':)', ';)', ';D', ':(', ':o', '8)', ':P', '???', ':-[', ':-X', ':-*', ':\'(', ':-\\', '^-^', 'O0', 'C:-)', 'O:)');
158 1
		$smileysto = array('evil.gif', 'cheesy.gif', 'rolleyes.gif', 'angry.gif', 'laugh.gif', 'smiley.gif', 'wink.gif', 'grin.gif', 'sad.gif', 'shocked.gif', 'cool.gif', 'tongue.gif', 'huh.gif', 'embarrassed.gif', 'lipsrsealed.gif', 'kiss.gif', 'cry.gif', 'undecided.gif', 'azn.gif', 'afro.gif', 'police.gif', 'angel.gif');
159 1
		$smileysdescs = array('', $txt['icon_cheesy'], $txt['icon_rolleyes'], $txt['icon_angry'], $txt['icon_laugh'], $txt['icon_smiley'], $txt['icon_wink'], $txt['icon_grin'], $txt['icon_sad'], $txt['icon_shocked'], $txt['icon_cool'], $txt['icon_tongue'], $txt['icon_huh'], $txt['icon_embarrassed'], $txt['icon_lips'], $txt['icon_kiss'], $txt['icon_cry'], $txt['icon_undecided'], '', '', '', $txt['icon_angel']);
160
161 1
		return array($smileysfrom, $smileysto, $smileysdescs);
162
	}
163
164
	protected function getFromDB()
165
	{
166
		// Load the smileys in reverse order by length so they don't get parsed wrong.
167
		if (($temp = cache_get_data('parsing_smileys', 480)) == null)
168
		{
169
			$smileysfrom = array();
170
			$smileysto = array();
171
			$smileysdescs = array();
172
173
			$db = database();
174
175
			$db->fetchQueryCallback('
176
					SELECT code, filename, description
177
					FROM {db_prefix}smileys
178
					ORDER BY LENGTH(code) DESC',
179
				array(
180
				),
181
				function($row) use (&$smileysfrom, &$smileysto, &$smileysdescs)
182
				{
183
					$smileysfrom[] = $row['code'];
184
					$smileysto[] = htmlspecialchars($row['filename']);
185
					$smileysdescs[] = $row['description'];
186
				}
187
			);
188
189
			$temp = array($smileysfrom, $smileysto, $smileysdescs);
190
191
			cache_put_data('parsing_smileys', $temp, 480);
192
		}
193
194
		return $temp;
195
	}
196
}