@@ -245,34 +245,29 @@ private void ApplyScaling()
245
245
this . idHeader . Width = ScaleHelper . Scale ( this . idHeader . Width ) ;
246
246
this . keyHeader . Width = ScaleHelper . Scale ( this . keyHeader . Width ) ;
247
247
}
248
-
249
- /// <summary>
250
- /// Gets the keys as a string
251
- /// </summary>
252
- private static String GetKeysAsString ( Keys keys )
253
- {
254
- return DataConverter . KeysToString ( keys ) ;
255
- }
256
-
248
+
257
249
/// <summary>
258
250
/// Updates the font highlight of the item
259
251
/// </summary>
260
252
private static void UpdateItemHighlightFont ( ShortcutListItem item )
261
253
{
262
254
item . ForeColor = item . Conflicts == null ? SystemColors . ControlText : Color . DarkRed ;
263
255
item . SubItems [ 1 ] . ForeColor = item . KeysString == "None" ? SystemColors . GrayText : SystemColors . ControlText ;
264
- if ( item . Default == item . Custom )
256
+ if ( item . IsModified )
265
257
{
266
- item . Font = new Font ( Globals . Settings . DefaultFont , FontStyle . Regular ) ;
267
- item . UseItemStyleForSubItems = false ;
258
+ item . Font = new Font ( Globals . Settings . DefaultFont , FontStyle . Bold ) ;
259
+ item . UseItemStyleForSubItems = true ;
268
260
}
269
261
else
270
262
{
271
- item . Font = new Font ( Globals . Settings . DefaultFont , FontStyle . Bold ) ;
272
- item . UseItemStyleForSubItems = true ;
263
+ item . Font = new Font ( Globals . Settings . DefaultFont , FontStyle . Regular ) ;
264
+ item . UseItemStyleForSubItems = false ;
273
265
}
274
266
}
275
267
268
+ /// <summary>
269
+ /// Initialize the full shortcut list.
270
+ /// </summary>
276
271
private void InitializeShortcutListItems ( )
277
272
{
278
273
Dictionary < String , ShortcutItem > . ValueCollection collection = ShortcutManager . RegisteredItems . Values ;
@@ -292,22 +287,8 @@ private void InitializeShortcutListItems()
292
287
/// </summary>
293
288
private void PopulateListView ( String filter )
294
289
{
295
- // TODO: Read starting char of filter
296
290
Boolean viewCustom = false , viewConflicts = false ;
297
- checkSpecialFilterKeys :
298
- if ( filter . StartsWith ( ViewCustomKey ) ) // TODO: StartsWithOrdinal
299
- {
300
- filter = filter . Substring ( ViewCustomKey . Length ) ;
301
- viewCustom = true ;
302
- }
303
- if ( ! viewConflicts && filter . StartsWith ( ViewConflictsKey ) )
304
- {
305
- filter = filter . Substring ( ViewConflictsKey . Length ) ;
306
- viewConflicts = true ;
307
- if ( ! viewCustom ) goto checkSpecialFilterKeys ;
308
- }
309
-
310
- filter = filter . Trim ( ) ;
291
+ filter = ExtractFilterKeywords ( filter , ref viewCustom , ref viewConflicts ) ;
311
292
312
293
this . listView . BeginUpdate ( ) ;
313
294
this . listView . Items . Clear ( ) ;
@@ -317,7 +298,7 @@ private void PopulateListView(String filter)
317
298
item . Id . IndexOf ( filter , StringComparison . OrdinalIgnoreCase ) >= 0 ||
318
299
item . KeysString . IndexOf ( filter , StringComparison . OrdinalIgnoreCase ) >= 0 )
319
300
{
320
- if ( viewCustom && item . Custom == item . Default ) continue ;
301
+ if ( viewCustom && ! item . IsModified ) continue ;
321
302
if ( viewConflicts && item . Conflicts == null ) continue ;
322
303
this . listView . Items . Add ( item ) ;
323
304
}
@@ -330,6 +311,27 @@ private void PopulateListView(String filter)
330
311
}
331
312
}
332
313
314
+ /// <summary>
315
+ /// Reads and removes filter keywords from the start of the filter.
316
+ /// Order of the keywords is irrelevant.
317
+ /// </summary>
318
+ private static String ExtractFilterKeywords ( String filter , ref Boolean viewCustom , ref Boolean viewConflicts )
319
+ {
320
+ if ( ! viewCustom && filter . StartsWith ( ViewCustomKey ) )
321
+ {
322
+ filter = filter . Substring ( ViewCustomKey . Length ) ;
323
+ viewCustom = true ;
324
+ return ExtractFilterKeywords ( filter , ref viewCustom , ref viewConflicts ) ;
325
+ }
326
+ if ( ! viewConflicts && filter . StartsWith ( ViewConflictsKey ) )
327
+ {
328
+ filter = filter . Substring ( ViewConflictsKey . Length ) ;
329
+ viewConflicts = true ;
330
+ return ExtractFilterKeywords ( filter , ref viewCustom , ref viewConflicts ) ;
331
+ }
332
+ return filter . Trim ( ) ;
333
+ }
334
+
333
335
/// <summary>
334
336
/// Raised when the context menu for the list view is opening.
335
337
/// </summary>
@@ -339,18 +341,17 @@ private void ContextMenuOpening(Object sender, EventArgs e)
339
341
{
340
342
ShortcutListItem item = ( ShortcutListItem ) this . listView . SelectedItems [ 0 ] ;
341
343
this . removeShortcut . Enabled = item . Custom != Keys . None ;
342
- this . revertToDefault . Enabled = this . revertAllToDefault . Enabled = item . Custom != item . Default ;
344
+ this . revertToDefault . Enabled = this . revertAllToDefault . Enabled = item . IsModified ;
345
+ if ( this . revertAllToDefault . Enabled ) return ;
343
346
}
344
- else
347
+ else this . removeShortcut . Enabled = this . revertToDefault . Enabled = false ;
348
+
349
+ foreach ( ShortcutListItem item in this . listView . Items )
345
350
{
346
- this . removeShortcut . Enabled = this . revertToDefault . Enabled = false ;
347
- foreach ( ShortcutListItem item in this . listView . Items )
351
+ if ( item . IsModified )
348
352
{
349
- if ( item . Custom != item . Default )
350
- {
351
- this . revertAllToDefault . Enabled = true ;
352
- break ;
353
- }
353
+ this . revertAllToDefault . Enabled = true ;
354
+ break ;
354
355
}
355
356
}
356
357
}
@@ -363,8 +364,7 @@ private void ListViewKeyDown(Object sender, KeyEventArgs e)
363
364
if ( this . listView . SelectedItems . Count == 0 ) return ;
364
365
365
366
ShortcutListItem item = ( ShortcutListItem ) this . listView . SelectedItems [ 0 ] ;
366
- if ( e . KeyData == Keys . Delete ) RemoveShortcut ( item ) ;
367
- else this . AssignNewShortcut ( item , e . KeyData ) ;
367
+ this . AssignNewShortcut ( item , e . KeyData ) ;
368
368
369
369
// Don't trigger list view default shortcuts like Ctrl+Add
370
370
if ( e . KeyData != Keys . Up && e . KeyData != Keys . Down ) e . Handled = true ;
@@ -375,44 +375,38 @@ private void ListViewKeyDown(Object sender, KeyEventArgs e)
375
375
/// </summary>
376
376
private void AssignNewShortcut ( ShortcutListItem item , Keys shortcut )
377
377
{
378
- if ( item . Custom == shortcut || ! ToolStripManager . IsValidShortcut ( shortcut ) ) return ;
378
+ if ( shortcut == Keys . None || shortcut == Keys . Delete ) shortcut = 0 ;
379
+ else if ( ! ToolStripManager . IsValidShortcut ( shortcut ) ) return ;
379
380
381
+ if ( item . Custom == shortcut ) return ;
380
382
item . Custom = shortcut ;
381
383
item . Selected = true ;
382
384
ResetConflicts ( item ) ;
383
385
List < ShortcutListItem > conflicts = this . GetConflictItems ( shortcut ) ;
384
- if ( conflicts != null )
386
+ if ( conflicts == null ) UpdateItemHighlightFont ( item ) ;
387
+ else
385
388
{
386
389
foreach ( ShortcutListItem i in conflicts )
387
390
{
388
391
i . Conflicts = conflicts ;
389
392
UpdateItemHighlightFont ( i ) ;
390
393
}
391
- String message = TextHelper . GetString ( "Info.ShortcutIsAlreadyUsed" ) ;
392
- ErrorManager . ShowWarning ( message , null ) ;
394
+ ErrorManager . ShowWarning ( TextHelper . GetString ( "Info.ShortcutIsAlreadyUsed" ) , null ) ;
393
395
this . filterTextBox . Focus ( ) ; // Set focus to filter...
394
- this . filterTextBox . Text = GetKeysAsString ( shortcut ) ;
396
+ this . filterTextBox . Text = ViewConflictsKey + item . KeysString ;
395
397
this . filterTextBox . SelectAll ( ) ;
396
398
}
397
399
}
398
-
400
+
399
401
/// <summary>
400
- /// Remove shortcut keys from an item
402
+ /// Resets the conflicts status of an item.
401
403
/// </summary>
402
- private static void RemoveShortcut ( ShortcutListItem item )
403
- {
404
- item . Custom = 0 ;
405
- item . Selected = true ;
406
- ResetConflicts ( item ) ;
407
- }
408
-
409
404
private static void ResetConflicts ( ShortcutListItem item )
410
405
{
411
406
List < ShortcutListItem > conflicts = item . Conflicts ;
412
407
if ( conflicts == null ) return ;
413
408
item . Conflicts = null ;
414
409
conflicts . Remove ( item ) ;
415
- UpdateItemHighlightFont ( item ) ;
416
410
if ( conflicts . Count == 1 )
417
411
{
418
412
item = conflicts [ 0 ] ;
@@ -444,6 +438,7 @@ private void ViewCustomCheckedChanged(Object sender, EventArgs e)
444
438
/// </summary>
445
439
private List < ShortcutListItem > GetConflictItems ( Keys keys )
446
440
{
441
+ if ( keys == Keys . None ) return null ;
447
442
// To prevent creation of unnecessary List<T> objects
448
443
ShortcutListItem first = null ;
449
444
List < ShortcutListItem > items = null ;
@@ -494,7 +489,7 @@ private void RemoveShortcutClick(Object sender, EventArgs e)
494
489
{
495
490
if ( this . listView . SelectedItems . Count == 0 ) return ;
496
491
ShortcutListItem item = ( ShortcutListItem ) this . listView . SelectedItems [ 0 ] ;
497
- RemoveShortcut ( item ) ;
492
+ this . AssignNewShortcut ( item , Keys . None ) ;
498
493
}
499
494
500
495
/// <summary>
@@ -511,18 +506,18 @@ private void ClearFilterClick(Object sender, EventArgs e)
511
506
/// </summary>
512
507
private void SetupUpdateTimer ( )
513
508
{
514
- updateTimer = new Timer ( ) ;
515
- updateTimer . Enabled = false ;
516
- updateTimer . Interval = 100 ;
517
- updateTimer . Tick += UpdateTimer_Tick ;
509
+ this . updateTimer = new Timer ( ) ;
510
+ this . updateTimer . Enabled = false ;
511
+ this . updateTimer . Interval = 100 ;
512
+ this . updateTimer . Tick += this . UpdateTimer_Tick ;
518
513
}
519
514
520
515
/// <summary>
521
516
/// Update the list with filter.
522
517
/// </summary>
523
518
private void UpdateTimer_Tick ( Object sender , EventArgs e )
524
519
{
525
- updateTimer . Enabled = false ;
520
+ this . updateTimer . Enabled = false ;
526
521
this . PopulateListView ( this . filterTextBox . Text ) ;
527
522
}
528
523
@@ -531,8 +526,8 @@ private void UpdateTimer_Tick(Object sender, EventArgs e)
531
526
/// </summary>
532
527
private void FilterTextChanged ( Object sender , EventArgs e )
533
528
{
534
- updateTimer . Stop ( ) ;
535
- updateTimer . Start ( ) ;
529
+ this . updateTimer . Stop ( ) ;
530
+ this . updateTimer . Start ( ) ;
536
531
}
537
532
538
533
/// <summary>
@@ -552,8 +547,7 @@ private void DialogClosing(Object sender, FormClosingEventArgs e)
552
547
{
553
548
if ( item . Conflicts != null )
554
549
{
555
- // TODO: Localize the text.
556
- ErrorManager . ShowError ( "There are one or more conflicts present." , null ) ;
550
+ ErrorManager . ShowError ( TextHelper . GetString ( "Info.ShortcutConflictsPresent" ) , null ) ;
557
551
this . filterTextBox . Text = ViewConflictsKey ;
558
552
e . Cancel = true ;
559
553
break ;
@@ -590,6 +584,9 @@ private void DialogClosed(Object sender, FormClosedEventArgs e)
590
584
591
585
#region ListViewComparer
592
586
587
+ /// <summary>
588
+ /// Defines a method that compares two <see cref="ShortcutListItem"/> objects.
589
+ /// </summary>
593
590
class ShorcutListItemComparer : IComparer < ShortcutListItem >
594
591
{
595
592
Int32 IComparer < ShortcutListItem > . Compare ( ShortcutListItem x , ShortcutListItem y )
@@ -600,38 +597,69 @@ Int32 IComparer<ShortcutListItem>.Compare(ShortcutListItem x, ShortcutListItem y
600
597
601
598
#endregion
602
599
600
+ /// <summary>
601
+ /// Represents a copy of a <see cref="ShortcutItem"/> as well as a visual component.
602
+ /// </summary>
603
603
class ShortcutListItem : ListViewItem
604
604
{
605
605
private Keys custom ;
606
606
607
- public ShortcutItem Item { get ; set ; }
607
+ /// <summary>
608
+ /// Gets the associated <see cref="ShortcutItem"/> object.
609
+ /// </summary>
610
+ public ShortcutItem Item { get ; private set ; }
611
+ /// <summary>
612
+ /// Gets or sets a list of <see cref="ShortcutListItem"/> objects that have conflicting keys with this instance.
613
+ /// </summary>
608
614
public List < ShortcutListItem > Conflicts { get ; set ; }
609
- public String Id { get { return Item . Id ; } }
610
- public Keys Default { get { return Item . Default ; } }
615
+ /// <summary>
616
+ /// Gets the ID of the associated <see cref="ShortcutItem"/>.
617
+ /// </summary>
618
+ public String Id { get { return this . Item . Id ; } }
619
+ /// <summary>
620
+ /// Gets the default shortcut keys.
621
+ /// </summary>
622
+ public Keys Default { get { return this . Item . Default ; } }
623
+ /// <summary>
624
+ /// Gets or sets the custom shortcut keys.
625
+ /// </summary>
611
626
public Keys Custom
612
627
{
613
- get { return custom ; }
628
+ get { return this . custom ; }
614
629
set
615
630
{
616
- custom = value ;
617
- KeysString = DataConverter . KeysToString ( value ) ;
618
- SubItems [ 1 ] . Text = KeysString ;
631
+ this . custom = value ;
632
+ this . KeysString = DataConverter . KeysToString ( value ) ;
633
+ this . SubItems [ 1 ] . Text = this . KeysString ;
619
634
}
620
635
}
636
+ /// <summary>
637
+ /// Gets the string representation of the custom shortcut keys.
638
+ /// </summary>
621
639
public String KeysString { get ; private set ; }
640
+ /// <summary>
641
+ /// Gets the modification status of the shortcut.
642
+ /// </summary>
643
+ public Boolean IsModified { get { return this . Custom != this . Default ; } }
622
644
645
+ /// <summary>
646
+ /// Creates a new instance of <see cref="ShortcutListItem"/> with an associated <see cref="ShortcutItem"/>.
647
+ /// </summary>
623
648
public ShortcutListItem ( ShortcutItem item )
624
649
{
625
- Name = Text = item . Id ;
626
- SubItems . Add ( string . Empty ) ;
627
- Item = item ;
628
- Conflicts = null ;
629
- Custom = item . Custom ;
650
+ this . SubItems . Add ( string . Empty ) ;
651
+ this . Name = this . Text = item . Id ;
652
+ this . Item = item ;
653
+ this . Conflicts = null ;
654
+ this . Custom = item . Custom ;
630
655
}
631
656
657
+ /// <summary>
658
+ /// Apply changes made to this instance to the associated <see cref="ShortcutItem"/>.
659
+ /// </summary>
632
660
public void ApplyChanges ( )
633
661
{
634
- Item . Custom = Custom ;
662
+ this . Item . Custom = this . Custom ;
635
663
}
636
664
}
637
665
0 commit comments