简体   繁体   English

如何防止控件改变Z顺序?

[英]How to prevent a control from changing Z order?

I have user control in .Net where I use a hit test in WndProc to allow resizing it in runtime with the mouse. 我在.Net中具有用户控件,在其中我在WndProc中使用命中测试以允许在运行时使用鼠标调整其大小。

The problem is that after the hit test succedes (mouse press, drag to resize, mouse release) the control jumps upwards in the Z order and ruins it position in the form. 问题是,命中测试成功(鼠标按下,拖动以调整大小,释放鼠标)后,控件将按Z顺序向上跳跃并破坏其在表单中的位置。

I need the hit test since it's a very customized control. 我需要进行点击测试,因为它是一个非常定制的控件。

Is there a way in WndProc to stop the control from changing it's Z order ? WndProc中是否有一种方法可以阻止控件更改其Z顺序?

Thanks. 谢谢。

The hit test code: 命中测试代码:

protected override void WndProc(ref Message m) {
  if (!DesignMode && Sizeable && (m.Msg == Win32Wrapper.WM_NCHITTEST)) {
    Point Hit = new Point((int)m.LParam & 0xFFFF, (int)m.LParam >> 16);
    Hit = this.PointToClient(Hit);
    int DistToBorder = 5;
    if (Hit.X < DistToBorder) {
      if (Hit.Y < DistToBorder) {
        m.Result = (IntPtr)Win32Wrapper.HTTOPLEFT;
        return;
      }
      if (Hit.Y > this.ClientRectangle.Bottom - DistToBorder) {
        m.Result = (IntPtr)Win32Wrapper.HTBOTTOMLEFT;
        return;
      }
      m.Result = (IntPtr)Win32Wrapper.HTLEFT;
      return;
    }
    else if (Hit.X > ClientRectangle.Right - DistToBorder) {
      if (Hit.Y < DistToBorder) {
        m.Result = (IntPtr)Win32Wrapper.HTTOPRIGHT;
        return;
      }
      else if (Hit.Y > this.ClientRectangle.Bottom - DistToBorder) {
        m.Result = (IntPtr)Win32Wrapper.HTBOTTOMRIGHT;
        return;
      }
      m.Result = (IntPtr)Win32Wrapper.HTRIGHT;
      return;
    }
    else if (Hit.Y < DistToBorder) {
      m.Result = (IntPtr)Win32Wrapper.HTTOP;
      return;
    }
    else if (Hit.Y > this.ClientRectangle.Bottom - DistToBorder) {
      m.Result = (IntPtr)Win32Wrapper.HTBOTTOM;
      return;
    }
  }

为了防止Z顺序更改,您应该捕获WM_WINDOWPOSCHANGING消息并设置SWP_NOZORDER标志。

Are you sure it's the hit test that's causing the problem? 您确定是导致问题的点击测试吗? How are you resizing the control? 您如何调整控件的大小? One option is to call SetWindowPos using p-invoke passing it SWP_NOZORDER flag. 一种选择是使用传递给它的SWP_NOZORDER标志的p调用来调用SetWindowPos。

没有答案,但是您是否尝试过使用ControlDesigner,而不是滚动自己的Deigner模式交互作用?

Window dialogs manage tab order and focus through the controls windows' z-order, the control that is given focus is raised to the top. 窗口对话框管理选项卡顺序,并通过控件窗口的z顺序进行聚焦,被赋予焦点的控件被提升到顶部。

If you want your custom control to retain its relative z-positioning, then ensure that its properties do not indicate its a TABSTOP or otherwise capable of receiving focus. 如果您希望自定义控件保留其相对的z位置,请确保其属性不指示其TABSTOP或能够接收焦点。 ie will it work if disabled? 即如果禁用它会工作吗?

The flip side of this is, even if you successfullly stop your control's z-order from changing, its implicitly going to be re-positioned as the user interacts with other controls. 不利的一面是,即使您成功地停止了控件的z顺序更改,它的隐式也将在用户与其他控件进行交互时重新定位。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM