Esempio n. 1
0
 /**
  * @brief Read a line, optionally setting the completer
  *
  * @param string $prompt The prompt to display
  * @param ReadlineAutoCompleter $completer The completer instance
  * @param boolean $autohistory Add command to history automatically (default is false)
  */
 static function read($prompt = null, ReadlineAutoCompleter $completer = null, $autohistory = false)
 {
     $oldcompleter = null;
     // If we got an autocompleter, assign it
     if ($completer) {
         // Save a copy of the old completer if any
         if (self::$completer && $completer !== self::$completer) {
             $oldcompleter = self::$completer;
         }
         // Assign and set up the proxy call
         self::$completer = $completer;
         readline_completion_function(array('Readline', '_rlAutoCompleteProxy'));
     }
     // Read the line
     $ret = readline($prompt);
     // Restore old completer (if any) and add the command to the history
     // if autohistory is enabled.
     if ($oldcompleter) {
         self::$completer = $oldcompleter;
     }
     if ($autohistory) {
         self::addHistory($ret);
     }
     return $ret;
 }
Esempio n. 2
0
 public function bindNewLine(Readline $self)
 {
     $self->addHistory($self->getLine());
     return $self::READ_BREAK;
 }
Esempio n. 3
0
 static function setAutoCompleteHandler($ac)
 {
     self::$autocompleter = $ac;
 }
