Skip to content

Commit

Permalink
Merge pull request #49 from php-school/dialouges
Browse files Browse the repository at this point in the history
Dialogue feature
  • Loading branch information
AydinHassan authored Oct 27, 2016
2 parents 0aa57bb + 8536871 commit 5472d7d
Show file tree
Hide file tree
Showing 21 changed files with 1,094 additions and 14 deletions.
62 changes: 62 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,12 @@ Check out the [examples](examples) directory and run them to check out what is p
##### Disabled Items & Submenus
<img width="600" alt="submenu" src="https://cloud.githubusercontent.com/assets/2174476/19047849/868fa8c0-899b-11e6-9004-811c8da6d435.png">

##### Flash Dialogue
<img width="600" alt="submenu" src="https://cloud.githubusercontent.com/assets/2817002/19786090/1f07dad6-9c94-11e6-91b0-c20ab2e6e27d.png">

##### Confirm Dialogue
<img width="600" alt="submenu" src="https://cloud.githubusercontent.com/assets/2817002/19786092/215d2dc2-9c94-11e6-910d-191b7b74f4d2.png">

### API

The `CliMenu` object is constructed via the Builder class
Expand Down Expand Up @@ -412,6 +418,62 @@ $menu = (new CliMenuBuilder)
$menu->open();
```

#### Dialogues

##### Flash

Show a one line message over the top of the menu. It has a separate style object which is colored by default different
to the menu. It can be modified to suit your own style. The dialogue is dismissed with any key press. In the example
below we change the background color on the flash to green.

```php
use PhpSchool\CliMenu\CliMenu;
use PhpSchool\CliMenu\CliMenuBuilder;

$itemCallable = function (CliMenu $menu) {
$flash = $menu->flash("PHP School FTW!!");
$flash->getStyle()->setBg('green');
$flash->display();
};

$menu = (new CliMenuBuilder)
->setTitle('Basic CLI Menu')
->addItem('First Item', $itemCallable)
->addItem('Second Item', $itemCallable)
->addItem('Third Item', $itemCallable)
->addLineBreak('-')
->build();

$menu->open();
```

##### Confirm

Prompts are very similar to flashes except that a button is shown which has to be selected to dismiss them. The button
text can be customised.

```php
use PhpSchool\CliMenu\CliMenu;
use PhpSchool\CliMenu\CliMenuBuilder;

require_once(__DIR__ . '/../vendor/autoload.php');

$itemCallable = function (CliMenu $menu) {
$menu->confirm('PHP School FTW!')
->display('OK!');
};

$menu = (new CliMenuBuilder)
->setTitle('Basic CLI Menu')
->addItem('First Item', $itemCallable)
->addItem('Second Item', $itemCallable)
->addItem('Third Item', $itemCallable)
->addLineBreak('-')
->build();

