An UI puzzle - Create a dialog in a thread.

Recently, I am in charge of a project. It has a function similar to the other programs, that is saving data to a file and load data from a file. But the saving and loading process may take quite a few seconds. If the data size is huge, it may take more time. I don't want the user interface lose response to the user in this process. So, I want to show a dialog box displaying "Please wait..." to the user. I think a mode dialog box is fit, because a mode dialog box would block the user's operation to the busy main window. But mode dialog box has a problem, not only the user's operation is blocked, but also the code is blocked in the DialogBox function. I cannot make futher process to perform loading and saving after I call the DialogBox. Immediately, I figure out a way. Of course, it's multi-thread. Please look at my chart below.
An UI puzzle - Create a dialog in a thread._第1张图片
Main Window was created by Main Thread. When I want to process saving and loading, I create the Sub Thread. The Sub Thread creates the dialog, and main thread continue to do the busy job saving and loading. When it is finished, close the Please Wait window. Implementation is not difficult, so I won't paste my code here.

But after doing so, I got a problem. The Please Wait window doesn't show until the busy process finishes. It's strange, I did it by multi-thread! In order to test it, I added a timer in the WM_INITDIALOG's procedure of the Please Wait dialog, printing debug message in every 100ms. I was surprised that the Sub Thread was busy too. No debug message was outputed until the Main Thread finished its busy job.

I checked my code. I didn't use SendMessage in any place. My code wasn't supposed to be blocked. But that is the issue... Although I didn't call the SendMessage explicitly, the DefDlgProc might do that implicitly. That's the truth. The SendMessage wouldn't return until the busy process was finished. So, the Please Wait dialog was blocked too.

How to solve this problem? The best way is to redesign the code. Let the busy process to be done in the Sub Thread but not the UI thread. Let the Sub Thread communicate with the UI thread by posting messages. But this job is difficult, I have to modify many code. So I did it by another way, but I must declare that it is not a good way. And this way may break the application's perfect structure. That's the description:

Don't let the Main Thread do the busy process immediately after creating the Sub Thread. What time should the Main Thread do the busy job? The Please Wait dialog will tell it. I gave 500ms to the Please Wait dialog to show itself by creating a timer in the WM_INITDIALOG. When the time event triggers, post a message to the Main Thread, and the Main Thread will begin the busy process. Yes, the Please Wait dialog is also busy now, it loses response to the user, but it's shown. After the busy process done, the Main Thread post a message to the Please Wait dialog to tell it to close. Not good method but it works.

你可能感兴趣的:(Windows编程)