[widget] propagate new TimeVal on horizontal drag
This commit is contained in:
parent
590815e7dc
commit
9a2ce69dee
10 changed files with 198 additions and 72 deletions
|
@ -54,6 +54,20 @@ void EventWidget::set_span_recursive()
|
|||
static_cast<StateWidget*>(s.get())->set_y();
|
||||
}
|
||||
|
||||
void EventWidget::time_propagate(const TimeVal& t)
|
||||
{
|
||||
model.setDate(t);
|
||||
|
||||
// FIXME : call scneario->time_propagate with StateModel
|
||||
// is tehre a beter way to find connected intervals ?
|
||||
for (auto& s : bugui::container_widget::children)
|
||||
{
|
||||
scenario->time_propagate(
|
||||
static_cast<StateWidget*>(s.get())->get_model(),
|
||||
t);
|
||||
}
|
||||
}
|
||||
|
||||
void EventWidget::paint(bugui::painter& painter) const
|
||||
{
|
||||
if (!press && m_height == 0) return;
|
||||
|
|
|
@ -20,6 +20,7 @@ struct EventWidget final : ScenarioComponentSpec<
|
|||
|
||||
void set_y();
|
||||
void set_span_recursive();
|
||||
void time_propagate(const TimeVal& t);
|
||||
|
||||
private:
|
||||
void on_state_added(Scenario::StateModel& state);
|
||||
|
|
|
@ -1,7 +1,9 @@
|
|||
#include <widgets/container_widget.hpp>
|
||||
|
||||
#include <Scenario/Document/Interval/IntervalDurations.hpp>
|
||||
|
||||
#include "IntervalWidget.hpp"
|
||||
#include "Hardware/Widgets/ScenarioWidget.hpp"
|
||||
#include "ScenarioWidget.hpp"
|
||||
|
||||
namespace Hardware
|
||||
{
|
||||
|
@ -38,6 +40,19 @@ void IntervalWidget::change_next(const Scenario::StateModel& state)
|
|||
scenario->change_next(model);
|
||||
}
|
||||
|
||||
void IntervalWidget::time_propagate(const TimeVal& t)
|
||||
{
|
||||
model.translate(t - model.date());
|
||||
scenario->time_propagate(model,
|
||||
model.date() + model.duration.defaultDuration());
|
||||
}
|
||||
|
||||
void IntervalWidget::set_duration(const TimeVal& t)
|
||||
{
|
||||
Scenario::IntervalDurations::Algorithms::changeAllDurations(
|
||||
model, t - model.date());
|
||||
}
|
||||
|
||||
bool IntervalWidget::contains(int px, int py) const
|
||||
{
|
||||
// ignore first and last cell
|
||||
|
|
|
@ -19,6 +19,8 @@ struct IntervalWidget final : ScenarioComponentSpec<Scenario::IntervalModel>
|
|||
|
||||
void change_previous(const Scenario::StateModel& state);
|
||||
void change_next(const Scenario::StateModel& state);
|
||||
void time_propagate(const TimeVal& t);
|
||||
void set_duration(const TimeVal& t);
|
||||
|
||||
private:
|
||||
bool contains(int px, int py) const override;
|
||||
|
|
|
@ -65,14 +65,81 @@ void ScenarioWidget::on_time_sync_removed(const Scenario::TimeSyncModel& timeSyn
|
|||
|
||||
void ScenarioWidget::recursive_change(const Scenario::StateModel& state)
|
||||
{
|
||||
change_next(state);
|
||||
change_previous(state);
|
||||
change_next(state);
|
||||
}
|
||||
|
||||
void ScenarioWidget::recursive_change(const Scenario::IntervalModel& interval)
|
||||
{
|
||||
change_next(interval);
|
||||
change_previous(interval);
|
||||
change_next(interval);
|
||||
}
|
||||
|
||||
void ScenarioWidget::time_propagate(const Scenario::StateModel& state, const TimeVal& t)
|
||||
{
|
||||
auto interval{state.previousInterval()};
|
||||
|
||||
if (interval.has_value())
|
||||
{
|
||||
auto& v{interval.value()};
|
||||
|
||||
for (const auto& c : children)
|
||||
{
|
||||
ScenarioComponent<>* s{static_cast<ScenarioComponent<>*>(c.get())};
|
||||
|
||||
if (s->this_model(v))
|
||||
{
|
||||
static_cast<IntervalWidget*>(s)->set_duration(t);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
interval = state.nextInterval();
|
||||
|
||||
if (interval.has_value())
|
||||
{
|
||||
auto& v{interval.value()};
|
||||
|
||||
for (const auto& c : children)
|
||||
{
|
||||
ScenarioComponent<>* s{static_cast<ScenarioComponent<>*>(c.get())};
|
||||
|
||||
if (s->this_model(v))
|
||||
{
|
||||
static_cast<IntervalWidget*>(s)->time_propagate(t);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::time_propagate(const Scenario::IntervalModel& interval, const TimeVal& t)
|
||||
{
|
||||
auto& es{interval.endState()};
|
||||
|
||||
for (const auto& s : states_proxy)
|
||||
{
|
||||
if (s->this_model(es))
|
||||
{
|
||||
s->time_propagate(t);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_previous(const Scenario::IntervalModel& interval)
|
||||
{
|
||||
auto& es{interval.startState()};
|
||||
|
||||
for (const auto& s : states_proxy)
|
||||
{
|
||||
if (s->this_model(es))
|
||||
{
|
||||
s->change_previous(interval);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_next(const Scenario::IntervalModel& interval)
|
||||
|
@ -89,6 +156,27 @@ void ScenarioWidget::change_next(const Scenario::IntervalModel& interval)
|
|||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_previous(const Scenario::StateModel& state)
|
||||
{
|
||||
auto& pi{state.previousInterval()};
|
||||
|
||||
if (pi)
|
||||
{
|
||||
auto& v{pi.value()};
|
||||
|
||||
for (const auto& c : children)
|
||||
{
|
||||
ScenarioComponent<>* s{static_cast<ScenarioComponent<>*>(c.get())};
|
||||
|
||||
if (s->this_model(v))
|
||||
{
|
||||
static_cast<IntervalWidget*>(s)->change_previous(state);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_next(const Scenario::StateModel& state)
|
||||
{
|
||||
auto& ni{state.nextInterval()};
|
||||
|
@ -110,39 +198,4 @@ void ScenarioWidget::change_next(const Scenario::StateModel& state)
|
|||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_previous(const Scenario::IntervalModel& interval)
|
||||
{
|
||||
auto& es{interval.startState()};
|
||||
|
||||
for (const auto& s : states_proxy)
|
||||
{
|
||||
if (s->this_model(es))
|
||||
{
|
||||
s->change_previous(interval);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ScenarioWidget::change_previous(const Scenario::StateModel& state)
|
||||
{
|
||||
auto& ni{state.previousInterval()};
|
||||
|
||||
if (ni)
|
||||
{
|
||||
auto& v{ni.value()};
|
||||
|
||||
for (const auto& c : children)
|
||||
{
|
||||
ScenarioComponent<>* s{static_cast<ScenarioComponent<>*>(c.get())};
|
||||
|
||||
if (s->this_model(v))
|
||||
{
|
||||
static_cast<IntervalWidget*>(s)->change_previous(state);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace Hardware
|
||||
|
|
|
@ -32,10 +32,13 @@ public:
|
|||
void recursive_change(const Scenario::IntervalModel& interval);
|
||||
|
||||
void change_previous(const Scenario::IntervalModel& interval);
|
||||
void change_previous(const Scenario::StateModel& state);
|
||||
void change_next(const Scenario::IntervalModel& interval);
|
||||
void change_previous(const Scenario::StateModel& state);
|
||||
void change_next(const Scenario::StateModel& state);
|
||||
|
||||
void time_propagate(const Scenario::StateModel& state, const TimeVal& t);
|
||||
void time_propagate(const Scenario::IntervalModel& interval, const TimeVal& t);
|
||||
|
||||
bool changing{false};
|
||||
|
||||
private:
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#include <Scenario/Document/State/StateModel.hpp>
|
||||
|
||||
#include "ScenarioWidget.hpp"
|
||||
#include "TimeSyncWidget.hpp"
|
||||
#include "EventWidget.hpp"
|
||||
#include "StateWidget.hpp"
|
||||
|
||||
|
@ -34,6 +35,24 @@ StateWidget::~StateWidget()
|
|||
scenario->remove_proxy(this);
|
||||
}
|
||||
|
||||
void StateWidget::set_absolute_y()
|
||||
{
|
||||
m_absolute_y = model.heightPercentage() * scenario->height();
|
||||
}
|
||||
|
||||
void StateWidget::set_y()
|
||||
{
|
||||
m_y = m_absolute_y -
|
||||
bugui::base_widget::parent->y() -
|
||||
bugui::base_widget::parent->get_parent()->y();
|
||||
}
|
||||
|
||||
void StateWidget::set_span_recursive()
|
||||
{
|
||||
static_cast<EventWidget*>(bugui::base_widget::parent)
|
||||
->set_span_recursive();
|
||||
}
|
||||
|
||||
void StateWidget::change_previous(const Scenario::IntervalModel& interval)
|
||||
{
|
||||
model.setHeightPercentage(interval.heightPercentage());
|
||||
|
@ -49,6 +68,13 @@ void StateWidget::change_next(const Scenario::IntervalModel& interval)
|
|||
scenario->change_next(model);
|
||||
}
|
||||
|
||||
void StateWidget::time_propagate(const TimeVal& t)
|
||||
{
|
||||
static_cast<TimeSyncWidget*>(
|
||||
bugui::base_widget::parent->get_parent())
|
||||
->time_propagate(t);
|
||||
}
|
||||
|
||||
void StateWidget::paint(bugui::painter& painter) const
|
||||
{
|
||||
const auto col{model.metadata().getColor().getBrush().color()};
|
||||
|
@ -79,38 +105,40 @@ void StateWidget::on_double_press(int x, int y)
|
|||
|
||||
void StateWidget::on_drag(int from_x, int from_y, int to_x, int to_y)
|
||||
{
|
||||
double new_height{model.heightPercentage() +
|
||||
to_y / static_cast<double>(scenario->height())};
|
||||
bool update{false};
|
||||
|
||||
// prevent dragging out of scenario
|
||||
if (new_height >= 0 && new_height <= 1)
|
||||
// handle vertical drag
|
||||
if (from_y != to_y)
|
||||
{
|
||||
double new_height{model.heightPercentage() +
|
||||
to_y / static_cast<double>(scenario->height())};
|
||||
|
||||
// prevent dragging out of scenario
|
||||
if (new_height >= 0 && new_height <= 1)
|
||||
{
|
||||
scenario->changing = true;
|
||||
model.setHeightPercentage(new_height);
|
||||
scenario->recursive_change(model);
|
||||
set_absolute_y();
|
||||
set_span_recursive();
|
||||
scenario->changing = false;
|
||||
update = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (from_x != to_x)
|
||||
{
|
||||
scenario->changing = true;
|
||||
model.setHeightPercentage(new_height);
|
||||
scenario->recursive_change(model);
|
||||
set_absolute_y();
|
||||
set_span_recursive();
|
||||
scenario->update();
|
||||
TimeSyncWidget* sync{static_cast<TimeSyncWidget*>(
|
||||
bugui::base_widget::parent->get_parent())};
|
||||
auto d{sync->get_model().date()};
|
||||
d.setMSecs(d.msec() + to_x * 1000);
|
||||
sync->time_propagate(d);
|
||||
scenario->changing = false;
|
||||
update = true;
|
||||
}
|
||||
}
|
||||
|
||||
void StateWidget::set_absolute_y()
|
||||
{
|
||||
m_absolute_y = model.heightPercentage() * scenario->height();
|
||||
}
|
||||
|
||||
void StateWidget::set_y()
|
||||
{
|
||||
m_y = m_absolute_y -
|
||||
bugui::base_widget::parent->y() -
|
||||
bugui::base_widget::parent->get_parent()->y();
|
||||
}
|
||||
|
||||
void StateWidget::set_span_recursive()
|
||||
{
|
||||
static_cast<EventWidget*>(bugui::base_widget::parent)
|
||||
->set_span_recursive();
|
||||
if (update) scenario->update();
|
||||
}
|
||||
|
||||
} // namespace Hardware
|
||||
|
|
|
@ -19,6 +19,7 @@ struct StateWidget final : ScenarioComponentSpec<Scenario::StateModel>
|
|||
void set_y();
|
||||
void change_previous(const Scenario::IntervalModel& interval);
|
||||
void change_next(const Scenario::IntervalModel& interval);
|
||||
void time_propagate(const TimeVal& t);
|
||||
|
||||
private:
|
||||
W_OBJECT(StateWidget)
|
||||
|
@ -36,6 +37,7 @@ private:
|
|||
void on_drag(int from_x, int from_y, int to_x, int to_y) override;
|
||||
|
||||
void set_absolute_y();
|
||||
|
||||
int m_absolute_y;
|
||||
int m_y;
|
||||
};
|
||||
|
|
|
@ -24,7 +24,12 @@ TimeSyncWidget::TimeSyncWidget(Scenario::TimeSyncModel& timeSync,
|
|||
connect(&model,
|
||||
&Scenario::TimeSyncModel::dateChanged,
|
||||
this,
|
||||
[scenario] (const TimeVal&) { scenario->update(); });
|
||||
[scenario] (const TimeVal&)
|
||||
{
|
||||
if (scenario->changing) return;
|
||||
|
||||
scenario->update();
|
||||
});
|
||||
}
|
||||
|
||||
TimeSyncWidget::~TimeSyncWidget()
|
||||
|
@ -58,6 +63,14 @@ void TimeSyncWidget::set_span()
|
|||
static_cast<EventWidget*>(e.get())->set_y();
|
||||
}
|
||||
|
||||
void TimeSyncWidget::time_propagate(const TimeVal& t)
|
||||
{
|
||||
model.setDate(t);
|
||||
|
||||
for (auto& s : bugui::container_widget::children)
|
||||
static_cast<EventWidget*>(s.get())->time_propagate(t);
|
||||
}
|
||||
|
||||
void TimeSyncWidget::on_state_added(Scenario::EventModel& event)
|
||||
{
|
||||
if (event.timeSync() != model.id()) return;
|
||||
|
@ -98,11 +111,6 @@ bool TimeSyncWidget::contains(int px, int py) const
|
|||
return false;
|
||||
}
|
||||
|
||||
void TimeSyncWidget::on_press(int x, int y, bool pressed)
|
||||
{
|
||||
press = pressed;
|
||||
}
|
||||
|
||||
} // namespace Hardware
|
||||
|
||||
#include <wobjectimpl.h>
|
||||
|
|
|
@ -23,6 +23,7 @@ struct TimeSyncWidget final : ScenarioComponentSpec<
|
|||
int height() const override { return m_height; }
|
||||
|
||||
void set_span();
|
||||
void time_propagate(const TimeVal& t);
|
||||
|
||||
private:
|
||||
W_OBJECT(TimeSyncWidget)
|
||||
|
@ -33,7 +34,6 @@ private:
|
|||
bool contains(int px, int py) const override;
|
||||
|
||||
void paint(bugui::painter& painter) const override;
|
||||
void on_press(int x, int y, bool pressed) override;
|
||||
|
||||
bool press{false};
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue