Using Encapsulation to Make an Awesome Angular JS Editor in Fiddle Salad

Sep 26 2013 Published by under Fiddle Salad,Programming

Angular JS is a popular MVC framework by Google, and I received a bug report that Fiddle Salad wouldn’t reload the preview as it does in all other cases. This problem was noticed before, but it wasn’t a priority since pressing the refresh button as required in all other web development methods solves the problem. However, this was because I was attempting to solve it at the wrong level by modifying a method. As I’ve learned, there are dependencies between the execute, reset, and initiation of the class involved.

Fiddle Salad’s CodeRunner class has just 5 public methods. They are

  • execute()
  • add_file()
  • remove_css()
  • reset()
  • debug()

as in the class diagram on the wiki at https://github.com/yuguang/fiddlesalad/wiki/2.-Classes. Therefore, any implementation of a CodeRunner just needs to support these 5 methods. The debug method could be refactored into a super class because it would generate the template for the new execute() method.

debug: ->
  ###
  Debug opens a new window with the code loaded in the page. External CSS and JS files are loaded through head tags.
  It assumes all external resources are stored in the view model.
  ###

  template =
    css: _.template '<link rel="stylesheet" type="text/css" href="<%= source %>" />'
    js: _.template '<script type="text/javascript" src="<%= source %>"></script>'
    html: _.template """
          <!DOCTYPE html>
          <html>
            <head>
              <title>Fiddle Salad Debug View</title>
              <script src="http://leaverou.github.com/prefixfree/prefixfree.min.js"></script>
              <style>
                <%= css %>
              </style>
            </head>
            <body>
              <%= body %>
              <%= headtags %>
              <script type="text/javascript">
                <%= javascript %>
              </script>
            </body>
          </html>
          """

  # initialize array of head tags
  headTags = new Array
  # for each external resource in view model
  _.each viewModel.resources(), (resource) =>
    # get the file type of the resource, call mapped template with resource, and append generated HTML to head tags
    headTags.push template[@filetype resource.source()](source: resource.source())
  headtags = headTags.join('')
  # get JavaScript and CSS code from the engine
  javascript = engine.get_code LANGUAGE_TYPE.COMPILED_PROGRAM
  body = engine.get_code LANGUAGE_TYPE.COMPILED_DOCUMENT
  css = engine.get_code LANGUAGE_TYPE.COMPILED_STYLE
  # call the template for the window with the head tags and code
  html = template.html {javascript, css, body, headtags}
  # open window with generated HTML
  window.open = 'data:text/html;charset=utf-8,' + encodeURIComponent(html)

If I just change the last line, the debug method turns into a reset method.

@window.location = 'data:text/html;charset=utf-8,' + encodeURIComponent(html)

The rest of the class still needs to be completed, but they are as obvious as appending to an array when adding JS/CSS files.

No responses yet