How to access parent slider variables in an Angular component

I've developed a slider as the parent component with multiple child components.

See the demo here: https://stackblitz.com/edit/angular-ivy-gcgxgh?file=src/app/slide2/slide2.component.html

Slider in the parent component:

 <ng-container *ngFor="let ques of current_slide_lists; let i = index">
    <div class="mySlides animated fadeInRight">
      <app-slide1 *ngIf="ques == 'Multiple choice'"> </app-slide1>
      <app-slide2 *ngIf="ques == 'Single choice'"> </app-slide2>
    </div>
  </ng-container>

Child Component 1:

<p>
  Multiple choice Questions :
  <br />
  <input
    #optA
    class="form-check-input"
    type="checkbox"
    name="answer"
    id="answer_A"
    value="A"
  />
  Option 1
  <br />
  <input
    #optB
    class="form-check-input"
    type="checkbox"
    name="answer"
    id="answer_A"
    value="A"
  />
  Option 2
  <br />
  <input
    #optC
    class="form-check-input"
    type="checkbox"
    name="answer"
    id="answer_A"
    value="A"
  />
  Option 3
</p>

Child Component 2:

Single choice choice Option :
<br />
<input
  [(ngModel)]="select_option"
  type="radio"
  name="answer"
  id="answer_A"
  value="A"
/>Option 1
<br />
<input
  [(ngModel)]="select_option"
  type="radio"
  name="answer"
  id="answer_A"
  value="B"
/>Option 2
<br />
<input
  [(ngModel)]="select_option"
  type="radio"
  name="answer"
  id="answer_A"
  value="C"
/>Option 3

There will be various child components, with these two examples showcasing different functionalities. I am relatively new to Angular and trying to figure out how the parent component can access and manipulate data from the child components when needed. Specifically, if a user interacts with the child components (e.g., selecting checkboxes), I want the selected values to be accessible in the parent component. Any suggestions on passing and managing data between parent and child components are greatly welcomed. Thank you.

Answer №1

When it comes to communication between child and parent components in Angular, the preferred method is using an @Output. This allows you to emit custom events as needed.

In the child component:

@Output() dataChange= new EventEmitter<any>();

//you can emit events like this
this.dataChange.emit({data:'hello',value:'other',count:0});

In the parent component:

<app-slide1 (dataChange)="makeSomething($event)"...>
makeSomething(data:any)
{
   console.log(data)
}

You can also access child components from the parent using a template reference variable and ViewChildren.

<app-slide1 #slide *ngIf="ques == 'Multiple choice'"> </app-slide1>
<app-slide2 #slide *ngIf="ques == 'Single choice'"> </app-slide2>

ViewChildren('slide') slides:QueryList<any>

//for example, accessing a variable in the first slide
const value = slides.first.anyVariable;

However, when using ViewChildren, you cannot use *ngIf directives.

[style.display]="!condition?'none':null"

Another approach is passing complex objects as input.

In the parent component:

obj: any = {};

<app-slide1 [dataObject]="obj" ...> </app-slide1>
<app-slide2 [dataObject]="obj" ...> </app-slide2>
 

In the child component:

@Input() dataObject;
//somewhere within the component
this.dataObject.newProperty = "Hello";

//assigning a new object to dataObject is not allowed
//this.dataObject = ...

Update

A special case arises when the child components are forms.

First, you need to decide whether to use ReactiveForms with FormGroups or Template-driven forms with [(ngModel)].

In both cases, you pass either a FormGroup or an object as input.

Example using FormGroup:

//in parent
form = new FormGroup({
    property: new FormControl()
})
<app-slide1 [control]="form.get('property')"...></app-slide1>

//in child
control: FormControl
@Input('control') _control(value)
{
    this.control = value as FormControl;
}
<input [formControl]="control">

Example using ngModel:

//in parent
obj = {property: null};

<!--passing the entire object-->
<app-slide1 [data]="obj" field="property" ...></app-slide1>

//in child
@Input() data
@Input() field
<input [(ngModel)]="data[field]">

Both approaches involve passing an object, ensuring that changes made in the child reflect in the parent due to the shared object.

For ReactiveForms, a "setter" is used to handle casting of the control because TypeScript does not recognize FormControls directly.

When utilizing ngModel for managing a single property, two-way binding can be implemented for seamless updates.

In the child component:

@Input() data
@Output() dataChange = new EventEmitter<any>()
<input [ngModel]="data" (ngModelChange)="dataChange.emit($event)">

This enables a concise syntax in the parent component for easy assignment.

<app-slide1 [(data)]="obj.property" ...></app-slide1>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Ways to indicate a checkbox as selected within angular version 4

I'm a complete beginner in Angular 2 and I need to be able to check checkboxes when a button is clicked. I have multiple checkboxes generated in a loop like this: <tr *ngFor="let roleObj of roleNameList"> <td> <input ty ...

