Пример #1
0
        /// <summary>
        /// 用户空间下分页留言列表
        /// </summary>
        /// <param name="ownerUserId">用户空间编号</param>
        /// <param name="size">子评论显示条数</param>
        /// <param name="index">子评论显示页数</param>
        /// <returns></returns>
        public PageResult GetSpaceComments(int ownerUserId, int size, int index)
        {
            var pageResult = new PageResult();
            IList <CommentsView> commentvideos = new List <CommentsView>();
            var parentComments = GetParentCommentUsers(ownerUserId);

            if (parentComments != null && parentComments.Any())
            {
                #region 根级评论分页
                int pageSize   = this.PageSize <= 0 ? 8 : this.PageSize;
                int totalCount = parentComments.Any() ? parentComments.Count() : 0;
                int totalIndex = totalCount % pageSize == 0 ? (totalCount / pageSize) : (totalCount / pageSize + 1);
                int pageIndex  = this.PageIndex <= 0 ? 1 : (this.PageIndex >= totalIndex ? totalIndex : this.PageIndex);
                pageResult.PageIndex  = pageIndex;
                pageResult.PageSize   = pageSize;
                pageResult.PageIndex  = pageIndex;
                pageResult.TotalCount = totalCount;
                //指定视频最上级的评论分页视图
                var pageParentComments = parentComments.Skip((pageIndex - 1) * pageSize).Take(pageSize);
                #endregion

                foreach (var parentComment in pageParentComments)
                {
                    var childCommentVideos = GetSpaceComments(ownerUserId, parentComment.Id, size, index);
                    var commentvideo       = new CommentsView()
                    {
                        ParentComment = parentComment,
                        ChildComments = childCommentVideos
                    };
                    commentvideos.Add(commentvideo);
                }
            }
            pageResult.Data = commentvideos;
            return(pageResult);
        }
Пример #2
0
        public async Task <IActionResult> PostComment(int lotId, string message)
        {
            var lot = await _lotRepository.Find(lotId);

            if (lot != null && !string.IsNullOrWhiteSpace(message))
            {
                var comment = new Comment
                {
                    AppUserId = HttpContext.UserId(),
                    CreatedAt = DateTime.UtcNow,
                    LotId     = lotId,
                    Text      = message
                };

                await _repository.Add(comment);

                var commentView = new CommentsView
                {
                    Comments = await _repository.GetCommentsList(lotId, 10, 0),
                    Take     = 10,
                    Skip     = 0,
                    LotId    = lotId
                };

                return(PartialView("_Comments", commentView));
            }

            return(BadRequest());
        }
        public void when_calling_GetComments_returns_CommentsView_Resort()
        {
            int Id = 1;

            List <Comment> commentList = new List <Comment>();

            for (int i = 0; i < 5; i++)
            {
                Comment comment = new Comment();
                comment.CommentId = i;
                comment.Text      = "CommentR" + i;
                comment.User      = new ApplicationUser();
                commentList.Add(comment);
            }

            CommentsView model = new CommentsView();

            model.Comments = commentList;

            Mock <IHolidaysRepository> mock = new Mock <IHolidaysRepository>();

            mock.Setup(m => m.GetCommentsHotel(It.IsAny <int>())).Returns(commentList);
            mock.Setup(m => m.GetCommentsResort(It.IsAny <int>())).Returns(commentList);
            HomeController controller = new HomeController(mock.Object);

            CommentsView result = (CommentsView)((PartialViewResult)controller.GetComments("Resort", Id)).ViewData.Model;


            Assert.AreEqual(result.Comments, model.Comments);
        }
Пример #4
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var additions = _split.AddButton("Additions", "-");
            var deletions = _split.AddButton("Deletions", "-");
            var parents   = _split.AddButton("Parents", "-");

            var commentsElement = new WebElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;
            //commentsSection.Add(commentsElement);

            var headerSection = new Section(HeaderView)
            {
                _split
            };

            Root.Reset(headerSection);

            ViewModel.WhenAnyValue(x => x.Commit).IsNotNull().SubscribeSafe(x =>
            {
                HeaderView.Image    = Images.LoginUserUnknown;
                HeaderView.ImageUri = x.GenerateGravatarUrl();

                var msg         = x.Commit.Message ?? string.Empty;
                var firstLine   = msg.IndexOf("\n", StringComparison.Ordinal);
                HeaderView.Text = firstLine > 0 ? msg.Substring(0, firstLine) : msg;

                HeaderView.SubText = "Commited " + (x.Commit.Committer.Date).ToDaysAgo();

                additions.Text = x.Stats.Additions.ToString();
                deletions.Text = x.Stats.Deletions.ToString();
                parents.Text   = x.Parents.Count.ToString();

                ReloadData();
            });

            ViewModel.WhenAnyValue(x => x.Commit).Where(x => x != null).Subscribe(Render);

            ViewModel.Comments.Changed
            .Select(_ => new Unit())
            .StartWith(new Unit())
            .Subscribe(x =>
            {
                var commentModels = ViewModel.Comments.Select(c =>
                                                              new Comment(c.User.AvatarUrl, c.User.Login, c.BodyHtml, c.CreatedAt.ToDaysAgo()));
                var razorView = new CommentsView {
                    Model = commentModels
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;

                if (commentsElement.GetRootElement() == null && ViewModel.Comments.Count > 0)
                {
                    _commentSection.Add(commentsElement);
                }
            });
        }
Пример #5
0
        public IActionResult ViewCommentsGroups(string postID)
        {
            string       myID     = HttpContext.User.FindFirst("UserID").Value.ToString();
            CommentsView comments = new CommentsView();

            comments = dataBase.GetCommentsGroups(myID, postID);
            return(View("comentariosgrupos", comments));
        }
        public ActionResult Leave(Media media)
        {
            List <Comment> comments            = _commentRepository.RetrieveAllByMediaId(media.MediaId);
            IDictionary <string, string> crumb = CommentCrumb(media, media.MediaId);

            CommentsView commentsView = ModelFactory <CommentsView>(new { media, comments });

            return(View(commentsView, crumb));
        }
        public async Task <CommentsView> GetAllForSlug(string slug)
        {
            var list = await this.repository.RetrieveAllForSlug(slug);

            var commentList = new CommentsView();

            // map domain objects to view objects
            commentList.Comments = list.Select(x => new CommentView(x)).ToList();
            return(commentList);
        }
        private void ShowCommentsButton_Click(object sender, RoutedEventArgs e)
        {
            ContentGrid.Visibility  = Visibility.Collapsed;
            CommentsGrid.Visibility = Visibility.Visible;

            if (!CommentsAlreadyLoaded)
            {
                CommentsView.Navigate(new Uri($"https://sce.seeriis.net/News/Comments/{ArticleID}"));
                CommentsAlreadyLoaded = true;
            }
        }
        public ActionResult CreateComment(CommentsView m)
        {
            var cardId  = m.Card.Id;
            var comment = new Comment {
                Text = m.NewComment.Text, CardId = cardId
            };

            // TODO wrap in try catch
            var newComment = Comment.Create(comment, this._api);

            if (newComment == null)
            {
                return(View("Error"));
            }
            return(RedirectToAction("Detail", new { id = cardId }));
        }
        public ActionResult Detail(string id)
        {
            // TODO wrap in try catch
            var comments = Comment.List(id, this._api);
            var card     = Card.Get(id, this._api);

            if (card.Id == null)
            {
                return(View("Error"));
            }
            var cv = new CommentsView {
                Comments = comments, NewComment = new Models.Comment(), Card = card
            };

            return(View(cv));
        }
Пример #11
0
        public ActionResult GetComments(string type, int id)
        {
            CommentsView model = new CommentsView();

            if (type == "Hotel")
            {
                model.Comments = repository.GetCommentsHotel(id);
            }
            else
            {
                model.Comments = repository.GetCommentsResort(id);
            }


            return(PartialView(model));
        }
        public ActionResult Leave(string id, CommentSaveView saveView)
        {
            int     photoId = Convert.ToInt32(id);
            Media   media   = _mediaRepository.RetrieveByPrimaryKeyAndUserId(photoId, Owner.Id);
            Comment comment = GetComment(Owner, saveView, media);

            _commentRepository.Save(comment);

            IDictionary <string, string> crumb = CommentCrumb(media, photoId);
            List <Comment> comments            = _commentRepository.RetrieveAllByMediaId(media.MediaId);

            CommentsView commentsView = ModelFactory <CommentsView>(new { media, comments });

            commentsView.UIMessage = "Thank you for commenting.";

            return(View(commentsView, crumb));
        }
Пример #13
0
        public void RenderComments()
        {
            var comments = ViewModel.Comments
                .Select(x => new Comment(x.User.AvatarUrl, x.User.Login, ViewModel.ConvertToMarkdown(x.Body), x.CreatedAt))
                .Concat(ViewModel.Events.Select(x => new Comment(x.Actor.AvatarUrl, x.Actor.Login, CreateEventBody(x.Event, x.CommitId), x.CreatedAt)))
                .Where(x => !string.IsNullOrEmpty(x.Body))
                .OrderBy(x => x.Date)
                .ToList();
            var commentModel = new CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
            var razorView = new CommentsView { Model = commentModel };
            var html = razorView.GenerateString();

            InvokeOnMainThread(() => {
                _commentsElement.SetValue(!comments.Any() ? null : html);
                Render();
            });
        }
Пример #14
0
        public async Task <IActionResult> GetComments(int lotId, int take, int skip)
        {
            var comments = await _repository.GetCommentsList(lotId, take, skip);

            if (comments.Count != 0)
            {
                var commentView = new CommentsView
                {
                    Comments = comments,
                    Take     = take,
                    Skip     = skip,
                    LotId    = lotId
                };

                return(PartialView("_Comments", commentView));
            }

            return(PartialView("_Comments"));
        }
 void ReleaseDesignerOutlets()
 {
     if (CommentsLabel != null)
     {
         CommentsLabel.Dispose();
         CommentsLabel = null;
     }
     if (CommentsTextView != null)
     {
         CommentsTextView.Dispose();
         CommentsTextView = null;
     }
     if (CommentsView != null)
     {
         CommentsView.Dispose();
         CommentsView = null;
     }
     if (imgScrollViewHeightCnstrnt != null)
     {
         imgScrollViewHeightCnstrnt.Dispose();
         imgScrollViewHeightCnstrnt = null;
     }
     if (PunchHeading != null)
     {
         PunchHeading.Dispose();
         PunchHeading = null;
     }
     if (punchImgScrollView != null)
     {
         punchImgScrollView.Dispose();
         punchImgScrollView = null;
     }
     if (punchSegmentControl != null)
     {
         punchSegmentControl.Dispose();
         punchSegmentControl = null;
     }
     if (takePictureBtn != null)
     {
         takePictureBtn.Dispose();
         takePictureBtn = null;
     }
 }
Пример #16
0
        protected void Page_Load(object sender, EventArgs e)
        {
            if (IsPostBack)
            {
                CommentsView.DataBind();
            }

            var commentAdapterFactory = new CommentDataAdapterFactory(Entity.ToEntityReference());

            var dataAdapter = commentAdapterFactory.GetAdapter(Portal, Request.RequestContext);

            if (dataAdapter == null)
            {
                Visible = false;

                return;
            }

            var commentPolicyReader = dataAdapter.GetCommentPolicyReader();

            CommentsView.Visible = (!commentPolicyReader.IsCommentPolicyNone);

            NewCommentPanel.Visible = CommentsOpenToCurrentUser(commentPolicyReader);
        }
Пример #17
0
        private List <CommentsView> GetComments(string id)
        {
            CommentsContext       commentsContext = new CommentsContext();
            IQueryable <Comments> query           = commentsContext.Comment.Where(x => x.SellerId == id);
            List <Comments>       commentsList    = query.ToList();
            //Builds container that have comment information after converting to userfriendly format
            List <CommentsView> commentsView = new List <CommentsView>();

            foreach (Comments item in commentsList)
            {
                CommentsView row = new CommentsView();
                row.AuctionUrl = "AuctionDetails.aspx?Id=" + item.AuctionId;
                Auction auction = ExtensionMethods.GetAuction(item.AuctionId);
                row.AuctionTitle = ExtensionMethods.GetAuction(item.AuctionId).Title;
                row.BuyerUrl     = "CommentSite.aspx?Id=" + item.BuyerId;
                row.SellerUrl    = "CommentSite.aspx?Id=" + item.SellerId;
                row.Description  = item.Description;
                row.Rate         = item.Rate;
                row.SellerName   = ExtensionMethods.GetUserNameByID(item.SellerId);
                row.BuyerName    = ExtensionMethods.GetUserNameByID(item.BuyerId);
                commentsView.Add(row);
            }
            return(commentsView);
        }
Пример #18
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.Image = Images.LoginUserUnknown;

            var split         = new SplitButtonElement();
            var headerSection = new Section {
                split
            };
            var descriptionElement = new MultilinedElement();
            var detailsSection     = new Section();
            var footerButton       = new TableFooterButton("Add Comment");
            var commentsSection    = new Section(null, footerButton);

            var diffButton       = new StringElement(Octicon.DiffAdded.ToImage());
            var removedButton    = new StringElement(Octicon.DiffRemoved.ToImage());
            var modifiedButton   = new StringElement(Octicon.DiffModified.ToImage());
            var allChangesButton = new StringElement("All Changes", Octicon.Diff.ToImage());

            detailsSection.Add(new [] { diffButton, removedButton, modifiedButton, allChangesButton });

            var additions       = split.AddButton("Additions");
            var deletions       = split.AddButton("Deletions");
            var parents         = split.AddButton("Parents");
            var commentsElement = new HtmlElement("comments");

            ViewModel.Comments.Changed
            .Select(_ => new Unit())
            .StartWith(new Unit())
            .Subscribe(x =>
            {
                var comments     = ViewModel.Comments.Select(c => new Comment(c.Avatar.ToUri(), c.Actor, c.Body, c.UtcCreatedAt.Humanize())).ToList();
                var commentModel = new CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                var razorView    = new CommentsView {
                    Model = commentModel
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;

                if (commentsElement.GetRootElement() == null && ViewModel.Comments.Count > 0)
                {
                    commentsSection.Add(commentsElement);
                }
                TableView.ReloadData();
            });

            this.WhenAnyValue(x => x.ViewModel.Commit)
            .IsNotNull()
            .Take(1)
            .Subscribe(_ => Root.Reset(headerSection, detailsSection, commentsSection));

            Appeared
            .Take(1)
            .Select(_ => this.WhenAnyValue(x => x.ViewModel.CommitMessage, y => y.ViewModel.CommiterName))
            .Switch()
            .Where(x => x.Item1 != null && x.Item2 != null)
            .Take(1)
            .Subscribe(_ => detailsSection.Insert(0, UITableViewRowAnimation.Automatic, descriptionElement));

            OnActivation(d => {
                d(allChangesButton.BindCommand(ViewModel.GoToAllFiles));
                d(footerButton.Clicked.InvokeCommand(ViewModel.AddCommentCommand));

                d(this.WhenAnyValue(x => x.ViewModel.Avatar)
                  .Subscribe(x => HeaderView.SetImage(x?.ToUri(128), Images.LoginUserUnknown)));

                d(this.WhenAnyValue(x => x.ViewModel.CommitMessage)
                  .Subscribe(x => descriptionElement.Details = x ?? string.Empty));

                d(descriptionElement.BindCaption(this.WhenAnyValue(x => x.ViewModel.CommiterName)));

                d(diffButton.BindCommand(ViewModel.GoToAddedFiles));
                d(diffButton.BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffAdditions).Select(x => x > 0)));
                d(diffButton.BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffAdditions).StartWith(0).Select(x => string.Format("{0} added", x))));

                d(removedButton.BindCommand(ViewModel.GoToRemovedFiles));
                d(removedButton.BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffDeletions).Select(x => x > 0)));
                d(removedButton.BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffDeletions).StartWith(0).Select(x => string.Format("{0} removed", x))));

                d(modifiedButton.BindCommand(ViewModel.GoToModifiedFiles));
                d(modifiedButton.BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffModifications).Select(x => x > 0)));
                d(modifiedButton.BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffModifications).StartWith(0).Select(x => string.Format("{0} modified", x))));

                d(allChangesButton.BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffAdditions, x => x.ViewModel.DiffDeletions, x => x.ViewModel.DiffModifications)
                                                  .Select(x => x.Item1 + x.Item2 + x.Item3 > 0)));

                d(commentsElement.UrlRequested.InvokeCommand(ViewModel.GoToUrlCommand));

                d(this.WhenAnyValue(x => x.ViewModel.ShowMenuCommand)
                  .ToBarButtonItem(UIBarButtonSystemItem.Action, x => NavigationItem.RightBarButtonItem = x));

                d(this.WhenAnyValue(x => x.ViewModel.CommitMessageSummary).Subscribe(x => RefreshHeaderView(x)));

                d(this.WhenAnyValue(x => x.ViewModel.Commit).IsNotNull()
                  .Select(x => "Commited " + x.Commit.Committer.Date.LocalDateTime.Humanize())
                  .Subscribe(x => RefreshHeaderView(subtext: x)));

                var statsObs = this.WhenAnyValue(x => x.ViewModel.Commit.Stats);
                d(additions.BindText(statsObs.Select(x => x != null ? x.Additions.ToString() : "-")));
                d(deletions.BindText(statsObs.Select(x => x != null ? x.Deletions.ToString() : "-")));

                d(this.WhenAnyValue(x => x.ViewModel.Commit.Parents)
                  .Subscribe(x => parents.Text = x != null ? x.Count.ToString() : "-"));
            });
        }
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var split        = new SplitButtonElement();
            var commentCount = split.AddButton("Comments", "-");
            var participants = split.AddButton("Participants", "-");
            var approvals    = split.AddButton("Approvals", "-");

            this.WhenAnyValue(x => x.ViewModel.Title)
            .Subscribe(x => RefreshHeaderView(x));

            ViewModel.WhenAnyValue(x => x.PullRequest).Subscribe(x =>
            {
                if (x != null)
                {
                    var avatarUrl      = x?.Author?.Links?.Avatar?.Href;
                    HeaderView.SubText = "Updated " + ViewModel.PullRequest.UpdatedOn.Humanize();
                    HeaderView.SetImage(new Avatar(avatarUrl).ToUrl(128), Images.Avatar);
                }
                else
                {
                    HeaderView.SetImage(null, Images.Avatar);
                    HeaderView.SubText = null;
                }
            });

            var root = new List <Section>();

            root.Add(new Section {
                split
            });

            var secDetails = new Section();

            root.Add(secDetails);

            this.WhenAnyValue(x => x.ViewModel.Description)
            .Where(x => !string.IsNullOrWhiteSpace(x))
            .Select(x => new DescriptionModel(x, (int)UIFont.PreferredSubheadline.PointSize, true))
            .Select(x => new MarkdownView {
                Model = x
            }.GenerateString())
            .Subscribe(content =>
            {
                _descriptionElement.SetValue(content);
                secDetails.Insert(0, UITableViewRowAnimation.None, _descriptionElement);
            });

            var split1 = new SplitViewElement(AtlassianIcon.Calendar.ToImage(), AtlassianIcon.Devtoolsbranch.ToImage());

            secDetails.Add(split1);

            this.WhenAnyValue(x => x.ViewModel.PullRequest.State)
            .Select(x => x?.ToLower().Humanize(LetterCasing.Title))
            .Subscribe(x => split1.Button2.Text = x ?? "Open");

            this.WhenAnyValue(x => x.ViewModel.PullRequest)
            .Select(x => x?.CreatedOn.ToString("MM/dd/yy"))
            .Subscribe(x => split1.Button1.Text = x);

            var commitsElement = new ButtonElement("Commits", AtlassianIcon.Devtoolscommit.ToImage());

            commitsElement.Clicked.SelectUnit().BindCommand(ViewModel.GoToCommitsCommand);
            secDetails.Add(commitsElement);

            var mergeElement = new ButtonElement("Merge", AtlassianIcon.ListAdd.ToImage());

            mergeElement.Accessory = UITableViewCellAccessory.None;

            var rejectElement = new LoaderButtonElement("Reject", AtlassianIcon.ListRemove.ToImage());

            rejectElement.Accessory = UITableViewCellAccessory.None;
            rejectElement.BindLoader(ViewModel.RejectCommand);

            var mergeSection = new Section {
                mergeElement, rejectElement
            };

            var approvalSection = new Section("Approvals");
            var approveElement  = new LoaderButtonElement("Approve", AtlassianIcon.Approve.ToImage());

            approveElement.Accessory = UITableViewCellAccessory.None;
            approveElement.BindLoader(ViewModel.ToggleApproveButton);
            approveElement.BindCaption(this.WhenAnyValue(x => x.ViewModel.Approved).Select(x => x ? "Unapprove" : "Approve"));
            root.Add(approvalSection);

            this.WhenAnyValue(x => x.ViewModel.Approvals)
            .Select(x => x.Select(y => new UserElement(y)).OfType <Element>())
            .Subscribe(x => approvalSection.Reset(x.Concat(new[] { approveElement })));

            var commentsSection = new Section("Comments");

            root.Add(commentsSection);

            var addComment = new ButtonElement("Add Comment")
            {
                Image = AtlassianIcon.Addcomment.ToImage()
            };

            commentsSection.Reset(new[] { addComment });

            ViewModel
            .Comments
            .ChangedObservable()
            .Subscribe(x =>
            {
                if (x.Count > 0)
                {
                    var comments     = x.Select(y => new Comment(y.Avatar.ToUrl(), y.Name, y.Content, y.CreatedOn)).ToList();
                    var commentModel = new CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                    var content      = new CommentsView {
                        Model = commentModel
                    }.GenerateString();
                    _commentsElement.SetValue(content);
                    commentsSection.Insert(0, UITableViewRowAnimation.None, _commentsElement);
                }
                else
                {
                    commentsSection.Remove(_commentsElement);
                }
            });

            Root.Reset(root);

            this.WhenAnyValue(x => x.ViewModel.IsOpen).Subscribe(x =>
            {
                if (x)
                {
                    Root.Insert(root.IndexOf(secDetails) + 1, mergeSection);
                }
                else
                {
                    Root.Remove(mergeSection);
                }
            });

            OnActivation(disposable =>
            {
                mergeElement
                .Clicked
                .SelectUnit()
                .BindCommand(this, x => x.ViewModel.MergeCommand)
                .AddTo(disposable);

                addComment
                .Clicked
                .Subscribe(_ => NewCommentViewController.Present(this, ViewModel.AddComment))
                .AddTo(disposable);

                this.WhenAnyValue(x => x.ViewModel.ParticipantCount)
                .Subscribe(x => participants.Text = x?.ToString() ?? "-")
                .AddTo(disposable);

                this.WhenAnyValue(x => x.ViewModel.ApprovalCount)
                .Subscribe(x => approvals.Text = x?.ToString() ?? "-")
                .AddTo(disposable);

                this.WhenAnyValue(x => x.ViewModel.CommentCount)
                .Subscribe(x => commentCount.Text = x?.ToString() ?? "-")
                .AddTo(disposable);

                this.WhenAnyObservable(x => x.ViewModel.MergeCommand)
                .Subscribe(_ =>
                {
                    var vc = new PullRequestApproveViewController(
                        ViewModel.Username, ViewModel.Repository, ViewModel.PullRequestId);
                    vc.DeleteSourceBranch = ViewModel.PullRequest.CloseSourceBranch;
                    vc.MergeCommand
                    .Do(x => ViewModel.PullRequest = x)
                    .Do(x => DismissViewController(true, null))
                    .Subscribe();
                    this.PresentModal(vc);
                })
                .AddTo(disposable);
            });
        }
