2

In this question, Remy said in a comment that:

the HWND provided by the TWinControl.Handle property is not persistent. It can get destroyed and recreated during a component's lifetime, even multiple times. Every time the TShellListView gets a new HWND assigned, you have to call DragAcceptFiles(TRUE) again. Overriding CreateWnd() allows you to do that. For good measure, you should also override DestroyWnd() to call DragAcceptFiles(FALSE) before the HWND is destroyed.

I wasn't aware of that until now and I want to understand the mechanism that destroy and recreate the HWND. What are the cases when this is happening and why ?

Marus Gradinaru
  • 2,824
  • 1
  • 26
  • 55
  • 1
    It usually happens when a style change requires it. It should be easy to debug this, using the debug units. – Rudy Velthuis Jun 22 '17 at 12:21
  • 1
    Very much depends on the control. Hard to be anything other than vague. If you need a window that is not subject to recreation use AllocateHWnd. – David Heffernan Jun 22 '17 at 12:28
  • 1
    Read the comments to the question [What external events trigger TCustomForm.RecreateWnd?](https://stackoverflow.com/q/27400973/62576). Then see the VCL source for TWinControl and the calls to RecreateWnd that are made in that source. – Ken White Jun 22 '17 at 12:33
  • 1
    @KenWhite That doesn't really get you there. The actual control that Remy mentioned is `TShellListView`, so it may very well have its own calls to recreate the window, beyond what `TWinControl` does. Marus seems to be asking more generally than just for that control. And also you need to know about every control in the parenting chain, because when a window is recreated, all children are too. – David Heffernan Jun 22 '17 at 13:12
  • @RudyVelthuis Hardly. Debugging allows you to track what happens when a recreation happens. It won't tell you all the events that can lead to recreation. – David Heffernan Jun 22 '17 at 13:13
  • @DavidHeffernan: Yes, I'm aware. It's a starting point. I didn't say it was a definitive, absolute list. If I had one of those, it would be provided as an answer. – Ken White Jun 22 '17 at 13:16
  • @David: it depends on where you put your breakpoints and what the call stack shows on each of them. Of course, it also helps to read the source code. – Rudy Velthuis Jun 22 '17 at 13:46
  • @RudyVelthuis Nonsense. If you don't trigger the event in the first place, no break points will get hit, no matter where you place them. – David Heffernan Jun 22 '17 at 14:01
  • 1
    @David: If no breakpoint gets hit, you know that no recreation has taken place. Of course you won't find all possible situations. Just the ones you care about, in your particular situation. But that is IMO not the question. He wants to know what general situations require such a recreation. – Rudy Velthuis Jun 22 '17 at 14:19
  • @RudyVelthuis How will you find the ones that you care about. You just sit there in front of the computer for five minutes and when no break point is hit you decide that your window won't ever get recreated. – David Heffernan Jun 22 '17 at 14:28
  • The ones I would probably care about (if at all) would be the ones that happen when I run my app. I would simply test the GUI (every aspect of it). Of course looking at the VCL code and looking when a window is recreated also helps. Knowing what situations cause such recreations also helps. – Rudy Velthuis Jun 22 '17 at 16:10
  • @Rudy OK, I understand where your misthink is. Recreations are often triggered by your own program, but not always. A classic is when the system theme settings are changed. But there are others. How are you going to test all of them? – David Heffernan Jun 22 '17 at 16:11
  • @David: I am not going to test all of them. ISTM that the questions is: in what kind of situations does this happen, i.e. what could cause it. That can be answered quite generally, without any specifics. – Rudy Velthuis Jun 22 '17 at 16:13
  • "Why" is when it is required, or when you are not sure if it is required or not. For instance "forms" use it when the api owner needs to change (PopupParent). That falls in the former category (when it is required). Anyway, it is practically impossible to come up with an exhausting list; for both *where* and *why*. – Sertac Akyuz Jun 22 '17 at 17:32
  • @Rudy And your answer, to do that, is to work it out in the debugger? Read what you wrote. – David Heffernan Jun 22 '17 at 17:57
  • 1
    @David: If I wanted to know when my control is recreated, I would use a debugger, yes. – Rudy Velthuis Jun 22 '17 at 18:08
  • @Rudy Then you'd fail to find out. – David Heffernan Jun 22 '17 at 18:16
  • @David: until now, I never failed to find out what I wanted to know. And most of the time, I used the debugger. – Rudy Velthuis Jun 22 '17 at 18:20
  • @rudy you failed this time, first time for everything! – David Heffernan Jun 22 '17 at 18:25
  • @David: I didn't fail yet. You think I might fail, fine. I don't think so. – Rudy Velthuis Jun 22 '17 at 18:34
  • @Rudy You are sitting there waiting for your debugger to break for an external event that won't fire on your machine, but will on another machine. So yeah, you failed to find out when windows are recreated. – David Heffernan Jun 22 '17 at 18:35
  • No, I am not. But you think I would, if I tried. Generally, RecreateWnd is used to set certain properties that require different create params. There may be other reasons that window is recreated, but hey, I don't care about them. So no, I won't wait. – Rudy Velthuis Jun 22 '17 at 18:38
  • @Rudy You might not care about them but that's the question that was asked. But hey, why answer the question that was asked when you can answer the question that you wish was asked. – David Heffernan Jun 22 '17 at 20:46
  • What is, in your interpretation, the question that was asked? – Rudy Velthuis Jun 22 '17 at 21:04
  • The question can be read above. The final sentence. – David Heffernan Jun 22 '17 at 21:25
  • How can I find out, what is re-re-recreating the form's handle 10+ times pro second? _Whenever I check with a timer, `Form2.Handle` is not the same as before._ Break when changed is greyed out at Watch window. Overriding the Form's `.CreateHandle` did not help, it does not stop there. This is a huge (1M lines) project. If I create a tiny project, I can not reproduce it. _(Using AlphaSkin components.)_ – SzakiLaci Aug 05 '23 at 19:07

0 Answers0