feat: nicer Humanoid ?scalenearest rendering
This commit is contained in:
parent
ed3a3d90fb
commit
ed8b22c472
@ -1374,4 +1374,35 @@ Json const& Humanoid::defaultMovementParameters() const {
|
|||||||
return m_defaultMovementParameters;
|
return m_defaultMovementParameters;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pair<Vec2F, Directives> Humanoid::extractScaleFromDirectives(Directives const& directives) {
|
||||||
|
if (!directives)
|
||||||
|
return make_pair(Vec2F::filled(1.f), Directives());
|
||||||
|
|
||||||
|
List<StringView> operations;
|
||||||
|
size_t totalLength = 0;
|
||||||
|
Maybe<Vec2F> scale;
|
||||||
|
|
||||||
|
for (auto& entry : directives.shared->entries) {
|
||||||
|
auto string = entry.string(*directives.shared);
|
||||||
|
const ScaleImageOperation* op = nullptr;
|
||||||
|
if (string.beginsWith("scalenearest") && string.utf8().find("skip") == NPos)
|
||||||
|
op = entry.loadOperation(*directives.shared).ptr<ScaleImageOperation>();
|
||||||
|
|
||||||
|
if (op)
|
||||||
|
scale = scale.value(Vec2F::filled(1.f)).piecewiseMultiply(op->scale);
|
||||||
|
else
|
||||||
|
totalLength += operations.emplace_back(string).utf8Size();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!scale)
|
||||||
|
return make_pair(Vec2F::filled(1.f), directives);
|
||||||
|
|
||||||
|
String mergedDirectives;
|
||||||
|
mergedDirectives.reserve(totalLength);
|
||||||
|
for (auto& directive : operations)
|
||||||
|
mergedDirectives.append(directive.utf8Ptr(), directive.utf8Size());
|
||||||
|
|
||||||
|
return make_pair(*scale, Directives(mergedDirectives));
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -240,6 +240,10 @@ public:
|
|||||||
|
|
||||||
Json const& defaultMovementParameters() const;
|
Json const& defaultMovementParameters() const;
|
||||||
|
|
||||||
|
// Extracts scalenearest from directives and returns the combined scale and
|
||||||
|
// a new Directives without those scalenearest directives.
|
||||||
|
static pair<Vec2F, Directives> extractScaleFromDirectives(Directives const& directives);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
struct HandDrawingInfo {
|
struct HandDrawingInfo {
|
||||||
List<Drawable> itemDrawables;
|
List<Drawable> itemDrawables;
|
||||||
|
@ -475,10 +475,19 @@ void Npc::render(RenderCallback* renderCallback) {
|
|||||||
renderLayer = loungeAnchor->loungeRenderLayer;
|
renderLayer = loungeAnchor->loungeRenderLayer;
|
||||||
|
|
||||||
m_tools->setupHumanoidHandItemDrawables(m_humanoid);
|
m_tools->setupHumanoidHandItemDrawables(m_humanoid);
|
||||||
|
|
||||||
|
DirectivesGroup humanoidDirectives;
|
||||||
|
Vec2F scale = Vec2F::filled(1.f);
|
||||||
|
for (auto& directives : m_statusController->parentDirectives().list()) {
|
||||||
|
auto result = Humanoid::extractScaleFromDirectives(directives);
|
||||||
|
scale = scale.piecewiseMultiply(result.first);
|
||||||
|
humanoidDirectives.append(result.second);
|
||||||
|
}
|
||||||
|
|
||||||
for (auto& drawable : m_humanoid.render()) {
|
for (auto& drawable : m_humanoid.render()) {
|
||||||
drawable.translate(position());
|
drawable.translate(position());
|
||||||
if (drawable.isImage())
|
if (drawable.isImage())
|
||||||
drawable.imagePart().addDirectivesGroup(m_statusController->parentDirectives(), true);
|
drawable.imagePart().addDirectivesGroup(humanoidDirectives, true);
|
||||||
renderCallback->addDrawable(std::move(drawable), renderLayer);
|
renderCallback->addDrawable(std::move(drawable), renderLayer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -373,11 +373,25 @@ List<Drawable> Player::drawables() const {
|
|||||||
drawables.appendAll(m_techController->backDrawables());
|
drawables.appendAll(m_techController->backDrawables());
|
||||||
if (!m_techController->parentHidden()) {
|
if (!m_techController->parentHidden()) {
|
||||||
m_tools->setupHumanoidHandItemDrawables(*m_humanoid);
|
m_tools->setupHumanoidHandItemDrawables(*m_humanoid);
|
||||||
|
|
||||||
|
// Auto-detect any ?scalenearest and apply them as a direct scale on the Humanoid's drawables instead.
|
||||||
|
DirectivesGroup humanoidDirectives;
|
||||||
|
Vec2F scale = Vec2F::filled(1.f);
|
||||||
|
auto extractScale = [&](List<Directives> const& list) {
|
||||||
|
for (auto& directives : list) {
|
||||||
|
auto result = Humanoid::extractScaleFromDirectives(directives);
|
||||||
|
scale = scale.piecewiseMultiply(result.first);
|
||||||
|
humanoidDirectives.append(result.second);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
extractScale(m_techController->parentDirectives().list());
|
||||||
|
extractScale(m_statusController->parentDirectives().list());
|
||||||
|
|
||||||
for (auto& drawable : m_humanoid->render()) {
|
for (auto& drawable : m_humanoid->render()) {
|
||||||
|
drawable.scale(scale);
|
||||||
drawable.translate(position() + m_techController->parentOffset());
|
drawable.translate(position() + m_techController->parentOffset());
|
||||||
if (drawable.isImage()) {
|
if (drawable.isImage()) {
|
||||||
drawable.imagePart().addDirectivesGroup(m_techController->parentDirectives(), true);
|
drawable.imagePart().addDirectivesGroup(humanoidDirectives, true);
|
||||||
drawable.imagePart().addDirectivesGroup(m_statusController->parentDirectives(), true);
|
|
||||||
|
|
||||||
if (auto anchor = as<LoungeAnchor>(m_movementController->entityAnchor())) {
|
if (auto anchor = as<LoungeAnchor>(m_movementController->entityAnchor())) {
|
||||||
if (auto& directives = anchor->directives)
|
if (auto& directives = anchor->directives)
|
||||||
|
Loading…
Reference in New Issue
Block a user