[ Index ]

PHP Cross Reference of Unnamed Project

title

Body

[close]

/lib/yuilib/3.17.2/frame/ -> frame.js (source)

   1  /*
   2  YUI 3.17.2 (build 9c3c78e)
   3  Copyright 2014 Yahoo! Inc. All rights reserved.
   4  Licensed under the BSD License.
   5  http://yuilibrary.com/license/
   6  */
   7  
   8  YUI.add('frame', function (Y, NAME) {
   9  
  10      /*jshint maxlen: 500 */
  11      /**
  12       * Creates a wrapper around an iframe. It loads the content either from a local
  13       * file or from script and creates a local YUI instance bound to that new window and document.
  14       * @class Frame
  15       * @for Frame
  16       * @extends Base
  17       * @constructor
  18       * @module editor
  19       * @submodule frame
  20       */
  21  
  22      var Lang = Y.Lang,
  23  
  24          EVENT_CONTENT_READY = 'contentready',
  25  
  26          HOST = 'host',
  27  
  28      Frame = function() {
  29          Frame.superclass.constructor.apply(this, arguments);
  30      };
  31  
  32  
  33      Y.extend(Frame, Y.Plugin.Base, {
  34          /**
  35          * @private
  36          * @property _ready
  37          * @description Internal reference set when the content is ready.
  38          * @type Boolean
  39          */
  40          _ready: null,
  41          /**
  42          * @private
  43          * @property _rendered
  44          * @description Internal reference set when render is called.
  45          * @type Boolean
  46          */
  47          _rendered: null,
  48          /**
  49          * @private
  50          * @property _iframe
  51          * @description Internal Node reference to the iFrame or the window
  52          * @type Node
  53          */
  54          _iframe: null,
  55          /**
  56          * @private
  57          * @property _instance
  58          * @description Internal reference to the YUI instance bound to the iFrame or window
  59          * @type YUI
  60          */
  61          _instance: null,
  62          /**
  63          * @private
  64          * @method _create
  65          * @description Create the iframe or Window and get references to the Document & Window
  66          * @return {Object} Hash table containing references to the new Document & Window
  67          */
  68          _create: function(cb) {
  69              var res, html = '', timer,
  70                  //if the src attr is different than the default, don't create the document
  71                  create = (this.get('src') === Frame.ATTRS.src.value),
  72                  extra_css = ((this.get('extracss')) ? '<style id="extra_css">' + this.get('extracss') + '</style>' : '');
  73  
  74              this._iframe = Y.one(Y.config.doc.createElement('iframe'));
  75              this._iframe.setAttrs(Frame.IFRAME_ATTRS);
  76  
  77              this._iframe.setStyle('visibility', 'hidden');
  78              this._iframe.set('src', this.get('src'));
  79              this.get('container').append(this._iframe);
  80              this._iframe.set('height', '99%');
  81  
  82              if (create) {
  83                  html = Y.Lang.sub(Frame.PAGE_HTML, {
  84                      DIR: this.get('dir'),
  85                      LANG: this.get('lang'),
  86                      TITLE: this.get('title'),
  87                      META: Frame.META,
  88                      LINKED_CSS: this.get('linkedcss'),
  89                      CONTENT: this.get('content'),
  90                      BASE_HREF: this.get('basehref'),
  91                      DEFAULT_CSS: Frame.DEFAULT_CSS,
  92                      EXTRA_CSS: extra_css
  93                  });
  94                  if (Y.config.doc.compatMode !== 'BackCompat') {
  95  
  96                      //html = Frame.DOC_TYPE + "\n" + html;
  97                      html = Frame.getDocType() + "\n" + html;
  98                  } else {
  99                  }
 100  
 101              }
 102  
 103              res = this._resolveWinDoc();
 104  
 105              if (html) {
 106                  res.doc.open();
 107                  res.doc.write(html);
 108                  res.doc.close();
 109              }
 110  
 111              if (!res.doc.documentElement) {
 112                  timer = Y.later(1, this, function() {
 113                      if (res.doc && res.doc.documentElement) {
 114                          cb(res);
 115                          timer.cancel();
 116                      }
 117                  }, null, true);
 118              } else {
 119                  cb(res);
 120              }
 121  
 122          },
 123          /**
 124          * @private
 125          * @method _resolveWinDoc
 126          * @description Resolves the document and window from an iframe or window instance
 127          * @param {Object} c The YUI Config to add the window and document to
 128          * @return {Object} Object hash of window and document references, if a YUI config was passed, it is returned.
 129          */
 130          _resolveWinDoc: function(c) {
 131              var config = (c) ? c : {};
 132              config.win = Y.Node.getDOMNode(this._iframe.get('contentWindow'));
 133              config.doc = Y.Node.getDOMNode(this._iframe.get('contentWindow.document'));
 134              if (!config.doc) {
 135                  config.doc = Y.config.doc;
 136              }
 137              if (!config.win) {
 138                  config.win = Y.config.win;
 139              }
 140              return config;
 141          },
 142          /**
 143          * @private
 144          * @method _onDomEvent
 145          * @description Generic handler for all DOM events fired by the iframe or window. This handler
 146          * takes the current EventFacade and augments it to fire on the Frame host. It adds two new properties
 147          * to the EventFacade called frameX and frameY which adds the scroll and xy position of the iframe
 148          * to the original pageX and pageY of the event so external nodes can be positioned over the frame.
 149          * @param {EventFacade} e
 150          */
 151          _onDomEvent: function(e) {
 152              var xy, node;
 153  
 154              if (!Y.Node.getDOMNode(this._iframe)) {
 155                  //The iframe is null for some reason, bail on sending events.
 156                  return;
 157              }
 158  
 159              e.frameX = e.frameY = 0;
 160  
 161              if (e.pageX > 0 || e.pageY > 0) {
 162                  if (e.type.substring(0, 3) !== 'key') {
 163                      node = this._instance.one('win');
 164                      xy = this._iframe.getXY();
 165                      e.frameX = xy[0] + e.pageX - node.get('scrollLeft');
 166                      e.frameY = xy[1] + e.pageY - node.get('scrollTop');
 167                  }
 168              }
 169  
 170              e.frameTarget = e.target;
 171              e.frameCurrentTarget = e.currentTarget;
 172              e.frameEvent = e;
 173  
 174              this.fire('dom:' + e.type, e);
 175          },
 176          initializer: function() {
 177              var host = this.get(HOST);
 178  
 179              if (host) {
 180                  host.frame = this;
 181              }
 182  
 183              this.publish('ready', {
 184                  emitFacade: true,
 185                  defaultFn: this._defReadyFn
 186              });
 187          },
 188          destructor: function() {
 189              var inst = this.getInstance();
 190  
 191              inst.one('doc').detachAll();
 192              inst = null;
 193              this._iframe.remove();
 194          },
 195          /**
 196          * @private
 197          * @method _DOMPaste
 198          * @description Simple pass thru handler for the paste event so we can do content cleanup
 199          * @param {EventFacade} e
 200          */
 201          _DOMPaste: function(e) {
 202              var inst = this.getInstance(),
 203                  data = '', win = inst.config.win;
 204  
 205              if (e._event.originalTarget) {
 206                  data = e._event.originalTarget;
 207              }
 208              if (e._event.clipboardData) {
 209                  data = e._event.clipboardData.getData('Text');
 210              }
 211  
 212              if (win.clipboardData) {
 213                  data = win.clipboardData.getData('Text');
 214                  if (data === '') { // Could be empty, or failed
 215                      // Verify failure
 216                      if (!win.clipboardData.setData('Text', data)) {
 217                          data = null;
 218                      }
 219                  }
 220              }
 221  
 222  
 223              e.frameTarget = e.target;
 224              e.frameCurrentTarget = e.currentTarget;
 225              e.frameEvent = e;
 226  
 227              if (data) {
 228                  e.clipboardData = {
 229                      data: data,
 230                      getData: function() {
 231                          return data;
 232                      }
 233                  };
 234              } else {
 235                  e.clipboardData = null;
 236              }
 237  
 238              this.fire('dom:paste', e);
 239          },
 240          /**
 241          * @private
 242          * @method _defReadyFn
 243          * @description Binds DOM events, sets the iframe to visible and fires the ready event
 244          */
 245          _defReadyFn: function() {
 246              var inst = this.getInstance();
 247  
 248              Y.each(Frame.DOM_EVENTS, function(v, k) {
 249                  var fn = Y.bind(this._onDomEvent, this),
 250                      kfn = ((Y.UA.ie && Frame.THROTTLE_TIME > 0) ? Y.throttle(fn, Frame.THROTTLE_TIME) : fn);
 251  
 252                  if (!inst.Node.DOM_EVENTS[k]) {
 253                      inst.Node.DOM_EVENTS[k] = 1;
 254                  }
 255                  if (v === 1) {
 256                      if (k !== 'focus' && k !== 'blur' && k !== 'paste') {
 257                          if (k.substring(0, 3) === 'key') {
 258                              //Throttle key events in IE
 259                              inst.on(k, kfn, inst.config.doc);
 260                          } else {
 261                              inst.on(k, fn, inst.config.doc);
 262                          }
 263                      }
 264                  }
 265              }, this);
 266  
 267              inst.Node.DOM_EVENTS.paste = 1;
 268  
 269              inst.on('paste', Y.bind(this._DOMPaste, this), inst.one('body'));
 270  
 271              //Adding focus/blur to the window object
 272              inst.on('focus', Y.bind(this._onDomEvent, this), inst.config.win);
 273              inst.on('blur', Y.bind(this._onDomEvent, this), inst.config.win);
 274  
 275              inst.__use = inst.use;
 276              inst.use = Y.bind(this.use, this);
 277              this._iframe.setStyles({
 278                  visibility: 'inherit'
 279              });
 280              inst.one('body').setStyle('display', 'block');
 281          },
 282          /**
 283          * It appears that having a BR tag anywhere in the source "below" a table with a percentage width (in IE 7 & 8)
 284          * if there is any TEXTINPUT's outside the iframe, the cursor will rapidly flickr and the CPU would occasionally
 285          * spike. This method finds all <BR>'s below the sourceIndex of the first table. Does some checks to see if they
 286          * can be modified and replaces then with a <WBR> so the layout will remain in tact, but the flickering will
 287          * no longer happen.
 288          * @method _fixIECursors
 289          * @private
 290          */
 291          _fixIECursors: function() {
 292              var inst = this.getInstance(),
 293                  tables = inst.all('table'),
 294                  brs = inst.all('br'), si;
 295  
 296              if (tables.size() && brs.size()) {
 297                  //First Table
 298                  si = tables.item(0).get('sourceIndex');
 299                  brs.each(function(n) {
 300                      var p = n.get('parentNode'),
 301                          c = p.get('children'), b = p.all('>br');
 302  
 303                      if (p.test('div')) {
 304                          if (c.size() > 2) {
 305                              n.replace(inst.Node.create('<wbr>'));
 306                          } else {
 307                              if (n.get('sourceIndex') > si) {
 308                                  if (b.size()) {
 309                                      n.replace(inst.Node.create('<wbr>'));
 310                                  }
 311                              } else {
 312                                  if (b.size() > 1) {
 313                                      n.replace(inst.Node.create('<wbr>'));
 314                                  }
 315                              }
 316                          }
 317                      }
 318  
 319                  });
 320              }
 321          },
 322          /**
 323          * @private
 324          * @method _onContentReady
 325          * @description Called once the content is available in the frame/window and calls the final use call
 326          * on the internal instance so that the modules are loaded properly.
 327          */
 328          _onContentReady: function(e) {
 329              if (!this._ready) {
 330                  this._ready = true;
 331                  var inst = this.getInstance(),
 332                      args = Y.clone(this.get('use'));
 333  
 334                  this.fire('contentready');
 335  
 336                  if (e) {
 337                      inst.config.doc = Y.Node.getDOMNode(e.target);
 338                  }
 339                  //TODO Circle around and deal with CSS loading...
 340                  args.push(Y.bind(function() {
 341                      if (inst.EditorSelection) {
 342                          inst.EditorSelection.DEFAULT_BLOCK_TAG = this.get('defaultblock');
 343                      }
 344                      //Moved to here so that the iframe is ready before allowing editing..
 345                      if (this.get('designMode')) {
 346                          if(Y.UA.ie) {
 347                              inst.config.doc.body.contentEditable = 'true';
 348                              this._ieSetBodyHeight();
 349                              inst.on('keyup', Y.bind(this._ieSetBodyHeight, this), inst.config.doc);
 350                          } else {
 351                              inst.config.doc.designMode = 'on';
 352                          }
 353                      }
 354                      this.fire('ready');
 355                  }, this));
 356                  inst.use.apply(inst, args);
 357  
 358                  inst.one('doc').get('documentElement').addClass('yui-js-enabled');
 359              }
 360          },
 361          _ieHeightCounter: null,
 362          /**
 363          * Internal method to set the height of the body to the height of the document in IE.
 364          * With contenteditable being set, the document becomes unresponsive to clicks, this
 365          * method expands the body to be the height of the document so that doesn't happen.
 366          * @private
 367          * @method _ieSetBodyHeight
 368          */
 369          _ieSetBodyHeight: function(e) {
 370              if (!this._ieHeightCounter) {
 371                  this._ieHeightCounter = 0;
 372              }
 373              this._ieHeightCounter++;
 374              var run = false, inst, h, bh;
 375              if (!e) {
 376                  run = true;
 377              }
 378              if (e) {
 379                  switch (e.keyCode) {
 380                      case 8:
 381                      case 13:
 382                          run = true;
 383                          break;
 384                  }
 385                  if (e.ctrlKey || e.shiftKey) {
 386                      run = true;
 387                  }
 388              }
 389              if (run) {
 390                  try {
 391                      inst = this.getInstance();
 392                      h = this._iframe.get('offsetHeight');
 393                      bh = inst.config.doc.body.scrollHeight;
 394                      if (h > bh) {
 395                          h = (h - 15) + 'px';
 396                          inst.config.doc.body.style.height = h;
 397                      } else {
 398                          inst.config.doc.body.style.height = 'auto';
 399                      }
 400                  } catch (e) {
 401                      if (this._ieHeightCounter < 100) {
 402                          Y.later(200, this, this._ieSetBodyHeight);
 403                      } else {
 404                      }
 405                  }
 406              }
 407          },
 408          /**
 409          * @private
 410          * @method _resolveBaseHref
 411          * @description Resolves the basehref of the page the frame is created on. Only applies to dynamic content.
 412          * @param {String} href The new value to use, if empty it will be resolved from the current url.
 413          * @return {String}
 414          */
 415          _resolveBaseHref: function(href) {
 416              if (!href || href === '') {
 417                  href = Y.config.doc.location.href;
 418                  if (href.indexOf('?') !== -1) { //Remove the query string
 419                      href = href.substring(0, href.indexOf('?'));
 420                  }
 421                  href = href.substring(0, href.lastIndexOf('/')) + '/';
 422              }
 423              return href;
 424          },
 425          /**
 426          * @private
 427          * @method _getHTML
 428          * @description Get the content from the iframe
 429          * @param {String} html The raw HTML from the body of the iframe.
 430          * @return {String}
 431          */
 432          _getHTML: function(html) {
 433              if (this._ready) {
 434                  var inst = this.getInstance();
 435                  html = inst.one('body').get('innerHTML');
 436              }
 437              return html;
 438          },
 439          /**
 440          * @private
 441          * @method _setHTML
 442          * @description Set the content of the iframe
 443          * @param {String} html The raw HTML to set the body of the iframe to.
 444          * @return {String}
 445          */
 446          _setHTML: function(html) {
 447              if (this._ready) {
 448                  var inst = this.getInstance();
 449                  inst.one('body').set('innerHTML', html);
 450              } else {
 451                  this.once(EVENT_CONTENT_READY, Y.bind(this._setHTML, this, html));
 452              }
 453  
 454              return html;
 455          },
 456          /**
 457          * @private
 458          * @method _getLinkedCSS
 459          * @description Get the linked CSS on the instance.
 460          */
 461          _getLinkedCSS: function(urls) {
 462              if (!Y.Lang.isArray(urls)) {
 463                  urls = [urls];
 464              }
 465              var str = '';
 466              if (!this._ready) {
 467                  Y.each(urls, function(v) {
 468                      if (v) {
 469                          str += '<link rel="stylesheet" href="' + v + '" type="text/css">';
 470                      }
 471                  });
 472              } else {
 473                  str = urls;
 474              }
 475              return str;
 476          },
 477          /**
 478          * @private
 479          * @method _setLinkedCSS
 480          * @description Sets the linked CSS on the instance..
 481          */
 482          _setLinkedCSS: function(css) {
 483              if (this._ready) {
 484                  var inst = this.getInstance();
 485                  inst.Get.css(css);
 486              }
 487              return css;
 488          },
 489          /**
 490          * @private
 491          * @method _setExtraCSS
 492          * @description Set's the extra CSS on the instance..
 493          */
 494          _setExtraCSS: function(css) {
 495              if (this._ready) {
 496                  var inst = this.getInstance(),
 497                      node = inst.one('#extra_css');
 498  
 499                  if (node) {
 500                      node.remove();
 501                  }
 502  
 503                  inst.one('head').append('<style id="extra_css">' + css + '</style>');
 504              } else {
 505                  //This needs to be wrapped in a contentready callback for the !_ready state
 506                  this.once(EVENT_CONTENT_READY, Y.bind(this._setExtraCSS, this, css));
 507              }
 508  
 509              return css;
 510          },
 511          /**
 512          * @private
 513          * @method _instanceLoaded
 514          * @description Called from the first YUI instance that sets up the internal instance.
 515          * This loads the content into the window/frame and attaches the contentready event.
 516          * @param {YUI} inst The internal YUI instance bound to the frame/window
 517          */
 518          _instanceLoaded: function(inst) {
 519              this._instance = inst;
 520              this._onContentReady();
 521  
 522              var doc = this._instance.config.doc;
 523  
 524              if (this.get('designMode')) {
 525                  if (!Y.UA.ie) {
 526                      try {
 527                          //Force other browsers into non CSS styling
 528                          doc.execCommand('styleWithCSS', false, false);
 529                          doc.execCommand('insertbronreturn', false, false);
 530                      } catch (err) {}
 531                  }
 532              }
 533          },
 534          //BEGIN PUBLIC METHODS
 535          /**
 536          * @method use
 537          * @description This is a scoped version of the normal YUI.use method & is bound to this frame/window.
 538          * At setup, the inst.use method is mapped to this method.
 539          */
 540          use: function() {
 541              var inst = this.getInstance(),
 542                  args = Y.Array(arguments),
 543                  cb = false;
 544  
 545              if (Y.Lang.isFunction(args[args.length - 1])) {
 546                  cb = args.pop();
 547              }
 548              if (cb) {
 549                  args.push(function() {
 550                      cb.apply(inst, arguments);
 551  
 552                  });
 553              }
 554  
 555              return inst.__use.apply(inst, args);
 556          },
 557          /**
 558          * @method delegate
 559          * @description A delegate method passed to the instance's delegate method
 560          * @param {String} type The type of event to listen for
 561          * @param {Function} fn The method to attach
 562          * @param {String} cont The container to act as a delegate, if no "sel" passed, the body is assumed as the container.
 563          * @param {String} sel The selector to match in the event (optional)
 564          * @return {EventHandle} The Event handle returned from Y.delegate
 565          */
 566          delegate: function(type, fn, cont, sel) {
 567              var inst = this.getInstance();
 568              if (!inst) {
 569                  return false;
 570              }
 571              if (!sel) {
 572                  sel = cont;
 573                  cont = 'body';
 574              }
 575              return inst.delegate(type, fn, cont, sel);
 576          },
 577          /**
 578          * @method getInstance
 579          * @description Get a reference to the internal YUI instance.
 580          * @return {YUI} The internal YUI instance
 581          */
 582          getInstance: function() {
 583              return this._instance;
 584          },
 585          /**
 586          * @method render
 587          * @description Render the iframe into the container config option or open the window.
 588          * @param {String/HTMLElement/Node} node The node to render to
 589          * @return {Frame}
 590          * @chainable
 591          */
 592          render: function(node) {
 593              if (this._rendered) {
 594                  return this;
 595              }
 596              this._rendered = true;
 597              if (node) {
 598                  this.set('container', node);
 599              }
 600  
 601              this._create(Y.bind(function(res) {
 602  
 603                  var inst, timer,
 604                      cb = Y.bind(function(i) {
 605                          this._instanceLoaded(i);
 606                      }, this),
 607                      args = Y.clone(this.get('use')),
 608                      config = {
 609                          debug: false,
 610                          win: res.win,
 611                          doc: res.doc
 612                      },
 613                      fn = Y.bind(function() {
 614                          config = this._resolveWinDoc(config);
 615                          inst = YUI(config);
 616                          inst.host = this.get(HOST); //Cross reference to Editor
 617  
 618                          try {
 619                              inst.use('node-base', cb);
 620                              if (timer) {
 621                                  clearInterval(timer);
 622                              }
 623                          } catch (e) {
 624                              timer = setInterval(function() {
 625                                  fn();
 626                              }, 350);
 627                          }
 628                      }, this);
 629  
 630                  args.push(fn);
 631  
 632                  Y.use.apply(Y, args);
 633  
 634              }, this));
 635  
 636              return this;
 637          },
 638          /**
 639          * @private
 640          * @method _handleFocus
 641          * @description Does some tricks on focus to set the proper cursor position.
 642          */
 643          _handleFocus: function() {
 644              var inst = this.getInstance(),
 645                  sel = new inst.EditorSelection(),
 646                  n, c, b, par;
 647  
 648              if (sel.anchorNode) {
 649                  n = sel.anchorNode;
 650  
 651                  if (n.test('p') && n.get('innerHTML') === '') {
 652                      n = n.get('parentNode');
 653                  }
 654                  c = n.get('childNodes');
 655  
 656                  if (c.size()) {
 657                      if (c.item(0).test('br')) {
 658                          sel.selectNode(n, true, false);
 659                      } else if (c.item(0).test('p')) {
 660                          n = c.item(0).one('br.yui-cursor');
 661                          if (n) {
 662                              n = n.get('parentNode');
 663                          }
 664                          if (!n) {
 665                              n = c.item(0).get('firstChild');
 666                          }
 667                          if (!n) {
 668                              n = c.item(0);
 669                          }
 670                          if (n) {
 671                              sel.selectNode(n, true, false);
 672                          }
 673                      } else {
 674                          b = inst.one('br.yui-cursor');
 675                          if (b) {
 676                              par = b.get('parentNode');
 677                              if (par) {
 678                                  sel.selectNode(par, true, false);
 679                              }
 680                          }
 681                      }
 682                  }
 683              }
 684          },
 685          /**
 686          * Validates linkedcss property
 687          *
 688          * @method _validateLinkedCSS
 689          * @private
 690          */
 691          _validateLinkedCSS: function(value) {
 692              return Lang.isString(value) || Lang.isArray(value);
 693          },
 694          /**
 695          * @method focus
 696          * @description Set the focus to the iframe
 697          * @param {Function} fn Callback function to execute after focus happens
 698          * @return {Frame}
 699          * @chainable
 700          */
 701          focus: function(fn) {
 702              if (Y.UA.ie && Y.UA.ie < 9) {
 703                  try {
 704                      Y.one('win').focus();
 705                      if (this.getInstance()) {
 706                          if (this.getInstance().one('win')) {
 707                              this.getInstance().one('win').focus();
 708                          }
 709                      }
 710                  } catch (ierr) {
 711                  }
 712                  if (fn === true) {
 713                      this._handleFocus();
 714                  }
 715                  if (Y.Lang.isFunction(fn)) {
 716                      fn();
 717                  }
 718              } else {
 719                  try {
 720                      Y.one('win').focus();
 721                      Y.later(100, this, function() {
 722                          if (this.getInstance()) {
 723                              if (this.getInstance().one('win')) {
 724                                  this.getInstance().one('win').focus();
 725                              }
 726                          }
 727                          if (fn === true) {
 728                              this._handleFocus();
 729                          }
 730                          if (Y.Lang.isFunction(fn)) {
 731                              fn();
 732                          }
 733                      });
 734                  } catch (ferr) {
 735                  }
 736              }
 737              return this;
 738          },
 739          /**
 740          * @method show
 741          * @description Show the iframe instance
 742          * @return {Frame}
 743          * @chainable
 744          */
 745          show: function() {
 746              this._iframe.setStyles({
 747                  position: 'static',
 748                  left: ''
 749              });
 750              if (Y.UA.gecko) {
 751                  try {
 752                      if (this.getInstance()) {
 753                          this.getInstance().config.doc.designMode = 'on';
 754                      }
 755                  } catch (e) { }
 756                  this.focus();
 757              }
 758              return this;
 759          },
 760          /**
 761          * @method hide
 762          * @description Hide the iframe instance
 763          * @return {Frame}
 764          * @chainable
 765          */
 766          hide: function() {
 767              this._iframe.setStyles({
 768                  position: 'absolute',
 769                  left: '-999999px'
 770              });
 771              return this;
 772          }
 773      }, {
 774          /**
 775          * @static
 776          * @property THROTTLE_TIME
 777          * @description The throttle time for key events in IE
 778          * @type Number
 779          * @default 100
 780          */
 781          THROTTLE_TIME: 100,
 782          /**
 783          * @static
 784          * @property DOM_EVENTS
 785          * @description The DomEvents that the frame automatically attaches and bubbles
 786          * @type Object
 787          */
 788          DOM_EVENTS: {
 789              dblclick: 1,
 790              click: 1,
 791              paste: 1,
 792              mouseup: 1,
 793              mousedown: 1,
 794              keyup: 1,
 795              keydown: 1,
 796              keypress: 1,
 797              activate: 1,
 798              deactivate: 1,
 799              beforedeactivate: 1,
 800              focusin: 1,
 801              focusout: 1
 802          },
 803  
 804          /**
 805          * @static
 806          * @property DEFAULT_CSS
 807          * @description The default css used when creating the document.
 808          * @type String
 809          */
 810          DEFAULT_CSS: 'body { background-color: #fff; font: 13px/1.22 arial,helvetica,clean,sans-serif;*font-size:small;*font:x-small; } a, a:visited, a:hover { color: blue !important; text-decoration: underline !important; cursor: text !important; } img { cursor: pointer !important; border: none; }',
 811          /**
 812          * The template string used to create the iframe, deprecated to use DOM instead of innerHTML
 813          * @static
 814          * @property HTML
 815          * @type String
 816          * @deprecated
 817          */
 818          //HTML: '<iframe border="0" frameBorder="0" marginWidth="0" marginHeight="0" leftMargin="0" topMargin="0" allowTransparency="true" width="100%" height="99%"></iframe>',
 819          /**
 820          * Attributes to auto add to the dynamic iframe under the hood
 821          * @static
 822          * @property IFRAME_ATTRS
 823          * @type Object
 824          */
 825          IFRAME_ATTRS: {
 826              border: '0',
 827              frameBorder: '0',
 828              marginWidth: '0',
 829              marginHeight: '0',
 830              leftMargin: '0',
 831              topMargin: '0',
 832              allowTransparency: 'true',
 833              width: "100%",
 834              height: "99%"
 835          },
 836          /**
 837          * @static
 838          * @property PAGE_HTML
 839          * @description The template used to create the page when created dynamically.
 840          * @type String
 841          */
 842          PAGE_HTML: '<html dir="{DIR}" lang="{LANG}"><head><title>{TITLE}</title>{META}<base href="{BASE_HREF}"/>{LINKED_CSS}<style id="editor_css">{DEFAULT_CSS}</style>{EXTRA_CSS}</head><body>{CONTENT}</body></html>',
 843  
 844          /**
 845          * @static
 846          * @method getDocType
 847          * @description Parses document.doctype and generates a DocType to match the parent page, if supported.
 848          * For IE8, it grabs document.all[0].nodeValue and uses that. For IE < 8, it falls back to Frame.DOC_TYPE.
 849          * @return {String} The normalized DocType to apply to the iframe
 850          */
 851          getDocType: function() {
 852              var dt = Y.config.doc.doctype,
 853                  str = Frame.DOC_TYPE;
 854  
 855              if (dt) {
 856                  str = '<!DOCTYPE ' + dt.name + ((dt.publicId) ? ' ' + dt.publicId : '') + ((dt.systemId) ? ' ' + dt.systemId : '') + '>';
 857              } else {
 858                  if (Y.config.doc.all) {
 859                      dt = Y.config.doc.all[0];
 860                      if (dt.nodeType) {
 861                          if (dt.nodeType === 8) {
 862                              if (dt.nodeValue) {
 863                                  if (dt.nodeValue.toLowerCase().indexOf('doctype') !== -1) {
 864                                      str = '<!' + dt.nodeValue + '>';
 865                                  }
 866                              }
 867                          }
 868                      }
 869                  }
 870              }
 871              return str;
 872          },
 873          /**
 874          * @static
 875          * @property DOC_TYPE
 876          * @description The DOCTYPE to prepend to the new document when created. Should match the one on the page being served.
 877          * @type String
 878          */
 879          DOC_TYPE: '<!DOCTYPE HTML PUBLIC "-/'+'/W3C/'+'/DTD HTML 4.01/'+'/EN" "http:/'+'/www.w3.org/TR/html4/strict.dtd">',
 880          /**
 881          * @static
 882          * @property META
 883          * @description The meta-tag for Content-Type to add to the dynamic document
 884          * @type String
 885          */
 886          META: '<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/><meta http-equiv="X-UA-Compatible" content="IE=7">',
 887          //META: '<meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>',
 888          /**
 889          * @static
 890          * @property NAME
 891          * @description The name of the class (frame)
 892          * @type String
 893          */
 894          NAME: 'frame',
 895          /**
 896          * The namespace on which Frame plugin will reside.
 897          *
 898          * @property NS
 899          * @type String
 900          * @default 'frame'
 901          * @static
 902          */
 903          NS: 'frame',
 904          ATTRS: {
 905              /**
 906              * @attribute title
 907              * @description The title to give the blank page.
 908              * @type String
 909              */
 910              title: {
 911                  value: 'Blank Page'
 912              },
 913              /**
 914              * @attribute dir
 915              * @description The default text direction for this new frame. Default: ltr
 916              * @type String
 917              */
 918              dir: {
 919                  value: 'ltr'
 920              },
 921              /**
 922              * @attribute lang
 923              * @description The default language. Default: en-US
 924              * @type String
 925              */
 926              lang: {
 927                  value: 'en-US'
 928              },
 929              /**
 930              * @attribute src
 931              * @description The src of the iframe/window. Defaults to javascript:;
 932              * @type String
 933              */
 934              src: {
 935                  //Hackish, IE needs the false in the Javascript URL
 936                  value: 'javascript' + ((Y.UA.ie) ? ':false' : ':') + ';'
 937              },
 938              /**
 939              * @attribute designMode
 940              * @description Should designMode be turned on after creation.
 941              * @writeonce
 942              * @type Boolean
 943              */
 944              designMode: {
 945                  writeOnce: true,
 946                  value: false
 947              },
 948              /**
 949              * @attribute content
 950              * @description The string to inject into the body of the new frame/window.
 951              * @type String
 952              */
 953              content: {
 954                  validator: Lang.isString,
 955                  value: '<br>',
 956                  setter: '_setHTML',
 957                  getter: '_getHTML'
 958              },
 959              /**
 960              * @attribute basehref
 961              * @description The base href to use in the iframe.
 962              * @type String
 963              */
 964              basehref: {
 965                  value: false,
 966                  getter: '_resolveBaseHref'
 967              },
 968              /**
 969              * @attribute use
 970              * @description Array of modules to include in the scoped YUI instance at render time. Default: ['none', 'selector-css2']
 971              * @writeonce
 972              * @type Array
 973              */
 974              use: {
 975                  writeOnce: true,
 976                  value: ['node', 'node-style', 'selector-css3']
 977              },
 978              /**
 979              * @attribute container
 980              * @description The container to append the iFrame to on render.
 981              * @type String/HTMLElement/Node
 982              */
 983              container: {
 984                  value: 'body',
 985                  setter: function(n) {
 986                      return Y.one(n);
 987                  }
 988              },
 989              /**
 990              * @attribute node
 991              * @description The Node instance of the iframe.
 992              * @type Node
 993              */
 994              node: {
 995                  readOnly: true,
 996                  value: null,
 997                  getter: function() {
 998                      return this._iframe;
 999                  }
1000              },
1001              /**
1002              * @attribute id
1003              * @description Set the id of the new Node. (optional)
1004              * @type String
1005              * @writeonce
1006              */
1007              id: {
1008                  writeOnce: true,
1009                  getter: function(id) {
1010                      if (!id) {
1011                          id = 'iframe-' + Y.guid();
1012                      }
1013                      return id;
1014                  }
1015              },
1016              /**
1017              * @attribute linkedcss
1018              * @description An array of url's to external linked style sheets
1019              * @type String|Array
1020              */
1021              linkedcss: {
1022                  validator: '_validateLinkedCSS',
1023                  getter: '_getLinkedCSS',
1024                  setter: '_setLinkedCSS'
1025              },
1026              /**
1027              * @attribute extracss
1028              * @description A string of CSS to add to the Head of the Editor
1029              * @type String
1030              */
1031              extracss: {
1032                  validator: Lang.isString,
1033                  setter: '_setExtraCSS'
1034              },
1035              /**
1036              * @attribute defaultblock
1037              * @description The default tag to use for block level items, defaults to: p
1038              * @type String
1039              */
1040              defaultblock: {
1041                  value: 'p'
1042              }
1043          }
1044      });
1045  
1046      Y.namespace('Plugin');
1047  
1048      Y.Plugin.Frame = Frame;
1049  
1050      Y.Frame = Frame;
1051  
1052  
1053  
1054  }, '3.17.2', {"requires": ["base", "node", "plugin", "selector-css3", "yui-throttle"]});


Generated: Thu Aug 11 10:00:09 2016 Cross-referenced by PHPXref 0.7.1