Skip to content

Commit

Permalink
fix layout issues on certain device resolutions, avoid piwheels build…
Browse files Browse the repository at this point in the history
… issues (again), enable gain/mute support for camilladsp, allow levels view to be driven by series provided by device rather than hardcoded, decouple rest of ui from minidsp specific features
  • Loading branch information
3ll3d00d committed Jun 3, 2023
1 parent 67af4a8 commit 7631b91
Show file tree
Hide file tree
Showing 15 changed files with 667 additions and 229 deletions.
12 changes: 1 addition & 11 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -282,10 +282,6 @@ The images field has special treatment as there can be a variable number of imag
ip: 192.168.1.181
port: 1710
timeout_secs: 2
input_gains:
mixer: input
channels:
- 4
channels:
- 4
- 7
Expand All @@ -308,13 +304,7 @@ On unload, the camilladsp configuration will be updated as follows:

User controlled master volume adjustments are supported using the [Volume](https://github.com/HEnquist/camilladsp/blob/master/README.md#volume) filter if that filter has been configured in the pipeline.

BEQ specific input gain adjustments are supported via the use of a gain option on the [Mixer](https://github.com/HEnquist/camilladsp/blob/master/README.md#mixers) if the `input_gains` key is configured in the device configuration.
This requires 2 pieces of configuration:

* the mixer name
* a list of 1 or more channels to apply the adjustment to

Note that ezbeq will take exclusive ownership over these values and will overwrite the gain value specified in the configuration as required. Use an additional mixer in the pipeline if further user configuration is required.
BEQ specific input gain adjustments are supported via the use of a [Gain](https://github.com/HEnquist/camilladsp#gain) filter which is inserted into the pipeline ahead of the BEQ filters themselves.

## Starting ezbeq on bootup

Expand Down
58 changes: 43 additions & 15 deletions ezbeq/apis/ws.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import abc
import json
import logging
from collections import defaultdict
from typing import Callable, Optional, List, Dict
from typing import Callable, Optional, List, Dict, TypeVar, Generic

from autobahn.exception import Disconnected
from autobahn.twisted import WebSocketServerProtocol, WebSocketServerFactory
Expand All @@ -11,23 +12,25 @@
logger = logging.getLogger('ezbeq.ws')


class WsServer:
class WsServerFactory(abc.ABC):
@abc.abstractmethod
def broadcast(self, msg: str):
pass

def __init__(self):
self.__factory = WsServerFactory()
@abc.abstractmethod
def has_levels_client(self, device: str) -> bool:
pass

@property
def factory(self) -> 'WsServerFactory':
return self.__factory
@abc.abstractmethod
def set_levels_provider(self, name: str, broadcaster: Callable[[], None]):
pass

def broadcast(self, msg: str):
self.__factory.broadcast(msg)
@abc.abstractmethod
def init(self, state_provider: Callable[[], str]):
pass

def levels(self, device: str, levels: dict) -> bool:
return self.__factory.send_levels(device, json.dumps({'message': 'Levels', 'data': levels}))

def has_levels_client(self, device: str) -> bool:
return self.__factory.has_levels_client(device)
T = TypeVar("T", bound=WsServerFactory)


class WsProtocol(WebSocketServerProtocol):
Expand All @@ -54,11 +57,11 @@ def onMessage(self, payload, is_binary):
logger.exception('Message received failure')


class WsServerFactory(WebSocketServerFactory):
class AutobahnWsServerFactory(WsServerFactory, WebSocketServerFactory):
protocol = WsProtocol

def __init__(self, *args, **kwargs):
super(WsServerFactory, self).__init__(*args, **kwargs)
super(AutobahnWsServerFactory, self).__init__(*args, **kwargs)
self.__clients: List[WsProtocol] = []
self.__levels_client: Dict[str, List[WsProtocol]] = defaultdict(list)
self.__state_provider: Optional[Callable[[], str]] = None
Expand Down Expand Up @@ -152,3 +155,28 @@ def send_levels(self, device: str, msg: str):

def has_levels_client(self, device: str):
return len(self.__levels_client.get(device, [])) > 0


class WsServer(abc.ABC, Generic[T]):

def __init__(self, factory: T):
self.__factory = factory

@property
def factory(self) -> T:
return self.__factory

def broadcast(self, msg: str):
self.factory.broadcast(msg)

def levels(self, device: str, levels: dict) -> bool:
return self.factory.send_levels(device, json.dumps({'message': 'Levels', 'data': levels}))

def has_levels_client(self, device: str) -> bool:
return self.factory.has_levels_client(device)


class AutobahnWsServer(WsServer[AutobahnWsServerFactory]):

def __init__(self):
super().__init__(AutobahnWsServerFactory())

0 comments on commit 7631b91

Please sign in to comment.