Can now click on the release artwork to see it fullscreen

This commit is contained in:
emeric
2025-02-14 16:53:02 +01:00
parent 4ff1c25f22
commit 91c98bc11c
6 changed files with 79 additions and 21 deletions
+13 -1
View File
@@ -9,7 +9,7 @@
<message id="Lms.Explore.Release.template"> <message id="Lms.Explore.Release.template">
<div class="row mb-3 gy-3"> <div class="row mb-3 gy-3">
<div class="col-lg-3 col-md-4"> <div class="col-lg-3 col-md-4">
${cover} ${cover class="Lms-cursor-pointer"}
</div> </div>
<div class="col"> <div class="col">
<h2>${name}${<if-has-release-comment>}<span class="ms-1 text-muted">[${comment}]</span>${</if-has-release-comment>}</h2> <h2>${name}${<if-has-release-comment>}<span class="ms-1 text-muted">[${comment}]</span>${</if-has-release-comment>}</h2>
@@ -45,6 +45,18 @@
${</if-has-similar-releases>} ${</if-has-similar-releases>}
</message> </message>
<message id="Lms.Explore.Release.template.full-cover">
<div class="modal fade" tabindex="-1">
<div class="modal-dialog modal-dialog-centered Lms-cover-full-modal-dialog">
<div class="modal-content bg-transparent border-0">
<div class="modal-body text-center">
${cover-full class="Lms-cover-full"}
</div>
</div>
</div>
</div>
</message>
<message id="Lms.Explore.Release.template.entry-release-artist"> <message id="Lms.Explore.Release.template.entry-release-artist">
${artist class="text-decoration-none link-success"} ${artist class="text-decoration-none link-success"}
</message> </message>
+24
View File
@@ -87,6 +87,30 @@ body {
min-width: 64px; min-width: 64px;
} }
.Lms-cover-full-modal-dialog {
width: auto;
max-width: none;
max-height: 90vh;
display: flex;
align-items: center;
justify-content: center;
}
.Lms-cover-full {
max-width: 100%;
max-height: 95vh;
width: auto;
height: auto;
display: block;
margin: auto;
cursor: pointer;
object-fit: contain;
}
.Lms-cursor-pointer {
cursor: pointer;
}
#lms-mp-progress { #lms-mp-progress {
transition: none; transition: none;
} }
+9 -7
View File
@@ -44,22 +44,24 @@ namespace lms::ui
void ModalManager::show(std::unique_ptr<Wt::WWidget> modalWidget) void ModalManager::show(std::unique_ptr<Wt::WWidget> modalWidget)
{ {
LMS_LOG(UI, DEBUG, "Want to show, id = " << modalWidget->id()); LMS_LOG(UI, DEBUG, "Want to show, id = " << modalWidget->id());
Wt::WWidget* modal{ modalWidget.get() };
addWidget(std::move(modalWidget));
std::ostringstream oss; std::ostringstream oss;
oss oss
<< R"({const modalElement = )" << jsRef() << R"(.getElementsByClassName('modal')[0];)" << R"({const modalElementParent = document.getElementById(')" << modal->id() << R"(');)"
<< R"(const modal = bootstrap.Modal.getOrCreateInstance(modalElement);)" << R"(const modalElement = modalElementParent.getElementsByClassName('modal')[0];)"
<< R"(const modal = bootstrap.Modal.getOrCreateInstance(modalElement,{backdrop:true, keyboard:true, focus:true});)"
<< R"(modal.show();)" << R"(modal.show();)"
<< R"(modalElement.addEventListener('hidden.bs.modal', function () {)" << R"(modalElement.addEventListener('hidden.bs.modal', function () {)"
<< _closed.createCall({ "'" + modalWidget->id() + "'" }) << _closed.createCall({ "'" + modal->id() + "'" })
<< R"(modal.dispose();)" << R"(modal.dispose();)"
<< R"(});})"; << R"(});})";
LMS_LOG(UI, DEBUG, "Running JS '" << oss.str() << "'"); LMS_LOG(UI, DEBUG, "Running JS '" << oss.str() << "'");
doJavaScript(oss.str()); // Execute in the modal's context to make sure the DOM is properly updated
modal->doJavaScript(oss.str());
addWidget(std::move(modalWidget));
} }
void ModalManager::dispose(Wt::WWidget* modalWidget) void ModalManager::dispose(Wt::WWidget* modalWidget)
@@ -74,6 +76,6 @@ namespace lms::ui
LMS_LOG(UI, DEBUG, "Running JS '" << oss.str() << "'"); LMS_LOG(UI, DEBUG, "Running JS '" << oss.str() << "'");
doJavaScript(oss.str()); modalWidget->doJavaScript(oss.str());
} }
} // namespace lms::ui } // namespace lms::ui
+12 -1
View File
@@ -24,6 +24,7 @@
#include <Wt/WAnchor.h> #include <Wt/WAnchor.h>
#include <Wt/WImage.h> #include <Wt/WImage.h>
#include <Wt/WPushButton.h> #include <Wt/WPushButton.h>
#include <Wt/WTemplate.h>
#include "av/IAudioFile.hpp" #include "av/IAudioFile.hpp"
#include "core/String.hpp" #include "core/String.hpp"
@@ -257,7 +258,17 @@ namespace lms::ui
refreshReleaseArtists(release); refreshReleaseArtists(release);
bindWidget<Wt::WImage>("cover", utils::createReleaseCover(release->getId(), ArtworkResource::Size::Large)); auto* image{ bindWidget<Wt::WImage>("cover", utils::createReleaseCover(release->getId(), ArtworkResource::Size::Large)) };
image->clicked().connect([=] {
auto fullCover{ std::make_unique<Wt::WTemplate>(Wt::WString::tr("Lms.Explore.Release.template.full-cover")) };
fullCover->bindNew<Wt::WImage>("cover-full", Wt::WLink{ LmsApp->getArtworkResource()->getReleaseCoverUrl(*releaseId) });
Wt::WTemplate* fullCoverPtr{ fullCover.get() };
fullCover->clicked().connect([=] {
LmsApp->getModalManager().dispose(fullCoverPtr);
});
LmsApp->getModalManager().show(std::move(fullCover));
});
Wt::WContainerWidget* clusterContainers{ bindNew<Wt::WContainerWidget>("clusters") }; Wt::WContainerWidget* clusterContainers{ bindNew<Wt::WContainerWidget>("clusters") };
{ {
+14 -7
View File
@@ -52,7 +52,7 @@ namespace lms::ui
beingDeleted(); beingDeleted();
} }
std::string ArtworkResource::getArtistImageUrl(db::ArtistId artistId, Size size) const std::string ArtworkResource::getArtistImageUrl(db::ArtistId artistId, std::optional<Size> size) const
{ {
std::string url; std::string url;
@@ -73,7 +73,7 @@ namespace lms::ui
return url; return url;
} }
std::string ArtworkResource::getReleaseCoverUrl(db::ReleaseId releaseId, Size size) const std::string ArtworkResource::getReleaseCoverUrl(db::ReleaseId releaseId, std::optional<Size> size) const
{ {
std::string url; std::string url;
@@ -107,7 +107,7 @@ namespace lms::ui
return url; return url;
} }
std::string ArtworkResource::getTrackImageUrl(db::TrackId trackId, Size size) const std::string ArtworkResource::getTrackImageUrl(db::TrackId trackId, std::optional<Size> size) const
{ {
std::string url; std::string url;
@@ -135,14 +135,21 @@ namespace lms::ui
return url; return url;
} }
std::string ArtworkResource::getImageUrl(db::ImageId imageId, Size size, std::string_view type) const std::string ArtworkResource::getImageUrl(db::ImageId imageId, std::optional<Size> size, std::string_view type) const
{ {
return url() + "&imageid=" + imageId.toString() + "&size=" + std::to_string(static_cast<std::size_t>(size)) + "&type=" + std::string{ type }; std::string res{ url() + "&imageid=" + imageId.toString() + "&type=" + std::string{ type } };
if (size)
res += "&size=" + std::to_string(static_cast<std::size_t>(*size));
return res;
} }
std::string ArtworkResource::getImageUrl(db::TrackId trackId, Size size, std::string_view type) const std::string ArtworkResource::getImageUrl(db::TrackId trackId, std::optional<Size> size, std::string_view type) const
{ {
return url() + "&trackid=" + trackId.toString() + "&size=" + std::to_string(static_cast<std::size_t>(size)) + "&type=" + std::string{ type }; std::string res{ url() + "&trackid=" + trackId.toString() + "&type=" + std::string{ type } };
if (size)
res += "&size=" + std::to_string(static_cast<std::size_t>(*size));
return res;
} }
std::string ArtworkResource::getDefaultArtistImageUrl() const std::string ArtworkResource::getDefaultArtistImageUrl() const
+7 -5
View File
@@ -19,6 +19,8 @@
#pragma once #pragma once
#include <optional>
#include <Wt/WResource.h> #include <Wt/WResource.h>
#include "database/ArtistId.hpp" #include "database/ArtistId.hpp"
@@ -42,13 +44,13 @@ namespace lms::ui
Large = 512, Large = 512,
}; };
std::string getArtistImageUrl(db::ArtistId artistId, Size size) const; std::string getArtistImageUrl(db::ArtistId artistId, std::optional<Size> size = std::nullopt) const;
std::string getReleaseCoverUrl(db::ReleaseId releaseId, Size size) const; std::string getReleaseCoverUrl(db::ReleaseId releaseId, std::optional<Size> size = std::nullopt) const;
std::string getTrackImageUrl(db::TrackId trackId, Size size) const; std::string getTrackImageUrl(db::TrackId trackId, std::optional<Size> size = std::nullopt) const;
private: private:
std::string getImageUrl(db::ImageId imageId, Size size, std::string_view type) const; std::string getImageUrl(db::ImageId imageId, std::optional<Size> size, std::string_view type) const;
std::string getImageUrl(db::TrackId trackId, Size size, std::string_view type) const; std::string getImageUrl(db::TrackId trackId, std::optional<Size> size, std::string_view type) const;
std::string getDefaultArtistImageUrl() const; std::string getDefaultArtistImageUrl() const;
std::string getDefaultReleaseCoverUrl() const; std::string getDefaultReleaseCoverUrl() const;