Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/271.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#_Image_Winforms_Modal Dialog - Fatal编程技术网

C# 如何从对话框“取消”加载事件

C# 如何从对话框“取消”加载事件,c#,image,winforms,modal-dialog,C#,Image,Winforms,Modal Dialog,我正在尝试创建一个从来可视化和编辑图像,简单的东西如下: 绘制矩形 写作材料 裁剪矩形 但我遇到了很多困难,例如:如果我试图加载一个不存在或无法打开的文件,它不是图像,我希望显示一个MessageBox,然后关闭表单。但是表单没有立即关闭,这可能会导致错误,因为我可能会尝试访问未打开的文件的属性。你能告诉我为什么吗?检查Abort方法,源代码在文章的末尾 我使用以下事件在内部创建表单: private void button2_Click(object sender, EventArgs e)

我正在尝试创建一个从来可视化和编辑图像,简单的东西如下:

绘制矩形 写作材料 裁剪矩形 但我遇到了很多困难,例如:如果我试图加载一个不存在或无法打开的文件,它不是图像,我希望显示一个MessageBox,然后关闭表单。但是表单没有立即关闭,这可能会导致错误,因为我可能会尝试访问未打开的文件的属性。你能告诉我为什么吗?检查Abort方法,源代码在文章的末尾

我使用以下事件在内部创建表单:

private void button2_Click(object sender, EventArgs e)
        {
            Forms.AreaSelector areaSelector = new Forms.AreaSelector(LabelInput);
            areaSelector.ShowDialog();
        }
我想以对话框的形式显示表单,这样用户就不能返回“主窗口”,而不查看对图像的修改,这就是我使用.ShowDialog而不是show的原因 我尝试在Abort方法中调用Close甚至Dispose,但是表单继续通过continues to load加载。我的意思是,UpdateWindowSize和UpdatePictureBox被称为与我在Abort中的操作无关

这是实际的表单代码

资料来源:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace PeeAlyser.Forms
{
    public partial class AreaSelector : Form
    {
        #region Variables

        Bitmap originalImage, modifiedImage;
        string fileName;

        #endregion


        #region Constructors

        public AreaSelector(string fileName)
        {
            InitializeComponent();

            this.fileName = fileName;
        }

        #endregion

        private void AreaSelector_Load(object sender, EventArgs e)
        {
            TryToLoadImage();
            UpdateWindowSize();
            UpdatePictureBox();
        }

        #region Private Methods

        private void Abort()
        {
            this.DialogResult = System.Windows.Forms.DialogResult.Cancel;
            this.BeginInvoke(new MethodInvoker(this.Close));
            //this.Close();
            //this.Dispose();
            // GODAMNIT!
        }

        private void TryToLoadImage()
        {
            if (!System.IO.File.Exists(fileName))
            {
                MessageBox.Show("File not found.");
                Abort();
            }


            try { originalImage = (Bitmap)Bitmap.FromFile(fileName); }
            catch (Exception error)
            {
                MessageBox.Show("Error: " + Environment.NewLine +
                                error.ToString());
                Abort();
            }


            this.modifiedImage = new Bitmap(originalImage);
        }

        private void UpdateWindowSize()
        {
            int widthDifference = this.Width - pictureBox1.Width;
            int heightDifference = this.Height - pictureBox1.Height;

            Size windowSize = originalImage.Size;
            windowSize.Width += widthDifference;
            windowSize.Height += heightDifference;

            this.Size = this.MinimumSize = this.MaximumSize = windowSize;
            this.pictureBox1.Size = originalImage.Size;

            this.AdjustFormScrollbars(true);
        }

        private void UpdatePictureBox()
        {
            this.pictureBox1.Image = modifiedImage;
            this.Refresh();
        }

        #endregion
    }
}
编辑:我收到了很多关于解决这个问题的建议。但是汉斯的回答不仅纠正了我的更正中的一个设计缺陷,也解决了这个问题,而且还解释了为什么在检查他的链接时会出现这种问题。所以我选择了他的答案。
请随意关闭此问题,mods。谢谢你们的帮助

您可以通过返回false使TryToLoadImage布尔替换Adort,并按如下方式运行它:

if(TryToLoadImage())
{
        UpdateWindowSize();
        UpdatePictureBox();
}
else Close();

