From bf4c6bd19cf604867dfd40ebfdc0ebe7e80527e0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 17:45:03 +0200 Subject: [PATCH 01/31] Implement Itemsystem --- src/app/project/game-model/GameModel.ts | 59 +++++++++++++++++++ .../project/game-model/ModelComponentType.ts | 4 +- .../game-model/inventory/AbstractItemGroup.ts | 10 ++++ .../game-model/inventory/ConcreteItemGroup.ts | 17 ++++++ src/app/project/game-model/inventory/Item.ts | 7 +++ .../project/game-model/inventory/ItemGroup.ts | 7 +++ .../game-model/inventory/ItemQuality.ts | 10 ++++ 7 files changed, 113 insertions(+), 1 deletion(-) create mode 100644 src/app/project/game-model/inventory/AbstractItemGroup.ts create mode 100644 src/app/project/game-model/inventory/ConcreteItemGroup.ts create mode 100644 src/app/project/game-model/inventory/Item.ts create mode 100644 src/app/project/game-model/inventory/ItemGroup.ts create mode 100644 src/app/project/game-model/inventory/ItemQuality.ts diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index 295b6bb..86a2003 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -11,6 +11,11 @@ import {SimpleTemplateGamesystem} from "./templates/simpleGamesystem/SimpleTempl import {ProductTemplateSystem} from "./templates/productGamesystem/ProductTemplateSystem"; import {ProductTemplateCreator} from "./templates/productGamesystem/ProductTemplateCreator"; import {CharacterRelation} from "./characters/CharacterRelation"; +import {ItemGroup} from "./inventory/ItemGroup"; +import {AbstractItemGroup} from "./inventory/AbstractItemGroup"; +import {GameModelLoader} from "../../../../app/storage/loader/GameModelLoader"; +import {ConcreteItemGroup} from "./inventory/ConcreteItemGroup"; +import {Item} from "./inventory/Item"; export class GameModel { gameModelName: string @@ -18,9 +23,63 @@ export class GameModel { gamesystems: Gamesystem[] = []; scriptAccounts: ScriptAccount[] = []; characters: Character[] = [] + itemgroups: ItemGroup[] = [] constructor(gameModelName: string) { this.gameModelName = gameModelName; + + this.addAbstractItemgroup("Clothing", undefined); + this.addAbstractItemgroup("Inventory", undefined); + this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); + this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); + } + + addAbstractItemgroup(groupName: string, parentgroup: AbstractItemGroup | undefined) { + //Ensure that Itemgroup does not exist + if(parentgroup == undefined) { + if(GameModel.findItemgroupByName(groupName, this.itemgroups) == undefined) { + this.itemgroups.push(new AbstractItemGroup(groupName, "", ModelComponentType.ITEMGROUP)); + } + } else { + if(GameModel.findItemgroupByName(groupName, parentgroup.children) == undefined) { + parentgroup.addChildItemgroup(new AbstractItemGroup(groupName, "", ModelComponentType.ITEMGROUP)); + } + } + } + + addConcreteItemgroup(groupName: string, parentgroup: AbstractItemGroup) { + //Ensure that Itemgroup does not exist + if(parentgroup == undefined) { + if(GameModel.findItemgroupByName(groupName, this.itemgroups) == undefined) { + this.itemgroups.push(new ConcreteItemGroup(groupName, "", ModelComponentType.ITEMGROUP)); + } + } else { + if(GameModel.findItemgroupByName(groupName, parentgroup.children) == undefined) { + parentgroup.addChildItemgroup(new ConcreteItemGroup(groupName, "", ModelComponentType.ITEMGROUP)); + } + } + } + + addItem(itemName: string, conceteItemgroupName: string) { + const itemgroup = GameModel.findItemgroupByName(conceteItemgroupName, this.itemgroups); + if(itemgroup instanceof ConcreteItemGroup) { + itemgroup.addItem(new Item(itemName, "", ModelComponentType.ITEM )) + } + } + + private static findItemgroupByName(name: string, itemgroups: ItemGroup[]) { + const itemgroupQueue: ItemGroup[] = itemgroups.concat(); + while(itemgroupQueue.length > 0 ) { + const currentItemgroup = itemgroupQueue.shift()!; + + if(currentItemgroup.componentName === name) { + return currentItemgroup; + } + + if(currentItemgroup instanceof AbstractItemGroup) { + currentItemgroup.children.forEach(itemgroup => itemgroupQueue.push(itemgroup)); + } + } } addGamesystem(gamesystem: Gamesystem) { diff --git a/src/app/project/game-model/ModelComponentType.ts b/src/app/project/game-model/ModelComponentType.ts index 14eaf8b..ffef110 100644 --- a/src/app/project/game-model/ModelComponentType.ts +++ b/src/app/project/game-model/ModelComponentType.ts @@ -1,6 +1,8 @@ export enum ModelComponentType { SCRIPTACCOUNT, GAMESYTEM, - CHARACTER + CHARACTER, + ITEMGROUP, + ITEM } diff --git a/src/app/project/game-model/inventory/AbstractItemGroup.ts b/src/app/project/game-model/inventory/AbstractItemGroup.ts new file mode 100644 index 0000000..9cb8a32 --- /dev/null +++ b/src/app/project/game-model/inventory/AbstractItemGroup.ts @@ -0,0 +1,10 @@ +import {ItemGroup} from "./ItemGroup"; + +export class AbstractItemGroup extends ItemGroup { + + children: ItemGroup[] = []; + + addChildItemgroup(itemGroup: ItemGroup) { + this.children.push(itemGroup) + } +} diff --git a/src/app/project/game-model/inventory/ConcreteItemGroup.ts b/src/app/project/game-model/inventory/ConcreteItemGroup.ts new file mode 100644 index 0000000..3dad098 --- /dev/null +++ b/src/app/project/game-model/inventory/ConcreteItemGroup.ts @@ -0,0 +1,17 @@ +import {ItemGroup} from "./ItemGroup"; +import {Item} from "./Item"; + +export class ConcreteItemGroup extends ItemGroup { + + items: Item[] = []; + + addItem(item: Item) { + if(this.findItemByName(item.componentName) == undefined) { + this.items.push(item); + } + } + + findItemByName(itemName: string) { + return this.items.find(item => item.componentName === itemName); + } +} diff --git a/src/app/project/game-model/inventory/Item.ts b/src/app/project/game-model/inventory/Item.ts new file mode 100644 index 0000000..179aa18 --- /dev/null +++ b/src/app/project/game-model/inventory/Item.ts @@ -0,0 +1,7 @@ +import {ModelComponent} from "../ModelComponent"; +import {ItemGroup} from "./ItemGroup"; + +export class Item extends ModelComponent { + + inheritedGroups: ItemGroup[] = [] +} diff --git a/src/app/project/game-model/inventory/ItemGroup.ts b/src/app/project/game-model/inventory/ItemGroup.ts new file mode 100644 index 0000000..ab21f62 --- /dev/null +++ b/src/app/project/game-model/inventory/ItemGroup.ts @@ -0,0 +1,7 @@ +import {ModelComponent} from "../ModelComponent"; +import {ItemQuality} from "./ItemQuality"; + +export abstract class ItemGroup extends ModelComponent { + + requiredItemQualities: ItemQuality[] = [] +} diff --git a/src/app/project/game-model/inventory/ItemQuality.ts b/src/app/project/game-model/inventory/ItemQuality.ts new file mode 100644 index 0000000..fa6abe1 --- /dev/null +++ b/src/app/project/game-model/inventory/ItemQuality.ts @@ -0,0 +1,10 @@ +export class ItemQuality { + + key: string + value: number + + constructor(key: string, value: number) { + this.key = key; + this.value = value; + } +} -- 2.34.1 From a57024c6af44895746c6119f8550609af3f9928b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 17:48:36 +0200 Subject: [PATCH 02/31] Automatically add Owning group of item to inherited group-list --- src/app/project/game-model/GameModel.ts | 1 - .../project/game-model/inventory/ConcreteItemGroup.ts | 1 + src/app/project/game-model/inventory/Item.ts | 10 ++++++++++ 3 files changed, 11 insertions(+), 1 deletion(-) diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index 86a2003..3d75321 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -13,7 +13,6 @@ import {ProductTemplateCreator} from "./templates/productGamesystem/ProductTempl import {CharacterRelation} from "./characters/CharacterRelation"; import {ItemGroup} from "./inventory/ItemGroup"; import {AbstractItemGroup} from "./inventory/AbstractItemGroup"; -import {GameModelLoader} from "../../../../app/storage/loader/GameModelLoader"; import {ConcreteItemGroup} from "./inventory/ConcreteItemGroup"; import {Item} from "./inventory/Item"; diff --git a/src/app/project/game-model/inventory/ConcreteItemGroup.ts b/src/app/project/game-model/inventory/ConcreteItemGroup.ts index 3dad098..478721c 100644 --- a/src/app/project/game-model/inventory/ConcreteItemGroup.ts +++ b/src/app/project/game-model/inventory/ConcreteItemGroup.ts @@ -7,6 +7,7 @@ export class ConcreteItemGroup extends ItemGroup { addItem(item: Item) { if(this.findItemByName(item.componentName) == undefined) { + item.addInheritedGroup(this); this.items.push(item); } } diff --git a/src/app/project/game-model/inventory/Item.ts b/src/app/project/game-model/inventory/Item.ts index 179aa18..f1d055f 100644 --- a/src/app/project/game-model/inventory/Item.ts +++ b/src/app/project/game-model/inventory/Item.ts @@ -4,4 +4,14 @@ import {ItemGroup} from "./ItemGroup"; export class Item extends ModelComponent { inheritedGroups: ItemGroup[] = [] + + addInheritedGroup(itemgroup: ItemGroup) { + if(this.findItemgroupByName(itemgroup.componentName) == undefined) { + this.inheritedGroups.push(itemgroup); + } + } + + findItemgroupByName(groupName: string) { + return this.inheritedGroups.find(group => group.componentName === groupName); + } } -- 2.34.1 From dd73d0d60b8522e8c221766b0acdb24e9dc82d01 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 17:57:29 +0200 Subject: [PATCH 03/31] Opening Item-Overview --- src/app/app.component.html | 5 ++++ src/app/app.component.ts | 6 +++++ src/app/app.module.ts | 4 +++- .../ModelComponentTypeUtillities.ts | 6 +++++ .../item-overview.component.html | 1 + .../item-overview.component.scss | 0 .../item-overview.component.spec.ts | 23 +++++++++++++++++++ .../item-overview/item-overview.component.ts | 23 +++++++++++++++++++ 8 files changed, 67 insertions(+), 1 deletion(-) create mode 100644 src/app/side-overviews/item-overview/item-overview.component.html create mode 100644 src/app/side-overviews/item-overview/item-overview.component.scss create mode 100644 src/app/side-overviews/item-overview/item-overview.component.spec.ts create mode 100644 src/app/side-overviews/item-overview/item-overview.component.ts diff --git a/src/app/app.component.html b/src/app/app.component.html index 0626929..899bd31 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -6,6 +6,9 @@ (click)="openGamesystemsOverview()">code + + @@ -23,11 +26,13 @@ + +
diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 3ad2831..8272f56 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -254,6 +254,11 @@ export class AppComponent implements OnInit{ this.drawer!.open() } + openOverview(overviewType: ModelComponentType) { + this.openContent = overviewType; + this.drawer!.open(); + } + protected readonly ModelComponentType = ModelComponentType; closeContentOverview() { @@ -284,4 +289,5 @@ export class AppComponent implements OnInit{ } + protected readonly open = open; } diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 34970f6..14cd10e 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -82,6 +82,7 @@ import { import { StateInitialCellComponent } from "./editor/gamesystem-editor/state-editor/simple-state-editor/state-initial-cell/state-initial-cell.component"; +import {ItemOverviewComponent} from "./side-overviews/item-overview/item-overview.component"; // AoT requires an exported function for factories const httpLoaderFactory = (http: HttpClient): TranslateHttpLoader => new TranslateHttpLoader(http, './assets/i18n/', '.json'); @@ -107,7 +108,8 @@ const httpLoaderFactory = (http: HttpClient): TranslateHttpLoader => new Transl CharacterOverviewComponent, CharacterEditorComponent, TemplateSpecificatorComponent, - StateInitialCellComponent + StateInitialCellComponent, + ItemOverviewComponent ], imports: [ BrowserModule, diff --git a/src/app/project/game-model/ModelComponentTypeUtillities.ts b/src/app/project/game-model/ModelComponentTypeUtillities.ts index aa736fd..984a7a2 100644 --- a/src/app/project/game-model/ModelComponentTypeUtillities.ts +++ b/src/app/project/game-model/ModelComponentTypeUtillities.ts @@ -6,6 +6,8 @@ export class ModelComponentTypeUtillities { case ModelComponentType.SCRIPTACCOUNT: return "ScriptAccounts"; case ModelComponentType.GAMESYTEM: return "Gamesystems"; case ModelComponentType.CHARACTER: return "Characters" + case ModelComponentType.ITEM: return "Items"; + case ModelComponentType.ITEMGROUP: return "Itemgroups"; default: return "Undefined"; } } @@ -15,6 +17,8 @@ export class ModelComponentTypeUtillities { case ModelComponentType.SCRIPTACCOUNT: return "ScriptAccount"; case ModelComponentType.GAMESYTEM: return "Gamesystem"; case ModelComponentType.CHARACTER: return "Character" + case ModelComponentType.ITEM: return "Item"; + case ModelComponentType.ITEMGROUP: return "Itemgroup"; default: return "Undefined"; } } @@ -24,6 +28,8 @@ export class ModelComponentTypeUtillities { case "gamesystem": return ModelComponentType.GAMESYTEM; case "scriptaccount": return ModelComponentType.SCRIPTACCOUNT; case "character": return ModelComponentType.CHARACTER + case "item": return ModelComponentType.ITEM; + case "itemgroup": return ModelComponentType.ITEMGROUP; } } } diff --git a/src/app/side-overviews/item-overview/item-overview.component.html b/src/app/side-overviews/item-overview/item-overview.component.html new file mode 100644 index 0000000..8678a9e --- /dev/null +++ b/src/app/side-overviews/item-overview/item-overview.component.html @@ -0,0 +1 @@ +

item-overview works!

diff --git a/src/app/side-overviews/item-overview/item-overview.component.scss b/src/app/side-overviews/item-overview/item-overview.component.scss new file mode 100644 index 0000000..e69de29 diff --git a/src/app/side-overviews/item-overview/item-overview.component.spec.ts b/src/app/side-overviews/item-overview/item-overview.component.spec.ts new file mode 100644 index 0000000..58c2547 --- /dev/null +++ b/src/app/side-overviews/item-overview/item-overview.component.spec.ts @@ -0,0 +1,23 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { ItemOverviewComponent } from './item-overview.component'; + +describe('ItemOverviewComponent', () => { + let component: ItemOverviewComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + imports: [ItemOverviewComponent] + }) + .compileComponents(); + + fixture = TestBed.createComponent(ItemOverviewComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/app/side-overviews/item-overview/item-overview.component.ts b/src/app/side-overviews/item-overview/item-overview.component.ts new file mode 100644 index 0000000..26a0e91 --- /dev/null +++ b/src/app/side-overviews/item-overview/item-overview.component.ts @@ -0,0 +1,23 @@ +import {Component, Input} from '@angular/core'; +import {GameModel} from "../../project/game-model/GameModel"; + +interface TreeNode { + name: string, + children: TreeNode[]; +} + +interface FlatNode { + expandable: boolean, + name: string, + level: number +} + +@Component({ + selector: 'app-item-overview', + templateUrl: './item-overview.component.html', + styleUrl: './item-overview.component.scss' +}) +export class ItemOverviewComponent { + + @Input() gameModel: GameModel | undefined +} -- 2.34.1 From 5a3c0e9d759f0537b1b1778fb29dcab332d570ec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 18:14:42 +0200 Subject: [PATCH 04/31] Basic Visualization of Itemgroups and their Items --- src/app/app.component.html | 2 +- src/app/project/game-model/GameModel.ts | 3 + .../item-overview.component.html | 18 +++++ .../item-overview/item-overview.component.ts | 70 +++++++++++++++++-- 4 files changed, 85 insertions(+), 8 deletions(-) diff --git a/src/app/app.component.html b/src/app/app.component.html index 899bd31..82cab2d 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -32,7 +32,7 @@ - +
diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index 3d75321..393c8c3 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -31,6 +31,9 @@ export class GameModel { this.addAbstractItemgroup("Inventory", undefined); this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); + + this.addItem("Hose 1", "Hose"); + this.addItem("Hose 2", "Hose"); } addAbstractItemgroup(groupName: string, parentgroup: AbstractItemGroup | undefined) { diff --git a/src/app/side-overviews/item-overview/item-overview.component.html b/src/app/side-overviews/item-overview/item-overview.component.html index 8678a9e..74e67b4 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.html +++ b/src/app/side-overviews/item-overview/item-overview.component.html @@ -1 +1,19 @@

item-overview works!

+ + + + + + {{node.name}} + + + + + {{node.name}} + + diff --git a/src/app/side-overviews/item-overview/item-overview.component.ts b/src/app/side-overviews/item-overview/item-overview.component.ts index 26a0e91..7f70374 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.ts +++ b/src/app/side-overviews/item-overview/item-overview.component.ts @@ -1,10 +1,13 @@ -import {Component, Input} from '@angular/core'; +import {Component, Input, OnInit} from '@angular/core'; import {GameModel} from "../../project/game-model/GameModel"; - -interface TreeNode { - name: string, - children: TreeNode[]; -} +import {FlatTreeControl} from "@angular/cdk/tree"; +import {MatTreeFlatDataSource, MatTreeFlattener} from "@angular/material/tree"; +import {ItemGroup} from "../../project/game-model/inventory/ItemGroup"; +import {AbstractItemGroup} from "../../project/game-model/inventory/AbstractItemGroup"; +import {ConcreteItemGroup} from "../../project/game-model/inventory/ConcreteItemGroup"; +import {ModelComponent} from "../../project/game-model/ModelComponent"; +import {Item} from "../../project/game-model/inventory/Item"; +import {ModelComponentType} from "../../project/game-model/ModelComponentType"; interface FlatNode { expandable: boolean, @@ -17,7 +20,60 @@ interface FlatNode { templateUrl: './item-overview.component.html', styleUrl: './item-overview.component.scss' }) -export class ItemOverviewComponent { +export class ItemOverviewComponent implements OnInit{ @Input() gameModel: GameModel | undefined + + private _transformer = (node: ModelComponent, level: number) => { + if(node instanceof AbstractItemGroup) { + return { + expandable: !!node.children && node.children.length > 0, + name: node.componentName, + level: level, + }; + } else if(node instanceof ConcreteItemGroup) { + return { + expandable: !!node.items && node.items.length > 0, + name: node.componentName, + level: level + } + } else { + return { + expandable: false, + name: node.componentName, + level: level + } + } + }; + + + treeControl = new FlatTreeControl( + node => node.level, + node => node.expandable, + ); + + treeFlattener = new MatTreeFlattener( + this._transformer, + node => node.level, + node => node.expandable, + node => this.getNodeChildren(node) + ); + + dataSource = new MatTreeFlatDataSource(this.treeControl, this.treeFlattener); + + hasChild = (_: number, node: FlatNode) => node.expandable; + + getNodeChildren(node: ModelComponent): ModelComponent[] { + if(node instanceof ConcreteItemGroup) { + return node.items; + } else if(node instanceof AbstractItemGroup) { + return node.children; + } else { + return []; + } + } + + ngOnInit() { + this.dataSource.data = this.gameModel!.itemgroups; + } } -- 2.34.1 From db0455cd0707e5e42cbf41acc3c5f8a37f1c2103 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 18:22:49 +0200 Subject: [PATCH 05/31] Prettier Visualization of Itemgroups --- .../item-overview.component.html | 12 ++++-- .../item-overview.component.scss | 41 +++++++++++++++++++ .../item-overview/item-overview.component.ts | 12 ++++-- 3 files changed, 58 insertions(+), 7 deletions(-) diff --git a/src/app/side-overviews/item-overview/item-overview.component.html b/src/app/side-overviews/item-overview/item-overview.component.html index 74e67b4..f7569d0 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.html +++ b/src/app/side-overviews/item-overview/item-overview.component.html @@ -1,19 +1,23 @@

item-overview works!

- + - + + folder + data_object {{node.name}} - - + folder + data_object {{node.name}} diff --git a/src/app/side-overviews/item-overview/item-overview.component.scss b/src/app/side-overviews/item-overview/item-overview.component.scss index e69de29..d799155 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.scss +++ b/src/app/side-overviews/item-overview/item-overview.component.scss @@ -0,0 +1,41 @@ +.mat-tree-node { + min-height: 1.8em !important; + height: 1.8em; +} + + +.small-icon-button { + width: 26px !important; + height: 26px !important; + padding: 0px !important; + display: inline-flex !important; + align-items: center; + justify-content: center; + margin-left: 5px; + margin-right: 5px; + margin-bottom: 2px; + + & > *[role=img] { + width: 18px; + height: 18px; + font-size: 18px; + + svg { + width: 18px; + height: 18px; + } + } + + .mat-mdc-button-touch-target { + width: 22px !important; + height: 22px !important; + } +} + +.small-icon-button mat-icon { + color: whitesmoke; +} + +.selected-node { + background-color: #545456 +} diff --git a/src/app/side-overviews/item-overview/item-overview.component.ts b/src/app/side-overviews/item-overview/item-overview.component.ts index 7f70374..44ee44a 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.ts +++ b/src/app/side-overviews/item-overview/item-overview.component.ts @@ -12,7 +12,8 @@ import {ModelComponentType} from "../../project/game-model/ModelComponentType"; interface FlatNode { expandable: boolean, name: string, - level: number + level: number, + type: ModelComponentType } @Component({ @@ -30,18 +31,21 @@ export class ItemOverviewComponent implements OnInit{ expandable: !!node.children && node.children.length > 0, name: node.componentName, level: level, + type: ModelComponentType.ITEMGROUP }; } else if(node instanceof ConcreteItemGroup) { return { expandable: !!node.items && node.items.length > 0, name: node.componentName, - level: level + level: level, + type: ModelComponentType.ITEMGROUP } } else { return { expandable: false, name: node.componentName, - level: level + level: level, + type: ModelComponentType.ITEM } } }; @@ -76,4 +80,6 @@ export class ItemOverviewComponent implements OnInit{ ngOnInit() { this.dataSource.data = this.gameModel!.itemgroups; } + + protected readonly ModelComponentType = ModelComponentType; } -- 2.34.1 From e1e9647b136115389d1f8a7de028a2557c471f48 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 18:23:13 +0200 Subject: [PATCH 06/31] Remove default angular test text --- .../side-overviews/item-overview/item-overview.component.html | 1 - 1 file changed, 1 deletion(-) diff --git a/src/app/side-overviews/item-overview/item-overview.component.html b/src/app/side-overviews/item-overview/item-overview.component.html index f7569d0..3867df5 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.html +++ b/src/app/side-overviews/item-overview/item-overview.component.html @@ -1,4 +1,3 @@ -

item-overview works!

-- 2.34.1 From c66049c4d8f9809a1a7ab2bdd617f0a0008b005c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Sun, 5 May 2024 18:29:44 +0200 Subject: [PATCH 07/31] Adapt Context-Menu to add Itemgroups and Items --- app/main.ts | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/app/main.ts b/app/main.ts index ba1a8b6..f6e57f9 100644 --- a/app/main.ts +++ b/app/main.ts @@ -96,6 +96,29 @@ function createWindow(): BrowserWindow { click: () => { win!.webContents.send('context-menu', "new-character"); } + }, + { + label: "Itemgroup", + submenu: [ + { + label: "Abstract Itemgroup", + click: () => { + win!.webContents.send('context-menu', "new-itemgroup_abstract") + } + }, + { + label: "Concrete Itemgroup", + click: () => { + win!.webContents.send('context-menu', "new-itemgroup_concrete") + } + }, + { + label: "Item", + click: () => { + win!.webContents.send("context-menu", "new-item") + } + } + ] } ] -- 2.34.1 From 7132030a81bb632089f347cf315f7f40fb3078b2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Mon, 6 May 2024 19:16:37 +0200 Subject: [PATCH 08/31] Open Itemgroup Editor --- src/app/app.component.html | 2 +- src/app/app.module.ts | 128 +++++++++--------- src/app/editor/editor.component.html | 1 + .../item-group-editor.component.html | 1 + .../item-group-editor.component.scss | 0 .../item-group-editor.component.spec.ts | 23 ++++ .../item-group-editor.component.ts | 12 ++ src/app/project/game-model/GameModel.ts | 2 +- .../item-overview.component.html | 4 +- .../item-overview/item-overview.component.ts | 20 ++- 10 files changed, 123 insertions(+), 70 deletions(-) create mode 100644 src/app/editor/items/item-group-editor/item-group-editor.component.html create mode 100644 src/app/editor/items/item-group-editor/item-group-editor.component.scss create mode 100644 src/app/editor/items/item-group-editor/item-group-editor.component.spec.ts create mode 100644 src/app/editor/items/item-group-editor/item-group-editor.component.ts diff --git a/src/app/app.component.html b/src/app/app.component.html index 82cab2d..836a9d0 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -32,7 +32,7 @@ - +
diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 14cd10e..da60456 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -83,6 +83,7 @@ import { StateInitialCellComponent } from "./editor/gamesystem-editor/state-editor/simple-state-editor/state-initial-cell/state-initial-cell.component"; import {ItemOverviewComponent} from "./side-overviews/item-overview/item-overview.component"; +import {ItemGroupEditorComponent} from "./editor/items/item-group-editor/item-group-editor.component"; // AoT requires an exported function for factories const httpLoaderFactory = (http: HttpClient): TranslateHttpLoader => new TranslateHttpLoader(http, './assets/i18n/', '.json'); @@ -111,69 +112,70 @@ const httpLoaderFactory = (http: HttpClient): TranslateHttpLoader => new Transl StateInitialCellComponent, ItemOverviewComponent ], - imports: [ - BrowserModule, - FormsModule, - HttpClientModule, - CoreModule, - SharedModule, - TranslateModule.forRoot({ - loader: { - provide: TranslateLoader, - useFactory: httpLoaderFactory, - deps: [HttpClient] - } - }), - BrowserAnimationsModule, - MatIcon, - MatToolbar, - MatButton, - MatFormField, - MatInput, - MatDrawerContainer, - MatDrawer, - MatIconButton, - MatMenuTrigger, - MatMenu, - MatMenuItem, - MatListItem, - MatActionList, - MatTabGroup, - MatTab, - MatTabLabel, - MatLabel, - MatFormField, - ReactiveFormsModule, - MatError, - MatDialogTitle, - MatDialogContent, - MatDialogActions, - MatMiniFabButton, - MatTreeModule, - MatTable, - MatColumnDef, - MatHeaderCell, - MatHeaderCellDef, - MatCellDef, - MatCell, - MatHeaderRow, - MatRow, - MatHeaderRowDef, - MatRowDef, - MatCheckbox, - MatSelect, - MatOption, - MatHint, - MatTooltip, - MatCard, - MatCardContent, - MatCardHeader, - MatAccordion, - MatExpansionPanel, - MatExpansionPanelTitle, - MatCardTitle, - MatExpansionPanelHeader - ], + imports: [ + BrowserModule, + FormsModule, + HttpClientModule, + CoreModule, + SharedModule, + TranslateModule.forRoot({ + loader: { + provide: TranslateLoader, + useFactory: httpLoaderFactory, + deps: [HttpClient] + } + }), + BrowserAnimationsModule, + MatIcon, + MatToolbar, + MatButton, + MatFormField, + MatInput, + MatDrawerContainer, + MatDrawer, + MatIconButton, + MatMenuTrigger, + MatMenu, + MatMenuItem, + MatListItem, + MatActionList, + MatTabGroup, + MatTab, + MatTabLabel, + MatLabel, + MatFormField, + ReactiveFormsModule, + MatError, + MatDialogTitle, + MatDialogContent, + MatDialogActions, + MatMiniFabButton, + MatTreeModule, + MatTable, + MatColumnDef, + MatHeaderCell, + MatHeaderCellDef, + MatCellDef, + MatCell, + MatHeaderRow, + MatRow, + MatHeaderRowDef, + MatRowDef, + MatCheckbox, + MatSelect, + MatOption, + MatHint, + MatTooltip, + MatCard, + MatCardContent, + MatCardHeader, + MatAccordion, + MatExpansionPanel, + MatExpansionPanelTitle, + MatCardTitle, + MatExpansionPanelHeader, + ItemGroupEditorComponent + ], providers: [], bootstrap: [AppComponent] }) diff --git a/src/app/editor/editor.component.html b/src/app/editor/editor.component.html index 23be637..985647c 100644 --- a/src/app/editor/editor.component.html +++ b/src/app/editor/editor.component.html @@ -20,5 +20,6 @@ > + diff --git a/src/app/editor/items/item-group-editor/item-group-editor.component.html b/src/app/editor/items/item-group-editor/item-group-editor.component.html new file mode 100644 index 0000000..a42a279 --- /dev/null +++ b/src/app/editor/items/item-group-editor/item-group-editor.component.html @@ -0,0 +1 @@ +

item-group-editor works!

diff --git a/src/app/editor/items/item-group-editor/item-group-editor.component.scss b/src/app/editor/items/item-group-editor/item-group-editor.component.scss new file mode 100644 index 0000000..e69de29 diff --git a/src/app/editor/items/item-group-editor/item-group-editor.component.spec.ts b/src/app/editor/items/item-group-editor/item-group-editor.component.spec.ts new file mode 100644 index 0000000..a6bbd54 --- /dev/null +++ b/src/app/editor/items/item-group-editor/item-group-editor.component.spec.ts @@ -0,0 +1,23 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { ItemGroupEditorComponent } from './item-group-editor.component'; + +describe('ItemGroupEditorComponent', () => { + let component: ItemGroupEditorComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + imports: [ItemGroupEditorComponent] + }) + .compileComponents(); + + fixture = TestBed.createComponent(ItemGroupEditorComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/app/editor/items/item-group-editor/item-group-editor.component.ts b/src/app/editor/items/item-group-editor/item-group-editor.component.ts new file mode 100644 index 0000000..ecccb74 --- /dev/null +++ b/src/app/editor/items/item-group-editor/item-group-editor.component.ts @@ -0,0 +1,12 @@ +import { Component } from '@angular/core'; + +@Component({ + selector: 'app-item-group-editor', + standalone: true, + imports: [], + templateUrl: './item-group-editor.component.html', + styleUrl: './item-group-editor.component.scss' +}) +export class ItemGroupEditorComponent { + +} diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index 393c8c3..d438107 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -69,7 +69,7 @@ export class GameModel { } } - private static findItemgroupByName(name: string, itemgroups: ItemGroup[]) { + public static findItemgroupByName(name: string, itemgroups: ItemGroup[]) { const itemgroupQueue: ItemGroup[] = itemgroups.concat(); while(itemgroupQueue.length > 0 ) { const currentItemgroup = itemgroupQueue.shift()!; diff --git a/src/app/side-overviews/item-overview/item-overview.component.html b/src/app/side-overviews/item-overview/item-overview.component.html index 3867df5..2622561 100644 --- a/src/app/side-overviews/item-overview/item-overview.component.html +++ b/src/app/side-overviews/item-overview/item-overview.component.html @@ -1,6 +1,6 @@ - + folder @@ -8,7 +8,7 @@ {{node.name}} - + + + diff --git a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts index 3369926..624eebd 100644 --- a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts +++ b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts @@ -16,6 +16,7 @@ export class InheritedItemCharacteristicEditorComponent implements OnInit{ datasource: MatTableDataSource = new MatTableDataSource(); displayedColumns: string[] = ['characteristic', 'value', 'edit'] + editedItemgroupCharacteristicValue: ItemgroupCharacteristicValue | undefined ngOnInit() { this.item!.initializeItemCharacteristics(); @@ -30,4 +31,12 @@ export class InheritedItemCharacteristicEditorComponent implements OnInit{ } return [] } + + editCharacteristicValue(itemCharacteristicValue: ItemgroupCharacteristicValue): void { + this.editedItemgroupCharacteristicValue = itemCharacteristicValue; + } + + finishEditing() { + this.editedItemgroupCharacteristicValue = undefined; + } } -- 2.34.1 From db0bd14ea885940a0ba286c4c78b529596d066fe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 07:04:19 +0200 Subject: [PATCH 21/31] Initialize Itemgroup Characteristic Values --- .../item-editor/item-editor.component.html | 2 +- .../item-editor/item-editor.component.ts | 12 ++++-- .../item-group-editor.component.ts | 3 +- .../game-model/inventory/AbstractItemGroup.ts | 7 +++ .../game-model/inventory/ConcreteItemGroup.ts | 11 ++++- src/app/project/game-model/inventory/Item.ts | 43 ++++++++++++++----- .../project/game-model/inventory/ItemGroup.ts | 25 +++++++++++ 7 files changed, 86 insertions(+), 17 deletions(-) diff --git a/src/app/editor/items/item-editor/item-editor.component.html b/src/app/editor/items/item-editor/item-editor.component.html index c15b565..8ff7a5d 100644 --- a/src/app/editor/items/item-editor/item-editor.component.html +++ b/src/app/editor/items/item-editor/item-editor.component.html @@ -4,7 +4,7 @@ - + {{itemgroup.componentName}} {{itemgroup.componentDescription}} diff --git a/src/app/editor/items/item-editor/item-editor.component.ts b/src/app/editor/items/item-editor/item-editor.component.ts index d259cb1..05a673d 100644 --- a/src/app/editor/items/item-editor/item-editor.component.ts +++ b/src/app/editor/items/item-editor/item-editor.component.ts @@ -17,29 +17,33 @@ export class ItemEditorComponent { @Input() gameModel: GameModel | undefined; - constructor(private dialog: MatDialog) { } onAddNewInheritedItemgroup() { + const itemgroups = this.item!.manuallyInheritedGroups.concat(this.item!.hierarchyInheritedGroups); const dialogRef = this.dialog.open(ItemgroupInheritorComponent, { - data: this.gameModel!.itemgroupsAsList.filter(group => !this.item!.inheritedGroups.includes(group)), + data: this.gameModel!.itemgroupsAsList.filter(group => !itemgroups.includes(group)), width: "400px" }) dialogRef.afterClosed().subscribe(res => { if(res != undefined) { - this.item!.inheritedGroups.push(res); + this.item!.addInheritedGroup(res); } }) } deleteInheritedItemgroup(itemgroup: ItemGroup) { - this.item!.inheritedGroups = this.item!.inheritedGroups.filter(group => group.componentName !== itemgroup.componentName); + this.item!.deleteInheritedGroup(itemgroup); } get automaticallyInheritedItemgroups() { return ItemgroupUtilities.findItemgroupPathToItem(this.item!.componentName, this.gameModel!.itemgroups); } + + get manuallyAndHierarchyItemgroups() { + return this.item!.hierarchyInheritedGroups.concat(this.item!.manuallyInheritedGroups); + } } diff --git a/src/app/editor/items/item-group-editor/item-group-editor.component.ts b/src/app/editor/items/item-group-editor/item-group-editor.component.ts index c47c0aa..2436e71 100644 --- a/src/app/editor/items/item-group-editor/item-group-editor.component.ts +++ b/src/app/editor/items/item-group-editor/item-group-editor.component.ts @@ -38,7 +38,8 @@ export class ItemGroupEditorComponent implements OnInit{ addItemgroupCharacteristic() { const itemgroupCharacteristic = new ItemGroupCharacteristic("", "", this.itemgroup!); - this.itemgroup!.itemGroupCharacteristics.push(itemgroupCharacteristic); + this.itemgroup!.addItemgroupCharacteristic(itemgroupCharacteristic); + this.itemQualityDatasource.data = this.itemgroup!.itemGroupCharacteristics; this.editedCharacteristic = itemgroupCharacteristic; } diff --git a/src/app/project/game-model/inventory/AbstractItemGroup.ts b/src/app/project/game-model/inventory/AbstractItemGroup.ts index e1b058a..5141f5a 100644 --- a/src/app/project/game-model/inventory/AbstractItemGroup.ts +++ b/src/app/project/game-model/inventory/AbstractItemGroup.ts @@ -1,4 +1,5 @@ import {ItemGroup} from "./ItemGroup"; +import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; export class AbstractItemGroup extends ItemGroup { @@ -8,4 +9,10 @@ export class AbstractItemGroup extends ItemGroup { this.children.push(itemGroup) itemGroup.parentGroup = this; } + + protected addCharacteristicValue(characteristic: ItemGroupCharacteristic): void { + //Do Nothing + } + + } diff --git a/src/app/project/game-model/inventory/ConcreteItemGroup.ts b/src/app/project/game-model/inventory/ConcreteItemGroup.ts index 605108c..21e6682 100644 --- a/src/app/project/game-model/inventory/ConcreteItemGroup.ts +++ b/src/app/project/game-model/inventory/ConcreteItemGroup.ts @@ -1,5 +1,6 @@ import {ItemGroup} from "./ItemGroup"; import {Item} from "./Item"; +import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; export class ConcreteItemGroup extends ItemGroup { @@ -8,7 +9,7 @@ export class ConcreteItemGroup extends ItemGroup { addItem(item: Item, parentItemgroups: ItemGroup[]) { if(this.findItemByName(item.componentName) == undefined) { parentItemgroups.forEach(itemgroup => { - item.inheritedGroups.push(itemgroup); + item.addInheritedHierarchyGroup(itemgroup); }) this.items.push(item); } @@ -17,4 +18,12 @@ export class ConcreteItemGroup extends ItemGroup { findItemByName(itemName: string) { return this.items.find(item => item.componentName === itemName); } + + protected addCharacteristicValue(characteristic: ItemGroupCharacteristic): void { + this.items.forEach(item => { + item.addCharacteristic(characteristic); + }) + } + + } diff --git a/src/app/project/game-model/inventory/Item.ts b/src/app/project/game-model/inventory/Item.ts index 6241ca9..bbe2140 100644 --- a/src/app/project/game-model/inventory/Item.ts +++ b/src/app/project/game-model/inventory/Item.ts @@ -5,17 +5,21 @@ import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; export class Item extends ModelComponent { - inheritedGroups: ItemGroup[] = [] + + manuallyInheritedGroups: ItemGroup[] = [] + hierarchyInheritedGroups: ItemGroup[] = [] itemCharacteristicValues: ItemgroupCharacteristicValue[] = [] initializeItemCharacteristics() { - this.inheritedGroups.forEach(itemGroup => { - itemGroup.itemGroupCharacteristics.forEach(characteristic => { - const characteristicValue = new ItemgroupCharacteristicValue(characteristic, 0); - if(!this.isValueInitialized(characteristic)) { - this.itemCharacteristicValues.push(characteristicValue); - } - }) + const inheritedGroups = this.manuallyInheritedGroups.concat(this.hierarchyInheritedGroups); + inheritedGroups.forEach(itemGroup => { + this.initializeItemCharacteristicsOfItemgroup(itemGroup); + }) + } + + initializeItemCharacteristicsOfItemgroup(itemGroup: ItemGroup) { + itemGroup.itemGroupCharacteristics.forEach(characteristic => { + this.addCharacteristic(characteristic); }) } @@ -25,11 +29,30 @@ export class Item extends ModelComponent { addInheritedGroup(itemgroup: ItemGroup) { if(this.findItemgroupByName(itemgroup.componentName) == undefined) { - this.inheritedGroups.push(itemgroup); + this.manuallyInheritedGroups.push(itemgroup); + this.initializeItemCharacteristicsOfItemgroup(itemgroup); } } findItemgroupByName(groupName: string) { - return this.inheritedGroups.find(group => group.componentName === groupName); + const itemgroups = this.hierarchyInheritedGroups.concat(this.manuallyInheritedGroups); + return itemgroups.find(group => group.componentName === groupName); + } + + addCharacteristic(characteristic: ItemGroupCharacteristic) { + const characteristicValue = new ItemgroupCharacteristicValue(characteristic, 0); + if(!this.isValueInitialized(characteristic)) { + this.itemCharacteristicValues.push(characteristicValue); + } + } + + deleteInheritedGroup(itemgroup: ItemGroup) { + this.manuallyInheritedGroups = this.manuallyInheritedGroups.filter(manually => manually.componentName !== itemgroup.componentName); + } + + addInheritedHierarchyGroup(itemgroup: ItemGroup) { + this.hierarchyInheritedGroups.push(itemgroup); + this.initializeItemCharacteristicsOfItemgroup(itemgroup); + } } diff --git a/src/app/project/game-model/inventory/ItemGroup.ts b/src/app/project/game-model/inventory/ItemGroup.ts index 9205238..3096e7b 100644 --- a/src/app/project/game-model/inventory/ItemGroup.ts +++ b/src/app/project/game-model/inventory/ItemGroup.ts @@ -1,10 +1,35 @@ import {ModelComponent} from "../ModelComponent"; import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; import {AbstractItemGroup} from "./AbstractItemGroup"; +import {Item} from "./Item"; export abstract class ItemGroup extends ModelComponent { itemGroupCharacteristics: ItemGroupCharacteristic[] = [] parentGroup: AbstractItemGroup | undefined + manuallyInheritedItems: Item[] = [] + + addItemgroupCharacteristic(itemgroupCharacteristic: ItemGroupCharacteristic) { + this.itemGroupCharacteristics.push(itemgroupCharacteristic); + this.addCharacteristicValueForManuallyItems(itemgroupCharacteristic); + this.addCharacteristicValue(itemgroupCharacteristic); + } + + protected abstract addCharacteristicValue(characteristic: ItemGroupCharacteristic): void; + + private addCharacteristicValueForManuallyItems(characteristic: ItemGroupCharacteristic) { + this.manuallyInheritedItems.forEach(item => { + item.addCharacteristic(characteristic); + }) + } + + inheritManualItem(item: Item) { + if(this.manuallyInheritedItems.find(inheritedItems => inheritedItems.componentName === item.componentName) == undefined) { + this.manuallyInheritedItems.push(item); + item.addInheritedGroup(this); + } + } + + } -- 2.34.1 From 34c139eecf124349ac00100f972dd7cce2b85884 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 07:06:51 +0200 Subject: [PATCH 22/31] Rerender table automatically on Change --- .../inherited-item-characteristic-editor.component.html | 2 +- .../inherited-item-characteristic-editor.component.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.html b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.html index a0e01af..42bbb40 100644 --- a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.html +++ b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.html @@ -1,4 +1,4 @@ - +
diff --git a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts index 624eebd..167bd38 100644 --- a/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts +++ b/src/app/editor/items/item-editor/inherited-item-characteristic-editor/inherited-item-characteristic-editor.component.ts @@ -24,7 +24,7 @@ export class InheritedItemCharacteristicEditorComponent implements OnInit{ } - private findCharacteristicValuesByItemgroup(itemGroup: ItemGroup): ItemgroupCharacteristicValue[] { + findCharacteristicValuesByItemgroup(itemGroup: ItemGroup): ItemgroupCharacteristicValue[] { const result = this.item?.itemCharacteristicValues.filter(value => value.key.itemgroup.componentName === itemGroup.componentName); if(result != undefined) { return result; -- 2.34.1 From aa6c051246949c55709588a6469802dd21e90831 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 07:19:05 +0200 Subject: [PATCH 23/31] Automatically initialize CharacteristicValues for manually Inherited groups --- src/app/project/game-model/GameModel.ts | 4 ++-- src/app/project/game-model/inventory/AbstractItemGroup.ts | 1 + src/app/project/game-model/inventory/Item.ts | 2 ++ src/app/project/game-model/inventory/ItemGroup.ts | 1 + 4 files changed, 6 insertions(+), 2 deletions(-) diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index a96ad25..a7d5c6c 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -29,7 +29,7 @@ export class GameModel { this.gameModelName = gameModelName; this.addAbstractItemgroup("Clothing", undefined); - this.addAbstractItemgroup("Inventory", undefined); + this.addConcreteItemgroup("Inventory", undefined); this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); @@ -50,7 +50,7 @@ export class GameModel { } } - addConcreteItemgroup(groupName: string, parentgroup: AbstractItemGroup) { + addConcreteItemgroup(groupName: string, parentgroup: AbstractItemGroup | undefined) { //Ensure that Itemgroup does not exist if(parentgroup == undefined) { if(GameModel.findItemgroupByName(groupName, this.itemgroups) == undefined) { diff --git a/src/app/project/game-model/inventory/AbstractItemGroup.ts b/src/app/project/game-model/inventory/AbstractItemGroup.ts index 5141f5a..5702524 100644 --- a/src/app/project/game-model/inventory/AbstractItemGroup.ts +++ b/src/app/project/game-model/inventory/AbstractItemGroup.ts @@ -11,6 +11,7 @@ export class AbstractItemGroup extends ItemGroup { } protected addCharacteristicValue(characteristic: ItemGroupCharacteristic): void { + console.log("Abstract Characteristic Value: Do nothing (" , characteristic.characteristicName , ")") //Do Nothing } diff --git a/src/app/project/game-model/inventory/Item.ts b/src/app/project/game-model/inventory/Item.ts index bbe2140..cc2a8ac 100644 --- a/src/app/project/game-model/inventory/Item.ts +++ b/src/app/project/game-model/inventory/Item.ts @@ -30,6 +30,7 @@ export class Item extends ModelComponent { addInheritedGroup(itemgroup: ItemGroup) { if(this.findItemgroupByName(itemgroup.componentName) == undefined) { this.manuallyInheritedGroups.push(itemgroup); + itemgroup.manuallyInheritedItems.push(this); this.initializeItemCharacteristicsOfItemgroup(itemgroup); } } @@ -40,6 +41,7 @@ export class Item extends ModelComponent { } addCharacteristic(characteristic: ItemGroupCharacteristic) { + console.log("Add Characteristic: " , characteristic) const characteristicValue = new ItemgroupCharacteristicValue(characteristic, 0); if(!this.isValueInitialized(characteristic)) { this.itemCharacteristicValues.push(characteristicValue); diff --git a/src/app/project/game-model/inventory/ItemGroup.ts b/src/app/project/game-model/inventory/ItemGroup.ts index 3096e7b..e4dd726 100644 --- a/src/app/project/game-model/inventory/ItemGroup.ts +++ b/src/app/project/game-model/inventory/ItemGroup.ts @@ -12,6 +12,7 @@ export abstract class ItemGroup extends ModelComponent { addItemgroupCharacteristic(itemgroupCharacteristic: ItemGroupCharacteristic) { this.itemGroupCharacteristics.push(itemgroupCharacteristic); this.addCharacteristicValueForManuallyItems(itemgroupCharacteristic); + console.log("[Itemgroup] Add ItemgroupCharacteristic ", itemgroupCharacteristic); this.addCharacteristicValue(itemgroupCharacteristic); } -- 2.34.1 From 133dc1d372e354a9495a43581e4e97ec94d76296 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 07:19:42 +0200 Subject: [PATCH 24/31] Remove logging statements --- src/app/project/game-model/inventory/AbstractItemGroup.ts | 1 - src/app/project/game-model/inventory/Item.ts | 1 - src/app/project/game-model/inventory/ItemGroup.ts | 1 - 3 files changed, 3 deletions(-) diff --git a/src/app/project/game-model/inventory/AbstractItemGroup.ts b/src/app/project/game-model/inventory/AbstractItemGroup.ts index 5702524..5141f5a 100644 --- a/src/app/project/game-model/inventory/AbstractItemGroup.ts +++ b/src/app/project/game-model/inventory/AbstractItemGroup.ts @@ -11,7 +11,6 @@ export class AbstractItemGroup extends ItemGroup { } protected addCharacteristicValue(characteristic: ItemGroupCharacteristic): void { - console.log("Abstract Characteristic Value: Do nothing (" , characteristic.characteristicName , ")") //Do Nothing } diff --git a/src/app/project/game-model/inventory/Item.ts b/src/app/project/game-model/inventory/Item.ts index cc2a8ac..6d0978c 100644 --- a/src/app/project/game-model/inventory/Item.ts +++ b/src/app/project/game-model/inventory/Item.ts @@ -41,7 +41,6 @@ export class Item extends ModelComponent { } addCharacteristic(characteristic: ItemGroupCharacteristic) { - console.log("Add Characteristic: " , characteristic) const characteristicValue = new ItemgroupCharacteristicValue(characteristic, 0); if(!this.isValueInitialized(characteristic)) { this.itemCharacteristicValues.push(characteristicValue); diff --git a/src/app/project/game-model/inventory/ItemGroup.ts b/src/app/project/game-model/inventory/ItemGroup.ts index e4dd726..3096e7b 100644 --- a/src/app/project/game-model/inventory/ItemGroup.ts +++ b/src/app/project/game-model/inventory/ItemGroup.ts @@ -12,7 +12,6 @@ export abstract class ItemGroup extends ModelComponent { addItemgroupCharacteristic(itemgroupCharacteristic: ItemGroupCharacteristic) { this.itemGroupCharacteristics.push(itemgroupCharacteristic); this.addCharacteristicValueForManuallyItems(itemgroupCharacteristic); - console.log("[Itemgroup] Add ItemgroupCharacteristic ", itemgroupCharacteristic); this.addCharacteristicValue(itemgroupCharacteristic); } -- 2.34.1 From fed0ca99bf03b9a7e4a7e06d42eb89c7169ce516 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 09:12:46 +0200 Subject: [PATCH 25/31] Persist Itemgroups --- app/main.ts | 4 ++ app/storage/ModelComponentFileDirectory.js | 1 + app/storage/ModelComponentFileDirectory.ts | 1 + app/storage/StoredGameModel.js | 3 +- app/storage/StoredGameModel.ts | 4 +- app/storage/loader/GameModelLoader.js | 2 +- app/storage/loader/GameModelLoader.ts | 2 +- app/storage/storing/ItemgroupStorage.js | 29 +++++++++ app/storage/storing/ItemgroupStorage.ts | 34 ++++++++++ src/app/app.component.ts | 6 +- src/app/project/game-model/GameModel.ts | 15 +++-- .../serializer/GamesystemSerializer.ts | 4 +- src/app/project/serializer/ItemSerializer.ts | 64 +++++++++++++++++++ testModel/items/Clothing/Clothing.json | 11 ++++ testModel/items/Clothing/Hose/Hose.json | 17 +++++ .../items/Clothing/Oberteil/Oberteil.json | 17 +++++ testModel/items/Inventory/Inventory.json | 22 +++++++ 17 files changed, 224 insertions(+), 12 deletions(-) create mode 100644 app/storage/storing/ItemgroupStorage.js create mode 100644 app/storage/storing/ItemgroupStorage.ts create mode 100644 src/app/project/serializer/ItemSerializer.ts create mode 100644 testModel/items/Clothing/Clothing.json create mode 100644 testModel/items/Clothing/Hose/Hose.json create mode 100644 testModel/items/Clothing/Oberteil/Oberteil.json create mode 100644 testModel/items/Inventory/Inventory.json diff --git a/app/main.ts b/app/main.ts index f6e57f9..cee7f28 100644 --- a/app/main.ts +++ b/app/main.ts @@ -8,6 +8,7 @@ import {ModelComponentFileDirectory} from "./storage/ModelComponentFileDirectory import {GamesystemStorage} from "./storage/storing/GamesystemStorage"; import {Character} from "../src/app/project/game-model/characters/Character"; import {CharacterStorage} from "./storage/storing/CharacterStorage"; +import {ItemgroupStorage} from "./storage/storing/ItemgroupStorage"; let win: BrowserWindow | null = null; const args = process.argv.slice(1), @@ -270,6 +271,9 @@ function recieveGameModelToStore(gameModel: StoredGameModel) { const characterStorage = new CharacterStorage(path.join(projectDirectory, ModelComponentFileDirectory.CHARACTER_DIR_NAME)) characterStorage.storeCharacters(gameModel.storedCharacters) + + const itemgroupStorage = new ItemgroupStorage(path.join(projectDirectory, ModelComponentFileDirectory.ITEMGROUP_DIR_NAME)) + itemgroupStorage.storeItemgroups(gameModel.storedItemgroups); } /*function deleteComponent(component: DeleteModel) { diff --git a/app/storage/ModelComponentFileDirectory.js b/app/storage/ModelComponentFileDirectory.js index 8d28902..eda48c4 100644 --- a/app/storage/ModelComponentFileDirectory.js +++ b/app/storage/ModelComponentFileDirectory.js @@ -7,4 +7,5 @@ exports.ModelComponentFileDirectory = ModelComponentFileDirectory; ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME = "script-accounts"; ModelComponentFileDirectory.GAMESYSTEM_DIR_NAME = "gamesystems"; ModelComponentFileDirectory.CHARACTER_DIR_NAME = "characters"; +ModelComponentFileDirectory.ITEMGROUP_DIR_NAME = "items"; //# sourceMappingURL=ModelComponentFileDirectory.js.map \ No newline at end of file diff --git a/app/storage/ModelComponentFileDirectory.ts b/app/storage/ModelComponentFileDirectory.ts index a0b9c8c..c68a714 100644 --- a/app/storage/ModelComponentFileDirectory.ts +++ b/app/storage/ModelComponentFileDirectory.ts @@ -2,4 +2,5 @@ export class ModelComponentFileDirectory { public static SCRIPTACCOUNT_DIR_NAME = "script-accounts" public static GAMESYSTEM_DIR_NAME = "gamesystems"; public static CHARACTER_DIR_NAME = "characters"; + static ITEMGROUP_DIR_NAME = "items"; } diff --git a/app/storage/StoredGameModel.js b/app/storage/StoredGameModel.js index 57bfbe7..2db851f 100644 --- a/app/storage/StoredGameModel.js +++ b/app/storage/StoredGameModel.js @@ -2,11 +2,12 @@ Object.defineProperty(exports, "__esModule", { value: true }); exports.StoredGameModel = void 0; class StoredGameModel { - constructor(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters) { + constructor(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups) { this.gameModelName = gameModelName; this.storedGamesystems = storedGamesystems; this.storedScriptAccounts = storedScriptAccounts; this.storedCharacters = storedCharacters; + this.storedItemgroups = storedItemgroups; } } exports.StoredGameModel = StoredGameModel; diff --git a/app/storage/StoredGameModel.ts b/app/storage/StoredGameModel.ts index d9d762b..7d9f330 100644 --- a/app/storage/StoredGameModel.ts +++ b/app/storage/StoredGameModel.ts @@ -6,13 +6,15 @@ export class StoredGameModel { storedGamesystems: StoreComponent[] storedScriptAccounts: StoreComponent[] storedCharacters: StoreComponent[] + storedItemgroups: StoreComponent[] constructor(gameModelName: string, storedScriptAccounts: StoreComponent[], storedGamesystems: StoreComponent[], - storedCharacters: StoreComponent[]) { + storedCharacters: StoreComponent[], storedItemgroups: StoreComponent[]) { this.gameModelName = gameModelName; this.storedGamesystems = storedGamesystems; this.storedScriptAccounts = storedScriptAccounts; this.storedCharacters = storedCharacters; + this.storedItemgroups = storedItemgroups; } } diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index 480dc36..d78f3b3 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -16,7 +16,7 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); - return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters); + return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, []); } loadScriptAccountComponents() { const scriptAccountDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME); diff --git a/app/storage/loader/GameModelLoader.ts b/app/storage/loader/GameModelLoader.ts index 615c354..fffebef 100644 --- a/app/storage/loader/GameModelLoader.ts +++ b/app/storage/loader/GameModelLoader.ts @@ -22,7 +22,7 @@ export class GameModelLoader { const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters() - return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters); + return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, []); } private loadScriptAccountComponents() { diff --git a/app/storage/storing/ItemgroupStorage.js b/app/storage/storing/ItemgroupStorage.js new file mode 100644 index 0000000..028aa92 --- /dev/null +++ b/app/storage/storing/ItemgroupStorage.js @@ -0,0 +1,29 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.ItemgroupStorage = void 0; +const FileUtils_1 = require("../FileUtils"); +const path = require("node:path"); +const fs = require("node:fs"); +class ItemgroupStorage { + constructor(itemgroupDir) { + this.itemgroupDir = itemgroupDir; + FileUtils_1.FileUtils.prepareDirectoryFroWriting(this.itemgroupDir); + } + storeItemgroups(itemgroups) { + console.log("Store Itemgroups"); + itemgroups.forEach(itemgroup => { + this.storeItemgroup(itemgroup); + }); + } + storeItemgroup(itemgroup) { + const file = path.join(...itemgroup.fileName.split("/")); + const completeFileName = path.join(this.itemgroupDir, file); + const itemgroupDirectory = path.join(...itemgroup.fileName.split("/").slice(0, -1)); + const completeItemgroupDirectory = path.join(this.itemgroupDir, itemgroupDirectory); + console.log(completeItemgroupDirectory); + FileUtils_1.FileUtils.prepareDirectoryFroWriting(completeItemgroupDirectory); + fs.writeFileSync(completeFileName + ".json", itemgroup.jsonString, "utf-8"); + } +} +exports.ItemgroupStorage = ItemgroupStorage; +//# sourceMappingURL=ItemgroupStorage.js.map \ No newline at end of file diff --git a/app/storage/storing/ItemgroupStorage.ts b/app/storage/storing/ItemgroupStorage.ts new file mode 100644 index 0000000..40953ca --- /dev/null +++ b/app/storage/storing/ItemgroupStorage.ts @@ -0,0 +1,34 @@ +import {FileUtils} from "../FileUtils"; +import {StoreComponent} from "../StoreComponent"; +import * as path from "node:path"; +import * as fs from "node:fs"; + +export class ItemgroupStorage { + private itemgroupDir: string + + + constructor(itemgroupDir: string) { + this.itemgroupDir = itemgroupDir; + FileUtils.prepareDirectoryFroWriting(this.itemgroupDir); + } + + public storeItemgroups(itemgroups: StoreComponent[]) { + console.log("Store Itemgroups") + itemgroups.forEach(itemgroup => { + this.storeItemgroup(itemgroup) + }) + } + + private storeItemgroup(itemgroup: StoreComponent) { + const file = path.join(... itemgroup.fileName.split("/")); + const completeFileName = path.join(this.itemgroupDir, file); + + const itemgroupDirectory = path.join(... itemgroup.fileName.split("/").slice(0, -1)) + const completeItemgroupDirectory = path.join(this.itemgroupDir, itemgroupDirectory) + console.log(completeItemgroupDirectory) + FileUtils.prepareDirectoryFroWriting(completeItemgroupDirectory); + fs.writeFileSync(completeFileName + ".json", itemgroup.jsonString, "utf-8") + } + + +} diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 8272f56..063c373 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -27,6 +27,7 @@ import {CharacterParser} from "./project/parser/characterParser/CharacterParser" import {TemplateType} from "./project/game-model/templates/TemplateType"; import {TemplateTypeUtilities} from "./project/game-model/templates/TemplateTypeUtilities"; import {SimpleTemplateGamesystem} from "./project/game-model/templates/simpleGamesystem/SimpleTemplateGamesystem"; +import {ItemSerializer} from "./project/serializer/ItemSerializer"; @Component({ selector: 'app-root', @@ -231,7 +232,10 @@ export class AppComponent implements OnInit{ const storedScriptAccounts = ScriptAccountSerializer.serializeScriptAccounts(this.gameModel.scriptAccounts) const storedGamesystems: StoreComponent[] = GamesystemSerializer.serializeGamesystems(this.gameModel.gamesystems) const storedCharacters: StoreComponent[] = CharacterSerializer.serializeCharacters(this.gameModel.characters) - const storeModel = new StoredGameModel(this.gameModel.gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters) + + const itemSerializer = new ItemSerializer(); + const storedItemgroups: StoreComponent[] = itemSerializer.serializeItemgroups(this.gameModel!.itemgroups); + const storeModel = new StoredGameModel(this.gameModel.gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups) if(this.electronService.isElectron) { this.electronService.ipcRenderer.send('save-model', storeModel) diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index a7d5c6c..c134c4d 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -16,6 +16,7 @@ import {AbstractItemGroup} from "./inventory/AbstractItemGroup"; import {ConcreteItemGroup} from "./inventory/ConcreteItemGroup"; import {Item} from "./inventory/Item"; import {ItemgroupUtilities} from "./utils/ItemgroupUtilities"; +import {ItemGroupCharacteristic} from "./inventory/ItemgroupCharacteristic"; export class GameModel { gameModelName: string @@ -29,11 +30,13 @@ export class GameModel { this.gameModelName = gameModelName; this.addAbstractItemgroup("Clothing", undefined); - this.addConcreteItemgroup("Inventory", undefined); + this.addAbstractItemgroup("Inventory", undefined); this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); - this.addItem("Hose 1", "Hose"); + const item = this.addItem("Hose 1", "Hose"); + item!.addInheritedGroup(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!) + console.log(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!.manuallyInheritedItems) this.addItem("Hose 2", "Hose"); } @@ -41,7 +44,9 @@ export class GameModel { //Ensure that Itemgroup does not exist if(parentgroup == undefined) { if(GameModel.findItemgroupByName(groupName, this.itemgroups) == undefined) { - this.itemgroups.push(new AbstractItemGroup(groupName, "", ModelComponentType.ITEMGROUP)); + const itemgroup = new AbstractItemGroup(groupName, "", ModelComponentType.ITEMGROUP) + this.itemgroups.push(itemgroup); + itemgroup.addItemgroupCharacteristic(new ItemGroupCharacteristic("Test0", "", itemgroup)); } } else { if(GameModel.findItemgroupByName(groupName, parentgroup.children) == undefined) { @@ -69,7 +74,9 @@ export class GameModel { const itemgroups: ItemGroup[] = ItemgroupUtilities.findItemgroupPathToItemgroup(conceteItemgroupName, this.itemgroups); if(itemgroups.length > 0) { - itemgroup.addItem(new Item(itemName, "", ModelComponentType.ITEM ), itemgroups) + const item = new Item(itemName, "", ModelComponentType.ITEM ) + itemgroup.addItem(item, itemgroups) + return item; } } } diff --git a/src/app/project/serializer/GamesystemSerializer.ts b/src/app/project/serializer/GamesystemSerializer.ts index 2ec8b43..3d8a8ca 100644 --- a/src/app/project/serializer/GamesystemSerializer.ts +++ b/src/app/project/serializer/GamesystemSerializer.ts @@ -27,9 +27,7 @@ export class GamesystemSerializer { private static serializeSimpleGamesystem(simpleGamesystem: SimpleGamesystem): StoreComponent { const fileName = this.computeSimpleGamesystemPath(simpleGamesystem); - if(simpleGamesystem.componentName === "Weather(Child)") { - console.log(fileName) - } + console.log(fileName) const jsonString = JSON.stringify(simpleGamesystem, (key, value) => { if(this.IGNORED_SIMPLE_ATTRIBUTES.includes(key)) { diff --git a/src/app/project/serializer/ItemSerializer.ts b/src/app/project/serializer/ItemSerializer.ts new file mode 100644 index 0000000..88916eb --- /dev/null +++ b/src/app/project/serializer/ItemSerializer.ts @@ -0,0 +1,64 @@ +import {ItemGroup} from "../game-model/inventory/ItemGroup"; +import {StoreComponent} from "../../../../app/storage/StoreComponent"; +import {AbstractItemGroup} from "../game-model/inventory/AbstractItemGroup"; +import {ConcreteItemGroup} from "../game-model/inventory/ConcreteItemGroup"; +import {ModelComponentType} from "../game-model/ModelComponentType"; +import {SerializeConstants} from "./SerializeConstants"; + +export class ItemSerializer { + + private serializedItemgroups: StoreComponent[] = [] + private static ignoredKeys: string[] = ['type', 'unsaved', 'children', "itemgroup", "manuallyInheritedGroups", "hierarchyInheritedGroups", "items"] + + public serializeItemgroups(itemgroups: ItemGroup[]): StoreComponent[] { + itemgroups.forEach(itemgroup => { + this.serializeSingleItemgroupHierarchy(itemgroup) + }) + return this.serializedItemgroups; + } + + private serializeSingleItemgroupHierarchy(itemgroup: ItemGroup) { + if(itemgroup instanceof AbstractItemGroup) { + const storeComponent = this.serializeItemgroup(itemgroup) + this.serializedItemgroups.push(storeComponent) + itemgroup.children.forEach(child => this.serializeSingleItemgroupHierarchy(child)); + } else { + const storeComponent = this.serializeItemgroup(itemgroup); + this.serializedItemgroups.push(storeComponent) + } + } + + private serializeItemgroup(itemgroup: ItemGroup): StoreComponent { + const componentType = ModelComponentType.ITEMGROUP; + const fileName = ItemSerializer.computeItemgroupPath(itemgroup); + + const jsonString = JSON.stringify(itemgroup, (key, value) => { + if(ItemSerializer.ignoredKeys.includes(key)) { + return undefined + } else { + + if(key === 'key') { + return value.characteristicName + } else { + return value; + } + + } + }, SerializeConstants.JSON_INDENT); + console.log(fileName) + return new StoreComponent(jsonString, fileName, componentType) + } + + private static computeItemgroupPath(itemgroup: ItemGroup): string { + const itemgroupPath: string[] = []; + itemgroupPath.push(itemgroup.componentName); + itemgroupPath.push(itemgroup.componentName); + + while(itemgroup.parentGroup !== undefined) { + itemgroupPath.unshift(itemgroup.parentGroup.componentName); + itemgroup = itemgroup.parentGroup; + } + + return itemgroupPath.join("/"); + } +} diff --git a/testModel/items/Clothing/Clothing.json b/testModel/items/Clothing/Clothing.json new file mode 100644 index 0000000..845e3dd --- /dev/null +++ b/testModel/items/Clothing/Clothing.json @@ -0,0 +1,11 @@ +{ + "componentName": "Clothing", + "componentDescription": "", + "itemGroupCharacteristics": [ + { + "characteristicName": "Test0", + "characteristicDescription": "" + } + ], + "manuallyInheritedItems": [] +} \ No newline at end of file diff --git a/testModel/items/Clothing/Hose/Hose.json b/testModel/items/Clothing/Hose/Hose.json new file mode 100644 index 0000000..cacc167 --- /dev/null +++ b/testModel/items/Clothing/Hose/Hose.json @@ -0,0 +1,17 @@ +{ + "componentName": "Hose", + "componentDescription": "", + "itemGroupCharacteristics": [], + "manuallyInheritedItems": [], + "parentGroup": { + "componentName": "Clothing", + "componentDescription": "", + "itemGroupCharacteristics": [ + { + "characteristicName": "Test0", + "characteristicDescription": "" + } + ], + "manuallyInheritedItems": [] + } +} \ No newline at end of file diff --git a/testModel/items/Clothing/Oberteil/Oberteil.json b/testModel/items/Clothing/Oberteil/Oberteil.json new file mode 100644 index 0000000..00be2b1 --- /dev/null +++ b/testModel/items/Clothing/Oberteil/Oberteil.json @@ -0,0 +1,17 @@ +{ + "componentName": "Oberteil", + "componentDescription": "", + "itemGroupCharacteristics": [], + "manuallyInheritedItems": [], + "parentGroup": { + "componentName": "Clothing", + "componentDescription": "", + "itemGroupCharacteristics": [ + { + "characteristicName": "Test0", + "characteristicDescription": "" + } + ], + "manuallyInheritedItems": [] + } +} \ No newline at end of file diff --git a/testModel/items/Inventory/Inventory.json b/testModel/items/Inventory/Inventory.json new file mode 100644 index 0000000..7b72ad9 --- /dev/null +++ b/testModel/items/Inventory/Inventory.json @@ -0,0 +1,22 @@ +{ + "componentName": "Inventory", + "componentDescription": "", + "itemGroupCharacteristics": [ + { + "characteristicName": "Test0", + "characteristicDescription": "" + } + ], + "manuallyInheritedItems": [ + { + "componentName": "Hose 1", + "componentDescription": "", + "itemCharacteristicValues": [ + { + "key": "Test0", + "value": 0 + } + ] + } + ] +} \ No newline at end of file -- 2.34.1 From 1b2fd273bfc6a5d3b3b55b33a65d0f1855ff6914 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 10:03:57 +0200 Subject: [PATCH 26/31] Persist Items --- src/app/project/serializer/ItemSerializer.ts | 49 ++++++++++++++++++-- testModel/items/Clothing/Hose/Hose 1.json | 13 ++++++ testModel/items/Clothing/Hose/Hose 2.json | 11 +++++ 3 files changed, 68 insertions(+), 5 deletions(-) create mode 100644 testModel/items/Clothing/Hose/Hose 1.json create mode 100644 testModel/items/Clothing/Hose/Hose 2.json diff --git a/src/app/project/serializer/ItemSerializer.ts b/src/app/project/serializer/ItemSerializer.ts index 88916eb..fc785c8 100644 --- a/src/app/project/serializer/ItemSerializer.ts +++ b/src/app/project/serializer/ItemSerializer.ts @@ -4,11 +4,13 @@ import {AbstractItemGroup} from "../game-model/inventory/AbstractItemGroup"; import {ConcreteItemGroup} from "../game-model/inventory/ConcreteItemGroup"; import {ModelComponentType} from "../game-model/ModelComponentType"; import {SerializeConstants} from "./SerializeConstants"; +import {Item} from "../game-model/inventory/Item"; export class ItemSerializer { private serializedItemgroups: StoreComponent[] = [] - private static ignoredKeys: string[] = ['type', 'unsaved', 'children', "itemgroup", "manuallyInheritedGroups", "hierarchyInheritedGroups", "items"] + private static ignoredGroupKeys: string[] = ['type', 'unsaved', 'children', "itemgroup", "manuallyInheritedGroups", "hierarchyInheritedGroups", "items"] + private static ignoredItemKeys: string[] = ['type', 'unsaved', 'hierarchyInheritedGroups'] public serializeItemgroups(itemgroups: ItemGroup[]): StoreComponent[] { itemgroups.forEach(itemgroup => { @@ -25,6 +27,8 @@ export class ItemSerializer { } else { const storeComponent = this.serializeItemgroup(itemgroup); this.serializedItemgroups.push(storeComponent) + + this.serializeItemsOfItemgroup(itemgroup as ConcreteItemGroup); } } @@ -33,7 +37,7 @@ export class ItemSerializer { const fileName = ItemSerializer.computeItemgroupPath(itemgroup); const jsonString = JSON.stringify(itemgroup, (key, value) => { - if(ItemSerializer.ignoredKeys.includes(key)) { + if(ItemSerializer.ignoredGroupKeys.includes(key)) { return undefined } else { @@ -45,14 +49,17 @@ export class ItemSerializer { } }, SerializeConstants.JSON_INDENT); - console.log(fileName) return new StoreComponent(jsonString, fileName, componentType) } - private static computeItemgroupPath(itemgroup: ItemGroup): string { + private static computeItemgroupPath(itemgroup: ItemGroup, itemPath: boolean = false): string { const itemgroupPath: string[] = []; itemgroupPath.push(itemgroup.componentName); - itemgroupPath.push(itemgroup.componentName); + + if(!itemPath) { + itemgroupPath.push(itemgroup.componentName); + } + while(itemgroup.parentGroup !== undefined) { itemgroupPath.unshift(itemgroup.parentGroup.componentName); @@ -61,4 +68,36 @@ export class ItemSerializer { return itemgroupPath.join("/"); } + + private serializeItemsOfItemgroup(itemgroup: ConcreteItemGroup) { + const fileName = ItemSerializer.computeItemgroupPath(itemgroup, true); + itemgroup.items.forEach(item => { + const storeComponent = this.serializeSingleItem(fileName, item); + this.serializedItemgroups.push(storeComponent) + }) + + + } + + private serializeSingleItem(itemgroupPath: string, item: Item) { + const itemFile = itemgroupPath + "/" + item.componentName; + + const jsonString = JSON.stringify(item, (key, value) => { + if(ItemSerializer.ignoredItemKeys.includes(key)) { + return undefined + } + + if(value instanceof ItemGroup) { + return value.componentName + } + + if(key == "key") { + return value.characteristicName + } + + return value; + }, SerializeConstants.JSON_INDENT) + + return new StoreComponent(jsonString, itemFile, ModelComponentType.ITEM) + } } diff --git a/testModel/items/Clothing/Hose/Hose 1.json b/testModel/items/Clothing/Hose/Hose 1.json new file mode 100644 index 0000000..52f24ba --- /dev/null +++ b/testModel/items/Clothing/Hose/Hose 1.json @@ -0,0 +1,13 @@ +{ + "componentName": "Hose 1", + "componentDescription": "", + "manuallyInheritedGroups": [ + "Inventory" + ], + "itemCharacteristicValues": [ + { + "key": "Test0", + "value": 0 + } + ] +} \ No newline at end of file diff --git a/testModel/items/Clothing/Hose/Hose 2.json b/testModel/items/Clothing/Hose/Hose 2.json new file mode 100644 index 0000000..ea92a4b --- /dev/null +++ b/testModel/items/Clothing/Hose/Hose 2.json @@ -0,0 +1,11 @@ +{ + "componentName": "Hose 2", + "componentDescription": "", + "manuallyInheritedGroups": [], + "itemCharacteristicValues": [ + { + "key": "Test0", + "value": 0 + } + ] +} \ No newline at end of file -- 2.34.1 From ddcbfc5bb34a38aca4247ca7e44cc2450503beb0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 10:10:55 +0200 Subject: [PATCH 27/31] Persist Items independly from Itemgroups --- app/main.ts | 1 + app/storage/StoredGameModel.js | 3 ++- app/storage/StoredGameModel.ts | 4 +++- app/storage/loader/GameModelLoader.js | 2 +- app/storage/loader/GameModelLoader.ts | 2 +- app/storage/storing/ItemgroupStorage.js | 4 +++- app/storage/storing/ItemgroupStorage.ts | 4 +++- src/app/app.component.ts | 4 +++- src/app/project/serializer/ItemSerializer.ts | 7 ++++++- 9 files changed, 23 insertions(+), 8 deletions(-) diff --git a/app/main.ts b/app/main.ts index cee7f28..30431c1 100644 --- a/app/main.ts +++ b/app/main.ts @@ -274,6 +274,7 @@ function recieveGameModelToStore(gameModel: StoredGameModel) { const itemgroupStorage = new ItemgroupStorage(path.join(projectDirectory, ModelComponentFileDirectory.ITEMGROUP_DIR_NAME)) itemgroupStorage.storeItemgroups(gameModel.storedItemgroups); + itemgroupStorage.storeItems(gameModel.storedItems) } /*function deleteComponent(component: DeleteModel) { diff --git a/app/storage/StoredGameModel.js b/app/storage/StoredGameModel.js index 2db851f..860b91d 100644 --- a/app/storage/StoredGameModel.js +++ b/app/storage/StoredGameModel.js @@ -2,12 +2,13 @@ Object.defineProperty(exports, "__esModule", { value: true }); exports.StoredGameModel = void 0; class StoredGameModel { - constructor(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups) { + constructor(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, storedItems) { this.gameModelName = gameModelName; this.storedGamesystems = storedGamesystems; this.storedScriptAccounts = storedScriptAccounts; this.storedCharacters = storedCharacters; this.storedItemgroups = storedItemgroups; + this.storedItems = storedItems; } } exports.StoredGameModel = StoredGameModel; diff --git a/app/storage/StoredGameModel.ts b/app/storage/StoredGameModel.ts index 7d9f330..829b038 100644 --- a/app/storage/StoredGameModel.ts +++ b/app/storage/StoredGameModel.ts @@ -7,14 +7,16 @@ export class StoredGameModel { storedScriptAccounts: StoreComponent[] storedCharacters: StoreComponent[] storedItemgroups: StoreComponent[] + storedItems: StoreComponent[] constructor(gameModelName: string, storedScriptAccounts: StoreComponent[], storedGamesystems: StoreComponent[], - storedCharacters: StoreComponent[], storedItemgroups: StoreComponent[]) { + storedCharacters: StoreComponent[], storedItemgroups: StoreComponent[], storedItems: StoreComponent[]) { this.gameModelName = gameModelName; this.storedGamesystems = storedGamesystems; this.storedScriptAccounts = storedScriptAccounts; this.storedCharacters = storedCharacters; this.storedItemgroups = storedItemgroups; + this.storedItems = storedItems; } } diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index d78f3b3..7b10263 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -16,7 +16,7 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); - return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, []); + return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); } loadScriptAccountComponents() { const scriptAccountDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME); diff --git a/app/storage/loader/GameModelLoader.ts b/app/storage/loader/GameModelLoader.ts index fffebef..170a147 100644 --- a/app/storage/loader/GameModelLoader.ts +++ b/app/storage/loader/GameModelLoader.ts @@ -22,7 +22,7 @@ export class GameModelLoader { const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters() - return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, []); + return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); } private loadScriptAccountComponents() { diff --git a/app/storage/storing/ItemgroupStorage.js b/app/storage/storing/ItemgroupStorage.js index 028aa92..3d6a0e1 100644 --- a/app/storage/storing/ItemgroupStorage.js +++ b/app/storage/storing/ItemgroupStorage.js @@ -10,7 +10,6 @@ class ItemgroupStorage { FileUtils_1.FileUtils.prepareDirectoryFroWriting(this.itemgroupDir); } storeItemgroups(itemgroups) { - console.log("Store Itemgroups"); itemgroups.forEach(itemgroup => { this.storeItemgroup(itemgroup); }); @@ -24,6 +23,9 @@ class ItemgroupStorage { FileUtils_1.FileUtils.prepareDirectoryFroWriting(completeItemgroupDirectory); fs.writeFileSync(completeFileName + ".json", itemgroup.jsonString, "utf-8"); } + storeItems(storedItems) { + storedItems.forEach(item => this.storeItemgroup(item)); + } } exports.ItemgroupStorage = ItemgroupStorage; //# sourceMappingURL=ItemgroupStorage.js.map \ No newline at end of file diff --git a/app/storage/storing/ItemgroupStorage.ts b/app/storage/storing/ItemgroupStorage.ts index 40953ca..3049f7e 100644 --- a/app/storage/storing/ItemgroupStorage.ts +++ b/app/storage/storing/ItemgroupStorage.ts @@ -13,7 +13,6 @@ export class ItemgroupStorage { } public storeItemgroups(itemgroups: StoreComponent[]) { - console.log("Store Itemgroups") itemgroups.forEach(itemgroup => { this.storeItemgroup(itemgroup) }) @@ -31,4 +30,7 @@ export class ItemgroupStorage { } + storeItems(storedItems: StoreComponent[]) { + storedItems.forEach(item => this.storeItemgroup(item)) + } } diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 063c373..d0e1c85 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -235,7 +235,9 @@ export class AppComponent implements OnInit{ const itemSerializer = new ItemSerializer(); const storedItemgroups: StoreComponent[] = itemSerializer.serializeItemgroups(this.gameModel!.itemgroups); - const storeModel = new StoredGameModel(this.gameModel.gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups) + const storedItems: StoreComponent[] = itemSerializer.getSerializedItems() + + const storeModel = new StoredGameModel(this.gameModel.gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, storedItems) if(this.electronService.isElectron) { this.electronService.ipcRenderer.send('save-model', storeModel) diff --git a/src/app/project/serializer/ItemSerializer.ts b/src/app/project/serializer/ItemSerializer.ts index fc785c8..ac54853 100644 --- a/src/app/project/serializer/ItemSerializer.ts +++ b/src/app/project/serializer/ItemSerializer.ts @@ -9,6 +9,7 @@ import {Item} from "../game-model/inventory/Item"; export class ItemSerializer { private serializedItemgroups: StoreComponent[] = [] + private serializedItems: StoreComponent[] = [] private static ignoredGroupKeys: string[] = ['type', 'unsaved', 'children', "itemgroup", "manuallyInheritedGroups", "hierarchyInheritedGroups", "items"] private static ignoredItemKeys: string[] = ['type', 'unsaved', 'hierarchyInheritedGroups'] @@ -73,7 +74,7 @@ export class ItemSerializer { const fileName = ItemSerializer.computeItemgroupPath(itemgroup, true); itemgroup.items.forEach(item => { const storeComponent = this.serializeSingleItem(fileName, item); - this.serializedItemgroups.push(storeComponent) + this.serializedItems.push(storeComponent) }) @@ -100,4 +101,8 @@ export class ItemSerializer { return new StoreComponent(jsonString, itemFile, ModelComponentType.ITEM) } + + getSerializedItems() { + return this.serializedItems; + } } -- 2.34.1 From 73edf03fa0547d04f326f0dad0727c682b1966f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 13:33:26 +0200 Subject: [PATCH 28/31] Load Itemgroups --- app/storage/loader/GameModelLoader.js | 7 +++ app/storage/loader/GameModelLoader.ts | 12 +++-- app/storage/loader/ItemLoader.ts | 46 +++++++++++++++++++ app/storage/storing/ItemgroupStorage.js | 1 - app/storage/storing/ItemgroupStorage.ts | 1 - .../game-model/inventory/AbstractItemGroup.ts | 2 + .../game-model/inventory/ConcreteItemGroup.ts | 2 + .../game-model/inventory/ItemgroupType.ts | 4 ++ .../parser/itemParser/ItemgroupParser.ts | 8 ++++ testModel/items/Clothing/Clothing.json | 3 +- testModel/items/Clothing/Hose/Hose.json | 4 +- .../items/Clothing/Oberteil/Oberteil.json | 4 +- testModel/items/Inventory/Inventory.json | 3 +- 13 files changed, 87 insertions(+), 10 deletions(-) create mode 100644 app/storage/loader/ItemLoader.ts create mode 100644 src/app/project/game-model/inventory/ItemgroupType.ts create mode 100644 src/app/project/parser/itemParser/ItemgroupParser.ts diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index 7b10263..1ff3639 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -7,6 +7,7 @@ const ModelComponentFileDirectory_1 = require("../ModelComponentFileDirectory"); const ScriptAccountLoader_1 = require("./ScriptAccountLoader"); const GamesystemLoader_1 = require("./GamesystemLoader"); const CharacterLoader_1 = require("./CharacterLoader"); +const ItemLoader_1 = require("./ItemLoader"); class GameModelLoader { constructor(gameModelDir) { this.gameModelDir = gameModelDir; @@ -16,6 +17,7 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); + const storedItemgroupsd = this.loadItemgroups(); return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); } loadScriptAccountComponents() { @@ -33,6 +35,11 @@ class GameModelLoader { const characterLoader = new CharacterLoader_1.CharacterLoader(characterDir); return characterLoader.loadCharacters(); } + loadItemgroups() { + const itemgroupDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.ITEMGROUP_DIR_NAME); + const itemgroupLoader = new ItemLoader_1.ItemLoader(itemgroupDir); + return itemgroupLoader.loadItemgroups(); + } } exports.GameModelLoader = GameModelLoader; //# sourceMappingURL=GameModelLoader.js.map \ No newline at end of file diff --git a/app/storage/loader/GameModelLoader.ts b/app/storage/loader/GameModelLoader.ts index 170a147..fc46748 100644 --- a/app/storage/loader/GameModelLoader.ts +++ b/app/storage/loader/GameModelLoader.ts @@ -6,6 +6,7 @@ import {ModelComponentFileDirectory} from "../ModelComponentFileDirectory"; import {ScriptAccountLoader} from "./ScriptAccountLoader"; import {GamesystemLoader} from "./GamesystemLoader"; import {CharacterLoader} from "./CharacterLoader"; +import {ItemLoader} from "./ItemLoader"; export class GameModelLoader { gameModelDir: string @@ -21,8 +22,9 @@ export class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters() + const storedItemgroups = this.loadItemgroups() - return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); + return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, []); } private loadScriptAccountComponents() { @@ -44,7 +46,9 @@ export class GameModelLoader { } - - - + private loadItemgroups() { + const itemgroupDir = path.join(this.gameModelDir, ModelComponentFileDirectory.ITEMGROUP_DIR_NAME); + const itemgroupLoader = new ItemLoader(itemgroupDir); + return itemgroupLoader.loadItemgroups(); + } } diff --git a/app/storage/loader/ItemLoader.ts b/app/storage/loader/ItemLoader.ts new file mode 100644 index 0000000..6e84368 --- /dev/null +++ b/app/storage/loader/ItemLoader.ts @@ -0,0 +1,46 @@ +import {StoreComponent} from "../StoreComponent"; +import {FileUtils} from "../FileUtils"; +import * as fs from "node:fs"; +import * as path from "node:path"; +import {ModelComponentType} from "../../../src/app/project/game-model/ModelComponentType"; + +export class ItemLoader { + + itemDir: string + + constructor(itemDir: string) { + this.itemDir = itemDir; + } + + loadItemgroups(): StoreComponent[] { + return this.loadItemgroupsRecursively(this.itemDir); + } + + private loadItemgroupsRecursively(currentDir: string): StoreComponent[] { + let loadedItemgroups : StoreComponent[] = [] + const itemgroupFiles = FileUtils.listFilesInDirectory(currentDir); + + itemgroupFiles.forEach(itemgroupFile => { + if(fs.lstatSync(itemgroupFile).isDirectory()) { + const childgroup = this.loadItemgroupsRecursively(itemgroupFile); + loadedItemgroups = loadedItemgroups.concat(childgroup); + } else if(path.basename(itemgroupFile).endsWith(".json") && this.fileRepresentsItemgroup(itemgroupFile)){ + const loadedItemgroup = this.loadSingleItemgroup(itemgroupFile)!; + loadedItemgroups.push(loadedItemgroup) + } + }) + return loadedItemgroups; + } + + private loadSingleItemgroup(itemgroupFile: string): StoreComponent | undefined { + if(itemgroupFile.endsWith(".json")) { + const data = fs.readFileSync(itemgroupFile, "utf-8"); + return new StoreComponent(data, itemgroupFile, ModelComponentType.ITEMGROUP); + } + return undefined + } + + private fileRepresentsItemgroup(file: string): boolean { + return path.basename(path.dirname(file)) === path.parse(path.basename(file)).name; + } +} diff --git a/app/storage/storing/ItemgroupStorage.js b/app/storage/storing/ItemgroupStorage.js index 3d6a0e1..2851c97 100644 --- a/app/storage/storing/ItemgroupStorage.js +++ b/app/storage/storing/ItemgroupStorage.js @@ -19,7 +19,6 @@ class ItemgroupStorage { const completeFileName = path.join(this.itemgroupDir, file); const itemgroupDirectory = path.join(...itemgroup.fileName.split("/").slice(0, -1)); const completeItemgroupDirectory = path.join(this.itemgroupDir, itemgroupDirectory); - console.log(completeItemgroupDirectory); FileUtils_1.FileUtils.prepareDirectoryFroWriting(completeItemgroupDirectory); fs.writeFileSync(completeFileName + ".json", itemgroup.jsonString, "utf-8"); } diff --git a/app/storage/storing/ItemgroupStorage.ts b/app/storage/storing/ItemgroupStorage.ts index 3049f7e..84f7fdd 100644 --- a/app/storage/storing/ItemgroupStorage.ts +++ b/app/storage/storing/ItemgroupStorage.ts @@ -24,7 +24,6 @@ export class ItemgroupStorage { const itemgroupDirectory = path.join(... itemgroup.fileName.split("/").slice(0, -1)) const completeItemgroupDirectory = path.join(this.itemgroupDir, itemgroupDirectory) - console.log(completeItemgroupDirectory) FileUtils.prepareDirectoryFroWriting(completeItemgroupDirectory); fs.writeFileSync(completeFileName + ".json", itemgroup.jsonString, "utf-8") } diff --git a/src/app/project/game-model/inventory/AbstractItemGroup.ts b/src/app/project/game-model/inventory/AbstractItemGroup.ts index 5141f5a..cc95cb0 100644 --- a/src/app/project/game-model/inventory/AbstractItemGroup.ts +++ b/src/app/project/game-model/inventory/AbstractItemGroup.ts @@ -1,9 +1,11 @@ import {ItemGroup} from "./ItemGroup"; import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; +import {ItemgroupType} from "./ItemgroupType"; export class AbstractItemGroup extends ItemGroup { children: ItemGroup[] = []; + itemgroupType = ItemgroupType.ABSTRACT addChildItemgroup(itemGroup: ItemGroup) { this.children.push(itemGroup) diff --git a/src/app/project/game-model/inventory/ConcreteItemGroup.ts b/src/app/project/game-model/inventory/ConcreteItemGroup.ts index 21e6682..5ad4710 100644 --- a/src/app/project/game-model/inventory/ConcreteItemGroup.ts +++ b/src/app/project/game-model/inventory/ConcreteItemGroup.ts @@ -1,10 +1,12 @@ import {ItemGroup} from "./ItemGroup"; import {Item} from "./Item"; import {ItemGroupCharacteristic} from "./ItemgroupCharacteristic"; +import {ItemgroupType} from "./ItemgroupType"; export class ConcreteItemGroup extends ItemGroup { items: Item[] = []; + itemgroupType = ItemgroupType.CONCRETE addItem(item: Item, parentItemgroups: ItemGroup[]) { if(this.findItemByName(item.componentName) == undefined) { diff --git a/src/app/project/game-model/inventory/ItemgroupType.ts b/src/app/project/game-model/inventory/ItemgroupType.ts new file mode 100644 index 0000000..f1ca933 --- /dev/null +++ b/src/app/project/game-model/inventory/ItemgroupType.ts @@ -0,0 +1,4 @@ +export enum ItemgroupType { + CONCRETE, + ABSTRACT +} diff --git a/src/app/project/parser/itemParser/ItemgroupParser.ts b/src/app/project/parser/itemParser/ItemgroupParser.ts new file mode 100644 index 0000000..36b509d --- /dev/null +++ b/src/app/project/parser/itemParser/ItemgroupParser.ts @@ -0,0 +1,8 @@ +import {ItemGroup} from "../../game-model/inventory/ItemGroup"; + +export class ItemgroupParser { + + private parsedItemgroups: ItemGroup[] = [] + + +} diff --git a/testModel/items/Clothing/Clothing.json b/testModel/items/Clothing/Clothing.json index 845e3dd..e3e3412 100644 --- a/testModel/items/Clothing/Clothing.json +++ b/testModel/items/Clothing/Clothing.json @@ -7,5 +7,6 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [] + "manuallyInheritedItems": [], + "itemgroupType": 1 } \ No newline at end of file diff --git a/testModel/items/Clothing/Hose/Hose.json b/testModel/items/Clothing/Hose/Hose.json index cacc167..2b39d60 100644 --- a/testModel/items/Clothing/Hose/Hose.json +++ b/testModel/items/Clothing/Hose/Hose.json @@ -3,6 +3,7 @@ "componentDescription": "", "itemGroupCharacteristics": [], "manuallyInheritedItems": [], + "itemgroupType": 0, "parentGroup": { "componentName": "Clothing", "componentDescription": "", @@ -12,6 +13,7 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [] + "manuallyInheritedItems": [], + "itemgroupType": 1 } } \ No newline at end of file diff --git a/testModel/items/Clothing/Oberteil/Oberteil.json b/testModel/items/Clothing/Oberteil/Oberteil.json index 00be2b1..2173a00 100644 --- a/testModel/items/Clothing/Oberteil/Oberteil.json +++ b/testModel/items/Clothing/Oberteil/Oberteil.json @@ -3,6 +3,7 @@ "componentDescription": "", "itemGroupCharacteristics": [], "manuallyInheritedItems": [], + "itemgroupType": 0, "parentGroup": { "componentName": "Clothing", "componentDescription": "", @@ -12,6 +13,7 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [] + "manuallyInheritedItems": [], + "itemgroupType": 1 } } \ No newline at end of file diff --git a/testModel/items/Inventory/Inventory.json b/testModel/items/Inventory/Inventory.json index 7b72ad9..01b3765 100644 --- a/testModel/items/Inventory/Inventory.json +++ b/testModel/items/Inventory/Inventory.json @@ -18,5 +18,6 @@ } ] } - ] + ], + "itemgroupType": 1 } \ No newline at end of file -- 2.34.1 From 2e29d4cde740d68cb4cfff9d69151fec47ed64d9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 15:24:36 +0200 Subject: [PATCH 29/31] Parse Itemgroups --- app/storage/loader/GameModelLoader.js | 4 +- src/app/app.component.ts | 6 ++ src/app/project/game-model/GameModel.ts | 10 --- .../parser/itemParser/ItemgroupParser.ts | 80 +++++++++++++++++++ src/app/project/serializer/ItemSerializer.ts | 55 +++++++++---- testModel/items/Clothing/Clothing.json | 1 - testModel/items/Clothing/Hose/Hose.json | 14 +--- .../items/Clothing/Oberteil/Oberteil.json | 14 +--- testModel/items/Inventory/Inventory.json | 12 --- 9 files changed, 131 insertions(+), 65 deletions(-) diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index 1ff3639..5ffc6d5 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -17,8 +17,8 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); - const storedItemgroupsd = this.loadItemgroups(); - return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); + const storedItemgroups = this.loadItemgroups(); + return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, []); } loadScriptAccountComponents() { const scriptAccountDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME); diff --git a/src/app/app.component.ts b/src/app/app.component.ts index d0e1c85..81392b6 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -28,6 +28,7 @@ import {TemplateType} from "./project/game-model/templates/TemplateType"; import {TemplateTypeUtilities} from "./project/game-model/templates/TemplateTypeUtilities"; import {SimpleTemplateGamesystem} from "./project/game-model/templates/simpleGamesystem/SimpleTemplateGamesystem"; import {ItemSerializer} from "./project/serializer/ItemSerializer"; +import {ItemgroupParser} from "./project/parser/itemParser/ItemgroupParser"; @Component({ selector: 'app-root', @@ -224,6 +225,11 @@ export class AppComponent implements OnInit{ const characterParser = new CharacterParser(characterTemplateSystems, characterRelationTemplateSystems, gameModel.scriptAccounts); gameModel.characters = characterParser.parseCharacters(storedGameModel.storedCharacters) + const itemgroupParser = new ItemgroupParser(); + itemgroupParser.parseItemgroups(storedGameModel.storedItemgroups); + + gameModel.itemgroups = itemgroupParser.getParsedTopItemgroups(); + this.gameModel = gameModel; } diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index c134c4d..dde1cc3 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -28,16 +28,6 @@ export class GameModel { constructor(gameModelName: string) { this.gameModelName = gameModelName; - - this.addAbstractItemgroup("Clothing", undefined); - this.addAbstractItemgroup("Inventory", undefined); - this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); - this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); - - const item = this.addItem("Hose 1", "Hose"); - item!.addInheritedGroup(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!) - console.log(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!.manuallyInheritedItems) - this.addItem("Hose 2", "Hose"); } addAbstractItemgroup(groupName: string, parentgroup: AbstractItemGroup | undefined) { diff --git a/src/app/project/parser/itemParser/ItemgroupParser.ts b/src/app/project/parser/itemParser/ItemgroupParser.ts index 36b509d..de65648 100644 --- a/src/app/project/parser/itemParser/ItemgroupParser.ts +++ b/src/app/project/parser/itemParser/ItemgroupParser.ts @@ -1,8 +1,88 @@ import {ItemGroup} from "../../game-model/inventory/ItemGroup"; +import {StoreComponent} from "../../../../../app/storage/StoreComponent"; +import {ItemGroupCharacteristic} from "../../game-model/inventory/ItemgroupCharacteristic"; +import {AbstractItemGroup} from "../../game-model/inventory/AbstractItemGroup"; +import {ModelComponentType} from "../../game-model/ModelComponentType"; +import {ConcreteItemGroup} from "../../game-model/inventory/ConcreteItemGroup"; export class ItemgroupParser { private parsedItemgroups: ItemGroup[] = [] + private topParsedItemgroups: ItemGroup[] = [] + parseItemgroups(storeComponents: StoreComponent[]) { + const topologicalSort = this.topologicalSort(storeComponents); + topologicalSort.forEach(storeComponent => this.parseSingleItemgroup(storeComponent)); + return this.parsedItemgroups; + } + + private topologicalSort(storeComponents: StoreComponent[]) { + const sortedObjects: StoreComponent[] = [] + const visited: {[key: string]: boolean} = {}; + + const visit = (object: StoreComponent) => { + const jsonData = JSON.parse(object.jsonString) + if(visited[jsonData.componentName]) return; + visited[jsonData.componentName] = true; + + if(jsonData.parent) { + const parentObject = storeComponents.find(obj => JSON.parse(obj.jsonString).componentName === jsonData.parent); + if(parentObject) { + visit(parentObject); + } + } + sortedObjects.push(object); + } + + storeComponents.forEach(object => visit(object)); + + return sortedObjects; + } + + parseSingleItemgroup(storeComponent: StoreComponent) { + const data = JSON.parse(storeComponent.jsonString); + + const componentName = data.componentName; + const componentDescription = data.componentDescription; + const parentgroupName = data.parentgroup; + + let itemgroup; + if(data.itemgroupType == 0) { + itemgroup = new ConcreteItemGroup(componentName, componentDescription, ModelComponentType.ITEMGROUP); + } else { + itemgroup = new AbstractItemGroup(componentName, componentDescription, ModelComponentType.ITEMGROUP); + } + + const parentgroup = this.parsedItemgroups.find(parent => parent.componentName === parentgroupName); + + if(parentgroup != undefined) { + const abstractParentgroup = parentgroup as AbstractItemGroup; + abstractParentgroup.addChildItemgroup(itemgroup) + } else { + this.parsedItemgroups.push(itemgroup); + this.topParsedItemgroups.push(itemgroup); + } + + this.parseItemgroupCharacteristics(data.itemGroupCharacteristics, itemgroup); + } + + parseItemgroupCharacteristics(itemgroupCharacteristicsData: any, itemgroup: ItemGroup): ItemGroupCharacteristic[] { + const itemgroupCharacteristics: ItemGroupCharacteristic[] = [] + for(let i=0; i this.serializeSingleItemgroupHierarchy(child)); } else { - const storeComponent = this.serializeItemgroup(itemgroup); + const storeComponent = this.serializeConcreteItemgroup(itemgroup as ConcreteItemGroup); this.serializedItemgroups.push(storeComponent) this.serializeItemsOfItemgroup(itemgroup as ConcreteItemGroup); } } - private serializeItemgroup(itemgroup: ItemGroup): StoreComponent { + private serializeAbstractItemgroup(itemgroup: AbstractItemGroup): StoreComponent { const componentType = ModelComponentType.ITEMGROUP; const fileName = ItemSerializer.computeItemgroupPath(itemgroup); - const jsonString = JSON.stringify(itemgroup, (key, value) => { - if(ItemSerializer.ignoredGroupKeys.includes(key)) { - return undefined - } else { - - if(key === 'key') { - return value.characteristicName - } else { - return value; + const jsonObject = { + componentName: itemgroup.componentName, + componentDescription: itemgroup.componentDescription, + itemGroupCharacteristics: itemgroup.itemGroupCharacteristics.map(characteristic => { + return { + characteristicName: characteristic.characteristicName, + characteristicDescription: characteristic.characteristicDescription } + }), + parentgroup: itemgroup.parentGroup, + itemgroupType: ItemgroupType.ABSTRACT + }; - } + const jsonString = JSON.stringify(jsonObject, (key, value) => { + return value; + }, SerializeConstants.JSON_INDENT); + return new StoreComponent(jsonString, fileName, componentType) + } + + private serializeConcreteItemgroup(itemgroup: ConcreteItemGroup) { + const componentType = ModelComponentType.ITEMGROUP; + const fileName = ItemSerializer.computeItemgroupPath(itemgroup); + + const jsonObject = { + componentName: itemgroup.componentName, + componentDescription: itemgroup.componentDescription, + itemGroupCharacteristics: itemgroup.itemGroupCharacteristics.map(characteristic => { + return { + characteristicName: characteristic.characteristicName, + characteristicDescription: characteristic.characteristicDescription + } + }), + itemgroupType: ItemgroupType.CONCRETE, + parentgroup: itemgroup.parentGroup?.componentName + }; + + const jsonString = JSON.stringify(jsonObject, (key, value) => { + return value; }, SerializeConstants.JSON_INDENT); return new StoreComponent(jsonString, fileName, componentType) } diff --git a/testModel/items/Clothing/Clothing.json b/testModel/items/Clothing/Clothing.json index e3e3412..af1c0a1 100644 --- a/testModel/items/Clothing/Clothing.json +++ b/testModel/items/Clothing/Clothing.json @@ -7,6 +7,5 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [], "itemgroupType": 1 } \ No newline at end of file diff --git a/testModel/items/Clothing/Hose/Hose.json b/testModel/items/Clothing/Hose/Hose.json index 2b39d60..241268e 100644 --- a/testModel/items/Clothing/Hose/Hose.json +++ b/testModel/items/Clothing/Hose/Hose.json @@ -2,18 +2,6 @@ "componentName": "Hose", "componentDescription": "", "itemGroupCharacteristics": [], - "manuallyInheritedItems": [], "itemgroupType": 0, - "parentGroup": { - "componentName": "Clothing", - "componentDescription": "", - "itemGroupCharacteristics": [ - { - "characteristicName": "Test0", - "characteristicDescription": "" - } - ], - "manuallyInheritedItems": [], - "itemgroupType": 1 - } + "parentgroup": "Clothing" } \ No newline at end of file diff --git a/testModel/items/Clothing/Oberteil/Oberteil.json b/testModel/items/Clothing/Oberteil/Oberteil.json index 2173a00..1079ae4 100644 --- a/testModel/items/Clothing/Oberteil/Oberteil.json +++ b/testModel/items/Clothing/Oberteil/Oberteil.json @@ -2,18 +2,6 @@ "componentName": "Oberteil", "componentDescription": "", "itemGroupCharacteristics": [], - "manuallyInheritedItems": [], "itemgroupType": 0, - "parentGroup": { - "componentName": "Clothing", - "componentDescription": "", - "itemGroupCharacteristics": [ - { - "characteristicName": "Test0", - "characteristicDescription": "" - } - ], - "manuallyInheritedItems": [], - "itemgroupType": 1 - } + "parentgroup": "Clothing" } \ No newline at end of file diff --git a/testModel/items/Inventory/Inventory.json b/testModel/items/Inventory/Inventory.json index 01b3765..27b2fe9 100644 --- a/testModel/items/Inventory/Inventory.json +++ b/testModel/items/Inventory/Inventory.json @@ -7,17 +7,5 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [ - { - "componentName": "Hose 1", - "componentDescription": "", - "itemCharacteristicValues": [ - { - "key": "Test0", - "value": 0 - } - ] - } - ], "itemgroupType": 1 } \ No newline at end of file -- 2.34.1 From cb2094aa49783c8a92f64d4cfd4719c2d289f1b5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 15:24:36 +0200 Subject: [PATCH 30/31] Parse Itemgroups --- app/storage/loader/GameModelLoader.js | 4 +- app/storage/loader/ItemLoader.js | 43 ++++++++++ src/app/app.component.ts | 6 ++ src/app/project/game-model/GameModel.ts | 10 --- .../parser/itemParser/ItemgroupParser.ts | 80 +++++++++++++++++++ src/app/project/serializer/ItemSerializer.ts | 55 +++++++++---- testModel/items/Clothing/Clothing.json | 1 - testModel/items/Clothing/Hose/Hose.json | 14 +--- .../items/Clothing/Oberteil/Oberteil.json | 14 +--- testModel/items/Inventory/Inventory.json | 12 --- 10 files changed, 174 insertions(+), 65 deletions(-) create mode 100644 app/storage/loader/ItemLoader.js diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index 1ff3639..5ffc6d5 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -17,8 +17,8 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); - const storedItemgroupsd = this.loadItemgroups(); - return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, [], []); + const storedItemgroups = this.loadItemgroups(); + return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, []); } loadScriptAccountComponents() { const scriptAccountDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME); diff --git a/app/storage/loader/ItemLoader.js b/app/storage/loader/ItemLoader.js new file mode 100644 index 0000000..a454616 --- /dev/null +++ b/app/storage/loader/ItemLoader.js @@ -0,0 +1,43 @@ +"use strict"; +Object.defineProperty(exports, "__esModule", { value: true }); +exports.ItemLoader = void 0; +const StoreComponent_1 = require("../StoreComponent"); +const FileUtils_1 = require("../FileUtils"); +const fs = require("node:fs"); +const path = require("node:path"); +const ModelComponentType_1 = require("../../../src/app/project/game-model/ModelComponentType"); +class ItemLoader { + constructor(itemDir) { + this.itemDir = itemDir; + } + loadItemgroups() { + return this.loadItemgroupsRecursively(this.itemDir); + } + loadItemgroupsRecursively(currentDir) { + let loadedItemgroups = []; + const itemgroupFiles = FileUtils_1.FileUtils.listFilesInDirectory(currentDir); + itemgroupFiles.forEach(itemgroupFile => { + if (fs.lstatSync(itemgroupFile).isDirectory()) { + const childgroup = this.loadItemgroupsRecursively(itemgroupFile); + loadedItemgroups = loadedItemgroups.concat(childgroup); + } + else if (path.basename(itemgroupFile).endsWith(".json") && this.fileRepresentsItemgroup(itemgroupFile)) { + const loadedItemgroup = this.loadSingleItemgroup(itemgroupFile); + loadedItemgroups.push(loadedItemgroup); + } + }); + return loadedItemgroups; + } + loadSingleItemgroup(itemgroupFile) { + if (itemgroupFile.endsWith(".json")) { + const data = fs.readFileSync(itemgroupFile, "utf-8"); + return new StoreComponent_1.StoreComponent(data, itemgroupFile, ModelComponentType_1.ModelComponentType.ITEMGROUP); + } + return undefined; + } + fileRepresentsItemgroup(file) { + return path.basename(path.dirname(file)) === path.parse(path.basename(file)).name; + } +} +exports.ItemLoader = ItemLoader; +//# sourceMappingURL=ItemLoader.js.map \ No newline at end of file diff --git a/src/app/app.component.ts b/src/app/app.component.ts index d0e1c85..81392b6 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -28,6 +28,7 @@ import {TemplateType} from "./project/game-model/templates/TemplateType"; import {TemplateTypeUtilities} from "./project/game-model/templates/TemplateTypeUtilities"; import {SimpleTemplateGamesystem} from "./project/game-model/templates/simpleGamesystem/SimpleTemplateGamesystem"; import {ItemSerializer} from "./project/serializer/ItemSerializer"; +import {ItemgroupParser} from "./project/parser/itemParser/ItemgroupParser"; @Component({ selector: 'app-root', @@ -224,6 +225,11 @@ export class AppComponent implements OnInit{ const characterParser = new CharacterParser(characterTemplateSystems, characterRelationTemplateSystems, gameModel.scriptAccounts); gameModel.characters = characterParser.parseCharacters(storedGameModel.storedCharacters) + const itemgroupParser = new ItemgroupParser(); + itemgroupParser.parseItemgroups(storedGameModel.storedItemgroups); + + gameModel.itemgroups = itemgroupParser.getParsedTopItemgroups(); + this.gameModel = gameModel; } diff --git a/src/app/project/game-model/GameModel.ts b/src/app/project/game-model/GameModel.ts index c134c4d..dde1cc3 100644 --- a/src/app/project/game-model/GameModel.ts +++ b/src/app/project/game-model/GameModel.ts @@ -28,16 +28,6 @@ export class GameModel { constructor(gameModelName: string) { this.gameModelName = gameModelName; - - this.addAbstractItemgroup("Clothing", undefined); - this.addAbstractItemgroup("Inventory", undefined); - this.addConcreteItemgroup("Oberteil", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); - this.addConcreteItemgroup("Hose", GameModel.findItemgroupByName("Clothing", this.itemgroups)! as AbstractItemGroup); - - const item = this.addItem("Hose 1", "Hose"); - item!.addInheritedGroup(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!) - console.log(GameModel.findItemgroupByName("Inventory", this.itemgroups!)!.manuallyInheritedItems) - this.addItem("Hose 2", "Hose"); } addAbstractItemgroup(groupName: string, parentgroup: AbstractItemGroup | undefined) { diff --git a/src/app/project/parser/itemParser/ItemgroupParser.ts b/src/app/project/parser/itemParser/ItemgroupParser.ts index 36b509d..de65648 100644 --- a/src/app/project/parser/itemParser/ItemgroupParser.ts +++ b/src/app/project/parser/itemParser/ItemgroupParser.ts @@ -1,8 +1,88 @@ import {ItemGroup} from "../../game-model/inventory/ItemGroup"; +import {StoreComponent} from "../../../../../app/storage/StoreComponent"; +import {ItemGroupCharacteristic} from "../../game-model/inventory/ItemgroupCharacteristic"; +import {AbstractItemGroup} from "../../game-model/inventory/AbstractItemGroup"; +import {ModelComponentType} from "../../game-model/ModelComponentType"; +import {ConcreteItemGroup} from "../../game-model/inventory/ConcreteItemGroup"; export class ItemgroupParser { private parsedItemgroups: ItemGroup[] = [] + private topParsedItemgroups: ItemGroup[] = [] + parseItemgroups(storeComponents: StoreComponent[]) { + const topologicalSort = this.topologicalSort(storeComponents); + topologicalSort.forEach(storeComponent => this.parseSingleItemgroup(storeComponent)); + return this.parsedItemgroups; + } + + private topologicalSort(storeComponents: StoreComponent[]) { + const sortedObjects: StoreComponent[] = [] + const visited: {[key: string]: boolean} = {}; + + const visit = (object: StoreComponent) => { + const jsonData = JSON.parse(object.jsonString) + if(visited[jsonData.componentName]) return; + visited[jsonData.componentName] = true; + + if(jsonData.parent) { + const parentObject = storeComponents.find(obj => JSON.parse(obj.jsonString).componentName === jsonData.parent); + if(parentObject) { + visit(parentObject); + } + } + sortedObjects.push(object); + } + + storeComponents.forEach(object => visit(object)); + + return sortedObjects; + } + + parseSingleItemgroup(storeComponent: StoreComponent) { + const data = JSON.parse(storeComponent.jsonString); + + const componentName = data.componentName; + const componentDescription = data.componentDescription; + const parentgroupName = data.parentgroup; + + let itemgroup; + if(data.itemgroupType == 0) { + itemgroup = new ConcreteItemGroup(componentName, componentDescription, ModelComponentType.ITEMGROUP); + } else { + itemgroup = new AbstractItemGroup(componentName, componentDescription, ModelComponentType.ITEMGROUP); + } + + const parentgroup = this.parsedItemgroups.find(parent => parent.componentName === parentgroupName); + + if(parentgroup != undefined) { + const abstractParentgroup = parentgroup as AbstractItemGroup; + abstractParentgroup.addChildItemgroup(itemgroup) + } else { + this.parsedItemgroups.push(itemgroup); + this.topParsedItemgroups.push(itemgroup); + } + + this.parseItemgroupCharacteristics(data.itemGroupCharacteristics, itemgroup); + } + + parseItemgroupCharacteristics(itemgroupCharacteristicsData: any, itemgroup: ItemGroup): ItemGroupCharacteristic[] { + const itemgroupCharacteristics: ItemGroupCharacteristic[] = [] + for(let i=0; i this.serializeSingleItemgroupHierarchy(child)); } else { - const storeComponent = this.serializeItemgroup(itemgroup); + const storeComponent = this.serializeConcreteItemgroup(itemgroup as ConcreteItemGroup); this.serializedItemgroups.push(storeComponent) this.serializeItemsOfItemgroup(itemgroup as ConcreteItemGroup); } } - private serializeItemgroup(itemgroup: ItemGroup): StoreComponent { + private serializeAbstractItemgroup(itemgroup: AbstractItemGroup): StoreComponent { const componentType = ModelComponentType.ITEMGROUP; const fileName = ItemSerializer.computeItemgroupPath(itemgroup); - const jsonString = JSON.stringify(itemgroup, (key, value) => { - if(ItemSerializer.ignoredGroupKeys.includes(key)) { - return undefined - } else { - - if(key === 'key') { - return value.characteristicName - } else { - return value; + const jsonObject = { + componentName: itemgroup.componentName, + componentDescription: itemgroup.componentDescription, + itemGroupCharacteristics: itemgroup.itemGroupCharacteristics.map(characteristic => { + return { + characteristicName: characteristic.characteristicName, + characteristicDescription: characteristic.characteristicDescription } + }), + parentgroup: itemgroup.parentGroup, + itemgroupType: ItemgroupType.ABSTRACT + }; - } + const jsonString = JSON.stringify(jsonObject, (key, value) => { + return value; + }, SerializeConstants.JSON_INDENT); + return new StoreComponent(jsonString, fileName, componentType) + } + + private serializeConcreteItemgroup(itemgroup: ConcreteItemGroup) { + const componentType = ModelComponentType.ITEMGROUP; + const fileName = ItemSerializer.computeItemgroupPath(itemgroup); + + const jsonObject = { + componentName: itemgroup.componentName, + componentDescription: itemgroup.componentDescription, + itemGroupCharacteristics: itemgroup.itemGroupCharacteristics.map(characteristic => { + return { + characteristicName: characteristic.characteristicName, + characteristicDescription: characteristic.characteristicDescription + } + }), + itemgroupType: ItemgroupType.CONCRETE, + parentgroup: itemgroup.parentGroup?.componentName + }; + + const jsonString = JSON.stringify(jsonObject, (key, value) => { + return value; }, SerializeConstants.JSON_INDENT); return new StoreComponent(jsonString, fileName, componentType) } diff --git a/testModel/items/Clothing/Clothing.json b/testModel/items/Clothing/Clothing.json index e3e3412..af1c0a1 100644 --- a/testModel/items/Clothing/Clothing.json +++ b/testModel/items/Clothing/Clothing.json @@ -7,6 +7,5 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [], "itemgroupType": 1 } \ No newline at end of file diff --git a/testModel/items/Clothing/Hose/Hose.json b/testModel/items/Clothing/Hose/Hose.json index 2b39d60..241268e 100644 --- a/testModel/items/Clothing/Hose/Hose.json +++ b/testModel/items/Clothing/Hose/Hose.json @@ -2,18 +2,6 @@ "componentName": "Hose", "componentDescription": "", "itemGroupCharacteristics": [], - "manuallyInheritedItems": [], "itemgroupType": 0, - "parentGroup": { - "componentName": "Clothing", - "componentDescription": "", - "itemGroupCharacteristics": [ - { - "characteristicName": "Test0", - "characteristicDescription": "" - } - ], - "manuallyInheritedItems": [], - "itemgroupType": 1 - } + "parentgroup": "Clothing" } \ No newline at end of file diff --git a/testModel/items/Clothing/Oberteil/Oberteil.json b/testModel/items/Clothing/Oberteil/Oberteil.json index 2173a00..1079ae4 100644 --- a/testModel/items/Clothing/Oberteil/Oberteil.json +++ b/testModel/items/Clothing/Oberteil/Oberteil.json @@ -2,18 +2,6 @@ "componentName": "Oberteil", "componentDescription": "", "itemGroupCharacteristics": [], - "manuallyInheritedItems": [], "itemgroupType": 0, - "parentGroup": { - "componentName": "Clothing", - "componentDescription": "", - "itemGroupCharacteristics": [ - { - "characteristicName": "Test0", - "characteristicDescription": "" - } - ], - "manuallyInheritedItems": [], - "itemgroupType": 1 - } + "parentgroup": "Clothing" } \ No newline at end of file diff --git a/testModel/items/Inventory/Inventory.json b/testModel/items/Inventory/Inventory.json index 01b3765..27b2fe9 100644 --- a/testModel/items/Inventory/Inventory.json +++ b/testModel/items/Inventory/Inventory.json @@ -7,17 +7,5 @@ "characteristicDescription": "" } ], - "manuallyInheritedItems": [ - { - "componentName": "Hose 1", - "componentDescription": "", - "itemCharacteristicValues": [ - { - "key": "Test0", - "value": 0 - } - ] - } - ], "itemgroupType": 1 } \ No newline at end of file -- 2.34.1 From f01d8c4dab6aae0c13a052a82e3516978a0b7708 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20B=C3=B6ckelmann?= Date: Thu, 9 May 2024 16:03:52 +0200 Subject: [PATCH 31/31] Parse Items --- app/storage/loader/GameModelLoader.js | 12 ++- app/storage/loader/GameModelLoader.ts | 14 ++- app/storage/loader/ItemLoader.js | 30 +++++-- app/storage/loader/ItemLoader.ts | 37 ++++++-- src/app/app.component.ts | 5 +- .../project/parser/itemParser/ItemParser.ts | 87 +++++++++++++++++++ .../parser/itemParser/ItemgroupParser.ts | 8 +- src/app/project/serializer/ItemSerializer.ts | 2 +- src/app/shared/Tupel.ts | 10 +++ testModel/items/Clothing/Hose/Hose 1.json | 4 + testModel/items/Clothing/Hose/Hose 2.json | 4 + 11 files changed, 186 insertions(+), 27 deletions(-) create mode 100644 src/app/project/parser/itemParser/ItemParser.ts create mode 100644 src/app/shared/Tupel.ts diff --git a/app/storage/loader/GameModelLoader.js b/app/storage/loader/GameModelLoader.js index 5ffc6d5..0b8447e 100644 --- a/app/storage/loader/GameModelLoader.js +++ b/app/storage/loader/GameModelLoader.js @@ -10,6 +10,8 @@ const CharacterLoader_1 = require("./CharacterLoader"); const ItemLoader_1 = require("./ItemLoader"); class GameModelLoader { constructor(gameModelDir) { + this.loadedItemgroups = []; + this.loadedItems = []; this.gameModelDir = gameModelDir; } loadGameModel() { @@ -17,8 +19,8 @@ class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters(); - const storedItemgroups = this.loadItemgroups(); - return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, []); + this.loadItemsAndItemgroups(); + return new StoredGameModel_1.StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, this.loadedItemgroups, this.loadedItems); } loadScriptAccountComponents() { const scriptAccountDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.SCRIPTACCOUNT_DIR_NAME); @@ -35,10 +37,12 @@ class GameModelLoader { const characterLoader = new CharacterLoader_1.CharacterLoader(characterDir); return characterLoader.loadCharacters(); } - loadItemgroups() { + loadItemsAndItemgroups() { const itemgroupDir = path.join(this.gameModelDir, ModelComponentFileDirectory_1.ModelComponentFileDirectory.ITEMGROUP_DIR_NAME); const itemgroupLoader = new ItemLoader_1.ItemLoader(itemgroupDir); - return itemgroupLoader.loadItemgroups(); + itemgroupLoader.loadItemgroups(); + this.loadedItems = itemgroupLoader.loadedItems; + this.loadedItemgroups = itemgroupLoader.loadedItemgroups; } } exports.GameModelLoader = GameModelLoader; diff --git a/app/storage/loader/GameModelLoader.ts b/app/storage/loader/GameModelLoader.ts index fc46748..9423d73 100644 --- a/app/storage/loader/GameModelLoader.ts +++ b/app/storage/loader/GameModelLoader.ts @@ -11,6 +11,9 @@ import {ItemLoader} from "./ItemLoader"; export class GameModelLoader { gameModelDir: string + loadedItemgroups: StoreComponent[] = [] + loadedItems: StoreComponent[] = [] + constructor(gameModelDir: string) { this.gameModelDir = gameModelDir; @@ -22,9 +25,9 @@ export class GameModelLoader { const storedScriptAccounts = this.loadScriptAccountComponents(); const storedGamesystems = this.loadGamesystems(); const storedCharacters = this.loadCharacters() - const storedItemgroups = this.loadItemgroups() + this.loadItemsAndItemgroups(); - return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, storedItemgroups, []); + return new StoredGameModel(gameModelName, storedScriptAccounts, storedGamesystems, storedCharacters, this.loadedItemgroups, this.loadedItems); } private loadScriptAccountComponents() { @@ -46,9 +49,12 @@ export class GameModelLoader { } - private loadItemgroups() { + private loadItemsAndItemgroups() { const itemgroupDir = path.join(this.gameModelDir, ModelComponentFileDirectory.ITEMGROUP_DIR_NAME); const itemgroupLoader = new ItemLoader(itemgroupDir); - return itemgroupLoader.loadItemgroups(); + itemgroupLoader.loadItemgroups(); + + this.loadedItems = itemgroupLoader.loadedItems; + this.loadedItemgroups = itemgroupLoader.loadedItemgroups; } } diff --git a/app/storage/loader/ItemLoader.js b/app/storage/loader/ItemLoader.js index a454616..acb1bff 100644 --- a/app/storage/loader/ItemLoader.js +++ b/app/storage/loader/ItemLoader.js @@ -3,30 +3,39 @@ Object.defineProperty(exports, "__esModule", { value: true }); exports.ItemLoader = void 0; const StoreComponent_1 = require("../StoreComponent"); const FileUtils_1 = require("../FileUtils"); -const fs = require("node:fs"); const path = require("node:path"); const ModelComponentType_1 = require("../../../src/app/project/game-model/ModelComponentType"); +const fs = require("node:fs"); class ItemLoader { constructor(itemDir) { + this._loadedItemgroups = []; + this._loadedItems = []; this.itemDir = itemDir; } loadItemgroups() { - return this.loadItemgroupsRecursively(this.itemDir); + this.loadItemgroupsRecursively(this.itemDir); + } + get loadedItemgroups() { + return this._loadedItemgroups; + } + get loadedItems() { + return this._loadedItems; } loadItemgroupsRecursively(currentDir) { - let loadedItemgroups = []; const itemgroupFiles = FileUtils_1.FileUtils.listFilesInDirectory(currentDir); itemgroupFiles.forEach(itemgroupFile => { if (fs.lstatSync(itemgroupFile).isDirectory()) { - const childgroup = this.loadItemgroupsRecursively(itemgroupFile); - loadedItemgroups = loadedItemgroups.concat(childgroup); + this.loadItemgroupsRecursively(itemgroupFile); } else if (path.basename(itemgroupFile).endsWith(".json") && this.fileRepresentsItemgroup(itemgroupFile)) { const loadedItemgroup = this.loadSingleItemgroup(itemgroupFile); - loadedItemgroups.push(loadedItemgroup); + this._loadedItemgroups.push(loadedItemgroup); + } + else if (path.basename(itemgroupFile).endsWith(".json")) { + const loadedItem = this.loadSingleItem(itemgroupFile); + this._loadedItems.push(loadedItem); } }); - return loadedItemgroups; } loadSingleItemgroup(itemgroupFile) { if (itemgroupFile.endsWith(".json")) { @@ -35,6 +44,13 @@ class ItemLoader { } return undefined; } + loadSingleItem(itemFile) { + if (itemFile.endsWith(".json")) { + const data = fs.readFileSync(itemFile, "utf-8"); + return new StoreComponent_1.StoreComponent(data, itemFile, ModelComponentType_1.ModelComponentType.ITEM); + } + return undefined; + } fileRepresentsItemgroup(file) { return path.basename(path.dirname(file)) === path.parse(path.basename(file)).name; } diff --git a/app/storage/loader/ItemLoader.ts b/app/storage/loader/ItemLoader.ts index 6e84368..91b6a83 100644 --- a/app/storage/loader/ItemLoader.ts +++ b/app/storage/loader/ItemLoader.ts @@ -1,35 +1,46 @@ import {StoreComponent} from "../StoreComponent"; import {FileUtils} from "../FileUtils"; -import * as fs from "node:fs"; import * as path from "node:path"; import {ModelComponentType} from "../../../src/app/project/game-model/ModelComponentType"; +import * as fs from "node:fs"; export class ItemLoader { itemDir: string + private _loadedItemgroups: StoreComponent[] = [] + private _loadedItems: StoreComponent[] = [] constructor(itemDir: string) { this.itemDir = itemDir; } - loadItemgroups(): StoreComponent[] { - return this.loadItemgroupsRecursively(this.itemDir); + loadItemgroups(){ + this.loadItemgroupsRecursively(this.itemDir); } - private loadItemgroupsRecursively(currentDir: string): StoreComponent[] { - let loadedItemgroups : StoreComponent[] = [] + + get loadedItemgroups(): StoreComponent[] { + return this._loadedItemgroups; + } + + get loadedItems(): StoreComponent[] { + return this._loadedItems; + } + + private loadItemgroupsRecursively(currentDir: string) { const itemgroupFiles = FileUtils.listFilesInDirectory(currentDir); itemgroupFiles.forEach(itemgroupFile => { if(fs.lstatSync(itemgroupFile).isDirectory()) { - const childgroup = this.loadItemgroupsRecursively(itemgroupFile); - loadedItemgroups = loadedItemgroups.concat(childgroup); + this.loadItemgroupsRecursively(itemgroupFile); } else if(path.basename(itemgroupFile).endsWith(".json") && this.fileRepresentsItemgroup(itemgroupFile)){ const loadedItemgroup = this.loadSingleItemgroup(itemgroupFile)!; - loadedItemgroups.push(loadedItemgroup) + this._loadedItemgroups.push(loadedItemgroup) + } else if(path.basename(itemgroupFile).endsWith(".json")) { + const loadedItem = this.loadSingleItem(itemgroupFile)!; + this._loadedItems.push(loadedItem); } }) - return loadedItemgroups; } private loadSingleItemgroup(itemgroupFile: string): StoreComponent | undefined { @@ -40,6 +51,14 @@ export class ItemLoader { return undefined } + private loadSingleItem(itemFile: string) { + if(itemFile.endsWith(".json")) { + const data = fs.readFileSync(itemFile, "utf-8"); + return new StoreComponent(data, itemFile, ModelComponentType.ITEM); + } + return undefined + } + private fileRepresentsItemgroup(file: string): boolean { return path.basename(path.dirname(file)) === path.parse(path.basename(file)).name; } diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 81392b6..6a0240f 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -29,6 +29,7 @@ import {TemplateTypeUtilities} from "./project/game-model/templates/TemplateType import {SimpleTemplateGamesystem} from "./project/game-model/templates/simpleGamesystem/SimpleTemplateGamesystem"; import {ItemSerializer} from "./project/serializer/ItemSerializer"; import {ItemgroupParser} from "./project/parser/itemParser/ItemgroupParser"; +import {ItemParser} from "./project/parser/itemParser/ItemParser"; @Component({ selector: 'app-root', @@ -227,9 +228,11 @@ export class AppComponent implements OnInit{ const itemgroupParser = new ItemgroupParser(); itemgroupParser.parseItemgroups(storedGameModel.storedItemgroups); - gameModel.itemgroups = itemgroupParser.getParsedTopItemgroups(); + const itemParser = new ItemParser(itemgroupParser.getParsedItemgroups()) + itemParser.parseItems(storedGameModel.storedItems); + this.gameModel = gameModel; } diff --git a/src/app/project/parser/itemParser/ItemParser.ts b/src/app/project/parser/itemParser/ItemParser.ts new file mode 100644 index 0000000..40da22f --- /dev/null +++ b/src/app/project/parser/itemParser/ItemParser.ts @@ -0,0 +1,87 @@ +import {ItemGroup} from "../../game-model/inventory/ItemGroup"; +import {StoreComponent} from "../../../../../app/storage/StoreComponent"; +import {Item} from "../../game-model/inventory/Item"; +import {ModelComponentType} from "../../game-model/ModelComponentType"; +import {ConcreteItemGroup} from "../../game-model/inventory/ConcreteItemGroup"; +import {ItemgroupCharacteristicValue} from "../../game-model/inventory/ItemgroupCharacteristicValue"; + +export class ItemParser { + parsedItemgroups: ItemGroup[] = [] + + constructor(itemgroups: ItemGroup[] = []) { + this.parsedItemgroups = itemgroups; + } + + parseItems(storeComponents: StoreComponent[]): Item[] { + const parsedItems: Item[] = [] + storeComponents.forEach(storeComponent => parsedItems.push(this.parseSingleItem(storeComponent))); + return parsedItems; + } + + private parseSingleItem(storeComponent: StoreComponent) { + const parsedData = JSON.parse(storeComponent.jsonString); + + const componentName = parsedData.componentName; + const componentDescription = parsedData.componentDescription; + + const manuallyInheritedGroups = this.parseInheritedGroups(parsedData.manuallyInheritedGroups); + const hierarchyInheritedGroups = this.parseInheritedGroups(parsedData.hierarchyInheritedGroups); + + const item = new Item(componentName, componentDescription, ModelComponentType.ITEM); + item.manuallyInheritedGroups = manuallyInheritedGroups; + item.hierarchyInheritedGroups = hierarchyInheritedGroups; + + const owningGroup = hierarchyInheritedGroups.find(itemgroup => itemgroup instanceof ConcreteItemGroup); + if (owningGroup) { + (owningGroup as ConcreteItemGroup).items.push(item); + } else { + console.log("[ERROR] No group found for item: ", item.componentName) + } + + + item.itemCharacteristicValues = this.parseItemCharacteristicValues(parsedData.itemCharacteristicValues); + return item; + } + + private parseInheritedGroups(inheritedGroupsData: any) { + const inheritedGroups: ItemGroup[] = [] + for(let i=0; i group.componentName === inheritedGroupName); + if (matchedGroup) { + inheritedGroups.push(matchedGroup); + } + } + + return inheritedGroups; + } + + private parseItemCharacteristicValues(data: any): ItemgroupCharacteristicValue[] { + const values: ItemgroupCharacteristicValue[] = [] + for(let i=0; i characteristic.characteristicName === itemCharacteristicName); + + if(characteristic != undefined) { + return characteristic; + } + } + return undefined; + } + + +} diff --git a/src/app/project/parser/itemParser/ItemgroupParser.ts b/src/app/project/parser/itemParser/ItemgroupParser.ts index de65648..fb18e77 100644 --- a/src/app/project/parser/itemParser/ItemgroupParser.ts +++ b/src/app/project/parser/itemParser/ItemgroupParser.ts @@ -58,6 +58,7 @@ export class ItemgroupParser { if(parentgroup != undefined) { const abstractParentgroup = parentgroup as AbstractItemGroup; abstractParentgroup.addChildItemgroup(itemgroup) + this.parsedItemgroups.push(itemgroup) } else { this.parsedItemgroups.push(itemgroup); this.topParsedItemgroups.push(itemgroup); @@ -78,11 +79,16 @@ export class ItemgroupParser { const name = itemgroupCharacteristicData.characteristicName; const description = itemgroupCharacteristicData.characteristicDescription; - return new ItemGroupCharacteristic(name, description, itemgroup); + const characteristic = new ItemGroupCharacteristic(name, description, itemgroup); + characteristic.itemgroup.addItemgroupCharacteristic(characteristic); + return characteristic; } getParsedTopItemgroups() { return this.topParsedItemgroups; } + getParsedItemgroups() { + return this.parsedItemgroups; + } } diff --git a/src/app/project/serializer/ItemSerializer.ts b/src/app/project/serializer/ItemSerializer.ts index 3b08183..80d51bf 100644 --- a/src/app/project/serializer/ItemSerializer.ts +++ b/src/app/project/serializer/ItemSerializer.ts @@ -12,7 +12,7 @@ export class ItemSerializer { private serializedItemgroups: StoreComponent[] = [] private serializedItems: StoreComponent[] = [] private static ignoredGroupKeys: string[] = ['type', 'unsaved', "itemgroup", "manuallyInheritedGroups", "hierarchyInheritedGroups", "items"] - private static ignoredItemKeys: string[] = ['type', 'unsaved', 'hierarchyInheritedGroups'] + private static ignoredItemKeys: string[] = ['type', 'unsaved'] public serializeItemgroups(itemgroups: ItemGroup[]): StoreComponent[] { itemgroups.forEach(itemgroup => { diff --git a/src/app/shared/Tupel.ts b/src/app/shared/Tupel.ts new file mode 100644 index 0000000..e05b237 --- /dev/null +++ b/src/app/shared/Tupel.ts @@ -0,0 +1,10 @@ +export class Tupel { + value00: A + value01: B + + + constructor(value00: A, value01: B) { + this.value00 = value00; + this.value01 = value01; + } +} diff --git a/testModel/items/Clothing/Hose/Hose 1.json b/testModel/items/Clothing/Hose/Hose 1.json index 52f24ba..e2f14c9 100644 --- a/testModel/items/Clothing/Hose/Hose 1.json +++ b/testModel/items/Clothing/Hose/Hose 1.json @@ -4,6 +4,10 @@ "manuallyInheritedGroups": [ "Inventory" ], + "hierarchyInheritedGroups": [ + "Clothing", + "Hose" + ], "itemCharacteristicValues": [ { "key": "Test0", diff --git a/testModel/items/Clothing/Hose/Hose 2.json b/testModel/items/Clothing/Hose/Hose 2.json index ea92a4b..50ef84c 100644 --- a/testModel/items/Clothing/Hose/Hose 2.json +++ b/testModel/items/Clothing/Hose/Hose 2.json @@ -2,6 +2,10 @@ "componentName": "Hose 2", "componentDescription": "", "manuallyInheritedGroups": [], + "hierarchyInheritedGroups": [ + "Clothing", + "Hose" + ], "itemCharacteristicValues": [ { "key": "Test0", -- 2.34.1
Characteristic {{characteristicValue.key.characteristicName}}