Kategorie

This commit is contained in:
Meik
2025-11-11 19:43:15 +01:00
parent dc3e8a2e4c
commit 05fb34815a
27 changed files with 1832 additions and 1109 deletions

View File

@@ -1051,11 +1051,7 @@
<xs:element name="State-Link" substitutionGroup="State">
<xs:complexType>
<xs:complexContent>
<xs:extension base="State">
<xs:attribute name="Reference" type="xs:string" />
</xs:extension>
</xs:complexContent>
<xs:attribute name="Reference" type="xs:string" />
</xs:complexType>
</xs:element>

File diff suppressed because it is too large Load Diff

View File

@@ -230,9 +230,6 @@ namespace FasdDesktopUi.Basics.Models
Dispatcher.CurrentDispatcher.Invoke(() => splashScreen?.SetStatusText(cMultiLanguageSupport.GetItem("StartUp.SplashScreen.AuthenticateUser")));
ApiConnectionStatus = enumOnlineStatus.unauthorized;
const string cockpitUserRole = "Cockpit.User";
#if isNewFeature
const string cockpitTicketAgentRole = "Cockpit.TicketAgent";
#endif
userInfo = await cFasdCockpitCommunicationBase.Instance.WinLogon();
lock (cFasdCockpitCommunicationBase.CockpitUserInfoLock)
{
@@ -247,10 +244,6 @@ namespace FasdDesktopUi.Basics.Models
{
await Task.Run(async () => await cFasdCockpitConfig.Instance.InstantiateAnalyticsAsync(cFasdCockpitConfig.SessionId));
ApiConnectionStatus = enumOnlineStatus.online;
#if isNewFeature
if (userInfo.Roles.Contains(cockpitTicketAgentRole))
cCockpitConfiguration.Instance.ticketSupport.EditTicket = true;
#endif
}
}
}

View File

@@ -0,0 +1,174 @@
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
namespace FasdDesktopUi.Basics.Models
{
public class HierarchicalSelectionItem : INotifyPropertyChanged
{
private bool _isExpanded;
public string Id { get; set; }
public string DisplayName { get; set; }
public string ParentId { get; set; }
public string ParentDisplayName { get; set; }
public ObservableCollection<HierarchicalSelectionItem> Children { get; } = new ObservableCollection<HierarchicalSelectionItem>();
public HierarchicalSelectionItem Parent { get; private set; }
public bool IsExpanded
{
get => _isExpanded;
set
{
if (_isExpanded == value)
return;
_isExpanded = value;
OnPropertyChanged(nameof(IsExpanded));
}
}
public string FullPath
{
get
{
if (Parent == null || string.IsNullOrWhiteSpace(Parent.DisplayName))
return DisplayName ?? string.Empty;
if (string.IsNullOrWhiteSpace(DisplayName))
return Parent.FullPath;
return $"{Parent.FullPath} / {DisplayName}";
}
}
public event PropertyChangedEventHandler PropertyChanged;
protected void OnPropertyChanged(string propertyName) =>
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
public void AddChild(HierarchicalSelectionItem child)
{
if (child == null)
return;
child.Parent = this;
Children.Add(child);
}
public void ClearChildren()
{
foreach (var child in Children)
child.Parent = null;
Children.Clear();
}
public void SortChildrenRecursive()
{
if (Children == null || Children.Count == 0)
return;
var orderedChildren = Children
.OrderBy(child => child.DisplayName, StringComparer.CurrentCultureIgnoreCase)
.ToList();
Children.Clear();
foreach (var child in orderedChildren)
{
Children.Add(child);
child.SortChildrenRecursive();
}
}
public IEnumerable<HierarchicalSelectionItem> SelfAndDescendants()
{
yield return this;
foreach (var child in Children)
{
foreach (var descendant in child.SelfAndDescendants())
yield return descendant;
}
}
public void SetExpandedRecursive(bool isExpanded)
{
IsExpanded = isExpanded;
foreach (var child in Children)
child.SetExpandedRecursive(isExpanded);
}
public HierarchicalSelectionItem CloneWithoutChildren()
{
return new HierarchicalSelectionItem
{
Id = Id,
DisplayName = DisplayName,
ParentId = ParentId,
ParentDisplayName = ParentDisplayName
};
}
public HierarchicalSelectionItem CloneBranch(Func<HierarchicalSelectionItem, bool> predicate)
{
bool matches = predicate?.Invoke(this) ?? true;
var matchingChildren = new List<HierarchicalSelectionItem>();
foreach (var child in Children)
{
var childClone = child.CloneBranch(predicate);
if (childClone != null)
matchingChildren.Add(childClone);
}
if (!matches && matchingChildren.Count == 0)
return null;
var clone = CloneWithoutChildren();
foreach (var childClone in matchingChildren)
clone.AddChild(childClone);
return clone;
}
public static ObservableCollection<HierarchicalSelectionItem> BuildTree(IEnumerable<HierarchicalSelectionItem> items)
{
if (items == null)
return new ObservableCollection<HierarchicalSelectionItem>();
var lookup = items
.Where(item => !string.IsNullOrWhiteSpace(item?.Id))
.GroupBy(item => item.Id)
.Select(group => group.First())
.ToDictionary(item => item.Id);
foreach (var entry in lookup.Values)
entry.ClearChildren();
var roots = new List<HierarchicalSelectionItem>();
foreach (var item in lookup.Values)
{
if (!string.IsNullOrWhiteSpace(item.ParentId) && lookup.TryGetValue(item.ParentId, out var parent))
{
parent.AddChild(item);
}
else
{
item.Parent = null;
roots.Add(item);
}
}
foreach (var root in roots)
root.SortChildrenRecursive();
return new ObservableCollection<HierarchicalSelectionItem>(
roots.OrderBy(root => root.DisplayName, StringComparer.CurrentCultureIgnoreCase));
}
}
}

View File

