11using System ;
2+ using System . ComponentModel ;
23using System . Drawing ;
34using System . IO ;
45using System . Linq ;
6+ using System . Resources ;
57using System . Windows . Forms ;
68
79namespace OpenEphys . Onix1 . Design
@@ -26,12 +28,26 @@ private enum ChannelPreset
2628 }
2729
2830 /// <summary>
29- /// Gets or sets the probe configuration.
31+ /// Public <see cref="NeuropixelsV1ProbeConfiguration"/> interface that is manipulated by
32+ /// <see cref="NeuropixelsV1ProbeConfigurationDialog"/>.
3033 /// </summary>
34+ /// <remarks>
35+ /// When a <see cref="NeuropixelsV1ProbeConfiguration"/> is passed to
36+ /// <see cref="NeuropixelsV1ProbeConfigurationDialog"/>, it is copied and stored in this
37+ /// variable so that any modifications made to configuration settings can be easily reversed
38+ /// by not copying the new settings back to the original instance.
39+ /// </remarks>
3140 public NeuropixelsV1ProbeConfiguration ProbeConfiguration
3241 {
33- get => ChannelConfiguration . ProbeConfiguration ;
34- set => ChannelConfiguration . ProbeConfiguration = value ;
42+ get => ( ( IConfigureNeuropixelsV1 ) propertyGrid . SelectedObject ) . ProbeConfiguration ;
43+ set => ( ( IConfigureNeuropixelsV1 ) propertyGrid . SelectedObject ) . ProbeConfiguration = value ;
44+ }
45+
46+ [ Obsolete ]
47+ IConfigureNeuropixelsV1 ConfigureNode
48+ {
49+ get => ( IConfigureNeuropixelsV1 ) propertyGrid . SelectedObject ;
50+ set => propertyGrid . SelectedObject = value ;
3551 }
3652
3753 /// <inheritdoc cref="NeuropixelsV1ProbeConfiguration.InvertPolarity"/>
@@ -45,56 +61,122 @@ public bool InvertPolarity
4561 /// <summary>
4662 /// Initializes a new instance of <see cref="NeuropixelsV1Dialog"/>.
4763 /// </summary>
48- /// <param name="probeConfiguration">A <see cref="NeuropixelsV1ProbeConfiguration"/> object holding the current configuration settings .</param>
49- public NeuropixelsV1ProbeConfigurationDialog ( NeuropixelsV1ProbeConfiguration probeConfiguration )
64+ /// <param name="configureNode">Existing configuration node .</param>
65+ public NeuropixelsV1ProbeConfigurationDialog ( IConfigureNeuropixelsV1 configureNode )
5066 {
5167 InitializeComponent ( ) ;
5268 Shown += FormShown ;
5369
54- ChannelConfiguration = new ( probeConfiguration ) ;
55- ChannelConfiguration
56- . SetChildFormProperties ( this )
57- . AddDialogToPanel ( panelProbe ) ;
58-
70+ ChannelConfiguration = new ( configureNode . ProbeConfiguration ) ;
71+ ChannelConfiguration . SetChildFormProperties ( this ) . AddDialogToPanel ( panelProbe ) ;
5972 this . AddMenuItemsFromDialogToFileOption ( ChannelConfiguration ) ;
6073
74+ panelProbe . Controls . Add ( ChannelConfiguration ) ;
75+
6176 ChannelConfiguration . OnZoom += UpdateTrackBarLocation ;
6277 ChannelConfiguration . OnFileLoad += OnFileLoadEvent ;
6378
64- comboBoxApGain . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1Gain ) ) ;
65- comboBoxApGain . SelectedItem = ProbeConfiguration . SpikeAmplifierGain ;
66- comboBoxApGain . SelectedIndexChanged += SpikeAmplifierGainIndexChanged ;
79+ propertyGrid . SelectedObject = configureNode ;
80+ bindingSource . DataSource = configureNode ;
6781
68- comboBoxLfpGain . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1Gain ) ) ;
69- comboBoxLfpGain . SelectedItem = ProbeConfiguration . LfpAmplifierGain ;
70- comboBoxLfpGain . SelectedIndexChanged += LfpAmplifierGainIndexChanged ;
82+ // NB: Needed to capture mouse scroll wheel updates
83+ void ForceBindingUpdate ( object sender , EventArgs e )
84+ {
85+ var control = sender as Control ;
7186
72- comboBoxReference . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1ReferenceSource ) ) ;
73- comboBoxReference . SelectedItem = ProbeConfiguration . Reference ;
74- comboBoxReference . SelectedIndexChanged += ReferenceIndexChanged ;
87+ foreach ( Binding binding in control . DataBindings )
88+ {
89+ binding . WriteValue ( ) ;
90+ }
7591
76- checkBoxSpikeFilter . Checked = ProbeConfiguration . SpikeFilter ;
77- checkBoxSpikeFilter . CheckedChanged += SpikeFilterIndexChanged ;
92+ bindingSource . ResetCurrentItem ( ) ;
93+ }
94+ ;
7895
79- checkBoxInvertPolarity . Checked = ProbeConfiguration . InvertPolarity ;
80- checkBoxInvertPolarity . CheckedChanged += InvertPolarityIndexChanged ;
96+ comboBoxApGain . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1Gain ) ) ;
97+ comboBoxApGain . DataBindings . Add ( "SelectedItem" ,
98+ bindingSource ,
99+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . SpikeAmplifierGain ) } ",
100+ false ,
101+ DataSourceUpdateMode . OnPropertyChanged ) ;
102+ comboBoxApGain . SelectedIndexChanged += ( sender , e ) =>
103+ {
104+ ForceBindingUpdate ( sender , e ) ;
105+ CheckStatus ( ) ;
106+ } ;
81107
82- textBoxAdcCalibrationFile . Text = ProbeConfiguration . AdcCalibrationFileName ;
83- textBoxAdcCalibrationFile . TextChanged += ( sender , e ) => ProbeConfiguration . AdcCalibrationFileName = ( ( TextBox ) sender ) . Text ;
108+ comboBoxLfpGain . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1Gain ) ) ;
109+ comboBoxLfpGain . DataBindings . Add ( "SelectedItem" ,
110+ bindingSource ,
111+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . LfpAmplifierGain ) } ",
112+ false ,
113+ DataSourceUpdateMode . OnPropertyChanged ) ;
114+ comboBoxLfpGain . SelectedIndexChanged += ( sender , e ) =>
115+ {
116+ ForceBindingUpdate ( sender , e ) ;
117+ CheckStatus ( ) ;
118+ } ;
84119
85- textBoxGainCalibrationFile . Text = ProbeConfiguration . GainCalibrationFileName ;
86- textBoxGainCalibrationFile . TextChanged += ( sender , e ) => ProbeConfiguration . GainCalibrationFileName = ( ( TextBox ) sender ) . Text ;
120+ comboBoxReference . DataSource = Enum . GetValues ( typeof ( NeuropixelsV1ReferenceSource ) ) ;
121+ comboBoxReference . DataBindings . Add ( "SelectedItem" ,
122+ bindingSource ,
123+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . Reference ) } ",
124+ false ,
125+ DataSourceUpdateMode . OnPropertyChanged ) ;
126+ comboBoxReference . SelectedIndexChanged += ForceBindingUpdate ;
127+
128+ checkBoxSpikeFilter . DataBindings . Add ( "Checked" ,
129+ bindingSource ,
130+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . SpikeFilter ) } ",
131+ false ,
132+ DataSourceUpdateMode . OnPropertyChanged ) ;
133+
134+ checkBoxInvertPolarity . DataBindings . Add ( "Checked" ,
135+ bindingSource ,
136+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . InvertPolarity ) } ",
137+ false ,
138+ DataSourceUpdateMode . OnPropertyChanged ) ;
139+
140+ textBoxAdcCalibrationFile . DataBindings . Add ( "Text" ,
141+ bindingSource ,
142+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . AdcCalibrationFileName ) } ",
143+ false ,
144+ DataSourceUpdateMode . OnPropertyChanged ) ;
145+ textBoxAdcCalibrationFile . TextChanged += ( sender , e ) => CheckStatus ( ) ;
146+
147+ textBoxGainCalibrationFile . DataBindings . Add ( "Text" ,
148+ bindingSource ,
149+ $ "{ nameof ( configureNode . ProbeConfiguration ) } .{ nameof ( configureNode . ProbeConfiguration . GainCalibrationFileName ) } ",
150+ false ,
151+ DataSourceUpdateMode . OnPropertyChanged ) ;
152+ textBoxGainCalibrationFile . TextChanged += ( sender , e ) => CheckStatus ( ) ;
87153
88154 comboBoxChannelPresets . DataSource = Enum . GetValues ( typeof ( ChannelPreset ) ) ;
89155 CheckForExistingChannelPreset ( ) ;
90- comboBoxChannelPresets . SelectedIndexChanged += ChannelPresetIndexChanged ;
156+ comboBoxChannelPresets . SelectedIndexChanged += ( sender , e ) =>
157+ {
158+ var channelPreset = ( ( ComboBox ) sender ) . SelectedItem is ChannelPreset preset
159+ ? preset
160+ : throw new InvalidEnumArgumentException ( $ "Invalid channel preset value found.") ;
161+
162+ if ( channelPreset != ChannelPreset . None )
163+ {
164+ SetChannelPreset ( channelPreset ) ;
165+ }
166+ } ;
91167
92168 CheckStatus ( ) ;
93- }
94169
95- private void InvertPolarityIndexChanged ( object sender , EventArgs e )
96- {
97- ProbeConfiguration . InvertPolarity = ( ( CheckBox ) sender ) . Checked ;
170+ bindingSource . ListChanged += ( sender , eventArgs ) => propertyGrid . Refresh ( ) ;
171+
172+ tabControl1 . SelectedIndexChanged += ( sender , eventArgs ) =>
173+ {
174+ if ( tabControl1 . SelectedTab == tabPageProperties )
175+ propertyGrid . Refresh ( ) ;
176+
177+ else if ( tabControl1 . SelectedTab == tabPageConfiguration )
178+ bindingSource . ResetCurrentItem ( ) ;
179+ } ;
98180 }
99181
100182 private void FormShown ( object sender , EventArgs e )
@@ -111,75 +193,32 @@ private void FormShown(object sender, EventArgs e)
111193 ChannelConfiguration . ConnectResizeEventHandler ( ) ;
112194 }
113195
114- private void GainCalibrationFileTextChanged ( object sender , EventArgs e )
115- {
116- CheckStatus ( ) ;
117- }
118-
119- private void AdcCalibrationFileTextChanged ( object sender , EventArgs e )
120- {
121- CheckStatus ( ) ;
122- }
123-
124- private void SpikeAmplifierGainIndexChanged ( object sender , EventArgs e )
125- {
126- ProbeConfiguration . SpikeAmplifierGain = ( NeuropixelsV1Gain ) ( ( ComboBox ) sender ) . SelectedItem ;
127- CheckStatus ( ) ;
128- }
129-
130- private void LfpAmplifierGainIndexChanged ( object sender , EventArgs e )
131- {
132- ProbeConfiguration . LfpAmplifierGain = ( NeuropixelsV1Gain ) ( ( ComboBox ) sender ) . SelectedItem ;
133- CheckStatus ( ) ;
134- }
135-
136- private void ReferenceIndexChanged ( object sender , EventArgs e )
137- {
138- ProbeConfiguration . Reference = ( NeuropixelsV1ReferenceSource ) ( ( ComboBox ) sender ) . SelectedItem ;
139- }
140-
141- private void ChannelPresetIndexChanged ( object sender , EventArgs e )
142- {
143- var channelPreset = ( ChannelPreset ) ( ( ComboBox ) sender ) . SelectedItem ;
144-
145- if ( channelPreset != ChannelPreset . None )
146- {
147- SetChannelPreset ( channelPreset ) ;
148- }
149- }
150-
151- private void SpikeFilterIndexChanged ( object sender , EventArgs e )
152- {
153- ProbeConfiguration . SpikeFilter = ( ( CheckBox ) sender ) . Checked ;
154- }
155-
156196 private void SetChannelPreset ( ChannelPreset preset )
157197 {
158- var probeConfiguration = ChannelConfiguration . ProbeConfiguration ;
159- var electrodes = NeuropixelsV1eProbeGroup . ToElectrodes ( ChannelConfiguration . ProbeConfiguration . ProbeGroup ) ;
198+ var electrodes = NeuropixelsV1eProbeGroup . ToElectrodes ( ProbeConfiguration . ProbeGroup ) ;
160199
161200 switch ( preset )
162201 {
163202 case ChannelPreset . BankA :
164- probeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . A ) . ToArray ( ) ) ;
203+ ProbeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . A ) . ToArray ( ) ) ;
165204 break ;
166205
167206 case ChannelPreset . BankB :
168- probeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . B ) . ToArray ( ) ) ;
207+ ProbeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . B ) . ToArray ( ) ) ;
169208 break ;
170209
171210 case ChannelPreset . BankC :
172- probeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . C ||
211+ ProbeConfiguration . SelectElectrodes ( electrodes . Where ( e => e . Bank == NeuropixelsV1Bank . C ||
173212 ( e . Bank == NeuropixelsV1Bank . B && e . Index >= 576 ) ) . ToArray ( ) ) ;
174213 break ;
175214
176215 case ChannelPreset . SingleColumn :
177- probeConfiguration . SelectElectrodes ( electrodes . Where ( e => ( e . Index % 2 == 0 && e . Bank == NeuropixelsV1Bank . A ) ||
216+ ProbeConfiguration . SelectElectrodes ( electrodes . Where ( e => ( e . Index % 2 == 0 && e . Bank == NeuropixelsV1Bank . A ) ||
178217 ( e . Index % 2 == 1 && e . Bank == NeuropixelsV1Bank . B ) ) . ToArray ( ) ) ;
179218 break ;
180219
181220 case ChannelPreset . Tetrodes :
182- probeConfiguration . SelectElectrodes ( electrodes . Where ( e => ( e . Index % 8 < 4 && e . Bank == NeuropixelsV1Bank . A ) ||
221+ ProbeConfiguration . SelectElectrodes ( electrodes . Where ( e => ( e . Index % 8 < 4 && e . Bank == NeuropixelsV1Bank . A ) ||
183222 ( e . Index % 8 > 3 && e . Bank == NeuropixelsV1Bank . B ) ) . ToArray ( ) ) ;
184223 break ;
185224 }
@@ -192,7 +231,7 @@ private void SetChannelPreset(ChannelPreset preset)
192231
193232 private void CheckForExistingChannelPreset ( )
194233 {
195- var channelMap = ChannelConfiguration . ProbeConfiguration . ChannelMap ;
234+ var channelMap = ProbeConfiguration . ChannelMap ;
196235
197236 if ( channelMap . All ( e => e . Bank == NeuropixelsV1Bank . A ) )
198237 {
@@ -225,7 +264,7 @@ private void CheckForExistingChannelPreset()
225264
226265 private void OnFileLoadEvent ( object sender , EventArgs e )
227266 {
228- // NB: Ensure that the newly loaded ProbeConfiguration in the ChannelConfigurationDialog is reflected here.
267+ // NB: Ensure that the newly loaded ProbeGroup in the ChannelConfigurationDialog is reflected here.
229268 ProbeConfiguration = ChannelConfiguration . ProbeConfiguration ;
230269 CheckForExistingChannelPreset ( ) ;
231270 }
@@ -320,6 +359,8 @@ private void CheckStatus()
320359 toolStripLabelGainCalibrationSn . Image = Properties . Resources . StatusBlockedImage ;
321360 else
322361 toolStripLabelGainCalibrationSn . Image = Properties . Resources . StatusReadyImage ;
362+
363+ propertyGrid . Refresh ( ) ;
323364 }
324365
325366 private void ChooseGainCalibrationFile_Click ( object sender , EventArgs e )
@@ -379,7 +420,7 @@ private void ViewAdcs_Click(object sender, EventArgs e)
379420 if ( Adcs == null )
380421 return ;
381422
382- System . Resources . ResourceManager resources = new System . ComponentModel . ComponentResourceManager ( typeof ( NeuropixelsV1Dialog ) ) ;
423+ ResourceManager resources = new ComponentResourceManager ( typeof ( NeuropixelsV1Dialog ) ) ;
383424
384425 var adcForm = new Form ( )
385426 {
0 commit comments