FinishPageCompleted() public method

public FinishPageCompleted ( ) : void
return void
示例#1
0
        public void ShowPage(PageType type, string [] warnings)
        {
            if (type == PageType.Setup)
            {
                Header      = "Welcome to SparkleShare!";
                Description = "First off, what’s your name and email?\n(visible only to team members)";

                FullNameLabel       = new SparkleLabel("Full Name:", NSTextAlignment.Right);
                FullNameLabel.Frame = new CGRect(165, Frame.Height - 234, 160, 17);

                FullNameTextField = new NSTextField()
                {
                    Frame       = new CGRect(330, Frame.Height - 238, 196, 22),
                    StringValue = new NSProcessInfo().GetFullUserName(),
                    Delegate    = new SparkleTextFieldDelegate()
                };

                EmailLabel       = new SparkleLabel("Email:", NSTextAlignment.Right);
                EmailLabel.Frame = new CGRect(165, Frame.Height - 264, 160, 17);

                EmailTextField = new NSTextField()
                {
                    Frame    = new CGRect(330, Frame.Height - 268, 196, 22),
                    Delegate = new SparkleTextFieldDelegate()
                };

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };

                ContinueButton = new NSButton()
                {
                    Title   = "Continue",
                    Enabled = false
                };


                (FullNameTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    Controller.CheckSetupPage(FullNameTextField.StringValue, EmailTextField.StringValue);
                };

                (EmailTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    Controller.CheckSetupPage(FullNameTextField.StringValue, EmailTextField.StringValue);
                };

                ContinueButton.Activated += delegate {
                    string full_name = FullNameTextField.StringValue.Trim();
                    string email     = EmailTextField.StringValue.Trim();

                    Controller.SetupPageCompleted(full_name, email);
                };

                CancelButton.Activated += delegate { Controller.SetupPageCancelled(); };

                Controller.UpdateSetupContinueButtonEvent += delegate(bool button_enabled) {
                    SparkleShare.Controller.Invoke(() => {
                        ContinueButton.Enabled = button_enabled;
                    });
                };


                ContentView.AddSubview(FullNameLabel);
                ContentView.AddSubview(FullNameTextField);
                ContentView.AddSubview(EmailLabel);
                ContentView.AddSubview(EmailTextField);

                Buttons.Add(ContinueButton);
                Buttons.Add(CancelButton);

                Controller.CheckSetupPage(FullNameTextField.StringValue, EmailTextField.StringValue);

                if (FullNameTextField.StringValue.Equals(""))
                {
                    MakeFirstResponder((NSResponder)FullNameTextField);
                }
                else
                {
                    MakeFirstResponder((NSResponder)EmailTextField);
                }
            }

            if (type == PageType.Invite)
            {
                Header      = "You’ve received an invite!";
                Description = "Do you want to add this project to SparkleShare?";

                AddressLabel       = new SparkleLabel("Address:", NSTextAlignment.Right);
                AddressLabel.Frame = new CGRect(165, Frame.Height - 238, 160, 17);
                AddressLabel.Font  = NSFont.BoldSystemFontOfSize(12);

                AddressTextField = new SparkleLabel(Controller.PendingInvite.Address, NSTextAlignment.Left)
                {
                    Frame = new CGRect(330, Frame.Height - 240, 260, 17)
                };

                PathLabel       = new SparkleLabel("Remote Path:", NSTextAlignment.Right);
                PathLabel.Frame = new CGRect(165, Frame.Height - 262, 160, 17);
                PathLabel.Font  = NSFont.BoldSystemFontOfSize(12);

                PathTextField = new SparkleLabel(Controller.PendingInvite.RemotePath, NSTextAlignment.Left)
                {
                    Frame = new CGRect(330, Frame.Height - 264, 260, 17)
                };

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };
                AddButton = new NSButton()
                {
                    Title = "Add"
                };


                CancelButton.Activated += delegate { Controller.PageCancelled(); };
                AddButton.Activated    += delegate { Controller.InvitePageCompleted(); };


                ContentView.AddSubview(AddressLabel);
                ContentView.AddSubview(PathLabel);
                ContentView.AddSubview(AddressTextField);
                ContentView.AddSubview(PathTextField);

                Buttons.Add(AddButton);
                Buttons.Add(CancelButton);
            }

            if (type == PageType.Add)
            {
                Header      = "Where’s your project hosted?";
                Description = "";

                AddressLabel = new SparkleLabel("Address:", NSTextAlignment.Left)
                {
                    Frame = new CGRect(190, Frame.Height - 310, 160, 17),
                    Font  = NSFont.BoldSystemFontOfSize(12)
                };

                AddressTextField = new NSTextField()
                {
                    Frame       = new CGRect(190, Frame.Height - 336, 196, 22),
                    Enabled     = (Controller.SelectedPreset.Address == null),
                    Delegate    = new SparkleTextFieldDelegate(),
                    StringValue = "" + Controller.PreviousAddress
                };

                AddressTextField.Cell.LineBreakMode = NSLineBreakMode.TruncatingTail;

                PathLabel = new SparkleLabel("Remote Path:", NSTextAlignment.Left)
                {
                    Frame = new CGRect(190 + 196 + 16, Frame.Height - 310, 160, 17),
                    Font  = NSFont.BoldSystemFontOfSize(12)
                };

                PathTextField = new NSTextField()
                {
                    Frame       = new CGRect(190 + 196 + 16, Frame.Height - 336, 196, 22),
                    Enabled     = (Controller.SelectedPreset.Path == null),
                    Delegate    = new SparkleTextFieldDelegate(),
                    StringValue = "" + Controller.PreviousPath
                };

                PathTextField.Cell.LineBreakMode = NSLineBreakMode.TruncatingTail;

                PathHelpLabel = new SparkleLabel(Controller.SelectedPreset.PathExample, NSTextAlignment.Left)
                {
                    TextColor = NSColor.DisabledControlText,
                    Frame     = new CGRect(190 + 196 + 16, Frame.Height - 358, 204, 19)
                };

                AddressHelpLabel = new SparkleLabel(Controller.SelectedPreset.AddressExample, NSTextAlignment.Left)
                {
                    TextColor = NSColor.DisabledControlText,
                    Frame     = new CGRect(190, Frame.Height - 358, 204, 19)
                };

                if (TableView == null || TableView.RowCount != Controller.Presets.Count)
                {
                    TableView = new NSTableView()
                    {
                        Frame            = new CGRect(0, 0, 0, 0),
                        RowHeight        = 38,
                        IntercellSpacing = new CGSize(8, 12),
                        HeaderView       = null,
                        Delegate         = new SparkleTableViewDelegate()
                    };

                    ScrollView = new NSScrollView()
                    {
                        Frame               = new CGRect(190, Frame.Height - 280, 408, 185),
                        DocumentView        = TableView,
                        HasVerticalScroller = true,
                        BorderType          = NSBorderType.BezelBorder
                    };

                    IconColumn = new NSTableColumn()
                    {
                        Width         = 36,
                        HeaderToolTip = "Icon",
                        DataCell      = new NSImageCell()
                        {
                            ImageAlignment = NSImageAlignment.Right
                        }
                    };

                    DescriptionColumn = new NSTableColumn()
                    {
                        Width         = 350,
                        HeaderToolTip = "Description",
                        Editable      = false
                    };

                    TableView.AddColumn(IconColumn);
                    TableView.AddColumn(DescriptionColumn);

                    // Hi-res display support was added after Snow Leopard
                    if (Environment.OSVersion.Version.Major < 11)
                    {
                        DataSource = new SparkleDataSource(1, Controller.Presets);
                    }
                    else
                    {
                        DataSource = new SparkleDataSource((float)BackingScaleFactor, Controller.Presets);
                    }

                    TableView.DataSource = DataSource;
                    TableView.ReloadData();

                    (TableView.Delegate as SparkleTableViewDelegate).SelectionChanged += delegate {
                        Controller.SelectedPresetChanged((int)TableView.SelectedRow);
                        Controller.CheckAddPage(AddressTextField.StringValue, PathTextField.StringValue, (int)TableView.SelectedRow);
                    };
                }

                TableView.SelectRow(Controller.SelectedPresetIndex, byExtendingSelection: false);
                TableView.ScrollRowToVisible(Controller.SelectedPresetIndex);
                MakeFirstResponder((NSResponder)TableView);

                HistoryCheckButton = new NSButton()
                {
                    Frame = new CGRect(190, Frame.Height - 400, 300, 18),
                    Title = "Fetch prior revisions"
                };

                if (Controller.FetchPriorHistory)
                {
                    HistoryCheckButton.State = NSCellStateValue.On;
                }

                HistoryCheckButton.SetButtonType(NSButtonType.Switch);

                AddButton = new NSButton()
                {
                    Title   = "Add",
                    Enabled = false
                };

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };


                Controller.ChangeAddressFieldEvent += delegate(string text, string example_text, FieldState state) {
                    SparkleShare.Controller.Invoke(() => {
                        AddressTextField.StringValue = text;
                        AddressTextField.Enabled     = (state == FieldState.Enabled);
                        AddressHelpLabel.StringValue = example_text;
                    });
                };

                Controller.ChangePathFieldEvent += delegate(string text, string example_text, FieldState state) {
                    SparkleShare.Controller.Invoke(() => {
                        PathTextField.StringValue = text;
                        PathTextField.Enabled     = (state == FieldState.Enabled);
                        PathHelpLabel.StringValue = example_text;
                    });
                };


                (AddressTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    Controller.CheckAddPage(AddressTextField.StringValue, PathTextField.StringValue, (int)TableView.SelectedRow);
                };

                (PathTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    Controller.CheckAddPage(AddressTextField.StringValue, PathTextField.StringValue, (int)TableView.SelectedRow);
                };


                HistoryCheckButton.Activated += delegate {
                    Controller.HistoryItemChanged(HistoryCheckButton.State == NSCellStateValue.On);
                };

                AddButton.Activated += delegate {
                    Controller.AddPageCompleted(AddressTextField.StringValue, PathTextField.StringValue);
                };

                CancelButton.Activated += delegate { Controller.PageCancelled(); };

                Controller.UpdateAddProjectButtonEvent += delegate(bool button_enabled) {
                    SparkleShare.Controller.Invoke(() => {
                        AddButton.Enabled = button_enabled;
                    });
                };

                ContentView.AddSubview(ScrollView);
                ContentView.AddSubview(AddressLabel);
                ContentView.AddSubview(AddressTextField);
                ContentView.AddSubview(AddressHelpLabel);
                ContentView.AddSubview(PathLabel);
                ContentView.AddSubview(PathTextField);
                ContentView.AddSubview(PathHelpLabel);
                ContentView.AddSubview(HistoryCheckButton);

                Buttons.Add(AddButton);
                Buttons.Add(CancelButton);

                Controller.CheckAddPage(AddressTextField.StringValue, PathTextField.StringValue, (int)TableView.SelectedRow);
            }

            if (type == PageType.Syncing)
            {
                Header      = "Adding project ‘" + Controller.SyncingFolder + "’…";
                Description = "This may take a while for large projects.\nIsn’t it coffee-o’clock?";

                ProgressIndicator = new NSProgressIndicator()
                {
                    Frame         = new CGRect(190, Frame.Height - 200, 640 - 150 - 80, 20),
                    Style         = NSProgressIndicatorStyle.Bar,
                    MinValue      = 0.0,
                    MaxValue      = 100.0,
                    Indeterminate = false,
                    DoubleValue   = Controller.ProgressBarPercentage
                };

                ProgressIndicator.StartAnimation(this);

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };

                FinishButton = new NSButton()
                {
                    Title   = "Finish",
                    Enabled = false
                };

                ProgressLabel       = new SparkleLabel("Preparing to fetch files…", NSTextAlignment.Right);
                ProgressLabel.Frame = new CGRect(Frame.Width - 40 - 250, 185, 250, 25);


                Controller.UpdateProgressBarEvent += delegate(double percentage, string speed) {
                    SparkleShare.Controller.Invoke(() => {
                        ProgressIndicator.DoubleValue = percentage;
                        ProgressLabel.StringValue     = speed;
                    });
                };


                CancelButton.Activated += delegate { Controller.SyncingCancelled(); };


                ContentView.AddSubview(ProgressLabel);
                ContentView.AddSubview(ProgressIndicator);

                Buttons.Add(FinishButton);
                Buttons.Add(CancelButton);
            }

            if (type == PageType.Error)
            {
                Header      = "Oops! Something went wrong…";
                Description = "Please check the following:";

                // Displaying marked up text with Cocoa is
                // a pain, so we just use a webview instead
                WebView web_view = new WebView();
                web_view.Frame = new CGRect(190, Frame.Height - 525, 375, 400);

                string html = "<style>" +
                              "* {" +
                              "  font-family: -apple-system, '" + UserInterface.FontName + "';" +
                              "  font-size: 12px; cursor: default;" +
                              "}" +
                              "body {" +
                              "  -webkit-user-select: none;" +
                              "  margin: 0;" +
                              "  padding: 3px;" +
                              "}" +
                              "li {" +
                              "  margin-bottom: 16px;" +
                              "  margin-left: 0;" +
                              "  padding-left: 0;" +
                              "  line-height: 20px;" +
                              "  word-wrap: break-word;" +
                              "}" +
                              "ul {" +
                              "  padding-left: 24px;" +
                              "}" +
                              "</style>" +
                              "<ul>" +
                              "  <li><b>" + Controller.PreviousUrl + "</b> is the address we’ve compiled. Does this look alright?</li>" +
                              "  <li>Is this computer’s Client ID known by the host?</li>" +
                              "</ul>";

                if (warnings.Length > 0)
                {
                    string warnings_markup = "";

                    foreach (string warning in warnings)
                    {
                        warnings_markup += "<br><b>" + warning + "</b>";
                    }

                    html = html.Replace("</ul>", "<li>Here’s the raw error message: " + warnings_markup + "</li></ul>");
                }

                web_view.MainFrame.LoadHtmlString(html, new NSUrl(""));
                web_view.DrawsBackground = false;

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };
                TryAgainButton = new NSButton()
                {
                    Title = "Retry"
                };


                CancelButton.Activated   += delegate { Controller.PageCancelled(); };
                TryAgainButton.Activated += delegate { Controller.ErrorPageCompleted(); };


                ContentView.AddSubview(web_view);

                Buttons.Add(TryAgainButton);
                Buttons.Add(CancelButton);
            }

            if (type == PageType.StorageSetup)
            {
                Header      = string.Format("Storage type for ‘{0}’", Controller.SyncingFolder);
                Description = "What type of storage would you like to use?";


                storage_type_descriptions = new List <NSTextField> ();

                ButtonCellProto = new NSButtonCell();
                ButtonCellProto.SetButtonType(NSButtonType.Radio);
                ButtonCellProto.Font = NSFont.BoldSystemFontOfSize(12);

                Matrix = new NSMatrix(new CGRect(202, Frame.Height - 256 - 128, 256, 256), NSMatrixMode.Radio,
                                      ButtonCellProto, SparkleShare.Controller.FetcherAvailableStorageTypes.Count, 1);

                Matrix.CellSize         = new CGSize(256, 36);
                Matrix.IntercellSpacing = new CGSize(32, 32);

                int i = 0;
                foreach (StorageTypeInfo storage_type in SparkleShare.Controller.FetcherAvailableStorageTypes)
                {
                    Matrix.Cells [i].Title = " " + storage_type.Name;

                    NSTextField storage_type_description = new SparkleLabel(storage_type.Description, NSTextAlignment.Left)
                    {
                        TextColor = NSColor.DisabledControlText,
                        Frame     = new CGRect(223, Frame.Height - 190 - (68 * i), 256, 32)
                    };

                    storage_type_descriptions.Add(storage_type_description);
                    ContentView.AddSubview(storage_type_description);

                    i++;
                }

                ContentView.AddSubview(Matrix);


                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };
                ContinueButton = new NSButton()
                {
                    Title = "Continue"
                };

                ContinueButton.Activated += delegate {
                    StorageTypeInfo selected_storage_type = SparkleShare.Controller.FetcherAvailableStorageTypes [(int)Matrix.SelectedRow];
                    Controller.StoragePageCompleted(selected_storage_type.Type);
                };

                CancelButton.Activated += delegate { Controller.SyncingCancelled(); };

                Buttons.Add(ContinueButton);
                Buttons.Add(CancelButton);


                NSApplication.SharedApplication.RequestUserAttention(NSRequestUserAttentionType.CriticalRequest);
            }

            if (type == PageType.CryptoSetup || type == PageType.CryptoPassword)
            {
                if (type == PageType.CryptoSetup)
                {
                    Header      = "Set up file encryption";
                    Description = "Please a provide a strong password that you don’t use elsewhere.";
                }
                else
                {
                    Header      = "This project contains encrypted files";
                    Description = "Please enter the password to see their contents.";
                }

                int extra_pos_y = 0;

                if (type == PageType.CryptoPassword)
                {
                    extra_pos_y = 20;
                }

                PasswordLabel = new SparkleLabel("Password:"******"Show password",
                    State = NSCellStateValue.Off
                };

                ShowPasswordCheckButton.SetButtonType(NSButtonType.Switch);

                WarningImage      = NSImage.ImageNamed("NSInfo");
                WarningImage.Size = new CGSize(24, 24);

                WarningImageView = new NSImageView()
                {
                    Image = WarningImage,
                    Frame = new CGRect(200, Frame.Height - 320, 24, 24)
                };

                WarningTextField = new SparkleLabel("This password can’t be changed later, and your files can’t be recovered if it’s forgotten.", NSTextAlignment.Left)
                {
                    Frame = new CGRect(235, Frame.Height - 390, 325, 100),
                };

                CancelButton = new NSButton()
                {
                    Title = "Cancel"
                };

                ContinueButton = new NSButton()
                {
                    Title   = "Continue",
                    Enabled = false
                };


                Controller.UpdateCryptoPasswordContinueButtonEvent += delegate(bool button_enabled) {
                    SparkleShare.Controller.Invoke(() => { ContinueButton.Enabled = button_enabled; });
                };

                Controller.UpdateCryptoSetupContinueButtonEvent += delegate(bool button_enabled) {
                    SparkleShare.Controller.Invoke(() => { ContinueButton.Enabled = button_enabled; });
                };

                ShowPasswordCheckButton.Activated += delegate {
                    if (PasswordTextField.Superview == ContentView)
                    {
                        PasswordTextField.RemoveFromSuperview();
                        ContentView.AddSubview(VisiblePasswordTextField);
                    }
                    else
                    {
                        VisiblePasswordTextField.RemoveFromSuperview();
                        ContentView.AddSubview(PasswordTextField);
                    }
                };

                (PasswordTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    VisiblePasswordTextField.StringValue = PasswordTextField.StringValue;

                    if (type == PageType.CryptoSetup)
                    {
                        Controller.CheckCryptoSetupPage(PasswordTextField.StringValue);
                    }
                    else
                    {
                        Controller.CheckCryptoPasswordPage(PasswordTextField.StringValue);
                    }
                };

                (VisiblePasswordTextField.Delegate as SparkleTextFieldDelegate).StringValueChanged += delegate {
                    PasswordTextField.StringValue = VisiblePasswordTextField.StringValue;

                    if (type == PageType.CryptoSetup)
                    {
                        Controller.CheckCryptoSetupPage(PasswordTextField.StringValue);
                    }
                    else
                    {
                        Controller.CheckCryptoPasswordPage(PasswordTextField.StringValue);
                    }
                };

                ContinueButton.Activated += delegate {
                    if (type == PageType.CryptoSetup)
                    {
                        Controller.CryptoSetupPageCompleted(PasswordTextField.StringValue);
                    }
                    else
                    {
                        Controller.CryptoPasswordPageCompleted(PasswordTextField.StringValue);
                    }
                };

                CancelButton.Activated += delegate { Controller.CryptoPageCancelled(); };


                ContentView.AddSubview(PasswordLabel);
                ContentView.AddSubview(PasswordTextField);
                ContentView.AddSubview(ShowPasswordCheckButton);

                if (type == PageType.CryptoSetup)
                {
                    ContentView.AddSubview(WarningImageView);
                    ContentView.AddSubview(WarningTextField);
                }

                Buttons.Add(ContinueButton);
                Buttons.Add(CancelButton);

                MakeFirstResponder((NSResponder)PasswordTextField);
                NSApplication.SharedApplication.RequestUserAttention(NSRequestUserAttentionType.CriticalRequest);
            }


            if (type == PageType.Finished)
            {
                Header      = "Your shared project is ready!";
                Description = "You can find the files in your SparkleShare folder.";

                if (warnings.Length > 0)
                {
                    WarningImage      = NSImage.ImageNamed("NSInfo");
                    WarningImage.Size = new CGSize(24, 24);

                    WarningImageView = new NSImageView()
                    {
                        Image = WarningImage,
                        Frame = new CGRect(200, Frame.Height - 175, 24, 24)
                    };

                    WarningTextField       = new SparkleLabel(warnings [0], NSTextAlignment.Left);
                    WarningTextField.Frame = new CGRect(235, Frame.Height - 245, 325, 100);

                    ContentView.AddSubview(WarningImageView);
                    ContentView.AddSubview(WarningTextField);
                }

                ShowFilesButton = new NSButton()
                {
                    Title = "Show Files"
                };
                FinishButton = new NSButton()
                {
                    Title = "Finish"
                };


                ShowFilesButton.Activated += delegate { Controller.ShowFilesClicked(); };
                FinishButton.Activated    += delegate { Controller.FinishPageCompleted(); };


                Buttons.Add(FinishButton);
                Buttons.Add(ShowFilesButton);

                NSApplication.SharedApplication.RequestUserAttention(NSRequestUserAttentionType.CriticalRequest);
            }
        }
