Start the gauge widget.

This commit is contained in:
Arthur Sonzogni
2018-09-19 21:52:25 +02:00
parent 49aeaa49c5
commit e577d67f2a
17 changed files with 211 additions and 12 deletions

View File

@@ -6,8 +6,11 @@ add_library(ftxui
src/ftxui/core/dom/flex.cpp
src/ftxui/core/dom/hbox.cpp
src/ftxui/core/dom/node.cpp
src/ftxui/core/dom/separator.cpp
src/ftxui/core/dom/text.cpp
src/ftxui/core/dom/centered.cpp
src/ftxui/core/dom/vbox.cpp
src/ftxui/core/dom/gauge.cpp
src/ftxui/core/screen.cpp
src/ftxui/core/terminal.cpp
src/ftxui/util/string.cpp

View File

@@ -7,17 +7,29 @@
namespace ftxui {
namespace dom {
using Child = std::unique_ptr<Node>;
using Element = std::unique_ptr<Node>;
using Children = std::vector<std::unique_ptr<Node>>;
// --- Layout ----
std::unique_ptr<Node> vbox(Children);
std::unique_ptr<Node> hbox(Children);
std::unique_ptr<Node> text(std::wstring text);
std::unique_ptr<Node> flex();
std::unique_ptr<Node> flex(Element);
// --- Widget --
std::unique_ptr<Node> text(std::wstring text);
std::unique_ptr<Node> separator();
std::unique_ptr<Node> gauge(float ratio);
// --- Decorator ---
std::unique_ptr<Node> hcenter(Element);
std::unique_ptr<Node> vcenter(Element);
std::unique_ptr<Node> center(Element);
template <class... Args>
std::vector<Child> unpack(Args... args) {
std::vector<Child> vec;
std::vector<Element> unpack(Args... args) {
std::vector<Element> vec;
(vec.push_back(std::forward<Args>(args)), ...);
return vec;
}

View File

@@ -3,8 +3,12 @@
#include <string>
#include <vector>
#include <memory>
namespace ftxui {
namespace dom {
class Node;
}
class Screen {
public:
@@ -16,6 +20,7 @@ class Screen {
size_t dimy() { return dimy_;}
static Screen WholeTerminal();
static Screen TerminalOutput(std::unique_ptr<dom::Node>& element);
private:
size_t dimx_;

View File

@@ -0,0 +1,20 @@
#include "ftxui/core/dom/node.hpp"
#include "ftxui/core/dom/elements.hpp"
namespace ftxui {
namespace dom {
std::unique_ptr<Node> hcenter(Element child) {
return hbox(flex(), std::move(child), flex());
}
std::unique_ptr<Node> vcenter(Element child) {
return vbox(flex(), std::move(child), flex());
}
std::unique_ptr<Node> center(Element child) {
return hcenter(vcenter(std::move(child)));
}
} // namespace dom
} // namespace ftxui

View File

@@ -1,4 +1,5 @@
#include "ftxui/core/dom/node.hpp"
#include "ftxui/core/dom/elements.hpp"
namespace ftxui {
namespace dom {
@@ -6,18 +7,33 @@ namespace dom {
class Flex : public Node {
public:
Flex() {}
Flex(Element child) : Node(unpack(std::move(child))) {}
~Flex() override {}
void ComputeRequirement() {
requirement_.min.x = 0;
requirement_.min.y = 0;
if (!children.empty()) {
children[0]->ComputeRequirement();
requirement_ = children[0]->requirement();
}
requirement_.flex.x = 1;
requirement_.flex.y = 1;
}
void SetBox(Box box) override {
if (children.empty())
return;
children[0]->SetBox(box);
}
};
std::unique_ptr<Node> flex() {
return std::make_unique<Flex>();
}
std::unique_ptr<Node> flex(Element child) {
return std::make_unique<Flex>(std::move(child));
}
}; // namespace dom
}; // namespace ftxui

View File

@@ -0,0 +1,32 @@
#include "ftxui/core/dom/node.hpp"
#include "ftxui/core/dom/elements.hpp"
namespace ftxui {
namespace dom {
class Gauge : public Node {
public:
Gauge(float progress) : progress_(progress) {}
~Gauge() {}
void ComputeRequirement() override {
requirement_.flex.x = 1;
requirement_.min.y = 1;
}
void Render(Screen& screen) override {
float y = box_.top;
int limit = box_.left + progress_ * (box_.right - box_.left);
for(int i = box_.left; i<=limit; ++i)
screen.at(i, y) = 'X';
}
private:
float progress_;
};
std::unique_ptr<Node> gauge(float progress) {
return std::make_unique<Gauge>(progress);
}
}; // namespace dom
}; // namespace ftxui

View File

@@ -0,0 +1,38 @@
#include "ftxui/core/dom/node.hpp"
namespace ftxui {
namespace dom {
class Separator : public Node {
public:
Separator() {}
~Separator() override {}
void ComputeRequirement() override {
requirement_.min.x = 1;
requirement_.min.y = 1;
}
void Render(Screen& screen) override {
bool is_column = (box_.right == box_.left);
bool is_line = (box_.top == box_.bottom);
wchar_t c = U'+';
if (is_line && !is_column)
c = U'';
else if (!is_line && is_column)
c = U'';
for (int y = box_.top; y <= box_.bottom; ++y) {
for (int x = box_.left; x <= box_.right; ++x) {
screen.at(x, y) = c;
}
}
}
};
std::unique_ptr<Node> separator() {
return std::make_unique<Separator>();
}
}; // namespace dom
}; // namespace ftxui

View File

@@ -35,7 +35,7 @@ class VBox : public Node {
int remaining_flex = flex_sum;
int remaining_extra_space = extra_space;
int y = box.left;
int y = box.top;
for (auto& child : children) {
if (y > box.right)
break;

View File

@@ -1,6 +1,7 @@
#include "ftxui/core/screen.hpp"
#include "ftxui/core/terminal.hpp"
#include "ftxui/util/string.hpp"
#include "ftxui/core/dom/node.hpp"
#include <sstream>
@@ -28,4 +29,10 @@ Screen Screen::WholeTerminal() {
return Screen(size.dimx, size.dimy);
}
Screen Screen::TerminalOutput(std::unique_ptr<dom::Node>& element) {
element->ComputeRequirement();
Terminal::Dimensions size = Terminal::Size();
return Screen(size.dimx, element->requirement().min.y);
}
}; // namespace ftxui