Skip to content

Commit

Permalink
Add a tab showing the production summary (shpaass#38)
Browse files Browse the repository at this point in the history
I tried to reuse the existing UI of YAFC, so I based the whole thing on
a `ProjectPageContents` and a `ProjectPageView`, so it would be
recognized and fit into the `MainScreen` (tabs) and serialization.

The UI of the new 'Summary' tab is ugly, I tried making it nicer, but I
found it hard to understand the `ImGui` and its features and how to use
them... So I propose this could be further improved om in separate PRs
to get the basic functionality/feature into YAFC already and make it
available for everyone (I used it a lot and cannot live without this
anymore).

I also fixed some issues I found while implementing the Summary tab,
moved to shpaass#31 and shpaass#34, except for:
* calculating `DatGrid` width when header is not used (I found the
header useless here)

The original idea is from
ShadowTheAge#123
  • Loading branch information
shpaass authored Feb 29, 2024
2 parents d930ab7 + c2397ce commit afcb955
Show file tree
Hide file tree
Showing 10 changed files with 344 additions and 12 deletions.
11 changes: 10 additions & 1 deletion YAFC/Widgets/DataGrid.cs
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,14 @@ private void BuildHeaderResizer(ImGui gui, DataColumn<TData> column, Rect rect)
}
}

private void CalculateWidth(ImGui gui) {
var x = 0f;
foreach (var column in columns) {
x += column.width + spacing;
}
width = MathF.Max(x + 0.2f - spacing, gui.width - 1f);
}

public void BuildHeader(ImGui gui) {
var spacing = innerPadding.left + innerPadding.right;
var x = 0f;
Expand All @@ -111,7 +119,7 @@ public void BuildHeader(ImGui gui) {
}
}
}
width = MathF.Max(x + 0.2f - spacing, gui.width - 1f);
CalculateWidth(gui);

var separator = gui.AllocateRect(x, 0.1f);
if (gui.isBuilding) {
Expand Down Expand Up @@ -141,6 +149,7 @@ public Rect BuildRow(ImGui gui, TData element, float startX = 0f) {
buildGroup.Complete();
}

CalculateWidth(gui);
var rect = gui.lastRect;
var bottom = gui.lastRect.Bottom;
if (gui.isBuilding)
Expand Down
2 changes: 1 addition & 1 deletion YAFC/Widgets/MainScreenTabBar.cs
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ private void BuildContents(ImGui gui) {
changePageTo = prevPage;
changePage = isActive ? 1 : 2;
}
project.RecordUndo(true).displayPages.RemoveAt(i);
screen.ClosePage(pageGuid);
i--;
}
}
Expand Down
33 changes: 33 additions & 0 deletions YAFC/Windows/MainScreen.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@

