Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/263.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# C在SizeChanged事件期间修改表单大小_C#_Winforms_Resize - Fatal编程技术网

C# C在SizeChanged事件期间修改表单大小

C# C在SizeChanged事件期间修改表单大小,c#,winforms,resize,C#,Winforms,Resize,如果满足条件,我将在调整窗体大小时尝试设置窗体的高度。我将其设置为仅允许使用手动更改窗体的宽度 我有一个FlowLayoutPanel,显示一组PictureBox控件,每个控件的固定高度为50像素。最初,表单的高度是38 Size.Height-ClientSize.Height+50+6 Margin.Top+Margin.bottomofimage=94 如果控件溢出,默认情况下FlowLayoutPanel会将它们向下推到新行上。我想做的是在这种情况下调整窗体的大小,或者手动更改窗体宽度

如果满足条件,我将在调整窗体大小时尝试设置窗体的高度。我将其设置为仅允许使用手动更改窗体的宽度

我有一个FlowLayoutPanel,显示一组PictureBox控件,每个控件的固定高度为50像素。最初,表单的高度是38 Size.Height-ClientSize.Height+50+6 Margin.Top+Margin.bottomofimage=94

如果控件溢出,默认情况下FlowLayoutPanel会将它们向下推到新行上。我想做的是在这种情况下调整窗体的大小,或者手动更改窗体宽度,这可能会导致控件跳转到下一行

以下代码有效,并在将新控件添加到FlowLayoutPanel itemPanel时调用:

private void ResizeForm()
{
    if (itemPanel.Controls.Count < 1) return;

    var lastElement = itemPanel.Controls[itemPanel.Controls.Count - 1];

    // The Form is the correct size, no need to resize it:
    if (lastElement.Bottom + lastElement.Margin.Bottom == itemPanel.Height) return;

    Height = 38 + lastElement.Bottom + lastElement.Margin.Bottom;
}
我猜原因是因为设置高度将再次触发SizeChange事件,但我不知道如何解决此问题。当我打印出lastElement.Bottom+lastElement.Margin.Bottom和itemPanel.Height的值时,设置高度后,它们是相同的,但代码仍然以某种方式达到了这一点

简而言之,我只希望手动更改表单宽度,但在添加项目或更改宽度时,表单的高度会更改,以便可以查看FlowLayoutPanel内的所有控件。

尝试一下:

private void ResizeForm()
{
    this.SuspendLayout(); // Suspends the layout logic until ResumeLayout() is called (below)

    if (itemPanel.Controls.Count < 1) return;

    var lastElement = itemPanel.Controls[itemPanel.Controls.Count - 1];

    // The Form is the correct size, no need to resize it:
    if (lastElement.Bottom + lastElement.Margin.Bottom == itemPanel.Height) return;

    Height = 38 + lastElement.Bottom + lastElement.Margin.Bottom;

    this.ResumeLayout(); // ADD THIS AS WELL
}
但是,当在my SizeChange事件中调用时,此方法会导致 要在初始高度和新高度之间闪烁的窗体

基本上,表单的任何库存调整事件都将发生得太晚,您无法在不被注意的情况下更改大小

您将要捕获该消息:

发送到用户正在调整大小的窗口。通过处理这个 消息,应用程序可以监视拖动的大小和位置 矩形,如果需要,更改其大小或位置

这将允许您在窗体在屏幕上实际更新之前更改窗体的大小

它看起来像这样:

public partial class Form1 : Form
{

    private struct RECT
    {
        public int Left;
        public int Top;
        public int Right;
        public int Bottom;
    }

    enum HitTest
    {
        Caption = 2,
        Transparent = -1,
        Nowhere = 0,
        Client = 1,
        Left = 10,
        Right = 11,
        Top = 12,
        TopLeft = 13,
        TopRight = 14,
        Bottom = 15,
        BottomLeft = 16,
        BottomRight = 17,
        Border = 18
    }

    private const int WM_SIZING = 0x214;
    private const int WM_NCHITTEST = 0x84;

