enzoliu / ch4pkeditor

0 stars 1 forks source link

Bug Fix: loadMemoryData() is being executed twice #5

Open resevp opened 2 hours ago

resevp commented 2 hours ago

In the file: Form1.cs, in an unknown circumstance, loadMemoryData() will executed twice when the button loadGameBtn is clicked, which will cause the following method to face error:

private void BindListBox(ListBox control, object list, EventHandler evt)
>> System.IndexOutOfRangeException: 'Index was outside the bounds of the array.'

or 

private void BindComboBox(ComboBox control, object list, EventHandler evt)
>> System.ArgumentNullException: 'Value cannot be null. Parameter name: item'

Therefore, I have added a global value of

bool _loadingInProgress = false;

the following is proposed to prevent the "double" execution:

private void loadMemoryData()
{
    // check is the loading is running, if yes, do not run the process again
    if (_loadingInProgress)
        return;

    // tell the program, the loading process start now
    _loadingInProgress = true;

    ShowMessage("讀取資料中,請稍後。");
    setControls(false);
    Task t = new Task(() =>
    {
        Center.shared.Setup();

        string[] errorMsgs = Core.shared.getErrorMessage();
        if (errorMsgs.Count() > 0)
        {
            foreach (string msg in errorMsgs)
            {
                ShowMessage(msg);
            }
        }
        else
        {
            BindListBox(generalCityListBox, Center.shared.CityList, generalCityListBox_SelectedIndexChanged);
            BindListBox(generalListBox, Center.shared.GeneralList, generalListBox_SelectedIndexChanged);
            BindListBox(cityListBox, Center.shared.CityList, cityListBox_SelectedIndexChanged);
            BindListBox(wifeListBox, Center.shared.WifeList, wifeListBox_SelectedIndexChanged);
            BindComboBox(wifeHusbandNameComboBox, Center.shared.HusbandList, wifeHusbandNameComboBox_SelectedIndexChanged);
            setControls(true);
            ShowMessage("讀取完畢。");
        }

        // here, tell the program the loading progress is completed.
        _loadingInProgress = false;
    });
    t.Start();
}
resevp commented 2 hours ago

I have found the reason, why loadMemoryData() is being executed twice.

This is because I have added a MessageBox to ask the user to choose the the Chinese version (繁體/簡體). The MessageBox will trigger the loadMemoryData() which is set by initializeEditorFocusMonitor().

When the MessageBox pop up, it make the main window loses focus, when the MessageBox closed, the main window regains focus and due to initializeEditorFocusMonitor(), the program executes loadMemoryData().

resevp commented 2 hours ago

As per my personal preference, I have disabled the initializeEditorFocusMonitor(), I will manually refresh/reload the data when needed by clicking on the button [讀取游戲].

public mainForm()
{
    InitializeComponent();

    // disable the focus monitor
    //initializeEditorFocusMonitor();

    versionLabel.Text = Application.ProductVersion;
}

I frequently switched focus between the game and editor for checking various data before doing some edits. I do not want the editor perform a fresh new reload each time I come back.