mirror of
https://github.com/ArthurSonzogni/FTXUI.git
synced 2025-09-18 17:18:08 +08:00
Animation (#355)
This commit is contained in:
@@ -1,10 +1,11 @@
|
||||
#include <memory> // for make_shared
|
||||
#include <memory> // for make_shared, allocator
|
||||
#include <string> // for string
|
||||
|
||||
#include "ftxui/dom/elements.hpp" // for Element, separator
|
||||
#include "ftxui/dom/node.hpp" // for Node
|
||||
#include "ftxui/dom/elements.hpp" // for Element, BorderStyle, LIGHT, separator, DOUBLE, EMPTY, HEAVY, separatorCharacter, separatorDouble, separatorEmpty, separatorHSelector, separatorHeavy, separatorLight, separatorStyled, separatorVSelector
|
||||
#include "ftxui/dom/node.hpp" // for Node
|
||||
#include "ftxui/dom/requirement.hpp" // for Requirement
|
||||
#include "ftxui/screen/box.hpp" // for Box
|
||||
#include "ftxui/screen/color.hpp" // for Color
|
||||
#include "ftxui/screen/screen.hpp" // for Pixel, Screen
|
||||
|
||||
namespace ftxui {
|
||||
@@ -369,6 +370,142 @@ Element separator(Pixel pixel) {
|
||||
return std::make_shared<SeparatorWithPixel>(pixel);
|
||||
}
|
||||
|
||||
/// @brief Draw an horizontal bar, with the area in between left/right colored
|
||||
/// differently.
|
||||
/// @param left the left limit of the active area.
|
||||
/// @param right the right limit of the active area.
|
||||
/// @param selected_color the color of the selected area.
|
||||
/// @param unselected_color the color of the unselected area.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```cpp
|
||||
/// Element document = separatorHSelector(2,5, Color::White, Color::Blue);
|
||||
/// ```
|
||||
Element separatorHSelector(float left,
|
||||
float right,
|
||||
Color selected_color,
|
||||
Color unselected_color) {
|
||||
class Impl : public Node {
|
||||
public:
|
||||
Impl(float left, float right, Color selected_color, Color unselected_color)
|
||||
: left_(left),
|
||||
right_(right),
|
||||
selected_color_(selected_color),
|
||||
unselected_color_(unselected_color) {}
|
||||
void ComputeRequirement() override {
|
||||
requirement_.min_x = 1;
|
||||
requirement_.min_y = 1;
|
||||
}
|
||||
|
||||
void Render(Screen& screen) override {
|
||||
if (box_.y_max < box_.y_min)
|
||||
return;
|
||||
|
||||
// This are the two location with an empty demi-cell.
|
||||
int demi_cell_left = left_ * 2 - 1;
|
||||
int demi_cell_right = right_ * 2 + 2;
|
||||
|
||||
int y = box_.y_min;
|
||||
for (int x = box_.x_min; x <= box_.x_max; ++x) {
|
||||
Pixel& pixel = screen.PixelAt(x, y);
|
||||
|
||||
int a = (x - box_.x_min) * 2;
|
||||
int b = a + 1;
|
||||
bool a_empty = demi_cell_left == a || demi_cell_right == a;
|
||||
bool b_empty = demi_cell_left == b || demi_cell_right == b;
|
||||
|
||||
if (!a_empty && !b_empty) {
|
||||
pixel.character = "─";
|
||||
pixel.automerge = true;
|
||||
} else {
|
||||
pixel.character = a_empty ? "╶" : "╴";
|
||||
pixel.automerge = false;
|
||||
}
|
||||
|
||||
if (demi_cell_left <= a && b <= demi_cell_right)
|
||||
pixel.foreground_color = selected_color_;
|
||||
else
|
||||
pixel.foreground_color = unselected_color_;
|
||||
}
|
||||
}
|
||||
|
||||
float left_;
|
||||
float right_;
|
||||
Color selected_color_;
|
||||
Color unselected_color_;
|
||||
};
|
||||
return std::make_shared<Impl>(left, right, selected_color, unselected_color);
|
||||
}
|
||||
|
||||
/// @brief Draw an vertical bar, with the area in between up/downcolored
|
||||
/// differently.
|
||||
/// @param up the left limit of the active area.
|
||||
/// @param down the right limit of the active area.
|
||||
/// @param selected_color the color of the selected area.
|
||||
/// @param unselected_color the color of the unselected area.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```cpp
|
||||
/// Element document = separatorHSelector(2,5, Color::White, Color::Blue);
|
||||
/// ```
|
||||
Element separatorVSelector(float up,
|
||||
float down,
|
||||
Color selected_color,
|
||||
Color unselected_color) {
|
||||
class Impl : public Node {
|
||||
public:
|
||||
Impl(float up, float down, Color selected_color, Color unselected_color)
|
||||
: up_(up),
|
||||
down_(down),
|
||||
selected_color_(selected_color),
|
||||
unselected_color_(unselected_color) {}
|
||||
void ComputeRequirement() override {
|
||||
requirement_.min_x = 1;
|
||||
requirement_.min_y = 1;
|
||||
}
|
||||
|
||||
void Render(Screen& screen) override {
|
||||
if (box_.x_max < box_.x_min)
|
||||
return;
|
||||
|
||||
// This are the two location with an empty demi-cell.
|
||||
int demi_cell_up = up_ * 2 - 1;
|
||||
int demi_cell_down = down_ * 2 + 2;
|
||||
|
||||
int x = box_.x_min;
|
||||
for (int y = box_.y_min; y <= box_.y_max; ++y) {
|
||||
Pixel& pixel = screen.PixelAt(x, y);
|
||||
|
||||
int a = (y - box_.y_min) * 2;
|
||||
int b = a + 1;
|
||||
bool a_empty = demi_cell_up == a || demi_cell_down == a;
|
||||
bool b_empty = demi_cell_up == b || demi_cell_down == b;
|
||||
|
||||
if (!a_empty && !b_empty) {
|
||||
pixel.character = "│";
|
||||
pixel.automerge = true;
|
||||
} else {
|
||||
pixel.character = a_empty ? "╷" : "╵";
|
||||
pixel.automerge = false;
|
||||
}
|
||||
|
||||
if (demi_cell_up <= a && b <= demi_cell_down)
|
||||
pixel.foreground_color = selected_color_;
|
||||
else
|
||||
pixel.foreground_color = unselected_color_;
|
||||
}
|
||||
}
|
||||
|
||||
float up_;
|
||||
float down_;
|
||||
Color selected_color_;
|
||||
Color unselected_color_;
|
||||
};
|
||||
return std::make_shared<Impl>(up, down, selected_color, unselected_color);
|
||||
}
|
||||
|
||||
} // namespace ftxui
|
||||
|
||||
// Copyright 2020 Arthur Sonzogni. All rights reserved.
|
||||
|
Reference in New Issue
Block a user