Esempio n. 4
0
 /**
  * Tab binding.
  *
  * @access  public
  * @param   \Hoa\Console\Readline  $self    Self.
  * @return  int
  */
 public function _bindTab(Readline $self)
 {
     $autocompleter = $self->getAutocompleter();
     $state = static::STATE_CONTINUE | static::STATE_NO_ECHO;
     if (null === $autocompleter) {
         return $state;
     }
     $current = $self->getLineCurrent();
     $line = $self->getLine();
     if (0 === $current) {
         return $state;
     }
     $matches = preg_match_all('#' . $autocompleter->getWordDefinition() . '#u', $line, $words, PREG_OFFSET_CAPTURE);
     if (0 === $matches) {
         return $state;
     }
     for ($i = 0, $max = count($words[0]); $i < $max && $current > $words[0][$i][1]; ++$i) {
     }
     $word = $words[0][$i - 1];
     if ('' === trim($word[0])) {
         return $state;
     }
     $prefix = mb_substr($word[0], 0, $current - $word[1]);
     $solution = $autocompleter->complete($prefix);
     $length = mb_strlen($prefix);
     if (null === $solution) {
         return $state;
     }
     if (is_array($solution)) {
         $_solution = $solution;
         $count = count($_solution) - 1;
         $cWidth = 0;
         $window = \Hoa\Console\Window::getSize();
         $wWidth = $window['x'];
         $cursor = \Hoa\Console\Cursor::getPosition();
         array_walk($_solution, function (&$value) use(&$cWidth) {
             $handle = mb_strlen($value);
             if ($handle > $cWidth) {
                 $cWidth = $handle;
             }
             return;
         });
         array_walk($_solution, function (&$value) use(&$cWidth) {
             $handle = mb_strlen($value);
             if ($handle >= $cWidth) {
                 return;
             }
             $value .= str_repeat(' ', $cWidth - $handle);
             return;
         });
         $mColumns = (int) floor($wWidth / ($cWidth + 2));
         $mLines = (int) ceil(($count + 1) / $mColumns);
         --$mColumns;
         $i = 0;
         if (0 > $window['y'] - $cursor['y'] - $mLines) {
             \Hoa\Console\Window::scroll('↑', $mLines);
             \Hoa\Console\Cursor::move('↑', $mLines);
         }
         \Hoa\Console\Cursor::save();
         \Hoa\Console\Cursor::hide();
         \Hoa\Console\Cursor::move('↓ LEFT');
         \Hoa\Console\Cursor::clear('↓');
         foreach ($_solution as $j => $s) {
             echo "", $s, "";
             if ($i++ < $mColumns) {
                 echo '  ';
             } else {
                 $i = 0;
                 if (isset($_solution[$j + 1])) {
                     echo "\n";
                 }
             }
         }
         \Hoa\Console\Cursor::restore();
         \Hoa\Console\Cursor::show();
         ++$mColumns;
         $read = array(STDIN);
         $mColumn = -1;
         $mLine = -1;
         $coord = -1;
         $unselect = function () use(&$mColumn, &$mLine, &$coord, &$_solution, &$cWidth) {
             \Hoa\Console\Cursor::save();
             \Hoa\Console\Cursor::hide();
             \Hoa\Console\Cursor::move('↓ LEFT');
             \Hoa\Console\Cursor::move('→', $mColumn * ($cWidth + 2));
             \Hoa\Console\Cursor::move('↓', $mLine);
             echo "" . $_solution[$coord] . "";
             \Hoa\Console\Cursor::restore();
             \Hoa\Console\Cursor::show();
             return;
         };
         $select = function () use(&$mColumn, &$mLine, &$coord, &$_solution, &$cWidth) {
             \Hoa\Console\Cursor::save();
             \Hoa\Console\Cursor::hide();
             \Hoa\Console\Cursor::move('↓ LEFT');
             \Hoa\Console\Cursor::move('→', $mColumn * ($cWidth + 2));
             \Hoa\Console\Cursor::move('↓', $mLine);
             echo "" . $_solution[$coord] . "";
             \Hoa\Console\Cursor::restore();
             \Hoa\Console\Cursor::show();
             return;
         };
         $init = function () use(&$mColumn, &$mLine, &$coord, &$select) {
             $mColumn = 0;
             $mLine = 0;
             $coord = 0;
             $select();
             return;
         };
         while (true) {
             @stream_select($read, $write, $except, 30, 0);
             if (empty($read)) {
                 $read = array(STDIN);
                 continue;
             }
             switch ($char = $self->_read()) {
                 case "":
                     if (-1 === $mColumn && -1 === $mLine) {
                         $init();
                         break;
                     }
                     $unselect();
                     $coord = max(0, $coord - $mColumns);
                     $mLine = (int) floor($coord / $mColumns);
                     $mColumn = $coord % $mColumns;
                     $select();
                     break;
                 case "":
                     if (-1 === $mColumn && -1 === $mLine) {
                         $init();
                         break;
                     }
                     $unselect();
                     $coord = min($count, $coord + $mColumns);
                     $mLine = (int) floor($coord / $mColumns);
                     $mColumn = $coord % $mColumns;
                     $select();
                     break;
                 case "\t":
                 case "":
                     if (-1 === $mColumn && -1 === $mLine) {
                         $init();
                         break;
                     }
                     $unselect();
                     $coord = min($count, $coord + 1);
                     $mLine = (int) floor($coord / $mColumns);
                     $mColumn = $coord % $mColumns;
                     $select();
                     break;
                 case "":
                     if (-1 === $mColumn && -1 === $mLine) {
                         $init();
                         break;
                     }
                     $unselect();
                     $coord = max(0, $coord - 1);
                     $mLine = (int) floor($coord / $mColumns);
                     $mColumn = $coord % $mColumns;
                     $select();
                     break;
                 case "\n":
                     if (-1 !== $mColumn && -1 !== $mLine) {
                         $tail = mb_substr($line, $current);
                         $current -= $length;
                         $self->setLine(mb_substr($line, 0, $current) . $solution[$coord] . $tail);
                         $self->setLineCurrent($current + mb_strlen($solution[$coord]));
                         \Hoa\Console\Cursor::move('←', $length);
                         echo $solution[$coord];
                         \Hoa\Console\Cursor::clear('→');
                         echo $tail;
                         \Hoa\Console\Cursor::move('←', mb_strlen($tail));
                     }
                 default:
                     $mColumn = -1;
                     $mLine = -1;
                     $coord = -1;
                     \Hoa\Console\Cursor::save();
                     \Hoa\Console\Cursor::move('↓ LEFT');
                     \Hoa\Console\Cursor::clear('↓');
                     \Hoa\Console\Cursor::restore();
                     if ("" !== $char && "\n" !== $char) {
                         $self->setBuffer($char);
                         return $self->_readLine($char);
                     }
                     break 2;
             }
         }
         return $state;
     }
     $tail = mb_substr($line, $current);
     $current -= $length;
     $self->setLine(mb_substr($line, 0, $current) . $solution . $tail);
     $self->setLineCurrent($current + mb_strlen($solution));
     \Hoa\Console\Cursor::move('←', $length);
     echo $solution;
     \Hoa\Console\Cursor::clear('→');
     echo $tail;
     \Hoa\Console\Cursor::move('←', mb_strlen($tail));
     return $state;
 }
Esempio n. 5
0
 protected function getWord(Readline $readline)
 {
     return $readline->getBuffer();
 }