public override void ViewDidLoad()
        {
            base.ViewDidLoad();

            AddProjectBubbleLabel.Text = Resources.AddProjectBubbleText;

            prepareViews();
            prepareOnboarding();

            var source = new StartTimeEntryTableViewSource(SuggestionsTableView);

            SuggestionsTableView.Source = source;

            source.Rx().ModelSelected()
            .Subscribe(ViewModel.SelectSuggestion.Inputs)
            .DisposedBy(DisposeBag);

            ViewModel.Suggestions
            .Subscribe(SuggestionsTableView.Rx().ReloadSections(source))
            .DisposedBy(DisposeBag);

            source.ToggleTasks
            .Subscribe(ViewModel.ToggleTasks.Inputs)
            .DisposedBy(DisposeBag);

            TimeInput.Rx().Duration()
            .Subscribe(ViewModel.SetRunningTime.Inputs)
            .DisposedBy(DisposeBag);

            //Text

            ViewModel.DisplayedTime
            .Subscribe(TimeLabel.Rx().Text())
            .DisposedBy(DisposeBag);

            Placeholder.Text = ViewModel.PlaceholderText;

            // Buttons
            UIColor booleanToColor(bool b) => b
                ? Colors.StartTimeEntry.ActiveButton.ToNativeColor()
                : Colors.StartTimeEntry.InactiveButton.ToNativeColor();

            ViewModel.IsBillable
            .Select(booleanToColor)
            .Subscribe(BillableButton.Rx().TintColor())
            .DisposedBy(DisposeBag);

            ViewModel.IsSuggestingTags
            .Select(booleanToColor)
            .Subscribe(TagsButton.Rx().TintColor())
            .DisposedBy(DisposeBag);

            ViewModel.IsSuggestingProjects
            .Select(booleanToColor)
            .Subscribe(ProjectsButton.Rx().TintColor())
            .DisposedBy(DisposeBag);

            //Visibility
            ViewModel.IsBillableAvailable
            .Select(b => b ? (nfloat)42 : 0)
            .Subscribe(BillableButtonWidthConstraint.Rx().Constant())
            .DisposedBy(DisposeBag);

            // Actions
            CloseButton.Rx().Tap()
            .Subscribe(ViewModel.CloseWithDefaultResult)
            .DisposedBy(DisposeBag);

            DoneButton.Rx()
            .BindAction(ViewModel.Done)
            .DisposedBy(DisposeBag);

            ViewModel.Done.Elements
            .Subscribe(IosDependencyContainer.Instance.IntentDonationService.DonateStartTimeEntry)
            .DisposedBy(DisposeBag);

            BillableButton.Rx()
            .BindAction(ViewModel.ToggleBillable)
            .DisposedBy(DisposeBag);

            StartDateButton.Rx()
            .BindAction(ViewModel.SetStartDate)
            .DisposedBy(DisposeBag);

            DateTimeButton.Rx()
            .BindAction(ViewModel.ChangeTime)
            .DisposedBy(DisposeBag);

            TagsButton.Rx()
            .BindAction(ViewModel.ToggleTagSuggestions)
            .DisposedBy(DisposeBag);

            ProjectsButton.Rx()
            .BindAction(ViewModel.ToggleProjectSuggestions)
            .DisposedBy(DisposeBag);

            // Reactive
            ViewModel.TextFieldInfo
            .DistinctUntilChanged()
            .Subscribe(onTextFieldInfo)
            .DisposedBy(DisposeBag);

            DescriptionTextView.Rx().AttributedText()
            .Select(attributedString => attributedString.Length == 0)
            .Subscribe(isDescriptionEmptySubject)
            .DisposedBy(DisposeBag);

            Observable.CombineLatest(
                DescriptionTextView.Rx().AttributedText().SelectUnit(),
                DescriptionTextView.Rx().CursorPosition().SelectUnit()
                )
            .Select(_ => DescriptionTextView.AttributedText)     // Programatically changing the text doesn't send an event, that's why we do this, to get the last version of the text
            .Do(updatePlaceholder)
            .Select(text => text.AsSpans((int)DescriptionTextView.SelectedRange.Location).ToIImmutableList())
            .Subscribe(ViewModel.SetTextSpans.Inputs)
            .DisposedBy(DisposeBag);
        }