Пример #20
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var commentsElement = new HtmlElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;

            ViewModel.WhenAnyValue(x => x.Commit).IsNotNull().SubscribeSafe(x =>
            {
                HeaderView.ImageUri = x.GenerateGravatarUrl();
                HeaderView.SubText  = "Commited " + x.Commit.Committer.Date.LocalDateTime.Humanize();
                RefreshHeaderView();
            });

            ViewModel.Comments.Changed.Select(_ => new Unit()).StartWith(new Unit()).Subscribe(x =>
            {
                var commentModels = ViewModel.Comments.Select(c =>
                                                              new Comment(c.User.AvatarUrl, c.User.Login, c.Body, c.CreatedAt.UtcDateTime.Humanize()));
                var razorView = new CommentsView {
                    Model = commentModels
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;

                if (commentsElement.GetRootElement() == null && ViewModel.Comments.Count > 0)
                {
                    _commentSection.Add(commentsElement);
                }
                TableView.ReloadData();
            });

            ViewModel.WhenAnyValue(x => x.Commit).IsNotNull().Subscribe(commitModel =>
            {
                var detailSection = new Section();
                Root.Reset(_headerSection, detailSection);

                var user = commitModel.GenerateCommiterName();
                detailSection.Add(new MultilinedElement(user, commitModel.Commit.Message)
                {
                    CaptionColor    = Theme.MainTextColor,
                    ValueColor      = Theme.MainTextColor,
                    BackgroundColor = UIColor.White
                });

                if (ViewModel.ShowRepository)
                {
                    var repo = new StyledStringElement(ViewModel.RepositoryName)
                    {
                        Accessory = UIKit.UITableViewCellAccessory.DisclosureIndicator,
                        Lines     = 1,
                        Font      = StyledStringElement.DefaultDetailFont,
                        TextColor = StyledStringElement.DefaultDetailColor,
                        Image     = Images.Repo
                    };
                    repo.Tapped += () => ViewModel.GoToRepositoryCommand.Execute(null);
                    detailSection.Add(repo);
                }

                var paths = commitModel.Files.GroupBy(y => {
                    var filename = "/" + y.Filename;
                    return(filename.Substring(0, filename.LastIndexOf("/", System.StringComparison.Ordinal) + 1));
                }).OrderBy(y => y.Key);

                foreach (var p in paths)
                {
                    var fileSection = new Section(p.Key);
                    foreach (var x in p)
                    {
                        var y       = x;
                        var file    = x.Filename.Substring(x.Filename.LastIndexOf('/') + 1);
                        var sse     = new ChangesetElement(file, x.Status, x.Additions, x.Deletions);
                        sse.Tapped += () => ViewModel.GoToFileCommand.Execute(y);
                        fileSection.Add(sse);
                    }
                    Root.Add(fileSection);
                }

                Root.Add(_commentSection);

                var addComment = new StyledStringElement("Add Comment")
                {
                    Image = Images.Pencil
                };
                addComment.Tapped += () => ViewModel.GoToCommentCommand.ExecuteIfCan();
                Root.Add(new Section {
                    addComment
                });
            });
        }
