首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >下拉UI组件

下拉UI组件
EN

Code Review用户
提问于 2015-07-04 08:24:11
回答 1查看 67关注 0票数 2

我实现了一个自定义下拉列表,它有助于从数据中查找用户。每个项目都有一个用户名、名字和姓氏。我的任务是创建一个下拉列表,设置为“是否使用图片”。我用create函数编写它,在一个循环中使用if-statement:if (is_use_picture) { /* ... */ }。如果我能得到一些关于这段代码的反馈,那就太好了。

代码语言:javascript
复制
function Dropdown(dropdown, data, is_use_picture, is_multiselect) {

    /**
     * Reformat a data and create a dropdown.
     */

    var formatted_data;

    this.init = function() {
        formatted_data = reformat(data);

        var DROPDOWN_ITEMS_LENGTH = 10;
        var result = new Array(DROPDOWN_ITEMS_LENGTH);

        for (var i = 0; i < DROPDOWN_ITEMS_LENGTH; ++i) {
            result[i] = data[i];
        }

        create(result, is_use_picture, is_multiselect);
    };


    /**
     * @param {Array.<Object>} data.
     * @return {Array.<Object>} result.
     */

    var reformat = function(data) {
        var len = response.items.length;
        var result = new Array(len);

        var first_name;
        var last_name;
        var domain;

        for (var i = 0; i < len; ++i) {
            first_name = response.items[i].first_name.toLowerCase();
            last_name = response.items[i].last_name.toLowerCase();
            domain = response.items[i].domain.toLowerCase();

            result[i] = {
                'item_info': response.items[i],
                'first_name': first_name,
                'last_name': last_name,
                'domain': domain
            };
        }

        return result;
    };


    /**
     * Create and insert dropdown items.
     * @param {Array.<Object>} data.
     * @param {bool} is_use_picture.
     */

    var dropdown_items;
    var dropdown_items_length;

    var create = function(data, is_use_picture) {
        var item_node = document.createElement('div');
        item_node.className = 'dropdown-item cf';

        var text_node = document.createElement('span');

        if (is_use_picture) {
            var picture_node = document.createElement('span');
            picture_node.className = 'dropdown-item-picture';
        }

        var len = data.length;
        var docfrag = document.createDocumentFragment();

        var i = 0;

        while (i < len) {
            var item = item_node.cloneNode(true);
            item.setAttribute('data-index', i);
            item.setAttribute('data-id', data[i].id);
            item.addEventListener('click', select);

            if (is_use_picture) {
                var picture = picture_node.cloneNode(true);
                picture.style.backgroundImage = 'url(' + data[i].photo_50 + ')';
                item.appendChild(picture);
            }

            var text = text_node.cloneNode(true);
            text.className = 'dropdown-item-text';
            text.textContent = data[i].first_name + ' ' + data[i].last_name;
            item.appendChild(text);

            docfrag.appendChild(item);

            i++;
        }

        dropdown_items_length = i;

        clean();

        dropdown_content.appendChild(docfrag);

        dropdown_items = dropdown.querySelectorAll('.dropdown-item');
    };


    /**
     * Open/close a dropdown.
     */

    var dropdown_content = dropdown.querySelector('.dropdown-content');
    var is_open;

    var open = function() {
        dropdown_content.classList.remove('hidden');
        is_open = true;
    };

    var close = function() {
        dropdown_content.className += ' hidden';
        is_open = false;
    };

    document.addEventListener('keydown', function(event) {
        event = event || window.event;
        if (is_open && event.keyCode === 27) {
            close();
        }
    }, false);

    document.addEventListener('click', function(event) {
        event = event || window.event;
        if (is_open && event.keyCode == 0) {
            var element = event.target;

            while (element !== document) {
                if (element.className === 'dropdown') {
                    return;
                }
                element = element.parentNode;
            }

            close();
        }
    }, false);


    /**
     *
     */

    var clean = function() {
        while (dropdown_content.hasChildNodes()) {
            dropdown_content.removeChild(dropdown_content.firstChild);
        }
    };


    /**
     * Navigation by dropdown.
     */

    var UP_KEY_CODE = 38;
    var DOWN_KEY_CODE = 40;
    var SCROLL_STEP = 66;

    var keydown_count = -1;

    var hover = function(event) {
        event = event || window.event;
        if (event.keyCode === UP_KEY_CODE || event.keyCode === DOWN_KEY_CODE) {
            if (event.keyCode === UP_KEY_CODE) {
                keydown_count--;

                if (keydown_count < 0) {
                    keydown_count = dropdown_items_length - 1;
                    dropdown_content.scrollTop = SCROLL_STEP * dropdown_items_length;
                }

                if (keydown_count < (dropdown_items_length - 3)) {
                    dropdown_content.scrollTop -= SCROLL_STEP;
                }

            } else if (event.keyCode === DOWN_KEY_CODE) {
                keydown_count++;

                if (keydown_count >= dropdown_items_length) {
                    keydown_count = 0;
                    dropdown_content.scrollTop = 0;
                }

                if (keydown_count > 2) {
                    dropdown_content.scrollTop += SCROLL_STEP;
                }
            }

            for (var i = 0; i < dropdown_items_length; ++i) {
                dropdown_items[i].classList.remove('dropdown-item--hover');
            }

            dropdown_items[keydown_count].className += ' dropdown-item--hover';
        }

    };


    /**
     *
     */

    var select = function() {
        if (!is_multiselect) {
            close();
        }

        dropdown_input.value = '';

        return this.getAttribute('data-id');
    };


    /**
     *
     */

    var dropdown_input = dropdown.querySelector('.dropdown-input');

    dropdown_input.addEventListener('keydown', hover, false);

    var dropdown_input_wrap = dropdown.querySelector('.dropdown-input-wrap');

    dropdown_input_wrap.addEventListener('click', open, false);

}

我使用这段代码插入下拉列表:

代码语言:javascript
复制
var dropdown = new Dropdown(document.getElementById('dropdown'), response.items, true, false);

dropdown.init();
EN

回答 1

Code Review用户

发布于 2015-07-04 15:51:16

我不太清楚你在这里问的是什么,但是如果你想在这里尝试一种面向对象的方法,你应该这样做:

代码语言:javascript
复制
function MyObject( ... ) {
    ...
}

MyObject.prototype.my_func = function( ... ) {
    ...
}

例如,您的init函数将变成如下(假设您已经为您的其他函数/变量这样做了):

代码语言:javascript
复制
Dropdown.prototype.init = function() {
    this.formatted_data = this.reformat(this.data);

    var DROPDOWN_ITEMS_LENGTH = 10;
    var result = new Array(DROPDOWN_ITEMS_LENGTH);

    for (var i = 0; i < DROPDOWN_ITEMS_LENGTH; ++i) {
        result[i] = this.data[i];
    }

    this.create(result, this.is_use_picture, this.is_multiselect);
};

另外,像下面的例子一样,空注释应该被删除,或者应该添加一些细节。

代码语言:javascript
复制
/**
 *
 */
票数 3
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/95754

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档