GCC Code Coverage Report
Directory: src/ Exec Total Coverage
File: src/gui/windows/registerdialog.cpp Lines: 60 143 42.0 %
Date: 2018-11-12 Branches: 68 270 25.2 %

Line Branch Exec Source
1
/*
2
 *  The ManaPlus Client
3
 *  Copyright (C) 2004-2009  The Mana World Development Team
4
 *  Copyright (C) 2009-2010  The Mana Developers
5
 *  Copyright (C) 2011-2018  The ManaPlus Developers
6
 *
7
 *  This file is part of The ManaPlus Client.
8
 *
9
 *  This program is free software; you can redistribute it and/or modify
10
 *  it under the terms of the GNU General Public License as published by
11
 *  the Free Software Foundation; either version 2 of the License, or
12
 *  any later version.
13
 *
14
 *  This program is distributed in the hope that it will be useful,
15
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
 *  GNU General Public License for more details.
18
 *
19
 *  You should have received a copy of the GNU General Public License
20
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
21
 */
22
23
#include "gui/windows/registerdialog.h"
24
25
#include "client.h"
26
#include "configuration.h"
27
28
#include "being/being.h"
29
30
#include "gui/windows/okdialog.h"
31
32
#include "gui/widgets/button.h"
33
#include "gui/widgets/containerplacer.h"
34
#include "gui/widgets/createwidget.h"
35
#include "gui/widgets/label.h"
36
#include "gui/widgets/layoutcell.h"
37
#include "gui/widgets/passwordfield.h"
38
#include "gui/widgets/radiobutton.h"
39
40
#include "listeners/wrongdatanoticelistener.h"
41
42
#include "net/logindata.h"
43
#include "net/loginhandler.h"
44
#include "net/serverfeatures.h"
45
46
#include "utils/delete2.h"
47
#include "utils/gettext.h"
48
49
#include "debug.h"
50
51
1
RegisterDialog::RegisterDialog(LoginData &data) :
52
    // TRANSLATORS: register dialog name
53
1
    Window(_("Register"), Modal_false, nullptr, "register.xml"),
54
    ActionListener(),
55
    KeyListener(),
56
    mLoginData(&data),
57
1
    mUserField(new TextField(this, mLoginData->username, LoseFocusOnTab_true,
58

3
        nullptr, std::string(), false)),
59

1
    mPasswordField(new PasswordField(this, mLoginData->password)),
60

2
    mConfirmField(new PasswordField(this, std::string())),
61
    mEmailField(nullptr),
62
    // TRANSLATORS: register dialog. button.
63
1
    mRegisterButton(new Button(this, _("Register"), "register",
64

1
        BUTTON_SKIN, this)),
65
    // TRANSLATORS: register dialog. button.
66
1
    mCancelButton(new Button(this, _("Cancel"), "cancel",
67

1
        BUTTON_SKIN, this)),
68
    mMaleButton(nullptr),
69
    mFemaleButton(nullptr),
70




27
    mWrongDataNoticeListener(new WrongDataNoticeListener)