Пример #21
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var headerSection = new Section();
            var filesSection  = new Section("Files");

            var split    = new SplitButtonElement();
            var files    = split.AddButton("Files", "-");
            var comments = split.AddButton("Comments", "-");
            var forks    = split.AddButton("Forks", "-");

            headerSection.Add(split);

            var commentsSection = new Section("Comments")
            {
                FooterView = new TableFooterButton("Add Comment", ViewModel.AddCommentCommand.ExecuteIfCan)
            };
            var commentsElement = new HtmlElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;
            commentsSection.Add(commentsElement);

            var detailsSection = new Section {
                _splitRow1, _splitRow2
            };

            Root.Reset(headerSection, detailsSection, filesSection, commentsSection);

            var updatedGistObservable = ViewModel.WhenAnyValue(x => x.Gist).Where(x => x != null);

            ViewModel.WhenAnyValue(x => x.Gist)
            .IsNotNull()
            .Select(x => x.Owner)
            .Subscribe(x =>
            {
                if (x == null)
                {
                    detailsSection.Remove(_ownerElement);
                }
                else if (x != null && !detailsSection.Contains(_ownerElement))
                {
                    detailsSection.Add(_ownerElement);
                }
            });

            updatedGistObservable.SubscribeSafe(x =>
            {
                if (x.Owner == null)
                {
                    _ownerElement.Value     = "Anonymous";
                    _ownerElement.Accessory = UITableViewCellAccessory.None;
                }
                else
                {
                    _ownerElement.Value     = x.Owner.Login;
                    _ownerElement.Accessory = UITableViewCellAccessory.DisclosureIndicator;
                }

                Root.Reload(_ownerElement);
            });

            updatedGistObservable.SubscribeSafe(x =>
            {
                HeaderView.SubText = x.Description;
                if (x.Owner != null)
                {
                    HeaderView.ImageUri = x.Owner.AvatarUrl;
                }
                else
                {
                    HeaderView.Image = Images.LoginUserUnknown;
                }
                TableView.ReloadData();
            });

            updatedGistObservable.Select(x => x.Files == null ? 0 : x.Files.Count()).SubscribeSafe(x => files.Text = x.ToString());
            updatedGistObservable.SubscribeSafe(x => comments.Text = x.Comments.ToString());
            updatedGistObservable.Select(x => x.Forks == null ? 0 : x.Forks.Count()).SubscribeSafe(x => forks.Text = x.ToString());

            updatedGistObservable.Subscribe(x =>
            {
                var elements = new List <Element>();
                foreach (var file in x.Files.Keys)
                {
                    var sse = new StyledStringElement(file, x.Files[file].Size + " bytes", UITableViewCellStyle.Subtitle)
                    {
                        Accessory     = UITableViewCellAccessory.DisclosureIndicator,
                        LineBreakMode = UILineBreakMode.TailTruncation,
                        Lines         = 1
                    };

                    sse.Tapped += () => ViewModel.GoToFileSourceCommand.Execute(x.Files[file]);
                    elements.Add(sse);
                }

                filesSection.Reset(elements);
            });


            ViewModel.Comments.Changed.Subscribe(_ =>
            {
                var commentModels = ViewModel.Comments
                                    .Select(x => new Comment(x.User.AvatarUrl, x.User.Login, x.BodyHtml, x.CreatedAt.UtcDateTime.Humanize()))
                                    .ToList();

                if (commentModels.Count > 0)
                {
                    var razorView = new CommentsView {
                        Model = commentModels
                    };
                    var html = razorView.GenerateString();
                    commentsElement.Value = html;

                    if (!commentsSection.Contains(commentsElement))
                    {
                        commentsSection.Insert(0, UITableViewRowAnimation.Fade, commentsElement);
                    }
                }
                else
                {
                    commentsSection.Remove(commentsElement);
                }
            });
        }
Пример #22
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var updatedGistObservable = ViewModel.WhenAnyValue(x => x.Gist).Where(x => x != null);

            var headerSection = new Section(HeaderView);
            var filesSection  = new Section("Files");

            var split    = new SplitButtonElement();
            var files    = split.AddButton("Files", "-");
            var comments = split.AddButton("Comments", "-");
            var forks    = split.AddButton("Forks", "-");

            headerSection.Add(split);

            var commentsSection = new Section("Comments");
            var commentsElement = new WebElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;
            commentsSection.Add(commentsElement);

            var detailsSection = new Section();
            var splitElement1  = new SplitElement();

            splitElement1.Button1 = new SplitElement.SplitButton(Images.Locked, string.Empty);
            splitElement1.Button2 = new SplitElement.SplitButton(Images.Language, string.Empty);
            detailsSection.Add(splitElement1);

            var splitElement2 = new SplitElement();

            splitElement2.Button1 = new SplitElement.SplitButton(Images.Update, string.Empty);
            splitElement2.Button2 = new SplitElement.SplitButton(Images.Star2, string.Empty);
            detailsSection.Add(splitElement2);

            var owner = new StyledStringElement("Owner", string.Empty)
            {
                Image = Images.Person
            };

            owner.Tapped += () => ViewModel.GoToUserCommand.ExecuteIfCan();
            detailsSection.Add(owner);

            updatedGistObservable.SubscribeSafe(x =>
            {
                var publicGist    = x.Public.HasValue && x.Public.Value;
                var revisionCount = x.History == null ? 0 : x.History.Count;

                splitElement1.Button1.Text  = publicGist ? "Public" : "Private";
                splitElement1.Button1.Image = publicGist ? Images.Unlocked : Images.Locked;
                splitElement1.Button2.Text  = revisionCount + " Revisions";
                splitElement2.Button1.Text  = x.UpdatedAt.ToLocalTime().ToString("MM/dd/yy");
            });

            updatedGistObservable.SubscribeSafe(x =>
            {
                if (x.Owner == null)
                {
                    owner.Value     = "Anonymous";
                    owner.Accessory = UITableViewCellAccessory.None;
                }
                else
                {
                    owner.Value     = x.Owner.Login;
                    owner.Accessory = UITableViewCellAccessory.DisclosureIndicator;
                }

                Root.Reload(owner);
            });

            ViewModel.WhenAnyValue(x => x.IsStarred).Where(x => x.HasValue).Subscribe(x =>
            {
                splitElement2.Button2.Text  = x.Value ? "Starred!" : "Unstarred";
                splitElement2.Button2.Image = x.Value ? Images.Star : Images.Star2;
            });

            Root.Reset(headerSection, detailsSection, filesSection);

            updatedGistObservable.SubscribeSafe(x =>
            {
                HeaderView.SubText = x.Description;
                if (x.Owner != null)
                {
                    HeaderView.ImageUri = x.Owner.AvatarUrl;
                }
                Root.Reload(headerSection);
            });

            updatedGistObservable.Select(x => x.Files == null ? 0 : x.Files.Count()).SubscribeSafe(x => files.Text = x.ToString());
            updatedGistObservable.SubscribeSafe(x => comments.Text = x.Comments.ToString());
            updatedGistObservable.Select(x => x.Forks == null ? 0 : x.Forks.Count()).SubscribeSafe(x => forks.Text = x.ToString());

            updatedGistObservable.Subscribe(x =>
            {
                var elements = new List <Element>();
                foreach (var file in x.Files.Keys)
                {
                    var sse = new StyledStringElement(file, x.Files[file].Size + " bytes", UITableViewCellStyle.Subtitle)
                    {
                        Accessory     = UITableViewCellAccessory.DisclosureIndicator,
                        LineBreakMode = UILineBreakMode.TailTruncation,
                        Lines         = 1
                    };

                    var fileSaved     = file;
                    var gistFileModel = x.Files[fileSaved];

                    //              if (string.Equals(gistFileModel.Language, "markdown", StringComparison.OrdinalIgnoreCase))
                    //                  sse.Tapped += () => ViewModel.GoToViewableFileCommand.Execute(gistFileModel);
                    //              else
                    sse.Tapped += () => ViewModel.GoToFileSourceCommand.Execute(gistFileModel);
                    elements.Add(sse);
                }

                filesSection.Reset(elements);
            });
//
//            updatedGistObservable.Take(1).Subscribe(_ => Root.Add(filesSection));


            ViewModel.Comments.Changed.Subscribe(_ =>
            {
                var commentModels = ViewModel.Comments.Select(x =>
                                                              new Comment(x.User.AvatarUrl, x.User.Login, x.BodyHtml, x.CreatedAt.ToDaysAgo()));
                var razorView = new CommentsView {
                    Model = commentModels
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;
            });

            ViewModel.Comments.Changed.Take(1).Select(x => ViewModel.Comments).Where(x => x.Count > 0)
            .Subscribe(_ => Root.Insert(Root.Count, commentsSection));


            ViewModel.WhenAnyValue(x => x.Gist).Where(x => x != null).Subscribe(gist =>
            {
                if (string.Equals(_applicationService.Account.Username, ViewModel.Gist.Owner.Login, StringComparison.OrdinalIgnoreCase))
                {
                    NavigationItem.RightBarButtonItem = new UIBarButtonItem(UIBarButtonSystemItem.Compose, (s, e) => { });

//                              try
//					{
//						var data = await this.DoWorkAsync("Loading...", () => app.Client.ExecuteAsync(app.Client.Gists[ViewModel.Id].Get()));
//						var gistController = new EditGistController(data.Data);
//						gistController.Created = editedGist => ViewModel.Gist = editedGist;
//						var navController = new UINavigationController(gistController);
//						PresentViewController(navController, true, null);
//
//					}
//					catch (Exception ex)
//					{
//						MonoTouch.Utilities.ShowAlert("Error", ex.Message);
//					}
                }
                else
                {
                    NavigationItem.RightBarButtonItem =
                        new UIBarButtonItem(Theme.CurrentTheme.ForkButton, UIBarButtonItemStyle.Plain, (s, e) =>
                                            ViewModel.ForkCommand.ExecuteIfCan());
                    NavigationItem.RightBarButtonItem.EnableIfExecutable(ViewModel.ForkCommand.CanExecuteObservable);
                }
            });

            ViewModel.ForkCommand.IsExecuting.Subscribe(x =>
            {
                if (x)
                {
                    _statusIndicatorService.Show("Forking...");
                }
                else
                {
                    _statusIndicatorService.Hide();
                }
            });
        }