Error encountered when providing valid data types as arguments in a React/Typescript function

I am facing an issue when passing a string variable to a function. To address this, I have created an interface called MyMessageProps where I declare the message as a string. Subsequently, the function MyMessage utilizes this interface to return with the ...

Tips for incorporating a captcha image into your angular 8 application

I would like to implement a captcha element with an image of letters and an input field for the user, (I prefer not to use the "I am not a robot" version) similar to this example: Is this feature still available today? ...

Running multiple instances of Chrome to execute all scenarios sequentially within a single feature file in Protractor

I need to run all scenarios in multiple instances of a browser. I've set the maximum instance value in capabilities, but only one instance of Chrome opens and the tests run sequentially. How can I ensure that the tests run in multiple instances simult ...

Angular 10: A Guide to Utilizing RouterModule

I'm working on enhancing one of my components by adding a button that will navigate the page to a different component : <input type="button" value="Shops List" [routerLink]="['shops-list']" class="btn&qu ...

State management in React using hooks

Recently, I've been grappling with form validation while working on a signup form for my React app using Next.js. I've noticed that many sign up pages typically hide an "invalid" message until the user interacts with an input field. I attempted t ...

`What is the best way to transfer an observable to a child component?`

I am facing an issue with passing an Observable down to a child component. I have tried various solutions but none seem to work. parent.component.ts: export class ParentComponent { items$ = of([{name: "Item 1"}, {name: "Item 2"}]); } ...

The FaceBook SDK in React Native is providing an incorrect signature when trying to retrieve a token for iOS

After successfully implementing the latest Facebook SDK react-native-fbsdk-next for Android, I am facing issues with its functionality on IOS. I have managed to obtain a token, but when attempting to use it to fetch pages, I keep getting a "wrong signature ...

Discover the syntax for reading route parameters in Angular

Currently, I am integrating the Paypal API into my project. After confirming a purchase, Paypal redirects to a specified URL. I set the desired URL as "localhost:4200/shop/order". However, when Paypal returns the URL, it appends the token and payerid at th ...

Encountering a Nextjs hydration issue after switching languages

I am facing an issue with my Next.js project using version v12.2.4 and implementing internationalization with i18next. The project supports two languages: Italian and English. Strangely, when I switch to English language, the app throws errors, while every ...

Sending a parameter to a route guard

I've been developing an application that involves multiple roles, each requiring its own guard to restrict access to various parts of the app. While I know it's possible to create separate guard classes for each role, I'm hoping to find a mo ...

Angular6 : PrimeNg datatable: the nova-light theme failing to activate

I'm currently working on an Angular 6 app that is equipped with the latest version of PrimeNG (6.1.4) and I am using a simple datatable component. My goal is to apply the nova-light theme to my datatable, but unfortunately, it is not being applied cor ...

Troubleshooting a Type Parameter Error in React Native TypeScript

I am working on a project in React Native using TypeScript, and I encountered this issue: I am getting the error Argument of type 'GestureResponderEvent' is not assignable to parameter of type 'SetStateAction<string>'.ts(2345) wit ...

Error: The function list.forEach does not exist within service.buildList [as project]

Today, I've been grappling with a challenging issue. As someone new to Typescript and Angular, I'm attempting to make a call to my backend API. However, when trying to populate an array for display, I keep encountering an error that says rawRegis ...

Managing a MySQL database in NodeJS using Typescript through a DatabaseController

I'm currently working on a restAPI using nodejs, express, and mysql. My starting point is the app.js file. Within the app.js, I set up the UserController: const router: express.Router = express.Router(); new UserController(router); The UserControll ...

Utilizing useContext data in conjunction with properties

When using useContext in a component page, I am able to successfully retrieve data through useContext within a property. customColorContext.js import { createContext, useEffect, useState, useContext } from 'react'; // creating the context objec ...

Merging two arrays in Typescript and incrementing the quantity if they share the same identifier

I am currently working on my Angular 8 project and I am facing a challenge with merging two arrays into one while also increasing the quantity if they share the same value in the object. Despite several attempts, I have not been able to achieve the desired ...

Is it possible for prettier to substitute var with let?

One of the tools I utilize to automatically format my Typescript code is prettier. My goal is to find out if there is a way to have prettier replace all instances of 'var' with 'let' during the formatting process. Below is the script I ...

What is the most reliable way to create an array ensuring that all potential values come from a specific dictionary?

I am seeking a method to define the testArray so that only keys from the example dictionary can be inserted into the array. enum example { key1 = 'A', key2 = 2, key3 = '3', }; const testArray: ?? = [example.key1, example.ke ...

Do changes in Input fields reflect in the parent component?

I was under the impression that I could share data with child components using @Input() directive and communicate data back to the parent component with @Output() along with the appropriate emit. However, I recently discovered that modifications made to th ...