Skip to content

Commit

Permalink
feat(shop): 添加行商页面及相关逻辑
Browse files Browse the repository at this point in the history
  • Loading branch information
Encaik committed Sep 21, 2024
1 parent f23b365 commit 9c3245a
Show file tree
Hide file tree
Showing 14 changed files with 208 additions and 61 deletions.
8 changes: 4 additions & 4 deletions src/app/app.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,14 +27,14 @@ export class AppComponent implements OnInit {
private rtSrv = inject(RuntimeService);
private router = inject(Router);
title = 'wanjie';
segmentedList: string[] = ['修炼', '功法', '虚空', '副本'];
segmentedRoutes: string[] = ['/home', '/method', '/universe', '/challenge'];
segmentedList: string[] = ['修炼', '功法', '虚空', '副本', '行商'];
segmentedRoutes: string[] = ['/home', '/method', '/universe', '/challenge', '/shop'];
currentSegmented: number = 0;

ngOnInit() {
this.rtSrv.load().then(data => {
if (data) {
this.rtSrv.init(data.characterData, data.envData, data.backpackData);
this.rtSrv.init(data.runtimeData, data.characterData, data.envData, data.backpackData);
} else {
this.init();
}
Expand All @@ -55,7 +55,7 @@ export class AppComponent implements OnInit {
nzWidth: '1000px'
})
.afterClose.subscribe(({ character, env }) => {
this.rtSrv.init(character, env);
this.rtSrv.init({ tick: 0 }, character, env);
});
}

Expand Down
4 changes: 3 additions & 1 deletion src/app/app.routes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { HomeComponent } from './pages/home/home.component';
import { UniverseComponent } from './pages/universe/universe.component';
import { MethodComponent } from './pages/method/method.component';
import { ChallengeComponent } from './pages/challenge/challenge.component';
import { ShopComponent } from './pages/shop/shop.component';

export const routes: Routes = [
{ path: '', redirectTo: '/home', pathMatch: 'full' },
Expand All @@ -15,7 +16,8 @@ export const routes: Routes = [
children: [
{ path: 'method', component: MethodComponent },
{ path: 'universe', component: UniverseComponent },
{ path: 'challenge', component: ChallengeComponent }
{ path: 'challenge', component: ChallengeComponent },
{ path: 'shop', component: ShopComponent }
]
}
];
33 changes: 33 additions & 0 deletions src/app/components/bag-item-view/bag-item-view.component.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
<nz-card class="h-full overflow-auto" [nzBodyStyle]="{ height: '100%', padding: '1rem', overflow: 'auto' }">
@for (bagItem of bagItems; track bagItem.id) {
<div
nz-card-grid
nz-popover
[nzPopoverContent]="contentTemplate"
class="flex flex-col justify-center items-center w-1/4 lg:w-1/6 2xl:w-1/12 h-16 p-2 relative"
>
{{ bagItem.item.name }}
<div class="absolute bottom-1 right-1 text-xs text-gray-500">
{{ bagItem.count }}
</div>
</div>
<ng-template #contentTemplate>
<div class="flex flex-col gap-2 justify-center items-center">
<span class="text-md font-bold">{{ bagItem.item.name }}</span>
<p class="text-gray-500">{{ bagItem.item.description }}</p>
<div class="flex gap-2">
@if (bagType === 'character') {
@if (bagItem.item.uesable) {
<button nz-button nzType="primary" nzSize="small" (click)="onItemUseClick(bagItem)">使用</button>
}
<button nz-button nzSize="small" (click)="onItemDropClick(bagItem, 1)">丢弃</button>
<button nz-button nzSize="small" (click)="onItemDropClick(bagItem, bagItem.count)">丢弃全部</button>
} @else if (bagType === 'shop') {
<button nz-button nzType="primary" nzSize="small" (click)="onItemBuyClick(bagItem, 1)">购买</button>
<button nz-button nzType="primary" nzSize="small" (click)="onItemBuyClick(bagItem, bagItem.count)">购买全部</button>
}
</div>
</div>
</ng-template>
}
</nz-card>
4 changes: 4 additions & 0 deletions src/app/components/bag-item-view/bag-item-view.component.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
:host{
flex: 1;
height: 0;
}
22 changes: 22 additions & 0 deletions src/app/components/bag-item-view/bag-item-view.component.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';

import { BagItemViewComponent } from './bag-item-view.component';

describe('ItemViewComponent', () => {
let component: BagItemViewComponent;
let fixture: ComponentFixture<BagItemViewComponent>;

beforeEach(async () => {
await TestBed.configureTestingModule({
imports: [BagItemViewComponent]
}).compileComponents();

fixture = TestBed.createComponent(BagItemViewComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});

it('should create', () => {
expect(component).toBeTruthy();
});
});
61 changes: 61 additions & 0 deletions src/app/components/bag-item-view/bag-item-view.component.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
import { Component, inject, Input } from '@angular/core';
import { NzCardModule } from 'ng-zorro-antd/card';
import { BagItem, ItemMap } from '../../models/item.model';
import { NzPopoverModule } from 'ng-zorro-antd/popover';
import { LogType, LogLevel } from '../../models';
import { BackpackService } from '../../services/backpack.service';
import { LogService } from '../../services/log.service';
import { NzButtonModule } from 'ng-zorro-antd/button';
import { NzMessageModule, NzMessageService } from 'ng-zorro-antd/message';

@Component({
selector: 'app-item-view',
standalone: true,
imports: [NzCardModule, NzPopoverModule, NzButtonModule, NzMessageModule],
templateUrl: './bag-item-view.component.html',
styleUrl: './bag-item-view.component.less'
})
export class BagItemViewComponent {
private backpackSrv = inject(BackpackService);
private logSrv = inject(LogService);
private msg = inject(NzMessageService);

@Input() bagItems: BagItem[] = [];
@Input() bagType: 'character' | 'shop' = 'character';

onItemUseClick(bagItem: BagItem) {
this.backpackSrv.useItem(bagItem.item).then(res => {
if (!res) {
this.backpackSrv.removeItem(bagItem.item, 1);
} else {
console.log(res);
}
});
}

onItemDropClick(bagItem: BagItem, count: number) {
this.backpackSrv.removeItem(bagItem.item, count);
this.logSrv.log({
msg: `丢弃${count}${bagItem.item.name}`,
type: LogType.Item,
level: LogLevel.Info
});
}

onItemBuyClick(bagItem: BagItem, count: number) {
const cost = bagItem.item.price * count;
const money = this.backpackSrv.getItemCountById('1');
if (money > cost) {
this.backpackSrv.addItem(bagItem.item, count);
this.backpackSrv.removeItem(ItemMap['1'], cost);
bagItem.count -= count;
this.logSrv.log({
msg: `花费${cost}个灵石,购买了${count}${bagItem.item.name}`,
type: LogType.Item,
level: LogLevel.Info
});
} else {
this.msg.warning('你买不起!');
}
}
}
29 changes: 1 addition & 28 deletions src/app/pages/home/components/backpack/backpack.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,34 +3,7 @@ <h5 nz-typography class="underline decoration-sky-500">背包</h5>
<nz-tabset class="h-full" [(nzSelectedIndex)]="tabIdx" nzType="card">
@for (tab of bagTabs; track $index) {
<nz-tab [nzTitle]="tab">
<nz-card class="h-full overflow-auto" [nzBodyStyle]="{ height: '100%', padding: '1rem', overflow: 'auto' }">
@for (bagItem of bagItems; track bagItem.id) {
<div
nz-card-grid
nz-popover
[nzPopoverContent]="contentTemplate"
class="flex flex-col justify-center items-center w-1/4 lg:w-1/6 2xl:w-1/12 h-16 p-2 relative"
>
{{ bagItem.item.name }}
<div class="absolute bottom-1 right-1 text-xs text-gray-500">
{{ bagItem.count }}
</div>
</div>
<ng-template #contentTemplate>
<div class="flex flex-col gap-2 justify-center items-center">
<span class="text-md font-bold">{{ bagItem.item.name }}</span>
<p class="text-gray-500">{{ bagItem.item.description }}</p>
<div class="flex gap-2">
@if (bagItem.item.uesable) {
<button nz-button nzType="primary" nzSize="small" (click)="onItemUseClick(bagItem)">使用</button>
}
<button nz-button nzSize="small" (click)="onItemDropClick(bagItem, 1)">丢弃</button>
<button nz-button nzSize="small" (click)="onItemDropClick(bagItem, bagItem.count)">丢弃全部</button>
</div>
</div>
</ng-template>
}
</nz-card>
<app-item-view [bagItems]="bagItems" />
</nz-tab>
}
</nz-tabset>
Expand Down
28 changes: 2 additions & 26 deletions src/app/pages/home/components/backpack/backpack.component.ts
Original file line number Diff line number Diff line change
@@ -1,48 +1,24 @@
import { Component, inject } from '@angular/core';
import { NzCardModule } from 'ng-zorro-antd/card';
import { NzPopoverModule } from 'ng-zorro-antd/popover';
import { NzTabsModule } from 'ng-zorro-antd/tabs';
import { NzTypographyModule } from 'ng-zorro-antd/typography';

import { BagItem, ItemTypeMap, ItemTypeValueMap } from '../../../../models/item.model';
import { BackpackService } from '../../../../services/backpack.service';
import { NzButtonModule } from 'ng-zorro-antd/button';
import { LogService } from '../../../../services/log.service';
import { LogLevel, LogType } from '../../../../models';
import { BagItemViewComponent } from '../../../../components/bag-item-view/bag-item-view.component';

@Component({
selector: 'app-backpack',
standalone: true,
imports: [NzTabsModule, NzCardModule, NzTypographyModule, NzPopoverModule, NzButtonModule],
imports: [NzTabsModule, NzTypographyModule, BagItemViewComponent],
templateUrl: './backpack.component.html',
styleUrl: './backpack.component.less'
})
export class BackpackComponent {
private backpackSrv = inject(BackpackService);
private logSrv = inject(LogService);
bagTabs: string[] = ['全部', ...Object.values(ItemTypeMap)];
tabIdx = 0;

get bagItems(): BagItem[] {
return this.backpackSrv.getItems(this.tabIdx ? ItemTypeValueMap[this.tabIdx] : undefined);
}

onItemUseClick(bagItem: BagItem) {
this.backpackSrv.useItem(bagItem.item).then(res => {
if (!res) {
this.backpackSrv.removeItem(bagItem.item, 1);
} else {
console.log(res);
}
});
}

onItemDropClick(bagItem: BagItem, count: number) {
this.backpackSrv.removeItem(bagItem.item, count);
this.logSrv.log({
msg: `丢弃${count}${bagItem.item.name}`,
type: LogType.Item,
level: LogLevel.Info
});
}
}
6 changes: 6 additions & 0 deletions src/app/pages/shop/shop.component.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
@if (isShopShow) {
<h5 nz-typography class="underline decoration-sky-500">商城</h5>
<app-item-view [bagItems]="bagItems" bagType="shop" />
} @else {
<nz-empty class="h-full flex flex-col justify-center items-center" nzNotFoundContent="行商已经离开,将在每年1月准时回来"></nz-empty>
}
6 changes: 6 additions & 0 deletions src/app/pages/shop/shop.component.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
:host{
flex: 1;
height: 0;
display: flex;
flex-direction: column;
}
23 changes: 23 additions & 0 deletions src/app/pages/shop/shop.component.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';

import { ShopComponent } from './shop.component';

describe('ShopComponent', () => {
let component: ShopComponent;
let fixture: ComponentFixture<ShopComponent>;

beforeEach(async () => {
await TestBed.configureTestingModule({
imports: [ShopComponent]
})
.compileComponents();

fixture = TestBed.createComponent(ShopComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});

it('should create', () => {
expect(component).toBeTruthy();
});
});
33 changes: 33 additions & 0 deletions src/app/pages/shop/shop.component.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { Component, inject } from '@angular/core';
import { RuntimeService } from '../../services/runtime.service';
import { NzTypographyModule } from 'ng-zorro-antd/typography';
import { NzEmptyModule } from 'ng-zorro-antd/empty';
import { BagItemViewComponent } from '../../components/bag-item-view/bag-item-view.component';
import { BagItem, ItemMap } from '../../models/item.model';

@Component({
selector: 'app-shop',
standalone: true,
imports: [NzTypographyModule, NzEmptyModule, BagItemViewComponent],
templateUrl: './shop.component.html',
styleUrl: './shop.component.less'
})
export class ShopComponent {
private rtSrv = inject(RuntimeService);

bagItems: BagItem[] = [];

get isShopShow() {
return this.rtSrv.timeTick.value % 36 < 3;
}

ngOnInit() {
this.bagItems = [
{
id: '40000',
item: ItemMap['40000'],
count: 100
}
];
}
}
4 changes: 4 additions & 0 deletions src/app/services/backpack.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,10 @@ export class BackpackService {

constructor() {}

getItemCountById(id: string) {
return this.items.get(ItemMap[id]) || 0;
}

saveItems() {
const items: { id: string; count: number }[] = [];
this.items.forEach((count, item) => {
Expand Down
8 changes: 6 additions & 2 deletions src/app/services/runtime.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,10 @@ export class RuntimeService {
}
}

init(characterData: Partial<Character>, envData: Env, backpackData?: BagItem[]) {
init(runtimeData: { tick: number }, characterData: Partial<Character>, envData: Env, backpackData?: BagItem[]) {
this.characterSrv.setCharacter(characterData);
this.envSrv.setEnv(envData);
this.timeTick.next(runtimeData.tick);
if (backpackData) this.backpackSrv.loadItems(backpackData);
this.isInit = true;
}
Expand All @@ -49,6 +50,9 @@ export class RuntimeService {
CryptoJS.AES.encrypt(
JSON.stringify({
time: time.getTime(),
runtimeData: {
tick: this.timeTick.value
},
characterData,
envData,
backpackData
Expand All @@ -59,7 +63,7 @@ export class RuntimeService {
this.notice.success('保存成功', `您的数据已保存,本次保存时间为${time.toLocaleString()}`);
}

load(): Promise<{ characterData: Character; envData: Env; backpackData: BagItem[] } | null> {
load(): Promise<{ runtimeData: { tick: number }; characterData: Character; envData: Env; backpackData: BagItem[] } | null> {
const data = localStorage.getItem(WANJIE_TOKEN);
if (data) {
const parseData = JSON.parse(CryptoJS.AES.decrypt(data, WANJIE_TOKEN).toString(CryptoJS.enc.Utf8));
Expand Down

1 comment on commit 9c3245a

@vercel
Copy link

@vercel vercel bot commented on 9c3245a Sep 21, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Successfully deployed to the following URLs:

wanjie – ./

wanjie.vercel.app
wanjie-git-main-encaiks-projects.vercel.app
wanjie-encaiks-projects.vercel.app

Please sign in to comment.