Lv2Proc: Sort scale point maps (#6859)

lilv can return the scale points in randomized order, and so the linked
models (of stereo effects wit 2 `Lv2Proc`) may have different scale
points. This would mean that the same combo enumeration value would have
different float values in linked models. This problem is fixed by
sorting the scale values.

Also, it is more natural for users if scale points are enumerated in a
numerical order.
This commit is contained in:
Johannes Lorenz
2023-09-22 23:42:45 +02:00
committed by Johannes Lorenz
parent 7aca8ae726
commit 94608eaad1
2 changed files with 23 additions and 11 deletions

View File

@@ -47,8 +47,14 @@ struct LilvNodesDeleter
void operator()(LilvNodes* n) { lilv_nodes_free(n); }
};
struct LilvScalePointsDeleter
{
void operator()(LilvScalePoints* s) { lilv_scale_points_free(s); }
};
using AutoLilvNode = std::unique_ptr<LilvNode, LilvNodeDeleter>;
using AutoLilvNodes = std::unique_ptr<LilvNodes, LilvNodesDeleter>;
using AutoLilvScalePoints = std::unique_ptr<LilvScalePoints, LilvScalePointsDeleter>;
/**
Return QString from a plugin's node, everything will be freed automatically

View File

@@ -574,19 +574,25 @@ void Lv2Proc::createPort(std::size_t portNum)
break;
case Lv2Ports::Vis::Enumeration:
{
auto comboModel = new ComboBoxModel(nullptr, dispName);
LilvScalePoints* sps =
lilv_port_get_scale_points(m_plugin, lilvPort);
LILV_FOREACH(scale_points, i, sps)
ComboBoxModel* comboModel = new ComboBoxModel(nullptr, dispName);
{
const LilvScalePoint* sp = lilv_scale_points_get(sps, i);
ctrl->m_scalePointMap.push_back(lilv_node_as_float(
lilv_scale_point_get_value(sp)));
comboModel->addItem(
lilv_node_as_string(
lilv_scale_point_get_label(sp)));
AutoLilvScalePoints sps (static_cast<LilvScalePoints*>(lilv_port_get_scale_points(m_plugin, lilvPort)));
// temporary map, since lilv may return scale points in random order
std::map<float, const char*> scalePointMap;
LILV_FOREACH(scale_points, i, sps.get())
{
const LilvScalePoint* sp = lilv_scale_points_get(sps.get(), i);
const float f = lilv_node_as_float(lilv_scale_point_get_value(sp));
const char* s = lilv_node_as_string(lilv_scale_point_get_label(sp));
scalePointMap[f] = s;
}
for (const auto& [f,s] : scalePointMap)
{
ctrl->m_scalePointMap.push_back(f);
comboModel->addItem(s);
}
}
lilv_scale_points_free(sps);
ctrl->m_connectedModel.reset(comboModel);
// TODO: use default value on comboModel, too?
break;