    public Form1()
    {
        InitializeComponent();
    }

    protected override void WndProc(ref Message m)
    {
        base.WndProc(ref m);

        switch (m.Msg)
        {
            case WM_NCHITTEST:
                var result = (HitTest)m.Result.ToInt32();
                if (result == HitTest.Top || result == HitTest.Bottom)
                    m.Result = new IntPtr((int)HitTest.Caption);
                if (result == HitTest.TopLeft || result == HitTest.BottomLeft)
                    m.Result = new IntPtr((int)HitTest.Left);
                if (result == HitTest.TopRight || result == HitTest.BottomRight)
                    m.Result = new IntPtr((int)HitTest.Right);
                break;

            case WM_SIZING:
                // Retrieve the "proposed" size of the Form in "rc":
                RECT rc = (RECT)Marshal.PtrToStructure(m.LParam, typeof(RECT));

                // ... do something with "rc" ...

                // this is your code (slightly modified):
                if (itemPanel.Controls.Count > 0)
                {
                    var lastElement = itemPanel.Controls[itemPanel.Controls.Count - 1];

                    if (lastElement.Bottom + lastElement.Margin.Bottom != itemPanel.Height)
                    {
                        int Height = 38 + lastElement.Bottom + lastElement.Margin.Bottom;
                        rc.Bottom = rc.Top + Height; // <--- use "Height" to update the "rc" struct
                    }
                }

                // Put the updated "rc" back into message structure:
                Marshal.StructureToPtr(rc, m.LParam, true);
                break;
        }
    }

}

这不管用。我决定采用“空闲思维”的解决方案。谢谢这太好笑了。我决定再试一次,看看是否有答案,我想出的解决办法就是这样!我正要回答我自己的问题,这时我看到你这样做了,所以我会接受你的回答。谢谢
public partial class Form1 : Form
{

    private struct RECT
    {
        public int Left;
        public int Top;
        public int Right;
        public int Bottom;
    }

    enum HitTest
    {
        Caption = 2,
        Transparent = -1,
        Nowhere = 0,
        Client = 1,
        Left = 10,
        Right = 11,
        Top = 12,
        TopLeft = 13,
        TopRight = 14,
        Bottom = 15,
        BottomLeft = 16,
        BottomRight = 17,
        Border = 18
    }

    private const int WM_SIZING = 0x214;
    private const int WM_NCHITTEST = 0x84;

    public Form1()
    {
        InitializeComponent();
    }

    protected override void WndProc(ref Message m)
    {
        base.WndProc(ref m);

        switch (m.Msg)
        {
            case WM_NCHITTEST:
                var result = (HitTest)m.Result.ToInt32();
                if (result == HitTest.Top || result == HitTest.Bottom)
                    m.Result = new IntPtr((int)HitTest.Caption);
                if (result == HitTest.TopLeft || result == HitTest.BottomLeft)
                    m.Result = new IntPtr((int)HitTest.Left);
                if (result == HitTest.TopRight || result == HitTest.BottomRight)
                    m.Result = new IntPtr((int)HitTest.Right);
                break;

            case WM_SIZING:
                // Retrieve the "proposed" size of the Form in "rc":
                RECT rc = (RECT)Marshal.PtrToStructure(m.LParam, typeof(RECT));

                // ... do something with "rc" ...

                // this is your code (slightly modified):
                if (itemPanel.Controls.Count > 0)
                {
                    var lastElement = itemPanel.Controls[itemPanel.Controls.Count - 1];

                    if (lastElement.Bottom + lastElement.Margin.Bottom != itemPanel.Height)
                    {
                        int Height = 38 + lastElement.Bottom + lastElement.Margin.Bottom;
                        rc.Bottom = rc.Top + Height; // <--- use "Height" to update the "rc" struct
                    }
                }

                // Put the updated "rc" back into message structure:
                Marshal.StructureToPtr(rc, m.LParam, true);
                break;
        }
    }

}