@@ -48,13 +48,12 @@ namespace FasdDesktopUi.Basics.Models
try
{
IRawValueFormatter formatter = new RawValueFormatter();
formatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
cUtility.RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
var outputTable = dataProvider.HealthCardDataHelper.HealthCardRawData.GetTableByName(valueAdress.ValueTable, true);
if (outputTable != null)
if (outputTable.Columns.TryGetValue(valueAdress.ValueColumn, out var outpuColumn))
output = formatter.GetDisplayValue(outpuColumn.Values[valueAdress.DayIndex], display);
output = cUtility.RawValueFormatter.GetDisplayValue(outpuColumn.Values[valueAdress.DayIndex], display);
}
catch (Exception E)
{

View File

@@ -15,7 +15,6 @@ namespace FasdDesktopUi.Basics.Services.ProtocollService
{
private readonly cFasdQuickAction _quickActionDefinition;
private readonly cQuickActionCopyData _quickActionCopyData;
private readonly IRawValueFormatter _rawValueFormatter = new RawValueFormatter();
const string AsciiSeperator = "\n\n";
@@ -261,18 +260,18 @@ namespace FasdDesktopUi.Basics.Services.ProtocollService
output += AsciiSeperator + cMultiLanguageSupport.GetItem("QuickAction.Copy.Measure");
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
cUtility.RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
foreach (var measureValue in measureValues)
{
try
{
string value = _rawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = _rawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string value = cUtility.RawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = cUtility.RawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string difference = string.Empty;
if (measureValue.Difference != null)
difference = $" (∆ {_rawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
difference = $" (∆ {cUtility.RawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
output += "\n" + measureValue.Names.GetValue(cF4SDCockpitXmlConfig.Instance.HealthCardConfig.ProtocollLanguage) + ": " + value + " ➜ " + postValue + difference;
}
@@ -475,18 +474,18 @@ namespace FasdDesktopUi.Basics.Services.ProtocollService
output += "<p>" + cMultiLanguageSupport.GetItem("QuickAction.Copy.Measure.Html") + "</p>";
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
cUtility.RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
foreach (var measureValue in measureValues)
{
try
{
string value = _rawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = _rawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string value = cUtility.RawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = cUtility.RawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string difference = string.Empty;
if (measureValue.Difference != null)
difference = $" (∆ {_rawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
difference = $" (∆ {cUtility.RawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
output += "<p>";
output += "<b>" + measureValue.Names.GetValue(cF4SDCockpitXmlConfig.Instance.HealthCardConfig.ProtocollLanguage) + ": </b>" + value + " ➜ " + postValue + difference;

View File

@@ -41,7 +41,7 @@ namespace FasdDesktopUi.Basics.Services.RelationService
stagedRelations.MergeAsRelationInfosWith(relatedTo);
_relations = _relations.Union(stagedRelations.Relations);
RelationsFound?.Invoke(this, new StagedSearchResultRelationsEventArgs() { RelatedTo = relatedTo, StagedResultRelations = stagedRelations });
RelationsFound?.Invoke(this, new StagedSearchResultRelationsEventArgs() { RelatedTo = relatedTo, StagedResultRelations = stagedRelations, RelationService = this });
if (stagedRelations?.IsComplete ?? false)
break;

View File

@@ -12,7 +12,7 @@ namespace FasdDesktopUi.Basics.Services.SupportCase
private static ISupportCase Create(cF4sdIdentityEntry primaryIdentity, IRelationService relationService, cSupportCaseDataProvider supportCaseDataProvider)
{
SupportCase supportCase = new SupportCase(primaryIdentity.Id, relationService.Clone(), supportCaseDataProvider);
SupportCase supportCase = new SupportCase(primaryIdentity.Id, relationService, supportCaseDataProvider);
_supportCases.Add(primaryIdentity.Id, supportCase);
supportCase.Initialize();
return supportCase;

View File

@@ -3,9 +3,6 @@ using C4IT.FASD.Cockpit.Communication;
using FasdDesktopUi.Basics.Services.RelationService;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using static C4IT.Logging.cLogManager;
@@ -19,12 +16,6 @@ namespace FasdDesktopUi.Basics.Services.SupportCaseSearchService
public SupportCaseSearchService(IRelationService relationService)
{
_relationService = relationService;
_relationService.RelationsFound += HandleRelationsFound;
}
~SupportCaseSearchService()
{
_relationService.RelationsFound -= HandleRelationsFound;
}
public static async Task<cFasdApiSearchResultCollection> GetSearchResultsAsync(string searchQuery, CancellationToken token = default)
@@ -53,12 +44,18 @@ namespace FasdDesktopUi.Basics.Services.SupportCaseSearchService
}
public async Task<cF4sdStagedSearchResultRelationTaskId> LoadRelationsAsync(IEnumerable<cFasdApiSearchResultEntry> relatedTo, CancellationToken token = default)
=> await _relationService.LoadRelationsAsync(relatedTo, token);
{
IRelationService relationService = _relationService.Clone();
relationService.RelationsFound += HandleRelationsFound;
return await relationService.LoadRelationsAsync(relatedTo, token);
}
private void HandleRelationsFound(object sender, StagedSearchResultRelationsEventArgs e)
{
e.RelationService = _relationService;
RelationsFound.Invoke(this, e);
if (e.StagedResultRelations.IsComplete)
e.RelationService.RelationsFound -= HandleRelationsFound;
}
public event EventHandler<StagedSearchResultRelationsEventArgs> RelationsFound;

View File

@@ -476,8 +476,8 @@ namespace FasdDesktopUi.Basics
return false;
}
var slimPageData = await HealthCardDataHelper.GetSlimPageDataAsync();
var detailsPageData = await HealthCardDataHelper.GetDetailsPageDataAsync();
var slimPageData = await HealthCardDataHelper.SlimCard.GetDataAsync();
var detailsPageData = await HealthCardDataHelper.DetailPage.GetDataAsync();
slimPage?.SetPropertyValues(slimPageData);
detailsPage?.SetPropertyValues(detailsPageData);

View File

@@ -326,8 +326,7 @@ namespace FasdDesktopUi.Basics.UiActions
shouldHideRow = true;
}
IRawValueFormatter rawValueFormatter = new RawValueFormatter();
rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
cUtility.RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
foreach (var index in rawColumnIndexes)
{
@@ -352,7 +351,7 @@ namespace FasdDesktopUi.Basics.UiActions
if (detailsRow[timeColumnIndex] is DateTime timeColumnValue)
ProcessDetailValue(valueProcessingsEnumerator.Current, ref rawDetailValue, timeColumnValue);
var displayValue = rawValueFormatter.GetDisplayValue(rawDetailValue, displayTypeEnumerator.Current);
var displayValue = cUtility.RawValueFormatter.GetDisplayValue(rawDetailValue, displayTypeEnumerator.Current);
displayValuesOfRow.Add(displayValue);
}
catch (Exception E)

View File

@@ -184,17 +184,17 @@ namespace FasdDesktopUi.Basics.UiActions
if (result != null && result[0].Equals(cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError")))
{
CancelRunningActionSteps();
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}
if (token.IsCancellationRequested)
{
CancelRunningActionSteps();
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
catch (Exception E)
{

View File

@@ -41,11 +41,11 @@ namespace FasdDesktopUi.Basics.UiActions
detailedData.FullDetailedData = new List<object>()
{
new List<object>() { "Status", cMultiLanguageSupport.GetItem("QuickAction.Revision.ExecutionTime")},
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddMinutes(-5), RawValueType.DATETIME)},
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddMinutes(-38), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddHours(-2).AddMinutes(12), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddDays(-1).AddHours(4).AddMinutes(-32), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddDays(-1).AddHours(4).AddMinutes(-34), RawValueType.DATETIME) }
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddMinutes(-5), RawValueType.DATETIME)},
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddMinutes(-38), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddHours(-2).AddMinutes(12), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddDays(-1).AddHours(4).AddMinutes(-32), RawValueType.DATETIME) },
new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow.AddDays(-1).AddHours(4).AddMinutes(-34), RawValueType.DATETIME) }
};
//Get Process Steps of Action
@@ -141,7 +141,7 @@ namespace FasdDesktopUi.Basics.UiActions
_msg = cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull");
}
return new List<object>() { _msg, _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { _msg, cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}
}

