bespoke arguments for the super function in a subclass of Angular

I am attempting to incorporate the ol sidebar from umbe1987/Turbo87 into an Angular project.

As I extend a class, I find myself needing to manipulate constructor parameters in the derived class constructor before passing them to the superclass constructor.

My challenge lies in retrieving a DOM div node from the current Angular component (derivedclass) and passing it as the 'element' argument in the super call.

  • If I stick with the existing

    var element = document.getElementById(options.element)
    , the DOM is not rendered by the time the constructor runs.

  • Trying

    var element = this.mySidebarDiv.nativeElement(options.element)
    results in the error message:
    this'super' must be called before accessing 'this' in the constructor of a derived class.ts(17009)

  1. How can I bypass the warning when using the viewChild property (this.mySidebarDiv)? This limitation leads me to pass a null element parameter.

  2. Although I know the sidebar won't be rendered until a specific lifecycle hook (ngAfterViewInit), I still need to fetch the DOM element beforehand, within its constructor, to pass it to the superclass constructor. How should I approach this?

Thank you

@Injectable()
export class ProjectInfoSidebarComponent extends Control {

  @ViewChild('sidebar') mySidebarDiv: ElementRef;

  _container;
  _tabitems;
  _panes;
  _closeButtons;
  classList;
  _sidebar;

