PluginProbe ʕ •ᴥ•ʔ
MailPoet – Newsletters, Email Marketing, and Automation / 5.34.2
MailPoet – Newsletters, Email Marketing, and Automation v5.34.2
5.35.0 5.34.3 5.34.2 5.34.1 5.34.0 5.33.1 5.33.0 5.32.0 5.31.0 5.30.0 5.29.0 5.28.1 5.28.0 5.27.0 5.26.0 5.26.1 5.25.0 5.24.0 4.43.0 4.43.1 4.44.0 4.44.1 4.45.0 4.46.0 4.47.0 4.48.0 4.48.1 4.48.2 4.49.0 4.49.1 4.5.0 4.5.1 4.5.2 4.50.0 4.50.1 4.51.0 4.51.1 4.51.2 4.52.0 4.53.0 4.54.0 4.55.0 4.56.0 4.57.0 4.58.0 4.58.1 4.58.2 4.6.0 4.6.1 4.6.2 4.7.0 4.7.1 4.8.0 4.8.1 4.9.0 5.0.0 5.0.1 5.0.2 5.1.0 5.1.1 5.10.0 5.10.1 5.11.0 5.12.0 5.12.1 5.12.10 5.12.11 5.12.12 5.12.13 5.12.2 5.12.3 5.12.4 5.12.5 5.12.6 5.12.7 5.12.8 5.12.9 5.13.0 5.13.1 5.13.2 5.14.0 5.14.1 5.14.2 5.14.3 5.15.0 5.15.1 5.16.0 5.16.1 5.16.2 5.16.3 5.16.4 5.17.0 5.17.1 5.17.2 5.17.3 5.17.4 5.17.5 5.17.6 5.18.0 5.19.0 5.2.0 5.2.1 5.2.2 5.2.3 5.20.0 5.21.0 5.21.1 5.21.2 5.21.3 5.22.0 5.22.1 5.22.2 5.22.3 5.22.4 5.23.0 5.23.1 5.23.2 5.3.0 5.3.1 5.3.2 5.3.3 5.3.4 5.3.5 5.3.6 5.3.7 5.4.0 5.4.1 5.4.2 5.5.0 5.5.1 5.5.2 5.6.0 5.6.1 5.6.2 5.6.3 5.6.4 5.7.0 5.7.1 5.8.0 5.8.1 5.9.0 3.0.0-beta.15 3.7.1 3.0.0-beta.16 3.7.2 3.0.0-beta.17 3.7.3 3.0.0-beta.18 3.7.4 3.0.0-beta.19 3.7.5 3.0.0-beta.2 3.7.6 3.0.0-beta.20 3.7.8 3.0.0-beta.21 3.70.0 3.0.0-beta.22 3.71.0 3.0.0-beta.23 3.71.1 3.0.0-beta.23.1 3.71.2 3.0.0-beta.23.2 3.71.3 3.0.0-beta.24 3.72.0 3.0.0-beta.25 3.73.0 3.0.0-beta.26 3.73.1 3.0.0-beta.27 3.73.2 3.0.0-beta.28 3.74.0 3.0.0-beta.29 3.74.1 3.0.0-beta.3 3.74.2 3.0.0-beta.30 3.74.3 3.0.0-beta.31 3.75.0 3.0.0-beta.32 3.75.1 3.0.0-beta.33 3.76.0 3.0.0-beta.33.1 3.77.0 3.0.0-beta.34.0.0 3.77.1 3.0.0-beta.36.0.0 3.78.0 3.0.0-beta.36.0.1 3.79.0 3.0.0-beta.36.2.0 3.8 3.0.0-beta.36.3.0 3.8.1 3.0.0-beta.36.3.1 3.8.2 3.0.0-beta.37.0.0 3.8.3 3.0.0-beta.4 3.8.4 3.0.0-beta.5 3.8.5 3.0.0-beta.6 3.8.6 3.0.0-beta.7 3.80.0 3.0.0-beta.7.1 3.81.0 3.0.0-beta.8 3.82.0 3.0.0-beta.9 3.83.0 3.0.0-rc.1.0.0 3.84.0 3.0.0-rc.1.0.1 3.84.1 3.0.0-rc.1.0.2 3.85.0 3.0.0-rc.1.0.3 3.85.1 3.0.0-rc.1.0.4 3.86.0 3.0.0-rc.2.0.0 3.87.0 3.0.0-rc.2.0.1 3.87.1 3.0.0-rc.2.0.2 3.87.2 3.0.0-rc.2.0.3 3.88.0 3.0.1 3.88.1 3.0.2 3.88.2 3.0.3 3.89.0 3.0.4 3.89.1 3.0.5 3.89.2 3.0.6 3.89.3 3.0.7 3.89.4 3.0.8 3.9.0 3.0.9 3.9.1 3.1.0 3.90.0 3.10 3.90.1 3.10.1 3.90.2 3.100.0 3.91.0 3.100.1 3.91.1 3.100.2 3.92.0 3.101.0 3.92.1 3.101.1 3.93.0 3.102.0 3.93.1 3.102.1 3.94.0 3.103.0 3.95.0 3.103.1 3.95.1 3.11.0 3.96.0 3.11.1 3.96.1 3.11.2 3.97.0 3.11.3 3.98.0 3.11.4 3.98.1 3.11.5 3.99.0 3.12.0 3.99.1 3.12.1 4.0.0 3.13.0 4.0.1 3.14.0 4.1.0 3.14.1 4.1.1 3.15.0 4.10.0 3.16.0 4.11.0 3.16.1 4.11.1 3.16.2 4.12.0 3.16.3 4.12.1 3.17.0 4.12.2 3.17.1 4.13.0 3.17.2 4.14.0 3.18.0 4.15.0 3.18.1 4.16.0 3.18.2 4.17.0 3.19.0 4.17.1 3.19.1 4.18.0 3.19.2 4.18.1 3.19.3 4.19.0 3.2.0 4.2.0 3.2.1 4.20.0 3.2.2 4.20.1 3.2.3 4.20.2 3.2.4 4.21.0 3.2.5 4.22.0 3.20.0 4.22.1 3.21.0 4.22.2 3.21.1 4.23.0 3.22.0 4.24.0 3.23.0 4.25.0 3.23.1 4.26.0 3.23.2 4.26.1 3.24.0 4.27.0 3.25.0 4.28.0 3.25.1 4.29.0 3.26.0 4.3.0 3.26.1 4.3.1 3.27.0 4.30.0 3.28.0 4.31.0 3.29.0 4.31.1 3.3.0 4.32.0 3.3.1 4.33.0 3.3.2 4.34.0 3.3.3 4.35.0 3.3.4 4.35.1 3.3.5 4.36.0 3.3.6 4.37.0 3.30.0 4.38.0 3.31.0 4.39.0 3.31.1 4.4.0 3.32.0 4.40.0 3.32.1 4.41.0 3.32.2 4.41.1 3.33.0 4.41.2 3.34.0 4.41.3 3.34.1 4.42.0 3.34.2 4.42.1 3.34.3 3.34.4 3.35.0 3.35.1 3.35.3 3.35.4 3.36.0 3.37.0 3.37.1 3.37.2 3.37.3 3.38.0 3.38.1 3.39.0 3.39.1 3.39.2 3.4.0 3.4.1 3.4.2 3.4.3 3.4.4 3.40.0 3.40.1 3.41.0 3.41.1 3.41.2 3.42.0 3.42.1 3.42.2 3.42.3 3.43.0 3.43.1 3.44.0 3.45.0 3.45.1 3.46.0 3.46.1 3.46.10 3.46.11 3.46.12 3.46.13 3.46.14 3.46.2 3.46.3 3.46.4 3.46.5 3.46.6 3.46.7 3.46.8 3.46.9 3.47.0 3.47.1 3.47.10 3.47.11 3.47.2 3.47.3 3.47.5 3.47.6 3.47.7 3.47.9 3.48.0 3.48.1 3.49.0 3.49.1 3.5.0 3.5.1 3.50.0 3.51.0 3.51.1 3.51.2 3.52.0 3.53.0 3.54.0 3.54.1 3.54.2 3.54.3 3.55.0 3.55.1 3.56.0 3.56.1 3.56.2 3.57.0 3.57.1 3.58.0 3.59.0 3.59.1 3.59.2 3.6.0 3.6.1 3.6.2 3.6.3 3.6.4 3.6.5 3.6.6 3.6.7 3.60.0 3.60.1 3.60.10 3.60.11 3.60.12 3.60.2 3.60.3 3.60.4 3.60.6 3.60.7 3.60.8 3.60.9 3.61.0 3.62.0 3.62.1 3.63.0 3.64.0 3.64.1 3.64.2 3.64.3 3.65.0 trunk 3.65.1 3.0.0 3.66.0 3.0.0-beta.1 3.67.0 3.0.0-beta.10 3.67.1 3.0.0-beta.11 3.68.0 3.0.0-beta.12 3.69.0 3.0.0-beta.13 3.69.1 3.0.0-beta.14 3.7.0
mailpoet / vendor-prefixed / sabberworm / php-css-parser / src / CSSList / CSSList.php
mailpoet / vendor-prefixed / sabberworm / php-css-parser / src / CSSList Last commit date
AtRuleBlockList.php 2 years ago CSSBlockList.php 4 years ago CSSList.php 2 years ago Document.php 8 months ago KeyFrame.php 2 years ago index.php 3 years ago
CSSList.php
302 lines
1 <?php
2 namespace MailPoetVendor\Sabberworm\CSS\CSSList;
3 if (!defined('ABSPATH')) exit;
4 use MailPoetVendor\Sabberworm\CSS\Comment\Comment;
5 use MailPoetVendor\Sabberworm\CSS\Comment\Commentable;
6 use MailPoetVendor\Sabberworm\CSS\OutputFormat;
7 use MailPoetVendor\Sabberworm\CSS\Parsing\ParserState;
8 use MailPoetVendor\Sabberworm\CSS\Parsing\SourceException;
9 use MailPoetVendor\Sabberworm\CSS\Parsing\UnexpectedEOFException;
10 use MailPoetVendor\Sabberworm\CSS\Parsing\UnexpectedTokenException;
11 use MailPoetVendor\Sabberworm\CSS\Property\AtRule;
12 use MailPoetVendor\Sabberworm\CSS\Property\Charset;
13 use MailPoetVendor\Sabberworm\CSS\Property\CSSNamespace;
14 use MailPoetVendor\Sabberworm\CSS\Property\Import;
15 use MailPoetVendor\Sabberworm\CSS\Property\Selector;
16 use MailPoetVendor\Sabberworm\CSS\Renderable;
17 use MailPoetVendor\Sabberworm\CSS\RuleSet\AtRuleSet;
18 use MailPoetVendor\Sabberworm\CSS\RuleSet\DeclarationBlock;
19 use MailPoetVendor\Sabberworm\CSS\RuleSet\RuleSet;
20 use MailPoetVendor\Sabberworm\CSS\Settings;
21 use MailPoetVendor\Sabberworm\CSS\Value\CSSString;
22 use MailPoetVendor\Sabberworm\CSS\Value\URL;
23 use MailPoetVendor\Sabberworm\CSS\Value\Value;
24 abstract class CSSList implements Renderable, Commentable
25 {
26 protected $aComments;
27 protected $aContents;
28 protected $iLineNo;
29 public function __construct($iLineNo = 0)
30 {
31 $this->aComments = [];
32 $this->aContents = [];
33 $this->iLineNo = $iLineNo;
34 }
35 public static function parseList(ParserState $oParserState, CSSList $oList)
36 {
37 $bIsRoot = $oList instanceof Document;
38 if (\is_string($oParserState)) {
39 $oParserState = new ParserState($oParserState, Settings::create());
40 }
41 $bLenientParsing = $oParserState->getSettings()->bLenientParsing;
42 $aComments = [];
43 while (!$oParserState->isEnd()) {
44 $aComments = \array_merge($aComments, $oParserState->consumeWhiteSpace());
45 $oListItem = null;
46 if ($bLenientParsing) {
47 try {
48 $oListItem = self::parseListItem($oParserState, $oList);
49 } catch (UnexpectedTokenException $e) {
50 $oListItem = \false;
51 }
52 } else {
53 $oListItem = self::parseListItem($oParserState, $oList);
54 }
55 if ($oListItem === null) {
56 // List parsing finished
57 return;
58 }
59 if ($oListItem) {
60 $oListItem->addComments($aComments);
61 $oList->append($oListItem);
62 }
63 $aComments = $oParserState->consumeWhiteSpace();
64 }
65 $oList->addComments($aComments);
66 if (!$bIsRoot && !$bLenientParsing) {
67 throw new SourceException("Unexpected end of document", $oParserState->currentLine());
68 }
69 }
70 private static function parseListItem(ParserState $oParserState, CSSList $oList)
71 {
72 $bIsRoot = $oList instanceof Document;
73 if ($oParserState->comes('@')) {
74 $oAtRule = self::parseAtRule($oParserState);
75 if ($oAtRule instanceof Charset) {
76 if (!$bIsRoot) {
77 throw new UnexpectedTokenException('@charset may only occur in root document', '', 'custom', $oParserState->currentLine());
78 }
79 if (\count($oList->getContents()) > 0) {
80 throw new UnexpectedTokenException('@charset must be the first parseable token in a document', '', 'custom', $oParserState->currentLine());
81 }
82 $oParserState->setCharset($oAtRule->getCharset());
83 }
84 return $oAtRule;
85 } elseif ($oParserState->comes('}')) {
86 if ($bIsRoot) {
87 if ($oParserState->getSettings()->bLenientParsing) {
88 return DeclarationBlock::parse($oParserState);
89 } else {
90 throw new SourceException("Unopened {", $oParserState->currentLine());
91 }
92 } else {
93 // End of list
94 return null;
95 }
96 } else {
97 return DeclarationBlock::parse($oParserState, $oList);
98 }
99 }
100 private static function parseAtRule(ParserState $oParserState)
101 {
102 $oParserState->consume('@');
103 $sIdentifier = $oParserState->parseIdentifier();
104 $iIdentifierLineNum = $oParserState->currentLine();
105 $oParserState->consumeWhiteSpace();
106 if ($sIdentifier === 'import') {
107 $oLocation = URL::parse($oParserState);
108 $oParserState->consumeWhiteSpace();
109 $sMediaQuery = null;
110 if (!$oParserState->comes(';')) {
111 $sMediaQuery = \trim($oParserState->consumeUntil([';', ParserState::EOF]));
112 }
113 $oParserState->consumeUntil([';', ParserState::EOF], \true, \true);
114 return new Import($oLocation, $sMediaQuery ?: null, $iIdentifierLineNum);
115 } elseif ($sIdentifier === 'charset') {
116 $oCharsetString = CSSString::parse($oParserState);
117 $oParserState->consumeWhiteSpace();
118 $oParserState->consumeUntil([';', ParserState::EOF], \true, \true);
119 return new Charset($oCharsetString, $iIdentifierLineNum);
120 } elseif (self::identifierIs($sIdentifier, 'keyframes')) {
121 $oResult = new KeyFrame($iIdentifierLineNum);
122 $oResult->setVendorKeyFrame($sIdentifier);
123 $oResult->setAnimationName(\trim($oParserState->consumeUntil('{', \false, \true)));
124 CSSList::parseList($oParserState, $oResult);
125 if ($oParserState->comes('}')) {
126 $oParserState->consume('}');
127 }
128 return $oResult;
129 } elseif ($sIdentifier === 'namespace') {
130 $sPrefix = null;
131 $mUrl = Value::parsePrimitiveValue($oParserState);
132 if (!$oParserState->comes(';')) {
133 $sPrefix = $mUrl;
134 $mUrl = Value::parsePrimitiveValue($oParserState);
135 }
136 $oParserState->consumeUntil([';', ParserState::EOF], \true, \true);
137 if ($sPrefix !== null && !\is_string($sPrefix)) {
138 throw new UnexpectedTokenException('Wrong namespace prefix', $sPrefix, 'custom', $iIdentifierLineNum);
139 }
140 if (!($mUrl instanceof CSSString || $mUrl instanceof URL)) {
141 throw new UnexpectedTokenException('Wrong namespace url of invalid type', $mUrl, 'custom', $iIdentifierLineNum);
142 }
143 return new CSSNamespace($mUrl, $sPrefix, $iIdentifierLineNum);
144 } else {
145 // Unknown other at rule (font-face or such)
146 $sArgs = \trim($oParserState->consumeUntil('{', \false, \true));
147 if (\substr_count($sArgs, "(") != \substr_count($sArgs, ")")) {
148 if ($oParserState->getSettings()->bLenientParsing) {
149 return null;
150 } else {
151 throw new SourceException("Unmatched brace count in media query", $oParserState->currentLine());
152 }
153 }
154 $bUseRuleSet = \true;
155 foreach (\explode('/', AtRule::BLOCK_RULES) as $sBlockRuleName) {
156 if (self::identifierIs($sIdentifier, $sBlockRuleName)) {
157 $bUseRuleSet = \false;
158 break;
159 }
160 }
161 if ($bUseRuleSet) {
162 $oAtRule = new AtRuleSet($sIdentifier, $sArgs, $iIdentifierLineNum);
163 RuleSet::parseRuleSet($oParserState, $oAtRule);
164 } else {
165 $oAtRule = new AtRuleBlockList($sIdentifier, $sArgs, $iIdentifierLineNum);
166 CSSList::parseList($oParserState, $oAtRule);
167 if ($oParserState->comes('}')) {
168 $oParserState->consume('}');
169 }
170 }
171 return $oAtRule;
172 }
173 }
174 private static function identifierIs($sIdentifier, $sMatch)
175 {
176 return \strcasecmp($sIdentifier, $sMatch) === 0 ?: \preg_match("/^(-\\w+-)?{$sMatch}\$/i", $sIdentifier) === 1;
177 }
178 public function getLineNo()
179 {
180 return $this->iLineNo;
181 }
182 public function prepend($oItem)
183 {
184 \array_unshift($this->aContents, $oItem);
185 }
186 public function append($oItem)
187 {
188 $this->aContents[] = $oItem;
189 }
190 public function splice($iOffset, $iLength = null, $mReplacement = null)
191 {
192 \array_splice($this->aContents, $iOffset, $iLength, $mReplacement);
193 }
194 public function remove($oItemToRemove)
195 {
196 $iKey = \array_search($oItemToRemove, $this->aContents, \true);
197 if ($iKey !== \false) {
198 unset($this->aContents[$iKey]);
199 return \true;
200 }
201 return \false;
202 }
203 public function replace($oOldItem, $mNewItem)
204 {
205 $iKey = \array_search($oOldItem, $this->aContents, \true);
206 if ($iKey !== \false) {
207 if (\is_array($mNewItem)) {
208 \array_splice($this->aContents, $iKey, 1, $mNewItem);
209 } else {
210 \array_splice($this->aContents, $iKey, 1, [$mNewItem]);
211 }
212 return \true;
213 }
214 return \false;
215 }
216 public function setContents(array $aContents)
217 {
218 $this->aContents = [];
219 foreach ($aContents as $content) {
220 $this->append($content);
221 }
222 }
223 public function removeDeclarationBlockBySelector($mSelector, $bRemoveAll = \false)
224 {
225 if ($mSelector instanceof DeclarationBlock) {
226 $mSelector = $mSelector->getSelectors();
227 }
228 if (!\is_array($mSelector)) {
229 $mSelector = \explode(',', $mSelector);
230 }
231 foreach ($mSelector as $iKey => &$mSel) {
232 if (!$mSel instanceof Selector) {
233 if (!Selector::isValid($mSel)) {
234 throw new UnexpectedTokenException("Selector did not match '" . Selector::SELECTOR_VALIDATION_RX . "'.", $mSel, "custom");
235 }
236 $mSel = new Selector($mSel);
237 }
238 }
239 foreach ($this->aContents as $iKey => $mItem) {
240 if (!$mItem instanceof DeclarationBlock) {
241 continue;
242 }
243 if ($mItem->getSelectors() == $mSelector) {
244 unset($this->aContents[$iKey]);
245 if (!$bRemoveAll) {
246 return;
247 }
248 }
249 }
250 }
251 public function __toString()
252 {
253 return $this->render(new OutputFormat());
254 }
255 protected function renderListContents(OutputFormat $oOutputFormat)
256 {
257 $sResult = '';
258 $bIsFirst = \true;
259 $oNextLevel = $oOutputFormat;
260 if (!$this->isRootList()) {
261 $oNextLevel = $oOutputFormat->nextLevel();
262 }
263 foreach ($this->aContents as $oContent) {
264 $sRendered = $oOutputFormat->safely(function () use($oNextLevel, $oContent) {
265 return $oContent->render($oNextLevel);
266 });
267 if ($sRendered === null) {
268 continue;
269 }
270 if ($bIsFirst) {
271 $bIsFirst = \false;
272 $sResult .= $oNextLevel->spaceBeforeBlocks();
273 } else {
274 $sResult .= $oNextLevel->spaceBetweenBlocks();
275 }
276 $sResult .= $sRendered;
277 }
278 if (!$bIsFirst) {
279 // Had some output
280 $sResult .= $oOutputFormat->spaceAfterBlocks();
281 }
282 return $sResult;
283 }
284 public abstract function isRootList();
285 public function getContents()
286 {
287 return $this->aContents;
288 }
289 public function addComments(array $aComments)
290 {
291 $this->aComments = \array_merge($this->aComments, $aComments);
292 }
293 public function getComments()
294 {
295 return $this->aComments;
296 }
297 public function setComments(array $aComments)
298 {
299 $this->aComments = $aComments;
300 }
301 }
302