From 4d821219f87cdac28d6e1775587a906bbabe8aab Mon Sep 17 00:00:00 2001 From: jules Date: Tue, 24 Oct 2017 15:55:32 +0100 Subject: [PATCH] BLOCKS: Throttle frequency of topology change listener callbacks --- .../topology/juce_PhysicalTopologySource.cpp | 48 +++++++++++++++---- 1 file changed, 39 insertions(+), 9 deletions(-) diff --git a/modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.cpp b/modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.cpp index c1d7838e2d..3d9d15fef1 100644 --- a/modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.cpp +++ b/modules/juce_blocks_basics/topology/juce_PhysicalTopologySource.cpp @@ -505,8 +505,7 @@ struct PhysicalTopologySource::Internal } //============================================================================== - // The following methods will be called by the DeviceToHostPacketDecoder: - + // The following methods will be called by the HostPacketDecoder: void beginTopology (int numDevices, int numConnections) { incomingTopologyDevices.clearQuick(); @@ -815,12 +814,13 @@ struct PhysicalTopologySource::Internal for (auto& packet : packets) { - lastGlobalPingTime = juce::Time::getCurrentTime(); auto data = static_cast (packet.getData()); BlocksProtocol::HostPacketDecoder ::processNextPacket (*this, *data, data + 1, (int) packet.getSize() - 1); } + + lastGlobalPingTime = juce::Time::getCurrentTime(); } JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (ConnectedDeviceGroup) @@ -833,11 +833,13 @@ struct PhysicalTopologySource::Internal { Detector() : defaultDetector (new MIDIDeviceDetector()), deviceDetector (*defaultDetector) { + topologyBroadcastThrottle.detector = this; startTimer (10); } Detector (DeviceDetector& dd) : deviceDetector (dd) { + topologyBroadcastThrottle.detector = this; startTimer (10); } @@ -947,12 +949,7 @@ struct PhysicalTopologySource::Internal currentTopology.connections.swapWith (newDeviceConnections); } - for (auto d : activeTopologySources) - d->listeners.call (&TopologySource::Listener::topologyChanged); - - #if DUMP_TOPOLOGY - dumpTopology (currentTopology); - #endif + topologyBroadcastThrottle.scheduleTopologyChangeCallback(); } void handleSharedDataACK (Block::UID deviceID, uint32 packetCounter) const @@ -1193,6 +1190,39 @@ struct PhysicalTopologySource::Internal juce::OwnedArray connectedDeviceGroups; + //============================================================================== + /** Flurries of topology messages sometimes arrive due to loose connections. + Avoid informing listeners until they've stabilised. + */ + struct TopologyBroadcastThrottle : private juce::Timer + { + TopologyBroadcastThrottle() = default; + + void scheduleTopologyChangeCallback() { startTimer (750); } + + void timerCallback() override + { + if (detector->currentTopology != lastTopology) + { + lastTopology = detector->currentTopology; + + for (auto* d : detector->activeTopologySources) + d->listeners.call (&TopologySource::Listener::topologyChanged); + + #if DUMP_TOPOLOGY + dumpTopology (lastTopology); + #endif + } + + stopTimer(); + } + + Detector* detector = nullptr; + BlockTopology lastTopology; + }; + + TopologyBroadcastThrottle topologyBroadcastThrottle; + JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Detector) };