代码之家  ›  专栏  ›  技术社区  ›  deadprogrammer

Php代码格式化程序/美化程序和Php美化程序[关闭]

  •  32
  • deadprogrammer  · 技术社区  · 16 年前

    14 回复  |  直到 6 年前
        1
  •  44
  •   grom    16 年前

    这是我最基本、最粗略的剧本:

    #!/usr/bin/php
    <?php
    class Token {
        public $type;
        public $contents;
    
        public function __construct($rawToken) {
            if (is_array($rawToken)) {
                $this->type = $rawToken[0];
                $this->contents = $rawToken[1];
            } else {
                $this->type = -1;
                $this->contents = $rawToken;
            }
        }
    }
    
    $file = $argv[1];
    $code = file_get_contents($file);
    
    $rawTokens = token_get_all($code);
    $tokens = array();
    foreach ($rawTokens as $rawToken) {
        $tokens[] = new Token($rawToken);
    }
    
    function skipWhitespace(&$tokens, &$i) {
        global $lineNo;
        $i++;
        $token = $tokens[$i];
        while ($token->type == T_WHITESPACE) {
            $lineNo += substr($token->contents, "\n");
            $i++;
            $token = $tokens[$i];
        }
    }
    
    function nextToken(&$j) {
        global $tokens, $i;
        $j = $i;
        do {
            $j++;
            $token = $tokens[$j];
        } while ($token->type == T_WHITESPACE);
        return $token;
    }
    
    $OPERATORS = array('=', '.', '+', '-', '*', '/', '%', '||', '&&', '+=', '-=', '*=', '/=', '.=', '%=', '==', '!=', '<=', '>=', '<', '>', '===', '!==');
    
    $IMPORT_STATEMENTS = array(T_REQUIRE, T_REQUIRE_ONCE, T_INCLUDE, T_INCLUDE_ONCE);
    
    $CONTROL_STRUCTURES = array(T_IF, T_ELSEIF, T_FOREACH, T_FOR, T_WHILE, T_SWITCH, T_ELSE);
    $WHITESPACE_BEFORE = array('?', '{', '=>');
    $WHITESPACE_AFTER = array(',', '?', '=>');
    
    foreach ($OPERATORS as $op) {
        $WHITESPACE_BEFORE[] = $op;
        $WHITESPACE_AFTER[] = $op;
    }
    
    $matchingTernary = false;
    
    // First pass - filter out unwanted tokens
    $filteredTokens = array();
    for ($i = 0, $n = count($tokens); $i < $n; $i++) {
        $token = $tokens[$i];
        if ($token->contents == '?') {
            $matchingTernary = true;
        }
        if (in_array($token->type, $IMPORT_STATEMENTS) && nextToken($j)->contents == '(') {
            $filteredTokens[] = $token;
            if ($tokens[$i + 1]->type != T_WHITESPACE) {
                $filteredTokens[] = new Token(array(T_WHITESPACE, ' '));
            }
            $i = $j;
            do {
                $i++;
                $token = $tokens[$i];
                if ($token->contents != ')') {
                    $filteredTokens[] = $token;
                }
            } while ($token->contents != ')');
        } elseif ($token->type == T_ELSE && nextToken($j)->type == T_IF) {
            $i = $j;
            $filteredTokens[] = new Token(array(T_ELSEIF, 'elseif'));
        } elseif ($token->contents == ':') {
            if ($matchingTernary) {
                $matchingTernary = false;
            } elseif ($tokens[$i - 1]->type == T_WHITESPACE) {
                array_pop($filteredTokens); // Remove whitespace before
            }
            $filteredTokens[] = $token;
        } else {
            $filteredTokens[] = $token;
        }
    }
    $tokens = $filteredTokens;
    
    function isAssocArrayVariable($offset = 0) {
        global $tokens, $i;
        $j = $i + $offset;
        return $tokens[$j]->type == T_VARIABLE &&
            $tokens[$j + 1]->contents == '[' &&
            $tokens[$j + 2]->type == T_STRING &&
            preg_match('/[a-z_]+/', $tokens[$j + 2]->contents) &&
            $tokens[$j + 3]->contents == ']';
    }
    
    // Second pass - add whitespace
    $matchingTernary = false;
    $doubleQuote = false;
    for ($i = 0, $n = count($tokens); $i < $n; $i++) {
        $token = $tokens[$i];
        if ($token->contents == '?') {
            $matchingTernary = true;
        }
        if ($token->contents == '"' && isAssocArrayVariable(1) && $tokens[$i + 5]->contents == '"') {
            /*
             * Handle case where the only thing quoted is the assoc array variable.
             * Eg. "$value[key]"
             */
            $quote = $tokens[$i++]->contents;
            $var = $tokens[$i++]->contents;
            $openSquareBracket = $tokens[$i++]->contents;
            $str = $tokens[$i++]->contents;
            $closeSquareBracket = $tokens[$i++]->contents;
            $quote = $tokens[$i]->contents;        
            echo $var . "['" . $str . "']";
            $doubleQuote = false;
            continue;
        }
        if ($token->contents == '"') {
            $doubleQuote = !$doubleQuote;
        }
        if ($doubleQuote && $token->contents == '"' && isAssocArrayVariable(1)) {
            // don't echo "
        } elseif ($doubleQuote && isAssocArrayVariable()) {
            if ($tokens[$i - 1]->contents != '"') {
                echo '" . ';
            }
            $var = $token->contents;
            $openSquareBracket = $tokens[++$i]->contents;
            $str = $tokens[++$i]->contents;
            $closeSquareBracket = $tokens[++$i]->contents;
            echo $var . "['" . $str . "']";
            if ($tokens[$i + 1]->contents != '"') {
                echo ' . "';
            } else {
                $i++; // process "
                $doubleQuote = false;
            }
        } elseif ($token->type == T_STRING && $tokens[$i - 1]->contents == '[' && $tokens[$i + 1]->contents == ']') {
            if (preg_match('/[a-z_]+/', $token->contents)) {
                echo "'" . $token->contents . "'";
            } else {
                echo $token->contents;
            }
        } elseif ($token->type == T_ENCAPSED_AND_WHITESPACE || $token->type == T_STRING) {
            echo $token->contents;
        } elseif ($token->contents == '-' && in_array($tokens[$i + 1]->type, array(T_LNUMBER, T_DNUMBER))) {
            echo '-';
        } elseif (in_array($token->type, $CONTROL_STRUCTURES)) {
            echo $token->contents;
            if ($tokens[$i + 1]->type != T_WHITESPACE) {
                echo ' ';
            }
        } elseif ($token->contents == '}' && in_array($tokens[$i + 1]->type, $CONTROL_STRUCTURES)) {
            echo '} ';
        } elseif ($token->contents == '=' && $tokens[$i + 1]->contents == '&') {
            if ($tokens[$i - 1]->type != T_WHITESPACE) {
                echo ' ';
            }
            $i++; // match &
            echo '=&';
            if ($tokens[$i + 1]->type != T_WHITESPACE) {
                echo ' ';          
            }
        } elseif ($token->contents == ':' && $matchingTernary) {
            $matchingTernary = false;
            if ($tokens[$i - 1]->type != T_WHITESPACE) {
                echo ' ';
            }
            echo ':';
            if ($tokens[$i + 1]->type != T_WHITESPACE) {
                echo ' ';
            }
        } elseif (in_array($token->contents, $WHITESPACE_BEFORE) && $tokens[$i - 1]->type != T_WHITESPACE &&
            in_array($token->contents, $WHITESPACE_AFTER) && $tokens[$i + 1]->type != T_WHITESPACE) {
            echo ' ' . $token->contents . ' ';
        } elseif (in_array($token->contents, $WHITESPACE_BEFORE) && $tokens[$i - 1]->type != T_WHITESPACE) {
            echo ' ' . $token->contents;
        } elseif (in_array($token->contents, $WHITESPACE_AFTER) && $tokens[$i + 1]->type != T_WHITESPACE) {
            echo $token->contents . ' ';
        } else {
            echo $token->contents;
        }
    }
    
        2
  •  15
  •   Chris    14 年前

    http://en.sourceforge.jp/projects/pdt-tools/

    ^^^将为您提供一个正确的CTRL+SHIFT+F Eclipse/Aptana PHP格式化程序,如Java。

    here 以获取安装帮助。

    eclipse php code formatter

        3
  •  13
  •   ConroyP    16 年前

    PHP Code Beautifier download page 不需要创建帐户。

    • 允许可视化处理文件的GUI版本。
    • 作为PHPEdit的集成工具。

    基本上,它会变成:

    if($code == BAD){$action = REWRITE;}else{$action = KEEP;}
    for($i=0; $i<10;$i++){while($j>0){$j++;doCall($i+$j);if($k){$k/=10;}}}
    

    if ($code == BAD) {
        $action = REWRITE;
    } else {
        $action = KEEP;
    }
    for($i = 0; $i < 10;$i++) {
        while ($j > 0) {
            $j++;
            doCall($i + $j);
            if ($k) {
                $k /= 10;
            }
        }
    }
    
        4
  •  6
  •   David Hedlund    14 年前

    有一个pear模块可以格式化您的代码。 PHP Beautifier

        5
  •  5
  •   Ian P    16 年前

    如果使用Zend开发环境,则可以使用缩进代码功能(Ctrl+Shift+F)。

        6
  •  5
  •   Stefan Brinkmann    12 年前

    使用NetBeans PHP并按alt+shift+F。

        7
  •  4
  •   micahwittman    16 年前
        8
  •  3
  •   Adam    16 年前
        10
  •  2
  •   Aaron    13 年前

    最简单的解决方案是只使用内置了此功能的IDE。如果您打算定期用PHP编写代码,只需放弃PHPStorm的60美元。你不会后悔的。

    http://www.jetbrains.com/phpstorm/

    它允许您在文件或目录级别使用简单的键盘快捷键以任意方式格式化代码,并具有无数其他强大功能。

        11
  •  1
  •   Ira Baxter    14 年前
        12
  •  0
  •   vaichidrewar    13 年前

    phpformatter.com 效果最好

    “这个免费的在线PHP格式化程序的设计目的是让您可以用自己喜欢的样式美化所有PHP脚本”

        13
  •  0
  •   user1501974    12 年前

    这是一个极好的问题。我有一个可以读取json并输出php、html和css的应用程序。我运行一个程序并生成几十(数百?)个文件。我希望这里的答案是有用的。

    我开始我的项目时使用了heredocs,特别的include文件,meta字符等,但很快就变得一团糟。我想要一个不需要框架或ide的独立解决方案。因此,我删除了所有的herdoc和其他垃圾,创建了一个通用的文本缓冲类,而不考虑格式问题。它可以是一条我所关心的线。对于html,我使用内置的tidy()。对于php,我使用 phpstylist

    UniversalIndent (2012年1月更新)在windows gui中。

    如果您使用的是windows,并且希望使用UniversalIndent尝试phpstylist,只需将php.exe目录添加到您的环境路径中即可。我用 ampps 因此,我的设置为c:\ampps\php。

    要找到一个好的固溶体并不容易。我还想听听其他人是如何对自动生成的php/html文件进行尽可能简单的批处理格式化的,以便于代码检查和归档的。

        14
  •  -1
  •   Aran    10 年前

    我尝试了上面的代码片段,但这对我来说也不起作用,缩进中仍然充满了空格和制表符,所有的空格和制表符都混在一起了。

    所以我也尝试过写一个简单的,这个只使用了所有的正则表达式,没有奇特的编译器魔法,所以它可能会破坏一些东西,并且仍然是测试版,正在各种混乱的代码上测试。界面目前也非常基本,但在接下来的几天内应该会有所改进。

    它是为MediaWiki的约定而硬连接的,但您可以非常轻松地修改它(我可能会在以后添加选项)。

    https://www.organicdesign.co.nz/Special:CodeTidy