ReagentDispenserWindow.xaml.cs 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124
  1. using Content.Client.Stylesheets;
  2. using Content.Client.UserInterface.Controls;
  3. using Content.Shared.Chemistry;
  4. using Content.Shared.Chemistry.Reagent;
  5. using Robust.Client.AutoGenerated;
  6. using Robust.Client.UserInterface.Controls;
  7. using Robust.Client.UserInterface.XAML;
  8. using Robust.Shared.Prototypes;
  9. using static Robust.Client.UserInterface.Controls.BoxContainer;
  10. namespace Content.Client.Chemistry.UI
  11. {
  12. /// <summary>
  13. /// Client-side UI used to control a <see cref="ReagentDispenserComponent"/>.
  14. /// </summary>
  15. [GenerateTypedNameReferences]
  16. public sealed partial class ReagentDispenserWindow : FancyWindow
  17. {
  18. [Dependency] private readonly IPrototypeManager _prototypeManager = default!;
  19. [Dependency] private readonly IEntityManager _entityManager = default!;
  20. public event Action<string>? OnDispenseReagentButtonPressed;
  21. public event Action<string>? OnEjectJugButtonPressed;
  22. /// <summary>
  23. /// Create and initialize the dispenser UI client-side. Creates the basic layout,
  24. /// actual data isn't filled in until the server sends data about the dispenser.
  25. /// </summary>
  26. public ReagentDispenserWindow()
  27. {
  28. RobustXamlLoader.Load(this);
  29. IoCManager.InjectDependencies(this);
  30. }
  31. /// <summary>
  32. /// Update the button grid of reagents which can be dispensed.
  33. /// </summary>
  34. /// <param name="inventory">Reagents which can be dispensed by this dispenser</param>
  35. public void UpdateReagentsList(List<ReagentInventoryItem> inventory)
  36. {
  37. if (ReagentList == null)
  38. return;
  39. ReagentList.Children.Clear();
  40. //Sort inventory by reagentLabel
  41. inventory.Sort((x, y) => x.ReagentLabel.CompareTo(y.ReagentLabel));
  42. foreach (var item in inventory)
  43. {
  44. var card = new ReagentCardControl(item);
  45. card.OnPressed += OnDispenseReagentButtonPressed;
  46. card.OnEjectButtonPressed += OnEjectJugButtonPressed;
  47. ReagentList.Children.Add(card);
  48. }
  49. }
  50. /// <summary>
  51. /// Update the UI state when new state data is received from the server.
  52. /// </summary>
  53. /// <param name="state">State data sent by the server.</param>
  54. public void UpdateState(BoundUserInterfaceState state)
  55. {
  56. var castState = (ReagentDispenserBoundUserInterfaceState) state;
  57. UpdateContainerInfo(castState);
  58. UpdateReagentsList(castState.Inventory);
  59. _entityManager.TryGetEntity(castState.OutputContainerEntity, out var outputContainerEnt);
  60. View.SetEntity(outputContainerEnt);
  61. // Disable the Clear & Eject button if no beaker
  62. ClearButton.Disabled = castState.OutputContainer is null;
  63. EjectButton.Disabled = castState.OutputContainer is null;
  64. AmountGrid.Selected = ((int)castState.SelectedDispenseAmount).ToString();
  65. }
  66. /// <summary>
  67. /// Update the fill state and list of reagents held by the current reagent container, if applicable.
  68. /// <para>Also highlights a reagent if it's dispense button is being mouse hovered.</para>
  69. /// </summary>
  70. /// <param name="state">State data for the dispenser.</param>
  71. /// or null if no button is being hovered.</param>
  72. public void UpdateContainerInfo(ReagentDispenserBoundUserInterfaceState state)
  73. {
  74. ContainerInfo.Children.Clear();
  75. if (state.OutputContainer is null)
  76. {
  77. ContainerInfoName.Text = "";
  78. ContainerInfoFill.Text = "";
  79. ContainerInfo.Children.Add(new Label { Text = Loc.GetString("reagent-dispenser-window-no-container-loaded-text") });
  80. return;
  81. }
  82. // Set Name of the container and its fill status (Ex: 44/100u)
  83. ContainerInfoName.Text = state.OutputContainer.DisplayName;
  84. ContainerInfoFill.Text = state.OutputContainer.CurrentVolume + "/" + state.OutputContainer.MaxVolume;
  85. foreach (var (reagent, quantity) in state.OutputContainer.Reagents!)
  86. {
  87. // Try get to the prototype for the given reagent. This gives us its name.
  88. var localizedName = _prototypeManager.TryIndex(reagent.Prototype, out ReagentPrototype? p)
  89. ? p.LocalizedName
  90. : Loc.GetString("reagent-dispenser-window-reagent-name-not-found-text");
  91. var nameLabel = new Label { Text = $"{localizedName}: " };
  92. var quantityLabel = new Label
  93. {
  94. Text = Loc.GetString("reagent-dispenser-window-quantity-label-text", ("quantity", quantity)),
  95. StyleClasses = { StyleNano.StyleClassLabelSecondaryColor },
  96. };
  97. ContainerInfo.Children.Add(new BoxContainer
  98. {
  99. Orientation = LayoutOrientation.Horizontal,
  100. Children =
  101. {
  102. nameLabel,
  103. quantityLabel,
  104. }
  105. });
  106. }
  107. }
  108. }
  109. }