teratail header banner
teratail header banner
質問するログイン新規登録

回答編集履歴

1

見直しキャンペーン中

2023/07/22 08:08

投稿

TN8001
TN8001

スコア10111

answer CHANGED
@@ -1,65 +1,65 @@
1
- 端的に言うと↓です。
2
- ```C#
3
- BeginInvoke((Action<FileSystemEventArgs>)OnChangedInMainThread, e);
4
- ```
5
-
6
- ほかの点はコード中のコメントに入れました。
7
- ```C#
8
- using System;
9
- using System.IO;
10
- using System.Windows;
11
- using System.Windows.Threading;
12
-
13
- namespace Questions273634
14
- {
15
- public partial class MainWindow : Window
16
- {
17
- private int count;
18
-
19
- public MainWindow()
20
- {
21
- InitializeComponent();
22
-
23
- var watcher = new FileSystemWatcher(Environment.CurrentDirectory);
24
- watcher.NotifyFilter = NotifyFilters.LastWrite;
25
- watcher.Changed += OnChanged;
26
- watcher.EnableRaisingEvents = true;
27
-
28
- // 検証がめんどくさいので自分でファイル変更
29
- var timer = new DispatcherTimer();
30
- timer.Interval = TimeSpan.FromSeconds(1);
31
- timer.Tick += (s, e) => File.WriteAllText(@"test.txt", "aaaa");
32
- timer.Start();
33
- }
34
-
35
- private void OnChanged(object sender, FileSystemEventArgs e)
36
- {
37
- // このメソッドがWindowのメソッドでないか、static限定なら
38
- // Application.Current.Dispatcher.BeginInvokeを使う
39
- // Windowのメソッドならthis.Dispatcher.BeginInvokeでいい
40
-
41
- // 指定しない限り別スレッドになるので、CheckAccessの確認は無駄な気がする
42
-
43
- Dispatcher.BeginInvoke((Action<FileSystemEventArgs>)OnChangedInMainThread, e);
44
- //Dispatcher.BeginInvoke((Action)(() => OnChangedInMainThread(e))); // ラムダで
45
- //Dispatcher.Invoke(() => OnChangedInMainThread(e)); // 同期 ラムダで
46
- }
47
-
48
- private void OnChangedInMainThread(FileSystemEventArgs e)
49
- {
50
- //new ImagePreview().Show();
51
-
52
- // xamlに<TextBlock x:Name="textBlock" />があるとして
53
- textBlock.Text = $"{e.Name} {DateTime.Now:yyyy/MM/dd HH:mm:ss.ffff} {count++}";
54
- }
55
- }
56
- }
57
- ```
58
-
59
- ---
60
-
61
- `FileSystemWatcher`は連続してイベント発火する場合がある(書き込んだアプリによるのでこちらで制御できない)ようなので、`Show()`だとちょっと困ったことになるかもしれません。
62
- 厳密にやろうとすると、かなり面倒&これといって決定版がない気がします。
63
-
64
- 簡易でいい場合は、↓なんかがスマートです。
1
+ 端的に言うと↓です。
2
+ ```cs
3
+ BeginInvoke((Action<FileSystemEventArgs>)OnChangedInMainThread, e);
4
+ ```
5
+
6
+ ほかの点はコード中のコメントに入れました。
7
+ ```cs
8
+ using System;
9
+ using System.IO;
10
+ using System.Windows;
11
+ using System.Windows.Threading;
12
+
13
+ namespace Questions273634
14
+ {
15
+ public partial class MainWindow : Window
16
+ {
17
+ private int count;
18
+
19
+ public MainWindow()
20
+ {
21
+ InitializeComponent();
22
+
23
+ var watcher = new FileSystemWatcher(Environment.CurrentDirectory);
24
+ watcher.NotifyFilter = NotifyFilters.LastWrite;
25
+ watcher.Changed += OnChanged;
26
+ watcher.EnableRaisingEvents = true;
27
+
28
+ // 検証がめんどくさいので自分でファイル変更
29
+ var timer = new DispatcherTimer();
30
+ timer.Interval = TimeSpan.FromSeconds(1);
31
+ timer.Tick += (s, e) => File.WriteAllText(@"test.txt", "aaaa");
32
+ timer.Start();
33
+ }
34
+
35
+ private void OnChanged(object sender, FileSystemEventArgs e)
36
+ {
37
+ // このメソッドがWindowのメソッドでないか、static限定なら
38
+ // Application.Current.Dispatcher.BeginInvokeを使う
39
+ // Windowのメソッドならthis.Dispatcher.BeginInvokeでいい
40
+
41
+ // 指定しない限り別スレッドになるので、CheckAccessの確認は無駄な気がする
42
+
43
+ Dispatcher.BeginInvoke((Action<FileSystemEventArgs>)OnChangedInMainThread, e);
44
+ //Dispatcher.BeginInvoke((Action)(() => OnChangedInMainThread(e))); // ラムダで
45
+ //Dispatcher.Invoke(() => OnChangedInMainThread(e)); // 同期 ラムダで
46
+ }
47
+
48
+ private void OnChangedInMainThread(FileSystemEventArgs e)
49
+ {
50
+ //new ImagePreview().Show();
51
+
52
+ // xamlに<TextBlock x:Name="textBlock" />があるとして
53
+ textBlock.Text = $"{e.Name} {DateTime.Now:yyyy/MM/dd HH:mm:ss.ffff} {count++}";
54
+ }
55
+ }
56
+ }
57
+ ```
58
+
59
+ ---
60
+
61
+ `FileSystemWatcher`は連続してイベント発火する場合がある(書き込んだアプリによるのでこちらで制御できない)ようなので、`Show()`だとちょっと困ったことになるかもしれません。
62
+ 厳密にやろうとすると、かなり面倒&これといって決定版がない気がします。
63
+
64
+ 簡易でいい場合は、↓なんかがスマートです。
65
65
  [FileSystemWatcherの連続して発生する同じ種類のイベントを無視る - かずきのBlog@hatena](https://blog.okazuki.jp/entry/20120322/1332378060)