Allow scheduling voice chats for up to 7 days.

This commit is contained in:
John Preston 2021-04-09 17:59:43 +04:00
parent 71c4cc9623
commit 4ecd1049b2
5 changed files with 78 additions and 46 deletions

View File

@ -134,13 +134,32 @@ void ScheduleGroupCallBox(
: tr::lng_group_call_schedule_notified_group)(
lt_duration,
duration->value());
auto descriptor = Ui::ChooseDateTimeBox(
box,
tr::lng_group_call_schedule_title(),
tr::lng_schedule_button(),
send,
base::unixtime::now() + kDefaultScheduleDuration,
std::move(description));
const auto now = QDateTime::currentDateTime();
const auto min = [] {
return base::unixtime::serialize(
QDateTime::currentDateTime().addSecs(12));
};
const auto max = [] {
return base::unixtime::serialize(
QDateTime(QDate::currentDate().addDays(8))) - 1;
};
// At least half an hour later, at zero minutes/seconds.
const auto schedule = QDateTime(
now.date(),
QTime(now.time().hour(), 0)
).addSecs(60 * 60 * (now.time().minute() < 30 ? 1 : 2));
auto descriptor = Ui::ChooseDateTimeBox(box, {
.title = tr::lng_group_call_schedule_title(),
.submit = tr::lng_schedule_button(),
.done = send,
.min = min,
.time = base::unixtime::serialize(schedule),
.max = max,
.description = std::move(description),
});
using namespace rpl::mappers;
*duration = rpl::combine(

View File

@ -76,14 +76,14 @@ void ScheduleBox(
box->closeBox();
copy(result);
};
auto descriptor = Ui::ChooseDateTimeBox(
box,
(type == SendMenu::Type::Reminder
auto descriptor = Ui::ChooseDateTimeBox(box, {
.title = (type == SendMenu::Type::Reminder
? tr::lng_remind_title()
: tr::lng_schedule_title()),
tr::lng_schedule_button(),
[=](TimeId result) { save(false, result); },
time);
.submit = tr::lng_schedule_button(),
.done = [=](TimeId result) { save(false, result); },
.time = time,
});
SendMenu::SetupMenuAndShortcuts(
descriptor.submit.data(),

View File

@ -50,11 +50,10 @@ QString DayString(const QDate &date) {
QString::number(date.day()));
}
QString TimeString(TimeId time) {
const auto parsed = base::unixtime::parse(time).time();
QString TimeString(QTime time) {
return QString("%1:%2"
).arg(parsed.hour()
).arg(parsed.minute(), 2, 10, QLatin1Char('0'));
).arg(time.hour()
).arg(time.minute(), 2, 10, QLatin1Char('0'));
}
int ProcessWheelEvent(not_null<QWheelEvent*> e) {
@ -569,36 +568,33 @@ void TimeInput::startBorderAnimation() {
ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
not_null<GenericBox*> box,
rpl::producer<QString> title,
rpl::producer<QString> submit,
Fn<void(TimeId)> done,
TimeId time,
rpl::producer<QString> description) {
ChooseDateTimeBoxArgs &&args) {
struct State {
rpl::variable<QDate> date;
not_null<InputField*> day;
not_null<TimeInput*> time;
not_null<FlatLabel*> at;
};
box->setTitle(std::move(title));
box->setTitle(std::move(args.title));
box->setWidth(st::boxWideWidth);
const auto content = box->addRow(
object_ptr<FixedHeightWidget>(box, st::scheduleHeight));
if (description) {
if (args.description) {
box->addRow(object_ptr<FlatLabel>(
box,
std::move(description),
std::move(args.description),
st::boxLabel));
}
const auto parsed = base::unixtime::parse(args.time);
const auto state = box->lifetime().make_state<State>(State{
.date = base::unixtime::parse(time).date(),
.date = parsed.date(),
.day = CreateChild<InputField>(
content,
st::scheduleDateField),
.time = CreateChild<TimeInput>(
content,
TimeString(time)),
TimeString(parsed.time())),
.at = CreateChild<FlatLabel>(
content,
tr::lng_schedule_at(),
@ -611,8 +607,19 @@ ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
state->time->setFocusFast();
}, state->day->lifetime());
const auto minDate = QDate::currentDate();
const auto maxDate = minDate.addYears(1).addDays(-1);
const auto min = args.min ? args.min : [] {
return base::unixtime::now() + kMinimalSchedule;
};
const auto max = args.max ? args.max : [] {
return base::unixtime::serialize(
QDateTime::currentDateTime().addYears(1)) - 1;
};
const auto minDate = [=] {
return base::unixtime::parse(min()).date();
};
const auto maxDate = [=] {
return base::unixtime::parse(max()).date();
};
const auto &dayViewport = state->day->rawTextEdit()->viewport();
base::install_event_filter(dayViewport, [=](not_null<QEvent*> event) {
@ -623,7 +630,7 @@ ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
return base::EventFilterResult::Continue;
}
const auto d = state->date.current().addDays(direction);
state->date = std::clamp(d, minDate, maxDate);
state->date = std::clamp(d, minDate(), maxDate());
return base::EventFilterResult::Cancel;
}
return base::EventFilterResult::Continue;
@ -661,8 +668,8 @@ ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
(*calendar)->closeBox();
};
const auto finalize = [=](not_null<CalendarBox*> box) {
box->setMinDate(minDate);
box->setMaxDate(maxDate);
box->setMinDate(minDate());
box->setMaxDate(maxDate());
};
*calendar = box->getDelegate()->show(Box<CalendarBox>(
state->date.current(),
@ -686,12 +693,12 @@ ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
}
const auto result = base::unixtime::serialize(
QDateTime(state->date.current(), time));
if (result <= base::unixtime::now() + kMinimalSchedule) {
if (result < min() || result > max()) {
return 0;
}
return result;
};
const auto save = [=] {
const auto save = [=, done = args.done] {
if (const auto result = collect()) {
done(result);
} else {
@ -703,7 +710,7 @@ ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
auto result = ChooseDateTimeBoxDescriptor();
box->setFocusCallback([=] { state->time->setFocusFast(); });
result.submit = box->addButton(std::move(submit), save);
result.submit = box->addButton(std::move(args.submit), save);
result.collect = [=] {
if (const auto result = collect()) {
return result;

View File

@ -19,12 +19,18 @@ struct ChooseDateTimeBoxDescriptor {
rpl::producer<TimeId> values;
};
struct ChooseDateTimeBoxArgs {
rpl::producer<QString> title;
rpl::producer<QString> submit;
Fn<void(TimeId)> done;
Fn<TimeId()> min;
TimeId time = 0;
Fn<TimeId()> max;
rpl::producer<QString> description;
};
ChooseDateTimeBoxDescriptor ChooseDateTimeBox(
not_null<GenericBox*> box,
rpl::producer<QString> title,
rpl::producer<QString> submit,
Fn<void(TimeId)> done,
TimeId time,
rpl::producer<QString> description = nullptr);
ChooseDateTimeBoxArgs &&args);
} // namespace Ui

View File

@ -201,12 +201,12 @@ void EditInviteLinkBox(
: (state->expireValue < 0)
? (now - state->expireValue)
: (now + kDay);
ChooseDateTimeBox(
box,
tr::lng_group_invite_expire_after(),
tr::lng_settings_save(),
save,
time);
ChooseDateTimeBox(box, {
.title = tr::lng_group_invite_expire_after(),
.submit = tr::lng_settings_save(),
.done = save,
.time = time,
});
}));
});
usageGroup->setChangedCallback([=](int value) {