《JS设计模式》笔记-组合模式(结合抽象工厂模式+组合继承)

组合模式:又称部分-整体模式,将对象组合成树形结构以表示"部分整体"的层次结构

先看代码示例

    /**************************
     * 抽象工程模式创建新闻类
     */
    var News = function () {
        // 子组件容器
        this.children = []
        // 当前组件容器
        this.element = null
    }
    News.prototype = {
        init: function () {
            throw new Error('请重写你的方法')
        },
        add: function () {
            throw new Error('请重写你的方法')
        },
        getElement: function () {
            throw new Error('请重写你的方法')
        }
    }
    /***************************
     * 原型继承模式
     */
    function inheritObject(o) {
        function F() {
        }
        F.prototype = o
        return new F()
    }
    function inheritPrototype(subClass, superClass) {
        var p = inheritObject(superClass.prototype)
        p.constructor = subClass
        subClass.prototype = p
    }

    /*****************************
     * 原型继承 + 构造函数继承 组合继承 模式
     */
    var Container = function (id, parent) {
        // 构造函数继承父类
        News.call(this)
        // 模块id
        this.id = id
        // 模块的父容器
        this.parent = parent
        // 构建方法
        this.init()
    }
    inheritPrototype(Container, News)
    // 构建方法
    Container.prototype.init = function () {
        this.element = document.createElement('ul')
        this.element.id = this.id
        this.element.className = 'new-container'
    }
    // 添加子元素方法
    Container.prototype.add = function (child) {
        // 在子元素容器中插入元素
        this.children.push(child)
        // 插入当前组件元素树中
        this.element.appendChild(child.getElement())
        return this
    }
    // 获取当前元素方法
    Container.prototype.getElement = function () {
        return this.element
    }
    // 显示方法
    Container.prototype.show = function () {
        this.parent.appendChild(this.element)
    }

    /*************************
     * 创建 li
     */
    var Item = function (classname) {
        News.call(this)
        this.classname = classname
        this.init()
    }
    inheritPrototype(Item, Container)
    Item.prototype.init = function () {
        this.element = document.createElement('li')
        this.element.className = this.classname
    }
    Item.prototype.add = function (child) {
        // 在子元素容器中插入子元素
        this.children.push(child)
        // 插入当前组件元素树中
        this.element.appendChild(child.getElement())
        return this
    }
    Item.prototype.getElement = function () {
        return this.element
    }


    /***************
     * 创建最底层 图片
     */

    // 创建一个图片成员类
    var ImageNews = function (url, href, classname) {
        News.call(this)
        this.url = url || ''
        this.href = href || '#'
        this.classname = classname || 'normal'
        this.init()
    }
    inheritObject(ImageNews, News)
    ImageNews.prototype.init = function () {
        this.element = document.createElement('a')
        var img = new Image()
        img.src = this.url
        this.element.appendChild(img)
        this.element.className = 'image-news ' + this.classname
        this.element.href = this.href
    }
    ImageNews.prototype.add = function () {

    }
    ImageNews.prototype.getElement = function () {
        return this.element
    }



    // 继承容器类
    var news1 = new Container('news', document.body)

    // 添加节点
    news1.add(
        new Item('normal').add(
            new ImageNews('http://mazhaoyang.cn/Public/Blog/src/images/lunzi.png', 'http://mazhaoyang.cn', 'small')
        ).add(
            new ImageNews('http://mazhaoyang.cn/Public/Blog/src/images/lunzi.png', 'http://mazhaoyang.cn', 'big')
        )
    ).add(
        new Item('normal')
    ).show()

总结

  • 1:最终,news1.add 部分,是组合模式描述的重点:组合成与最终结果类似的层次结构
  • 2:组合模式必须要有一个容器
  • 3:抽象工厂模式,抽象出通用的News类。详情看这里
  • 4:通过 原型继承+构造函数继承 的组合继承。详情看这里

随机浏览