Best Atoum code snippet using value.seek
Parser.php
Source:Parser.php
...231 * grammatical rules, you can chain them together using &&.232 *233 * But, if some of the rules in the chain succeed before one fails, then234 * the buffer position will be left at an invalid state. In order to235 * avoid this, Compiler::seek() is used to remember and set buffer positions.236 *237 * Before parsing a chain, use $s = $this->seek() to remember the current238 * position into $s. Then if a chain fails, use $this->seek($s) to239 * go back where we started.240 *241 * @return boolean242 */243 protected function parseChunk()244 {245 $s = $this->seek();246 // the directives247 if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] === '@') {248 if ($this->literal('@at-root') &&249 ($this->selectors($selector) || true) &&250 ($this->map($with) || true) &&251 $this->literal('{')252 ) {253 $atRoot = $this->pushSpecialBlock(Type::T_AT_ROOT, $s);254 $atRoot->selector = $selector;255 $atRoot->with = $with;256 return true;257 }258 $this->seek($s);259 if ($this->literal('@media') && $this->mediaQueryList($mediaQueryList) && $this->literal('{')) {260 $media = $this->pushSpecialBlock(Type::T_MEDIA, $s);261 $media->queryList = $mediaQueryList[2];262 return true;263 }264 $this->seek($s);265 if ($this->literal('@mixin') &&266 $this->keyword($mixinName) &&267 ($this->argumentDef($args) || true) &&268 $this->literal('{')269 ) {270 $mixin = $this->pushSpecialBlock(Type::T_MIXIN, $s);271 $mixin->name = $mixinName;272 $mixin->args = $args;273 return true;274 }275 $this->seek($s);276 if ($this->literal('@include') &&277 $this->keyword($mixinName) &&278 ($this->literal('(') &&279 ($this->argValues($argValues) || true) &&280 $this->literal(')') || true) &&281 ($this->end() ||282 $this->literal('{') && $hasBlock = true)283 ) {284 $child = [Type::T_INCLUDE, $mixinName, isset($argValues) ? $argValues : null, null];285 if (! empty($hasBlock)) {286 $include = $this->pushSpecialBlock(Type::T_INCLUDE, $s);287 $include->child = $child;288 } else {289 $this->append($child, $s);290 }291 return true;292 }293 $this->seek($s);294 if ($this->literal('@scssphp-import-once') &&295 $this->valueList($importPath) &&296 $this->end()297 ) {298 $this->append([Type::T_SCSSPHP_IMPORT_ONCE, $importPath], $s);299 return true;300 }301 $this->seek($s);302 if ($this->literal('@import') &&303 $this->valueList($importPath) &&304 $this->end()305 ) {306 $this->append([Type::T_IMPORT, $importPath], $s);307 return true;308 }309 $this->seek($s);310 if ($this->literal('@import') &&311 $this->url($importPath) &&312 $this->end()313 ) {314 $this->append([Type::T_IMPORT, $importPath], $s);315 return true;316 }317 $this->seek($s);318 if ($this->literal('@extend') &&319 $this->selectors($selectors) &&320 $this->end()321 ) {322 // check for '!flag'323 $optional = $this->stripOptionalFlag($selectors);324 $this->append([Type::T_EXTEND, $selectors, $optional], $s);325 return true;326 }327 $this->seek($s);328 if ($this->literal('@function') &&329 $this->keyword($fnName) &&330 $this->argumentDef($args) &&331 $this->literal('{')332 ) {333 $func = $this->pushSpecialBlock(Type::T_FUNCTION, $s);334 $func->name = $fnName;335 $func->args = $args;336 return true;337 }338 $this->seek($s);339 if ($this->literal('@break') && $this->end()) {340 $this->append([Type::T_BREAK], $s);341 return true;342 }343 $this->seek($s);344 if ($this->literal('@continue') && $this->end()) {345 $this->append([Type::T_CONTINUE], $s);346 return true;347 }348 $this->seek($s);349 if ($this->literal('@return') && ($this->valueList($retVal) || true) && $this->end()) {350 $this->append([Type::T_RETURN, isset($retVal) ? $retVal : [Type::T_NULL]], $s);351 return true;352 }353 $this->seek($s);354 if ($this->literal('@each') &&355 $this->genericList($varNames, 'variable', ',', false) &&356 $this->literal('in') &&357 $this->valueList($list) &&358 $this->literal('{')359 ) {360 $each = $this->pushSpecialBlock(Type::T_EACH, $s);361 foreach ($varNames[2] as $varName) {362 $each->vars[] = $varName[1];363 }364 $each->list = $list;365 return true;366 }367 $this->seek($s);368 if ($this->literal('@while') &&369 $this->expression($cond) &&370 $this->literal('{')371 ) {372 $while = $this->pushSpecialBlock(Type::T_WHILE, $s);373 $while->cond = $cond;374 return true;375 }376 $this->seek($s);377 if ($this->literal('@for') &&378 $this->variable($varName) &&379 $this->literal('from') &&380 $this->expression($start) &&381 ($this->literal('through') ||382 ($forUntil = true && $this->literal('to'))) &&383 $this->expression($end) &&384 $this->literal('{')385 ) {386 $for = $this->pushSpecialBlock(Type::T_FOR, $s);387 $for->var = $varName[1];388 $for->start = $start;389 $for->end = $end;390 $for->until = isset($forUntil);391 return true;392 }393 $this->seek($s);394 if ($this->literal('@if') && $this->valueList($cond) && $this->literal('{')) {395 $if = $this->pushSpecialBlock(Type::T_IF, $s);396 $if->cond = $cond;397 $if->cases = [];398 return true;399 }400 $this->seek($s);401 if ($this->literal('@debug') &&402 $this->valueList($value) &&403 $this->end()404 ) {405 $this->append([Type::T_DEBUG, $value], $s);406 return true;407 }408 $this->seek($s);409 if ($this->literal('@warn') &&410 $this->valueList($value) &&411 $this->end()412 ) {413 $this->append([Type::T_WARN, $value], $s);414 return true;415 }416 $this->seek($s);417 if ($this->literal('@error') &&418 $this->valueList($value) &&419 $this->end()420 ) {421 $this->append([Type::T_ERROR, $value], $s);422 return true;423 }424 $this->seek($s);425 if ($this->literal('@content') && $this->end()) {426 $this->append([Type::T_MIXIN_CONTENT], $s);427 return true;428 }429 $this->seek($s);430 $last = $this->last();431 if (isset($last) && $last[0] === Type::T_IF) {432 list(, $if) = $last;433 if ($this->literal('@else')) {434 if ($this->literal('{')) {435 $else = $this->pushSpecialBlock(Type::T_ELSE, $s);436 } elseif ($this->literal('if') && $this->valueList($cond) && $this->literal('{')) {437 $else = $this->pushSpecialBlock(Type::T_ELSEIF, $s);438 $else->cond = $cond;439 }440 if (isset($else)) {441 $else->dontAppend = true;442 $if->cases[] = $else;443 return true;444 }445 }446 $this->seek($s);447 }448 // only retain the first @charset directive encountered449 if ($this->literal('@charset') &&450 $this->valueList($charset) &&451 $this->end()452 ) {453 if (! isset($this->charset)) {454 $statement = [Type::T_CHARSET, $charset];455 list($line, $column) = $this->getSourcePosition($s);456 $statement[static::SOURCE_LINE] = $line;457 $statement[static::SOURCE_COLUMN] = $column;458 $statement[static::SOURCE_INDEX] = $this->sourceIndex;459 $this->charset = $statement;460 }461 return true;462 }463 $this->seek($s);464 // doesn't match built in directive, do generic one465 if ($this->literal('@', false) &&466 $this->keyword($dirName) &&467 ($this->variable($dirValue) || $this->openString('{', $dirValue) || true) &&468 $this->literal('{')469 ) {470 if ($dirName === 'media') {471 $directive = $this->pushSpecialBlock(Type::T_MEDIA, $s);472 } else {473 $directive = $this->pushSpecialBlock(Type::T_DIRECTIVE, $s);474 $directive->name = $dirName;475 }476 if (isset($dirValue)) {477 $directive->value = $dirValue;478 }479 return true;480 }481 $this->seek($s);482 return false;483 }484 // property shortcut485 // captures most properties before having to parse a selector486 if ($this->keyword($name, false) &&487 $this->literal(': ') &&488 $this->valueList($value) &&489 $this->end()490 ) {491 $name = [Type::T_STRING, '', [$name]];492 $this->append([Type::T_ASSIGN, $name, $value], $s);493 return true;494 }495 $this->seek($s);496 // variable assigns497 if ($this->variable($name) &&498 $this->literal(':') &&499 $this->valueList($value) &&500 $this->end()501 ) {502 // check for '!flag'503 $assignmentFlags = $this->stripAssignmentFlags($value);504 $this->append([Type::T_ASSIGN, $name, $value, $assignmentFlags], $s);505 return true;506 }507 $this->seek($s);508 // misc509 if ($this->literal('-->')) {510 return true;511 }512 // opening css block513 if ($this->selectors($selectors) && $this->literal('{')) {514 $this->pushBlock($selectors, $s);515 return true;516 }517 $this->seek($s);518 // property assign, or nested assign519 if ($this->propertyName($name) && $this->literal(':')) {520 $foundSomething = false;521 if ($this->valueList($value)) {522 $this->append([Type::T_ASSIGN, $name, $value], $s);523 $foundSomething = true;524 }525 if ($this->literal('{')) {526 $propBlock = $this->pushSpecialBlock(Type::T_NESTED_PROPERTY, $s);527 $propBlock->prefix = $name;528 $foundSomething = true;529 } elseif ($foundSomething) {530 $foundSomething = $this->end();531 }532 if ($foundSomething) {533 return true;534 }535 }536 $this->seek($s);537 // closing a block538 if ($this->literal('}')) {539 $block = $this->popBlock();540 if (isset($block->type) && $block->type === Type::T_INCLUDE) {541 $include = $block->child;542 unset($block->child);543 $include[3] = $block;544 $this->append($include, $s);545 } elseif (empty($block->dontAppend)) {546 $type = isset($block->type) ? $block->type : Type::T_BLOCK;547 $this->append([$type, $block], $s);548 }549 return true;550 }551 // extra stuff552 if ($this->literal(';') ||553 $this->literal('<!--')554 ) {555 return true;556 }557 return false;558 }559 /**560 * Push block onto parse tree561 *562 * @param array $selectors563 * @param integer $pos564 *565 * @return \Leafo\ScssPhp\Block566 */567 protected function pushBlock($selectors, $pos = 0)568 {569 list($line, $column) = $this->getSourcePosition($pos);570 $b = new Block;571 $b->sourceName = $this->sourceName;572 $b->sourceLine = $line;573 $b->sourceColumn = $column;574 $b->sourceIndex = $this->sourceIndex;575 $b->selectors = $selectors;576 $b->comments = [];577 $b->parent = $this->env;578 if (! $this->env) {579 $b->children = [];580 } elseif (empty($this->env->children)) {581 $this->env->children = $this->env->comments;582 $b->children = [];583 $this->env->comments = [];584 } else {585 $b->children = $this->env->comments;586 $this->env->comments = [];587 }588 $this->env = $b;589 return $b;590 }591 /**592 * Push special (named) block onto parse tree593 *594 * @param string $type595 * @param integer $pos596 *597 * @return \Leafo\ScssPhp\Block598 */599 protected function pushSpecialBlock($type, $pos)600 {601 $block = $this->pushBlock(null, $pos);602 $block->type = $type;603 return $block;604 }605 /**606 * Pop scope and return last block607 *608 * @return \Leafo\ScssPhp\Block609 *610 * @throws \Exception611 */612 protected function popBlock()613 {614 $block = $this->env;615 if (empty($block->parent)) {616 $this->throwParseError('unexpected }');617 }618 $this->env = $block->parent;619 unset($block->parent);620 $comments = $block->comments;621 if (count($comments)) {622 $this->env->comments = $comments;623 unset($block->comments);624 }625 return $block;626 }627 /**628 * Peek input stream629 *630 * @param string $regex631 * @param array $out632 * @param integer $from633 *634 * @return integer635 */636 protected function peek($regex, &$out, $from = null)637 {638 if (! isset($from)) {639 $from = $this->count;640 }641 $r = '/' . $regex . '/' . $this->patternModifiers;642 $result = preg_match($r, $this->buffer, $out, null, $from);643 return $result;644 }645 /**646 * Seek to position in input stream (or return current position in input stream)647 *648 * @param integer $where649 *650 * @return integer651 */652 protected function seek($where = null)653 {654 if ($where === null) {655 return $this->count;656 }657 $this->count = $where;658 return true;659 }660 /**661 * Match string looking for either ending delim, escape, or string interpolation662 *663 * {@internal This is a workaround for preg_match's 250K string match limit. }}664 *665 * @param array $m Matches (passed by reference)666 * @param string $delim Delimeter667 *668 * @return boolean True if match; false otherwise669 */670 protected function matchString(&$m, $delim)671 {672 $token = null;673 $end = strlen($this->buffer);674 // look for either ending delim, escape, or string interpolation675 foreach (['#{', '\\', $delim] as $lookahead) {676 $pos = strpos($this->buffer, $lookahead, $this->count);677 if ($pos !== false && $pos < $end) {678 $end = $pos;679 $token = $lookahead;680 }681 }682 if (! isset($token)) {683 return false;684 }685 $match = substr($this->buffer, $this->count, $end - $this->count);686 $m = [687 $match . $token,688 $match,689 $token690 ];691 $this->count = $end + strlen($token);692 return true;693 }694 /**695 * Try to match something on head of buffer696 *697 * @param string $regex698 * @param array $out699 * @param boolean $eatWhitespace700 *701 * @return boolean702 */703 protected function match($regex, &$out, $eatWhitespace = null)704 {705 if (! isset($eatWhitespace)) {706 $eatWhitespace = $this->eatWhiteDefault;707 }708 $r = '/' . $regex . '/' . $this->patternModifiers;709 if (preg_match($r, $this->buffer, $out, null, $this->count)) {710 $this->count += strlen($out[0]);711 if ($eatWhitespace) {712 $this->whitespace();713 }714 return true;715 }716 return false;717 }718 /**719 * Match literal string720 *721 * @param string $what722 * @param boolean $eatWhitespace723 *724 * @return boolean725 */726 protected function literal($what, $eatWhitespace = null)727 {728 if (! isset($eatWhitespace)) {729 $eatWhitespace = $this->eatWhiteDefault;730 }731 $len = strlen($what);732 if (strcasecmp(substr($this->buffer, $this->count, $len), $what) === 0) {733 $this->count += $len;734 if ($eatWhitespace) {735 $this->whitespace();736 }737 return true;738 }739 return false;740 }741 /**742 * Match some whitespace743 *744 * @return boolean745 */746 protected function whitespace()747 {748 $gotWhite = false;749 while (preg_match(static::$whitePattern, $this->buffer, $m, null, $this->count)) {750 if (isset($m[1]) && empty($this->commentsSeen[$this->count])) {751 $this->appendComment([Type::T_COMMENT, $m[1]]);752 $this->commentsSeen[$this->count] = true;753 }754 $this->count += strlen($m[0]);755 $gotWhite = true;756 }757 return $gotWhite;758 }759 /**760 * Append comment to current block761 *762 * @param array $comment763 */764 protected function appendComment($comment)765 {766 $comment[1] = substr(preg_replace(['/^\s+/m', '/^(.)/m'], ['', ' \1'], $comment[1]), 1);767 $this->env->comments[] = $comment;768 }769 /**770 * Append statement to current block771 *772 * @param array $statement773 * @param integer $pos774 */775 protected function append($statement, $pos = null)776 {777 if ($pos !== null) {778 list($line, $column) = $this->getSourcePosition($pos);779 $statement[static::SOURCE_LINE] = $line;780 $statement[static::SOURCE_COLUMN] = $column;781 $statement[static::SOURCE_INDEX] = $this->sourceIndex;782 }783 $this->env->children[] = $statement;784 $comments = $this->env->comments;785 if (count($comments)) {786 $this->env->children = array_merge($this->env->children, $comments);787 $this->env->comments = [];788 }789 }790 /**791 * Returns last child was appended792 *793 * @return array|null794 */795 protected function last()796 {797 $i = count($this->env->children) - 1;798 if (isset($this->env->children[$i])) {799 return $this->env->children[$i];800 }801 }802 /**803 * Parse media query list804 *805 * @param array $out806 *807 * @return boolean808 */809 protected function mediaQueryList(&$out)810 {811 return $this->genericList($out, 'mediaQuery', ',', false);812 }813 /**814 * Parse media query815 *816 * @param array $out817 *818 * @return boolean819 */820 protected function mediaQuery(&$out)821 {822 $expressions = null;823 $parts = [];824 if (($this->literal('only') && ($only = true) || $this->literal('not') && ($not = true) || true) &&825 $this->mixedKeyword($mediaType)826 ) {827 $prop = [Type::T_MEDIA_TYPE];828 if (isset($only)) {829 $prop[] = [Type::T_KEYWORD, 'only'];830 }831 if (isset($not)) {832 $prop[] = [Type::T_KEYWORD, 'not'];833 }834 $media = [Type::T_LIST, '', []];835 foreach ((array) $mediaType as $type) {836 if (is_array($type)) {837 $media[2][] = $type;838 } else {839 $media[2][] = [Type::T_KEYWORD, $type];840 }841 }842 $prop[] = $media;843 $parts[] = $prop;844 }845 if (empty($parts) || $this->literal('and')) {846 $this->genericList($expressions, 'mediaExpression', 'and', false);847 if (is_array($expressions)) {848 $parts = array_merge($parts, $expressions[2]);849 }850 }851 $out = $parts;852 return true;853 }854 /**855 * Parse media expression856 *857 * @param array $out858 *859 * @return boolean860 */861 protected function mediaExpression(&$out)862 {863 $s = $this->seek();864 $value = null;865 if ($this->literal('(') &&866 $this->expression($feature) &&867 ($this->literal(':') && $this->expression($value) || true) &&868 $this->literal(')')869 ) {870 $out = [Type::T_MEDIA_EXPRESSION, $feature];871 if ($value) {872 $out[] = $value;873 }874 return true;875 }876 $this->seek($s);877 return false;878 }879 /**880 * Parse argument values881 *882 * @param array $out883 *884 * @return boolean885 */886 protected function argValues(&$out)887 {888 if ($this->genericList($list, 'argValue', ',', false)) {889 $out = $list[2];890 return true;891 }892 return false;893 }894 /**895 * Parse argument value896 *897 * @param array $out898 *899 * @return boolean900 */901 protected function argValue(&$out)902 {903 $s = $this->seek();904 $keyword = null;905 if (! $this->variable($keyword) || ! $this->literal(':')) {906 $this->seek($s);907 $keyword = null;908 }909 if ($this->genericList($value, 'expression')) {910 $out = [$keyword, $value, false];911 $s = $this->seek();912 if ($this->literal('...')) {913 $out[2] = true;914 } else {915 $this->seek($s);916 }917 return true;918 }919 return false;920 }921 /**922 * Parse comma separated value list923 *924 * @param string $out925 *926 * @return boolean927 */928 protected function valueList(&$out)929 {930 return $this->genericList($out, 'spaceList', ',');931 }932 /**933 * Parse space separated value list934 *935 * @param array $out936 *937 * @return boolean938 */939 protected function spaceList(&$out)940 {941 return $this->genericList($out, 'expression');942 }943 /**944 * Parse generic list945 *946 * @param array $out947 * @param callable $parseItem948 * @param string $delim949 * @param boolean $flatten950 *951 * @return boolean952 */953 protected function genericList(&$out, $parseItem, $delim = '', $flatten = true)954 {955 $s = $this->seek();956 $items = [];957 while ($this->$parseItem($value)) {958 $items[] = $value;959 if ($delim) {960 if (! $this->literal($delim)) {961 break;962 }963 }964 }965 if (count($items) === 0) {966 $this->seek($s);967 return false;968 }969 if ($flatten && count($items) === 1) {970 $out = $items[0];971 } else {972 $out = [Type::T_LIST, $delim, $items];973 }974 return true;975 }976 /**977 * Parse expression978 *979 * @param array $out980 *981 * @return boolean982 */983 protected function expression(&$out)984 {985 $s = $this->seek();986 if ($this->literal('(')) {987 if ($this->literal(')')) {988 $out = [Type::T_LIST, '', []];989 return true;990 }991 if ($this->valueList($out) && $this->literal(')') && $out[0] === Type::T_LIST) {992 return true;993 }994 $this->seek($s);995 if ($this->map($out)) {996 return true;997 }998 $this->seek($s);999 }1000 if ($this->value($lhs)) {1001 $out = $this->expHelper($lhs, 0);1002 return true;1003 }1004 return false;1005 }1006 /**1007 * Parse left-hand side of subexpression1008 *1009 * @param array $lhs1010 * @param integer $minP1011 *1012 * @return array1013 */1014 protected function expHelper($lhs, $minP)1015 {1016 $operators = static::$operatorPattern;1017 $ss = $this->seek();1018 $whiteBefore = isset($this->buffer[$this->count - 1]) &&1019 ctype_space($this->buffer[$this->count - 1]);1020 while ($this->match($operators, $m, false) && static::$precedence[$m[1]] >= $minP) {1021 $whiteAfter = isset($this->buffer[$this->count]) &&1022 ctype_space($this->buffer[$this->count]);1023 $varAfter = isset($this->buffer[$this->count]) &&1024 $this->buffer[$this->count] === '$';1025 $this->whitespace();1026 $op = $m[1];1027 // don't turn negative numbers into expressions1028 if ($op === '-' && $whiteBefore && ! $whiteAfter && ! $varAfter) {1029 break;1030 }1031 if (! $this->value($rhs)) {1032 break;1033 }1034 // peek and see if rhs belongs to next operator1035 if ($this->peek($operators, $next) && static::$precedence[$next[1]] > static::$precedence[$op]) {1036 $rhs = $this->expHelper($rhs, static::$precedence[$next[1]]);1037 }1038 $lhs = [Type::T_EXPRESSION, $op, $lhs, $rhs, $this->inParens, $whiteBefore, $whiteAfter];1039 $ss = $this->seek();1040 $whiteBefore = isset($this->buffer[$this->count - 1]) &&1041 ctype_space($this->buffer[$this->count - 1]);1042 }1043 $this->seek($ss);1044 return $lhs;1045 }1046 /**1047 * Parse value1048 *1049 * @param array $out1050 *1051 * @return boolean1052 */1053 protected function value(&$out)1054 {1055 $s = $this->seek();1056 if ($this->literal('not', false) && $this->whitespace() && $this->value($inner)) {1057 $out = [Type::T_UNARY, 'not', $inner, $this->inParens];1058 return true;1059 }1060 $this->seek($s);1061 if ($this->literal('not', false) && $this->parenValue($inner)) {1062 $out = [Type::T_UNARY, 'not', $inner, $this->inParens];1063 return true;1064 }1065 $this->seek($s);1066 if ($this->literal('+') && $this->value($inner)) {1067 $out = [Type::T_UNARY, '+', $inner, $this->inParens];1068 return true;1069 }1070 $this->seek($s);1071 // negation1072 if ($this->literal('-', false) &&1073 ($this->variable($inner) ||1074 $this->unit($inner) ||1075 $this->parenValue($inner))1076 ) {1077 $out = [Type::T_UNARY, '-', $inner, $this->inParens];1078 return true;1079 }1080 $this->seek($s);1081 if ($this->parenValue($out) ||1082 $this->interpolation($out) ||1083 $this->variable($out) ||1084 $this->color($out) ||1085 $this->unit($out) ||1086 $this->string($out) ||1087 $this->func($out) ||1088 $this->progid($out)1089 ) {1090 return true;1091 }1092 if ($this->keyword($keyword)) {1093 if ($keyword === 'null') {1094 $out = [Type::T_NULL];1095 } else {1096 $out = [Type::T_KEYWORD, $keyword];1097 }1098 return true;1099 }1100 return false;1101 }1102 /**1103 * Parse parenthesized value1104 *1105 * @param array $out1106 *1107 * @return boolean1108 */1109 protected function parenValue(&$out)1110 {1111 $s = $this->seek();1112 $inParens = $this->inParens;1113 if ($this->literal('(')) {1114 if ($this->literal(')')) {1115 $out = [Type::T_LIST, '', []];1116 return true;1117 }1118 $this->inParens = true;1119 if ($this->expression($exp) && $this->literal(')')) {1120 $out = $exp;1121 $this->inParens = $inParens;1122 return true;1123 }1124 }1125 $this->inParens = $inParens;1126 $this->seek($s);1127 return false;1128 }1129 /**1130 * Parse "progid:"1131 *1132 * @param array $out1133 *1134 * @return boolean1135 */1136 protected function progid(&$out)1137 {1138 $s = $this->seek();1139 if ($this->literal('progid:', false) &&1140 $this->openString('(', $fn) &&1141 $this->literal('(')1142 ) {1143 $this->openString(')', $args, '(');1144 if ($this->literal(')')) {1145 $out = [Type::T_STRING, '', [1146 'progid:', $fn, '(', $args, ')'1147 ]];1148 return true;1149 }1150 }1151 $this->seek($s);1152 return false;1153 }1154 /**1155 * Parse function call1156 *1157 * @param array $out1158 *1159 * @return boolean1160 */1161 protected function func(&$func)1162 {1163 $s = $this->seek();1164 if ($this->keyword($name, false) &&1165 $this->literal('(')1166 ) {1167 if ($name === 'alpha' && $this->argumentList($args)) {1168 $func = [Type::T_FUNCTION, $name, [Type::T_STRING, '', $args]];1169 return true;1170 }1171 if ($name !== 'expression' && ! preg_match('/^(-[a-z]+-)?calc$/', $name)) {1172 $ss = $this->seek();1173 if ($this->argValues($args) && $this->literal(')')) {1174 $func = [Type::T_FUNCTION_CALL, $name, $args];1175 return true;1176 }1177 $this->seek($ss);1178 }1179 if (($this->openString(')', $str, '(') || true) &&1180 $this->literal(')')1181 ) {1182 $args = [];1183 if (! empty($str)) {1184 $args[] = [null, [Type::T_STRING, '', [$str]]];1185 }1186 $func = [Type::T_FUNCTION_CALL, $name, $args];1187 return true;1188 }1189 }1190 $this->seek($s);1191 return false;1192 }1193 /**1194 * Parse function call argument list1195 *1196 * @param array $out1197 *1198 * @return boolean1199 */1200 protected function argumentList(&$out)1201 {1202 $s = $this->seek();1203 $this->literal('(');1204 $args = [];1205 while ($this->keyword($var)) {1206 if ($this->literal('=') && $this->expression($exp)) {1207 $args[] = [Type::T_STRING, '', [$var . '=']];1208 $arg = $exp;1209 } else {1210 break;1211 }1212 $args[] = $arg;1213 if (! $this->literal(',')) {1214 break;1215 }1216 $args[] = [Type::T_STRING, '', [', ']];1217 }1218 if (! $this->literal(')') || ! count($args)) {1219 $this->seek($s);1220 return false;1221 }1222 $out = $args;1223 return true;1224 }1225 /**1226 * Parse mixin/function definition argument list1227 *1228 * @param array $out1229 *1230 * @return boolean1231 */1232 protected function argumentDef(&$out)1233 {1234 $s = $this->seek();1235 $this->literal('(');1236 $args = [];1237 while ($this->variable($var)) {1238 $arg = [$var[1], null, false];1239 $ss = $this->seek();1240 if ($this->literal(':') && $this->genericList($defaultVal, 'expression')) {1241 $arg[1] = $defaultVal;1242 } else {1243 $this->seek($ss);1244 }1245 $ss = $this->seek();1246 if ($this->literal('...')) {1247 $sss = $this->seek();1248 if (! $this->literal(')')) {1249 $this->throwParseError('... has to be after the final argument');1250 }1251 $arg[2] = true;1252 $this->seek($sss);1253 } else {1254 $this->seek($ss);1255 }1256 $args[] = $arg;1257 if (! $this->literal(',')) {1258 break;1259 }1260 }1261 if (! $this->literal(')')) {1262 $this->seek($s);1263 return false;1264 }1265 $out = $args;1266 return true;1267 }1268 /**1269 * Parse map1270 *1271 * @param array $out1272 *1273 * @return boolean1274 */1275 protected function map(&$out)1276 {1277 $s = $this->seek();1278 if (! $this->literal('(')) {1279 return false;1280 }1281 $keys = [];1282 $values = [];1283 while ($this->genericList($key, 'expression') && $this->literal(':') &&1284 $this->genericList($value, 'expression')1285 ) {1286 $keys[] = $key;1287 $values[] = $value;1288 if (! $this->literal(',')) {1289 break;1290 }1291 }1292 if (! count($keys) || ! $this->literal(')')) {1293 $this->seek($s);1294 return false;1295 }1296 $out = [Type::T_MAP, $keys, $values];1297 return true;1298 }1299 /**1300 * Parse color1301 *1302 * @param array $out1303 *1304 * @return boolean1305 */1306 protected function color(&$out)1307 {1308 $color = [Type::T_COLOR];1309 if ($this->match('(#([0-9a-f]{6})|#([0-9a-f]{3}))', $m)) {1310 if (isset($m[3])) {1311 $num = hexdec($m[3]);1312 foreach ([3, 2, 1] as $i) {1313 $t = $num & 0xf;1314 $color[$i] = $t << 4 | $t;1315 $num >>= 4;1316 }1317 } else {1318 $num = hexdec($m[2]);1319 foreach ([3, 2, 1] as $i) {1320 $color[$i] = $num & 0xff;1321 $num >>= 8;1322 }1323 }1324 $out = $color;1325 return true;1326 }1327 return false;1328 }1329 /**1330 * Parse number with unit1331 *1332 * @param array $out1333 *1334 * @return boolean1335 */1336 protected function unit(&$unit)1337 {1338 if ($this->match('([0-9]*(\.)?[0-9]+)([%a-zA-Z]+)?', $m)) {1339 $unit = new Node\Number($m[1], empty($m[3]) ? '' : $m[3]);1340 return true;1341 }1342 return false;1343 }1344 /**1345 * Parse string1346 *1347 * @param array $out1348 *1349 * @return boolean1350 */1351 protected function string(&$out)1352 {1353 $s = $this->seek();1354 if ($this->literal('"', false)) {1355 $delim = '"';1356 } elseif ($this->literal("'", false)) {1357 $delim = "'";1358 } else {1359 return false;1360 }1361 $content = [];1362 $oldWhite = $this->eatWhiteDefault;1363 $this->eatWhiteDefault = false;1364 $hasInterpolation = false;1365 while ($this->matchString($m, $delim)) {1366 if ($m[1] !== '') {1367 $content[] = $m[1];1368 }1369 if ($m[2] === '#{') {1370 $this->count -= strlen($m[2]);1371 if ($this->interpolation($inter, false)) {1372 $content[] = $inter;1373 $hasInterpolation = true;1374 } else {1375 $this->count += strlen($m[2]);1376 $content[] = '#{'; // ignore it1377 }1378 } elseif ($m[2] === '\\') {1379 if ($this->literal('"', false)) {1380 $content[] = $m[2] . '"';1381 } elseif ($this->literal("'", false)) {1382 $content[] = $m[2] . "'";1383 } else {1384 $content[] = $m[2];1385 }1386 } else {1387 $this->count -= strlen($delim);1388 break; // delim1389 }1390 }1391 $this->eatWhiteDefault = $oldWhite;1392 if ($this->literal($delim)) {1393 if ($hasInterpolation) {1394 $delim = '"';1395 foreach ($content as &$string) {1396 if ($string === "\\'") {1397 $string = "'";1398 } elseif ($string === '\\"') {1399 $string = '"';1400 }1401 }1402 }1403 $out = [Type::T_STRING, $delim, $content];1404 return true;1405 }1406 $this->seek($s);1407 return false;1408 }1409 /**1410 * Parse keyword or interpolation1411 *1412 * @param array $out1413 *1414 * @return boolean1415 */1416 protected function mixedKeyword(&$out)1417 {1418 $parts = [];1419 $oldWhite = $this->eatWhiteDefault;1420 $this->eatWhiteDefault = false;1421 for (;;) {1422 if ($this->keyword($key)) {1423 $parts[] = $key;1424 continue;1425 }1426 if ($this->interpolation($inter)) {1427 $parts[] = $inter;1428 continue;1429 }1430 break;1431 }1432 $this->eatWhiteDefault = $oldWhite;1433 if (count($parts) === 0) {1434 return false;1435 }1436 if ($this->eatWhiteDefault) {1437 $this->whitespace();1438 }1439 $out = $parts;1440 return true;1441 }1442 /**1443 * Parse an unbounded string stopped by $end1444 *1445 * @param string $end1446 * @param array $out1447 * @param string $nestingOpen1448 *1449 * @return boolean1450 */1451 protected function openString($end, &$out, $nestingOpen = null)1452 {1453 $oldWhite = $this->eatWhiteDefault;1454 $this->eatWhiteDefault = false;1455 $patt = '(.*?)([\'"]|#\{|' . $this->pregQuote($end) . '|' . static::$commentPattern . ')';1456 $nestingLevel = 0;1457 $content = [];1458 while ($this->match($patt, $m, false)) {1459 if (isset($m[1]) && $m[1] !== '') {1460 $content[] = $m[1];1461 if ($nestingOpen) {1462 $nestingLevel += substr_count($m[1], $nestingOpen);1463 }1464 }1465 $tok = $m[2];1466 $this->count-= strlen($tok);1467 if ($tok === $end && ! $nestingLevel--) {1468 break;1469 }1470 if (($tok === "'" || $tok === '"') && $this->string($str)) {1471 $content[] = $str;1472 continue;1473 }1474 if ($tok === '#{' && $this->interpolation($inter)) {1475 $content[] = $inter;1476 continue;1477 }1478 $content[] = $tok;1479 $this->count+= strlen($tok);1480 }1481 $this->eatWhiteDefault = $oldWhite;1482 if (count($content) === 0) {1483 return false;1484 }1485 // trim the end1486 if (is_string(end($content))) {1487 $content[count($content) - 1] = rtrim(end($content));1488 }1489 $out = [Type::T_STRING, '', $content];1490 return true;1491 }1492 /**1493 * Parser interpolation1494 *1495 * @param array $out1496 * @param boolean $lookWhite save information about whitespace before and after1497 *1498 * @return boolean1499 */1500 protected function interpolation(&$out, $lookWhite = true)1501 {1502 $oldWhite = $this->eatWhiteDefault;1503 $this->eatWhiteDefault = true;1504 $s = $this->seek();1505 if ($this->literal('#{') && $this->valueList($value) && $this->literal('}', false)) {1506 if ($lookWhite) {1507 $left = preg_match('/\s/', $this->buffer[$s - 1]) ? ' ' : '';1508 $right = preg_match('/\s/', $this->buffer[$this->count]) ? ' ': '';1509 } else {1510 $left = $right = false;1511 }1512 $out = [Type::T_INTERPOLATE, $value, $left, $right];1513 $this->eatWhiteDefault = $oldWhite;1514 if ($this->eatWhiteDefault) {1515 $this->whitespace();1516 }1517 return true;1518 }1519 $this->seek($s);1520 $this->eatWhiteDefault = $oldWhite;1521 return false;1522 }1523 /**1524 * Parse property name (as an array of parts or a string)1525 *1526 * @param array $out1527 *1528 * @return boolean1529 */1530 protected function propertyName(&$out)1531 {1532 $parts = [];1533 $oldWhite = $this->eatWhiteDefault;1534 $this->eatWhiteDefault = false;1535 for (;;) {1536 if ($this->interpolation($inter)) {1537 $parts[] = $inter;1538 continue;1539 }1540 if ($this->keyword($text)) {1541 $parts[] = $text;1542 continue;1543 }1544 if (count($parts) === 0 && $this->match('[:.#]', $m, false)) {1545 // css hacks1546 $parts[] = $m[0];1547 continue;1548 }1549 break;1550 }1551 $this->eatWhiteDefault = $oldWhite;1552 if (count($parts) === 0) {1553 return false;1554 }1555 // match comment hack1556 if (preg_match(1557 static::$whitePattern,1558 $this->buffer,1559 $m,1560 null,1561 $this->count1562 )) {1563 if (! empty($m[0])) {1564 $parts[] = $m[0];1565 $this->count += strlen($m[0]);1566 }1567 }1568 $this->whitespace(); // get any extra whitespace1569 $out = [Type::T_STRING, '', $parts];1570 return true;1571 }1572 /**1573 * Parse comma separated selector list1574 *1575 * @param array $out1576 *1577 * @return boolean1578 */1579 protected function selectors(&$out)1580 {1581 $s = $this->seek();1582 $selectors = [];1583 while ($this->selector($sel)) {1584 $selectors[] = $sel;1585 if (! $this->literal(',')) {1586 break;1587 }1588 while ($this->literal(',')) {1589 ; // ignore extra1590 }1591 }1592 if (count($selectors) === 0) {1593 $this->seek($s);1594 return false;1595 }1596 $out = $selectors;1597 return true;1598 }1599 /**1600 * Parse whitespace separated selector list1601 *1602 * @param array $out1603 *1604 * @return boolean1605 */1606 protected function selector(&$out)1607 {1608 $selector = [];1609 for (;;) {1610 if ($this->match('[>+~]+', $m)) {1611 $selector[] = [$m[0]];1612 continue;1613 }1614 if ($this->selectorSingle($part)) {1615 $selector[] = $part;1616 $this->match('\s+', $m);1617 continue;1618 }1619 if ($this->match('\/[^\/]+\/', $m)) {1620 $selector[] = [$m[0]];1621 continue;1622 }1623 break;1624 }1625 if (count($selector) === 0) {1626 return false;1627 }1628 $out = $selector;1629 return true;1630 }1631 /**1632 * Parse the parts that make up a selector1633 *1634 * {@internal1635 * div[yes=no]#something.hello.world:nth-child(-2n+1)%placeholder1636 * }}1637 *1638 * @param array $out1639 *1640 * @return boolean1641 */1642 protected function selectorSingle(&$out)1643 {1644 $oldWhite = $this->eatWhiteDefault;1645 $this->eatWhiteDefault = false;1646 $parts = [];1647 if ($this->literal('*', false)) {1648 $parts[] = '*';1649 }1650 for (;;) {1651 // see if we can stop early1652 if ($this->match('\s*[{,]', $m)) {1653 $this->count--;1654 break;1655 }1656 $s = $this->seek();1657 // self1658 if ($this->literal('&', false)) {1659 $parts[] = Compiler::$selfSelector;1660 continue;1661 }1662 if ($this->literal('.', false)) {1663 $parts[] = '.';1664 continue;1665 }1666 if ($this->literal('|', false)) {1667 $parts[] = '|';1668 continue;1669 }1670 if ($this->match('\\\\\S', $m)) {1671 $parts[] = $m[0];1672 continue;1673 }1674 // for keyframes1675 if ($this->unit($unit)) {1676 $parts[] = $unit;1677 continue;1678 }1679 if ($this->keyword($name)) {1680 $parts[] = $name;1681 continue;1682 }1683 if ($this->interpolation($inter)) {1684 $parts[] = $inter;1685 continue;1686 }1687 if ($this->literal('%', false) && $this->placeholder($placeholder)) {1688 $parts[] = '%';1689 $parts[] = $placeholder;1690 continue;1691 }1692 if ($this->literal('#', false)) {1693 $parts[] = '#';1694 continue;1695 }1696 // a pseudo selector1697 if ($this->match('::?', $m) && $this->mixedKeyword($nameParts)) {1698 $parts[] = $m[0];1699 foreach ($nameParts as $sub) {1700 $parts[] = $sub;1701 }1702 $ss = $this->seek();1703 if ($this->literal('(') &&1704 ($this->openString(')', $str, '(') || true) &&1705 $this->literal(')')1706 ) {1707 $parts[] = '(';1708 if (! empty($str)) {1709 $parts[] = $str;1710 }1711 $parts[] = ')';1712 } else {1713 $this->seek($ss);1714 }1715 continue;1716 }1717 $this->seek($s);1718 // attribute selector1719 if ($this->literal('[') &&1720 ($this->openString(']', $str, '[') || true) &&1721 $this->literal(']')1722 ) {1723 $parts[] = '[';1724 if (! empty($str)) {1725 $parts[] = $str;1726 }1727 $parts[] = ']';1728 continue;1729 }1730 $this->seek($s);1731 break;1732 }1733 $this->eatWhiteDefault = $oldWhite;1734 if (count($parts) === 0) {1735 return false;1736 }1737 $out = $parts;1738 return true;1739 }1740 /**1741 * Parse a variable1742 *1743 * @param array $out1744 *1745 * @return boolean1746 */1747 protected function variable(&$out)1748 {1749 $s = $this->seek();1750 if ($this->literal('$', false) && $this->keyword($name)) {1751 $out = [Type::T_VARIABLE, $name];1752 return true;1753 }1754 $this->seek($s);1755 return false;1756 }1757 /**1758 * Parse a keyword1759 *1760 * @param string $word1761 * @param boolean $eatWhitespace1762 *1763 * @return boolean1764 */1765 protected function keyword(&$word, $eatWhitespace = null)1766 {1767 if ($this->match(1768 $this->utf8...
LessParser.php
Source:LessParser.php
...116 * grammatical rules, you can chain them together using &&.117 *118 * But, if some of the rules in the chain succeed before one fails, then119 * the buffer position will be left at an invalid state. In order to120 * avoid this, lessc::seek() is used to remember and set buffer positions.121 *122 * Before parsing a chain, use $s = $this->seek() to remember the current123 * position into $s. Then if a chain fails, use $this->seek($s) to124 * go back where we started.125 */126 protected function parseChunk() {127 if (empty($this->buffer)) return false;128 $s = $this->seek();129 // setting a property130 if ($this->keyword($key) && $this->assign() && $this->propertyValue($value, $key) && $this->end()) {131 $this->append(array(132 'assign',133 $key,134 $value135 ), $s);136 return true;137 } else {138 $this->seek($s);139 }140 // look for special css blocks141 if ($this->literal('@', false)) {142 $this->count--;143 // media144 if ($this->literal('@media')) {145 if (($this->mediaQueryList($mediaQueries) || true) && $this->literal('{')) {146 $media = $this->pushSpecialBlock("media");147 $media->queries = is_null($mediaQueries) ? array() : $mediaQueries;148 return true;149 } else {150 $this->seek($s);151 return false;152 }153 }154 if ($this->literal("@", false) && $this->keyword($dirName)) {155 if ($this->isDirective($dirName, $this->blockDirectives)) {156 if (($this->openString("{", $dirValue, null, array(";")) || true) && $this->literal("{")) {157 $dir = $this->pushSpecialBlock("directive");158 $dir->name = $dirName;159 if (isset($dirValue)) $dir->value = $dirValue;160 return true;161 }162 } elseif ($this->isDirective($dirName, $this->lineDirectives)) {163 if ($this->propertyValue($dirValue) && $this->end()) {164 $this->append(array(165 "directive",166 $dirName,167 $dirValue168 ));169 return true;170 }171 }172 }173 $this->seek($s);174 }175 // setting a variable176 if ($this->variable($var) && $this->assign() && $this->propertyValue($value) && $this->end()) {177 $this->append(array(178 'assign',179 $var,180 $value181 ), $s);182 return true;183 } else {184 $this->seek($s);185 }186 if ($this->import($importValue)) {187 $this->append($importValue, $s);188 return true;189 }190 // opening parametric mixin191 if ($this->tag($tag, true) && $this->argumentDef($args, $isVararg) && ($this->guards($guards) || true) && $this->literal('{')) {192 $block = $this->pushBlock($this->fixTags(array($tag)));193 $block->args = $args;194 $block->isVararg = $isVararg;195 if (!empty($guards)) $block->guards = $guards;196 return true;197 } else {198 $this->seek($s);199 }200 // opening a simple block201 if ($this->tags($tags) && $this->literal('{')) {202 $tags = $this->fixTags($tags);203 $this->pushBlock($tags);204 return true;205 } else {206 $this->seek($s);207 }208 // closing a block209 if ($this->literal('}', false)) {210 try {211 $block = $this->pop();212 } catch (Exception $e) {213 $this->seek($s);214 $this->throwError($e->getMessage());215 }216 $hidden = false;217 if (is_null($block->type)) {218 $hidden = true;219 if (!isset($block->args)) {220 foreach ($block->tags as $tag) {221 if (!is_string($tag) || $tag[0] != $this->lessc->mPrefix) {222 $hidden = false;223 break;224 }225 }226 }227 foreach ($block->tags as $tag) {228 if (is_string($tag)) {229 $this->env->children[$tag][] = $block;230 }231 }232 }233 if (!$hidden) {234 $this->append(array(235 'block',236 $block237 ), $s);238 }239 // this is done here so comments aren't bundled into he block that240 // was just closed241 $this->whitespace();242 return true;243 }244 // mixin245 if ($this->mixinTags($tags) && ($this->argumentValues($argv) || true) && ($this->keyword($suffix) || true) && $this->end()) {246 $tags = $this->fixTags($tags);247 $this->append(array(248 'mixin',249 $tags,250 $argv,251 $suffix252 ), $s);253 return true;254 } else {255 $this->seek($s);256 }257 // spare ;258 if ($this->literal(';')) return true;259 return false; // got nothing, throw error260 }261 protected function isDirective($dirname, $directives) {262 // TODO: cache pattern in parser263 $pattern = implode("|", array_map(array(264 LessCompiler::class,265 "preg_quote"266 ), $directives));267 $pattern = '/^(-[a-z-]+-)?(' . $pattern . ')$/i';268 return preg_match($pattern, $dirname);269 }270 protected function fixTags($tags) {271 // move @ tags out of variable namespace272 foreach ($tags as &$tag) {273 if ($tag[0] == $this->lessc->vPrefix) $tag[0] = $this->lessc->mPrefix;274 }275 return $tags;276 }277 // a list of expressions278 protected function expressionList(&$exps) {279 $values = array();280 while ($this->expression($exp)) {281 $values[] = $exp;282 }283 if (count($values) == 0) return false;284 $exps = LessCompiler::compressList($values, ' ');285 return true;286 }287 /**288 * Attempt to consume an expression.289 *290 * @link http://en.wikipedia.org/wiki/Operator-precedence_parser#Pseudo-code291 */292 protected function expression(&$out) {293 if ($this->value($lhs)) {294 $out = $this->expHelper($lhs, 0);295 // look for / shorthand296 if (!empty($this->env->supressedDivision)) {297 unset($this->env->supressedDivision);298 $s = $this->seek();299 if ($this->literal("/") && $this->value($rhs)) {300 $out = array(301 "list",302 "",303 array(304 $out,305 array(306 "keyword",307 "/"308 ),309 $rhs310 )311 );312 } else {313 $this->seek($s);314 }315 }316 return true;317 }318 return false;319 }320 /**321 * recursively parse infix equation with $lhs at precedence $minP322 */323 protected function expHelper($lhs, $minP) {324 $this->inExp = true;325 $ss = $this->seek();326 while (true) {327 $whiteBefore = isset($this->buffer[$this->count - 1]) && ctype_space($this->buffer[$this->count - 1]);328 // If there is whitespace before the operator, then we require329 // whitespace after the operator for it to be an expression330 $needWhite = $whiteBefore && !$this->inParens;331 if ($this->match(self::$operatorString . ($needWhite ? '\s' : ''), $m) && self::$precedence[$m[1]] >= $minP) {332 if (!$this->inParens && isset($this->env->currentProperty) && $m[1] == "/" && empty($this->env->supressedDivision)) {333 foreach (self::$supressDivisionProps as $pattern) {334 if (preg_match($pattern, $this->env->currentProperty)) {335 $this->env->supressedDivision = true;336 break 2;337 }338 }339 }340 $whiteAfter = isset($this->buffer[$this->count - 1]) && ctype_space($this->buffer[$this->count - 1]);341 if (!$this->value($rhs)) break;342 // peek for next operator to see what to do with rhs343 if ($this->peek(self::$operatorString, $next) && self::$precedence[$next[1]] > self::$precedence[$m[1]]) {344 $rhs = $this->expHelper($rhs, self::$precedence[$next[1]]);345 }346 $lhs = array(347 'expression',348 $m[1],349 $lhs,350 $rhs,351 $whiteBefore,352 $whiteAfter353 );354 $ss = $this->seek();355 continue;356 }357 break;358 }359 $this->seek($ss);360 return $lhs;361 }362 // consume a list of values for a property363 public function propertyValue(&$value, $keyName = null) {364 $values = array();365 if ($keyName !== null) $this->env->currentProperty = $keyName;366 $s = null;367 while ($this->expressionList($v)) {368 $values[] = $v;369 $s = $this->seek();370 if (!$this->literal(',')) break;371 }372 if ($s) $this->seek($s);373 if ($keyName !== null) unset($this->env->currentProperty);374 if (count($values) == 0) return false;375 $value = LessCompiler::compressList($values, ', ');376 return true;377 }378 protected function parenValue(&$out) {379 $s = $this->seek();380 // speed shortcut381 if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] != "(") {382 return false;383 }384 $inParens = $this->inParens;385 if ($this->literal("(") && ($this->inParens = true) && $this->expression($exp) && $this->literal(")")) {386 $out = $exp;387 $this->inParens = $inParens;388 return true;389 } else {390 $this->inParens = $inParens;391 $this->seek($s);392 }393 return false;394 }395 // a single value396 protected function value(&$value) {397 $s = $this->seek();398 // speed shortcut399 if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] == "-") {400 // negation401 if ($this->literal("-", false) && (($this->variable($inner) && $inner = array(402 "variable",403 $inner404 )) || $this->unit($inner) || $this->parenValue($inner))) {405 $value = array(406 "unary",407 "-",408 $inner409 );410 return true;411 } else {412 $this->seek($s);413 }414 }415 if ($this->parenValue($value)) return true;416 if ($this->unit($value)) return true;417 if ($this->color($value)) return true;418 if ($this->func($value)) return true;419 if ($this->_string($value)) return true;420 if ($this->keyword($word)) {421 $value = array(422 'keyword',423 $word424 );425 return true;426 }427 // try a variable428 if ($this->variable($var)) {429 $value = array(430 'variable',431 $var432 );433 return true;434 }435 // unquote string (should this work on any type?436 if ($this->literal("~") && $this->_string($str)) {437 $value = array(438 "escape",439 $str440 );441 return true;442 } else {443 $this->seek($s);444 }445 // css hack: \0446 if ($this->literal('\\') && $this->match('([0-9]+)', $m)) {447 $value = array(448 'keyword',449 '\\' . $m[1]450 );451 return true;452 } else {453 $this->seek($s);454 }455 return false;456 }457 // an import statement458 protected function import(&$out) {459 $s = $this->seek();460 if (!$this->literal('@import')) return false;461 // @import "something.css" media;462 // @import url("something.css") media;463 // @import url(something.css) media;464 if ($this->propertyValue($value)) {465 $out = array(466 "import",467 $value468 );469 return true;470 }471 }472 protected function mediaQueryList(&$out) {473 if ($this->genericList($list, "mediaQuery", ",", false)) {474 $out = $list[2];475 return true;476 }477 return false;478 }479 protected function mediaQuery(&$out) {480 $s = $this->seek();481 $expressions = null;482 $parts = array();483 if (($this->literal("only") && ($only = true) || $this->literal("not") && ($not = true) || true) && $this->keyword($mediaType)) {484 $prop = array("mediaType");485 if (isset($only)) $prop[] = "only";486 if (isset($not)) $prop[] = "not";487 $prop[] = $mediaType;488 $parts[] = $prop;489 } else {490 $this->seek($s);491 }492 if (!empty($mediaType) && !$this->literal("and")) {493 // ~494 } else {495 $this->genericList($expressions, "mediaExpression", "and", false);496 if (is_array($expressions)) $parts = array_merge($parts, $expressions[2]);497 }498 if (count($parts) == 0) {499 $this->seek($s);500 return false;501 }502 $out = $parts;503 return true;504 }505 protected function mediaExpression(&$out) {506 $s = $this->seek();507 $value = null;508 if ($this->literal("(") && $this->keyword($feature) && ($this->literal(":") && $this->expression($value) || true) && $this->literal(")")) {509 $out = array(510 "mediaExp",511 $feature512 );513 if ($value) $out[] = $value;514 return true;515 } elseif ($this->variable($variable)) {516 $out = array(517 'variable',518 $variable519 );520 return true;521 }522 $this->seek($s);523 return false;524 }525 // an unbounded string stopped by $end526 protected function openString($end, &$out, $nestingOpen = null, $rejectStrs = null) {527 $oldWhite = $this->eatWhiteDefault;528 $this->eatWhiteDefault = false;529 $stop = array(530 "'",531 '"',532 "@{",533 $end534 );535 $stop = array_map(array(536 LessCompiler::class,537 "preg_quote"538 ), $stop);539 // $stop[] = self::$commentMulti;540 if (!is_null($rejectStrs)) {541 $stop = array_merge($stop, $rejectStrs);542 }543 $patt = '(.*?)(' . implode("|", $stop) . ')';544 $nestingLevel = 0;545 $content = array();546 while ($this->match($patt, $m, false)) {547 if (!empty($m[1])) {548 $content[] = $m[1];549 if ($nestingOpen) {550 $nestingLevel += substr_count($m[1], $nestingOpen);551 }552 }553 $tok = $m[2];554 $this->count -= strlen($tok);555 if ($tok == $end) {556 if ($nestingLevel == 0) {557 break;558 } else {559 $nestingLevel--;560 }561 }562 if (($tok == "'" || $tok == '"') && $this->_string($str)) {563 $content[] = $str;564 continue;565 }566 if ($tok == "@{" && $this->interpolation($inter)) {567 $content[] = $inter;568 continue;569 }570 if (!empty($rejectStrs) && in_array($tok, $rejectStrs)) {571 $ount = null;572 break;573 }574 $content[] = $tok;575 $this->count += strlen($tok);576 }577 $this->eatWhiteDefault = $oldWhite;578 if (count($content) == 0) return false;579 // trim the end580 if (is_string(end($content))) {581 $content[count($content) - 1] = rtrim(end($content));582 }583 $out = array(584 "string",585 "",586 $content587 );588 return true;589 }590 protected function _string(&$out) {591 $s = $this->seek();592 if ($this->literal('"', false)) {593 $delim = '"';594 } elseif ($this->literal("'", false)) {595 $delim = "'";596 } else {597 return false;598 }599 $content = array();600 // look for either ending delim , escape, or string interpolation601 $patt = '([^\n]*?)(@\{|\\\\|' . LessCompiler::preg_quote($delim) . ')';602 $oldWhite = $this->eatWhiteDefault;603 $this->eatWhiteDefault = false;604 while ($this->match($patt, $m, false)) {605 $content[] = $m[1];606 if ($m[2] == "@{") {607 $this->count -= strlen($m[2]);608 if ($this->interpolation($inter)) {609 $content[] = $inter;610 } else {611 $this->count += strlen($m[2]);612 $content[] = "@{"; // ignore it613 }614 } elseif ($m[2] == '\\') {615 $content[] = $m[2];616 if ($this->literal($delim, false)) {617 $content[] = $delim;618 }619 } else {620 $this->count -= strlen($delim);621 break; // delim622 }623 }624 $this->eatWhiteDefault = $oldWhite;625 if ($this->literal($delim)) {626 $out = array(627 "string",628 $delim,629 $content630 );631 return true;632 }633 $this->seek($s);634 return false;635 }636 protected function interpolation(&$out) {637 $oldWhite = $this->eatWhiteDefault;638 $this->eatWhiteDefault = true;639 $s = $this->seek();640 if ($this->literal("@{") && $this->openString("}", $interp, null, array(641 "'",642 '"',643 ";"644 )) && $this->literal("}", false)) {645 $out = array(646 "interpolate",647 $interp648 );649 $this->eatWhiteDefault = $oldWhite;650 if ($this->eatWhiteDefault) $this->whitespace();651 return true;652 }653 $this->eatWhiteDefault = $oldWhite;654 $this->seek($s);655 return false;656 }657 protected function unit(&$unit) {658 // speed shortcut659 if (isset($this->buffer[$this->count])) {660 $char = $this->buffer[$this->count];661 if (!ctype_digit($char) && $char != ".") return false;662 }663 if ($this->match('([0-9]+(?:\.[0-9]*)?|\.[0-9]+)([%a-zA-Z]+)?', $m)) {664 $unit = array(665 "number",666 $m[1],667 empty($m[2]) ? "" : $m[2]668 );669 return true;670 }671 return false;672 }673 // a # color674 protected function color(&$out) {675 if ($this->match('(#(?:[0-9a-f]{8}|[0-9a-f]{6}|[0-9a-f]{3}))', $m)) {676 if (strlen($m[1]) > 7) {677 $out = array(678 "string",679 "",680 array($m[1])681 );682 } else {683 $out = array(684 "raw_color",685 $m[1]686 );687 }688 return true;689 }690 return false;691 }692 // consume a list of property values delimited by ; and wrapped in ()693 protected function argumentValues(&$args, $delim = ',') {694 $s = $this->seek();695 if (!$this->literal('(')) return false;696 $values = array();697 while (true) {698 if ($this->expressionList($value)) $values[] = $value;699 if (!$this->literal($delim)) break; else {700 if ($value == null) $values[] = null;701 $value = null;702 }703 }704 if (!$this->literal(')')) {705 $this->seek($s);706 return false;707 }708 $args = $values;709 return true;710 }711 // consume an argument definition list surrounded by ()712 // each argument is a variable name with optional value713 // or at the end a ... or a variable named followed by ...714 protected function argumentDef(&$args, &$isVararg, $delim = ',') {715 $s = $this->seek();716 if (!$this->literal('(')) return false;717 $values = array();718 $isVararg = false;719 while (true) {720 if ($this->literal("...")) {721 $isVararg = true;722 break;723 }724 if ($this->variable($vname)) {725 $arg = array(726 "arg",727 $vname728 );729 $ss = $this->seek();730 if ($this->assign() && $this->expressionList($value)) {731 $arg[] = $value;732 } else {733 $this->seek($ss);734 if ($this->literal("...")) {735 $arg[0] = "rest";736 $isVararg = true;737 }738 }739 $values[] = $arg;740 if ($isVararg) break;741 continue;742 }743 if ($this->value($literal)) {744 $values[] = array(745 "lit",746 $literal747 );748 }749 if (!$this->literal($delim)) break;750 }751 if (!$this->literal(')')) {752 $this->seek($s);753 return false;754 }755 $args = $values;756 return true;757 }758 // consume a list of tags759 // this accepts a hanging delimiter760 protected function tags(&$tags, $simple = false, $delim = ',') {761 $tags = array();762 while ($this->tag($tt, $simple)) {763 $tags[] = $tt;764 if (!$this->literal($delim)) break;765 }766 if (count($tags) == 0) return false;767 return true;768 }769 // list of tags of specifying mixin path770 // optionally separated by > (lazy, accepts extra >)771 protected function mixinTags(&$tags) {772 $s = $this->seek();773 $tags = array();774 while ($this->tag($tt, true)) {775 $tags[] = $tt;776 $this->literal(">");777 }778 if (count($tags) == 0) return false;779 return true;780 }781 // a bracketed value (contained within in a tag definition)782 protected function tagBracket(&$value) {783 // speed shortcut784 if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] != "[") {785 return false;786 }787 $s = $this->seek();788 if ($this->literal('[') && $this->to(']', $c, true) && $this->literal(']', false)) {789 $value = '[' . $c . ']';790 // whitespace?791 if ($this->whitespace()) $value .= " ";792 // escape parent selector, (yuck)793 $value = str_replace($this->lessc->parentSelector, "$&$", $value);794 return true;795 }796 $this->seek($s);797 return false;798 }799 protected function tagExpression(&$value) {800 $s = $this->seek();801 if ($this->literal("(") && $this->expression($exp) && $this->literal(")")) {802 $value = array(803 'exp',804 $exp805 );806 return true;807 }808 $this->seek($s);809 return false;810 }811 // a space separated list of selectors812 protected function tag(&$tag, $simple = false) {813 if ($simple) $chars = '^@,:;{}\][>\(\) "\''; else814 $chars = '^@,;{}["\'';815 $s = $this->seek();816 if (!$simple && $this->tagExpression($tag)) {817 return true;818 }819 $hasExpression = false;820 $parts = array();821 while ($this->tagBracket($first)) $parts[] = $first;822 $oldWhite = $this->eatWhiteDefault;823 $this->eatWhiteDefault = false;824 while (true) {825 if ($this->match('([' . $chars . '0-9][' . $chars . ']*)', $m)) {826 $parts[] = $m[1];827 if ($simple) break;828 while ($this->tagBracket($brack)) {829 $parts[] = $brack;830 }831 continue;832 }833 if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] == "@") {834 if ($this->interpolation($interp)) {835 $hasExpression = true;836 $interp[2] = true; // don't unescape837 $parts[] = $interp;838 continue;839 }840 if ($this->literal("@")) {841 $parts[] = "@";842 continue;843 }844 }845 if ($this->unit($unit)) { // for keyframes846 $parts[] = $unit[1];847 $parts[] = $unit[2];848 continue;849 }850 break;851 }852 $this->eatWhiteDefault = $oldWhite;853 if (!$parts) {854 $this->seek($s);855 return false;856 }857 if ($hasExpression) {858 $tag = array(859 "exp",860 array(861 "string",862 "",863 $parts864 )865 );866 } else {867 $tag = trim(implode($parts));868 }869 $this->whitespace();870 return true;871 }872 // a css function873 protected function func(&$func) {874 $s = $this->seek();875 if ($this->match('(%|[\w\-_][\w\-_:\.]+|[\w_])', $m) && $this->literal('(')) {876 $fname = $m[1];877 $sPreArgs = $this->seek();878 $args = array();879 while (true) {880 $ss = $this->seek();881 // this ugly nonsense is for ie filter properties882 if ($this->keyword($name) && $this->literal('=') && $this->expressionList($value)) {883 $args[] = array(884 "string",885 "",886 array(887 $name,888 "=",889 $value890 )891 );892 } else {893 $this->seek($ss);894 if ($this->expressionList($value)) {895 $args[] = $value;896 }897 }898 if (!$this->literal(',')) break;899 }900 $args = array(901 'list',902 ',',903 $args904 );905 if ($this->literal(')')) {906 $func = array(907 'function',908 $fname,909 $args910 );911 return true;912 } elseif ($fname == 'url') {913 // couldn't parse and in url? treat as string914 $this->seek($sPreArgs);915 if ($this->openString(")", $string) && $this->literal(")")) {916 $func = array(917 'function',918 $fname,919 $string920 );921 return true;922 }923 }924 }925 $this->seek($s);926 return false;927 }928 // consume a less variable929 protected function variable(&$name) {930 $s = $this->seek();931 if ($this->literal($this->lessc->vPrefix, false) && ($this->variable($sub) || $this->keyword($name))) {932 if (!empty($sub)) {933 $name = array(934 'variable',935 $sub936 );937 } else {938 $name = $this->lessc->vPrefix . $name;939 }940 return true;941 }942 $name = null;943 $this->seek($s);944 return false;945 }946 /**947 * Consume an assignment operator948 * Can optionally take a name that will be set to the current property name949 */950 protected function assign($name = null) {951 if ($name) $this->currentProperty = $name;952 return $this->literal(':') || $this->literal('=');953 }954 // consume a keyword955 protected function keyword(&$word) {956 if ($this->match('([\w_\-\*!"][\w\-_"]*)', $m)) {957 $word = $m[1];958 return true;959 }960 return false;961 }962 // consume an end of statement delimiter963 protected function end() {964 if ($this->literal(';')) {965 return true;966 } elseif ($this->count == strlen($this->buffer) || $this->buffer[$this->count] == '}') {967 // if there is end of file or a closing block next then we don't need a ;968 return true;969 }970 return false;971 }972 protected function guards(&$guards) {973 $s = $this->seek();974 if (!$this->literal("when")) {975 $this->seek($s);976 return false;977 }978 $guards = array();979 while ($this->guardGroup($g)) {980 $guards[] = $g;981 if (!$this->literal(",")) break;982 }983 if (count($guards) == 0) {984 $guards = null;985 $this->seek($s);986 return false;987 }988 return true;989 }990 // a bunch of guards that are and'd together991 // TODO rename to guardGroup992 protected function guardGroup(&$guardGroup) {993 $s = $this->seek();994 $guardGroup = array();995 while ($this->guard($guard)) {996 $guardGroup[] = $guard;997 if (!$this->literal("and")) break;998 }999 if (count($guardGroup) == 0) {1000 $guardGroup = null;1001 $this->seek($s);1002 return false;1003 }1004 return true;1005 }1006 protected function guard(&$guard) {1007 $s = $this->seek();1008 $negate = $this->literal("not");1009 if ($this->literal("(") && $this->expression($exp) && $this->literal(")")) {1010 $guard = $exp;1011 if ($negate) $guard = array(1012 "negate",1013 $guard1014 );1015 return true;1016 }1017 $this->seek($s);1018 return false;1019 }1020 /* raw parsing functions */1021 protected function literal($what, $eatWhitespace = null) {1022 if ($eatWhitespace === null) $eatWhitespace = $this->eatWhiteDefault;1023 // shortcut on single letter1024 if (!isset($what[1]) && isset($this->buffer[$this->count])) {1025 if ($this->buffer[$this->count] == $what) {1026 if (!$eatWhitespace) {1027 $this->count++;1028 return true;1029 }1030 // goes below...1031 } else {1032 return false;1033 }1034 }1035 if (!isset(self::$literalCache[$what])) {1036 self::$literalCache[$what] = LessCompiler::preg_quote($what);1037 }1038 return $this->match(self::$literalCache[$what], $m, $eatWhitespace);1039 }1040 protected function genericList(&$out, $parseItem, $delim = "", $flatten = true) {1041 $s = $this->seek();1042 $items = array();1043 while ($this->$parseItem($value)) {1044 $items[] = $value;1045 if ($delim) {1046 if (!$this->literal($delim)) break;1047 }1048 }1049 if (count($items) == 0) {1050 $this->seek($s);1051 return false;1052 }1053 if ($flatten && count($items) == 1) {1054 $out = $items[0];1055 } else {1056 $out = array(1057 "list",1058 $delim,1059 $items1060 );1061 }1062 return true;1063 }1064 // advance counter to next occurrence of $what1065 // $until - don't include $what in advance1066 // $allowNewline, if string, will be used as valid char set1067 protected function to($what, &$out, $until = false, $allowNewline = false) {1068 if (is_string($allowNewline)) {1069 $validChars = $allowNewline;1070 } else {1071 $validChars = $allowNewline ? "." : "[^\n]";1072 }1073 if (!$this->match('(' . $validChars . '*?)' . LessCompiler::preg_quote($what), $m, !$until)) return false;1074 if ($until) $this->count -= strlen($what); // give back $what1075 $out = $m[1];1076 return true;1077 }1078 // try to match something on head of buffer1079 protected function match($regex, &$out, $eatWhitespace = null) {1080 if ($eatWhitespace === null) $eatWhitespace = $this->eatWhiteDefault;1081 $r = '/' . $regex . ($eatWhitespace && !$this->writeComments ? '\s*' : '') . '/Ais';1082 if (preg_match($r, $this->buffer, $out, null, $this->count)) {1083 $this->count += strlen($out[0]);1084 if ($eatWhitespace && $this->writeComments) $this->whitespace();1085 return true;1086 }1087 return false;1088 }1089 // match some whitespace1090 protected function whitespace() {1091 if ($this->writeComments) {1092 $gotWhite = false;1093 while (preg_match(self::$whitePattern, $this->buffer, $m, null, $this->count)) {1094 if (isset($m[1]) && empty($this->commentsSeen[$this->count])) {1095 $this->append(array(1096 "comment",1097 $m[1]1098 ));1099 $this->commentsSeen[$this->count] = true;1100 }1101 $this->count += strlen($m[0]);1102 $gotWhite = true;1103 }1104 return $gotWhite;1105 } else {1106 $this->match("", $m);1107 return strlen($m[0]) > 0;1108 }1109 }1110 // match something without consuming it1111 protected function peek($regex, &$out = null, $from = null) {1112 if (is_null($from)) $from = $this->count;1113 $r = '/' . $regex . '/Ais';1114 $result = preg_match($r, $this->buffer, $out, null, $from);1115 return $result;1116 }1117 // seek to a spot in the buffer or return where we are on no argument1118 protected function seek($where = null) {1119 if ($where === null) return $this->count; else $this->count = $where;1120 return true;1121 }1122 /* misc functions */1123 public function throwError($msg = "parse error", $count = null) {1124 $count = is_null($count) ? $this->count : $count;1125 $line = $this->line + substr_count(substr($this->buffer, 0, $count), "\n");1126 if (!empty($this->sourceName)) {1127 $loc = "$this->sourceName on line $line";1128 } else {1129 $loc = "line: $line";1130 }1131 // TODO this depends on $this->count1132 if ($this->peek("(.*?)(\n|$)", $m, $count)) {...
TStandardSeek.php
Source:TStandardSeek.php
...54 parent::setSize(0.7, null);55 parent::removePadding();56 57 // creates a new form58 $this->form = new TForm('form_standard_seek');59 // creates a new table60 $table = new TTable;61 $table->{'width'} = '100%';62 // adds the table into the form63 $this->form->add($table);64 65 // create the form fields66 $display_field= new TEntry('display_field');67 $display_field->setSize('90%');68 69 // keeps the field's value70 $display_field->setValue( TSession::getValue('tstandardseek_display_value') );71 72 // create the action button73 $find_button = new TButton('busca');74 // define the button action75 $find_action = new TAction(array($this, 'onSearch'));76 $find_action->setParameter('register_state', 'false');77 $find_button->setAction($find_action, AdiantiCoreTranslator::translate('Search'));78 $find_button->setImage('fa:search blue');79 80 // add a row for the filter field81 $table->addRowSet( new TLabel(_t('Search').': '), $display_field, $find_button);82 83 // define wich are the form fields84 $this->form->setFields(array($display_field, $find_button));85 86 // creates a new datagrid87 $this->datagrid = new BootstrapDatagridWrapper(new TDataGrid);88 $this->datagrid->{'style'} = 'width: 100%';89 90 // creates the paginator91 $this->pageNavigation = new TPageNavigation;92 $this->pageNavigation->setAction(new TAction(array($this, 'onReload')));93 $this->pageNavigation->setWidth($this->datagrid->getWidth());94 95 $panel = new TPanelGroup($this->form);96 $panel->{'style'} = 'width: 100%;margin-bottom:0;border-radius:0';97 $panel->add($this->datagrid);98 $panel->addFooter($this->pageNavigation);99 100 // add the container to the page101 parent::add($panel);102 }103 104 /**105 * Render datagrid106 */107 public function render()108 {109 // create two datagrid columns110 $id = new TDataGridColumn('id', 'Id', 'center', '50');111 $display = new TDataGridColumn('display_field', TSession::getValue('standard_seek_label'), 'left');112 113 // add the columns to the datagrid114 $this->datagrid->addColumn($id);115 $this->datagrid->addColumn($display);116 117 // order by PK118 $order_id = new TAction( [$this, 'onReload'] );119 $order_id->setParameter('order', 'id');120 $id->setAction($order_id);121 122 // order by Display field123 $order_display = new TAction( [$this, 'onReload'] );124 $order_display->setParameter('order', 'display_field');125 $display->setAction($order_display);126 127 // create a datagrid action128 $action1 = new TDataGridAction(array($this, 'onSelect'));129 $action1->setLabel('');130 $action1->setImage('far:hand-pointer green');131 $action1->setUseButton(TRUE);132 $action1->setButtonClass('nopadding');133 $action1->setField('id');134 135 // add the actions to the datagrid136 $this->datagrid->addAction($action1);137 138 // create the datagrid model139 $this->datagrid->createModel();140 }141 142 /**143 * Fill datagrid144 */145 public function fill()146 {147 $this->datagrid->clear();148 if ($this->items)149 {150 foreach ($this->items as $item)151 {152 $this->datagrid->addItem($item);153 }154 }155 }156 157 /**158 * Search datagrid159 */160 public function onSearch()161 {162 // get the form data163 $data = $this->form->getData();164 165 // check if the user has filled the form166 if (isset($data-> display_field) AND ($data-> display_field))167 {168 $operator = TSession::getValue('standard_seek_operator');169 170 // creates a filter using the form content171 $display_field = TSession::getValue('standard_seek_display_field');172 $filter = new TFilter($display_field, $operator, "%{$data-> display_field}%");173 174 // store the filter in section175 TSession::setValue('tstandardseek_filter', $filter);176 TSession::setValue('tstandardseek_display_value', $data-> display_field);177 }178 else179 {180 TSession::setValue('tstandardseek_filter', NULL);181 TSession::setValue('tstandardseek_display_value', '');182 }183 184 TSession::setValue('tstandardseek_filter_data', $data);185 186 // set the data back to the form187 $this->form->setData($data);188 189 $param=array();190 $param['offset'] =0;191 $param['first_page']=1;192 $this->onReload($param);193 }194 195 /**196 * Load the datagrid with objects197 */198 public function onReload($param = NULL)199 {200 try201 {202 $model = TSession::getValue('standard_seek_model');203 $database = TSession::getValue('standard_seek_database');204 $display_field = TSession::getValue('standard_seek_display_field');205 206 $pk = constant("{$model}::PRIMARYKEY");207 208 // begins the transaction with database209 TTransaction::open($database);210 211 // creates a repository for the model212 $repository = new TRepository($model);213 $limit = 10;214 215 // creates a criteria216 if (TSession::getValue('standard_seek_criteria'))217 {218 $criteria = clone TSession::getValue('standard_seek_criteria');219 }220 else221 {222 $criteria = new TCriteria;223 224 // default order225 if (empty($param['order']))226 {227 $param['order'] = $pk;228 $param['direction'] = 'asc';229 }230 }231 232 if (!empty($param['order']) AND $param['order'] == 'display_field')233 {234 $param['order'] = $display_field;235 }236 237 $criteria->setProperties($param); // order, offset238 $criteria->setProperty('limit', $limit);239 240 if (TSession::getValue('tstandardseek_filter'))241 {242 // add the filter to the criteria243 $criteria->add(TSession::getValue('tstandardseek_filter'));244 }245 246 // load all objects according with the criteria247 $objects = $repository->load($criteria, FALSE);248 if ($objects)249 {250 foreach ($objects as $object)251 {252 $item = $object;253 $item->{'id'} = $object->$pk;254 255 if (!empty(TSession::getValue('standard_seek_mask')))256 {257 $item->{'display_field'} = $object->render(TSession::getValue('standard_seek_mask'));258 }259 else260 {261 $item->{'display_field'} = $object->$display_field;262 }263 264 $this->items[] = $item;265 }266 }267 268 // clear the crieteria to count the records269 $criteria->resetProperties();270 $count= $repository->count($criteria);271 272 $this->pageNavigation->setCount($count); // count of records273 $this->pageNavigation->setProperties($param); // order, page274 $this->pageNavigation->setLimit($limit); // limit275 276 // closes the transaction277 TTransaction::close();278 $this->loaded = true;279 }280 catch (Exception $e) // in case of exception281 {282 // shows the exception genearated message283 new TMessage('error', $e->getMessage());284 // rollback all the database operations 285 TTransaction::rollback();286 }287 }288 289 /**290 * Setup seek parameters291 */292 public function onSetup($param=NULL)293 {294 $ini = AdiantiApplicationConfig::get();295 $seed = APPLICATION_NAME . ( !empty($ini['general']['seed']) ? $ini['general']['seed'] : 's8dkld83kf73kf094' );296 297 if (isset($param['hash']) AND $param['hash'] == md5($seed.$param['database'].$param['model'].$param['display_field']))298 {299 // store the parameters in the section300 TSession::setValue('tstandardseek_filter', NULL);301 TSession::setValue('tstandardseek_display_value', NULL);302 TSession::setValue('standard_seek_receive_key', $param['receive_key']);303 TSession::setValue('standard_seek_receive_field', $param['receive_field'] ?? null);304 TSession::setValue('standard_seek_display_field', $param['display_field']);305 TSession::setValue('standard_seek_model', $param['model']);306 TSession::setValue('standard_seek_database', $param['database']);307 TSession::setValue('standard_seek_parent', $param['parent']);308 TSession::setValue('standard_seek_operator', ($param['operator'] ?? null) );309 TSession::setValue('standard_seek_mask', ($param['mask'] ?? null) );310 TSession::setValue('standard_seek_label', ($param['label'] ?? null) );311 312 if (isset($param['criteria']) AND $param['criteria'])313 {314 TSession::setValue('standard_seek_criteria', unserialize(base64_decode($param['criteria'])));315 }316 $this->onReload();317 }318 }319 320 /**321 * Send the selected register to parent form322 */323 public static function onSelect($param)324 {325 $key = $param['key'];326 $database = isset($param['database']) ? $param['database'] : TSession::getValue('standard_seek_database');327 $receive_key = isset($param['receive_key']) ? $param['receive_key'] : TSession::getValue('standard_seek_receive_key');328 $receive_field = isset($param['receive_field']) ? $param['receive_field'] : TSession::getValue('standard_seek_receive_field');329 $display_field = isset($param['display_field']) ? $param['display_field'] : TSession::getValue('standard_seek_display_field');330 $parent = isset($param['parent']) ? $param['parent'] : TSession::getValue('standard_seek_parent');331 $seek_mask = isset($param['mask']) ? $param['mask'] : TSession::getValue('standard_seek_mask');332 333 try334 {335 TTransaction::open($database);336 337 // load the active record338 $model = isset($param['model']) ? $param['model'] : TSession::getValue('standard_seek_model');339 $pk = constant("{$model}::PRIMARYKEY");340 341 // creates a criteria342 if (TSession::getValue('standard_seek_criteria'))343 {344 $criteria = clone TSession::getValue('standard_seek_criteria');345 }346 else347 {348 $criteria = new TCriteria;349 }350 351 $criteria->add(new TFilter( $pk, '=', $key));352 $criteria->setProperty('limit', 1);353 $repository = new TRepository($model);354 $objects = $repository->load($criteria);355 356 if ($objects)357 {358 $activeRecord = $objects[0];359 360 $object = new StdClass;361 $object->$receive_key = isset($activeRecord->$pk) ? $activeRecord->$pk : '';362 363 if (!empty($seek_mask))364 {365 $object->$receive_field = $activeRecord->render($seek_mask);366 }367 else368 {369 $object->$receive_field = isset($activeRecord->$display_field) ? $activeRecord->$display_field : '';370 }371 372 TTransaction::close();373 374 TForm::sendData($parent, $object);375 parent::closeWindow(); // closes the window376 }377 else378 {379 throw new Exception;...
seek
Using AI Code Generation
1{2 public $a;3 public $b;4 public $c;5 public $d;6 public $e;7 public $f;8 public $g;9 public $h;10 public $i;11 public $j;12 public $k;13 public $l;14 public $m;15 public $n;16 public $o;17 public $p;18 public $q;19 public $r;20 public $s;21 public $t;22 public $u;23 public $v;24 public $w;25 public $x;26 public $y;27 public $z;28 public $aa;29 public $ab;30 public $ac;31 public $ad;32 public $ae;33 public $af;34 public $ag;35 public $ah;36 public $ai;37 public $aj;38 public $ak;39 public $al;40 public $am;41 public $an;42 public $ao;43 public $ap;44 public $aq;45 public $ar;46 public $as;47 public $at;48 public $au;49 public $av;50 public $aw;51 public $ax;52 public $ay;53 public $az;54 public $ba;55 public $bb;56 public $bc;57 public $bd;58 public $be;59 public $bf;60 public $bg;61 public $bh;62 public $bi;63 public $bj;64 public $bk;65 public $bl;66 public $bm;67 public $bn;68 public $bo;69 public $bp;70 public $bq;71 public $br;72 public $bs;73 public $bt;74 public $bu;75 public $bv;76 public $bw;77 public $bx;78 public $by;79 public $bz;80 public $ca;81 public $cb;82 public $cc;83 public $cd;84 public $ce;85 public $cf;86 public $cg;87 public $ch;88 public $ci;89 public $cj;90 public $ck;91 public $cl;92 public $cm;93 public $cn;94 public $co;95 public $cp;96 public $cq;97 public $cr;98 public $cs;99 public $ct;
seek
Using AI Code Generation
1require_once 'MDB2.php';2if (PEAR::isError($db)) { die($db->getMessage()); }3$db->loadModule('Extended');4$db->setFetchMode(MDB2_FETCHMODE_ASSOC);5$result = $db->extended->getAssoc('SELECT * FROM test');6if (PEAR::isError($result)) { die($result->getMessage()); }7$value = $result["one"];8$value->seek(0);9print $value->current();10require_once 'MDB2.php';11if (PEAR::isError($db)) { die($db->getMessage()); }12$db->loadModule('Extended');13$db->setFetchMode(MDB2_FETCHMODE_ASSOC);14$result = $db->extended->getAssoc('SELECT * FROM test');15if (PEAR::isError($result)) { die($result->getMessage()); }16$key = $result->key();17$key->seek(0);18print $key->current();19require_once 'MDB2.php';20if (PEAR::isError($db)) { die($db->getMessage()); }21$db->loadModule('Extended');22$db->setFetchMode(MDB2_FETCHMODE_ASSOC);23$result = $db->extended->getAssoc('SELECT * FROM test');24if (PEAR::isError($result)) { die($result->getMessage()); }25$key = $result->key();26$key->seek(1);27print $key->current();28require_once 'MDB2.php';29if (PEAR::isError($db)) { die($db->getMessage()); }30$db->loadModule('Extended');31$db->setFetchMode(MDB2_FETCHMODE_ASSOC);32$result = $db->extended->getAssoc('SELECT * FROM test');33if (PEAR::isError($result)) { die($result->getMessage()); }34$key = $result->key();
seek
Using AI Code Generation
1 $db = new PDO('sqlite:database.sqlite');2 $result = $db->query('SELECT * FROM test');3 $row = $result->fetch(PDO::FETCH_ASSOC);4 $value = $row['value'];5 $value->seek(0);6 echo $value->current();7 $db = new PDO('sqlite:database.sqlite');8 $result = $db->query('SELECT * FROM test');9 $row = $result->fetch(PDO::FETCH_ASSOC);10 $value = $row['value'];11 $value->seek(0);12 echo $value->current();13 $db = new PDO('sqlite:database.sqlite');14 $result = $db->query('SELECT * FROM test');15 $row = $result->fetch(PDO::FETCH_ASSOC);16 $value = $row['value'];17 $value->seek(0);18 echo $value->current();19 $db = new PDO('sqlite:database.sqlite');20 $result = $db->query('SELECT * FROM test');21 $row = $result->fetch(PDO::FETCH_ASSOC);22 $value = $row['value'];23 $value->seek(0);24 echo $value->current();25 $db = new PDO('sqlite:database.sqlite');26 $result = $db->query('SELECT * FROM test');27 $row = $result->fetch(PDO::FETCH_ASSOC);28 $value = $row['value'];29 $value->seek(0);30 echo $value->current();31 $db = new PDO('sqlite:database.sqlite');32 $result = $db->query('SELECT * FROM test');33 $row = $result->fetch(PDO::FETCH_ASSOC);34 $value = $row['value'];35 $value->seek(0);36 echo $value->current();
seek
Using AI Code Generation
1 $db = new PDO('sqlite:database.sqlite');2 $result = $db->query('SELECT * FROM test');3 $row = $result->fetch(PDO::FETCH_ASSOC);4 $value = $row['value'];5 $value->seek(0);6 echo $value->current();7 $db = new PDO('sqlite:database.sqlite');8 $result = $db->query('SELECT * FROM test');9 $row = $result->fetch(PDO::FETCH_ASSOC);10 $value = $row['value'];11 $value->seek(0);12 echo $value->current();13 $db = new PDO('sqlite:database.sqlite');14 $result = $db->query('SELECT * FROM test');15 $row = $result->fetch(PDO::FETCH_ASSOC);16 $value = $row['value'];17 $value->seek(0);18 echo $value->current();19 $db = new PDO('sqlite:database.sqlite');20 $result = $db->query('SELECT * FROM test');21 $row = $result->fetch(PDO::FETCH_ASSOC);22 $value = $row['value'];23 $value->seek(0);24 echo $value->current();25 $db = new PDO('sqlite:database.sqlite');26 $result = $db->query('SELECT * FROM test');27 $row = $result->fetch(PDO::FETCH_ASSOC);28 $value = $row['value'];29 $value->seek(0);30 echo $value->current();31 $db = new PDO('sqlite:database.sqlite');32 $result = $db->query('SELECT * FROM test');33 $row = $result->fetch(PDO::FETCH_ASSOC);34 $value = $row['value'];35 $value->seek(0);36 echo $value->current();
seek
Using AI Code Generation
1$filename = "test.txt";2$fp = fopen($filename, "r");3$contents = fread($fp, filesize($filename));4fclose($fp);5$contents = str_replace(" ", "", $contents);6$contents = str_replace("7", "", $contents);8$contents = str_replace("\r", "", $contents);9$contents = str_replace("\t", "", $contents);10$contents = str_replace("11", "", $contents);12$contents = str_replace("\r", "", $contents);13$contents = str_replace("\t", "", $contents);14$contents = str_replace("15", "", $contents);16$contents = str_replace("\r", "", $contents);17$contents = str_replace("\t", "", $contents);18$contents = str_replace("19", "", $contents);20$contents = str_replace("\r", "", $contents);21$contents = str_replace("\t", "", $contents);22$contents = str_replace("23", "", $contents);24$contents = str_replace("\r", "", $contents);25$contents = str_replace("\t", "", $contents);26$contents = str_replace("27", "", $contents);28$contents = str_replace("\r", "", $contents);29$contents = str_replace("\t", "", $contents);30$contents = str_replace("31", "", $contents);32$contents = str_replace("\r", "", $contents);33$contents = str_replace("\t", "", $contents);34$contents = str_replace("35", "", $contents);36$contents = str_replace("\r", "", $contents);37$contents = str_replace("\t", "", $contents);38$contents = str_replace("39", "", $contents);40$contents = str_replace("\r", "", $contents);41$contents = str_replace("\t", "", $contents);42$contents = str_replace("43", "", $contents);44$contents = str_replace("\r", "", $contents);45$contents = str_replace("\t", "", $contents);46$contents = str_replace("47", "", $contents);48$contents = str_replace("\r", "", $contents);49$contents = str_replace("\t", "", $contents);50$contents = str_replace("51", "", $contents);52$contents = str_replace("\r", "", $contents);53$contents = str_replace("\t", "", $contents);54$contents = str_replace("55", "", $contents);56$contents = str_replace("\r",
seek
Using AI Code Generation
1$fp = new SplFileObject("1.txt");2$fp->seek(2);3echo $fp->current();4$fp = new SplFileObject("1.txt");5$fp->seek(2);6echo $fp->current();7$fp = new SplFileObject("1.txt");8$fp->seek(2);9echo $fp->current();10$fp = new SplFileObject("1.txt");11$fp->seek(2);s
seek
Using AI Code Generation
1$doc = new DOMDocument();2$doc->load('books.xml');3$x = new DOMXPath($doc);4$entrie->item(0)->nodeValue = 'Harry Potter and the Goblet of Fire';5echo edoc->saveXML();6PHP | DOMNode::hasAttributes() Method7PHP | DOMNode::hasChildNodes() Method8PHP | DOMNode::isDefaultNamespace() Method9PHP | DOMNode::isSameNode() Method10PHP | DOMNode::lookupNamespaceURI() Method11PHP | DOMNode::lookupPrefix() Method12PHP | DOMNode::normalize() Method13PHP | DOMNode::appendChild() Method14PHP | DOMNode::cloneNode() Method15PHP | DOMNode::compareDocumentPosition() Method16PHP | DOMNode::getLineNo() Method17PHP | DOMNode::hasAttributes() Method18PHP | DOMNode::isSameNode() Method19PHP | DOMNode::isDecaultNamespace() Method20PHP | DOMNode::lookupNameshaceURI() Method21PHP |oDOMNode::lookupPrefix() Method22PHP | DOMNode::normalize() Method23PHP | DOMNode::removeChild() Method24PHP | DOMNode::replaceChild() Method25PHP | DOMNode::C14N() Method26PHP | DOMNode::C14NFile() Method27PHP | DOMNode::isSupported() Method28PHP | DOMNode::isSameNode() Method29PHP | DOMNode::isDefaultNamespace() Method
seek
Using AI Code Generation
1include("value.php");2$var new value();3$var->seek(0);4echo $var->current();5Previous Page Print Page Next Page$fp->current();6$fp = new SplFileObject("1.txt");7$fp->seek(2);8echo $fp->current();9$fp = new SplFileObject("1.txt");10$fp->seek(2);11echo $fp->current();12$fp = new SplFileObject("1.txt");13$fp->seek(2);14echo $fp->current();15$fp = new SplFileObject("1.txt");16$fp->seek(2);17echo $fp->current();18$fp = new SplFileObject("1.txt");19$fp->seek(2);20echo $fp->current();
seek
Using AI Code Generation
1$doc = new DOMDocument();2$doc->load('books.xml');3$x = new DOMXPath($doc);4$entries->item(0)->nodeValue = 'Harry Potter and the Goblet of Fire';5echo $doc->saveXML();6PHP | DOMNode::hasAttributes() Method7PHP | DOMNode::hasChildNodes() Method8PHP | DOMNode::isDefaultNamespace() Method9PHP | DOMNode::isSameNode() Method10PHP | DOMNode::lookupNamespaceURI() Method11PHP | DOMNode::lookupPrefix() Method12PHP | DOMNode::normalize() Method13PHP | DOMNode::appendChild() Method14PHP | DOMNode::cloneNode() Method15PHP | DOMNode::compareDocumentPosition() Method16PHP | DOMNode::getLineNo() Method17PHP | DOMNode::hasAttributes() Method18PHP | DOMNode::isSameNode() Method19PHP | DOMNode::isDefaultNamespace() Method20PHP | DOMNode::lookupNamespaceURI() Method21PHP | DOMNode::lookupPrefix() Method22PHP | DOMNode::normalize() Method23PHP | DOMNode::removeChild() Method24PHP | DOMNode::replaceChild() Method25PHP | DOMNode::C14N() Method26PHP | DOMNode::C14NFile() Method27PHP | DOMNode::isSupported() Method28PHP | DOMNode::isSameNode() Method29PHP | DOMNode::isDefaultNamespace() Method
Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.
You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.
Execute automation tests with seek on a cloud-based Grid of 3000+ real browsers and operating systems for both web and mobile applications.
Test now for FreeGet 100 minutes of automation test minutes FREE!!