Пример #23
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.Image = Images.LoginUserUnknown;
            HeaderView.SubImageView.TintColor = UIColor.FromRGB(243, 156, 18);

            var headerSection = new Section();
            var filesSection  = new Section();

            var split    = new SplitButtonElement();
            var files    = split.AddButton("Files", "-");
            var comments = split.AddButton("Comments", "-");
            var forks    = split.AddButton("Forks", "-");

            headerSection.Add(split);

            var commentsSection = new Section()
            {
                FooterView = new TableFooterButton("Add Comment", ViewModel.AddCommentCommand.ExecuteIfCan)
            };
            var commentsElement = new HtmlElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;
            commentsSection.Add(commentsElement);

            var detailsSection = new Section {
                _splitRow1, _splitRow2
            };

            Root.Reset(headerSection, detailsSection, filesSection, commentsSection);

            var updatedGistObservable = ViewModel.WhenAnyValue(x => x.Gist).Where(x => x != null);

            ViewModel.WhenAnyValue(x => x.Gist)
            .IsNotNull()
            .Select(x => x.Owner)
            .Subscribe(x =>
            {
                if (x == null)
                {
                    detailsSection.Remove(_ownerElement);
                }
                else if (x != null && !detailsSection.Contains(_ownerElement))
                {
                    detailsSection.Add(_ownerElement);
                }
            });


            updatedGistObservable
            .Select(x => x?.Owner?.Login ?? "Anonymous")
            .Subscribe(x => _ownerElement.Value = x);

            updatedGistObservable
            .Select(x => x.Owner != null ? () => ViewModel.GoToOwnerCommand.ExecuteIfCan() : (Action)null)
            .SubscribeSafe(x => _ownerElement.Tapped = x);

            this.WhenAnyValue(x => x.ViewModel.Avatar)
            .Subscribe(x => HeaderView.SetImage(x?.ToUri(64), Images.LoginUserUnknown));

            updatedGistObservable.SubscribeSafe(x => {
                HeaderView.SubText = x.Description;
                RefreshHeaderView();
            });

            updatedGistObservable.Select(x => x.Files == null ? 0 : x.Files.Count()).SubscribeSafe(x => files.Text = x.ToString());
            updatedGistObservable.SubscribeSafe(x => comments.Text = x.Comments.ToString());
            updatedGistObservable.Select(x => x.Forks == null ? 0 : x.Forks.Count()).SubscribeSafe(x => forks.Text = x.ToString());

            updatedGistObservable.Subscribe(x =>
            {
                var elements = new List <Element>();
                foreach (var file in x.Files.Keys)
                {
                    var sse     = new StringElement(file);
                    sse.Image   = Octicon.FileCode.ToImage();
                    sse.Tapped += () => ViewModel.GoToFileSourceCommand.Execute(x.Files[file]);
                    elements.Add(sse);
                }

                filesSection.Reset(elements);
            });


            ViewModel.Comments.Changed.Subscribe(_ => {
                var commentModels = ViewModel.Comments
                                    .Select(x => {
                    var avatarUrl = x?.User?.AvatarUrl;
                    var avatar    = new GitHubAvatar(avatarUrl);
                    return(new Comment(avatar.ToUri(), x.User.Login, x.BodyHtml, x.CreatedAt.UtcDateTime.Humanize()));
                }).ToList();

                if (commentModels.Count > 0)
                {
                    var model     = new CommentModel(commentModels, (int)UIFont.PreferredSubheadline.PointSize);
                    var razorView = new CommentsView {
                        Model = model
                    };
                    var html = razorView.GenerateString();
                    commentsElement.Value = html;

                    if (!commentsSection.Contains(commentsElement))
                    {
                        commentsSection.Insert(0, UITableViewRowAnimation.Fade, commentsElement);
                    }
                }
                else
                {
                    commentsSection.Remove(commentsElement);
                }
            });
        }
Пример #24
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.Image = Images.LoginUserUnknown;
            HeaderView.SubImageView.TintColor = UIColor.FromRGB(243, 156, 18);

            var headerSection = new Section();
            var filesSection  = new Section();

            var split    = new SplitButtonElement();
            var files    = split.AddButton("Files", "-");
            var comments = split.AddButton("Comments", "-");
            var forks    = split.AddButton("Forks", "-");

            headerSection.Add(split);

            var footerButton    = new TableFooterButton("Add Comment");
            var commentsSection = new Section(null, footerButton);
            var commentsElement = new HtmlElement("comments");

            commentsSection.Add(commentsElement);

            var splitRow1      = new SplitViewElement(Octicon.Lock.ToImage(), Octicon.Package.ToImage());
            var splitRow2      = new SplitViewElement(Octicon.Pencil.ToImage(), Octicon.Star.ToImage());
            var ownerElement   = new ButtonElement("Owner", Octicon.Person.ToImage());
            var detailsSection = new Section {
                splitRow1, splitRow2, ownerElement
            };

            Root.Reset(headerSection, detailsSection, filesSection, commentsSection);

            Appeared.Take(1).Delay(TimeSpan.FromSeconds(0.35f))
            .ObserveOn(RxApp.MainThreadScheduler)
            .Select(_ => this.WhenAnyValue(x => x.ViewModel.IsStarred).Where(x => x.HasValue))
            .Switch()
            .Select(x => x.Value ? Octicon.Star.ToImage() : null)
            .Subscribe(HeaderView.SetSubImage);

            ViewModel.Comments.Changed.Subscribe(_ => {
                var commentModels = ViewModel.Comments
                                    .Select(x => {
                    var avatarUrl = x?.User?.AvatarUrl;
                    var avatar    = new GitHubAvatar(avatarUrl);
                    return(new Comment(avatar.ToUri(), x.User.Login, x.BodyHtml, x.CreatedAt.UtcDateTime.Humanize()));
                }).ToList();

                if (commentModels.Count > 0)
                {
                    var model     = new CommentModel(commentModels, (int)UIFont.PreferredSubheadline.PointSize);
                    var razorView = new CommentsView {
                        Model = model
                    };
                    var html = razorView.GenerateString();
                    commentsElement.Value = html;

                    if (!commentsSection.Contains(commentsElement))
                    {
                        commentsSection.Insert(0, UITableViewRowAnimation.Fade, commentsElement);
                    }
                }
                else
                {
                    commentsSection.Remove(commentsElement);
                }
            });

            OnActivation(d => {
                d(footerButton.Clicked.InvokeCommand(ViewModel.AddCommentCommand));
                d(HeaderView.Clicked.InvokeCommand(ViewModel.GoToOwnerCommand));
                d(commentsElement.UrlRequested.InvokeCommand(ViewModel.GoToUrlCommand));
                d(splitRow2.Button2.Clicked.InvokeCommand(ViewModel.ToggleStarCommand));
                d(ownerElement.Clicked.InvokeCommand(ViewModel.GoToOwnerCommand));
                d(DialogSource.SelectedObservable.OfType <FileElement>().Select(x => x.File).InvokeCommand(ViewModel.GoToFileSourceCommand));

                var updatedGistObservable = ViewModel.WhenAnyValue(x => x.Gist).Where(x => x != null);
                d(updatedGistObservable.SubscribeSafe(x => RefreshHeaderView(subtext: x.Description)));
                d(updatedGistObservable.Subscribe(x => filesSection.Reset(x.Files.Select(y => new FileElement(y.Value)))));
                d(ownerElement.BindValue(updatedGistObservable.Select(x => x.Owner?.Login ?? "Anonymous")));
                d(files.BindText(updatedGistObservable.Select(x => x.Files?.Count() ?? 0)));
                d(forks.BindText(updatedGistObservable.Select(x => x.Forks?.Count() ?? 0)));
                d(comments.BindText(updatedGistObservable.Select(x => x.Comments.ToString())));
                d(splitRow1.Button1.BindText(updatedGistObservable.Select(x => x.Public ? "Public" : "Private")));
                d(splitRow1.Button2.BindText(updatedGistObservable.Select(x => "Revisions".ToQuantity(x.History?.Count ?? 0))));

                d(this.WhenAnyValue(x => x.ViewModel.Gist.Owner).Select(x => x == null)
                  .Subscribe(x => ownerElement.Hidden = x));

                d(this.WhenAnyValue(x => x.ViewModel.Avatar)
                  .Subscribe(x => HeaderView.SetImage(x?.ToUri(64), Images.LoginUserUnknown)));

                d(this.WhenAnyValue(x => x.ViewModel.ShowMenuCommand)
                  .ToBarButtonItem(UIBarButtonSystemItem.Action, x => NavigationItem.RightBarButtonItem = x));

                d(this.WhenAnyValue(x => x.ViewModel.IsStarred)
                  .Where(x => x.HasValue)
                  .Select(x => x.Value ? "Starred!" : "Unstarred")
                  .Subscribe(x => splitRow2.Button2.Text = x));

                d(splitRow2.Button1.BindText(this.WhenAnyValue(x => x.ViewModel.Gist).Select(x => {
                    var delta = DateTimeOffset.UtcNow.UtcDateTime - x.UpdatedAt.UtcDateTime;
                    return((delta.Days <= 0) ? "Created Today" : string.Format("{0} Days Old", delta.Days));
                })));
            });
        }
