#

API Docs for: 3.10.3
Show: Inherited Protected Private Deprecated

# File: widget/js/WidgetHTMLParser.js

    /**
     * Adds HTML Parser support to the base Widget class
     *
     * @module widget
     * @submodule widget-htmlparser
     * @for Widget
     */

    var Widget = Y.Widget,
        Node = Y.Node,
        Lang = Y.Lang,

        SRC_NODE = "srcNode",
        CONTENT_BOX = "contentBox";

    /**
     * Object hash, defining how attribute values are to be parsed from
     * markup contained in the widget's content box. e.g.:
     * <pre>
     *   {
     *       // Set single Node references using selector syntax
     *       // (selector is run through node.one)
     *       titleNode: "span.yui-title",
     *       // Set NodeList references using selector syntax
     *       // (array indicates selector is to be run through node.all)
     *       listNodes: ["li.yui-item"],
     *       // Set other attribute types, using a parse function.
     *       // Context is set to the widget instance.
     *       label: function(contentBox) {
     *           return contentBox.one("span.title").get("innerHTML");
     *       }
     *   }
     * </pre>
     *
     * @property HTML_PARSER
     * @type Object
     * @static
     */
    Widget.HTML_PARSER = {};

    /**
     * The build configuration for the Widget class.
     * <p>
     * Defines the static fields which need to be aggregated,
     * when this class is used as the main class passed to
     * the <a href="Base.html#method_build">Base.build</a> method.
     * </p>
     * @property _buildCfg
     * @type Object
     * @static
     * @final
     * @private
     */
    Widget._buildCfg = {
        aggregates : ["HTML_PARSER"]
    };

    /**
     * The DOM node to parse for configuration values, passed to the Widget's HTML_PARSER definition
     *
     * @attribute srcNode
     * @type String | Node
     * @writeOnce
     */
    Widget.ATTRS[SRC_NODE] = {
        value: null,
        setter: Node.one,
        getter: "_getSrcNode",
        writeOnce: true
    };

    Y.mix(Widget.prototype, {

        /**
         * @method _getSrcNode
         * @protected
         * @return {Node} The Node to apply HTML_PARSER to
         */
        _getSrcNode : function(val) {
            return val || this.get(CONTENT_BOX);
        },

        /**
         * @method _applyParsedConfig
         * @protected
         * @return {Object} The merged configuration literal
         */
        _applyParsedConfig : function(node, cfg, parsedCfg) {
            return (parsedCfg) ? Y.mix(cfg, parsedCfg, false) : cfg;
        },

        /**
         * Utility method used to apply the <code>HTML_PARSER</code> configuration for the
         * instance, to retrieve config data values.
         *
         * @method _applyParser
         * @protected
         * @param config {Object} User configuration object (will be populated with values from Node)
         */
        _applyParser : function(config) {

            var widget = this,
                srcNode = this._getNodeToParse(),
                schema = widget._getHtmlParser(),
                parsedConfig,
                val;

            if (schema && srcNode) {
                Y.Object.each(schema, function(v, k, o) {
                    val = null;

                    if (Lang.isFunction(v)) {
                        val = v.call(widget, srcNode);
                    } else {
                        if (Lang.isArray(v)) {
                            val = srcNode.all(v[0]);
                            if (val.isEmpty()) {
                                val = null;
                            }
                        } else {
                            val = srcNode.one(v);
                        }
                    }

                    if (val !== null && val !== undefined) {
                        parsedConfig = parsedConfig || {};
                        parsedConfig[k] = val;
                    }
                });
            }
            config = widget._applyParsedConfig(srcNode, config, parsedConfig);
        },

        /**
         * Determines whether we have a node reference which we should try and parse.
         *
         * The current implementation does not parse nodes generated from CONTENT_TEMPLATE,
         * only explicitly set srcNode, or contentBox attributes.
         *
         * @method _getNodeToParse
         * @return {Node} The node reference to apply HTML_PARSER to.
         * @private
         */
        _getNodeToParse : function() {
            var srcNode = this.get("srcNode");
            return (!this._cbFromTemplate) ? srcNode : null;
        },

        /**
         * Gets the HTML_PARSER definition for this instance, by merging HTML_PARSER
         * definitions across the class hierarchy.
         *
         * @private
         * @method _getHtmlParser
         * @return {Object} HTML_PARSER definition for this instance
         */
        _getHtmlParser : function() {
            // Removed caching for kweight. This is a private method
            // and only called once so don't need to cache HTML_PARSER
            var classes = this._getClasses(),
                parser = {},
                i, p;

            for (i = classes.length - 1; i >= 0; i--) {
                p = classes[i].HTML_PARSER;
                if (p) {
                    Y.mix(parser, p, true);
                }
            }
            return parser;
        }
    });