JSFiddle - React, Tailwind, and code Playground

by David Kyle

HTML

<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.1.1/css/bootstrap.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/4.1.1/js/bootstrap.min.js"></script>
<div class="container-fluid bg-dark">
  <section aria-role="commands">
    <div class="row h-25">
      <div class="bg-secondary h-25 col-12 text-center">
        <h1>Commands</h1>
      </div>
      <div class="bg h-25 m-2">
        <button name="addContainer" type="button" id="addContainer" class="btn btn-primary" data-toggle="modal" data-target="#newContainerModal">Add Container</button>
        <button name="removeContainer" type="button" id="removeContainer" class="btn btn-primary" data-toggle="modal" data-target="#removeContainerModal">Remove Container</button>
      </div>
    </div>
  </section>
  <section id="dynamic-containers" aria-role="content">
    <div class="row h-25 bg-primary">
      <h1 class="text-center col-12">Containers</h1>
    </div>
    <div class="row auto container">
      <div class="col h-100 auto col-12">
        <div class="row" id="container-target">

        </div>
      </div>
    </div>
  </section>
  <section id="example" aria-role="content">
    <div class="row">
      <div class="bg-secondary text-center col-12 auto">
        <h1>Example</h1>
      </div>
    </div>
    <div class="row auto">
      <div class="col-12 auto bg-light">
        Try adding the following to the content of a new container:<br />
        <quote>
          &lt;button type="button" class="custom-button btn btn-primary" class="btn" name="custom-button"&gt;Click&lt;/button&gt;
        </quote>
      </div>
    </div>
  </section>
</div>

<div id="newContainerModal" class="modal" tabindex="-1" role="dialog">
  <div class="modal-dialog" role="document">
    <div class="modal-content">
      <div class="modal-header">
        <h5 class="modal-title">Add New Dynamic Container</h5>
        <button type="button" class="close"...

CSS

#newContainerModal {
  display: none;
}

#container-template {
  display: none;
}

.container-instance {
  border-radius: 3px;
}

JavaScript

// Utility "namespace"
var Page = (function() {
  var self = this;
  var initialized = false;
  var containers = (function() {
    var local = this;
    var registeredContainers = Array();

    var updateUIRegistration = function() {
      var $containerList = $("#removalList");
      $containerList.html("");
      $containerList.append("<option value=\"-1\" selected>--Select Container--</option>");
      if (registeredContainers != null && registeredContainers != undefined && Array.isArray(registeredContainers) && registeredContainers.length > 0) {
        for (var i = 0; i < registeredContainers.length; i++) {
          $containerList.append("<option value=\"" + i + "\">" + registeredContainers[i].WindowName + "</option>");
        }
        $("#removeContainerModal").find("#confirmRemove").attr("disabled", false);
      } else {
        $("#removeContainerModal").find("#confirmRemove").attr("disabled", true);
      }
    }

    local.AddContainerRegistration = function(registration) {
      if (registration != null && registration != undefined) {
        if (registration.id != null && registration.id != undefined) {
          if (registeredContainers != null && registeredContainers != undefined && Array.isArray(registeredContainers)) {
            var alreadyRegistered = false;
            for (var i = 0; i < registeredContainers.length; i++) {
              if (registeredContainers[i].WindowName == registration.id) {
                alreadyRegistered = true;
                alert("The container has already been registered.");
                break;
              }
            }

            if (!alreadyRegistered) {
              var newContainer = new DynamicContainer(registration);
              if (newContainer === false) {} else {
                registeredContainers.push(newContainer);
                updateUIRegistration();
              }
            }
          }
        }
      }
    };

    local.Close = function(e) {
      var removeIndex = -1;
   ...