Пример #25
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.Image = Images.LoginUserUnknown;

            var split         = new SplitButtonElement();
            var headerSection = new Section {
                split
            };
            var descriptionElement = new MultilinedElement();
            var detailsSection     = new Section();
            var commentsSection    = new Section(null, new TableFooterButton("Add Comment", () => ViewModel.AddCommentCommand.ExecuteIfCan()));

            var additions = split.AddButton("Additions");
            var deletions = split.AddButton("Deletions");
            var parents   = split.AddButton("Parents");

            var gotoRepositoryElement = new StringElement(string.Empty)
            {
                Font      = StringElement.DefaultDetailFont,
                TextColor = StringElement.DefaultDetailColor,
                Image     = Octicon.Repo.ToImage()
            };

            gotoRepositoryElement.Tapped += () => ViewModel.GoToRepositoryCommand.ExecuteIfCan();

            detailsSection.Add(
                new StringElement(Octicon.DiffAdded.ToImage())
                .BindCommand(() => ViewModel.GoToAddedFiles)
                .BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffAdditions).Select(x => x > 0))
                .BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffAdditions).StartWith(0).Select(x => string.Format("{0} added", x))));

            detailsSection.Add(
                new StringElement(Octicon.DiffRemoved.ToImage())
                .BindCommand(() => ViewModel.GoToRemovedFiles)
                .BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffDeletions).Select(x => x > 0))
                .BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffDeletions).StartWith(0).Select(x => string.Format("{0} removed", x))));

            detailsSection.Add(
                new StringElement(Octicon.DiffModified.ToImage())
                .BindCommand(() => ViewModel.GoToModifiedFiles)
                .BindDisclosure(this.WhenAnyValue(x => x.ViewModel.DiffModifications).Select(x => x > 0))
                .BindCaption(this.WhenAnyValue(x => x.ViewModel.DiffModifications).StartWith(0).Select(x => string.Format("{0} modified", x))));

            detailsSection.Add(new StringElement("All Changes", () => ViewModel.GoToAllFiles.ExecuteIfCan(), Octicon.Diff.ToImage()));

            var commentsElement = new HtmlElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;

            ViewModel.Comments.Changed
            .Select(_ => new Unit())
            .StartWith(new Unit())
            .Subscribe(x =>
            {
                var comments     = ViewModel.Comments.Select(c => new Comment(c.Avatar.ToUri(), c.Actor, c.Body, c.UtcCreatedAt.Humanize())).ToList();
                var commentModel = new CodeHub.WebViews.CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                var razorView    = new CommentsView {
                    Model = commentModel
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;

                if (commentsElement.GetRootElement() == null && ViewModel.Comments.Count > 0)
                {
                    commentsSection.Add(commentsElement);
                }
                TableView.ReloadData();
            });

            this.WhenAnyValue(x => x.ViewModel.Commit)
            .IsNotNull()
            .Take(1)
            .Subscribe(_ => Root.Reset(headerSection, detailsSection, commentsSection));

            Appeared
            .Take(1)
            .Select(_ => this.WhenAnyValue(x => x.ViewModel.CommitMessage, y => y.ViewModel.CommiterName))
            .Switch()
            .Where(x => x.Item1 != null && x.Item2 != null)
            .Take(1)
            .Subscribe(_ => detailsSection.Insert(0, UITableViewRowAnimation.Automatic, descriptionElement));

            this.WhenAnyValue(x => x.ViewModel.CommiterName)
            .Subscribe(x => descriptionElement.Caption = x ?? string.Empty);

            this.WhenAnyValue(x => x.ViewModel.CommitMessage)
            .Subscribe(x => descriptionElement.Details = x ?? string.Empty);


            this.WhenAnyValue(x => x.ViewModel.RepositoryName)
            .Subscribe(x => gotoRepositoryElement.Caption = x);

            this.WhenAnyValue(x => x.ViewModel.ShowRepository)
            .StartWith(false)
            .Where(x => x)
            .Take(1)
            .Subscribe(x => detailsSection.Add(gotoRepositoryElement));

            this.WhenAnyValue(x => x.ViewModel.Commit)
            .SubscribeSafe(x =>
            {
                additions.Text = x != null ? x.Stats.Additions.ToString() : "-";
                deletions.Text = x != null ? x.Stats.Deletions.ToString() : "-";
                parents.Text   = x != null ? x.Parents.Count.ToString() : "-";
            });

            this.WhenAnyValue(x => x.ViewModel.ShowMenuCommand)
            .Select(x => x.ToBarButtonItem(UIBarButtonSystemItem.Action))
            .Subscribe(x => NavigationItem.RightBarButtonItem = x);

            this.WhenAnyValue(x => x.ViewModel.CommitMessageSummary)
            .Subscribe(x => {
                HeaderView.Text = x;
                RefreshHeaderView();
            });

            this.WhenAnyValue(x => x.ViewModel.Avatar)
            .Subscribe(x => HeaderView.SetImage(x?.ToUri(128), Images.LoginUserUnknown));

            this.WhenAnyValue(x => x.ViewModel.Commit)
            .IsNotNull()
            .Subscribe(x => {
                HeaderView.SubText = "Commited " + x.Commit.Committer.Date.LocalDateTime.Humanize();
                RefreshHeaderView();
            });
        }
Пример #26
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.SetImage(null, Images.Avatar);

            var compose = new UIBarButtonItem(UIBarButtonSystemItem.Compose);
            var more    = new UIBarButtonItem(UIBarButtonSystemItem.Action);

            NavigationItem.RightBarButtonItems = new[] { more, compose };

            var split        = new SplitButtonElement();
            var commentCount = split.AddButton("Comments", "-");
            var watchers     = split.AddButton("Watchers", "-");

            ICollection <Section> root = new LinkedList <Section>();

            root.Add(new Section {
                split
            });

            var secDetails = new Section();

            root.Add(secDetails);

            this.WhenAnyValue(x => x.ViewModel.ShowDescription)
            .DistinctUntilChanged()
            .Subscribe(x =>
            {
                if (x)
                {
                    secDetails.Insert(0, UITableViewRowAnimation.None, _descriptionElement);
                }
                else
                {
                    secDetails.Remove(_descriptionElement);
                }
            });

            this.WhenAnyValue(x => x.ViewModel.Description)
            .Where(x => !string.IsNullOrWhiteSpace(x))
            .Select(x => new DescriptionModel(x, (int)UIFont.PreferredSubheadline.PointSize, true))
            .Select(x => new MarkdownView {
                Model = x
            }.GenerateString())
            .Subscribe(_descriptionElement.SetValue);

            var split1 = new SplitViewElement(AtlassianIcon.Configure.ToImage(), AtlassianIcon.Error.ToImage());
            var split2 = new SplitViewElement(AtlassianIcon.Flag.ToImage(), AtlassianIcon.Spacedefault.ToImage());
            var split3 = new SplitViewElement(AtlassianIcon.Copyclipboard.ToImage(), AtlassianIcon.Calendar.ToImage());

            secDetails.Add(split1);
            secDetails.Add(split2);
            secDetails.Add(split3);

            var assigneeElement = new ButtonElement("Assigned", string.Empty, UITableViewCellStyle.Value1)
            {
                Image = AtlassianIcon.User.ToImage(),
            };

            secDetails.Add(assigneeElement);

            var commentsSection = new Section("Comments");

            root.Add(commentsSection);

            var addComment = new ButtonElement("Add Comment")
            {
                Image = AtlassianIcon.Addcomment.ToImage()
            };

            commentsSection.Reset(new[] { addComment });

            ViewModel
            .Comments
            .ChangedObservable()
            .Subscribe(x =>
            {
                if (x.Count > 0)
                {
                    var comments     = x.Select(y => new Comment(y.Avatar.ToUrl(), y.Name, y.Content, y.CreatedOn)).ToList();
                    var commentModel = new CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                    var content      = new CommentsView {
                        Model = commentModel
                    }.GenerateString();
                    _commentsElement.SetValue(content);
                    commentsSection.Insert(0, UITableViewRowAnimation.None, _commentsElement);
                }
                else
                {
                    commentsSection.Remove(_commentsElement);
                }
            });

            Root.Reset(root);

            OnActivation(d =>
            {
                this.WhenAnyValue(x => x.ViewModel.Issue)
                .Where(x => x != null)
                .Subscribe(x =>
                {
                    var avatarUrl      = x.ReportedBy?.Avatar;
                    HeaderView.Text    = x.Title;
                    HeaderView.SubText = "Updated " + ViewModel.Issue.UtcLastUpdated.Humanize();
                    HeaderView.SetImage(new Avatar(avatarUrl).ToUrl(128), Images.Avatar);
                    TableView.TableHeaderView = HeaderView;
                })
                .AddTo(d);

                this.WhenAnyObservable(x => x.ViewModel.DismissCommand)
                .Subscribe(_ => NavigationController.PopViewController(true))
                .AddTo(d);

                this.WhenAnyValue(x => x.ViewModel.Issue)
                .Subscribe(x =>
                {
                    split1.Button1.Text = x?.Status;
                    split1.Button2.Text = x?.Priority;
                    split2.Button1.Text = x?.Metadata?.Kind;
                    split2.Button2.Text = x?.Metadata?.Component ?? "No Component";
                    split3.Button1.Text = x?.Metadata?.Version ?? "No Version";
                    split3.Button2.Text = x?.Metadata?.Milestone ?? "No Milestone";
                })
                .AddTo(d);

                HeaderView
                .Clicked
                .BindCommand(this, x => x.ViewModel.GoToReporterCommand)
                .AddTo(d);

                compose
                .GetClickedObservable()
                .SelectUnit()
                .BindCommand(ViewModel.GoToEditCommand)
                .AddTo(d);

                addComment
                .Clicked
                .Subscribe(_ => NewCommentViewController.Present(this, ViewModel.AddComment))
                .AddTo(d);

                assigneeElement
                .BindValue(this.WhenAnyValue(x => x.ViewModel.Assigned))
                .AddTo(d);

                assigneeElement
                .BindDisclosure(
                    this.WhenAnyValue(x => x.ViewModel.Assigned)
                    .Select(x => !string.Equals(x, "Unassigned", StringComparison.OrdinalIgnoreCase)))
                .AddTo(d);

                assigneeElement
                .Clicked
                .SelectUnit()
                .BindCommand(ViewModel.GoToAssigneeCommand)
                .AddTo(d);

                more.Bind(ViewModel.ShowMenuCommand)
                .AddTo(d);

                this.WhenAnyValue(x => x.ViewModel.Issue)
                .Select(x => x != null)
                .Subscribe(x => compose.Enabled = x)
                .AddTo(d);

                this.WhenAnyObservable(x => x.ViewModel.Comments.CountChanged)
                .StartWith(ViewModel.Comments.Count)
                .Subscribe(x => commentCount.Text = x.ToString())
                .AddTo(d);

                this.WhenAnyValue(x => x.ViewModel.Issue.FollowerCount)
                .Subscribe(x => watchers.Text = x.ToString())
                .AddTo(d);
            });
        }
