diff --git a/frontend/src/components/GraphCanvas.svelte b/frontend/src/components/GraphCanvas.svelte
index a8248a6..1ffc482 100644
--- a/frontend/src/components/GraphCanvas.svelte
+++ b/frontend/src/components/GraphCanvas.svelte
@@ -113,13 +113,10 @@
return pt.matrixTransform(ctm.inverse());
}
- function isNodeHidden(nodeName: string): boolean {
+ function isNodeHidden(nd: { name: string; nick: string }): boolean {
+ const dn = displayName(nd).toLowerCase();
for (const rule of $patchbay.hide_rules) {
- try {
- if (new RegExp(rule, 'i').test(nodeName)) return true;
- } catch {
- if (nodeName.toLowerCase().includes(rule.toLowerCase())) return true;
- }
+ if (dn === rule.toLowerCase()) return true;
}
return false;
}
@@ -145,7 +142,7 @@
for (const port of p) portMap.set(port.id, port);
// Filter hidden nodes
- let visible = n.filter(nd => !isNodeHidden(nd.name));
+ let visible = n.filter(nd => !isNodeHidden(nd));
// Merge nodes by prefix (unless split mode)
if (!splitNodes) {
@@ -223,8 +220,8 @@
// Check if both endpoint nodes are visible
const outNode = $nodes.find(n => n.id === outPort.node_id);
const inNode = $nodes.find(n => n.id === inPort.node_id);
- if (outNode && isNodeHidden(outNode.name)) return null;
- if (inNode && isNodeHidden(inNode.name)) return null;
+ if (outNode && isNodeHidden(outNode)) return null;
+ if (inNode && isNodeHidden(inNode)) return null;
const pinned = pb.pinned_connections.includes(link.id);
return { ...link, outPort, inPort, pinned };
}).filter(Boolean) as Array;
diff --git a/frontend/src/lib/stores.ts b/frontend/src/lib/stores.ts
index 0e4304e..f6d86cf 100644
--- a/frontend/src/lib/stores.ts
+++ b/frontend/src/lib/stores.ts
@@ -322,11 +322,20 @@ export async function saveProfile(name: string) {
});
}
+ const volumes: Record = {};
+ const mutes: Record = {};
+ for (const n of currentNodes) {
+ volumes[n.name] = n.volume;
+ mutes[n.name] = n.mute;
+ }
+
const profile: PatchbayProfile = {
name,
connections,
hide_rules: [...pb.hide_rules],
merge_rules: [...pb.merge_rules],
+ volumes,
+ mutes,
};
patchbay.update(pb => ({
@@ -337,11 +346,26 @@ export async function saveProfile(name: string) {
savePatchbayState();
}
+async function applyProfileVolumes(profile: PatchbayProfile) {
+ if (!profile.volumes && !profile.mutes) return;
+ const currentNodes = get_store_value(nodes);
+ for (const n of currentNodes) {
+ if (profile.volumes?.[n.name] !== undefined) {
+ await setNodeVolume(n.id, profile.volumes[n.name]);
+ }
+ if (profile.mutes?.[n.name] !== undefined) {
+ await setNodeMute(n.id, profile.mutes[n.name]);
+ }
+ }
+}
+
export function loadProfile(name: string) {
patchbay.update(pb => ({ ...pb, active_profile: name }));
const pb = get_store_value(patchbay);
// Always apply connections when explicitly loading a profile
applyPatchbay(pb);
+ const profile = pb.profiles[name];
+ if (profile) applyProfileVolumes(profile);
savePatchbayState();
}
diff --git a/frontend/src/lib/types.ts b/frontend/src/lib/types.ts
index ad7b92a..d59dafb 100644
--- a/frontend/src/lib/types.ts
+++ b/frontend/src/lib/types.ts
@@ -73,6 +73,8 @@ export interface PatchbayProfile {
connections: ConnectionRule[];
hide_rules?: string[];
merge_rules?: string[];
+ volumes?: Record; // PW node name → volume (0..1)
+ mutes?: Record; // PW node name → mute state
}
export interface PatchbayState {