您可以通过返回false使TryToLoadImage布尔替换Adort,并按如下方式运行它:

if(TryToLoadImage())
{
        UpdateWindowSize();
        UpdatePictureBox();
}
else Close();

最好的选择是避免负载事件中的可疑部分

但是,如果您想在Load事件本身中执行操作,我建议使用一个简单的过程

使用名为access的整数变量,并在默认情况下将其设置为1

正如您所提到的,您希望显示一个messagebox,然后关闭它。在messagebox行之前,将access变量的值设置为0

将PostMessageBox代码包含在If-Else块中

您需要的代码是:-

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Windows.Forms;

    namespace PeeAlyser.Forms
    {
      public partial class AreaSelector : Form
       {
    #region Variables

    Bitmap originalImage, modifiedImage;
    string fileName;

    #endregion


    #region Constructors

    public AreaSelector(string fileName)
    {
        InitializeComponent();

        this.fileName = fileName;
    }

    #endregion

public int access=1;

    private void AreaSelector_Load(object sender, EventArgs e)
    {
        TryToLoadImage();
        if(access==1)
    {
        UpdateWindowSize();
            UpdatePictureBox();
    }
    }

    #region Private Methods

    private void Abort()
    {
        this.DialogResult = System.Windows.Forms.DialogResult.Cancel;
        this.BeginInvoke(new MethodInvoker(this.Close));
        //this.Close();
        //this.Dispose();
        // GODAMNIT!
    }

    private void TryToLoadImage()
    {
        if (!System.IO.File.Exists(fileName))
        {
    access=0;
            MessageBox.Show("File not found.");
            Abort();
        }


        try { originalImage = (Bitmap)Bitmap.FromFile(fileName); }
        catch (Exception error)
        {
            MessageBox.Show("Error: " + Environment.NewLine +
                            error.ToString());
            Abort();
        }


        this.modifiedImage = new Bitmap(originalImage);
    }

    private void UpdateWindowSize()
    {
        int widthDifference = this.Width - pictureBox1.Width;
        int heightDifference = this.Height - pictureBox1.Height;

        Size windowSize = originalImage.Size;
        windowSize.Width += widthDifference;
        windowSize.Height += heightDifference;

        this.Size = this.MinimumSize = this.MaximumSize = windowSize;
        this.pictureBox1.Size = originalImage.Size;

        this.AdjustFormScrollbars(true);
    }

    private void UpdatePictureBox()
    {
        this.pictureBox1.Image = modifiedImage;
        this.Refresh();
    }

    #endregion
}
}

最好的选择是避免负载事件中的可疑部分

但是,如果您想在Load事件本身中执行操作,我建议使用一个简单的过程

使用名为access的整数变量,并在默认情况下将其设置为1

正如您所提到的,您希望显示一个messagebox,然后关闭它。在messagebox行之前,将access变量的值设置为0

将PostMessageBox代码包含在If-Else块中

您需要的代码是:-

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Windows.Forms;

    namespace PeeAlyser.Forms
    {
      public partial class AreaSelector : Form
       {
    #region Variables

    Bitmap originalImage, modifiedImage;
    string fileName;

    #endregion


    #region Constructors

    public AreaSelector(string fileName)
    {
        InitializeComponent();

        this.fileName = fileName;
    }

    #endregion

public int access=1;

    private void AreaSelector_Load(object sender, EventArgs e)
    {
        TryToLoadImage();
        if(access==1)
    {
        UpdateWindowSize();
            UpdatePictureBox();
    }
    }

    #region Private Methods

    private void Abort()
    {
        this.DialogResult = System.Windows.Forms.DialogResult.Cancel;
        this.BeginInvoke(new MethodInvoker(this.Close));
        //this.Close();
        //this.Dispose();
        // GODAMNIT!
    }

    private void TryToLoadImage()
    {
        if (!System.IO.File.Exists(fileName))
        {
    access=0;
            MessageBox.Show("File not found.");
            Abort();
        }


        try { originalImage = (Bitmap)Bitmap.FromFile(fileName); }
        catch (Exception error)
        {
            MessageBox.Show("Error: " + Environment.NewLine +
                            error.ToString());
            Abort();
        }


        this.modifiedImage = new Bitmap(originalImage);
    }

    private void UpdateWindowSize()
    {
        int widthDifference = this.Width - pictureBox1.Width;
        int heightDifference = this.Height - pictureBox1.Height;

        Size windowSize = originalImage.Size;
        windowSize.Width += widthDifference;
        windowSize.Height += heightDifference;

        this.Size = this.MinimumSize = this.MaximumSize = windowSize;
        this.pictureBox1.Size = originalImage.Size;

        this.AdjustFormScrollbars(true);
    }

    private void UpdatePictureBox()
    {
        this.pictureBox1.Image = modifiedImage;
        this.Refresh();
    }

    #endregion
}
}
加载事件在Winforms中被过度使用。它继承了它的前身VB6的一个挂起,在那里它是非常重要的,因为这是放置任何初始化代码的地方。这使得它成为默认事件,太容易使用了

