diff --git a/package.json b/package.json index 2245985..5a46bdc 100644 --- a/package.json +++ b/package.json @@ -19,6 +19,7 @@ "@angular/router": "17.1.0", "@ngrx/component-store": "^17.0.1", "@nx/angular": "17.2.8", + "ng-zorro-antd": "^17.1.0", "rxjs": "~7.8.0", "tslib": "^2.3.0", "zone.js": "0.14.2" @@ -34,6 +35,7 @@ "@angular/compiler-cli": "17.1.0", "@angular/language-service": "17.1.0", "@nx/devkit": "17.2.8", + "@nx/eslint": "17.2.8", "@nx/eslint-plugin": "17.2.8", "@nx/jest": "17.2.8", "@nx/js": "17.2.8", @@ -56,8 +58,6 @@ "prettier": "^2.6.2", "ts-jest": "^29.1.0", "ts-node": "10.9.1", - "typescript": "5.2.2", - "@nx/eslint": "17.2.8" + "typescript": "5.2.2" } } - diff --git a/project.json b/project.json index 7c99217..d431d60 100644 --- a/project.json +++ b/project.json @@ -15,8 +15,16 @@ "main": "./src/main.ts", "polyfills": ["zone.js"], "tsConfig": "./tsconfig.app.json", - "assets": ["./src/favicon.ico", "./src/assets"], - "styles": ["./src/styles.scss"], + "assets": [ + "./src/favicon.ico", + "./src/assets", + { + "glob": "**/*", + "input": "./node_modules/@ant-design/icons-angular/src/inline-svg/", + "output": "/assets/" + } + ], + "styles": ["src/theme.less", "./src/styles.scss"], "scripts": [] }, "configurations": { @@ -25,7 +33,7 @@ { "type": "initial", "maximumWarning": "500kb", - "maximumError": "1mb" + "maximumError": "2mb" }, { "type": "anyComponentStyle", diff --git a/src/app/app.component.html b/src/app/app.component.html index 0680b43..8d7dca5 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -1 +1,16 @@ - + + + + + + +
+ +
+
+ Series Demo ©2024 Arcadio Quintero +
diff --git a/src/app/app.component.scss b/src/app/app.component.scss index e69de29..32303b5 100644 --- a/src/app/app.component.scss +++ b/src/app/app.component.scss @@ -0,0 +1,40 @@ +.layout { + min-height: 100vh; +} + +.logo { + width: 120px; + height: 31px; + background: rgba(255, 255, 255, 0.2); + margin: 16px 24px 16px 0; + float: left; +} + +nz-header { + position: fixed; + width: 100%; + z-index: 1; +} + +[nz-menu] { + line-height: 64px; +} + +nz-content { + padding: 0 50px; + margin-top: 64px; +} + +nz-breadcrumb { + margin: 16px 0; +} + +.inner-content { + background: #fff; + padding: 24px; + min-height: 380px; +} + +nz-footer { + text-align: center; +} diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 3d31863..a3e0274 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -1,9 +1,26 @@ import { Component } from '@angular/core'; import { RouterModule } from '@angular/router'; +import { + NzContentComponent, + NzFooterComponent, + NzHeaderComponent, + NzLayoutComponent, +} from 'ng-zorro-antd/layout'; +import { NzBreadCrumbComponent } from 'ng-zorro-antd/breadcrumb'; +import { NzMenuDirective, NzMenuItemComponent } from 'ng-zorro-antd/menu'; @Component({ standalone: true, - imports: [RouterModule], + imports: [ + RouterModule, + NzContentComponent, + NzBreadCrumbComponent, + NzFooterComponent, + NzHeaderComponent, + NzLayoutComponent, + NzMenuDirective, + NzMenuItemComponent, + ], selector: 'app-root', templateUrl: './app.component.html', styleUrls: ['./app.component.scss'], diff --git a/src/app/app.config.ts b/src/app/app.config.ts index 2cfae42..192b0a2 100644 --- a/src/app/app.config.ts +++ b/src/app/app.config.ts @@ -5,10 +5,21 @@ import { } from '@angular/router'; import { appRoutes } from './app.routes'; import { HttpClientModule } from '@angular/common/http'; +import { en_US, provideNzI18n } from 'ng-zorro-antd/i18n'; +import { registerLocaleData } from '@angular/common'; +import en from '@angular/common/locales/en'; +import { FormsModule } from '@angular/forms'; +import { provideAnimations } from '@angular/platform-browser/animations'; + +registerLocaleData(en); export const appConfig: ApplicationConfig = { providers: [ importProvidersFrom(HttpClientModule), provideRouter(appRoutes, withEnabledBlockingInitialNavigation()), + provideNzI18n(en_US), + importProvidersFrom(FormsModule), + importProvidersFrom(HttpClientModule), + provideAnimations(), ], }; diff --git a/src/app/series/series.component.html b/src/app/series/series.component.html index f026e1e..a302c91 100644 --- a/src/app/series/series.component.html +++ b/src/app/series/series.component.html @@ -1,12 +1,28 @@

Series

-@if (vm().isLoading){ +@if (vm().isLoading) {

Loading...

-} @else{ - + + + } diff --git a/src/app/series/series.component.scss b/src/app/series/series.component.scss index e69de29..a1ea207 100644 --- a/src/app/series/series.component.scss +++ b/src/app/series/series.component.scss @@ -0,0 +1,14 @@ +.series-card__wrapper { + display: flex; + flex-wrap: wrap; + width: 100%; + justify-content: space-around; + gap: 2rem; +} + +:host ::ng-deep { + nz-card { + width: 210px; + flex: 0 0 auto; + } +} diff --git a/src/app/series/series.component.ts b/src/app/series/series.component.ts index fd9a9ca..7c4adb3 100644 --- a/src/app/series/series.component.ts +++ b/src/app/series/series.component.ts @@ -6,14 +6,33 @@ import { Signal, } from '@angular/core'; import { SeriesStore } from './store/series.store'; -import { AsyncPipe, NgForOf, NgIf } from '@angular/common'; +import { AsyncPipe, NgForOf, NgIf, NgOptimizedImage } from '@angular/common'; import { SeriesService } from './services/series.service'; import { ViewModelComponent } from './shared/series.models'; +import { NzCardComponent, NzCardMetaComponent } from 'ng-zorro-antd/card'; +import { NzColDirective, NzRowDirective } from 'ng-zorro-antd/grid'; +import { NzPaginationComponent } from 'ng-zorro-antd/pagination'; +import { NzSpaceItemDirective } from 'ng-zorro-antd/space'; +import { NzImageDirective } from 'ng-zorro-antd/image'; +import { NzEmptyComponent } from 'ng-zorro-antd/empty'; @Component({ selector: 'app-series', standalone: true, - imports: [AsyncPipe, NgForOf, NgIf], + imports: [ + AsyncPipe, + NgForOf, + NgIf, + NzCardComponent, + NzCardMetaComponent, + NgOptimizedImage, + NzRowDirective, + NzColDirective, + NzPaginationComponent, + NzSpaceItemDirective, + NzImageDirective, + NzEmptyComponent, + ], templateUrl: './series.component.html', styleUrls: ['./series.component.scss'], providers: [SeriesStore, SeriesService], diff --git a/src/app/series/services/series.service.ts b/src/app/series/services/series.service.ts index c67000b..55e1229 100644 --- a/src/app/series/services/series.service.ts +++ b/src/app/series/services/series.service.ts @@ -1,19 +1,17 @@ import { inject, Injectable } from '@angular/core'; import { HttpClient } from '@angular/common/http'; -import { delay, Observable, tap } from 'rxjs'; +import { Observable, tap } from 'rxjs'; import { Serie } from '../shared/series.models'; const TVMAZE_ENDPOINT = 'https://api.tvmaze.com/'; -const DELAY_MS = 1000; @Injectable() export class SeriesService { private httpClient = inject(HttpClient); getSeries(): Observable { - return this.httpClient.get(`${TVMAZE_ENDPOINT}shows`).pipe( - delay(DELAY_MS), - tap((s) => console.log(s)) - ); + return this.httpClient + .get(`${TVMAZE_ENDPOINT}shows`) + .pipe(tap((s) => console.log(s))); } } diff --git a/src/app/series/shared/series.models.ts b/src/app/series/shared/series.models.ts index de84780..c617061 100644 --- a/src/app/series/shared/series.models.ts +++ b/src/app/series/shared/series.models.ts @@ -1,10 +1,11 @@ export type ComponentState = 'idle' | 'loading' | 'loaded' | 'error'; +// We will add more here export interface Serie { id: number; name: string; - description: string; - thumbnail: string; + summary: string; + image: { medium: string; original: string }; } // Store state related diff --git a/src/styles.scss b/src/styles.scss index 90d4ee0..48da018 100644 --- a/src/styles.scss +++ b/src/styles.scss @@ -1 +1 @@ -/* You can add global styles to this file, and also import other style files */ +//@import "~ng-zorro-antd/ng-zorro-antd.css"; diff --git a/src/theme.less b/src/theme.less new file mode 100644 index 0000000..9101118 --- /dev/null +++ b/src/theme.less @@ -0,0 +1,25 @@ +// For more information: https://ng.ant.design/docs/customize-theme/en +// -------- import official less file ----------- +@import '/node_modules/ng-zorro-antd/ng-zorro-antd.less'; + +@imdb-yellow: #f5c518; // Color amarillo de IMDB +@imdb-black: #000000; // Negro +@imdb-grey: #f4f4f4; // Gris claro para fondos + +// -------- override less variables ----------- +// View all variables: https://github.com/NG-ZORRO/ng-zorro-antd/blob/master/components/style/themes/default.less + +// Sobrescribir variables de NG-ZORRO +@primary-color: @imdb-yellow; // Color primario +@layout-header-background: @imdb-black; // Color de fondo del header +@layout-body-background: @imdb-grey; // Color de fondo del contenido +@text-color: darken(@imdb-grey, 70%); // Color del texto +@heading-color: @imdb-black; // Color de los encabezados +@border-radius-base: 4px; // Radio de borde +@link-color: @imdb-yellow; // Color de los enlaces + +// Otros colores de estado +@success-color: #52c41a; // Verde para éxitos +@warning-color: #faad14; // Amarillo para advertencias +@error-color: #f5222d; // Rojo para errores +@info-color: @primary-color; // Color para información, usa el color primario diff --git a/yarn.lock b/yarn.lock index 845d816..0bb260c 100644 --- a/yarn.lock +++ b/yarn.lock @@ -210,6 +210,15 @@ dependencies: tslib "^2.3.0" +"@angular/cdk@^17.0.0": + version "17.1.1" + resolved "https://registry.npmjs.org/@angular/cdk/-/cdk-17.1.1.tgz#b6c06481cdde574ac89a7f1303dc8314fd1a88ad" + integrity sha512-Q5qC6VUyT7N/hj8eETdh0bkmBmsXm0JZikhXdBvcDUl8yPbhMPKQCkx4UJzBrZJg/+78XyI9FI/q8w/yQAJZJA== + dependencies: + tslib "^2.3.0" + optionalDependencies: + parse5 "^7.1.2" + "@angular/cli@~17.0.0": version "17.0.6" resolved "https://registry.npmjs.org/@angular/cli/-/cli-17.0.6.tgz#9a44efd0cfee28871e9bee77a2bf9154bf76fb88" @@ -302,6 +311,21 @@ dependencies: tslib "^2.3.0" +"@ant-design/colors@^7.0.0": + version "7.0.2" + resolved "https://registry.npmjs.org/@ant-design/colors/-/colors-7.0.2.tgz#c5c753a467ce8d86ba7ca4736d2c01f599bb5492" + integrity sha512-7KJkhTiPiLHSu+LmMJnehfJ6242OCxSlR3xHVBecYxnMW8MS/878NXct1GqYARyL59fyeFdKRxXTfvR9SnDgJg== + dependencies: + "@ctrl/tinycolor" "^3.6.1" + +"@ant-design/icons-angular@^17.0.0": + version "17.0.0" + resolved "https://registry.npmjs.org/@ant-design/icons-angular/-/icons-angular-17.0.0.tgz#5e072f4be7fa0bcef1498be735de8b54ada23620" + integrity sha512-MNEh3UbkSl6gkdb5MQRNHEuWI1DnU1dME9zSymnWCipEXN7MB0mcYHSfyYTqKL1j45ftp6l1UnsLvhokRYyhXA== + dependencies: + "@ant-design/colors" "^7.0.0" + tslib "^2.0.0" + "@assemblyscript/loader@^0.10.1": version "0.10.1" resolved "https://registry.yarnpkg.com/@assemblyscript/loader/-/loader-0.10.1.tgz#70e45678f06c72fa2e350e8553ec4a4d72b92e06" @@ -1906,6 +1930,13 @@ dependencies: regenerator-runtime "^0.14.0" +"@babel/runtime@^7.21.0": + version "7.23.9" + resolved "https://registry.npmjs.org/@babel/runtime/-/runtime-7.23.9.tgz#47791a15e4603bb5f905bc0753801cf21d6345f7" + integrity sha512-0CX6F+BI2s9dkUqr08KFrAIZgNFj75rdBU/DjCyYLIaV/quFjkk6T+EJ2LkZHyZTbEV4L5p97mNkUsHl2wLFAw== + dependencies: + regenerator-runtime "^0.14.0" + "@babel/runtime@^7.22.6", "@babel/runtime@^7.7.2", "@babel/runtime@^7.8.4": version "7.23.2" resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.23.2.tgz#062b0ac103261d68a966c4c7baf2ae3e62ec3885" @@ -1984,6 +2015,11 @@ dependencies: "@jridgewell/trace-mapping" "0.3.9" +"@ctrl/tinycolor@^3.6.1": + version "3.6.1" + resolved "https://registry.npmjs.org/@ctrl/tinycolor/-/tinycolor-3.6.1.tgz#b6c75a56a1947cc916ea058772d666a2c8932f31" + integrity sha512-SITSV6aIXsuVNV3f3O0f2n/cgyEDWoSqtZMYiAmcsYHydcKrOz3gUxB/iXd/Qf08+IZX4KpgNbvUdMBmWz+kcA== + "@discoveryjs/json-ext@0.5.7": version "0.5.7" resolved "https://registry.yarnpkg.com/@discoveryjs/json-ext/-/json-ext-0.5.7.tgz#1d572bfbbe14b7704e0ba0f39b74815b84870d70" @@ -4942,6 +4978,13 @@ data-urls@^3.0.2: whatwg-mimetype "^3.0.0" whatwg-url "^11.0.0" +date-fns@^2.16.1: + version "2.30.0" + resolved "https://registry.npmjs.org/date-fns/-/date-fns-2.30.0.tgz#f367e644839ff57894ec6ac480de40cae4b0f4d0" + integrity sha512-fnULvOpxnC5/Vg3NCiWelDsLiUc9bRwAPs/+LfTLNvetFCtCTN+yQz15C/fs4AwX1R9K5GLtLfn8QW+dWisaAw== + dependencies: + "@babel/runtime" "^7.21.0" + debug@2.6.9: version "2.6.9" resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f" @@ -7657,6 +7700,16 @@ neo-async@^2.6.2: resolved "https://registry.yarnpkg.com/neo-async/-/neo-async-2.6.2.tgz#b4aafb93e3aeb2d8174ca53cf163ab7d7308305f" integrity sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw== +ng-zorro-antd@^17.1.0: + version "17.1.0" + resolved "https://registry.npmjs.org/ng-zorro-antd/-/ng-zorro-antd-17.1.0.tgz#0af10f4994489b6be3d9dc90f463a714f4ccd6f0" + integrity sha512-1lpknv5QXTeXk9k01GLbmxuXLyfRCGF91hVl3NF6Fedef7OJIstOmLy2VxvXoAQxrRyuYsDkEke2GJRC33mxhw== + dependencies: + "@angular/cdk" "^17.0.0" + "@ant-design/icons-angular" "^17.0.0" + date-fns "^2.16.1" + tslib "^2.3.0" + nice-napi@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/nice-napi/-/nice-napi-1.0.2.tgz#dc0ab5a1eac20ce548802fc5686eaa6bc654927b" @@ -8107,7 +8160,7 @@ parse5@4.0.0: resolved "https://registry.yarnpkg.com/parse5/-/parse5-4.0.0.tgz#6d78656e3da8d78b4ec0b906f7c08ef1dfe3f608" integrity sha512-VrZ7eOd3T1Fk4XWNXMgiGBK/z0MG48BWG2uQNU4I72fkQuKUTZpl+u9k+CxEG0twMVzSmXEEz12z5Fnw1jIQFA== -parse5@^7.0.0, parse5@^7.1.1: +parse5@^7.0.0, parse5@^7.1.1, parse5@^7.1.2: version "7.1.2" resolved "https://registry.yarnpkg.com/parse5/-/parse5-7.1.2.tgz#0736bebbfd77793823240a23b7fc5e010b7f8e32" integrity sha512-Czj1WaSVpaoj0wbhMzLmWD69anp2WH7FXMB9n1Sy8/ZFF9jolSQVMu1Ij5WIyGmcBmhk7EOndpO4mIpihVqAXw==