@@ -17,14 +17,16 @@ public class DeviceManager
1717 {
1818 public event InterfaceChangeHandler InterfaceChanged ;
1919 public event DeviceConnectHandler DeviceConnected ;
20- private IScope mainDevice = null ;
21- public IScope MainDevice { get { return mainDevice ; } }
22- public bool SmartScopeConnected { get { return mainDevice is SmartScope ; } }
20+ private IDevice activeDevice = null ;
21+ public IDevice ActiveDevice { get { return activeDevice ; } }
2322 Thread pollThread ;
2423 private List < IHardwareInterface > connectedList = new List < IHardwareInterface > ( ) ; //list of all connected devices, serial and type provided
25- private List < IScope > deviceList = new List < IScope > ( ) ; // list of all devices which have actually been created.
2624
2725 public List < IHardwareInterface > ConnectedList { get { return this . connectedList ; } }
26+ private Dictionary < Type , Type > InterfaceActivators = new Dictionary < Type , Type > ( ) {
27+ { typeof ( DummyInterface ) , typeof ( DummyScope ) } ,
28+ { typeof ( ISmartScopeInterface ) , typeof ( SmartScope ) }
29+ } ;
2830
2931#if WINDOWS
3032 Thread badDriverDetectionThread ;
@@ -51,21 +53,43 @@ Context context
5153#if ANDROID
5254 context ,
5355#endif
54- null, null ) { Start ( ) ; }
56+ null, null ) { }
57+
58+ public DeviceManager (
59+ #if ANDROID
60+ Context context
61+ #endif
62+ DeviceConnectHandler deviceConnectHandler
63+ )
64+ : this (
65+ #if ANDROID
66+ context ,
67+ #endif
68+ null, deviceConnectHandler ) { }
5569
5670 public DeviceManager (
5771#if ANDROID
5872 Context context ,
5973#endif
60- InterfaceChangeHandler interfaceChangeHandler , DeviceConnectHandler deviceConnectHandler
74+ InterfaceChangeHandler interfaceChangeHandler , DeviceConnectHandler deviceConnectHandler ,
75+ Dictionary < Type , Type > interfaceActivatorOverride = null
6176 )
6277 {
6378#if ANDROID
6479 this . context = context ;
6580#endif
6681 this . DeviceConnected = deviceConnectHandler ;
6782 this . InterfaceChanged = interfaceChangeHandler ;
68-
83+ if ( interfaceActivatorOverride != null )
84+ {
85+ foreach ( var kvp in interfaceActivatorOverride )
86+ {
87+ if ( kvp . Key is IHardwareInterface && kvp . Value is IDevice )
88+ {
89+ this . InterfaceActivators [ kvp . Key ] = kvp . Value ;
90+ }
91+ }
92+ }
6993 connectedList . Add ( DummyInterface . Generator ) ;
7094 //FIXME: android should add audio-scope here!!!
7195 }
@@ -76,16 +100,16 @@ public void Start(bool async = true)
76100 pollThread . Name = "Devicemanager Startup poll" ;
77101
78102 //disable because of the crash by Wait
79- //InterfaceManagerZeroConf.Instance.onConnect += OnHardwareConnect ;
103+ //InterfaceManagerZeroConf.Instance.onConnect += OnInterfaceChanged ;
80104#if ANDROID
81105 InterfaceManagerXamarin . context = this . context ;
82- InterfaceManagerXamarin . Instance . onConnect += OnHardwareConnect ;
106+ InterfaceManagerXamarin . Instance . onConnect += OnInterfaceChanged ;
83107#elif WINUSB
84- InterfaceManagerWinUsb . Instance . onConnect += OnHardwareConnect ;
108+ InterfaceManagerWinUsb . Instance . onConnect += OnInterfaceChanged ;
85109#elif IOS
86110 //Nothing for the moment
87111#else
88- InterfaceManagerLibUsb . Instance . onConnect += OnHardwareConnect ;
112+ InterfaceManagerLibUsb . Instance . onConnect += OnInterfaceChanged ;
89113#endif
90114
91115 pollThread . Start ( ) ;
@@ -111,13 +135,13 @@ private void PollUponStart()
111135
112136 public void Stop ( )
113137 {
114- if ( mainDevice != null )
115- mainDevice . DataSourceScope . Stop ( ) ;
138+ if ( activeDevice != null && activeDevice is IScope )
139+ ( activeDevice as IScope ) . DataSourceScope . Stop ( ) ;
116140
117141 if ( pollThread != null )
118142 pollThread . Join ( 100 ) ;
119143
120- InterfaceManagerZeroConf . Instance . Destroy ( ) ;
144+ // InterfaceManagerZeroConf.Instance.Destroy();
121145#if ANDROID
122146 //Nothing to do here, just keeping same ifdef structure as above
123147#elif WINDOWS
@@ -133,83 +157,84 @@ public void Stop()
133157#endif
134158 }
135159
136- private void OnHardwareConnect ( IHardwareInterface hardwareInterface , bool connected )
160+ private void OnInterfaceChanged ( IHardwareInterface hardwareInterface , bool connected )
137161 {
138162 if ( connected ) {
139163 connectedList . Add ( hardwareInterface ) ;
140164
141165 #if WINDOWS
142166 lastSmartScopeDetectedThroughWinUsb = DateTime . Now ;
143- Logger . Debug ( String . Format ( "Update winusb detection time to {0}" , lastSmartScopeDetectedThroughWinUsb ) ) ;
144167 #endif
145-
146- Logger . Debug ( "DeviceManager: calling connectHandler after new Connect event" ) ;
147168 }
148169 else
149170 {
150171 if ( connectedList . Contains ( hardwareInterface ) )
151172 connectedList . Remove ( hardwareInterface ) ;
152- IScope device = deviceList . Where ( x => x . HardwareInterface == hardwareInterface ) . FirstOrDefault ( ) ;
153- if ( device != null )
154- {
155- //need to dispose smartscope here: when it's being unplugged
156- Logger . Debug ( "DeviceManager: disposing device" ) ;
157- if ( device is SmartScope )
158- ( device as SmartScope ) . Dispose ( ) ;
159-
160- deviceList . Remove ( device ) ;
161- }
162-
173+
163174 #if WINDOWS
164175 lastSmartScopeDetectedThroughWinUsb = null ;
165176 #endif
166-
167- Logger . Debug ( "DeviceManager: calling connectHandler after new Disconnect event" ) ;
168177 }
169178
179+ /* If application handles interface preferences, pass it the updated
180+ * list of connected interfaces for it to decide who to call SetActiveDevice
181+ * with
182+ */
170183 if ( InterfaceChanged != null )
171184 InterfaceChanged ( this , connectedList ) ;
185+ /* Else activate the lastly connected interface */
172186 else
173- {
174- //in case no event handlers are specified: connect real smartscope if none was active yet, or switch to dummymode
175- if ( connected && ! ( mainDevice is SmartScope ) )
176- {
177- //at this point, no real smartscope was attached, and a USB or ethernet scope was detected
178- SwitchMainDevice ( hardwareInterface ) ;
179- }
180- else
181- {
182- SwitchMainDevice ( null ) ;
183- }
184- }
187+ SetActiveDevice ( connectedList . Last ( ) ) ;
185188 }
186189
187- public void SwitchMainDevice ( IHardwareInterface iface )
190+ public void SetActiveDevice ( IHardwareInterface iface )
188191 {
189192 if ( ! connectedList . Contains ( iface ) )
190193 return ;
191194
192- //when changing device -> first fire previous device
193- if ( mainDevice != null && mainDevice . HardwareInterface != iface )
195+ // Don't handle a second activation if the interface
196+ // has already been activated
197+ if ( activeDevice != null && activeDevice . HardwareInterface == iface )
198+ return ;
199+
200+ // Activate new device
201+ Type DeviceType = null ;
202+ Type ifaceType = iface . GetType ( ) ;
203+ foreach ( Type t in this . InterfaceActivators . Keys )
194204 {
195- if ( DeviceConnected != null )
196- DeviceConnected ( mainDevice , false ) ;
205+ if ( ifaceType == t || ifaceType . IsSubclassOf ( t ) || ifaceType . GetInterfaces ( ) . Contains ( t ) )
206+ {
207+ DeviceType = InterfaceActivators [ t ] ;
208+ break ;
209+ }
197210 }
198211
199- //activate new device
200- if ( iface is DummyInterface )
201- mainDevice = new DummyScope ( iface as DummyInterface ) ;
202- else if ( iface is ISmartScopeInterface ) //real SmartScope
212+ if ( DeviceType == null )
203213 {
204- //need to make sure a smartscope is created only once from an interface
205- if ( deviceList . Where ( x => x . HardwareInterface == iface ) . Count ( ) == 0 )
206- deviceList . Add ( new SmartScope ( iface as ISmartScopeInterface ) ) ;
207-
208- mainDevice = deviceList . Where ( x => x . HardwareInterface == iface ) . First ( ) ;
214+ Logger . Error ( "Unsupported interface type " + iface . GetType ( ) . FullName ) ;
215+ return ;
209216 }
210217
211- if ( DeviceConnected != null )
212- DeviceConnected ( mainDevice , true ) ;
218+ try
219+ {
220+ IDevice newDevice = ( IDevice ) Activator . CreateInstance ( DeviceType , iface ) ;
221+
222+ if ( activeDevice != null )
223+ {
224+ if ( DeviceConnected != null )
225+ DeviceConnected ( activeDevice , false ) ;
226+ if ( activeDevice is IDisposable )
227+ ( activeDevice as IDisposable ) . Dispose ( ) ;
228+ }
229+
230+ activeDevice = newDevice ;
231+ if ( DeviceConnected != null )
232+ DeviceConnected ( activeDevice , true ) ;
233+ }
234+ catch ( Exception e )
235+ {
236+ Logger . Error ( "Failed to create device: " + e . Message ) ;
237+ }
213238 }
214239
215240#if WINDOWS
0 commit comments