mirror of
https://github.com/robbert-vdh/yabridge.git
synced 2026-05-07 03:50:11 +02:00
f944bf4a39
Although all of this stuff is completely untested, and since no host on Linux uses it we'll likely never know whether this implementation is correct.
121 lines
4.6 KiB
C++
121 lines
4.6 KiB
C++
// yabridge: a Wine VST bridge
|
|
// Copyright (C) 2020-2021 Robbert van der Helm
|
|
//
|
|
// This program is free software: you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License as published by
|
|
// the Free Software Foundation, either version 3 of the License, or
|
|
// (at your option) any later version.
|
|
//
|
|
// This program is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
// GNU General Public License for more details.
|
|
//
|
|
// You should have received a copy of the GNU General Public License
|
|
// along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
|
|
#include "context-menu-proxy.h"
|
|
|
|
#include <iostream>
|
|
|
|
Vst3ContextMenuProxyImpl::Vst3ContextMenuProxyImpl(
|
|
Vst3Bridge& bridge,
|
|
Vst3ContextMenuProxy::ConstructArgs&& args)
|
|
: Vst3ContextMenuProxy(std::move(args)), bridge(bridge) {
|
|
bridge.register_context_menu(*this);
|
|
}
|
|
|
|
Vst3ContextMenuProxyImpl::~Vst3ContextMenuProxyImpl() {
|
|
// Also drop the context menu smart pointer on plugin side when this gets
|
|
// dropped
|
|
bridge.send_message(
|
|
Vst3ContextMenuProxy::Destruct{.owner_instance_id = owner_instance_id(),
|
|
.context_menu_id = context_menu_id()});
|
|
bridge.unregister_context_menu(owner_instance_id(), context_menu_id());
|
|
}
|
|
|
|
tresult PLUGIN_API
|
|
Vst3ContextMenuProxyImpl::queryInterface(const Steinberg::TUID _iid,
|
|
void** obj) {
|
|
const tresult result = Vst3ContextMenuProxy::queryInterface(_iid, obj);
|
|
bridge.logger.log_query_interface("In IContextMenu::queryInterface()",
|
|
result, Steinberg::FUID::fromTUID(_iid));
|
|
|
|
return result;
|
|
}
|
|
|
|
int32 PLUGIN_API Vst3ContextMenuProxyImpl::getItemCount() {
|
|
return bridge.send_message(
|
|
YaContextMenu::GetItemCount{.owner_instance_id = owner_instance_id(),
|
|
.context_menu_id = context_menu_id()});
|
|
}
|
|
|
|
tresult PLUGIN_API Vst3ContextMenuProxyImpl::getItem(
|
|
int32 index,
|
|
Steinberg::Vst::IContextMenuItem& item /*out*/,
|
|
Steinberg::Vst::IContextMenuTarget** target /*out*/) {
|
|
// XXX: Should the plugin be able to get targets created by the host this
|
|
// way? We'll just assume that this function won't ever be called by
|
|
// the plugin (but we'll implement a basic version anyways).
|
|
if (index < 0 || index >= static_cast<int32>(items.size())) {
|
|
return Steinberg::kInvalidArgument;
|
|
} else {
|
|
item = items[index];
|
|
*target = context_menu_targets[item.tag];
|
|
|
|
return Steinberg::kResultOk;
|
|
}
|
|
}
|
|
|
|
tresult PLUGIN_API
|
|
Vst3ContextMenuProxyImpl::addItem(const Steinberg::Vst::IContextMenuItem& item,
|
|
Steinberg::Vst::IContextMenuTarget* target) {
|
|
const tresult result = bridge.send_message(YaContextMenu::AddItem{
|
|
.owner_instance_id = owner_instance_id(),
|
|
.context_menu_id = context_menu_id(),
|
|
.item = item,
|
|
.target =
|
|
(target ? std::make_optional<YaContextMenuTarget::ConstructArgs>(
|
|
owner_instance_id(), context_menu_id(), item.tag)
|
|
: std::nullopt)});
|
|
|
|
if (result == Steinberg::kResultOk) {
|
|
items.push_back(item);
|
|
context_menu_targets[item.tag] = target;
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
tresult PLUGIN_API Vst3ContextMenuProxyImpl::removeItem(
|
|
const Steinberg::Vst::IContextMenuItem& item,
|
|
Steinberg::Vst::IContextMenuTarget* /*target*/) {
|
|
const tresult result = bridge.send_message(
|
|
YaContextMenu::RemoveItem{.owner_instance_id = owner_instance_id(),
|
|
.context_menu_id = context_menu_id(),
|
|
.item = item});
|
|
|
|
if (result == Steinberg::kResultOk) {
|
|
items.erase(
|
|
std::remove_if(
|
|
items.begin(), items.end(),
|
|
[&](const Steinberg::Vst::IContextMenuItem& candidate_item) {
|
|
// They didn't implement `operator==` on the struct
|
|
return candidate_item.tag == item.tag;
|
|
}),
|
|
items.end());
|
|
context_menu_targets.erase(item.tag);
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
tresult PLUGIN_API Vst3ContextMenuProxyImpl::popup(Steinberg::UCoord x,
|
|
Steinberg::UCoord y) {
|
|
return bridge.send_message(
|
|
YaContextMenu::Popup{.owner_instance_id = owner_instance_id(),
|
|
.context_menu_id = context_menu_id(),
|
|
.x = x,
|
|
.y = y});
|
|
}
|