Skip to content

Commit

Permalink
closes #6
Browse files Browse the repository at this point in the history
  • Loading branch information
seiyria committed Apr 26, 2024
1 parent 1ff3121 commit bb20c46
Show file tree
Hide file tree
Showing 11 changed files with 213 additions and 61 deletions.
9 changes: 9 additions & 0 deletions interfaces/faq.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
export interface ICardFAQEntry {
q: string;
a: string;
}

export interface ICardFAQ {
card: string;
faq: ICardFAQEntry[];
}
1 change: 1 addition & 0 deletions interfaces/index.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
export * from './carddata';
export * from './cardhelp';
export * from './faq';
export * from './product';
1 change: 1 addition & 0 deletions interfaces/product.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,5 +16,6 @@ export interface IProduct extends IProductDefinition {
cardTemplate: string;
external: {
rules: string;
faq: Record<string, string>;
};
}
9 changes: 8 additions & 1 deletion src/app/_shared/components/card-text/card-text.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,18 @@ export class CardTextComponent {

constructor() {
const renderer = this.getCustomRenderer();

effect(() => {
this.html = marked(this.text(), { renderer });
this.html = marked(this.fixText(), {
renderer,
});
});
}

private fixText(): string {
return this.text().split('+').join('\\+').split('-').join('\\-');
}

private getCustomRenderer(): marked.Renderer {
const renderer = new marked.Renderer();

Expand Down
30 changes: 16 additions & 14 deletions src/app/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ import { environment } from '../environments/environment';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { CardsService } from './cards.service';
import { FAQService } from './faq.service';
import { LocaleService } from './locale.service';
import { MetaService } from './meta.service';

@NgModule({
Expand All @@ -32,21 +34,21 @@ import { MetaService } from './meta.service';
{ provide: RouteReuseStrategy, useClass: IonicRouteStrategy },
{
provide: APP_INITIALIZER,
useFactory: (cardsService: CardsService) => async () => {
await cardsService.init();
return cardsService;
},
deps: [CardsService],
multi: true,
},
{
provide: APP_INITIALIZER,
useFactory: (metaService: MetaService) => async () => {
await metaService.init();
return metaService;
},
deps: [MetaService],
multi: true,
deps: [MetaService, LocaleService, FAQService, CardsService],
useFactory:
(
metaService: MetaService,
localeService: LocaleService,
faqService: FAQService,
cardsService: CardsService
) =>
async () => {
await metaService.init();
await localeService.init();
await faqService.init();
await cardsService.init();
},
},
],
bootstrap: [AppComponent],
Expand Down
33 changes: 32 additions & 1 deletion src/app/card/card.page.html
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

<ion-content>
<div class="page-container">
@if(cardData) {
@if(cardData(); as cardData) {
<ion-grid>
<ion-row>
<ion-col [sizeXs]="12" [sizeMd]="6" [sizeLg]="4" [offsetLg]="2">
Expand Down Expand Up @@ -44,7 +44,38 @@
}
</ion-label>
</ion-item>
</ion-list>
</ion-card-content>
</ion-card>

@if(faq().length > 0) {
<ion-card class="card-info">
<ion-card-header>
<ion-card-title>FAQ</ion-card-title>
</ion-card-header>

<ion-card-content>
<ion-list>
@for(entry of faq(); track $index) {
<ion-item>
<ion-label text-wrap>
<h3>Q: {{ entry.q }}</h3>
<p>A: {{ entry.a }}</p>
</ion-label>
</ion-item>
}
</ion-list>
</ion-card-content>
</ion-card>
}

<ion-card class="card-info">
<ion-card-header>
<ion-card-title>More {{ metaService.getProductNameByProductId(cardData.product) }}</ion-card-title>
</ion-card-header>

<ion-card-content>
<ion-list>
<ion-item [href]="metaService.getRulesByProductId(cardData.product)" target="_blank">
<ion-icon slot="start" name="link-outline"></ion-icon>
Rules
Expand Down
38 changes: 2 additions & 36 deletions src/app/card/card.page.scss
Original file line number Diff line number Diff line change
@@ -1,44 +1,10 @@

.page-container {
margin-top: 1em;
}

.card-info {

&.color-B {
--color-bar-color-start: #0099d9;
--color-bar-color-end: #00587c;
}

&.color-R {
--color-bar-color-start: #e63028;
--color-bar-color-end: #6a111b;
}

&.color-G {
--color-bar-color-start: #3db554;
--color-bar-color-end: #21613d;
}

&.color-Y {
--color-bar-color-start: #faed00;
--color-bar-color-end: #7d700c;
}

.ability, .flavortext {
font-size: 0.75em;
}

.color-bar {
z-index: 0;
min-height: 22px;
width: 100%;
position: absolute;
bottom: 0;
left: 0;
right: 0;

background: linear-gradient(to right, var(--color-bar-color-start), var(--color-bar-color-end));
&:not(:first-child) {
margin-top: 2em;
}

app-cardicon {
Expand Down
38 changes: 29 additions & 9 deletions src/app/card/card.page.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,19 @@
import { Component, inject, type OnInit } from '@angular/core';
import {
Component,
computed,
inject,
signal,
type OnInit,
type Signal,
type WritableSignal,
} from '@angular/core';
import { ActivatedRoute, Router } from '@angular/router';
import { type ICard } from '../../../interfaces';
import { type ICard, type ICardFAQEntry } from '../../../interfaces';
import { CardsService } from '../cards.service';
import { MetaService } from '../meta.service';

import Handlebars from 'handlebars';
import { FAQService } from '../faq.service';

@Component({
selector: 'app-card',
Expand All @@ -15,25 +24,34 @@ export class CardPage implements OnInit {
private router = inject(Router);
private route = inject(ActivatedRoute);
private cardsService = inject(CardsService);
private faqService = inject(FAQService);
public metaService = inject(MetaService);

public cardData: ICard | undefined = undefined;
public cardData: WritableSignal<ICard | undefined> = signal(undefined);
public template = '';

public faq: Signal<ICardFAQEntry[]> = computed(() => {
const cardData = this.cardData();
if (!this.faqService.ready$() || !cardData) return [];

return this.faqService.getCardFAQ(cardData.product, cardData.name);
});

ngOnInit() {
const cardId = this.route.snapshot.paramMap.get('id');
this.cardData = this.cardsService.getCardById(cardId ?? '');
const cardData = this.cardsService.getCardById(cardId ?? '');

if (!this.cardData) {
if (!cardData) {
this.router.navigate(['/']);
return;
}

const template = this.metaService.getTemplateByProductId(
this.cardData.product
);
const template = this.metaService.getTemplateByProductId(cardData.product);
const compiledTemplate = Handlebars.compile(template);
this.template = compiledTemplate(this.cardData);
this.template = compiledTemplate(cardData);

this.cardData.set(cardData);
this.loadFAQ();
}

search(query: string) {
Expand All @@ -43,4 +61,6 @@ export class CardPage implements OnInit {
searchTag(tag: string) {
this.search(`tag:"${tag}"`);
}

loadFAQ() {}
}
73 changes: 73 additions & 0 deletions src/app/faq.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import { effect, inject, Injectable, Injector, signal } from '@angular/core';
import type { ICardFAQ, ICardFAQEntry } from '../../interfaces';
import { LocaleService } from './locale.service';
import { MetaService } from './meta.service';

@Injectable({
providedIn: 'root',
})
export class FAQService {
private metaService = inject(MetaService);
private localeService = inject(LocaleService);
private injector = inject(Injector);

private isReady = signal<boolean>(false);
public ready$ = this.isReady.asReadonly();

private allFAQs: Array<{
productId: string;
locale: string;
url: string;
}> = [];

private faqByProductIdAndLocale: Record<string, Record<string, ICardFAQ[]>> =
{};

private faqByProductLocaleCard: Record<
string,
Record<string, Record<string, ICardFAQEntry[]>>
> = {};

public async init() {
this.allFAQs = this.metaService.getAllFAQs();

effect(
() => {
const locale = this.localeService.currentLocale();
this.loadLocaleFAQs(locale);
},
{ injector: this.injector, allowSignalWrites: true }
);
}

private loadLocaleFAQs(locale: string) {
this.allFAQs.forEach(async (faq) => {
if (faq.locale !== locale) return;
if (this.faqByProductIdAndLocale[faq.productId]?.[faq.locale]) return;

this.faqByProductIdAndLocale[faq.productId] ??= {};

const faqData = await fetch(faq.url);
const realData = await faqData.json();

this.faqByProductIdAndLocale[faq.productId][faq.locale] = realData;

realData.forEach((cardFAQ: ICardFAQ) => {
this.faqByProductLocaleCard[faq.productId] ??= {};
this.faqByProductLocaleCard[faq.productId][faq.locale] ??= {};
this.faqByProductLocaleCard[faq.productId][faq.locale][cardFAQ.card] ??=
cardFAQ.faq;
});
});

if (!this.isReady()) this.isReady.set(true);
}

public getCardFAQ(productId: string, card: string): ICardFAQEntry[] {
return (
this.faqByProductLocaleCard[productId]?.[
this.localeService.currentLocale()
]?.[card] ?? []
);
}
}
14 changes: 14 additions & 0 deletions src/app/locale.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { Injectable, signal } from '@angular/core';

@Injectable({
providedIn: 'root',
})
export class LocaleService {
private locale = signal<string>('en-US');

public get currentLocale() {
return this.locale.asReadonly();
}

public async init() {}
}
Loading

0 comments on commit bb20c46

Please sign in to comment.