$menu->open();
```

---

Once you get going you might just end up with something that looks a little like this...
Expand Down
21 changes: 21 additions & 0 deletions examples/confirm.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
<?php

use PhpSchool\CliMenu\CliMenu;
use PhpSchool\CliMenu\CliMenuBuilder;

require_once(__DIR__ . '/../vendor/autoload.php');

$itemCallable = function (CliMenu $menu) {
$menu->confirm('PHP School FTW!')
->display('OK');
};

$menu = (new CliMenuBuilder)
->setTitle('Basic CLI Menu')
->addItem('First Item', $itemCallable)
->addItem('Second Item', $itemCallable)
->addItem('Third Item', $itemCallable)
->addLineBreak('-')
->build();

$menu->open();
22 changes: 22 additions & 0 deletions examples/flash.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<?php

use PhpSchool\CliMenu\CliMenu;
use PhpSchool\CliMenu\CliMenuBuilder;

require_once(__DIR__ . '/../vendor/autoload.php');

$itemCallable = function (CliMenu $menu) {
$flash = $menu->flash("PHP School FTW!!");
$flash->getStyle()->setBg('green');
$flash->display();
};

$menu = (new CliMenuBuilder)
->setTitle('Basic CLI Menu')
->addItem('First Item', $itemCallable)
->addItem('Second Item', $itemCallable)
->addItem('Third Item', $itemCallable)
->addLineBreak('-')
->build();

$menu->open();
81 changes: 67 additions & 14 deletions src/CliMenu.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
use PhpSchool\CliMenu\MenuItem\LineBreakItem;
use PhpSchool\CliMenu\MenuItem\MenuItemInterface;
use PhpSchool\CliMenu\MenuItem\StaticItem;
use PhpSchool\CliMenu\Dialogue\Confirm;
use PhpSchool\CliMenu\Dialogue\Flash;
use PhpSchool\CliMenu\Terminal\TerminalFactory;
use PhpSchool\CliMenu\Terminal\TerminalInterface;
use PhpSchool\CliMenu\Util\StringUtil as s;
Expand Down Expand Up @@ -55,6 +57,11 @@ class CliMenu
*/
protected $parent;

/**
* @var Frame|null
*/
private $currentFrame;

/**
* @param string $title
* @param array $items
Expand Down Expand Up @@ -258,28 +265,37 @@ protected function draw()
$this->terminal->clean();
$this->terminal->moveCursorToTop();

echo "\n\n";
$frame = new Frame;

$frame->newLine(2);

if (is_string($this->title)) {
$this->drawMenuItem(new LineBreakItem());
$this->drawMenuItem(new StaticItem($this->title));
$this->drawMenuItem(new LineBreakItem($this->style->getTitleSeparator()));
$frame->addRows($this->drawMenuItem(new LineBreakItem()));
$frame->addRows($this->drawMenuItem(new StaticItem($this->title)));
$frame->addRows($this->drawMenuItem(new LineBreakItem($this->style->getTitleSeparator())));
}

array_map(function ($item, $index) {
$this->drawMenuItem($item, $index === $this->selectedItem);
array_map(function ($item, $index) use ($frame) {
$frame->addRows($this->drawMenuItem($item, $index === $this->selectedItem));
}, $this->items, array_keys($this->items));

$this->drawMenuItem(new LineBreakItem());
$frame->addRows($this->drawMenuItem(new LineBreakItem()));

$frame->newLine(2);

foreach ($frame->getRows() as $row) {
echo $row;
}

echo "\n\n";
$this->currentFrame = $frame;
}

/**
* Draw a menu item
*
* @param MenuItemInterface $item
* @param bool|false $selected
* @return array
*/
protected function drawMenuItem(MenuItemInterface $item, $selected = false)
{
Expand All @@ -293,9 +309,9 @@ protected function drawMenuItem(MenuItemInterface $item, $selected = false)
? $this->style->getSelectedUnsetCode()
: $this->style->getUnselectedUnsetCode();

foreach ($rows as $row) {
echo sprintf(
"%s%s%s%s%s%s%s",
return array_map(function ($row) use ($setColour, $unsetColour) {
return sprintf(
"%s%s%s%s%s%s%s\n\r",
str_repeat(' ', $this->style->getMargin()),
$setColour,
str_repeat(' ', $this->style->getPadding()),
Expand All @@ -304,9 +320,7 @@ protected function drawMenuItem(MenuItemInterface $item, $selected = false)
$unsetColour,
str_repeat(' ', $this->style->getMargin())
);

echo "\n\r";
}
}, $rows);
}

/**
Expand Down Expand Up @@ -379,4 +393,43 @@ public function getStyle()
{
return $this->style;
}

public function getCurrentFrame()
{
return $this->currentFrame;
}

/**
* @param string $text
* @return Flash
*/
public function flash($text)
{
if (strpos($text, "\n") !== false) {
throw new \InvalidArgumentException;
}

$style = (new MenuStyle($this->terminal))
->setBg('yellow')
->setFg('red');

return new Flash($this, $style, $this->terminal, $text);
}

/**
* @param string $text
* @return Confirm
*/
public function confirm($text)
{
if (strpos($text, "\n") !== false) {
throw new \InvalidArgumentException;
}

$style = (new MenuStyle($this->terminal))
->setBg('yellow')
->setFg('red');

return new Confirm($this, $style, $this->terminal, $text);
}
}
85 changes: 85 additions & 0 deletions src/Dialogue/Confirm.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
<?php

namespace PhpSchool\CliMenu\Dialogue;

/**
* @author Aydin Hassan <[email protected]>
*/
class Confirm extends Dialogue
{

/**
* Display confirmation with a button with the given text
*
* @param string $confirmText
*/
public function display($confirmText = 'OK')
{
$this->assertMenuOpen();

$this->terminal->moveCursorToRow($this->y);

$promptWidth = mb_strlen($this->text) + 4;

$this->emptyRow();

$this->write(sprintf(
"%s%s%s%s%s\n",
$this->style->getUnselectedSetCode(),
str_repeat(' ', $this->style->getPadding()),
$this->text,
str_repeat(' ', $this->style->getPadding()),
$this->style->getUnselectedUnsetCode()
));

$this->emptyRow();

$confirmText = sprintf(' < %s > ', $confirmText);
$leftFill = ($promptWidth / 2) - (mb_strlen($confirmText) / 2);

$this->write(sprintf(
'%s%s%s',
$this->style->getUnselectedSetCode(),
str_repeat(' ', $leftFill),
$this->style->getUnselectedSetCode()
));

$this->write(
sprintf(
'%s%s%s',
$this->style->getSelectedSetCode(),
$confirmText,
$this->style->getSelectedUnsetCode()
),
-1
);

$this->write(
sprintf(
"%s%s%s\n",
$this->style->getUnselectedSetCode(),
str_repeat(' ', ceil($promptWidth - $leftFill - mb_strlen($confirmText))),
$this->style->getSelectedUnsetCode()
),
-1
);

$this->write(sprintf(
"%s%s%s%s%s\n",
$this->style->getUnselectedSetCode(),
str_repeat(' ', $this->style->getPadding()),
str_repeat(' ', mb_strlen($this->text)),
str_repeat(' ', $this->style->getPadding()),
$this->style->getUnselectedUnsetCode()
));

$this->terminal->moveCursorToTop();
$input = $this->terminal->getKeyedInput();

while ($input !== 'enter') {
$input = $this->terminal->getKeyedInput();
}

$this->parentMenu->redraw();
}
}
Loading

0 comments on commit 5472d7d

Please sign in to comment.