Added Settings view
This commit is contained in:
@@ -29,6 +29,7 @@ lms_approot_DATA = \
|
|||||||
approot/playqueue.xml \
|
approot/playqueue.xml \
|
||||||
approot/release.xml \
|
approot/release.xml \
|
||||||
approot/releases.xml \
|
approot/releases.xml \
|
||||||
|
approot/settings.xml \
|
||||||
approot/templates.xml \
|
approot/templates.xml \
|
||||||
approot/tracks.xml
|
approot/tracks.xml
|
||||||
|
|
||||||
|
|||||||
+11
-4
@@ -13,9 +13,9 @@
|
|||||||
<message id="Lms.not-a-directory">Not a directory</message>
|
<message id="Lms.not-a-directory">Not a directory</message>
|
||||||
<message id="Lms.password">Password</message>
|
<message id="Lms.password">Password</message>
|
||||||
<message id="Lms.password-confirm">Confirm password</message>
|
<message id="Lms.password-confirm">Confirm password</message>
|
||||||
|
<message id="Lms.passwords-dont-match">Passwords don't match</message>
|
||||||
<message id="Lms.playqueue">Play Queue</message>
|
<message id="Lms.playqueue">Play Queue</message>
|
||||||
<message id="Lms.quit-confirm">Are you sure?</message>
|
<message id="Lms.quit-confirm">Are you sure?</message>
|
||||||
<message id="Lms.settings">Settings</message>
|
|
||||||
|
|
||||||
<!--Administration-->
|
<!--Administration-->
|
||||||
<message id="Lms.Admin.Database.daily">Daily</message>
|
<message id="Lms.Admin.Database.daily">Daily</message>
|
||||||
@@ -54,9 +54,16 @@
|
|||||||
<message id="Lms.Explore.value">Value</message>
|
<message id="Lms.Explore.value">Value</message>
|
||||||
<message id="Lms.Explore.various-artists">Various artists</message>
|
<message id="Lms.Explore.various-artists">Various artists</message>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<!--Settings-->
|
<!--Settings-->
|
||||||
|
<message id="Lms.Settings.account">Account</message>
|
||||||
|
<message id="Lms.Settings.audio">Audio</message>
|
||||||
|
<message id="Lms.Settings.auto">Auto</message>
|
||||||
|
<message id="Lms.Settings.bitrate">Bitrate</message>
|
||||||
|
<message id="Lms.Settings.encoding">Encoding</message>
|
||||||
|
<message id="Lms.Settings.mp3">MP3</message>
|
||||||
|
<message id="Lms.Settings.oga">OGA</message>
|
||||||
|
<message id="Lms.Settings.settings">Settings</message>
|
||||||
|
<message id="Lms.Settings.webma">WEBMA</message>
|
||||||
|
<message id="Lms.Settings.settings-saved">New settings saved!</message>
|
||||||
|
|
||||||
</messages>
|
</messages>
|
||||||
|
|||||||
@@ -0,0 +1,65 @@
|
|||||||
|
|
||||||
|
<?xml version="1.0" encoding="UTF-8" ?>
|
||||||
|
<messages xmlns:if="Wt.WTemplate.conditions">
|
||||||
|
<!--FORMS message blocks-->
|
||||||
|
|
||||||
|
<message id="Lms.Settings.template">
|
||||||
|
<legend>${tr:Lms.Settings.audio}</legend>
|
||||||
|
<div class="form-horizontal">
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="control-label col-sm-2" for="${id:bitrate}">
|
||||||
|
${tr:Lms.Settings.bitrate}
|
||||||
|
</label>
|
||||||
|
<div class="col-sm-5">
|
||||||
|
${bitrate}
|
||||||
|
</div>
|
||||||
|
<div class="help-block col-sm-5">
|
||||||
|
${bitrate-info}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="control-label col-sm-2" for="${id:encoding}">
|
||||||
|
${tr:Lms.Settings.encoding}
|
||||||
|
</label>
|
||||||
|
<div class="col-sm-5">
|
||||||
|
${encoding}
|
||||||
|
</div>
|
||||||
|
<div class="help-block col-sm-5">
|
||||||
|
${encoding-info}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<legend>${tr:Lms.Settings.account}</legend>
|
||||||
|
<div class="form-horizontal">
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="control-label col-sm-2" for="${id:password}">
|
||||||
|
${tr:Lms.password}
|
||||||
|
</label>
|
||||||
|
<div class="col-sm-5">
|
||||||
|
${password}
|
||||||
|
</div>
|
||||||
|
<div class="help-block col-sm-5">
|
||||||
|
${password-info}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="control-label col-sm-2" for="${id:password-confirm}">
|
||||||
|
${tr:Lms.password-confirm}
|
||||||
|
</label>
|
||||||
|
<div class="col-sm-5">
|
||||||
|
${password-confirm}
|
||||||
|
</div>
|
||||||
|
<div class="help-block col-sm-5">
|
||||||
|
${password-confirm-info}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-group">
|
||||||
|
<div class="col-sm-offset-2 col-sm-10">
|
||||||
|
${apply-btn class="btn-primary"} ${discard-btn}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</message>
|
||||||
|
|
||||||
|
</messages>
|
||||||
+11
-10
@@ -21,6 +21,17 @@ lms_SOURCES = \
|
|||||||
$(srcdir)/metadata/AvFormat.cpp \
|
$(srcdir)/metadata/AvFormat.cpp \
|
||||||
$(srcdir)/metadata/TagLibParser.cpp \
|
$(srcdir)/metadata/TagLibParser.cpp \
|
||||||
$(srcdir)/scanner/MediaScanner.cpp \
|
$(srcdir)/scanner/MediaScanner.cpp \
|
||||||
|
$(srcdir)/ui/Auth.cpp \
|
||||||
|
$(srcdir)/ui/HomeView.cpp \
|
||||||
|
$(srcdir)/ui/LmsApplication.cpp \
|
||||||
|
$(srcdir)/ui/MediaPlayer.cpp \
|
||||||
|
$(srcdir)/ui/PlayQueueView.cpp \
|
||||||
|
$(srcdir)/ui/SettingsView.cpp \
|
||||||
|
$(srcdir)/ui/admin/DatabaseSettingsView.cpp \
|
||||||
|
$(srcdir)/ui/admin/AdminWizardView.cpp \
|
||||||
|
$(srcdir)/ui/common/InputRange.cpp \
|
||||||
|
$(srcdir)/ui/common/LineEdit.cpp \
|
||||||
|
$(srcdir)/ui/common/Validators.cpp \
|
||||||
$(srcdir)/ui/explore/ArtistView.cpp \
|
$(srcdir)/ui/explore/ArtistView.cpp \
|
||||||
$(srcdir)/ui/explore/ArtistsView.cpp \
|
$(srcdir)/ui/explore/ArtistsView.cpp \
|
||||||
$(srcdir)/ui/explore/Explore.cpp \
|
$(srcdir)/ui/explore/Explore.cpp \
|
||||||
@@ -28,16 +39,6 @@ lms_SOURCES = \
|
|||||||
$(srcdir)/ui/explore/ReleasesView.cpp \
|
$(srcdir)/ui/explore/ReleasesView.cpp \
|
||||||
$(srcdir)/ui/explore/ReleaseView.cpp \
|
$(srcdir)/ui/explore/ReleaseView.cpp \
|
||||||
$(srcdir)/ui/explore/TracksView.cpp \
|
$(srcdir)/ui/explore/TracksView.cpp \
|
||||||
$(srcdir)/ui/Auth.cpp \
|
|
||||||
$(srcdir)/ui/HomeView.cpp \
|
|
||||||
$(srcdir)/ui/LmsApplication.cpp \
|
|
||||||
$(srcdir)/ui/MediaPlayer.cpp \
|
|
||||||
$(srcdir)/ui/PlayQueueView.cpp \
|
|
||||||
$(srcdir)/ui/admin/DatabaseSettingsView.cpp \
|
|
||||||
$(srcdir)/ui/admin/AdminWizardView.cpp \
|
|
||||||
$(srcdir)/ui/common/InputRange.cpp \
|
|
||||||
$(srcdir)/ui/common/LineEdit.cpp \
|
|
||||||
$(srcdir)/ui/common/Validators.cpp \
|
|
||||||
$(srcdir)/ui/resource/AvConvTranscodeStreamResource.cpp \
|
$(srcdir)/ui/resource/AvConvTranscodeStreamResource.cpp \
|
||||||
$(srcdir)/ui/resource/ImageResource.cpp \
|
$(srcdir)/ui/resource/ImageResource.cpp \
|
||||||
$(srcdir)/ui/resource/TranscodeResource.cpp \
|
$(srcdir)/ui/resource/TranscodeResource.cpp \
|
||||||
|
|||||||
@@ -31,15 +31,6 @@ User::audioBitrates =
|
|||||||
320000,
|
320000,
|
||||||
};
|
};
|
||||||
|
|
||||||
const std::vector<AudioEncoding>
|
|
||||||
User::audioEncodings =
|
|
||||||
{
|
|
||||||
AudioEncoding::AUTO,
|
|
||||||
AudioEncoding::MP3,
|
|
||||||
AudioEncoding::OGA,
|
|
||||||
AudioEncoding::WEBMA,
|
|
||||||
};
|
|
||||||
|
|
||||||
User::User()
|
User::User()
|
||||||
: _maxAudioBitrate(maxAudioBitrate),
|
: _maxAudioBitrate(maxAudioBitrate),
|
||||||
_isAdmin(false),
|
_isAdmin(false),
|
||||||
|
|||||||
@@ -52,7 +52,6 @@ class User
|
|||||||
|
|
||||||
// list of audio parameters
|
// list of audio parameters
|
||||||
static const std::vector<std::size_t> audioBitrates;
|
static const std::vector<std::size_t> audioBitrates;
|
||||||
static const std::vector<AudioEncoding> audioEncodings;
|
|
||||||
|
|
||||||
User();
|
User();
|
||||||
|
|
||||||
|
|||||||
@@ -35,6 +35,7 @@
|
|||||||
#include "HomeView.hpp"
|
#include "HomeView.hpp"
|
||||||
#include "MediaPlayer.hpp"
|
#include "MediaPlayer.hpp"
|
||||||
#include "PlayQueueView.hpp"
|
#include "PlayQueueView.hpp"
|
||||||
|
#include "SettingsView.hpp"
|
||||||
|
|
||||||
#include "admin/DatabaseSettingsView.hpp"
|
#include "admin/DatabaseSettingsView.hpp"
|
||||||
#include "admin/AdminWizardView.hpp"
|
#include "admin/AdminWizardView.hpp"
|
||||||
@@ -93,6 +94,7 @@ LmsApplication::LmsApplication(const Wt::WEnvironment& env, Wt::Dbo::SqlConnecti
|
|||||||
messageResourceBundle().use(appRoot() + "playqueue");
|
messageResourceBundle().use(appRoot() + "playqueue");
|
||||||
messageResourceBundle().use(appRoot() + "release");
|
messageResourceBundle().use(appRoot() + "release");
|
||||||
messageResourceBundle().use(appRoot() + "releases");
|
messageResourceBundle().use(appRoot() + "releases");
|
||||||
|
messageResourceBundle().use(appRoot() + "settings");
|
||||||
messageResourceBundle().use(appRoot() + "tracks");
|
messageResourceBundle().use(appRoot() + "tracks");
|
||||||
messageResourceBundle().use(appRoot() + "templates");
|
messageResourceBundle().use(appRoot() + "templates");
|
||||||
|
|
||||||
@@ -185,6 +187,7 @@ enum IdxRoot
|
|||||||
IdxHome = 0,
|
IdxHome = 0,
|
||||||
IdxExplore,
|
IdxExplore,
|
||||||
IdxPlayQueue,
|
IdxPlayQueue,
|
||||||
|
IdxSettings,
|
||||||
IdxAdminDatabase,
|
IdxAdminDatabase,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -200,6 +203,7 @@ handlePathChange(Wt::WStackedWidget* stack)
|
|||||||
{ "/release", IdxExplore },
|
{ "/release", IdxExplore },
|
||||||
{ "/tracks", IdxExplore },
|
{ "/tracks", IdxExplore },
|
||||||
{ "/playqueue", IdxPlayQueue },
|
{ "/playqueue", IdxPlayQueue },
|
||||||
|
{ "/settings", IdxSettings },
|
||||||
{ "/admin/database", IdxAdminDatabase },
|
{ "/admin/database", IdxAdminDatabase },
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -288,7 +292,7 @@ LmsApplication::handleAuthEvent(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
{
|
{
|
||||||
auto menuItem = rightMenu->insertItem(itemCounter++, Wt::WString::tr("Lms.settings"));
|
auto menuItem = rightMenu->insertItem(itemCounter++, Wt::WString::tr("Lms.Settings.settings"));
|
||||||
menuItem->setLink(Wt::WLink(Wt::WLink::InternalPath, "/settings"));
|
menuItem->setLink(Wt::WLink(Wt::WLink::InternalPath, "/settings"));
|
||||||
menuItem->setSelectable(false);
|
menuItem->setSelectable(false);
|
||||||
}
|
}
|
||||||
@@ -315,6 +319,10 @@ LmsApplication::handleAuthEvent(void)
|
|||||||
auto playqueue = new PlayQueue();
|
auto playqueue = new PlayQueue();
|
||||||
mainStack->addWidget(playqueue);
|
mainStack->addWidget(playqueue);
|
||||||
|
|
||||||
|
auto settings = new SettingsView();
|
||||||
|
mainStack->addWidget(settings);
|
||||||
|
|
||||||
|
// Admin stuff
|
||||||
auto databaseSettings = new DatabaseSettingsView();
|
auto databaseSettings = new DatabaseSettingsView();
|
||||||
mainStack->addWidget(databaseSettings);
|
mainStack->addWidget(databaseSettings);
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,304 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2018 Emeric Poupon
|
||||||
|
*
|
||||||
|
* This file is part of LMS.
|
||||||
|
*
|
||||||
|
* LMS is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* LMS is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with LMS. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <Wt/WString>
|
||||||
|
#include <Wt/WPushButton>
|
||||||
|
#include <Wt/WComboBox>
|
||||||
|
#include <Wt/WLineEdit>
|
||||||
|
|
||||||
|
#include <Wt/WFormModel>
|
||||||
|
#include <Wt/WStringListModel>
|
||||||
|
|
||||||
|
#include "common/Validators.hpp"
|
||||||
|
|
||||||
|
#include "utils/Logger.hpp"
|
||||||
|
#include "LmsApplication.hpp"
|
||||||
|
|
||||||
|
#include "SettingsView.hpp"
|
||||||
|
|
||||||
|
namespace UserInterface {
|
||||||
|
|
||||||
|
using namespace Database;
|
||||||
|
|
||||||
|
class SettingsModel : public Wt::WFormModel
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Associate each field with a unique string literal.
|
||||||
|
static const Field BitrateField;
|
||||||
|
static const Field EncodingField;
|
||||||
|
static const Field PasswordField;
|
||||||
|
static const Field PasswordConfirmField;
|
||||||
|
|
||||||
|
SettingsModel(Wt::WObject *parent = 0)
|
||||||
|
: Wt::WFormModel(parent)
|
||||||
|
{
|
||||||
|
initializeModels();
|
||||||
|
|
||||||
|
addField(BitrateField);
|
||||||
|
addField(EncodingField);
|
||||||
|
addField(PasswordField);
|
||||||
|
addField(PasswordConfirmField);
|
||||||
|
|
||||||
|
setValidator(BitrateField, createMandatoryValidator());
|
||||||
|
setValidator(EncodingField, createMandatoryValidator());
|
||||||
|
|
||||||
|
loadData();
|
||||||
|
}
|
||||||
|
|
||||||
|
Wt::WAbstractItemModel *bitrateModel() { return _bitrateModel; }
|
||||||
|
Wt::WAbstractItemModel *encodingModel() { return _encodingModel; }
|
||||||
|
|
||||||
|
void loadData()
|
||||||
|
{
|
||||||
|
Wt::Dbo::Transaction transaction(DboSession());
|
||||||
|
|
||||||
|
auto bitrate = getBitrateRow(CurrentUser()->getAudioBitrate());
|
||||||
|
if (bitrate)
|
||||||
|
setValue(BitrateField, bitrateString(*bitrate));
|
||||||
|
|
||||||
|
auto encodingRow = getEncodingRow(CurrentUser()->getAudioEncoding());
|
||||||
|
if (encodingRow)
|
||||||
|
setValue(EncodingField, encodingString(*encodingRow));
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
void saveData()
|
||||||
|
{
|
||||||
|
Wt::Dbo::Transaction transaction(DboSession());
|
||||||
|
|
||||||
|
auto bitrateRow = getBitrateRow(Wt::asString(value(BitrateField)));
|
||||||
|
assert(bitrateRow);
|
||||||
|
CurrentUser().modify()->setAudioBitrate(bitrate(*bitrateRow));
|
||||||
|
|
||||||
|
auto encodingRow = getEncodingRow(Wt::asString(value(EncodingField)));
|
||||||
|
CurrentUser().modify()->setAudioEncoding(encoding(*encodingRow));
|
||||||
|
|
||||||
|
if (!valueText(PasswordField).empty())
|
||||||
|
{
|
||||||
|
Database::Handler::getPasswordService().updatePassword(CurrentAuthUser(), valueText(PasswordField));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool validateField(Field field)
|
||||||
|
{
|
||||||
|
Wt::WString error;
|
||||||
|
|
||||||
|
if (field == PasswordField)
|
||||||
|
{
|
||||||
|
if (!valueText(PasswordField).empty())
|
||||||
|
{
|
||||||
|
// Evaluate the strength of the password
|
||||||
|
auto res = Database::Handler::getPasswordService().strengthValidator()->evaluateStrength(valueText(PasswordField),
|
||||||
|
CurrentAuthUser().identity(Wt::Auth::Identity::LoginName), "");
|
||||||
|
|
||||||
|
if (!res.isValid())
|
||||||
|
error = res.message();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return Wt::WFormModel::validateField(field);
|
||||||
|
}
|
||||||
|
else if (field == PasswordConfirmField)
|
||||||
|
{
|
||||||
|
if (validation(PasswordField).state() == Wt::WValidator::Valid)
|
||||||
|
{
|
||||||
|
if (valueText(PasswordField) != valueText(PasswordConfirmField))
|
||||||
|
error = Wt::WString::tr("Lms.passwords-dont-match");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return Wt::WFormModel::validateField(field);
|
||||||
|
}
|
||||||
|
|
||||||
|
setValidation(field, Wt::WValidator::Result( error.empty() ? Wt::WValidator::Valid : Wt::WValidator::Invalid, error));
|
||||||
|
|
||||||
|
return (validation(field).state() == Wt::WValidator::Valid);
|
||||||
|
}
|
||||||
|
|
||||||
|
boost::optional<int> getBitrateRow(Wt::WString value)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _bitrateModel->rowCount(); ++i)
|
||||||
|
{
|
||||||
|
if (bitrateString(i) == value)
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
|
return boost::none;
|
||||||
|
}
|
||||||
|
|
||||||
|
boost::optional<int> getBitrateRow(std::size_t value)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _bitrateModel->rowCount(); ++i)
|
||||||
|
{
|
||||||
|
if (bitrate(i) == value)
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
|
return boost::none;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::size_t bitrate(int row)
|
||||||
|
{
|
||||||
|
return boost::any_cast<std::size_t>
|
||||||
|
(_bitrateModel->data(_encodingModel->index(row, 0), Wt::UserRole));
|
||||||
|
}
|
||||||
|
|
||||||
|
Wt::WString bitrateString(int row)
|
||||||
|
{
|
||||||
|
return boost::any_cast<Wt::WString>
|
||||||
|
(_bitrateModel->data(_encodingModel->index(row, 0), Wt::DisplayRole));
|
||||||
|
}
|
||||||
|
|
||||||
|
boost::optional<int> getEncodingRow(Wt::WString value)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _encodingModel->rowCount(); ++i)
|
||||||
|
{
|
||||||
|
if (encodingString(i) == value)
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
|
return boost::none;
|
||||||
|
}
|
||||||
|
|
||||||
|
boost::optional<int> getEncodingRow(Database::AudioEncoding enc)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _encodingModel->rowCount(); ++i)
|
||||||
|
{
|
||||||
|
if (encoding(i) == enc)
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
|
return boost::none;
|
||||||
|
}
|
||||||
|
|
||||||
|
Database::AudioEncoding encoding(int row)
|
||||||
|
{
|
||||||
|
return boost::any_cast<Database::AudioEncoding>
|
||||||
|
(_encodingModel->data(_encodingModel->index(row, 0), Wt::UserRole));
|
||||||
|
}
|
||||||
|
|
||||||
|
Wt::WString encodingString(int row)
|
||||||
|
{
|
||||||
|
return boost::any_cast<Wt::WString>
|
||||||
|
(_encodingModel->data(_encodingModel->index(row, 0), Wt::DisplayRole));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
void initializeModels()
|
||||||
|
{
|
||||||
|
|
||||||
|
_bitrateModel = new Wt::WStringListModel(this);
|
||||||
|
|
||||||
|
std::size_t id = 0;
|
||||||
|
for (auto bitrate : Database::User::audioBitrates)
|
||||||
|
{
|
||||||
|
_bitrateModel->addString( Wt::WString::fromUTF8(std::to_string(bitrate / 1000)) );
|
||||||
|
_bitrateModel->setData( id++, 0, bitrate, Wt::UserRole);
|
||||||
|
}
|
||||||
|
|
||||||
|
_encodingModel = new Wt::WStringListModel(this);
|
||||||
|
|
||||||
|
_encodingModel->addString(Wt::WString::tr("Lms.Settings.auto"));
|
||||||
|
_encodingModel->setData(0, 0, Database::AudioEncoding::AUTO, Wt::UserRole);
|
||||||
|
|
||||||
|
_encodingModel->addString(Wt::WString::tr("Lms.Settings.mp3"));
|
||||||
|
_encodingModel->setData(1, 0, Database::AudioEncoding::MP3, Wt::UserRole);
|
||||||
|
|
||||||
|
_encodingModel->addString(Wt::WString::tr("Lms.Settings.oga"));
|
||||||
|
_encodingModel->setData(2, 0, Database::AudioEncoding::OGA, Wt::UserRole);
|
||||||
|
|
||||||
|
_encodingModel->addString(Wt::WString::tr("Lms.Settings.webma"));
|
||||||
|
_encodingModel->setData(3, 0, Database::AudioEncoding::WEBMA, Wt::UserRole);
|
||||||
|
}
|
||||||
|
|
||||||
|
Wt::WStringListModel* _bitrateModel;
|
||||||
|
Wt::WStringListModel* _encodingModel;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
const Wt::WFormModel::Field SettingsModel::BitrateField = "bitrate";
|
||||||
|
const Wt::WFormModel::Field SettingsModel::EncodingField = "encoding";
|
||||||
|
const Wt::WFormModel::Field SettingsModel::PasswordField = "password";
|
||||||
|
const Wt::WFormModel::Field SettingsModel::PasswordConfirmField = "password-confirm";
|
||||||
|
|
||||||
|
SettingsView::SettingsView(Wt::WContainerWidget *parent)
|
||||||
|
: Wt::WTemplateFormView(parent)
|
||||||
|
{
|
||||||
|
auto model = new SettingsModel(this);
|
||||||
|
|
||||||
|
setTemplateText(tr("Lms.Settings.template"));
|
||||||
|
addFunction("tr", &WTemplate::Functions::tr);
|
||||||
|
addFunction("id", &WTemplate::Functions::id);
|
||||||
|
|
||||||
|
// Password
|
||||||
|
Wt::WLineEdit *password = new Wt::WLineEdit();
|
||||||
|
setFormWidget(SettingsModel::PasswordField, password);
|
||||||
|
password->setEchoMode(Wt::WLineEdit::Password);
|
||||||
|
|
||||||
|
// Password confirm
|
||||||
|
Wt::WLineEdit *passwordConfirm = new Wt::WLineEdit();
|
||||||
|
setFormWidget(SettingsModel::PasswordConfirmField, passwordConfirm);
|
||||||
|
passwordConfirm->setEchoMode(Wt::WLineEdit::Password);
|
||||||
|
|
||||||
|
// Bitrate
|
||||||
|
Wt::WComboBox *bitrate = new Wt::WComboBox();
|
||||||
|
setFormWidget(SettingsModel::BitrateField, bitrate);
|
||||||
|
bitrate->setModel(model->bitrateModel());
|
||||||
|
|
||||||
|
// Encoding
|
||||||
|
Wt::WComboBox *encoding = new Wt::WComboBox();
|
||||||
|
setFormWidget(SettingsModel::EncodingField, encoding);
|
||||||
|
encoding->setModel(model->encodingModel());
|
||||||
|
|
||||||
|
// Buttons
|
||||||
|
Wt::WPushButton *saveBtn = new Wt::WPushButton(Wt::WString::tr("Lms.apply"));
|
||||||
|
bindWidget("apply-btn", saveBtn);
|
||||||
|
|
||||||
|
Wt::WPushButton *discardBtn = new Wt::WPushButton(Wt::WString::tr("Lms.discard"));
|
||||||
|
bindWidget("discard-btn", discardBtn);
|
||||||
|
|
||||||
|
saveBtn->clicked().connect(std::bind([=] ()
|
||||||
|
{
|
||||||
|
updateModel(model);
|
||||||
|
|
||||||
|
if (model->validate())
|
||||||
|
{
|
||||||
|
model->saveData();
|
||||||
|
LmsApp->notify(Wt::WString::tr("Lms.Settings.settings-saved"));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Udate the view: Delete any validation message in the view, etc.
|
||||||
|
updateView(model);
|
||||||
|
}));
|
||||||
|
|
||||||
|
discardBtn->clicked().connect(std::bind([=] ()
|
||||||
|
{
|
||||||
|
model->loadData();
|
||||||
|
model->validate();
|
||||||
|
updateView(model);
|
||||||
|
}));
|
||||||
|
|
||||||
|
updateView(model);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace UserInterface
|
||||||
|
|
||||||
|
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2018 Emeric Poupon
|
||||||
|
*
|
||||||
|
* This file is part of LMS.
|
||||||
|
*
|
||||||
|
* LMS is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* LMS is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with LMS. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <Wt/WContainerWidget>
|
||||||
|
#include <Wt/WTemplateFormView>
|
||||||
|
|
||||||
|
namespace UserInterface {
|
||||||
|
|
||||||
|
class SettingsView : public Wt::WTemplateFormView
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
SettingsView(Wt::WContainerWidget *parent = 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace UserInterface
|
||||||
|
|
||||||
@@ -97,7 +97,7 @@ class AdminWizardModel : public Wt::WFormModel
|
|||||||
if (validation(PasswordField).state() == Wt::WValidator::Valid)
|
if (validation(PasswordField).state() == Wt::WValidator::Valid)
|
||||||
{
|
{
|
||||||
if (valueText(PasswordField) != valueText(PasswordConfirmField))
|
if (valueText(PasswordField) != valueText(PasswordConfirmField))
|
||||||
error = Wt::WString::tr("Wt.Auth.passwords-dont-match");
|
error = Wt::WString::tr("Lms.passwords-dont-match");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -20,7 +20,6 @@
|
|||||||
#include <Wt/WString>
|
#include <Wt/WString>
|
||||||
#include <Wt/WPushButton>
|
#include <Wt/WPushButton>
|
||||||
#include <Wt/WComboBox>
|
#include <Wt/WComboBox>
|
||||||
#include <Wt/WMessageBox>
|
|
||||||
#include <Wt/WLineEdit>
|
#include <Wt/WLineEdit>
|
||||||
|
|
||||||
#include <Wt/WFormModel>
|
#include <Wt/WFormModel>
|
||||||
@@ -177,7 +176,8 @@ class DatabaseSettingsModel : public Wt::WFormModel
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
void initializeModels() {
|
void initializeModels()
|
||||||
|
{
|
||||||
|
|
||||||
_updatePeriodModel = new Wt::WStringListModel(this);
|
_updatePeriodModel = new Wt::WStringListModel(this);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user