2

I'm adding a tab and a tab pane to a Bootstrap tab box in a custom element. Sometimes they appear, often they don't. Sometimes the pane appears but not the tab. The result is different on each reload. If it doesn't appear, causing a reflow by doing something like resizing the browser window or opening the Dartium inspector makes it suddenly appear.

I'm using Polymer 0.9.5. Here's the HTML:

<polymer-element name="confab-output-box">
  <link rel="stylesheet" type="text/css" href="../resources/css/bootstrap.min.css">
  <template bind>
    <div id="output_container">
      <ul id="tabs" class="nav nav-tabs">
      </ul>
      <div id="tab-content" class="tab-content">
      </div>
    </div>
  </template>
  <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
  <script src="../resources/js/bootstrap.min.js"></script>
  <script type="application/dart" src="confab_output_box.dart"></script>
</polymer-element>

and here's the Dart class:

library confab_output_box;

import 'dart:html';
import 'package:polymer/polymer.dart';
import '../confab_view/confab_view.dart';

@CustomTag('confab-output-box')
class ConfabOutputBox extends PolymerElement {
    ConfabView activeView;

    ConfabOutputBox.created() : super.created();

    void attachView(ConfabView view) {
        $['tabs'].children.add(
            new LIElement()
                ..id = '${view.id}-tab'
                ..children.add(
                    new AnchorElement()
                        ..href = '#${view.id}'
                        ..onClick.listen(tabClicked)
                        ..text = view.tabTitle
                )
        );

        $['tab-content'].children.add(view..classes.add('tab-pane'));
    }

    void detachView(ConfabView view) {
        shadowRoot.getElementById('${view.id}-tab').remove();
        shadowRoot.getElementById(view.id).remove();
    }

    void activateView(ConfabView view) {
        if (activeView != null) {
            shadowRoot.getElementById('${activeView.id}-tab').classes.remove('active');
            shadowRoot.getElementById(activeView.id).classes.remove('active');
        }
        shadowRoot.getElementById('${view.id}-tab').classes.add('active');
        shadowRoot.getElementById(view.id).classes.add('active');
        activeView = view;
    }

    void tabClicked(Event e) {
        e.preventDefault();
        ConfabView view = shadowRoot.querySelector((e.toElement as AnchorElement).href);
        activateView(view);
    }
}
Isvara
  • 3,403
  • 1
  • 28
  • 42

1 Answers1

0

Problems with dynamically added elements are mostly caused by not using initPolymer in main.

see: Polymer querySelector working on DartVM but not in Chrome after compile

<template bind> <!-- bind is redundant here -->

The problem could be a timing issue. Maybe the BootStrap scripts are executed before the new tags are inserted.

Can you try to move the code that adds the new elements to enteredView

void enteredView() {
  // create and add your elements here
  super.enteredView();
}
Community
  • 1
  • 1
Günter Zöchbauer
  • 623,577
  • 216
  • 2,003
  • 1,567
  • I have `` in the `head` of my `index.html`. Is that not sufficient? (I never did understand why it's an `export`, but that's what the docs say.) – Isvara Apr 06 '14 at 14:27
  • This has changed with Polymer 0.10.0-pre.7 anyway. So you don't have a `main` method? – Günter Zöchbauer Apr 06 '14 at 14:29
  • Sorry I think I misunderstood the question. You are not dynamically adding Polymer elements but simple DOM elements. I added a hint to my answer about some mistake I found in your code. The problem could be a timing issue. Maybe the BootStrap scripts are executed before the new tags are inserted. – Günter Zöchbauer Apr 06 '14 at 14:32
  • The elements are added way after `enteredView` has fired. It's in response to a websocket message triggered by a button click. – Isvara Apr 06 '14 at 15:02
  • But no, I don't have a main function, and I'm using polymer 0.9.5. – Isvara Apr 06 '14 at 15:03
  • Have you examined the DOM using Chrome developer tools to verify whether the elements are actually added to the page? Do the added elements need to be processed by Bootstap scripts to be visible? Is the behavior more consistent when you remove the Bootstrap/JQuery scripts? – Günter Zöchbauer Apr 06 '14 at 15:08
  • Yes, the elements correctly appear in the DOM. Initially, the scripts were not in the element, but the effect was the same. They don't actually need any Bootstrap JS, AFAIK. – Isvara Apr 06 '14 at 15:32
  • I think this is a known bug in Dartium. Do you have this problem also when built to JavaScript? – Günter Zöchbauer Apr 06 '14 at 15:36
  • I couldn't find the bug. Maybe it is already fixes. I didn't encounter this for a while therefor I didn't think of it. What Dart version are you using? – Günter Zöchbauer Apr 06 '14 at 15:41
  • Than I'm quite sure this is this bug. I'm using 1.3 for a while. I expect a stable 1.3 release very soon if you don't want to use an unstable version. – Günter Zöchbauer Apr 06 '14 at 20:36