71
{
72
1
    setCloseButton(true);
73
74
    // TRANSLATORS: register dialog. label.
75

4
    Label *const userLabel = new Label(this, _("Name:"));
76
    // TRANSLATORS: register dialog. label.
77

4
    Label *const passwordLabel = new Label(this, _("Password:"));
78
    // TRANSLATORS: register dialog. label.
79

4
    Label *const confirmLabel = new Label(this, _("Confirm:"));
80
81
1
    ContainerPlacer placer(nullptr, nullptr);
82
1
    placer = getPlacer(0, 0);
83
1
    placer(0, 0, userLabel, 1, 1);
84
1
    placer(0, 1, passwordLabel, 1, 1);
85
1
    placer(0, 2, confirmLabel, 1, 1);
86
87
2
    placer(1, 0, mUserField, 3, 1).setPadding(2);
88
2
    placer(1, 1, mPasswordField, 3, 1).setPadding(2);
89
2
    placer(1, 2, mConfirmField, 3, 1).setPadding(2);
90
91
1
    int row = 3;
92
93

4
    if (features.getIntValue("forceAccountGender") == -1)
94
    {
95
        // TRANSLATORS: register dialog. button.
96


7
        mMaleButton = new RadioButton(this, _("Male"), "sex", true);
97
        // TRANSLATORS: register dialog. button.
98


7
        mFemaleButton = new RadioButton(this, _("Female"), "sex", false);
99
1
        placer(1, row, mMaleButton, 1, 1);
100
1
        placer(2, row, mFemaleButton, 1, 1);
101
102
        row++;
103
    }
104
105

1
    if (serverFeatures->haveEmailOnRegister())
106
    {
107
        // TRANSLATORS: register dialog. label.
108
        Label *const emailLabel = new Label(this, _("Email:"));
109
        mEmailField = new TextField(this,
110
            std::string(),
111
            LoseFocusOnTab_true,
112
            nullptr,
113
            std::string(),
114
            false);
115
        placer(0, row, emailLabel, 1, 1);
116
        placer(1, row, mEmailField, 3, 1).setPadding(2);
117
        mEmailField->addKeyListener(this);
118
        mEmailField->setActionEventId("register");
119
        mEmailField->addActionListener(this);
120
//        row++;
121
    }
122
123
1
    placer = getPlacer(0, 2);
124
1
    placer(1, 0, mRegisterButton, 1, 1);
125
1
    placer(2, 0, mCancelButton, 1, 1);
126
1
    reflowLayout(250, 0);
127
128
1
    mUserField->addKeyListener(this);
129
1
    mPasswordField->addKeyListener(this);
130
1
    mConfirmField->addKeyListener(this);
131
132
5
    mUserField->setActionEventId("register");
133
5
    mPasswordField->setActionEventId("register");
134
5
    mConfirmField->setActionEventId("register");
135
136
1
    mUserField->addActionListener(this);
137
1
    mPasswordField->addActionListener(this);
138
1
    mConfirmField->addActionListener(this);
139
140
1
    center();
141
1
}
142
143
1
void RegisterDialog::postInit()
144
{
145
1
    Window::postInit();
146
1
    setVisible(Visible_true);
147
1
    mUserField->requestFocus();
148
1
    mUserField->setCaretPosition(CAST_U32(
149
2
                                 mUserField->getText().length()));
150
151
2
    mRegisterButton->setEnabled(canSubmit());
152
1
}
153
154
5
RegisterDialog::~RegisterDialog()
155
{
156
2
    delete2(mWrongDataNoticeListener);
157
2
}
158
159
void RegisterDialog::action(const ActionEvent &event)
160
{
161
    const std::string &eventId = event.getId();
162
    if (eventId == "cancel")
163
    {
164
        close();
165
    }
166
    else if (eventId == "register" && canSubmit())
167
    {
168
        const std::string &user = mUserField->getText();
169
        logger->log("RegisterDialog::register Username is %s", user.c_str());
170
171
        std::string errorMsg;
172
        int error = 0;
173
174
        const unsigned int minUser = loginHandler->getMinUserNameLength();
175
        const unsigned int maxUser = loginHandler->getMaxUserNameLength();
176
        const unsigned int minPass = loginHandler->getMinPasswordLength();
177
        const unsigned int maxPass = loginHandler->getMaxPasswordLength();
178
179
        if (user.length() < minUser)
180
        {
181
            // Name too short
182
            errorMsg = strprintf
183
                // TRANSLATORS: error message
184
                (_("The username needs to be at least %u characters long."),
185
                 minUser);
186
            error = 1;
187
        }
188
        else if (user.length() > maxUser - 1)
189
        {
190
            // Name too long
191
            errorMsg = strprintf
192
                // TRANSLATORS: error message
193
                (_("The username needs to be less than %u characters long."),
194
                 maxUser);
195
            error = 1;
196
        }
197
        else if (mPasswordField->getText().length() < minPass)
198
        {
199
            // Pass too short
200
            errorMsg = strprintf
201
                // TRANSLATORS: error message
202
                (_("The password needs to be at least %u characters long."),
203
                 minPass);
204
            error = 2;
205
        }
206
        else if (mPasswordField->getText().length() > maxPass)
207
        {
208
            // Pass too long
209
            errorMsg = strprintf
210
                // TRANSLATORS: error message
211
                (_("The password needs to be less than %u characters long."),
212
                 maxPass);
213
            error = 2;
214
        }
215
        else if (mPasswordField->getText() != mConfirmField->getText())
216
        {
217
            // Password does not match with the confirmation one
218
            // TRANSLATORS: error message
219
            errorMsg = _("Passwords do not match.");
220
            error = 2;
221
        }
222
        else if ((mEmailField != nullptr) &&
223
                 mEmailField->getText().find('@') == std::string::npos)
224
        {
225
            // TRANSLATORS: error message
226
            errorMsg = _("Incorrect email.");
227
            error = 1;
228
        }
229
        else if (mEmailField != nullptr &&
230
                 mEmailField->getText().size() > 40)
231
        {
232
            // TRANSLATORS: error message
233
            errorMsg = _("Email too long.");
234
            error = 1;
235
        }
236
237
        if (error > 0)
238
        {
239
            if (error == 1)
240
            {
241
                mWrongDataNoticeListener->setTarget(this->mUserField);
242
            }
243
            else if (error == 2)
244
            {
245
                // Reset password confirmation
246
                mPasswordField->setText("");
247
                mConfirmField->setText("");
248
                mWrongDataNoticeListener->setTarget(this->mPasswordField);
249
            }
250
251
            OkDialog *const dlg = CREATEWIDGETR(OkDialog,
252
                // TRANSLATORS: error message
253
                _("Error"), errorMsg, _("OK"),
254
                DialogType::ERROR,
255
                Modal_true,
256
                ShowCenter_true,
257
                nullptr,
258
                260);
259
            dlg->addActionListener(mWrongDataNoticeListener);
260
        }
261
        else
262
        {
263
            // No errors detected, register the new user.
264
            mRegisterButton->setEnabled(false);
265
            mLoginData->username = mUserField->getText();
266
            mLoginData->password = mPasswordField->getText();
267
            if (features.getIntValue("forceAccountGender") == -1)
268
            {
269
                if ((mFemaleButton != nullptr) && mFemaleButton->isSelected())
270
                    mLoginData->gender = Gender::FEMALE;
271
                else
272
                    mLoginData->gender = Gender::MALE;
273
            }
274
            else
275
            {
276
                mLoginData->gender = Being::intToGender(
277
                    CAST_U8(features.getIntValue("forceAccountGender")));
278
            }
279
280
            if (mEmailField != nullptr)
281
                mLoginData->email = mEmailField->getText();
282
            mLoginData->registerLogin = true;
283
284
            client->setState(State::REGISTER_ATTEMPT);
285
        }
286
    }
287
}
288
289
void RegisterDialog::keyPressed(KeyEvent &event)
290
{
291
    if (event.isConsumed())
292
    {
293
        mRegisterButton->setEnabled(canSubmit());
294
        return;
295
    }
296
    const InputActionT actionId = event.getActionId();
297
    if (actionId == InputAction::GUI_CANCEL)
298
    {
299
        action(ActionEvent(nullptr, mCancelButton->getActionEventId()));
300
    }
301
    else if (actionId == InputAction::GUI_SELECT ||
302
             actionId == InputAction::GUI_SELECT2)
303
    {
304
        action(ActionEvent(nullptr, mRegisterButton->getActionEventId()));
305
    }
306
    else
307
    {
308
        mRegisterButton->setEnabled(canSubmit());
309
    }
310
}
311
312
1
bool RegisterDialog::canSubmit() const
313
{
314
1
    return !mUserField->getText().empty() &&
315
           !mPasswordField->getText().empty() &&
316
           !mConfirmField->getText().empty() &&
317

1
           client->getState() == State::REGISTER &&
318
           ((mEmailField == nullptr) || !mEmailField->getText().empty());
319
}
320
321
void RegisterDialog::close()
322
{
323
    client->setState(State::LOGIN);
324
    Window::close();
325

3
}