microsoft / fast

The adaptive interface system for modern web experiences.
https://www.fast.design
Other
9.28k stars 595 forks source link

observe not working with repeat #6850

Open vasicvuk opened 1 year ago

vasicvuk commented 1 year ago

πŸ› Bug Report

I created a simple navigation component containing _menuItems array:

export const template = html<Navbar>`
  <div id="nav-content" class="${x => { return x.open === true ? '' : 'closed' }}">
   ${repeat(x => x._menuItems,
      html<MenuItem, Navbar>`
        <router-link path="${x => x.route}" >
          <div class="${x => x.active ? 'selected' : ''}" >
            <div class="nav-button">
              <asee-icon name="${x => x.icon}"></asee-icon>
              <span>${x => x.title}</span>
            </div>
          </div>
        </router-link>`
  )}
  </div>`

Since I want to observe the properties of the objects in code when I am loading the menu items list I set it like this:

this._menuItems = menuItemsLoader.menuItems.map(x => reactive(x));

Then i have the method which changes the active property on the route change:

public activateRoute() {
    for (let menuItem of this._menuItems) {
      if (menuItem.route === this.activeRoute) {
        menuItem.active = true;
      } else {
        if (menuItem.active) {
          menuItem.active = false;
        }
      }
    }
}

But when the active property is changed, rerendering of the menu item does not happen.

πŸ€” Expected Behavior

I would expect for an active class to change on the menu item click

😯 Current Behavior

It does not trigger rendering of menuItems on active property change

🌍 Your Environment

chrisdholt commented 1 year ago

Thanks for this issue - while I see you have some example code above it would be great if you could put together a min-repro with stackblitz someone can dig into.

vasicvuk commented 1 year ago

Hi @chrisdholt I tried to replicate the issue but cannot do it on Stackblitz (it's working fine). It seems that the issue relies somewhere in the build part of my application. I am using the esbuild and i am bundling dependencies of my package as seperate JavaScripts. When I bundle everything in single JS everything works as expected, but when i have the fast-element imported over importmap it ignores reactive totally for some reason. I will try to investigate more to find where the issue comes from

chrisdholt commented 1 year ago

Hi @chrisdholt I tried to replicate the issue but cannot do it on Stackblitz (it's working fine). It seems that the issue relies somewhere in the build part of my application. I am using the esbuild and i am bundling dependencies of my package as seperate JavaScripts. When I bundle everything in single JS everything works as expected, but when i have the fast-element imported over importmap it ignores reactive totally for some reason. I will try to investigate more to find where the issue comes from

Thanks for this - I wonder if this could be related to the fact that state is only currently available from an export path and not from the fast-element root?

vasicvuk commented 1 year ago

@chrisdholt Not sure i am importing it using @microsoft/fast-element/state.js so i get seperate js in vendor folder for @microsoft/fast-element and @microsoft/fast-element/state.js and i am using import map like this to load them:

  <script type="importmap">
    {
      "imports": {
        "@microsoft/fast-element":"./vendor/_microsoft_fast-element.js",
        "@microsoft/fast-element/state.js":"./vendor/_microsoft_fast-element_state.js",
      }
    }
    </script>

JS loads fine but just reactive function does not react to changes for some reason. When i bundle everything in single JS it works normally. Still trying to figure out why

vasicvuk commented 1 year ago

Is there some special requirement for state.js in order for it to work? If I take a look at the reactive method in both, there is no difference but it only works when all is bundled together.

vasicvuk commented 1 year ago

Okay the issue is that apparently state.js has some references on fast-element itself internally so I guess that duplicate code in those two files is making a problem