Пример #27
0
        protected BaseIssueViewController()
        {
            CommentsElement = new HtmlElement("comments");
            this.WhenAnyValue(x => x.ViewModel.GoToUrlCommand)
            .Subscribe(x => CommentsElement.UrlRequested = x.ExecuteIfCan);

            DescriptionElement = new HtmlElement("description");
            this.WhenAnyValue(x => x.ViewModel.GoToUrlCommand)
            .Subscribe(x => DescriptionElement.UrlRequested = x.ExecuteIfCan);

            this.WhenAnyValue(x => x.ViewModel.ShowMenuCommand)
            .Select(x => x.ToBarButtonItem(UIBarButtonSystemItem.Action))
            .Subscribe(x => NavigationItem.RightBarButtonItem = x);

            this.WhenAnyObservable(x => x.ViewModel.GoToAssigneesCommand)
            .Subscribe(_ => IssueAssigneeViewController.Show(this, ViewModel.CreateAssigneeViewModel()));

            this.WhenAnyObservable(x => x.ViewModel.GoToMilestonesCommand)
            .Subscribe(_ => IssueMilestonesViewController.Show(this, ViewModel.CreateMilestonesViewModel()));

            this.WhenAnyObservable(x => x.ViewModel.GoToLabelsCommand)
            .Subscribe(_ => IssueLabelsViewController.Show(this, ViewModel.CreateLabelsViewModel()));

            this.WhenAnyValue(x => x.ViewModel.GoToOwnerCommand)
            .Subscribe(x => HeaderView.ImageButtonAction = x != null ? new Action(() => ViewModel.GoToOwnerCommand.ExecuteIfCan()) : null);

            Appeared.Take(1)
            .Select(_ => Observable.Timer(TimeSpan.FromSeconds(0.2f)))
            .Switch()
            .ObserveOn(RxApp.MainThreadScheduler)
            .Select(_ => this.WhenAnyValue(x => x.ViewModel.IsClosed))
            .Switch()
            .Subscribe(x =>
            {
                HeaderView.SubImageView.TintColor = x ? UIColor.FromRGB(0xbd, 0x2c, 0) : UIColor.FromRGB(0x6c, 0xc6, 0x44);
                HeaderView.SetSubImage((x ? Octicon.IssueClosed :Octicon.IssueOpened).ToImage());
            });

            MilestoneElement = new StringElement("Milestone", string.Empty, UITableViewCellStyle.Value1)
            {
                Image = Octicon.Milestone.ToImage()
            };
            MilestoneElement.Tapped = () => ViewModel.GoToMilestonesCommand.ExecuteIfCan();
            this.WhenAnyValue(x => x.ViewModel.AssignedMilestone)
            .Select(x => x == null ? "No Milestone" : x.Title)
            .Subscribe(x => MilestoneElement.Value = x);

            AssigneeElement = new StringElement("Assigned", string.Empty, UITableViewCellStyle.Value1)
            {
                Image = Octicon.Person.ToImage()
            };
            AssigneeElement.Tapped = () => ViewModel.GoToAssigneesCommand.ExecuteIfCan();
            this.WhenAnyValue(x => x.ViewModel.AssignedUser)
            .Select(x => x == null ? "Unassigned" : x.Login)
            .Subscribe(x => AssigneeElement.Value = x);

            LabelsElement = new StringElement("Labels", string.Empty, UITableViewCellStyle.Value1)
            {
                Image = Octicon.Tag.ToImage()
            };
            LabelsElement.Tapped = () => ViewModel.GoToLabelsCommand.ExecuteIfCan();
            this.WhenAnyValue(x => x.ViewModel.AssignedLabels)
            .Select(x => (x == null || x.Count == 0) ? "None" : string.Join(",", x.Select(y => y.Name)))
            .Subscribe(x => LabelsElement.Value = x);

            this.WhenAnyValue(x => x.ViewModel.CanModify)
            .Select(x => x ? UITableViewCellAccessory.DisclosureIndicator : UITableViewCellAccessory.None)
            .Subscribe(x => MilestoneElement.Accessory = AssigneeElement.Accessory = LabelsElement.Accessory = x);

            DetailsSection.Add(MilestoneElement);
            DetailsSection.Add(AssigneeElement);
            DetailsSection.Add(LabelsElement);

            this.WhenAnyValue(x => x.ViewModel.Avatar)
            .SubscribeSafe(x => HeaderView.SetImage(x?.ToUri(128), Images.LoginUserUnknown));

            this.WhenAnyValue(x => x.ViewModel.Issue)
            .IsNotNull()
            .Subscribe(x => {
                HeaderView.Text    = x.Title;
                HeaderView.SubText = x.UpdatedAt.HasValue ?
                                     ("Updated " + x.UpdatedAt.Value.UtcDateTime.Humanize()) :
                                     ("Created " + x.CreatedAt.UtcDateTime.Humanize());
                RefreshHeaderView();
            });

            this.WhenAnyValue(x => x.ViewModel.MarkdownDescription)
            .Subscribe(x =>
            {
                if (string.IsNullOrEmpty(x))
                {
                    DetailsSection.Remove(DescriptionElement);
                }
                else
                {
                    var model    = new DescriptionModel(x, (int)UIFont.PreferredSubheadline.PointSize);
                    var markdown = new MarkdownView {
                        Model = model
                    };
                    var html = markdown.GenerateString();
                    DescriptionElement.Value = html;

                    if (!DetailsSection.Contains(DescriptionElement))
                    {
                        DetailsSection.Insert(0, UITableViewRowAnimation.Fade, DescriptionElement);
                    }
                }
            });

            CommentsSection.FooterView = new TableFooterButton("Add Comment", () => ViewModel.AddCommentCommand.ExecuteIfCan());

            this.WhenAnyValue(x => x.ViewModel.Events)
            .Select(x => x.Changed)
            .Switch()
            .Select(x => ViewModel.Events)
            .Subscribe(events =>
            {
                var comments = events.Select(x =>
                {
                    var body    = string.Empty;
                    var comment = x as IssueCommentItemViewModel;
                    var @event  = x as IssueEventItemViewModel;

                    if (comment != null)
                    {
                        body = comment.Comment;
                    }
                    else if (@event != null)
                    {
                        body = CreateEventBody(@event.EventInfo, @event.Commit);
                    }

                    return(new Comment(x.AvatarUrl.ToUri(), x.Actor, body, x.CreatedAt.Humanize()));
                })
                               .Where(x => !string.IsNullOrEmpty(x.Body))
                               .ToList();

                if (comments.Count > 0)
                {
                    var commentModel = new CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                    var razorView    = new CommentsView {
                        Model = commentModel
                    };
                    var html = razorView.GenerateString();
                    CommentsElement.Value = html;

                    if (!CommentsSection.Contains(CommentsElement))
                    {
                        CommentsSection.Insert(0, UITableViewRowAnimation.Fade, CommentsElement);
                    }
                }
                else
                {
                    CommentsSection.Remove(CommentsElement);
                }
            });

            var commentsButton     = SplitButton.AddButton("Comments", "-");
            var participantsButton = SplitButton.AddButton("Participants", "-");

            this.WhenAnyValue(x => x.ViewModel.CommentCount)
            .Subscribe(x => commentsButton.Text = x.ToString());

            this.WhenAnyValue(x => x.ViewModel.Participants)
            .Subscribe(x => participantsButton.Text = x.ToString());
        }
Пример #28
0
 void ReleaseDesignerOutlets()
 {
     if (CommentsView != null)
     {
         CommentsView.Dispose();
         CommentsView = null;
     }
     if (CommentTextBox != null)
     {
         CommentTextBox.Dispose();
         CommentTextBox = null;
     }
     if (CostLabel != null)
     {
         CostLabel.Dispose();
         CostLabel = null;
     }
     if (DateLabel != null)
     {
         DateLabel.Dispose();
         DateLabel = null;
     }
     if (DistanceLabel != null)
     {
         DistanceLabel.Dispose();
         DistanceLabel = null;
     }
     if (DriverLabel != null)
     {
         DriverLabel.Dispose();
         DriverLabel = null;
     }
     if (EndLabel != null)
     {
         EndLabel.Dispose();
         EndLabel = null;
     }
     if (FromLabel != null)
     {
         FromLabel.Dispose();
         FromLabel = null;
     }
     if (MakerLabel != null)
     {
         MakerLabel.Dispose();
         MakerLabel = null;
     }
     if (ModelLabel != null)
     {
         ModelLabel.Dispose();
         ModelLabel = null;
     }
     if (RateLabel != null)
     {
         RateLabel.Dispose();
         RateLabel = null;
     }
     if (ResumeView != null)
     {
         ResumeView.Dispose();
         ResumeView = null;
     }
     if (SegmentedControl != null)
     {
         SegmentedControl.Dispose();
         SegmentedControl = null;
     }
     if (StartLabel != null)
     {
         StartLabel.Dispose();
         StartLabel = null;
     }
     if (ToLabel != null)
     {
         ToLabel.Dispose();
         ToLabel = null;
     }
     if (VehicleImage != null)
     {
         VehicleImage.Dispose();
         VehicleImage = null;
     }
 }
