Some UI tweaks + display roles for performers
This commit is contained in:
+9
-5
@@ -94,13 +94,14 @@
|
||||
${<if-has-track-number>}${track-number}${</if-has-track-number>}
|
||||
</div>
|
||||
<div class="row align-items-center flex-fill overflow-hidden">
|
||||
<div class="col-12 col-md-6">
|
||||
<div class="col-12 col-md-8">
|
||||
<div class="p-2">
|
||||
${name}
|
||||
${<if-has-artists>}${artists class="d-block d-md-none"}${</if-has-artists>}
|
||||
${<if-has-artist-links>}${artist-links}${</if-has-artist-links>}
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-md-6">
|
||||
<div class="col-md-4">
|
||||
${<if-has-artists>}${artists-md class="d-none d-md-block"}${</if-has-artists>}
|
||||
</div>
|
||||
</div>
|
||||
@@ -123,9 +124,12 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
${<if-has-artist-links>}
|
||||
${artist-links}
|
||||
${</if-has-artist-links>}
|
||||
</message>
|
||||
|
||||
<message id="Lms.Explore.Release.template.artist-links-entry">
|
||||
<div class=" text-muted small ms-2 d-flex">
|
||||
<span class="text-nowrap text-muted">${role} — </span>${anchors class="ms-1"}
|
||||
</div>
|
||||
</message>
|
||||
|
||||
<message id="Lms.Explore.Release.template.release-info">
|
||||
|
||||
@@ -185,6 +185,24 @@ namespace lms::ui
|
||||
|
||||
return core::stringUtils::readAs<ReleaseId::ValueType>(wApp->internalPathNextPart("/release/"));
|
||||
}
|
||||
|
||||
void fillTrackArtistLinks(Wt::WTemplate* trackEntry, const db::Track::pointer& track)
|
||||
{
|
||||
const std::map<Wt::WString, std::set<ArtistId>> artistsByRole{ TrackListHelpers::getArtistsByRole(track->getId()) };
|
||||
|
||||
if (artistsByRole.empty())
|
||||
return;
|
||||
|
||||
trackEntry->setCondition("if-has-artist-links", true);
|
||||
Wt::WContainerWidget* artistLinksContainer = trackEntry->bindNew<Wt::WContainerWidget>("artist-links");
|
||||
|
||||
for (auto& [role, artists] : artistsByRole)
|
||||
{
|
||||
Wt::WTemplate* artistLinkEntry{ artistLinksContainer->addNew<Wt::WTemplate>(Wt::WString::tr("Lms.Explore.Release.template.artist-links-entry")) };
|
||||
artistLinkEntry->bindString("role", role, Wt::TextFormat::Plain);
|
||||
artistLinkEntry->bindWidget("anchors", utils::createArtistAnchorList(std::vector<db::ArtistId>(std::cbegin(artists), std::cend(artists))));
|
||||
}
|
||||
}
|
||||
} // namespace
|
||||
|
||||
Release::Release(Filters& filters, PlayQueueController& playQueueController)
|
||||
@@ -415,7 +433,7 @@ namespace lms::ui
|
||||
const db::TrackId trackId{ track->getId() };
|
||||
const auto discNumber{ track->getDiscNumber() };
|
||||
|
||||
Wt::WContainerWidget* container;
|
||||
Wt::WContainerWidget* container{};
|
||||
if (useSubtitleContainers && discNumber)
|
||||
container = getOrAddDiscContainer(*discNumber, track->getDiscSubtitle());
|
||||
else if (hasDiscSubtitle && !discNumber)
|
||||
@@ -437,45 +455,7 @@ namespace lms::ui
|
||||
entry->bindWidget("artists-md", utils::createArtistDisplayNameWithAnchors(track->getArtistDisplayName(), artists));
|
||||
}
|
||||
|
||||
{ // Generate all artist link widgets
|
||||
// TODO: add config to chose whether to only show Remixer or show All.
|
||||
std::vector<std::pair<Wt::WString, std::unique_ptr<Wt::WContainerWidget>>> artistLinksList;
|
||||
auto createTrackArtistLink = [&](TrackArtistLinkType linkType, const std::string& trkey) {
|
||||
const auto artists{ track->getArtistIds({ linkType }) };
|
||||
const auto text = Wt::WString::trn(trkey, artists.size()).arg(artists.size());
|
||||
auto anchors{ utils::createArtistAnchorList(std::vector(std::cbegin(artists), std::cend(artists))) };
|
||||
if (!artists.empty())
|
||||
{
|
||||
auto myPair = std::make_pair(text, std::move(anchors));
|
||||
artistLinksList.push_back(std::move(myPair));
|
||||
}
|
||||
};
|
||||
createTrackArtistLink(TrackArtistLinkType::Remixer, "Lms.Explore.Artists.linktype-remixer");
|
||||
createTrackArtistLink(TrackArtistLinkType::Producer, "Lms.Explore.Artists.linktype-producer");
|
||||
createTrackArtistLink(TrackArtistLinkType::Performer, "Lms.Explore.Artists.linktype-performer");
|
||||
createTrackArtistLink(TrackArtistLinkType::Composer, "Lms.Explore.Artists.linktype-composer");
|
||||
createTrackArtistLink(TrackArtistLinkType::Conductor, "Lms.Explore.Artists.linktype-conductor");
|
||||
createTrackArtistLink(TrackArtistLinkType::Lyricist, "Lms.Explore.Artists.linktype-lyricist");
|
||||
createTrackArtistLink(TrackArtistLinkType::Mixer, "Lms.Explore.Artists.linktype-mixer");
|
||||
|
||||
if (!artistLinksList.empty())
|
||||
{
|
||||
entry->setCondition("if-has-artist-links", true);
|
||||
Wt::WContainerWidget* artistLinksContainer = entry->bindNew<Wt::WContainerWidget>("artist-links");
|
||||
|
||||
for (auto& [role, artistWidget] : artistLinksList)
|
||||
{
|
||||
auto* currContainer = artistLinksContainer->addNew<Wt::WContainerWidget>();
|
||||
currContainer->setStyleClass("overflow-hidden ms-5 pb-2 px-2 text-small d-flex");
|
||||
|
||||
auto* roleText = currContainer->addNew<Wt::WText>(role + Wt::WString::fromUTF8(" — "));
|
||||
roleText->setStyleClass("d-inline");
|
||||
|
||||
auto* newArtistWidget = currContainer->addWidget(std::move(artistWidget));
|
||||
newArtistWidget->setInline(true);
|
||||
}
|
||||
}
|
||||
}
|
||||
fillTrackArtistLinks(entry, track);
|
||||
|
||||
auto trackNumber{ track->getTrackNumber() };
|
||||
if (trackNumber)
|
||||
|
||||
@@ -50,18 +50,8 @@ namespace lms::ui::TrackListHelpers
|
||||
{
|
||||
using namespace db;
|
||||
|
||||
void showTrackInfoModal(db::TrackId trackId, Filters& filters)
|
||||
std::map<Wt::WString, std::set<ArtistId>> getArtistsByRole(db::TrackId trackId)
|
||||
{
|
||||
auto transaction{ LmsApp->getDbSession().createReadTransaction() };
|
||||
|
||||
const db::Track::pointer track{ Track::find(LmsApp->getDbSession(), trackId) };
|
||||
if (!track)
|
||||
return;
|
||||
|
||||
auto trackInfo{ std::make_unique<Template>(Wt::WString::tr("Lms.Explore.Tracks.template.track-info")) };
|
||||
Wt::WWidget* trackInfoPtr{ trackInfo.get() };
|
||||
trackInfo->addFunction("tr", &Wt::WTemplate::Functions::tr);
|
||||
|
||||
std::map<Wt::WString, std::set<ArtistId>> artistMap;
|
||||
|
||||
auto addArtists = [&](TrackArtistLinkType linkType, const char* type) {
|
||||
@@ -73,7 +63,7 @@ namespace lms::ui::TrackListHelpers
|
||||
return;
|
||||
|
||||
Wt::WString typeStr{ Wt::WString::trn(type, artistIds.results.size()) };
|
||||
;
|
||||
|
||||
for (ArtistId artistId : artistIds.results)
|
||||
artistMap[typeStr].insert(artistId);
|
||||
};
|
||||
@@ -103,6 +93,22 @@ namespace lms::ui::TrackListHelpers
|
||||
artistMap.erase(itRolelessPerformers);
|
||||
}
|
||||
|
||||
return artistMap;
|
||||
}
|
||||
|
||||
void showTrackInfoModal(db::TrackId trackId, Filters& filters)
|
||||
{
|
||||
auto transaction{ LmsApp->getDbSession().createReadTransaction() };
|
||||
|
||||
const db::Track::pointer track{ Track::find(LmsApp->getDbSession(), trackId) };
|
||||
if (!track)
|
||||
return;
|
||||
|
||||
auto trackInfo{ std::make_unique<Template>(Wt::WString::tr("Lms.Explore.Tracks.template.track-info")) };
|
||||
Wt::WWidget* trackInfoPtr{ trackInfo.get() };
|
||||
trackInfo->addFunction("tr", &Wt::WTemplate::Functions::tr);
|
||||
|
||||
std::map<Wt::WString, std::set<ArtistId>> artistMap{ getArtistsByRole(trackId) };
|
||||
if (!artistMap.empty())
|
||||
{
|
||||
trackInfo->setCondition("if-has-artist", true);
|
||||
|
||||
@@ -19,10 +19,14 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <map>
|
||||
#include <memory>
|
||||
#include <set>
|
||||
|
||||
#include <Wt/WString.h>
|
||||
#include <Wt/WWidget.h>
|
||||
|
||||
#include "database/ArtistId.hpp"
|
||||
#include "database/Object.hpp"
|
||||
#include "database/TrackId.hpp"
|
||||
|
||||
@@ -39,6 +43,7 @@ namespace lms::ui
|
||||
|
||||
namespace lms::ui::TrackListHelpers
|
||||
{
|
||||
std::map<Wt::WString, std::set<db::ArtistId>> getArtistsByRole(db::TrackId trackId);
|
||||
void showTrackInfoModal(db::TrackId trackId, Filters& filters);
|
||||
void showTrackLyricsModal(db::TrackId trackId);
|
||||
std::unique_ptr<Wt::WWidget> createEntry(const db::ObjectPtr<db::Track>& track, PlayQueueController& playQueueController, Filters& filters);
|
||||
|
||||
Reference in New Issue
Block a user