Activity 32: Angular Library Grid
In this activity, I created a grid layout to display a collection of items, such as books, in an Angular application. Using Angular’s ngFor for iteration and CSS Grid for layout management, I designed a responsive and visually appealing library grid. This task allowed me to practice creating dynamic grids, managing data efficiently, and implementing a clean, modern user interface. The result was a flexible grid that adapts to various screen sizes, providing a seamless experience across devices.
book.service.ts
import { Injectable } from '@angular/core';
export interface Book {
id: number;
title: string;
author: string;
genre: string;
image: string;
}
@Injectable({
providedIn: 'root',
})
export class BookService {
getBooks(): Book[] {
return [
{
id: 1,
title: 'The Great Gatsby',
author: 'F. Scott Fitzgerald',
genre: 'Fiction',
image: 'assets/images/gatsby.jpg',
},
{
id: 2,
title: 'To Kill a Mockingbird',
author: 'Harper Lee',
genre: 'Fiction',
image: 'assets/images/mockingbird.jpg',
},
{
id: 3,
title: '1984',
author: 'George Orwell',
genre: 'Dystopian',
image: 'assets/images/1984.jpg',
},
{
id: 4,
title: 'Pride and Prejudice',
author: 'Jane Austen',
genre: 'Romance',
image: 'assets/images/pride.jpg',
},
{
id: 5,
title: 'Moby Dick',
author: 'Herman Melville',
genre: 'Adventure',
image: 'assets/images/mobydick.jpg',
},
{
id: 6,
title: 'The Catcher in the Rye',
author: 'J.D. Salinger',
genre: 'Fiction',
image: 'assets/images/catcher.jpg',
},
{
id: 7,
title: 'The Hobbit',
author: 'J.R.R. Tolkien',
genre: 'Fantasy',
image: 'assets/images/hobbit.jpg',
},
{
id: 8,
title: 'Crime and Punishment',
author: 'Fyodor Dostoevsky',
genre: 'Philosophical Fiction',
image: 'assets/images/crime.jpg',
},
{
id: 9,
title: 'War and Peace',
author: 'Leo Tolstoy',
genre: 'Historical Fiction',
image: 'assets/images/warpeace.jpg',
},
{
id: 10,
title: 'Brave New World',
author: 'Aldous Huxley',
genre: 'Science Fiction',
image: 'assets/images/bravenewworld.jpg',
},
];
}
}
Book Interface: The
Book
interface specifies the structure for book objects, requiring properties likeid
,title
,author
,genre
, andimage
(URL for the book cover).BookService:
The
@Injectable
decorator marks the service as available for dependency injection throughout the application.The
getBooks()
method returns an array of books, each with anid
,title
,author
,genre
, andimage
.
This service can be used in components to fetch and display a list of books, along with their details. The id
is used to uniquely identify each book.
book.model.ts
export interface Book {
id: number;
title: string;
author: string;
genre: string;
}
id: A unique identifier for each book (of type
number
).title: The title of the book (of type
string
).author: The author of the book (of type
string
).genre: The genre/category of the book (of type
string
).
book.component.ts
import { Component, OnInit } from '@angular/core';
import { BookService, Book } from './book.service';
@Component({
selector: 'app-book',
templateUrl: './book.component.html',
styleUrls: ['./book.component.css'],
})
export class BookComponent implements OnInit {
books: Book[] = [];
constructor(private bookService: BookService) {}
ngOnInit(): void {
this.books = this.bookService.getBooks();
}
viewDetails(book: Book): void {
alert(`Details for: ${book.title}`);
}
}
Imports:
The
Component
andOnInit
decorators are imported from@angular/core
.The
BookService
andBook
are imported from./book.service
.
BookComponent Class:
@Component
: This decorator defines theBookComponent
and specifies its HTML template and CSS styles.books
: A property of typeBook[]
, which will hold the list of books fetched from the service.
Constructor: The
BookService
is injected into the component through the constructor, making it available for use in the class.ngOnInit
: This lifecycle hook runs when the component is initialized. It callsbookService.getBooks()
to fetch the list of books and assigns it to thebooks
property.viewDetails
: This method takes abook
as a parameter and shows an alert with the book’s title when the user views the book's details.
This component allows you to display and interact with a list of books fetched from the BookService
.
book.component.html
<div class="book-list">
<div class="book-list__item" *ngFor="let book of books">
<div class="book-card">
<img class="book-card__image" [src]="book.image" [alt]="book.title" />
<h3 class="book-card__title">{{ book.title }}</h3>
<p class="book-card__author">Author: {{ book.author }}</p>
<p class="book-card__genre">Genre: {{ book.genre }}</p>
<button class="book-card__button" (click)="viewDetails(book)">View Details</button>
</div>
</div>
</div>
<div class="book-list">
: This is the container element for the list of books.*ngFor="let book of books"
: This directive is used to iterate over thebooks
array, which contains the list of books from theBookService
. For eachbook
, a new<div class="book-list__item">
is created.Book Card Structure:
<div class="book-card">
: A wrapper for each book's information.<img class="book-card__image" [src]="book.image" [alt]="book.title" />
: Displays the book's image, with its source (src
) and alternative text (alt
) set dynamically using thebook
properties. Theimage
property in theBook
interface is expected to be used here.<h3 class="book-card__title">{{ book.title }}</h3>
: Displays the book's title.<p class="book-card__author">Author: {{
book.author
}}</p>
: Displays the book's author.<p class="book-card__genre">Genre: {{ book.genre }}</p>
: Displays the genre of the book.
<button class="book-card__button" (click)="viewDetails(book)">View Details</button>
: A button that triggers theviewDetails(book)
method when clicked. It displays an alert showing the book's details.
OUTPUT:
DESKTOP
TABLET
MOBILE