slider.cpp
algorithm
ftxui/component/component_options.hpp
ftxui/dom/direction.hpp
string
utility
ftxui/component/captured_mouse.hpp
ftxui/component/component.hpp
ftxui/component/component_base.hpp
ftxui/component/event.hpp
ftxui/component/mouse.hpp
ftxui/component/screen_interactive.hpp
ftxui/dom/elements.hpp
ftxui/screen/box.hpp
ftxui/screen/color.hpp
ftxui/util/ref.hpp
ftxui/component/animation.hpp
ftxui/component/captured_mouse.hpp
ftxui/component/component.hpp
ftxui/component/component_base.hpp
ftxui/component/component_options.hpp
ftxui/component/event.hpp
ftxui/component/mouse.hpp
ftxui/component/receiver.hpp
ftxui/component/screen_interactive.hpp
ftxui/component/task.hpp
ftxui/dom/canvas.hpp
ftxui/dom/deprecated.hpp
ftxui/dom/direction.hpp
ftxui/dom/elements.hpp
ftxui/dom/flexbox_config.hpp
ftxui/dom/linear_gradient.hpp
ftxui/dom/node.hpp
ftxui/dom/requirement.hpp
ftxui/dom/selection.hpp
ftxui/screen/box.hpp
ftxui/screen/color.hpp
ftxui/screen/image.hpp
ftxui/screen/pixel.hpp
ftxui/screen/screen.hpp
ftxui/screen/string.hpp
ftxui/screen/terminal.hpp
ftxui/util/autoreset.hpp
ftxui/util/ref.hpp
src/ftxui/component/slider.cpp
algorithm
atomic
chrono
condition_variable
cstddef
cstdint
ftxui/dom/take_any_args.hpp
functional
memory
mutex
optional
queue
sstream
string
thread
unordered_map
utility
variant
vector
ftxui

    //Copyright2020ArthurSonzogni.Allrightsreserved.
    //UseofthissourcecodeisgovernedbytheMITlicensethatcanbefoundin
    //theLICENSEfile.
    #include<algorithm>//formax,min
    #include<ftxui/component/component_options.hpp>//forSliderOption
    #include<ftxui/dom/direction.hpp>//forDirection,Direction::Down,Direction::Left,Direction::Right,Direction::Up
    #include<string>//forallocator
    #include<utility>//formove

    #include"ftxui/component/captured_mouse.hpp"//forCapturedMouse
    #include"ftxui/component/component.hpp"//forMake,Slider
    #include"ftxui/component/component_base.hpp"//forComponentBase
    #include"ftxui/component/event.hpp"//forEvent,Event::ArrowDown,Event::ArrowLeft,Event::ArrowRight,Event::ArrowUp
    #include"ftxui/component/mouse.hpp"//forMouse,Mouse::Left,Mouse::Pressed,Mouse::Released
    #include"ftxui/component/screen_interactive.hpp"//forComponent
    #include"ftxui/dom/elements.hpp"//foroperator|,text,Element,xflex,hbox,color,underlined,reflect,Decorator,dim,vcenter,focus,nothing,select,yflex,gaugeDirection
    #include"ftxui/screen/box.hpp"//forBox
    #include"ftxui/screen/color.hpp"//forColor,Color::GrayDark,Color::White
    #include"ftxui/util/ref.hpp"//forConstRef,Ref,ConstStringRef

    namespaceftxui{

    namespace{
    DecoratorflexDirection(Directiondirection){
    switch(direction){
    caseDirection::Up:
    caseDirection::Down:
    returnyflex;
    caseDirection::Left:
    caseDirection::Right:
    returnxflex;
    }
    returnxflex;//NOT_REACHED()
    }

    template<classT>
    classSliderBase:publicSliderOption<T>,publicComponentBase{
    public:
    explicitSliderBase(SliderOption<T>options):SliderOption<T>(options){}

    ElementOnRender()override{
    autogauge_color=
    Focused()?color(this->color_active):color(this->color_inactive);
    constfloatpercent=
    float(this->value()-this->min())/float(this->max()-this->min());
    returngaugeDirection(percent,this->direction)|
    flexDirection(this->direction)|reflect(gauge_box_)|gauge_color;
    }

    voidOnLeft(){
    switch(this->direction){
    caseDirection::Right:
    this->value()-=this->increment();
    break;
    caseDirection::Left:
    this->value()+=this->increment();
    break;
    caseDirection::Up:
    caseDirection::Down:
    break;
    }
    }

    voidOnRight(){
    switch(this->direction){
    caseDirection::Right:
    this->value()+=this->increment();
    break;
    caseDirection::Left:
    this->value()-=this->increment();
    break;
    caseDirection::Up:
    caseDirection::Down:
    break;
    }
    }

    voidOnUp(){
    switch(this->direction){
    caseDirection::Up:
    this->value()-=this->increment();
    break;
    caseDirection::Down:
    this->value()+=this->increment();
    break;
    caseDirection::Left:
    caseDirection::Right:
    break;
    }
    }

    voidOnDown(){
    switch(this->direction){
    caseDirection::Down:
    this->value()+=this->increment();
    break;
    caseDirection::Up:
    this->value()-=this->increment();
    break;
    caseDirection::Left:
    caseDirection::Right:
    break;
    }
    }

    boolOnEvent(Eventevent)final{
    if(event.is_mouse()){
    returnOnMouseEvent(event);
    }

    Told_value=this->value();
    if(event==Event::ArrowLeft||event==Event::Character('h')){
    OnLeft();
    }
    if(event==Event::ArrowRight||event==Event::Character('l')){
    OnRight();
    }
    if(event==Event::ArrowUp||event==Event::Character('k')){
    OnDown();
    }
    if(event==Event::ArrowDown||event==Event::Character('j')){
    OnUp();
    }

    this->value()=std::max(this->min(),std::min(this->max(),this->value()));
    if(old_value!=this->value()){
    if(this->on_change){
    this->on_change();
    }
    returntrue;
    }

    returnComponentBase::OnEvent(event);
    }

    boolOnCapturedMouseEvent(Eventevent){
    if(event.mouse().motion==Mouse::Released){
    captured_mouse_=nullptr;
    returntrue;
    }

    Told_value=this->value();
    switch(this->direction){
    caseDirection::Right:{
    this->value()=this->min()+(event.mouse().x-gauge_box_.x_min)*
    (this->max()-this->min())/
    (gauge_box_.x_max-gauge_box_.x_min);

    break;
    }
    caseDirection::Left:{
    this->value()=this->max()-(event.mouse().x-gauge_box_.x_min)*
    (this->max()-this->min())/
    (gauge_box_.x_max-gauge_box_.x_min);
    break;
    }
    caseDirection::Down:{
    this->value()=this->min()+(event.mouse().y-gauge_box_.y_min)*
    (this->max()-this->min())/
    (gauge_box_.y_max-gauge_box_.y_min);
    break;
    }
    caseDirection::Up:{
    this->value()=this->max()-(event.mouse().y-gauge_box_.y_min)*
    (this->max()-this->min())/
    (gauge_box_.y_max-gauge_box_.y_min);
    break;
    }
    }

    this->value()=std::max(this->min(),std::min(this->max(),this->value()));

    if(old_value!=this->value()&&this->on_change){
    this->on_change();
    }
    returntrue;
    }

    boolOnMouseEvent(Eventevent){
    if(captured_mouse_){
    returnOnCapturedMouseEvent(event);
    }

    if(event.mouse().button!=Mouse::Left){
    returnfalse;
    }
    if(event.mouse().motion!=Mouse::Pressed){
    returnfalse;
    }

    if(!gauge_box_.Contain(event.mouse().x,event.mouse().y)){
    returnfalse;
    }

    captured_mouse_=CaptureMouse(event);

    if(captured_mouse_){
    TakeFocus();
    returnOnCapturedMouseEvent(event);
    }

    returnfalse;
    }

    boolFocusable()constfinal{returntrue;}

    private:
    Boxgauge_box_;
    CapturedMousecaptured_mouse_;
    };

    classSliderWithLabel:publicComponentBase{
    public:
    SliderWithLabel(ConstStringReflabel,Componentinner)
    :label_(std::move(label)){
    Add(std::move(inner));
    SetActiveChild(ChildAt(0));
    }

    private:
    boolOnEvent(Eventevent)final{
    if(ComponentBase::OnEvent(event)){
    returntrue;
    }

    if(!event.is_mouse()){
    returnfalse;
    }

    mouse_hover_=box_.Contain(event.mouse().x,event.mouse().y);

    if(!mouse_hover_){
    returnfalse;
    }

    if(!CaptureMouse(event)){
    returnfalse;
    }

    returntrue;
    }

    ElementOnRender()override{
    autogauge_color=(Focused()||mouse_hover_)?color(Color::White)
    :color(Color::GrayDark);
    autoelement=hbox({
    text(label_())|dim|vcenter,
    hbox({
    text("["),
    ComponentBase::Render()|underlined,
    text("]"),
    })|xflex,
    })|
    gauge_color|xflex|reflect(box_);

    element|=focus;
    returnelement;
    }

    ConstStringReflabel_;
    Boxbox_;
    boolmouse_hover_=false;
    };

    }//namespace

    ///@briefAnhorizontalslider.
    ///@paramlabelThenameoftheslider.
    ///@paramvalueThecurrentvalueoftheslider.
    ///@paramminTheminimumvalue.
    ///@parammaxThemaximumvalue.
    ///@paramincrementTheincrementwhenusedbythecursor.
    ///@ingroupcomponent
    ///
    ///###Example
    ///
    ///```cpp
    ///autoscreen=ScreenInteractive::TerminalOutput();
    ///intvalue=50;
    ///autoslider=Slider("Value:",&value,0,100,1);
    ///screen.Loop(slider);
    ///```
    ///
    ///###Output
    ///
    ///```bash
    ///Value:[██████████████████████████]
    ///```
    ComponentSlider(ConstStringReflabel,
    Ref<int>value,
    ConstRef<int>min,
    ConstRef<int>max,
    ConstRef<int>increment){
    SliderOption<int>option;
    option.value=value;
    option.min=min;
    option.max=max;
    option.increment=increment;
    autoslider=Make<SliderBase<int>>(option);
    returnMake<SliderWithLabel>(std::move(label),slider);
    }

    ComponentSlider(ConstStringReflabel,
    Ref<float>value,
    ConstRef<float>min,
    ConstRef<float>max,
    ConstRef<float>increment){
    SliderOption<float>option;
    option.value=value;
    option.min=min;
    option.max=max;
    option.increment=increment;
    autoslider=Make<SliderBase<float>>(option);
    returnMake<SliderWithLabel>(std::move(label),slider);
    }
    ComponentSlider(ConstStringReflabel,
    Ref<long>value,
    ConstRef<long>min,
    ConstRef<long>max,
    ConstRef<long>increment){
    SliderOption<long>option;
    option.value=value;
    option.min=min;
    option.max=max;
    option.increment=increment;
    autoslider=Make<SliderBase<long>>(option);
    returnMake<SliderWithLabel>(std::move(label),slider);
    }

    ///@briefAsliderinanydirection.
    ///@paramoptionsTheoptions
    ///###Example
    ///
    ///```cpp
    ///autoscreen=ScreenInteractive::TerminalOutput();
    ///intvalue=50;
    ///autoslider=Slider({
    ///.value=&value,
    ///.min=0,
    ///.max=100,
    ///.increment=20,
    ///});
    ///screen.Loop(slider);
    ///```
    template<typenameT>
    ComponentSlider(SliderOption<T>options){
    returnMake<SliderBase<T>>(options);
    }

    templateComponentSlider(SliderOption<int8_t>);
    templateComponentSlider(SliderOption<int16_t>);
    templateComponentSlider(SliderOption<int32_t>);
    templateComponentSlider(SliderOption<int64_t>);

    templateComponentSlider(SliderOption<uint8_t>);
    templateComponentSlider(SliderOption<uint16_t>);
    templateComponentSlider(SliderOption<uint32_t>);
    templateComponentSlider(SliderOption<uint64_t>);

    templateComponentSlider(SliderOption<float>);
    templateComponentSlider(SliderOption<double>);

    }//namespaceftxui