View File

@@ -35,7 +35,7 @@ namespace FasdDesktopUi.Basics.UiActions
public override async Task<List<object>> ProcessActionAsync(CancellationToken token, Dictionary<cAdjustableParameter, object> ParameterDictionary = null)
{
await Task.CompletedTask;
List<object> result = new List<object> { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
List<object> result = new List<object> { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return result;
}

View File

@@ -176,7 +176,7 @@ namespace FasdDesktopUi.Basics.UiActions
break;
}
output = new List<object>() { quickActionStatus, _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
output = new List<object>() { quickActionStatus, cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
else
{
@@ -196,7 +196,7 @@ namespace FasdDesktopUi.Basics.UiActions
cQuickActionCopyData copyData = QuickActionProtocollEntry.GetCopyData(LocalQuickAction, DataProvider, false, protocollOutput, StatusMonitor.MeasureValues);
F4SDProtocoll.Instance.Add(new QuickActionProtocollEntry(LocalQuickAction, copyData));
output = new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
output = new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
_ = Task.Run(async () =>
@@ -239,7 +239,7 @@ namespace FasdDesktopUi.Basics.UiActions
catch (Exception E)
{
LogException(E);
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}
}

View File

@@ -102,7 +102,7 @@ namespace FasdDesktopUi.Basics.UiActions
cQuickActionStatusMonitorModel.cQuickActionStep.SetQuickActionStepStatuses(StatusMonitor.QuickActionData.ActionSteps, LocalQuickAction.Name, cQuickActionStatusMonitorModel.cQuickActionStep.enumActionStepType.main, enumQuickActionRevisionStatus.canceled);
cQuickActionStatusMonitorModel.cQuickActionStep.SetQuickActionStepStatuses(StatusMonitor.QuickActionData.ActionSteps, LocalQuickAction.Name, cQuickActionStatusMonitorModel.cQuickActionStep.enumActionStepType.running, enumQuickActionRevisionStatus.canceled);
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
cQuickActionOutput quickActionOutput = new cQuickActionOutputSingle(new cF4sdQuickActionRevision.cOutput() { ResultCode = enumQuickActionSuccess.unknown }); ;
@@ -127,7 +127,7 @@ namespace FasdDesktopUi.Basics.UiActions
cQuickActionCopyData copyData = QuickActionProtocollEntry.GetCopyData(LocalQuickAction, DataProvider, false, protocollOutput, StatusMonitor.MeasureValues);
F4SDProtocoll.Instance.Add(new QuickActionProtocollEntry(LocalQuickAction, copyData));
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedSuccessfull"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
else
{
@@ -145,13 +145,13 @@ namespace FasdDesktopUi.Basics.UiActions
F4SDProtocoll.Instance.Add(new QuickActionProtocollEntry(LocalQuickAction, copyData));
cMultiLanguageSupport.CurrentLanguage = tempLang;
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}
catch (Exception E)
{
LogException(E);
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
finally
{

View File

@@ -28,8 +28,6 @@ namespace FasdDesktopUi.Basics.UiActions
{
private readonly bool shouldRunImmidiate = false;
protected readonly IRawValueFormatter _rawValueFormatter = new RawValueFormatter();
public cFasdQuickAction QuickActionConfig { get; private set; }
public cSupportCaseDataProvider DataProvider { get; set; }
@@ -46,7 +44,7 @@ namespace FasdDesktopUi.Basics.UiActions
if (QuickActionConfig is null)
return;
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
cUtility.RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
shouldRunImmidiate = QuickActionConfig.RunImmediate;
Description = QuickActionConfig.Descriptions?.GetValue(Default: null);

View File

@@ -64,7 +64,7 @@ namespace FasdDesktopUi.Basics.UiActions
var quickActionHistory = await dataProvider.QuickActionProtocollHelper.GetQuickActionHistoryAsync(RemoteQuickAction.Name);
foreach (var quickActionLine in quickActionHistory)
{
quickActionLine[1] = _rawValueFormatter.GetDisplayValue(quickActionLine[1], RawValueType.DATETIME);
quickActionLine[1] = cUtility.RawValueFormatter.GetDisplayValue(quickActionLine[1], RawValueType.DATETIME);
detailedData.FullDetailedData.Add(quickActionLine);
}
}
@@ -157,7 +157,7 @@ namespace FasdDesktopUi.Basics.UiActions
cQuickActionCopyData copyData = QuickActionProtocollEntry.GetCopyData(RemoteQuickAction, DataProvider, true, protocollOutput, StatusMonitor.MeasureValues);
F4SDProtocoll.Instance.Add(new QuickActionProtocollEntry(RemoteQuickAction, copyData));
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
string quickActionStatus;
@@ -213,12 +213,12 @@ namespace FasdDesktopUi.Basics.UiActions
}
});
return new List<object>() { quickActionStatus, _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { quickActionStatus, cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
catch (Exception E)
{
LogException(E);
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}

View File

@@ -191,7 +191,7 @@ namespace FasdDesktopUi.Basics.UiActions
break;
}
output = new List<object>() { quickActionStatus, _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
output = new List<object>() { quickActionStatus, cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
else
{
@@ -211,7 +211,7 @@ namespace FasdDesktopUi.Basics.UiActions
cQuickActionCopyData copyData = QuickActionProtocollEntry.GetCopyData(ServerQuickAction, DataProvider, false, protocollOutput, StatusMonitor.MeasureValues);
F4SDProtocoll.Instance.Add(new QuickActionProtocollEntry(ServerQuickAction, copyData));
output = new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
output = new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.Canceled"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
_ = Task.Run(async () =>
@@ -254,7 +254,7 @@ namespace FasdDesktopUi.Basics.UiActions
catch (Exception E)
{
LogException(E);
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), _rawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
return new List<object>() { cMultiLanguageSupport.GetItem("QuickAction.Revision.Status.FinishedWithError"), cUtility.RawValueFormatter.GetDisplayValue(DateTime.UtcNow, RawValueType.DATETIME) };
}
}
}

View File

@@ -0,0 +1,160 @@
<UserControl x:Class="FasdDesktopUi.Basics.UserControls.HierarchicalSelectionControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:ico="clr-namespace:FasdDesktopUi.Basics.UserControls.AdaptableIcon;assembly=F4SD-AdaptableIcon"
xmlns:vc="clr-namespace:FasdDesktopUi.Basics.Converter"
xmlns:models="clr-namespace:FasdDesktopUi.Basics.Models"
mc:Ignorable="d"
x:Name="HierarchySelector"
Focusable="True"
d:DesignHeight="60"
d:DesignWidth="350">
<UserControl.Resources>
<vc:LanguageDefinitionsConverter x:Key="LanguageConverter" />
<vc:NullValueToVisibilityConverter x:Key="NullToVisibility" />
</UserControl.Resources>
<Grid>
<Border x:Name="DisplayBorder"
Height="28"
Background="{Binding ElementName=HierarchySelector, Path=ComboBoxBackground}"
BorderBrush="{Binding ElementName=HierarchySelector, Path=BorderBrush}"
BorderThickness="1"
CornerRadius="7.5"
Padding="6 0"
MouseLeftButtonUp="DisplayBorder_MouseLeftButtonUp">
<Border.Style>
<Style TargetType="Border">
<Setter Property="Opacity" Value="1" />
<Setter Property="Cursor" Value="Hand" />
<Style.Triggers>
<DataTrigger Binding="{Binding IsOpen, ElementName=DropDownPopup}"
Value="True">
<Setter Property="BorderBrush" Value="{DynamicResource BackgroundColor.Menu.SubCategory.Hover}" />
<Setter Property="Background" Value="{DynamicResource BackgroundColor.DetailsPage.DataHistory.ValueColumn}" />
</DataTrigger>
<Trigger Property="IsMouseOver"
Value="True">
<Setter Property="BorderBrush" Value="{DynamicResource BackgroundColor.Menu.SubCategory.Hover}" />
</Trigger>
<DataTrigger Binding="{Binding ElementName=HierarchySelector, Path=IsEnabled}"
Value="False">
<Setter Property="Opacity" Value="0.5" />
<Setter Property="Cursor" Value="Arrow" />
</DataTrigger>
</Style.Triggers>
</Style>
</Border.Style>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Grid Grid.Column="0"
Margin="0 0 10 0"
VerticalAlignment="Center">
<TextBlock Text="{Binding ElementName=HierarchySelector, Path=SelectedItem.FullPath}"
Foreground="{DynamicResource FontColor.Menu.Categories}"
VerticalAlignment="Center"
TextTrimming="CharacterEllipsis"
ToolTip="{Binding ElementName=HierarchySelector, Path=SelectedItem.FullPath}" />
</Grid>
<Path Grid.Column="1"
Margin="0 0 6 0"
Data="F1 M 2.89067,4.99467C 2.89067,4.22933 3.724,3.74533 4.39067,4.13067L 10.8227,7.844L 17.26,4.13067C 18.412,3.48 19.4013,5.19333 18.26,5.86533L 11.3227,9.86533C 11.016,10.0413 10.636,10.0413 10.3227,9.86533L 3.39067,5.86533C 3.07867,5.688 2.89067,5.35467 2.89067,4.99467 Z"
Fill="{DynamicResource Color.Menu.Icon}"
HorizontalAlignment="Right"
VerticalAlignment="Center"
Width="10"
Height="6"
Stretch="Uniform"
IsHitTestVisible="False" />
</Grid>
</Border>
<Popup x:Name="DropDownPopup"
PlacementTarget="{Binding ElementName=DisplayBorder}"
Placement="Bottom"
StaysOpen="False"
AllowsTransparency="True"
Width="{Binding ElementName=DisplayBorder, Path=ActualWidth}"
Opened="DropDownPopup_Opened"
Closed="DropDownPopup_Closed">
<Border Background="{DynamicResource BackgroundColor.Menu.SubCategory}"
CornerRadius="7.5"
Padding="10">
<Border.Effect>
<DropShadowEffect BlurRadius="10"
Color="{DynamicResource DropShadowColor.Menu}"
Direction="55"
ShadowDepth="10"
Opacity="0.35" />
</Border.Effect>
<StackPanel>
<Grid Margin="0 0 10 0">
<TextBox x:Name="SearchTextBox"
Style="{DynamicResource Customizable.Editable.TextBox.EditOnly}"
Background="{Binding ElementName=HierarchySelector, Path=ComboBoxBackground}"
Padding="27 5 5 5"
VerticalContentAlignment="Center"
TextChanged="SearchTextBox_TextChanged" />
<ico:AdaptableIcon SelectedInternIcon="menuBar_search"
Style="{DynamicResource Menu.MenuBar.PinnedIcon.Base}"
BorderPadding="5 5 5 7"
Margin="0"
IconBackgroundColor="Transparent"
HorizontalAlignment="Left"
VerticalAlignment="Center" />
<TextBlock Margin="30 0 0 0"
Foreground="{DynamicResource FontColor.DetailsPage.DataHistory.Date}"
IsHitTestVisible="False"
VerticalAlignment="Center">
<TextBlock.Style>
<Style TargetType="TextBlock">
<Setter Property="Visibility" Value="Collapsed" />
<Style.Triggers>
<DataTrigger Binding="{Binding Text, ElementName=SearchTextBox}"
Value="">
<Setter Property="Text"
Value="{Binding ElementName=HierarchySelector, Path=SearchPlaceholderText}" />
<Setter Property="Visibility" Value="Visible" />
</DataTrigger>
</Style.Triggers>
</Style>
</TextBlock.Style>
</TextBlock>
</Grid>
<Border Margin="0 10 0 0"
Background="{DynamicResource BackgroundColor.Menu.SubCategory}"
BorderThickness="0"
CornerRadius="5">
<ScrollViewer MaxHeight="300"
VerticalScrollBarVisibility="Auto">
<TreeView x:Name="TreeViewControl"
Background="{Binding ElementName=HierarchySelector, Path=ComboBoxBackground}"
ItemsSource="{Binding VisibleItems, ElementName=HierarchySelector}"
SelectedItemChanged="TreeViewControl_SelectedItemChanged">
<TreeView.Resources>
<Style TargetType="TreeViewItem">
<Setter Property="IsExpanded"
Value="{Binding IsExpanded, Mode=TwoWay}" />
</Style>
<HierarchicalDataTemplate DataType="{x:Type models:HierarchicalSelectionItem}"
ItemsSource="{Binding Children}">
<TextBlock Text="{Binding DisplayName}"
Foreground="{DynamicResource FontColor.Menu.Categories}"
Margin="0 2 0 2" />
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
</ScrollViewer>
</Border>
</StackPanel>
</Border>
</Popup>
</Grid>
</UserControl>

View File

@@ -0,0 +1,256 @@
using FasdDesktopUi.Basics.Models;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Threading;
namespace FasdDesktopUi.Basics.UserControls
{
public partial class HierarchicalSelectionControl : UserControl, IFocusInvoker
{
private readonly ObservableCollection<HierarchicalSelectionItem> visibleItems = new ObservableCollection<HierarchicalSelectionItem>();
private readonly Dictionary<string, HierarchicalSelectionItem> itemLookup = new Dictionary<string, HierarchicalSelectionItem>();
private readonly DispatcherTimer searchDelayTimer = new DispatcherTimer { Interval = TimeSpan.FromMilliseconds(250) };
private string lastSearchText = string.Empty;
public ObservableCollection<HierarchicalSelectionItem> VisibleItems => visibleItems;
public int? ParentIndex { get; set; }
public UIElement ParentElement { get; set; }
public HierarchicalSelectionControl()
{
InitializeComponent();
TreeViewControl.ItemsSource = visibleItems;
searchDelayTimer.Tick += SearchDelayTimer_Tick;
}
#region DependencyProperties
public ObservableCollection<HierarchicalSelectionItem> ItemsSource
{
get => (ObservableCollection<HierarchicalSelectionItem>)GetValue(ItemsSourceProperty);
set => SetValue(ItemsSourceProperty, value);
}
public static readonly DependencyProperty ItemsSourceProperty = DependencyProperty.Register(
nameof(ItemsSource),
typeof(ObservableCollection<HierarchicalSelectionItem>),
typeof(HierarchicalSelectionControl),
new PropertyMetadata(null, OnItemsSourceChanged));
private static void OnItemsSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
if (d is HierarchicalSelectionControl control)
{
control.RebuildLookup();
control.ApplyFilter(control.lastSearchText);
control.TryExpandToSelectedItem();
}
}
public HierarchicalSelectionItem SelectedItem
{
get => (HierarchicalSelectionItem)GetValue(SelectedItemProperty);
set => SetValue(SelectedItemProperty, value);
}
public static readonly DependencyProperty SelectedItemProperty = DependencyProperty.Register(
nameof(SelectedItem),
typeof(HierarchicalSelectionItem),
typeof(HierarchicalSelectionControl),
new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnSelectedItemChanged));
private static void OnSelectedItemChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
if (d is HierarchicalSelectionControl control)
{
control.TryExpandToSelectedItem();
}
}
public Brush ComboBoxBackground
{
get => (Brush)GetValue(ComboBoxBackgroundProperty);
set => SetValue(ComboBoxBackgroundProperty, value);
}
public static readonly DependencyProperty ComboBoxBackgroundProperty =
DependencyProperty.Register(nameof(ComboBoxBackground), typeof(Brush), typeof(HierarchicalSelectionControl), new PropertyMetadata(Brushes.Transparent));
public string SearchPlaceholderText
{
get => (string)GetValue(SearchPlaceholderTextProperty);
set => SetValue(SearchPlaceholderTextProperty, value);
}
public static readonly DependencyProperty SearchPlaceholderTextProperty =
DependencyProperty.Register(nameof(SearchPlaceholderText), typeof(string), typeof(HierarchicalSelectionControl), new PropertyMetadata(string.Empty));
#endregion
private void DropDownPopup_Opened(object sender, EventArgs e)
{
SearchTextBox.Focus();
SearchTextBox.SelectAll();
EnsureParentPlacement();
cFocusInvoker.InvokeGotFocus(this, e);
}
private void DropDownPopup_Closed(object sender, EventArgs e)
{
searchDelayTimer.Stop();
cFocusInvoker.InvokeLostFocus(this, e);
}
private void EnsureParentPlacement()
{
if (ParentElement == null || ParentElement != this.Parent)
{
ParentElement = this.Parent as UIElement;
if (this.Parent is Panel panel)
ParentIndex = panel.Children.IndexOf(this);
else
ParentIndex = null;
}
}
private void SearchTextBox_TextChanged(object sender, TextChangedEventArgs e)
{
searchDelayTimer.Stop();
searchDelayTimer.Start();
}
private void SearchDelayTimer_Tick(object sender, EventArgs e)
{
searchDelayTimer.Stop();
lastSearchText = SearchTextBox.Text ?? string.Empty;
ApplyFilter(lastSearchText);
}
private void TreeViewControl_SelectedItemChanged(object sender, RoutedPropertyChangedEventArgs<object> e)
{
if (e.NewValue is HierarchicalSelectionItem selected)
{
var original = ResolveOriginalItem(selected);
if (original != null)
SelectedItem = original;
DropDownPopup.IsOpen = false;
}
}
private HierarchicalSelectionItem ResolveOriginalItem(HierarchicalSelectionItem item)
{
if (item == null)
return null;
if (!string.IsNullOrWhiteSpace(item.Id) && itemLookup.TryGetValue(item.Id, out var original))
return original;
return item;
}
private void RebuildLookup()
{
itemLookup.Clear();
if (ItemsSource == null)
return;
foreach (var entry in ItemsSource.SelectMany(item => item.SelfAndDescendants()))
{
if (string.IsNullOrWhiteSpace(entry.Id))
continue;
itemLookup[entry.Id] = entry;
}
}
private void ApplyFilter(string searchText)
{
visibleItems.Clear();
if (ItemsSource == null)
return;
if (string.IsNullOrWhiteSpace(searchText))
{
foreach (var item in ItemsSource)
{
item.SetExpandedRecursive(false);
visibleItems.Add(item);
}
TryExpandToSelectedItem();
return;
}
var comparison = StringComparison.CurrentCultureIgnoreCase;
foreach (var root in ItemsSource)
{
var clone = root.CloneBranch(node =>
node.FullPath?.IndexOf(searchText, comparison) >= 0 ||
node.DisplayName?.IndexOf(searchText, comparison) >= 0);
if (clone == null)
continue;
clone.SetExpandedRecursive(true);
visibleItems.Add(clone);
}
}
private void TryExpandToSelectedItem()
{
if (SelectedItem == null || string.IsNullOrWhiteSpace(SelectedItem.Id))
return;
if (!string.IsNullOrWhiteSpace(lastSearchText))
return;
var chain = SelectedItem;
while (chain != null)
{
chain.IsExpanded = true;
chain = chain.Parent;
}
}
private void DisplayBorder_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
{
if (!IsEnabled)
return;
e.Handled = true;
DropDownPopup.IsOpen = !DropDownPopup.IsOpen;
}
protected override void OnPreviewKeyDown(KeyEventArgs e)
{
base.OnPreviewKeyDown(e);
if (!IsEnabled)
return;
if (!DropDownPopup.IsOpen && (e.Key == Key.Enter || e.Key == Key.Down || e.Key == Key.Space))
{
DropDownPopup.IsOpen = true;
e.Handled = true;
return;
}
if (DropDownPopup.IsOpen && e.Key == Key.Escape)
{
DropDownPopup.IsOpen = false;
e.Handled = true;
}
}
}
}

View File

@@ -160,13 +160,13 @@
Margin="0 10 0 0"
Foreground="{DynamicResource FontColor.Menu.Categories}" />
</StackPanel>
<local:ComboBoxPageable x:Name="CategorySelectionControl"
Margin="0 5 0 0"
SelectedItem="{Binding SelectedCategory, ElementName=CloseCaseDialogUc, Mode=TwoWay}"
ComboBoxBackground="{DynamicResource BackgroundColor.DetailsPage.DataHistory.ValueColumn}"
BorderBrush="{DynamicResource BackgroundColor.Menu.SubCategory.Hover}"
PreviewKeyDown="Combobox_PreviewKeyDown"
/>
<local:HierarchicalSelectionControl x:Name="CategorySelectionControl"
Margin="0 5 0 0"
SelectedItem="{Binding SelectedCategory, ElementName=CloseCaseDialogUc, Mode=TwoWay}"
ComboBoxBackground="{DynamicResource BackgroundColor.DetailsPage.DataHistory.ValueColumn}"
BorderBrush="{DynamicResource BackgroundColor.Menu.SubCategory.Hover}"
SearchPlaceholderText="{Binding Converter={StaticResource LanguageConverter}, ConverterParameter=Searchbar.Placeholder}"
PreviewKeyDown="Combobox_PreviewKeyDown" />
<StackPanel>
<TextBlock Text="{Binding Converter={StaticResource LanguageConverter}, ConverterParameter=Dialog.CloseCase.Template}"
FontWeight="Bold"

View File

@@ -67,6 +67,14 @@ namespace FasdDesktopUi.Basics.UserControls
Infos = new Dictionary<string, string> { ["Special"] = "RemoveAffectedAssetEntry" }
};
private const string CategoryTableNamePrimary = "M42Wpm-Ticket-Categories";
private const string CategoryTableNameLegacy = "M42Wpm-Ticket-CloseCase-Categories";
private string activeCategoryTableName = CategoryTableNamePrimary;
private ObservableCollection<HierarchicalSelectionItem> categoryHierarchy = new ObservableCollection<HierarchicalSelectionItem>();
private readonly Dictionary<string, HierarchicalSelectionItem> categoryLookup = new Dictionary<string, HierarchicalSelectionItem>(StringComparer.OrdinalIgnoreCase);
private bool isCategoryLoading;
public bool IsTicket
{
get
@@ -147,7 +155,7 @@ namespace FasdDesktopUi.Basics.UserControls
EnableHoldTicketAction = statusId != enumTicketStatus.OnHold;
}
}
TrySelectTicketCategoryFromTicketInfos();
}
}
@@ -209,23 +217,19 @@ namespace FasdDesktopUi.Basics.UserControls
public static readonly DependencyProperty SelectedCategoryProperty = DependencyProperty.Register(
"SelectedCategory",
typeof(KeyValuePair<string, object>),
typeof(HierarchicalSelectionItem),
typeof(CloseCaseDialogWithTicket),
new PropertyMetadata(default(KeyValuePair<string, object>), OnSelectedCategoryChanged));
new PropertyMetadata(null, OnSelectedCategoryChanged));
public KeyValuePair<string, object> SelectedCategory
public HierarchicalSelectionItem SelectedCategory
{
get { return (KeyValuePair<string, object>)GetValue(SelectedCategoryProperty); }
set
{
SetValue(SelectedCategoryProperty, value);
}
get { return (HierarchicalSelectionItem)GetValue(SelectedCategoryProperty); }
set { SetValue(SelectedCategoryProperty, value); }
}
private static void OnSelectedCategoryChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var control = (CloseCaseDialogWithTicket)d;
var newValue = (KeyValuePair<string, object>)e.NewValue;
// Reserved for future use when additional reactions are required.
}
#endregion
@@ -377,14 +381,10 @@ namespace FasdDesktopUi.Basics.UserControls
me.ServiceSelectionControl.ParentElement = me.MainStack;
me.ServiceSelectionControl.ParentIndex = me.MainStack.Children.IndexOf(me.ServiceSelectionControl);
me.CategorySelectionControl.ParentElement = me.MainStack;
me.CategorySelectionControl.ParentIndex = me.MainStack.Children.IndexOf(me.CategorySelectionControl);
me.CategorySelectionControl.SearchDataChanged = me.HandleCategorySearchDataChanged;
me.AddNewOrExistingOrNoneTicketSelection();
me.UpdateCaseNotesPreview();
me.UpdateTicketComponentVisibility();
await me.InitializeCategorySelectionAsync();
await me.UpdateQuickCallsComboBoxAsync();
}
catch (Exception E)
@@ -412,11 +412,6 @@ namespace FasdDesktopUi.Basics.UserControls
dpd?.AddValueChanged(CaseNotesPreview, TicketCaseNotesTextBlock_TextChanged);
#if !IsNewFeature
CategoryLabelPanel.Visibility = Visibility.Collapsed;
CategorySelectionControl.Visibility = Visibility.Collapsed;
#endif
SupportNotepad = true;
}
@@ -886,93 +881,191 @@ namespace FasdDesktopUi.Basics.UserControls
return null;
}
private string lastCategorySearch;
private async void HandleCategorySearchDataChanged(object sender, cF4sdHealthSelectionDataRequest e)
private async Task InitializeCategorySelectionAsync()
{
await UpdateCategorySelectionControlAsync(e);
}
if (isCategoryLoading)
return;
private async Task UpdateCategorySelectionControlAsync(cF4sdHealthSelectionDataRequest requestData)
{
try
{
if (DataProvider == null || CategorySelectionControl == null)
return;
requestData.Identities = DataProvider.Identities;
requestData.Table = "M42Wpm-Ticket-CloseCase-Categories";
requestData.ResetFilter = CategorySelectionControl.ResetFilter;
isCategoryLoading = true;
if (string.IsNullOrEmpty(lastCategorySearch) ||
!lastCategorySearch.Equals(requestData.Search, StringComparison.CurrentCultureIgnoreCase))
var tableCandidates = new[] { CategoryTableNamePrimary, CategoryTableNameLegacy };
bool initialized = false;
foreach (var tableName in tableCandidates)
{
var resCategoryCount = await cFasdCockpitCommunicationBase.Instance.GetPagedDataCount(requestData);
CategorySelectionControl.TotalItemCount = resCategoryCount;
lastCategorySearch = requestData.Search;
}
var categoryData = await cFasdCockpitCommunicationBase.Instance.GetPagedData(requestData);
var categoriesList = GetCategorySelectionData(categoryData) ?? new ObservableCollection<KeyValuePair<string, object>>();
// Aktuell am Ticket gesetzte Kategorie ggf. sicherstellen
string categoryId = null;
string categoryName = null;
if (SelectedTicket != null && SelectedTicket.Infos != null)
{
var catIdPair = SelectedTicket.Infos.FirstOrDefault(x => x.Key == "CategoryId");
categoryId = catIdPair.Value;
var catNamePair = SelectedTicket.Infos.FirstOrDefault(x => x.Key == "CategoryName");
categoryName = catNamePair.Value;
}
if (!string.IsNullOrEmpty(categoryId) && Guid.Empty.ToString() != categoryId)
{
bool exists = categoriesList.Any(kvp => kvp.Value != null && kvp.Value.ToString() == categoryId);
if (!exists)
if (await TryPopulateCategoryHierarchyAsync(tableName))
{
categoriesList.Add(new KeyValuePair<string, object>(
string.IsNullOrEmpty(categoryName) ? categoryId : categoryName,
categoryId));
activeCategoryTableName = tableName;
initialized = true;
break;
}
}
CategorySelectionControl.ItemData = categoriesList;
if (initialized)
{
CategorySelectionControl.ItemsSource = categoryHierarchy;
TrySelectTicketCategoryFromTicketInfos();
}
}
catch (Exception E)
{
LogException(E);
}
finally
{
isCategoryLoading = false;
}
}
private ObservableCollection<KeyValuePair<string, object>> GetCategorySelectionData(cF4SDHealthCardRawData.cHealthCardTable dataTable)
private async Task<bool> TryPopulateCategoryHierarchyAsync(string tableName)
{
try
{
if (dataTable == null || dataTable.Name != "M42Wpm-Ticket-CloseCase-Categories")
return null;
const int defaultPageSize = 250;
if (!dataTable.Columns.TryGetValue("id", out var idColumn))
return null;
var requestData = new cF4sdHealthSelectionDataRequest
{
Identities = DataProvider.Identities,
Table = tableName,
Page = 0,
PageSize = defaultPageSize,
Search = string.Empty
};
if (!dataTable.Columns.TryGetValue("Name", out var nameColumn))
return null;
var totalCount = await cFasdCockpitCommunicationBase.Instance.GetPagedDataCount(requestData);
var effectivePageSize = requestData.PageSize > 0 ? requestData.PageSize : defaultPageSize;
var pageCount = Math.Max(1, (int)Math.Ceiling((double)totalCount / Math.Max(1, effectivePageSize)));
var zippedKeyValuePairs =
idColumn.Values.Zip(nameColumn.Values, (id, display) =>
new KeyValuePair<string, object>(display != null ? display.ToString() : string.Empty, id));
var flatItems = new Dictionary<string, HierarchicalSelectionItem>(StringComparer.OrdinalIgnoreCase);
return new ObservableCollection<KeyValuePair<string, object>>(zippedKeyValuePairs);
for (int pageIndex = 0; pageIndex < pageCount; pageIndex++)
{
requestData.Page = pageIndex;
requestData.PageSize = effectivePageSize;
var categoryTable = await cFasdCockpitCommunicationBase.Instance.GetPagedData(requestData);
bool rowAdded = false;
foreach (var item in ConvertCategoryTable(categoryTable))
{
if (string.IsNullOrWhiteSpace(item.Id))
continue;
flatItems[item.Id] = item;
rowAdded = true;
}
if (!rowAdded && categoryTable == null)
return false;
}
var hierarchy = HierarchicalSelectionItem.BuildTree(flatItems.Values);
if (hierarchy == null || hierarchy.Count == 0)
return false;
categoryHierarchy = hierarchy;
UpdateCategoryLookup();
return true;
}
catch (Exception E)
{
LogException(E);
return false;
}
}
private IEnumerable<HierarchicalSelectionItem> ConvertCategoryTable(cF4SDHealthCardRawData.cHealthCardTable dataTable)
{
if (dataTable == null || dataTable.Columns == null)
yield break;
if (!dataTable.Columns.TryGetValue("id", out var idColumn))
yield break;
if (!dataTable.Columns.TryGetValue("Name", out var nameColumn))
yield break;
cF4SDHealthCardRawData.cHealthCardTableColumn parentIdColumn = null;
cF4SDHealthCardRawData.cHealthCardTableColumn parentNameColumn = null;
if (!dataTable.Columns.TryGetValue("parentValue", out parentIdColumn))
dataTable.Columns.TryGetValue("Parent_Value", out parentIdColumn);
if (!dataTable.Columns.TryGetValue("parent", out parentNameColumn))
dataTable.Columns.TryGetValue("Parent", out parentNameColumn);
for (int index = 0; index < idColumn.Values.Count; index++)
{
var id = idColumn.Values[index]?.ToString();
if (string.IsNullOrWhiteSpace(id))
continue;
var displayName = index < nameColumn.Values.Count ? nameColumn.Values[index]?.ToString() : string.Empty;
string parentId = null;
if (parentIdColumn != null && index < parentIdColumn.Values.Count)
parentId = parentIdColumn.Values[index]?.ToString();
if (Guid.TryParse(parentId, out var parsedParentId) && parsedParentId == Guid.Empty)
parentId = null;
var parentDisplayName = parentNameColumn != null && index < parentNameColumn.Values.Count
? parentNameColumn.Values[index]?.ToString()
: null;
yield return new HierarchicalSelectionItem
{
Id = id,
DisplayName = string.IsNullOrWhiteSpace(displayName) ? parentDisplayName ?? id : displayName,
ParentId = parentId,
ParentDisplayName = parentDisplayName
};
}
}
private void UpdateCategoryLookup()
{
categoryLookup.Clear();
if (categoryHierarchy == null)
return;
foreach (var node in categoryHierarchy.SelectMany(item => item.SelfAndDescendants()))
{
if (!string.IsNullOrWhiteSpace(node.Id))
categoryLookup[node.Id] = node;
}
}
private void TrySelectTicketCategoryFromTicketInfos()
{
try
{
if (SelectedTicket?.Infos == null)
{
SelectedCategory = null;
return;
}
if (!SelectedTicket.Infos.TryGetValue("CategoryId", out var categoryId) || string.IsNullOrWhiteSpace(categoryId))
{
SelectedCategory = null;
return;
}
if (categoryLookup.TryGetValue(categoryId, out var categoryNode))
SelectedCategory = categoryNode;
}
catch (Exception E)
{
LogException(E);
}
return null;
}
private async Task UpdateQuickCallsComboBoxAsync()
{
try

View File

@@ -24,7 +24,7 @@ namespace FasdDesktopUi.Basics
{
public static class cUtility
{
private static readonly IRawValueFormatter _rawValueFormatter = new RawValueFormatter();
public static readonly IRawValueFormatter RawValueFormatter = new RawValueFormatter();
internal static RawValueType GetRawValueType(enumHealthCardDisplayTypes displayType)
{
@@ -568,18 +568,18 @@ namespace FasdDesktopUi.Basics
output += "\n\n" + cMultiLanguageSupport.GetItem("QuickAction.Copy.Measure");
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
foreach (var measureValue in measureValues)
{
try
{
string value = _rawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = _rawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string value = RawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = RawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string difference = string.Empty;
if (measureValue.Difference != null)
difference = $" (∆ {_rawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
difference = $" (∆ {RawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
output += "\n" + measureValue.Names.GetValue(cF4SDCockpitXmlConfig.Instance.HealthCardConfig.ProtocollLanguage) + ": " + value + " ➜ " + postValue + difference;
}
@@ -807,18 +807,18 @@ namespace FasdDesktopUi.Basics
output += "<p>" + cMultiLanguageSupport.GetItem("QuickAction.Copy.Measure.Html") + "</p>";
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
foreach (var measureValue in measureValues)
{
try
{
string value = _rawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = _rawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string value = RawValueFormatter.GetDisplayValue(measureValue.Value, measureValue.Display);
string postValue = RawValueFormatter.GetDisplayValue(measureValue.PostValue, measureValue.Display);
string difference = string.Empty;
if (measureValue.Difference != null)
difference = $" (∆ {_rawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
difference = $" (∆ {RawValueFormatter.GetDisplayValue(measureValue.Difference, measureValue.Display)})";
output += "<p>";
output += "<b>" + measureValue.Names.GetValue(cF4SDCockpitXmlConfig.Instance.HealthCardConfig.ProtocollLanguage) + ": </b>" + value + " ➜ " + postValue + difference;
@@ -850,30 +850,30 @@ namespace FasdDesktopUi.Basics
{
FormattingOptions options = new FormattingOptions() { ReferenceDate = DateTime.UtcNow.AddDays(_v.ReferenceDays) };
_rawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
var _strVal = _rawValueFormatter.GetDisplayValue(_v.Value, GetRawValueType(_v.StateDefinition.DisplayType), options);
RawValueFormatter.SetDefaultCulture(new System.Globalization.CultureInfo(cFasdCockpitConfig.Instance.SelectedLanguage));
var _strVal = RawValueFormatter.GetDisplayValue(_v.Value, GetRawValueType(_v.StateDefinition.DisplayType), options);
_t.rawValue.Text = _strVal;
if (_v.StateDefinition is cHealthCardStateLevel _sl)
{
_strVal = _rawValueFormatter.GetDisplayValue(_sl.Warning, GetRawValueType(_v.StateDefinition.DisplayType), options);
_strVal = RawValueFormatter.GetDisplayValue(_sl.Warning, GetRawValueType(_v.StateDefinition.DisplayType), options);
_t.tresholdWarning.Text = _strVal;
_strVal = _rawValueFormatter.GetDisplayValue(_sl.Error, GetRawValueType(_v.StateDefinition.DisplayType), options);
_strVal = RawValueFormatter.GetDisplayValue(_sl.Error, GetRawValueType(_v.StateDefinition.DisplayType), options);
_t.tresholdError.Text = _strVal;
}
else if (_v.StateDefinition is cHealthCardStateVersion _sv)
{
_strVal = _rawValueFormatter.GetDisplayValue(_sv.Warning, GetRawValueType(_v.StateDefinition.DisplayType), options);
_strVal = RawValueFormatter.GetDisplayValue(_sv.Warning, GetRawValueType(_v.StateDefinition.DisplayType), options);
_t.tresholdWarning.Text = _strVal;
_strVal = _rawValueFormatter.GetDisplayValue(_sv.Error, GetRawValueType(_v.StateDefinition.DisplayType), options);
_strVal = RawValueFormatter.GetDisplayValue(_sv.Error, GetRawValueType(_v.StateDefinition.DisplayType), options);
_t.tresholdError.Text = _strVal;
}
else if (_v.StateDefinition is cHealthCardStateDateTime _sd)
{
_strVal = _rawValueFormatter.GetDisplayValue(_sd.WarningHours, RawValueType.DURATION_HOUR, options);
_strVal = RawValueFormatter.GetDisplayValue(_sd.WarningHours, RawValueType.DURATION_HOUR, options);
_t.tresholdWarning.Text = _strVal;
_strVal = _rawValueFormatter.GetDisplayValue(_sd.ErrorHours, RawValueType.DURATION_HOUR, options);
_strVal = RawValueFormatter.GetDisplayValue(_sd.ErrorHours, RawValueType.DURATION_HOUR, options);
_t.tresholdError.Text = _strVal;
}
else if (_v.StateDefinition is cHealthCardStateTranslation _st)

View File

@@ -197,6 +197,7 @@
<Compile Include="Basics\Services\Models\TicketOverviewCountsChangedEventArgs.cs" />
<Compile Include="Basics\Services\TicketOverviewUpdateService.cs" />
<Compile Include="Basics\Models\ConnectionStatusHelper.cs" />
<Compile Include="Basics\Models\HierarchicalSelectionItem.cs" />
<Compile Include="Basics\Models\HotKeyInformation.cs" />
<Compile Include="Basics\Models\IBlurrable.cs" />
<Compile Include="Basics\Models\ContainerDataModels.cs" />
@@ -240,6 +241,9 @@
<Compile Include="Basics\UserControls\ComboBoxPageAble.xaml.cs">
<DependentUpon>ComboBoxPageAble.xaml</DependentUpon>
</Compile>
<Compile Include="Basics\UserControls\HierarchicalSelectionControl.xaml.cs">
<DependentUpon>HierarchicalSelectionControl.xaml</DependentUpon>
</Compile>
<Compile Include="Basics\UserControls\DataCanvas\DynamicChart.xaml.cs">
<DependentUpon>DynamicChart.xaml</DependentUpon>
</Compile>
@@ -447,6 +451,10 @@
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Basics\UserControls\HierarchicalSelectionControl.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>
</Page>
<Page Include="Basics\UserControls\DataCanvas\DynamicChart.xaml">
<SubType>Designer</SubType>
<Generator>MSBuild:Compile</Generator>

View File

@@ -949,7 +949,7 @@ namespace FasdDesktopUi.Pages.DetailsPage
if (!(e is BooleanEventArgs booleanArg) || booleanArg.BooleanArg == false)
isDataProviderLoading = true;
var data = _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.GetDetailsPageDataWithoutHeading();
var data = _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.DetailPage.GetDataWithoutHeading();
await Dispatcher.Invoke(async () =>
{
NavigationHeadingUc.HeadingData = _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.GetHeadingDataWithoutOnlineStatus();

View File

@@ -310,7 +310,7 @@ namespace FasdDesktopUi.Pages.SlimPage
return;
}
var data = await _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.GetSlimPageDataAsync();
var data = await _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.SlimCard.GetDataAsync();
//todo: check if there is a more performant way solving this
Dispatcher.Invoke(() => WidgetCollectionUc.HeadingData = data.HeadingData);
Dispatcher.Invoke(() => WidgetCollectionUc.WidgetData = data.WidgetData);
@@ -339,7 +339,7 @@ namespace FasdDesktopUi.Pages.SlimPage
{
try
{
var data = await _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.GetSlimPageDataAsync();
var data = await _supportCase?.SupportCaseDataProviderArtifact.HealthCardDataHelper.SlimCard.GetDataAsync();
//todo: check if there is a more performant way solving this
Dispatcher.Invoke(() => WidgetCollectionUc.HeadingData = data.HeadingData);
Dispatcher.Invoke(() => WidgetCollectionUc.WidgetData = data.WidgetData);