c # - аргумент командной строки WPF для открытия файла дает бесконечный цикл - PullRequest
2 голосов
/ 05 марта 2011

Это странно! Я работаю над приложением, которое читает файлы vCard, которые содержат контактную информацию и т. Д. Для человека. Каждый файл может содержать отдельные «разделы», каждый из которых содержит сведения об одном человеке, разделенные BEGIN: VCARD [данные здесь] END: VCARD.

Чтобы позволить моим пользователям просматривать все различные детали, я позволил моей программе заполнить текстовые поля в моем приложении сведениями, а затем открыть новое окно и сделать это с этим, но для каждого из разделы в файле.

Проблема возникает, когда моя программа открывается при двойном щелчке файла vCard в Проводнике. Он продолжает проходить через vCard. Я не знаю, что делать, но ниже приведен мой проблемный код:

    public void readVcard(string fname)//Reads vCard and then loops through sections
    {
        try
        {
            using (StreamReader r = new StreamReader(fname))
            {
                string input = File.ReadAllText(fname);//read through file

                String[] vArray = input.Split(new string[] { "BEGIN:VCARD" }, StringSplitOptions.None);

                int i;

                for (i = 1; i < vArray.Length; i++)
                {
                    MainWindow a = new MainWindow();
                    a.parser(vArray[i]); //Parser is the function that populates the app
                    a.Show();
                }

                return;
            }
        }...

Эта функция вызывается отсюда:

    void MainWindow_Loaded(object sender, RoutedEventArgs e)//Processes a file when opened externally
    {
        if (Application.Current.Properties["ArbitraryArgName"] != null)
        {
            string fname = Application.Current.Properties["ArbitraryArgName"].ToString();

            readVcard(fname);

        }
    }

Если бы кто-нибудь мог помочь, это было бы очень признательно.

Ответы [ 3 ]

3 голосов
/ 05 марта 2011

Я думаю, что Артём на правильном пути.

Каждый раз, когда вы создаете другое MainWindow и загружаете его, вы получаете текущий аргумент приложения и возвращаетесь к readVcard , которая будет обрабатывать ту же самую vCard, что и вы.уже обрабатывают и открывают еще одно MainWindow , которое продолжит процесс.

Рассмотрите возможность перемещения всего кода, который есть внутри MainWindow_Loaded () , на Запуск событие для вашего приложения.Таким образом, он будет вызываться только один раз при первой загрузке вашей программы, а не каждый раз, когда вы создаете новое окно.

Для этого вам нужно зарегистрироваться для события в вашем файле App.xaml, например:

<Application x:Class="MyProgram.App"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Startup="Application_Startup">
</Application>

А затем в коде App.xaml вы помещаете свой код для чтения vCard.Как это:

namespace MyProgram
{
    /// <summary>
    /// Interaction logic for App.xaml
    /// </summary>
    public partial class App : Application
    {
        private void Application_Startup(object sender, StartupEventArgs e)
        {
            if (Application.Current.Properties["ArbitraryArgName"] != null)
            {
                string fname = Application.Current.Properties["ArbitraryArgName"].ToString();

                readVcard(fname);

            }
        }
    }
}
1 голос
/ 05 марта 2011

Когда вы создаете и отображаете новое MainWindow (a.Show ()), событие MainWindow_Loaded запускается снова и снова вызывает метод readVcard. Так что есть бесконечный цикл.

Или может быть не очень бесконечным, потому что, я полагаю, через некоторое время может возникнуть исключение StackOverflowException.

Вам просто нужно просмотреть логику запуска, поэтому readVcard будет запускаться не в событии MainWindow_Loaded, а, например, в методе Main (в файле program.cs). Или вы можете добавить какой-нибудь флаг, который будет установлен при первом вызове метода readVcard.

0 голосов
/ 06 марта 2011

Я понял!Теперь у меня есть следующий код в App.xaml.cs:

public partial class App : Application
{
    protected override void OnStartup(StartupEventArgs e)
    {
        if (e.Args != null && e.Args.Count() > 0)
        {
            this.Properties["ArbitraryArgName"] = e.Args[0];
        }
        base.OnStartup(e);

        if (Application.Current.Properties["ArbitraryArgName"] != null)
        {
            string fname = Application.Current.Properties["ArbitraryArgName"].ToString();

            MainWindow mw = new MainWindow();
            mw.readVcard(fname);

        }
    }

}

Работает отлично!Спасибо всем.Кстати, следующий блог содержит информацию о командной строке, которую я первоначально использовал, если кому-то это нужно: http://blogs.msdn.com/b/avip/archive/2008/10/27/wpf-supporting-command-line-arguments-and-file-extensions.aspx.

...