namespace YAFC {
public class MainScreen : WindowMain, IKeyboardFocus, IProgress<(string, string)> {
///<summary>Unique ID for the Summary page</summary>
public static readonly Guid SummaryGuid = Guid.Parse("9bdea333-4be2-4be3-b708-b36a64672a40");
public static MainScreen Instance { get; private set; }
private readonly ObjectTooltip objectTooltip = new ObjectTooltip();
private readonly List<PseudoScreen> pseudoScreens = new List<PseudoScreen>();
Expand All @@ -28,6 +30,7 @@ public class MainScreen : WindowMain, IKeyboardFocus, IProgress<(string, string)
private ProjectPage _secondaryPage;
public ProjectPage secondaryPage => _secondaryPage;
private ProjectPageView secondaryPageView;
private readonly SummaryView summaryView;

private bool analysisUpdatePending;
private SearchQuery pageSearch;
Expand All @@ -40,9 +43,11 @@ public class MainScreen : WindowMain, IKeyboardFocus, IProgress<(string, string)
private readonly Dictionary<Type, ProjectPageView> secondaryPageViews = new Dictionary<Type, ProjectPageView>();

public MainScreen(int display, Project project) : base(default) {
summaryView = new SummaryView();
RegisterPageView<ProductionTable>(new ProductionTableView());
RegisterPageView<AutoPlanner>(new AutoPlannerView());
RegisterPageView<ProductionSummary>(new ProductionSummaryView());
RegisterPageView<Summary>(summaryView);
searchGui = new ImGui(BuildSearch, new Padding(1f)) { boxShadow = RectangleBorder.Thin, boxColor = SchemeColor.Background };
Instance = this;
tabBar = new MainScreenTabBar(this);
Expand Down Expand Up @@ -71,10 +76,17 @@ private void SetProject(Project project) {
if (project.displayPages.Count == 0)
project.displayPages.Add(project.pages[0].guid);

// Hack to activate all page solvers for the summary view
foreach (var page in project.pages) {
page.SetActive(true);
page.SetActive(false);
}

SetActivePage(project.FindPage(project.displayPages[0]));
project.metaInfoChanged += ProjectOnMetaInfoChanged;
project.settings.changed += ProjectSettingsChanged;
InputSystem.Instance.SetDefaultKeyboardFocus(this);
summaryView.SetProject(project);
}

private void ProjectSettingsChanged(bool visualOnly) {
Expand Down Expand Up @@ -338,6 +350,9 @@ private void SettingsDropdown(ImGui gui) {
if (gui.BuildContextMenuButton("Preferences") && gui.CloseDropdown())
PreferencesScreen.Show();

if (gui.BuildContextMenuButton("Summary") && gui.CloseDropdown())
ShowSummaryTab();

if (gui.BuildContextMenuButton("Never Enough Items Explorer", "Ctrl+" + ImGuiUtils.ScanToString(SDL.SDL_Scancode.SDL_SCANCODE_N)) && gui.CloseDropdown())
ShowNeie();

Expand Down Expand Up @@ -443,6 +458,24 @@ public void ClosePseudoScreen(PseudoScreen screen) {
rootGui.Rebuild();
}

public void ClosePage(Guid page) {
project.RecordUndo(true).displayPages.Remove(page);
}

public void ShowSummaryTab() {

ProjectPage summaryPage = project.FindPage(SummaryGuid);
if (summaryPage == null) {

summaryPage = new ProjectPage(project, typeof(Summary), false, SummaryGuid) {
name = "Summary",
};
project.pages.Add(summaryPage);
}

SetActivePage(summaryPage);
}

public bool KeyDown(SDL.SDL_Keysym key) {
var ctrl = (key.mod & SDL.SDL_Keymod.KMOD_CTRL) != 0;
if (ctrl) {
Expand Down
12 changes: 9 additions & 3 deletions YAFC/Windows/ProjectPageSettingsPanel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -68,14 +68,20 @@ public override void Build(ImGui gui) {

gui.allocator = RectAllocator.LeftRow;
if (editingPage != null && gui.BuildRedButton("Delete page")) {
Project.current.RemovePage(editingPage);
if (editingPage.canDelete) {
Project.current.RemovePage(editingPage);
}
else {
// Only hide if the (singleton) page cannot be deleted
MainScreen.Instance.ClosePage(editingPage.guid);
}
Close();
}
}
}

private void OtherToolsDropdown(ImGui gui) {
if (gui.BuildContextMenuButton("Duplicate page")) {
if (editingPage.guid != MainScreen.SummaryGuid && gui.BuildContextMenuButton("Duplicate page")) {
gui.CloseDropdown();
var project = editingPage.owner;
var collector = new ErrorCollector();
Expand All @@ -92,7 +98,7 @@ private void OtherToolsDropdown(ImGui gui) {
}
}

if (gui.BuildContextMenuButton("Share (export string to clipboard)")) {
if (editingPage.guid != MainScreen.SummaryGuid && gui.BuildContextMenuButton("Share (export string to clipboard)")) {
gui.CloseDropdown();
var data = JsonUtils.SaveToJson(editingPage);
using (var targetStream = new MemoryStream()) {
Expand Down
4 changes: 2 additions & 2 deletions YAFC/Workspace/ProductionTable/ProductionTableView.cs
Original file line number Diff line number Diff line change
Expand Up @@ -712,9 +712,9 @@ private void DrawDesiredProduct(ImGui gui, ProductionLink element) {
element.RecordUndo().amount = newAmount;
}

public override void Rebuild(bool visuaOnly = false) {
public override void Rebuild(bool visualOnly = false) {
flatHierarchyBuilder.SetData(model);
base.Rebuild(visuaOnly);
base.Rebuild(visualOnly);
}

private void BuildGoodsIcon(ImGui gui, Goods goods, ProductionLink link, float amount, ProductDropdownType dropdownType, RecipeRow recipe, ProductionTable context, Goods[] variants = null) {
Expand Down
Loading

0 comments on commit afcb955

Please sign in to comment.