  constructor(@Inject(String)opt_options) {

    var defaults = {
        element: null,
        position: 'left'
    }, i, child;

    var options = Object.assign({}, defaults, opt_options);

    //var element = document.getElementById(options.element);
    var element = this.mySidebarDiv.nativeElement(options.element)

    super({
        element: element,
        target: options.target
    });
    // super((() => {
    //   return {
    //     element: this.mySidebarDiv.nativeElement.querySelector(options.element),
    //     target: options.target
    //   }
    // })());

    // Attach .sidebar-left/right class
    element.classList.add('sidebar-' + options.position);
    ...
    ...
    ...

Answer №1

If you're looking to merge ol5-sidebar with a custom Angular component, consider taking a different approach. Instead of combining the two into a single class, it's recommended to utilize inversion of control by creating a wrapper Angular component. This wrapper component can generate a <div> element and then pass it to an instance of OLSidebar once it's been rendered in the DOM.

To implement this, first add the ol5-sidebar.js file directly from the specified Github repository to your project. Then, create a separate Angular component named

project-info-sidebar.component.ts
with the following structure:

import { Component, ViewChild, ElementRef, AfterViewInit, Inject, InjectionToken } from "@angular/core";
import OLSidebar from "./ol5-sidebar.js";

const SIDEBAR_OPTS = new InjectionToken<SidebarOptions>('SIDEBAR_OPTS');

interface SidebarOptions {
  /* default: `left` */
  position?: string;
  target: any; // not sure what the correct type is here
}

@Component({
  selector: "sidebar",
  template: "<div #sidebar></div>",
})
export class ProjectInfoSidebarComponent implements AfterViewInit {
  @ViewChild("sidebar") mySidebarDiv: ElementRef<HTMLDivElement>;

  sidebar: OLSidebar | null = null;

  constructor(@Inject(SIDEBAR_OPTS) private options: SidebarOptions) {}

  ngAfterViewInit() {
    // obtain a reference to the recently rendered `<div>`
    const element = this.mySidebarDiv.nativeElement;

    // create an OLSidebar instance to take over control
    this.sidebar = new OLSidebar({
      element,
      target: this.options.target,
    });
  }
}

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

Accessing different pages in Angular 2 based on user type

If I have four pages and two user types, how can we implement access control in Angular 2 so that one user can access all four pages while the other is restricted to only two pages? ...

Tips on accessing the JS file api within an angular component.ts file

I've got a function in my JS file located at src/server/js/controller.js, and I'm trying to use that API within a component's ts file. I attempted the following code to achieve this but it doesn't seem to be working properly. controlle ...

Do we need to import Vue in every component when using Nuxt with TypeScript?

I recently integrated TypeScript into Nuxt using the guidelines provided in the documentation: However, I have a specific question regarding component setup. Should I always include import vue from "vue" and export default Vue.extend ({}); in al ...

Issue encountered: Cannot locate module: Error message - Unable to find 'stream' in 'C:devjszip-test ode_modulesjsziplib' folder

I am encountering an issue in my angular 7 application while using jszip v3.2.1. During the project build process (e.g., running npm start), I receive the following error message: ERROR in ./node_modules/jszip/lib/readable-stream-browser.js Module not fo ...

Retrieve specific data points within a dataset

Within the dataset provided, I am attempting to retrieve specific values. { "id": "0f0126f5-aed3-49bb-97dd-7ad2d00b67a4", "retirementData": "{\"benefits\":[{\"availableBenefitOptions\":{\"anniversaryDate\":\"202 ...

Utilize Array.push to add 2 new rows to a table using Angular 4

I have two arrays that are almost identical, except for two items which are the fakeDates: this.prodotti.push({ idAgreement: this.idAgreement,landingStatus: this.landingStatus, landingType: this.landingType, startDate: this.startDate, expirationDate: thi ...

I'm looking for a way to implement a jQuery-style initialization pattern using TypeScript - how can I

My library utilizes a jQuery-like initialization pattern, along with some specific requirements for the types it should accept and return: function JQueryInitializer ( selector /*: string | INSTANCE_OF_JQUERY*/ ) { if ( selector.__jquery ) return select ...

Informing ng2-bootstrap's Timepicker of the invalidation

I have integrated ng2-bootstrap's timepicker component into my project. To enhance user experience, I created a custom validation function that is triggered by the ngModelChange() event. However, the timepicker component also comes with its own built- ...

The functionality of Angular 4 routing is limited to directing to just one subsequent route at

I am encountering a peculiar problem with Angular 2 routing. I can successfully navigate to the next page, but for some reason, I am unable to navigate from that page. My application consists of 4 components: Home, Search Result, Profile, and Admin. Upon ...

Issue with reading the current length of an array object in a while loop in Angular 6

After successfully splitting an array into parts, I decided to add some filters to only include the items in the list that have an action status of (4). However, I encountered a problem where the while loop couldn't read the length of the array. This ...

The error message "Directive does not contain a property called 'element'.ts" is displayed

I'm encountering an issue where the property 'element' is not recognized on 'directive'. I am currently working on implementing functionalities for directives. import { Directive, ElementRef, HostListener } from '@angular/cor ...

Contrasting the provision of ComponentStore directly versus utilizing provideComponentStore in Angular standalone components

As I delve into the realm of standalone Angular components and tinker with the NgRx Component Store, I find myself grappling with a dilemma on how to properly inject the component store into my component. Here's the current approach I've been usi ...

Creating a global variable in Angular 4 and Ionic 3 is simple when following these steps

Currently, I am developing an application in ionic3 and within it, there are numerous services and functions that utilize specific variables such as: let apiUrlPublic = 'http://localhost:8080/'; let apiUrl = 'http://localhost:9999/api/&apo ...

Removing items from an array within an object stored in local storage using an Ionic application

One of my challenges involves an Ionic App that stores data in the localStorage. I need to remove specific items from an array within an object in the localStorage when a user clicks on them. Even though I have the code below, it doesn't seem to be f ...

What are the steps for creating and deploying a project that utilizes asp.net core on the server-side and Angular on the client-side

My latest project combines asp.net core 5 and angular 15 technologies for the backend and frontend, respectively. The asp.net core MVC portion of the project is contained in a dedicated folder named serverApi, while the angular part is generated in another ...

ControlValueAccessor failing to populate with data from external service

After realizing the previous question was slightly off track, I am focusing on creating a custom component that can be bound to a FormControl within a FormGroup. I have successfully made it work for user input using CVA, but facing issues when preloading ...

Selecting a radio button by clicking on its corresponding label within an Angular Material dialog

I recently implemented a custom rating bar in Angular, which worked perfectly fine in a basic component. However, when I tried to move it to a MatDialog component, I encountered some issues. In the initial setup, my input was set to display: none so that t ...

Creating a universal wrapper function to serve as a logging tool?

Currently, I am working on a generic JS function that can wrap any other function. The purpose of this wrapper is to execute the wrapped function, log the input and output events, and then return the output for "transparent" logging. However, as I attempt ...

Is it possible to create a function that only accepts a union type if it includes a specific subtype within it?

Is there a way to define the function processArray so that it can handle arrays of type string[], without explicitly mentioning individual types like type1 or type2? For instance, could we indicate this by using arr: type1 | type2? The objective here is t ...

Angular input range slider that automatically rounds decimal values from the data bindings

I've implemented a range slider within an Angular form to capture and display recorded values. <input [formControlName]="object.id" [id]="object.id" type="range" [(ngModel)]="object.answer" [step]="objec ...