themesberg / themesberg/flowbite

Dropdown Component Not Initializing correctly on Navigation with Angular RouterLink

Open
#861 0 comments 3 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
HTML
Stars
9.4k
Forks
862
PR merge metrics
No merged PRs in 30d

Description

Describe the bug
When navigating between pages using Angular's routerLink, the dropdown components powered by Flowbite do not initialize correctly on the new page unless a full browser reload is performed. This issue affects navigation from a login page to an admin page, both of which utilize Flowbite's dropdown component.

To Reproduce

  1. Start the Angular application with Flowbite dropdown components on the login and admin pages.
  2. Navigate from the login page to the admin page using routerLink.
  3. Observe that the dropdown on the admin page does not function.
    Reload the browser on the admin page; the dropdown now works as expected.

Expected behavior
The dropdown components should initialize and function correctly after navigation between pages without requiring a browser reload.

Desktop (please complete the following information):

  • OS: MacOS
  • Browser: Google Chrome
  • Version: 123.0.6312.122

Additional context
Currently, I am initializing Flowbite on every NavigationEnd event by subscribing to router events in the ngOnInit lifecycle hook of the app.component.ts.

ngOnInit() {
  this.router.events.subscribe((event) => {
    if (event instanceof NavigationEnd) {
      initFlowbite();
    }
  });
}

Alternatively, a directive is used specifically on components where Flowbite is utilized to manage the initialization, ensuring that elements are properly recognized and initialized by Flowbite post-navigation. (source)

import { initFlowbite } from 'flowbite';
import { Subject, concatMap, delay, of } from 'rxjs';

const flowbiteQueue = new Subject<() => void>();

flowbiteQueue.pipe(concatMap((item) => of(item).pipe(delay(100)))).subscribe((x) => {
  x();
});

export function Flowbite() {
  return function (target: any) {
    const originalOnInit = target.prototype.ngOnInit;
    target.prototype.ngOnInit = function () {
      if (originalOnInit) {
        originalOnInit.apply(this);
      }
      initFlowbiteFix();
    };
  };
}

export function initFlowbiteFix() {
  flowbiteQueue.next(() => {
    const elements = Array.from(document.querySelectorAll('*'));
    const flowbiteElements: Element[] = [];
    const initializedElements = Array.from(document.querySelectorAll('[flowbite-initialized]'));

    for (const element of elements) {
      const attributes = Array.from(element.attributes);

      for (const attribute of attributes) {
        if (attribute.name.startsWith('data-') && !initializedElements.includes(element)) {
          flowbiteElements.push(element);
          break;
        }
      }
    }

    for (const element of flowbiteElements) {
      element.setAttribute('flowbite-initialized', '');
    }
    initFlowbite();

    for (const element of flowbiteElements) {
      const attributes: { name: string; value: string }[] = Array.from(element.attributes);
      const dataAttributes = attributes.filter((attribute) => attribute.name.startsWith('data-'));

      for (const attribute of dataAttributes) {
        element.setAttribute(attribute.name.replace('data-', 'fb-'), attribute.value);
        element.removeAttribute(attribute.name);
      }
    }
  });
}

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by reproducing the login-to-admin navigation in the Angular application using routerLink and inspect app.component.ts, the NavigationEnd subscription, and initFlowbite(). Review the linked directive approach and verify that dropdowns initialize after route changes without a full reload; done means the admin-page dropdown works after navigation.

Written by the indexing model from the issue text.

Assessment

Tech stack
angular, tailwindcss, typescript
Domain
frontend
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
25/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.