mirror of
https://github.com/miniflux/v2.git
synced 2025-09-15 18:57:04 +00:00
parent
b68ada396a
commit
00dabc1d3c
31 changed files with 188 additions and 74 deletions
|
@ -33,6 +33,7 @@ type SettingsForm struct {
|
|||
DefaultHomePage string
|
||||
CategoriesSortingOrder string
|
||||
MarkReadOnView bool
|
||||
MediaPlaybackRate float64
|
||||
}
|
||||
|
||||
// Merge updates the fields of the given user.
|
||||
|
@ -55,6 +56,7 @@ func (s *SettingsForm) Merge(user *model.User) *model.User {
|
|||
user.DefaultHomePage = s.DefaultHomePage
|
||||
user.CategoriesSortingOrder = s.CategoriesSortingOrder
|
||||
user.MarkReadOnView = s.MarkReadOnView
|
||||
user.MediaPlaybackRate = s.MediaPlaybackRate
|
||||
|
||||
if s.Password != "" {
|
||||
user.Password = s.Password
|
||||
|
@ -84,6 +86,10 @@ func (s *SettingsForm) Validate() *locale.LocalizedError {
|
|||
}
|
||||
}
|
||||
|
||||
if s.MediaPlaybackRate < 0.25 || s.MediaPlaybackRate > 4 {
|
||||
return locale.NewLocalizedError("error.settings_media_playback_rate_range")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -101,6 +107,10 @@ func NewSettingsForm(r *http.Request) *SettingsForm {
|
|||
if err != nil {
|
||||
cjkReadingSpeed = 0
|
||||
}
|
||||
mediaPlaybackRate, err := strconv.ParseFloat(r.FormValue("media_playback_rate"), 64)
|
||||
if err != nil {
|
||||
mediaPlaybackRate = 1
|
||||
}
|
||||
return &SettingsForm{
|
||||
Username: r.FormValue("username"),
|
||||
Password: r.FormValue("password"),
|
||||
|
@ -122,5 +132,6 @@ func NewSettingsForm(r *http.Request) *SettingsForm {
|
|||
DefaultHomePage: r.FormValue("default_home_page"),
|
||||
CategoriesSortingOrder: r.FormValue("categories_sorting_order"),
|
||||
MarkReadOnView: r.FormValue("mark_read_on_view") == "1",
|
||||
MediaPlaybackRate: mediaPlaybackRate,
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,6 +22,7 @@ func TestValid(t *testing.T) {
|
|||
DefaultReadingSpeed: 35,
|
||||
CJKReadingSpeed: 25,
|
||||
DefaultHomePage: "unread",
|
||||
MediaPlaybackRate: 1.25,
|
||||
}
|
||||
|
||||
err := settings.Validate()
|
||||
|
@ -45,6 +46,7 @@ func TestConfirmationEmpty(t *testing.T) {
|
|||
DefaultReadingSpeed: 35,
|
||||
CJKReadingSpeed: 25,
|
||||
DefaultHomePage: "unread",
|
||||
MediaPlaybackRate: 1.25,
|
||||
}
|
||||
|
||||
err := settings.Validate()
|
||||
|
@ -72,6 +74,7 @@ func TestConfirmationIncorrect(t *testing.T) {
|
|||
DefaultReadingSpeed: 35,
|
||||
CJKReadingSpeed: 25,
|
||||
DefaultHomePage: "unread",
|
||||
MediaPlaybackRate: 1.25,
|
||||
}
|
||||
|
||||
err := settings.Validate()
|
||||
|
|
|
@ -41,6 +41,7 @@ func (h *handler) showSettingsPage(w http.ResponseWriter, r *http.Request) {
|
|||
DefaultHomePage: user.DefaultHomePage,
|
||||
CategoriesSortingOrder: user.CategoriesSortingOrder,
|
||||
MarkReadOnView: user.MarkReadOnView,
|
||||
MediaPlaybackRate: user.MediaPlaybackRate,
|
||||
}
|
||||
|
||||
timezones, err := h.store.Timezones()
|
||||
|
|
|
@ -62,6 +62,7 @@ func (h *handler) updateSettings(w http.ResponseWriter, r *http.Request) {
|
|||
DefaultReadingSpeed: model.OptionalInt(settingsForm.DefaultReadingSpeed),
|
||||
CJKReadingSpeed: model.OptionalInt(settingsForm.CJKReadingSpeed),
|
||||
DefaultHomePage: model.OptionalString(settingsForm.DefaultHomePage),
|
||||
MediaPlaybackRate: model.OptionalFloat(settingsForm.MediaPlaybackRate),
|
||||
}
|
||||
|
||||
if validationErr := validator.ValidateUserModification(h.store, loggedUser.ID, userModificationRequest); validationErr != nil {
|
||||
|
|
12
internal/ui/static/js/bootstrap.js
vendored
12
internal/ui/static/js/bootstrap.js
vendored
|
@ -152,11 +152,19 @@ document.addEventListener("DOMContentLoaded", () => {
|
|||
});
|
||||
|
||||
// Save and resume media position
|
||||
const elements = document.querySelectorAll("audio[data-last-position],video[data-last-position]");
|
||||
elements.forEach((element) => {
|
||||
const lastPositionElements = document.querySelectorAll("audio[data-last-position],video[data-last-position]");
|
||||
lastPositionElements.forEach((element) => {
|
||||
if (element.dataset.lastPosition) {
|
||||
element.currentTime = element.dataset.lastPosition;
|
||||
}
|
||||
element.ontimeupdate = () => handlePlayerProgressionSave(element);
|
||||
});
|
||||
|
||||
// Set media playback rate
|
||||
const playbackRateElements = document.querySelectorAll("audio[data-playback-rate],video[data-playback-rate]");
|
||||
playbackRateElements.forEach((element) => {
|
||||
if (element.dataset.playbackRate) {
|
||||
element.playbackRate = element.dataset.playbackRate;
|
||||
}
|
||||
});
|
||||
});
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue