mirror of
https://github.com/telegramdesktop/tdesktop
synced 2024-12-28 09:32:56 +00:00
Fill all required fields in identity and address.
This commit is contained in:
parent
2790919733
commit
94bfd59b76
@ -1507,7 +1507,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
"lng_passport_request2" = "to sign you up for their services";
|
||||
"lng_passport_password_placeholder" = "Your password";
|
||||
"lng_passport_next" = "Next";
|
||||
"lng_passport_password_wrong" = "Wrong password";
|
||||
"lng_passport_password_wrong" = "The password you entered is not valid.";
|
||||
"lng_passport_header" = "Requested information";
|
||||
"lng_passport_identity_title" = "Identity document";
|
||||
"lng_passport_identity_description" = "Upload a scan of your passport or other ID";
|
||||
@ -1534,8 +1534,17 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
"lng_passport_choose_image" = "Choose scan image";
|
||||
"lng_passport_delete_scan_undo" = "Undo";
|
||||
"lng_passport_scan_uploaded" = "Uploaded on {date}";
|
||||
"lng_passport_first_name" = "First name";
|
||||
"lng_passport_last_name" = "Last name";
|
||||
"lng_passport_first_name" = "Name";
|
||||
"lng_passport_last_name" = "Surname";
|
||||
"lng_passport_birth_date" = "Date of birth";
|
||||
"lng_passport_gender" = "Gender";
|
||||
"lng_passport_country" = "Country";
|
||||
"lng_passport_document_number" = "Card Number";
|
||||
"lng_passport_expiry_date" = "Expiry date";
|
||||
"lng_passport_street" = "Street";
|
||||
"lng_passport_city" = "City";
|
||||
"lng_passport_state" = "State";
|
||||
"lng_passport_postcode" = "Postcode";
|
||||
|
||||
// Wnd specific
|
||||
|
||||
|
@ -8,12 +8,133 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
#include "passport/passport_panel_controller.h"
|
||||
|
||||
#include "lang/lang_keys.h"
|
||||
#include "passport/passport_panel_edit_identity.h"
|
||||
#include "passport/passport_panel_edit_document.h"
|
||||
#include "passport/passport_panel.h"
|
||||
#include "boxes/confirm_box.h"
|
||||
#include "layout.h"
|
||||
|
||||
namespace Passport {
|
||||
namespace {
|
||||
|
||||
PanelEditDocument::Scheme GetDocumentScheme(Scope::Type type) {
|
||||
using Scheme = PanelEditDocument::Scheme;
|
||||
|
||||
const auto DontValidate = nullptr;
|
||||
const auto NotEmptyValidate = [](const QString &value) {
|
||||
return !value.isEmpty();
|
||||
};
|
||||
const auto DateValidate = [](const QString &value) {
|
||||
return QRegularExpression(
|
||||
"^\\d{2}\\.\\d{2}\\.\\d{4}$"
|
||||
).match(value).hasMatch();
|
||||
};
|
||||
const auto DateOrEmptyValidate = [=](const QString &value) {
|
||||
return value.isEmpty() || DateValidate(value);
|
||||
};
|
||||
const auto GenderValidate = [](const QString &value) {
|
||||
return value == qstr("male") || value == qstr("female");
|
||||
};
|
||||
const auto CountryValidate = [](const QString &value) {
|
||||
return QRegularExpression("^[A-Z]{2}$").match(value).hasMatch();
|
||||
};
|
||||
|
||||
switch (type) {
|
||||
case Scope::Type::Identity: {
|
||||
auto result = Scheme();
|
||||
result.rows = {
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("first_name"),
|
||||
lang(lng_passport_first_name),
|
||||
NotEmptyValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("last_name"),
|
||||
lang(lng_passport_last_name),
|
||||
DontValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("birth_date"),
|
||||
lang(lng_passport_birth_date),
|
||||
DateValidate,
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("gender"),
|
||||
lang(lng_passport_gender),
|
||||
GenderValidate,
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("country_code"),
|
||||
lang(lng_passport_country),
|
||||
CountryValidate,
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Scans,
|
||||
qsl("document_no"),
|
||||
lang(lng_passport_document_number),
|
||||
NotEmptyValidate,
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Scans,
|
||||
qsl("expiry_date"),
|
||||
lang(lng_passport_expiry_date),
|
||||
DateOrEmptyValidate,
|
||||
},
|
||||
};
|
||||
return result;
|
||||
} break;
|
||||
|
||||
case Scope::Type::Address: {
|
||||
auto result = Scheme();
|
||||
result.rows = {
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("street_line1"),
|
||||
lang(lng_passport_street),
|
||||
NotEmptyValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("street_line2"),
|
||||
lang(lng_passport_street),
|
||||
DontValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("city"),
|
||||
lang(lng_passport_city),
|
||||
NotEmptyValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("state"),
|
||||
lang(lng_passport_state),
|
||||
DontValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("country_code"),
|
||||
lang(lng_passport_country),
|
||||
CountryValidate
|
||||
},
|
||||
{
|
||||
Scheme::ValueType::Fields,
|
||||
qsl("post_code"),
|
||||
lang(lng_passport_postcode),
|
||||
NotEmptyValidate
|
||||
},
|
||||
};
|
||||
return result;
|
||||
} break;
|
||||
}
|
||||
Unexpected("Type in GetDocumentScheme().");
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
BoxPointer::BoxPointer(QPointer<BoxContent> value)
|
||||
: _value(value) {
|
||||
@ -241,12 +362,20 @@ void PanelController::editScope(int index) {
|
||||
auto content = [&]() -> object_ptr<Ui::RpWidget> {
|
||||
switch (_editScope->type) {
|
||||
case Scope::Type::Identity:
|
||||
return object_ptr<PanelEditIdentity>(
|
||||
_panel.get(),
|
||||
this,
|
||||
_editScope->fields->data.parsed,
|
||||
_editScope->files[_editScopeFilesIndex]->data.parsed,
|
||||
valueFiles(*_editScope->files[_editScopeFilesIndex]));
|
||||
case Scope::Type::Address:
|
||||
return (_editScopeFilesIndex >= 0)
|
||||
? object_ptr<PanelEditDocument>(
|
||||
_panel.get(),
|
||||
this,
|
||||
std::move(GetDocumentScheme(_editScope->type)),
|
||||
_editScope->fields->data.parsed,
|
||||
_editScope->files[_editScopeFilesIndex]->data.parsed,
|
||||
valueFiles(*_editScope->files[_editScopeFilesIndex]))
|
||||
: object_ptr<PanelEditDocument>(
|
||||
_panel.get(),
|
||||
this,
|
||||
std::move(GetDocumentScheme(_editScope->type)),
|
||||
_editScope->fields->data.parsed);
|
||||
}
|
||||
return { nullptr };
|
||||
}();
|
||||
|
@ -20,8 +20,13 @@ PanelDetailsRow::PanelDetailsRow(
|
||||
, _field(this, st::passportDetailsField, nullptr, value) {
|
||||
}
|
||||
|
||||
QPointer<Ui::InputField> PanelDetailsRow::field() const {
|
||||
return _field.data();
|
||||
bool PanelDetailsRow::setFocusFast() {
|
||||
_field->setFocusFast();
|
||||
return true;
|
||||
}
|
||||
|
||||
QString PanelDetailsRow::getValue() const {
|
||||
return _field->getLastText();
|
||||
}
|
||||
|
||||
int PanelDetailsRow::resizeGetHeight(int newWidth) {
|
||||
|
@ -22,7 +22,8 @@ public:
|
||||
const QString &label,
|
||||
const QString &value);
|
||||
|
||||
QPointer<Ui::InputField> field() const;
|
||||
bool setFocusFast();
|
||||
QString getValue() const;
|
||||
|
||||
protected:
|
||||
int resizeGetHeight(int newWidth) override;
|
||||
|
@ -5,7 +5,7 @@ the official desktop application for the Telegram messaging service.
|
||||
For license and copyright information please follow this link:
|
||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
*/
|
||||
#include "passport/passport_panel_edit_identity.h"
|
||||
#include "passport/passport_panel_edit_document.h"
|
||||
|
||||
#include "passport/passport_panel_controller.h"
|
||||
#include "passport/passport_panel_details_row.h"
|
||||
@ -25,13 +25,15 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||
|
||||
namespace Passport {
|
||||
|
||||
PanelEditIdentity::PanelEditIdentity(
|
||||
PanelEditDocument::PanelEditDocument(
|
||||
QWidget*,
|
||||
not_null<PanelController*> controller,
|
||||
Scheme scheme,
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
std::vector<ScanInfo> &&files)
|
||||
: _controller(controller)
|
||||
, _scheme(std::move(scheme))
|
||||
, _scroll(this, st::passportPanelScroll)
|
||||
, _topShadow(this)
|
||||
, _bottomShadow(this)
|
||||
@ -39,12 +41,29 @@ PanelEditIdentity::PanelEditIdentity(
|
||||
this,
|
||||
langFactory(lng_passport_save_value),
|
||||
st::passportPanelSaveValue) {
|
||||
setupControls(data, scanData, std::move(files));
|
||||
setupControls(data, &scanData, std::move(files));
|
||||
}
|
||||
|
||||
void PanelEditIdentity::setupControls(
|
||||
PanelEditDocument::PanelEditDocument(
|
||||
QWidget*,
|
||||
not_null<PanelController*> controller,
|
||||
Scheme scheme,
|
||||
const ValueMap &data)
|
||||
: _controller(controller)
|
||||
, _scheme(std::move(scheme))
|
||||
, _scroll(this, st::passportPanelScroll)
|
||||
, _topShadow(this)
|
||||
, _bottomShadow(this)
|
||||
, _done(
|
||||
this,
|
||||
langFactory(lng_passport_save_value),
|
||||
st::passportPanelSaveValue) {
|
||||
setupControls(data, nullptr, {});
|
||||
}
|
||||
|
||||
void PanelEditDocument::setupControls(
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
const ValueMap *scanData,
|
||||
std::vector<ScanInfo> &&files) {
|
||||
const auto inner = setupContent(data, scanData, std::move(files));
|
||||
|
||||
@ -59,9 +78,9 @@ void PanelEditIdentity::setupControls(
|
||||
});
|
||||
}
|
||||
|
||||
not_null<Ui::RpWidget*> PanelEditIdentity::setupContent(
|
||||
not_null<Ui::RpWidget*> PanelEditDocument::setupContent(
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
const ValueMap *scanData,
|
||||
std::vector<ScanInfo> &&files) {
|
||||
const auto inner = _scroll->setOwnedWidget(
|
||||
object_ptr<Ui::VerticalLayout>(this));
|
||||
@ -70,8 +89,10 @@ not_null<Ui::RpWidget*> PanelEditIdentity::setupContent(
|
||||
inner->resizeToWidth(width);
|
||||
}, inner->lifetime());
|
||||
|
||||
_editScans = inner->add(
|
||||
object_ptr<EditScans>(inner, _controller, std::move(files)));
|
||||
if (scanData) {
|
||||
_editScans = inner->add(
|
||||
object_ptr<EditScans>(inner, _controller, std::move(files)));
|
||||
}
|
||||
|
||||
inner->add(object_ptr<BoxContentDivider>(
|
||||
inner,
|
||||
@ -84,34 +105,45 @@ not_null<Ui::RpWidget*> PanelEditIdentity::setupContent(
|
||||
st::passportFormHeader),
|
||||
st::passportDetailsHeaderPadding);
|
||||
|
||||
const auto valueOrEmpty = [&](const QString &key) {
|
||||
if (const auto i = data.fields.find(key); i != data.fields.end()) {
|
||||
const auto valueOrEmpty = [&](
|
||||
const ValueMap &values,
|
||||
const QString &key) {
|
||||
const auto &fields = values.fields;
|
||||
if (const auto i = fields.find(key); i != fields.end()) {
|
||||
return i->second;
|
||||
}
|
||||
return QString();
|
||||
};
|
||||
|
||||
_firstName = inner->add(object_ptr<PanelDetailsRow>(
|
||||
inner,
|
||||
lang(lng_passport_first_name),
|
||||
valueOrEmpty("first_name")))->field();
|
||||
_lastName = inner->add(object_ptr<PanelDetailsRow>(
|
||||
inner,
|
||||
lang(lng_passport_last_name),
|
||||
valueOrEmpty("last_name")))->field();
|
||||
for (const auto &row : _scheme.rows) {
|
||||
auto fields = (row.type == Scheme::ValueType::Fields)
|
||||
? &data
|
||||
: scanData;
|
||||
if (!fields) {
|
||||
continue;
|
||||
}
|
||||
_details.push_back(inner->add(object_ptr<PanelDetailsRow>(
|
||||
inner,
|
||||
row.label,
|
||||
valueOrEmpty(*fields, row.key))));
|
||||
}
|
||||
|
||||
return inner;
|
||||
}
|
||||
|
||||
void PanelEditIdentity::focusInEvent(QFocusEvent *e) {
|
||||
_firstName->setFocusFast();
|
||||
void PanelEditDocument::focusInEvent(QFocusEvent *e) {
|
||||
for (const auto row : _details) {
|
||||
if (row->setFocusFast()) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void PanelEditIdentity::resizeEvent(QResizeEvent *e) {
|
||||
void PanelEditDocument::resizeEvent(QResizeEvent *e) {
|
||||
updateControlsGeometry();
|
||||
}
|
||||
|
||||
void PanelEditIdentity::updateControlsGeometry() {
|
||||
void PanelEditDocument::updateControlsGeometry() {
|
||||
const auto submitTop = height() - _done->height();
|
||||
_scroll->setGeometry(0, 0, width(), submitTop);
|
||||
_topShadow->resizeToWidth(width());
|
||||
@ -124,11 +156,18 @@ void PanelEditIdentity::updateControlsGeometry() {
|
||||
_scroll->updateBars();
|
||||
}
|
||||
|
||||
void PanelEditIdentity::save() {
|
||||
void PanelEditDocument::save() {
|
||||
Expects(_details.size() == _scheme.rows.size());
|
||||
|
||||
auto data = ValueMap();
|
||||
data.fields["first_name"] = _firstName->getLastText();
|
||||
data.fields["last_name"] = _lastName->getLastText();
|
||||
auto scanData = ValueMap();
|
||||
for (auto i = 0, count = int(_details.size()); i != count; ++i) {
|
||||
const auto &row = _scheme.rows[i];
|
||||
auto &fields = (row.type == Scheme::ValueType::Fields)
|
||||
? data
|
||||
: scanData;
|
||||
fields.fields[row.key] = _details[i]->getValue();
|
||||
}
|
||||
_controller->saveScope(std::move(data), std::move(scanData));
|
||||
}
|
||||
|
@ -23,15 +23,37 @@ class PanelController;
|
||||
struct ValueMap;
|
||||
struct ScanInfo;
|
||||
class EditScans;
|
||||
class PanelDetailsRow;
|
||||
|
||||
class PanelEditIdentity : public Ui::RpWidget {
|
||||
class PanelEditDocument : public Ui::RpWidget {
|
||||
public:
|
||||
PanelEditIdentity(
|
||||
struct Scheme {
|
||||
enum class ValueType {
|
||||
Fields,
|
||||
Scans,
|
||||
};
|
||||
struct Row {
|
||||
ValueType type = ValueType::Fields;
|
||||
QString key;
|
||||
QString label;
|
||||
base::lambda<bool(const QString &value)> validate;
|
||||
};
|
||||
std::vector<Row> rows;
|
||||
|
||||
};
|
||||
|
||||
PanelEditDocument(
|
||||
QWidget *parent,
|
||||
not_null<PanelController*> controller,
|
||||
Scheme scheme,
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
std::vector<ScanInfo> &&files);
|
||||
PanelEditDocument(
|
||||
QWidget *parent,
|
||||
not_null<PanelController*> controller,
|
||||
Scheme scheme,
|
||||
const ValueMap &data);
|
||||
|
||||
protected:
|
||||
void focusInEvent(QFocusEvent *e) override;
|
||||
@ -40,25 +62,25 @@ protected:
|
||||
private:
|
||||
void setupControls(
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
const ValueMap *scanData,
|
||||
std::vector<ScanInfo> &&files);
|
||||
not_null<Ui::RpWidget*> setupContent(
|
||||
const ValueMap &data,
|
||||
const ValueMap &scanData,
|
||||
const ValueMap *scanData,
|
||||
std::vector<ScanInfo> &&files);
|
||||
void updateControlsGeometry();
|
||||
|
||||
void save();
|
||||
|
||||
not_null<PanelController*> _controller;
|
||||
Scheme _scheme;
|
||||
|
||||
object_ptr<Ui::ScrollArea> _scroll;
|
||||
object_ptr<Ui::FadeShadow> _topShadow;
|
||||
object_ptr<Ui::PlainShadow> _bottomShadow;
|
||||
|
||||
QPointer<EditScans> _editScans;
|
||||
QPointer<Ui::InputField> _firstName;
|
||||
QPointer<Ui::InputField> _lastName;
|
||||
std::vector<QPointer<PanelDetailsRow>> _details;
|
||||
|
||||
object_ptr<Ui::RoundButton> _done;
|
||||
|
@ -466,8 +466,8 @@
|
||||
<(src_loc)/passport/passport_panel_controller.h
|
||||
<(src_loc)/passport/passport_panel_details_row.cpp
|
||||
<(src_loc)/passport/passport_panel_details_row.h
|
||||
<(src_loc)/passport/passport_panel_edit_identity.cpp
|
||||
<(src_loc)/passport/passport_panel_edit_identity.h
|
||||
<(src_loc)/passport/passport_panel_edit_document.cpp
|
||||
<(src_loc)/passport/passport_panel_edit_document.h
|
||||
<(src_loc)/passport/passport_panel_edit_scans.cpp
|
||||
<(src_loc)/passport/passport_panel_edit_scans.h
|
||||
<(src_loc)/passport/passport_panel_form.cpp
|
||||
|
Loading…
Reference in New Issue
Block a user