예제 #1
0
        public EditTimeEntryViewModel(
            ITimeService timeService,
            ITogglDataSource dataSource,
            ISyncManager syncManager,
            IInteractorFactory interactorFactory,
            IMvxNavigationService navigationService,
            IOnboardingStorage onboardingStorage,
            IDialogService dialogService,
            IAnalyticsService analyticsService,
            IStopwatchProvider stopwatchProvider,
            IRxActionFactory actionFactory,
            ISchedulerProvider schedulerProvider)
        {
            Ensure.Argument.IsNotNull(dataSource, nameof(dataSource));
            Ensure.Argument.IsNotNull(syncManager, nameof(syncManager));
            Ensure.Argument.IsNotNull(timeService, nameof(timeService));
            Ensure.Argument.IsNotNull(dialogService, nameof(dialogService));
            Ensure.Argument.IsNotNull(interactorFactory, nameof(interactorFactory));
            Ensure.Argument.IsNotNull(onboardingStorage, nameof(onboardingStorage));
            Ensure.Argument.IsNotNull(navigationService, nameof(navigationService));
            Ensure.Argument.IsNotNull(analyticsService, nameof(analyticsService));
            Ensure.Argument.IsNotNull(stopwatchProvider, nameof(stopwatchProvider));
            Ensure.Argument.IsNotNull(schedulerProvider, nameof(schedulerProvider));
            Ensure.Argument.IsNotNull(actionFactory, nameof(actionFactory));

            this.dataSource        = dataSource;
            this.syncManager       = syncManager;
            this.timeService       = timeService;
            this.dialogService     = dialogService;
            this.interactorFactory = interactorFactory;
            this.navigationService = navigationService;
            this.analyticsService  = analyticsService;
            this.stopwatchProvider = stopwatchProvider;
            this.schedulerProvider = schedulerProvider;
            this.actionFactory     = actionFactory;
            OnboardingStorage      = onboardingStorage;

            workspaceIdSubject
            .Where(id => id.HasValue)
            .Subscribe(id => workspaceId = id.Value)
            .DisposedBy(disposeBag);

            isEditingDescriptionSubject = new BehaviorSubject <bool>(false);
            Description = new BehaviorRelay <string>(string.Empty, CommonFunctions.Trim);

            projectClientTaskSubject = new BehaviorSubject <ProjectClientTaskInfo>(ProjectClientTaskInfo.Empty);
            ProjectClientTask        = projectClientTaskSubject
                                       .AsDriver(ProjectClientTaskInfo.Empty, schedulerProvider);

            IsBillableAvailable = workspaceIdSubject
                                  .Where(id => id.HasValue)
                                  .SelectMany(workspaceId => interactorFactory.IsBillableAvailableForWorkspace(workspaceId.Value).Execute())
                                  .DistinctUntilChanged()
                                  .AsDriver(false, schedulerProvider);

            isBillableSubject = new BehaviorSubject <bool>(false);
            IsBillable        = isBillableSubject
                                .DistinctUntilChanged()
                                .AsDriver(false, schedulerProvider);

            startTimeSubject = new BehaviorSubject <DateTimeOffset>(DateTimeOffset.UtcNow);
            var startTimeObservable = startTimeSubject.DistinctUntilChanged();

            StartTime = startTimeObservable
                        .AsDriver(default(DateTimeOffset), schedulerProvider);

            var now = timeService.CurrentDateTimeObservable.StartWith(timeService.CurrentDateTime);

            durationSubject = new ReplaySubject <TimeSpan?>(bufferSize: 1);
            Duration        =
                durationSubject
                .Select(duration
                        => duration.HasValue
                            ? Observable.Return(duration.Value)
                            : now.CombineLatest(
                            startTimeObservable,
                            (currentTime, startTime) => currentTime - startTime))
                .Switch()
                .DistinctUntilChanged()
                .AsDriver(TimeSpan.Zero, schedulerProvider);

            var stopTimeObservable = Observable.CombineLatest(startTimeObservable, durationSubject, calculateStopTime)
                                     .DistinctUntilChanged();

            StopTime = stopTimeObservable
                       .AsDriver(null, schedulerProvider);

            var isTimeEntryRunningObservable = stopTimeObservable
                                               .Select(stopTime => !stopTime.HasValue)
                                               .Do(value => isRunning = value)
                                               .DistinctUntilChanged();

            IsTimeEntryRunning = isTimeEntryRunningObservable
                                 .AsDriver(false, schedulerProvider);

            tagsSubject = new BehaviorSubject <IEnumerable <IThreadSafeTag> >(Enumerable.Empty <IThreadSafeTag>());
            Tags        = tagsSubject
                          .Select(tags => tags.Select(ellipsize).ToImmutableList())
                          .AsDriver(ImmutableList <string> .Empty, schedulerProvider);

            isInaccessibleSubject = new BehaviorSubject <bool>(false);
            IsInaccessible        = isInaccessibleSubject
                                    .DistinctUntilChanged()
                                    .AsDriver(false, schedulerProvider);

            syncErrorMessageSubject = new BehaviorSubject <string>(string.Empty);
            SyncErrorMessage        = syncErrorMessageSubject
                                      .Select(error => error ?? string.Empty)
                                      .DistinctUntilChanged()
                                      .AsDriver(string.Empty, schedulerProvider);

            IsSyncErrorMessageVisible = syncErrorMessageSubject
                                        .Select(error => !string.IsNullOrEmpty(error))
                                        .DistinctUntilChanged()
                                        .AsDriver(false, schedulerProvider);

            Preferences = interactorFactory.GetPreferences().Execute()
                          .AsDriver(null, schedulerProvider);

            // Actions
            Close                   = actionFactory.FromAsync(closeWithConfirmation);
            SelectProject           = actionFactory.FromAsync(selectProject);
            SelectTags              = actionFactory.FromAsync(selectTags);
            ToggleBillable          = actionFactory.FromAction(toggleBillable);
            EditTimes               = actionFactory.FromAsync <EditViewTapSource>(editTimes);
            SelectStartDate         = actionFactory.FromAsync(selectStartDate);
            StopTimeEntry           = actionFactory.FromAction(stopTimeEntry, isTimeEntryRunningObservable);
            DismissSyncErrorMessage = actionFactory.FromAction(dismissSyncErrorMessage);
            Save   = actionFactory.FromAsync(save);
            Delete = actionFactory.FromAsync(delete);
        }