示例#2
0
        public Setup()
        {
            Controller.ShowWindowEvent += delegate {
                Dispatcher.BeginInvoke((Action) delegate {
                    Show();
                    Activate();
                    BringIntoView();
                });
            };

            Controller.HideWindowEvent += delegate {
                Dispatcher.BeginInvoke((Action) delegate {
                    Hide();
                });
            };

            Controller.ChangePageEvent += delegate(PageType type, string [] warnings) {
                Dispatcher.BeginInvoke((Action) delegate {
                    Reset();

                    // TODO: Remove switch statement for ifs
                    switch (type)
                    {
                    case PageType.Setup: {
                        Header      = "Welcome to SparkleShare!";
                        Description = "First off, what’s your name and email?\n(Visible only to team members)";

                        TextBlock name_label = new TextBlock()
                        {
                            Text          = "Full Name:",
                            Width         = 150,
                            TextAlignment = TextAlignment.Right,
                            FontWeight    = FontWeights.Bold
                        };

                        string name = System.Security.Principal.WindowsIdentity.GetCurrent().Name;
                        name        = name.Split("\\".ToCharArray()) [1];

                        TextBox name_box = new TextBox()
                        {
                            Text  = name,
                            Width = 175
                        };

                        TextBlock email_label = new TextBlock()
                        {
                            Text          = "Email:",
                            Width         = 150,
                            TextAlignment = TextAlignment.Right,
                            FontWeight    = FontWeights.Bold
                        };

                        TextBox email_box = new TextBox()
                        {
                            Width = 175
                        };


                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        Button continue_button = new Button()
                        {
                            Content   = "Continue",
                            IsEnabled = false
                        };


                        ContentCanvas.Children.Add(name_label);
                        Canvas.SetLeft(name_label, 180);
                        Canvas.SetTop(name_label, 200 + 3);

                        ContentCanvas.Children.Add(name_box);
                        Canvas.SetLeft(name_box, 340);
                        Canvas.SetTop(name_box, 200);

                        ContentCanvas.Children.Add(email_label);
                        Canvas.SetLeft(email_label, 180);
                        Canvas.SetTop(email_label, 230 + 3);

                        ContentCanvas.Children.Add(email_box);
                        Canvas.SetLeft(email_box, 340);
                        Canvas.SetTop(email_box, 230);

                        Buttons.Add(cancel_button);
                        Buttons.Add(continue_button);

                        Controller.UpdateSetupContinueButtonEvent += delegate(bool enabled) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    continue_button.IsEnabled = enabled;
                                });
                        };

                        name_box.TextChanged += delegate {
                            Controller.CheckSetupPage(name_box.Text, email_box.Text);
                        };

                        email_box.TextChanged += delegate {
                            Controller.CheckSetupPage(name_box.Text, email_box.Text);
                        };

                        cancel_button.Click += delegate {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    SparkleShare.UI.StatusIcon.Dispose();
                                    Controller.SetupPageCancelled();
                                });
                        };

                        continue_button.Click += delegate {
                            Controller.SetupPageCompleted(name_box.Text, email_box.Text);
                        };

                        Controller.CheckSetupPage(name_box.Text, email_box.Text);

                        if (name_box.Text.Equals(""))
                        {
                            name_box.Focus();
                        }
                        else
                        {
                            email_box.Focus();
                        }

                        break;
                    }

                    case PageType.Invite: {
                        Header      = "You’ve received an invite!";
                        Description = "Do you want to add this project to SparkleShare?";


                        TextBlock address_label = new TextBlock()
                        {
                            Text          = "Address:",
                            Width         = 150,
                            TextAlignment = TextAlignment.Right
                        };

                        TextBlock address_value = new TextBlock()
                        {
                            Text       = Controller.PendingInvite.Address,
                            Width      = 175,
                            FontWeight = FontWeights.Bold
                        };


                        TextBlock path_label = new TextBlock()
                        {
                            Text          = "Remote Path:",
                            Width         = 150,
                            TextAlignment = TextAlignment.Right
                        };

                        TextBlock path_value = new TextBlock()
                        {
                            Width      = 175,
                            Text       = Controller.PendingInvite.RemotePath,
                            FontWeight = FontWeights.Bold
                        };



                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        Button add_button = new Button()
                        {
                            Content = "Add"
                        };


                        ContentCanvas.Children.Add(address_label);
                        Canvas.SetLeft(address_label, 180);
                        Canvas.SetTop(address_label, 200);

                        ContentCanvas.Children.Add(address_value);
                        Canvas.SetLeft(address_value, 340);
                        Canvas.SetTop(address_value, 200);

                        ContentCanvas.Children.Add(path_label);
                        Canvas.SetLeft(path_label, 180);
                        Canvas.SetTop(path_label, 225);

                        ContentCanvas.Children.Add(path_value);
                        Canvas.SetLeft(path_value, 340);
                        Canvas.SetTop(path_value, 225);

                        Buttons.Add(add_button);
                        Buttons.Add(cancel_button);


                        cancel_button.Click += delegate {
                            Controller.PageCancelled();
                        };

                        add_button.Click += delegate {
                            Controller.InvitePageCompleted();
                        };

                        break;
                    }

                    case PageType.Add: {
                        Header = "Where’s your project hosted?";


                        ListView list_view = new ListView()
                        {
                            Width         = 419,
                            Height        = 195,
                            SelectionMode = SelectionMode.Single
                        };

                        GridView grid_view = new GridView()
                        {
                            AllowsColumnReorder = false
                        };

                        grid_view.Columns.Add(new GridViewColumn());

                        string xaml =
                            "<DataTemplate xmlns=\"http://schemas.microsoft.com/winfx/2006/xaml/presentation\"" +
                            "  xmlns:x=\"http://schemas.microsoft.com/winfx/2006/xaml\">" +
                            "  <Grid>" +
                            "    <StackPanel Orientation=\"Horizontal\">" +
                            "      <Image Margin=\"5,0,0,0\" Source=\"{Binding Image}\" Height=\"24\" Width=\"24\"/>" +
                            "      <StackPanel>" +
                            "        <TextBlock Padding=\"10,4,0,0\" FontWeight=\"Bold\" Text=\"{Binding Name}\">" +
                            "        </TextBlock>" +
                            "        <TextBlock Padding=\"10,0,0,4\" Opacity=\"0.5\" Text=\"{Binding Description}\">" +
                            "        </TextBlock>" +
                            "      </StackPanel>" +
                            "    </StackPanel>" +
                            "  </Grid>" +
                            "</DataTemplate>";

                        grid_view.Columns [0].CellTemplate = (DataTemplate)XamlReader.Parse(xaml);

                        Style header_style = new Style(typeof(GridViewColumnHeader));
                        header_style.Setters.Add(new Setter(GridViewColumnHeader.VisibilityProperty, Visibility.Collapsed));
                        grid_view.ColumnHeaderContainerStyle = header_style;

                        foreach (Preset plugin in Controller.Presets)
                        {
                            // FIXME: images are blurry
                            BitmapFrame image = BitmapFrame.Create(
                                new Uri(plugin.ImagePath)
                                );

                            list_view.Items.Add(
                                new {
                                    Name        = plugin.Name,
                                    Description = plugin.Description,
                                    Image       = image
                                }
                                );
                        }

                        list_view.View          = grid_view;
                        list_view.SelectedIndex = Controller.SelectedPresetIndex;

                        TextBlock address_label = new TextBlock()
                        {
                            Text       = "Address:",
                            FontWeight = FontWeights.Bold
                        };

                        TextBox address_box = new TextBox()
                        {
                            Width     = 200,
                            Text      = Controller.PreviousAddress,
                            IsEnabled = (Controller.SelectedPreset.Address == null)
                        };

                        TextBlock address_help_label = new TextBlock()
                        {
                            Text       = Controller.SelectedPreset.AddressExample,
                            FontSize   = 11,
                            Foreground = new SolidColorBrush(Color.FromRgb(128, 128, 128))
                        };

                        TextBlock path_label = new TextBlock()
                        {
                            Text       = "Remote Path:",
                            FontWeight = FontWeights.Bold,
                            Width      = 200
                        };

                        TextBox path_box = new TextBox()
                        {
                            Width     = 200,
                            Text      = Controller.PreviousPath,
                            IsEnabled = (Controller.SelectedPreset.Path == null)
                        };

                        TextBlock path_help_label = new TextBlock()
                        {
                            Text       = Controller.SelectedPreset.PathExample,
                            FontSize   = 11,
                            Width      = 200,
                            Foreground = new SolidColorBrush(Color.FromRgb(128, 128, 128))
                        };

                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        Button add_button = new Button()
                        {
                            Content = "Add"
                        };

                        CheckBox history_check_box = new CheckBox()
                        {
                            Content   = "Fetch prior revisions",
                            IsChecked = Controller.FetchPriorHistory
                        };

                        history_check_box.Click += delegate {
                            Controller.HistoryItemChanged(history_check_box.IsChecked.Value);
                        };

                        ContentCanvas.Children.Add(history_check_box);
                        Canvas.SetLeft(history_check_box, 185);
                        Canvas.SetBottom(history_check_box, 12);

                        ContentCanvas.Children.Add(list_view);
                        Canvas.SetTop(list_view, 70);
                        Canvas.SetLeft(list_view, 185);

                        ContentCanvas.Children.Add(address_label);
                        Canvas.SetTop(address_label, 285);
                        Canvas.SetLeft(address_label, 185);

                        ContentCanvas.Children.Add(address_box);
                        Canvas.SetTop(address_box, 305);
                        Canvas.SetLeft(address_box, 185);

                        ContentCanvas.Children.Add(address_help_label);
                        Canvas.SetTop(address_help_label, 330);
                        Canvas.SetLeft(address_help_label, 185);

                        ContentCanvas.Children.Add(path_label);
                        Canvas.SetTop(path_label, 285);
                        Canvas.SetRight(path_label, 30);

                        ContentCanvas.Children.Add(path_box);
                        Canvas.SetTop(path_box, 305);
                        Canvas.SetRight(path_box, 30);

                        ContentCanvas.Children.Add(path_help_label);
                        Canvas.SetTop(path_help_label, 330);
                        Canvas.SetRight(path_help_label, 30);

                        TaskbarItemInfo.ProgressValue = 0.0;
                        TaskbarItemInfo.ProgressState = TaskbarItemProgressState.None;

                        Buttons.Add(add_button);
                        Buttons.Add(cancel_button);

                        address_box.Focus();
                        address_box.Select(address_box.Text.Length, 0);


                        Controller.ChangeAddressFieldEvent += delegate(string text,
                                                                       string example_text, FieldState state) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    address_box.Text        = text;
                                    address_box.IsEnabled   = (state == FieldState.Enabled);
                                    address_help_label.Text = example_text;
                                });
                        };

                        Controller.ChangePathFieldEvent += delegate(string text,
                                                                    string example_text, FieldState state) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    path_box.Text        = text;
                                    path_box.IsEnabled   = (state == FieldState.Enabled);
                                    path_help_label.Text = example_text;
                                });
                        };

                        Controller.UpdateAddProjectButtonEvent += delegate(bool button_enabled) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    add_button.IsEnabled = button_enabled;
                                });
                        };

                        list_view.SelectionChanged += delegate {
                            Controller.SelectedPresetChanged(list_view.SelectedIndex);
                        };

                        list_view.KeyDown += delegate {
                            Controller.SelectedPresetChanged(list_view.SelectedIndex);
                        };

                        Controller.CheckAddPage(address_box.Text, path_box.Text, list_view.SelectedIndex);

                        address_box.TextChanged += delegate {
                            Controller.CheckAddPage(address_box.Text, path_box.Text, list_view.SelectedIndex);
                        };

                        path_box.TextChanged += delegate {
                            Controller.CheckAddPage(address_box.Text, path_box.Text, list_view.SelectedIndex);
                        };

                        cancel_button.Click += delegate {
                            Controller.PageCancelled();
                        };

                        add_button.Click += delegate {
                            Controller.AddPageCompleted(address_box.Text, path_box.Text);
                        };

                        break;
                    }


                    case PageType.Syncing: {
                        Header      = "Adding project ‘" + Controller.SyncingFolder + "’…";
                        Description = "This may take a while for large projects.\nIsn’t it coffee-o’clock?";

                        Button finish_button = new Button()
                        {
                            Content   = "Finish",
                            IsEnabled = false
                        };

                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        ProgressBar progress_bar = new ProgressBar()
                        {
                            Width  = 414,
                            Height = 15,
                            Value  = Controller.ProgressBarPercentage
                        };

                        TextBlock progress_label = new TextBlock()
                        {
                            Width         = 414,
                            Text          = "Preparing to fetch files…",
                            TextAlignment = TextAlignment.Right
                        };

                        ContentCanvas.Children.Add(progress_bar);
                        ContentCanvas.Children.Add(progress_label);

                        Canvas.SetLeft(progress_bar, 185);
                        Canvas.SetTop(progress_bar, 150);

                        Canvas.SetLeft(progress_label, 185);
                        Canvas.SetTop(progress_label, 175);

                        TaskbarItemInfo.ProgressState = TaskbarItemProgressState.Normal;

                        Buttons.Add(cancel_button);
                        Buttons.Add(finish_button);


                        Controller.UpdateProgressBarEvent += delegate(double percentage, string speed) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    progress_bar.Value            = percentage;
                                    TaskbarItemInfo.ProgressValue = percentage / 100;
                                    progress_label.Text           = speed;
                                });
                        };

                        cancel_button.Click += delegate {
                            Controller.SyncingCancelled();
                        };

                        break;
                    }


                    case PageType.Error: {
                        Header      = "Oops! Something went wrong…";
                        Description = "Please check the following:";

                        TextBlock help_block = new TextBlock()
                        {
                            TextWrapping = TextWrapping.Wrap,
                            Width        = 310
                        };

                        TextBlock bullets_block = new TextBlock()
                        {
                            Text = "•\n\n\n•"
                        };

                        help_block.Inlines.Add(new Bold(new Run(Controller.PreviousUrl)));
                        help_block.Inlines.Add(" is the address we’ve compiled. Does this look alright?\n\n");
                        help_block.Inlines.Add("Is this computer’s Client ID known by the host?");

                        if (warnings.Length > 0)
                        {
                            bullets_block.Text += "\n\n•";
                            help_block.Inlines.Add("\n\nHere’s the raw error message:");

                            foreach (string warning in warnings)
                            {
                                help_block.Inlines.Add("\n");
                                help_block.Inlines.Add(new Bold(new Run(warning)));
                            }
                        }

                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        Button try_again_button = new Button()
                        {
                            Content = "Try again…"
                        };


                        ContentCanvas.Children.Add(bullets_block);
                        Canvas.SetLeft(bullets_block, 195);
                        Canvas.SetTop(bullets_block, 100);

                        ContentCanvas.Children.Add(help_block);
                        Canvas.SetLeft(help_block, 210);
                        Canvas.SetTop(help_block, 100);

                        TaskbarItemInfo.ProgressValue = 1.0;
                        TaskbarItemInfo.ProgressState = TaskbarItemProgressState.Error;

                        Buttons.Add(try_again_button);
                        Buttons.Add(cancel_button);


                        cancel_button.Click += delegate {
                            Controller.PageCancelled();
                        };

                        try_again_button.Click += delegate {
                            Controller.ErrorPageCompleted();
                        };

                        break;
                    }

                    case PageType.CryptoSetup: {
                        // TODO: Merge crypto pages
                        Header      = "Set up file encryption";
                        Description = "Please a provide a strong password that you don’t use elsewhere.";

                        TextBlock password_label = new TextBlock()
                        {
                            Text       = "Password:"******"Show password",
                            IsChecked = false
                        };

                        TextBlock info_label = new TextBlock()
                        {
                            Text         = "This password can’t be changed later, and your files can’t be recovered if it’s forgotten.",
                            TextWrapping = TextWrapping.Wrap,
                            Width        = 315
                        };

                        Image warning_image = new Image()
                        {
                            Source = Imaging.CreateBitmapSourceFromHIcon(Drawing.SystemIcons.Information.Handle,
                                                                         Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions())
                        };

                        show_password_checkbox.Checked += delegate {
                            visible_password_box.Text       = password_box.Password;
                            visible_password_box.Visibility = Visibility.Visible;
                            password_box.Visibility         = Visibility.Hidden;
                        };

                        show_password_checkbox.Unchecked += delegate {
                            password_box.Password           = visible_password_box.Text;
                            password_box.Visibility         = Visibility.Visible;
                            visible_password_box.Visibility = Visibility.Hidden;
                        };

                        password_box.PasswordChanged += delegate {
                            Controller.CheckCryptoSetupPage(password_box.Password);
                        };

                        visible_password_box.TextChanged += delegate {
                            Controller.CheckCryptoSetupPage(visible_password_box.Text);
                        };

                        Button continue_button = new Button()
                        {
                            Content   = "Continue",
                            IsEnabled = false
                        };

                        continue_button.Click += delegate {
                            if (show_password_checkbox.IsChecked == true)
                            {
                                Controller.CryptoSetupPageCompleted(visible_password_box.Text);
                            }
                            else
                            {
                                Controller.CryptoSetupPageCompleted(password_box.Password);
                            }
                        };

                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        cancel_button.Click += delegate {
                            Controller.CryptoPageCancelled();
                        };

                        Controller.UpdateCryptoSetupContinueButtonEvent += delegate(bool button_enabled) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    continue_button.IsEnabled = button_enabled;
                                });
                        };

                        ContentCanvas.Children.Add(password_label);
                        Canvas.SetLeft(password_label, 270);
                        Canvas.SetTop(password_label, 180);

                        ContentCanvas.Children.Add(password_box);
                        Canvas.SetLeft(password_box, 335);
                        Canvas.SetTop(password_box, 180);

                        ContentCanvas.Children.Add(visible_password_box);
                        Canvas.SetLeft(visible_password_box, 335);
                        Canvas.SetTop(visible_password_box, 180);

                        ContentCanvas.Children.Add(show_password_checkbox);
                        Canvas.SetLeft(show_password_checkbox, 338);
                        Canvas.SetTop(show_password_checkbox, 208);

                        ContentCanvas.Children.Add(info_label);
                        Canvas.SetLeft(info_label, 240);
                        Canvas.SetTop(info_label, 300);

                        ContentCanvas.Children.Add(warning_image);
                        Canvas.SetLeft(warning_image, 193);
                        Canvas.SetTop(warning_image, 300);

                        Buttons.Add(continue_button);
                        Buttons.Add(cancel_button);

                        password_box.Focus();

                        break;
                    }

                    case PageType.CryptoPassword: {
                        Header      = "This project contains encrypted files";
                        Description = "Please enter the password to see their contents.";

                        TextBlock password_label = new TextBlock()
                        {
                            Text       = "Password:"******"Show password",
                            IsChecked = false
                        };

                        show_password_checkbox.Checked += delegate {
                            visible_password_box.Text       = password_box.Password;
                            visible_password_box.Visibility = Visibility.Visible;
                            password_box.Visibility         = Visibility.Hidden;
                        };

                        show_password_checkbox.Unchecked += delegate {
                            password_box.Password           = visible_password_box.Text;
                            password_box.Visibility         = Visibility.Visible;
                            visible_password_box.Visibility = Visibility.Hidden;
                        };

                        password_box.PasswordChanged += delegate {
                            Controller.CheckCryptoPasswordPage(password_box.Password);
                        };

                        visible_password_box.TextChanged += delegate {
                            Controller.CheckCryptoPasswordPage(visible_password_box.Text);
                        };

                        Button continue_button = new Button()
                        {
                            Content   = "Continue",
                            IsEnabled = false
                        };

                        continue_button.Click += delegate {
                            if (show_password_checkbox.IsChecked == true)
                            {
                                Controller.CryptoPasswordPageCompleted(visible_password_box.Text);
                            }
                            else
                            {
                                Controller.CryptoPasswordPageCompleted(password_box.Password);
                            }
                        };

                        Button cancel_button = new Button()
                        {
                            Content = "Cancel"
                        };

                        cancel_button.Click += delegate {
                            Controller.CryptoPageCancelled();
                        };

                        Controller.UpdateCryptoPasswordContinueButtonEvent += delegate(bool button_enabled) {
                            Dispatcher.BeginInvoke((Action) delegate {
                                    continue_button.IsEnabled = button_enabled;
                                });
                        };

                        ContentCanvas.Children.Add(password_label);
                        Canvas.SetLeft(password_label, 270);
                        Canvas.SetTop(password_label, 180);

                        ContentCanvas.Children.Add(password_box);
                        Canvas.SetLeft(password_box, 335);
                        Canvas.SetTop(password_box, 180);

                        ContentCanvas.Children.Add(visible_password_box);
                        Canvas.SetLeft(visible_password_box, 335);
                        Canvas.SetTop(visible_password_box, 180);

                        ContentCanvas.Children.Add(show_password_checkbox);
                        Canvas.SetLeft(show_password_checkbox, 338);
                        Canvas.SetTop(show_password_checkbox, 208);

                        Buttons.Add(continue_button);
                        Buttons.Add(cancel_button);

                        password_box.Focus();

                        break;
                    }

                    case PageType.Finished: {
                        Header      = "Your shared project is ready!";
                        Description = "You can find the files in your SparkleShare folder.";


                        Button finish_button = new Button()
                        {
                            Content = "Finish"
                        };

                        Button show_files_button = new Button()
                        {
                            Content = "Show files"
                        };

                        if (warnings.Length > 0)
                        {
                            Image warning_image = new Image()
                            {
                                Source = Imaging.CreateBitmapSourceFromHIcon(Drawing.SystemIcons.Information.Handle,
                                                                             Int32Rect.Empty, BitmapSizeOptions.FromEmptyOptions())
                            };

                            TextBlock warning_block = new TextBlock()
                            {
                                Text         = warnings [0],
                                Width        = 310,
                                TextWrapping = TextWrapping.Wrap
                            };

                            ContentCanvas.Children.Add(warning_image);
                            Canvas.SetLeft(warning_image, 193);
                            Canvas.SetTop(warning_image, 100);

                            ContentCanvas.Children.Add(warning_block);
                            Canvas.SetLeft(warning_block, 240);
                            Canvas.SetTop(warning_block, 100);
                        }

                        TaskbarItemInfo.ProgressValue = 0.0;
                        TaskbarItemInfo.ProgressState = TaskbarItemProgressState.None;

                        Buttons.Add(show_files_button);
                        Buttons.Add(finish_button);


                        finish_button.Click += delegate {
                            Controller.FinishPageCompleted();
                        };

                        show_files_button.Click += delegate {
                            Controller.ShowFilesClicked();
                        };

                        break;
                    }
                    }

                    ShowAll();
                });
            };
        }