private async void Page_OnLoaded(object sender, RoutedEventArgs e)
        {
            // load name of the user
            Title = "Chatting with " + (await SharedStuff.Database.Table <DatabaseHelper.Users>().Where(row => row.Username == Username)
                                        .FirstAsync()).Name;
            // load fist 100 messages
            var messages = await SharedStuff.Database.QueryAsync <DatabaseHelper.Messages>
                               (DatabaseHelper.LastRowsQuery(0, 100), Username);

            if (messages.Count < 100) // prevent additional load on db
            {
                _reachedEnd = true;
            }
            foreach (var message in messages)
            {
                if (message.Type == 0)
                {
                    MessagesList.Insert(0, new ChatMessagesNotify
                    {
                        MyMessage = message.MyMessage,
                        Message   = message.Payload,
                        FullDate  = message.Date,
                        Type      = message.Type,
                        Sent      = 0,
                        Progress  = 101
                    });
                }
                else if (message.Type == 1)
                {
                    var fileInfo = await SharedStuff.Database.Table <DatabaseHelper.Files>()
                                   .FirstAsync(file => file.Token == message.Payload);

                    var downloadButtonIcon = PackIconKind.Download;
                    if (!string.IsNullOrEmpty(fileInfo.Location))
                    {
                        downloadButtonIcon = File.Exists(fileInfo.Location) ? PackIconKind.File : PackIconKind.DownloadOff;
                    }
                    MessagesList.Insert(0, new ChatMessagesNotify
                    {
                        MyMessage          = message.MyMessage,
                        Message            = fileInfo.Name,
                        FullDate           = message.Date,
                        Type               = message.Type,
                        Sent               = 0,
                        Token              = message.Payload,
                        DownloadButtonIcon = downloadButtonIcon,
                        Progress           = 101
                    });
                }
            }

            MainScrollViewer.ScrollToBottom(); // Go to the last of scroll view that is actually the first of it
            MainScrollViewer.UpdateLayout();
            _stopLoading = false;
        }
    private void LogViewer_Loaded(object sender, RoutedEventArgs e)
    {
        MainScrollViewer.ScrollToBottom();

        // TODO: Unsubscribe when closing log viewer
        // Scroll to bottom when a new log is added
        ViewModel.LogItems.CollectionChanged += async(_, ee) =>
        {
            if (ee.Action == NotifyCollectionChangedAction.Add)
            {
                await Dispatcher.InvokeAsync(() => MainScrollViewer.ScrollToBottom());
            }
        };
    }
 /// <summary>
 /// Add message to UI
 /// </summary>
 /// <param name="message">The message to add</param>
 public void AddMessage(ChatMessagesNotify message)
 {
     _lastMessageIndex++; //TODO: Will this make some problems when the message is not sent?
     Application.Current.Dispatcher.Invoke(() => MessagesList.Add(message));
     if (!message.MyMessage)
     {
         _stopLoading = true;
         // scroll to bottom if needed
         MainScrollViewer.UpdateLayout();
         if (MainScrollViewer.ScrollableHeight - MainScrollViewer.VerticalOffset < 30)
         {
             MainScrollViewer.ScrollToBottom();
             MainScrollViewer.UpdateLayout();
         }
         _stopLoading = false;
     }
 }
        private async void MessageTextBox_OnKeyDown(object sender, KeyEventArgs e)
        {
            if ((Keyboard.Modifiers & ModifierKeys.Control) == ModifierKeys.Control)
            {
                if (Keyboard.IsKeyDown(Key.Enter))
                {
                    string message = MessageTextBox.Text.Trim().TrimEnd(Environment.NewLine.ToCharArray());
                    // do not send the message if it's empty
                    if (string.IsNullOrWhiteSpace(message))
                    {
                        return;
                    }
                    if (SharedStuff.Websocket.IsAlive)
                    {
                        string id = Guid.NewGuid().ToString();
                        await Task.Run(() => SendMessage(message, id)); // send message over network

                        var msgUi = new ChatMessagesNotify
                        {
                            MyMessage = true,
                            Message   = message,
                            FullDate  = DateTime.Now,
                            Type      = 0,
                            Sent      = 1
                        };
                        AddMessage(msgUi);                          // add it to ui
                        SharedStuff.PendingMessages.Add(id, msgUi); // add message to pending messages
                    }
                    else
                    {
                        var msgUi = new ChatMessagesNotify
                        {
                            MyMessage = true,
                            Message   = message,
                            FullDate  = DateTime.Now,
                            Type      = 0,
                            Sent      = 2
                        };
                        AddMessage(msgUi);
                    }
                    // finalizing UI
                    MessageTextBox.Text = "";
                    MessageTextBox.Focus();
                    _stopLoading = true;
                    MainScrollViewer.ScrollToBottom();
                    MainScrollViewer.UpdateLayout();
                    _stopLoading        = false;
                    SendButtonIcon.Kind = PackIconKind.Attachment;
                    SendButton.ToolTip  = "Send File";
                }
            }
            if (string.IsNullOrWhiteSpace(MessageTextBox.Text)) // show attachment icon
            {
                SendButtonIcon.Kind = PackIconKind.Attachment;
                SendButton.ToolTip  = "Send File";
            }
            else
            {
                SendButtonIcon.Kind = PackIconKind.Send;
                SendButton.ToolTip  = "Send Message";
            }
        }
        private async void SendBtnClicked(object sender, RoutedEventArgs e)
        {
            string message = MessageTextBox.Text.Trim();

            // initialize file send
            if (string.IsNullOrWhiteSpace(message))
            {
                OpenFileDialog ofd = new OpenFileDialog {
                    Title = "Send File"
                };
                bool?result = ofd.ShowDialog();
                if (result.HasValue && result.Value)
                {
                    string key = (await SharedStuff.Database.Table <DatabaseHelper.Users>().Where(user => user.Username == Username)
                                  .FirstAsync()).Key;
                    // at first request a token
                    string id    = Guid.NewGuid().ToString();
                    var    msgUi = new ChatMessagesNotify
                    {
                        MyMessage = true,
                        Message   = Path.GetFileName(ofd.FileName),
                        FullDate  = DateTime.Now,
                        Type      = 1,
                        Sent      = 1,
                        FilePath  = ofd.FileName,
                        With      = Username
                    };
                    SharedStuff.PendingMessages.Add(id, msgUi);
                    // create json
                    string json = JsonConvert.SerializeObject(new JsonTypes.SendMessage
                    {
                        Type    = 2,
                        Id      = id,
                        Payload = new JsonTypes.SendMessagePayload
                        {
                            To      = Username,
                            Message = Path.GetFileName(ofd.FileName)
                        }
                    });
                    SharedStuff.Websocket.SendAsync(json, null);
                    AddMessage(msgUi);
                }
            }
            else
            {
                if (SharedStuff.Websocket.IsAlive)
                {
                    string id = Guid.NewGuid().ToString();
                    await Task.Run(() => SendMessage(message, id));

                    var msgUi = new ChatMessagesNotify
                    {
                        MyMessage = true,
                        Message   = message,
                        FullDate  = DateTime.Now,
                        Type      = 0,
                        Sent      = 1
                    };
                    AddMessage(msgUi);                          // add it to ui
                    SharedStuff.PendingMessages.Add(id, msgUi); // add message to pending messages
                }
                else
                {
                    var msgUi = new ChatMessagesNotify
                    {
                        MyMessage = true,
                        Message   = message,
                        FullDate  = DateTime.Now,
                        Type      = 0,
                        Sent      = 2
                    };
                    AddMessage(msgUi);
                }

                // finalizing UI
                MessageTextBox.Text = "";
                MessageTextBox.Focus();
                _stopLoading = true;
                MainScrollViewer.ScrollToBottom();
                MainScrollViewer.UpdateLayout();
                _stopLoading        = false;
                SendButtonIcon.Kind = PackIconKind.Attachment;
                SendButton.ToolTip  = "Send File";
            }
        }