Пример #29
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            var commentsElement = new HtmlElement("comments");

            commentsElement.UrlRequested = ViewModel.GoToUrlCommand.ExecuteIfCan;

            ViewModel.Comments.Changed
            .Select(_ => new Unit())
            .StartWith(new Unit())
            .Subscribe(x =>
            {
                var comments     = ViewModel.Comments.Select(c => new Comment(c.Avatar.ToUri(), c.Actor, c.Body, c.UtcCreatedAt.Humanize())).ToList();
                var commentModel = new CodeHub.WebViews.CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                var razorView    = new CommentsView {
                    Model = commentModel
                };
                var html = razorView.GenerateString();
                commentsElement.Value = html;

                if (commentsElement.GetRootElement() == null && ViewModel.Comments.Count > 0)
                {
                    _commentsSection.Add(commentsElement);
                }
                TableView.ReloadData();
            });

            ViewModel.WhenAnyValue(x => x.Commit).IsNotNull().Subscribe(commitModel =>
            {
                var detailSection = new Section();
                Root.Reset(_headerSection, detailSection);

                var user = commitModel.GenerateCommiterName();
                detailSection.Add(new MultilinedElement(user, commitModel.Commit.Message)
                {
                    CaptionColor    = Theme.MainTextColor,
                    ValueColor      = Theme.MainTextColor,
                    BackgroundColor = UIColor.White
                });

                if (ViewModel.ShowRepository)
                {
                    var repo = new StringElement(ViewModel.RepositoryName)
                    {
                        Font      = StringElement.DefaultDetailFont,
                        TextColor = StringElement.DefaultDetailColor,
                        Image     = Octicon.Repo.ToImage()
                    };
                    repo.Tapped += () => ViewModel.GoToRepositoryCommand.Execute(null);
                    detailSection.Add(repo);
                }

                var paths = commitModel.Files.GroupBy(y => {
                    var filename = "/" + y.Filename;
                    return(filename.Substring(0, filename.LastIndexOf("/", System.StringComparison.Ordinal) + 1));
                }).OrderBy(y => y.Key);

                foreach (var p in paths)
                {
                    var fileSection = new Section(p.Key);
                    foreach (var x in p)
                    {
                        var y       = x;
                        var file    = x.Filename.Substring(x.Filename.LastIndexOf('/') + 1);
                        var sse     = new ChangesetElement(file, x.Status, x.Additions, x.Deletions);
                        sse.Tapped += () => ViewModel.GoToFileCommand.Execute(y);
                        fileSection.Add(sse);
                    }
                    Root.Add(fileSection);
                }

                Root.Add(_commentsSection);
            });
        }
Пример #30
0
        public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            HeaderView.SetImage(null, Images.Avatar);

            var detailsSection   = new Section();
            var diffButton       = new ButtonElement(AtlassianIcon.ListAdd.ToImage());
            var removedButton    = new ButtonElement(AtlassianIcon.ListRemove.ToImage());
            var modifiedButton   = new ButtonElement(AtlassianIcon.Edit.ToImage());
            var allChangesButton = new ButtonElement("All Changes", AtlassianIcon.Devtoolssidediff.ToImage());

            detailsSection.Add(new [] { diffButton, removedButton, modifiedButton, allChangesButton });

            var additions = ViewModel.WhenAnyValue(x => x.DiffAdditions);

            diffButton.BindClick(ViewModel.GoToAddedFiles);
            diffButton.BindDisclosure(additions.Select(x => x > 0));
            diffButton.BindCaption(additions.Select(x => $"{x} Added"));

            var deletions = ViewModel.WhenAnyValue(x => x.DiffDeletions);

            removedButton.BindClick(ViewModel.GoToRemovedFiles);
            removedButton.BindDisclosure(deletions.Select(x => x > 0));
            removedButton.BindCaption(deletions.Select(x => $"{x} Removed"));

            var modifications = ViewModel.WhenAnyValue(x => x.DiffModifications);

            modifiedButton.BindClick(ViewModel.GoToModifiedFiles);
            modifiedButton.BindDisclosure(modifications.Select(x => x > 0));
            modifiedButton.BindCaption(modifications.Select(x => $"{x} Modified"));

            allChangesButton.BindClick(ViewModel.GoToAllFiles);

            var split         = new SplitButtonElement();
            var commentCount  = split.AddButton("Comments", "-");
            var participants  = split.AddButton("Participants", "-");
            var approvals     = split.AddButton("Approvals", "-");
            var headerSection = new Section {
                split
            };

            var actionButton = new UIBarButtonItem(UIBarButtonSystemItem.Action);

            NavigationItem.RightBarButtonItem = actionButton;

            var detailSection  = new Section();
            var detailsElement = new MultilinedElement();

            detailSection.Add(detailsElement);

            var approvalSection = new Section("Approvals");
            var approveElement  = new LoaderButtonElement("Approve", AtlassianIcon.Approve.ToImage());

            approveElement.Accessory = UITableViewCellAccessory.None;
            approveElement.BindLoader(ViewModel.ToggleApproveButton);
            approveElement.BindCaption(ViewModel.WhenAnyValue(x => x.Approved).Select(x => x ? "Unapprove" : "Approve"));

            var commentsSection   = new Section("Comments");
            var addCommentElement = new ButtonElement("Add Comment", AtlassianIcon.Addcomment.ToImage());

            commentsSection.Add(addCommentElement);

            if (ViewModel.ShowRepository)
            {
                var repo = new ButtonElement(ViewModel.Repository)
                {
                    TextColor = StringElement.DefaultDetailColor,
                    Image     = AtlassianIcon.Devtoolsrepository.ToImage()
                };

                detailSection.Add(repo);
                repo.Clicked.SelectUnit().BindCommand(ViewModel.GoToRepositoryCommand);
            }

            ViewModel.WhenAnyValue(x => x.Commit).Where(x => x != null).Subscribe(x => {
                participants.Text = x?.Participants?.Count.ToString() ?? "-";
                approvals.Text    = x?.Participants?.Count(y => y.Approved).ToString() ?? "-";

                var titleMsg  = (ViewModel.Commit.Message ?? string.Empty).Split(new [] { '\n' }, 2).FirstOrDefault();
                var avatarUrl = ViewModel.Commit.Author?.User?.Links?.Avatar?.Href;

                HeaderView.SubText = titleMsg ?? "Commited " + (ViewModel.Commit.Date).Humanize();
                HeaderView.SetImage(new Avatar(avatarUrl).ToUrl(128), Images.Avatar);
                RefreshHeaderView();

                var user = x.Author?.User?.DisplayName ?? x.Author?.Raw ?? "Unknown";
                detailsElement.Caption = user;
                detailsElement.Details = x.Message;
            });

            this.WhenAnyValue(x => x.ViewModel.Approvals)
            .Select(x => x.Select(y => new UserElement(y)).OfType <Element>())
            .Subscribe(x => approvalSection.Reset(x.Concat(new[] { approveElement })));

            ViewModel.Comments
            .CountChanged
            .Select(x => x.ToString())
            .StartWith("-")
            .Subscribe(x => commentCount.Text = x);

            ViewModel
            .Comments
            .ChangedObservable()
            .Subscribe(x =>
            {
                if (x.Count > 0)
                {
                    var comments     = x.Select(y => new Comment(y.Avatar.ToUrl(), y.Name, y.Content, y.CreatedOn)).ToList();
                    var commentModel = new Views.CommentModel(comments, (int)UIFont.PreferredSubheadline.PointSize);
                    var content      = new CommentsView {
                        Model = commentModel
                    }.GenerateString();
                    _commentsElement.SetValue(content);
                    commentsSection.Insert(0, UITableViewRowAnimation.None, _commentsElement);
                }
                else
                {
                    commentsSection.Remove(_commentsElement);
                }
            });

            ViewModel.WhenAnyValue(x => x.Commit)
            .Where(x => x != null)
            .Take(1)
            .Subscribe(_ => Root.Reset(headerSection, detailsSection, approvalSection, commentsSection));

            ViewModel.GoToAddedFiles.Select(_ => CommitFileType.Added).Subscribe(GoToFiles);
            ViewModel.GoToRemovedFiles.Select(_ => CommitFileType.Removed).Subscribe(GoToFiles);
            ViewModel.GoToModifiedFiles.Select(_ => CommitFileType.Modified).Subscribe(GoToFiles);
            ViewModel.GoToAllFiles.Subscribe(_ => GoToAllFiles());

            OnActivation(d =>
            {
                actionButton
                .GetClickedObservable()
                .Select(x => (object)x)
                .BindCommand(ViewModel.ShowMenuCommand)
                .AddTo(d);

                addCommentElement
                .Clicked
                .SelectUnit()
                .BindCommand(ViewModel.AddCommentCommand)
                .AddTo(d);

                this.WhenAnyObservable(x => x.ViewModel.AddCommentCommand)
                .Subscribe(_ => NewCommentViewController.Present(this, ViewModel.AddComment))
                .AddTo(d);
            });
        }