< Summary

Information
Class: MyNet.Observable.CultureBoundValue<T>
Assembly: MyNet.Observable
File(s): https://raw.githubusercontent.com/sandre58/MyNet/85372080fe102cd9ee155ceab49ae000e7f66103/src/MyNet.Observable/Base/CultureBoundValue.cs
Tag: 323_28699572109
Line coverage
94%
Covered lines: 17
Uncovered lines: 1
Coverable lines: 18
Total lines: 75
Line coverage: 94.4%
Branch coverage
60%
Covered branches: 6
Total branches: 10
Branch coverage: 60%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity Line coverage
.ctor(...)100%11100%
.ctor(...)50%44100%
get_Value()100%11100%
OnEvent(...)100%11100%
ToString()0%620%
GetOrCompute()100%44100%

File(s)

https://raw.githubusercontent.com/sandre58/MyNet/85372080fe102cd9ee155ceab49ae000e7f66103/src/MyNet.Observable/Base/CultureBoundValue.cs

#LineLine coverage
 1// -----------------------------------------------------------------------
 2// <copyright file="CultureBoundValue.cs" company="Stéphane ANDRE">
 3// Copyright (c) Stéphane ANDRE. All rights reserved.
 4// </copyright>
 5// -----------------------------------------------------------------------
 6
 7using System;
 8using System.Globalization;
 9using MyNet.Globalization.Culture;
 10using MyNet.Globalization.Facade;
 11using MyNet.Observable.Behaviors.Metadata.Features.Events;
 12using MyNet.Observable.Metadata;
 13
 14#pragma warning disable IDE0130 // Namespace does not match folder structure
 15namespace MyNet.Observable;
 16#pragma warning restore IDE0130 // Namespace does not match folder structure
 17
 18/// <summary>
 19/// Observable value recomputed when the application culture changes, with per-culture caching.
 20/// </summary>
 21[ExemptFromGeneratedMetadata]
 22public class CultureBoundValue<T> : ObservableObject, IObservableValue<T>, IEventAware<CultureChangedEvent>
 23{
 24    private readonly Func<T?> _valueFactory;
 25    private readonly ICultureService _cultureService;
 26    private CultureInfo? _cachedCulture;
 27    private T? _cachedValue;
 28    private bool _hasCachedValue;
 29
 30    /// <summary>
 31    /// Initializes a new instance of the <see cref="CultureBoundValue{T}"/> class that uses <see cref="GlobalizationSer
 32    /// </summary>
 33    /// <param name="valueFactory">Factory invoked when the value must be computed for the current culture.</param>
 34    public CultureBoundValue(Func<T?> valueFactory)
 24635        : this(valueFactory, GlobalizationServices.Current) { }
 36
 37    /// <summary>
 38    /// Initializes a new instance of the <see cref="CultureBoundValue{T}"/> class with an explicit culture service.
 39    /// </summary>
 40    /// <param name="valueFactory">Factory invoked when the value must be computed for the current culture.</param>
 41    /// <param name="cultureService">Culture service used to detect culture changes.</param>
 14442    public CultureBoundValue(Func<T?> valueFactory, ICultureService cultureService)
 43    {
 14444        _valueFactory = valueFactory ?? throw new ArgumentNullException(nameof(valueFactory));
 14445        _cultureService = cultureService ?? throw new ArgumentNullException(nameof(cultureService));
 14446        this.ReactOnCultureChanged(cultureService);
 14447    }
 48
 49    /// <inheritdoc />
 16250    public virtual T? Value => GetOrCompute();
 51
 52    /// <inheritdoc />
 53    public virtual void OnEvent(CultureChangedEvent e)
 54    {
 13555        _hasCachedValue = false;
 13556        NotifyPropertyChanged(nameof(Value));
 13557    }
 58
 59    /// <inheritdoc />
 060    public override string? ToString() => Value?.ToString();
 61
 62    private T? GetOrCompute()
 63    {
 16264        var culture = _cultureService.CurrentCulture;
 65
 16266        if (_hasCachedValue && Equals(_cachedCulture, culture))
 3067            return _cachedValue;
 68
 13269        _cachedCulture = culture;
 13270        _cachedValue = _valueFactory();
 13271        _hasCachedValue = true;
 13272        return _cachedValue;
 73    }
 74}
 75