但不是在.NET中,初始化是在类的构造函数中完成的。负载事件太晚了,列车离开车站,已经获得了相当大的速度。试图阻止它是困难的,例如,抛出异常没有效果。事实上是这样。只有在需要知道窗口的大小和位置时,才应使用Load事件。这是非常罕见的,尽管看起来你有用处

你需要在火车开动之前停下来,你的TryToLoadImage调用属于构造函数。现在它非常简单,当正常工作的东西不能工作时,你在C中做正常的事情,你抛出一个异常。并在ShowDialog呼叫站点捕获它。轻松搞定。

加载事件在Winforms中被过度使用。它继承了它的前身VB6的一个挂起,在那里它是非常重要的,因为这是放置任何初始化代码的地方。这使得它成为默认事件,太容易使用了

但不是在.NET中,初始化是在类的构造函数中完成的。负载事件太晚了,列车离开车站,已经获得了相当大的速度。试图阻止它是困难的,例如,抛出异常没有效果。事实上是这样。只有在需要知道窗口的大小和位置时,才应使用Load事件。这是非常罕见的,尽管看起来你有用处


你需要在火车开动之前停下来,你的TryToLoadImage调用属于构造函数。现在它非常简单,当正常工作的东西不能工作时,你在C中做正常的事情,你抛出一个异常。并在ShowDialog呼叫站点捕获它。轻松轻松。

在加载事件中不应该这样做。将错误检测逻辑从加载事件中释放。如何。。。我可以这样做吗?我是说。我是否应该将图像的数据源设置在加载事件之外?那么,在哪种情况下?继续加载是指它进入UpdateWindowSize还是什么?是的,这就是我所说的继续加载。在加载事件中尝试e.取消?你不应该这样做
在加载事件中。将错误检测逻辑从加载事件中释放。如何。。。我可以这样做吗?我是说。我是否应该将图像的数据源设置在加载事件之外?在哪种情况下,那么?继续加载你的意思是它进入UpdateWindowSize还是什么?是的,我的意思是继续加载。在加载事件中尝试e.取消?谢谢你的比喻和建议。我将把我的TryToLoadImage移到构造函数中,并很快回复结果。但是,为什么火车不能停下来呢?顺便说一句这样做是有道理的。在构造函数中分配内容。。。糟糕的是,火车是操作系统创建的本地窗口。它已经创建并初始化,只是还不可见。加载事件是我将要收到的可见通知。您可以调用Close或设置DialogResult属性,但这不会阻止窗口在屏幕上短暂闪烁。并引发一些其他事件,这些事件可能会因为位图未加载而爆炸。Windows没有取消通知的选项,最明显的是加载事件没有CancelEventArgs参数。感谢您的隐喻和建议。我将把我的TryToLoadImage移到构造函数中,并很快回复结果。但是,为什么火车不能停下来呢?顺便说一句这样做是有道理的。在构造函数中分配内容。。。糟糕的是,火车是操作系统创建的本地窗口。它已经创建并初始化,只是还不可见。加载事件是我将要收到的可见通知。您可以调用Close或设置DialogResult属性,但这不会阻止窗口在屏幕上短暂闪烁。并引发一些其他事件,这些事件可能会因为位图未加载而爆炸。Windows没有取消通知的选项,最明显的是加载事件没有CancelEventArgs参数。