Giter Site home page Giter Site logo

select's Introduction

Select


spm package Build Status Coverage Status

模拟 select 的组件。


使用方法

Select 继承了 overlay,可使用其中包括 widgetbaseclasseventsattributeaspect 的属性和方法。

trigger 为 select

html 片段

<select id="city" name="city">
    <option value="value1">text1</option>
    <option value="value2">text2</option>
</select>

javascript 片段

new Select({
    trigger: '#city'
}).render()

trigger 为其他 DOM

html 片段

<a href="#" id="city"></a>

javascript 片段

new Select({
    trigger: '#city',
    name: 'city',
    model: [
        {value:'value1', text: 'text1'},
        {value:'value2', text: 'text2'}
    ]
}).render();

配置说明

trigger element

trigger 可以为 select 或 其他任何 DOM。

**注意:**trigger只能为一个 DOM,如果选出来多个会取第一个

  • 如果为 select,会将其隐藏并生成一个 a 标签放在原来的位置。
  • 如果为 DOM,实例化的时候则需要提供 model 作为数据源

如果 trigger 比较复杂,可以选择 DOM 自定义结构,而且需要设置 data-role="trigger-content" 来指定填入内容的位置。

model object

model 的来源有两处

  1. 初始化传入
  2. 如果 trigger 为 select,则会根据结构生成 model

model 的格式为

[
    {value:'value1', text: 'text1', selected: true},
    {value:'value2', text: 'text2'}
]

value text selected 均为 option 的属性

template string

生成组件的模版,数据源为 model。

triggerTpl string

可以指定触发器的 DOM 结构,默认就是个 a 标签。

classPrefix string (0.9.0 修改,之前为 prefix)

样式前缀,默认为 ui-select

name string

模拟 select 的属性,表单项需要的 name 值,等同于 select.name

注意:如果 trigger 不是 select,那么会先在页面找 name 的 input,找不到再创建一个。

value string

模拟 select 的属性,获取被选中 option 的 value 值,等同于 select.value

length number

模拟 select 的属性,获取 option 的个数,等同于 select.length

selectedIndex number

模拟 select 的属性,获取被选中 option 的索引值,等同于 select.selectedIndex

multiple boolean

// TODO

disabled boolean

模拟 select 的属性,设置 select 是否可点,等同于 select.disabled

方法

.select(option)

选中某项,option 支持三种

  1. 列表索引,为 Number
  2. 选择器,为 String
  3. DOM,支持 DOM Element 和 jQuery 对象

.syncModel(model)

重新跟进给定的 demo 渲染 select

model 为数据源,和上面提到的 model 格式保持一致

.addOption(option)

将一个选项添加到最后,option 的格式为

{value: 'value1', text: 'text1'}

.getOption(option)

获取某个选项,参数和 .select 方法一致

.removeOption(option)

删除某个选项,参数和 .select 方法一致

.enableOption(option)

使某个选项可选,参数和 .select 方法一致

.disableOption(option)

使某个选项不可选,参数和 .select 方法一致

事件

change

当选择某项的时候会触发,组件初始化不会触发此事件

回调传回的参数为当前选中的项,为 jQuery 对象

new Select({
    trigger: ''
}).on('change', function(target, prev) {
    console.log(target.html());
})

disabledChange

在 disabled 状态变化时会触发这个事件,在初始化的时候也会触发此事件。

.on('disabledChange', function(target, status) {
    console.log(target.html());
})

target 为当前选中的项,status 为变化后的 disabled 状态

问题讨论

  • ui-select-item 避免设置 height #13
  • trigger 和 template 的字体保持一致,不然宽度可能有不对齐的情况

select's People

Contributors

afc163 avatar antife-yinyue avatar jaredleechn avatar leoner avatar lianqin7 avatar lizzie avatar meowtec avatar popomore avatar sehuo avatar sorrycc avatar tsj1107 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

select's Issues

ie6/7下一处兼容性问题

根据文档,trigger 为任意 DOM,测试发现如果为input[type="text"]或者textarea时会报错(jquery-1.8.3)。
追踪发现_onRenderSelectedIndex 方法中简单的调用

trigger.html(selected.html());

在ie6/7下会报错,表单元素不能调用html方法

在生成select的时候判断一下IE

因为IE浏览器丑陋的scrollbar,会造成只适应宽度的数据换行了
image

在生成select的时候能不能加一下IE的判断,给trigger加上scrollbar的宽度

支持表单项

如果 select 的选项变更后,表单项也要跟着变更

  • 如果初始化是 select,则变更原来的 select
  • 如果初始化是 DOM,则生成一个 input

增加 name 的参数

  • 如果为 select 则先从 select 获取,再读取 name 参数,如果都不存在则不处理。
  • 如果是 DOM,则直接从 name 参数获取,并生成 input,如果不存在则不生成。

option 支持 disabled

<select id="test" name="test">
  <option value="SelectBoxIt is:">SelectBoxIt is:</option>
  <option value="a jQuery Plugin" disabled>a jQuery Plugin</option>
  <option value="a Select Box Replacement" disabled>a Select Box Replacement</option>
  <option value="a Stateful UI Widget" selected>a Stateful UI Widget</option>
</select>

提供 disableOption enableOption 方法

select在IE6下模拟出来的组件宽度几乎是屏幕的宽度

 // trigger 的宽度和浮层保持一致
        _setTriggerWidth: function() {
            var trigger = this.get("trigger");
            var width = this.element.outerWidth();
            var pl = parseInt(trigger.css("padding-left"), 10);
            var pr = parseInt(trigger.css("padding-right"), 10);
            var bl = parseInt(trigger.css("border-left-width"), 10);
            var br = parseInt(trigger.css("border-right-width"), 10);
            trigger.css("width", width - pl - pr - bl - br);
        }

这些代码好像在IE6下不是太有效,后来修改代码,将ui-select-trigger与ui-select-content的宽度直接设置成原始select的宽度。

2个建议

  • 希望如果不设置 classPrefix 就不做那些 addClass/removeClass 相关的操作

原因:我们的 dpl 的 class 后缀和默认的不一致,会添加很多无效class(比如 xxx-trigger-hover这些,-trigger-hover根本无法修改)

  • 对 item 的 clcik 事件不冒泡

原因:既然是对 原生select的模拟 ,事件处理部分也应该一致(原生select的选择不会触发click的冒泡,还有以后的键盘事件支持也是)
场景:在一个 overlay 的表单中使用了 select ,如果点击了 item 后, overlay 就自动关闭了(click的冒泡引起的)。

@popomore @lizzie

model是否支持动态获取

  1. 宽度是有限的,比如搜索条,如果宽度动态调整的话,会产生bug。
  2. 某些场景下,model可能需要从服务器端获取,现在好像不支持,不知道能否支持。

能不能提供一个方法设置selec的disabled

能不能提供一个方法设置selec的disabled,现在有个联动的交互,一级select的值无效的时候,需要动态的改变二级select的disabled,但是Select组件没有这个方法,好蛋疼,只能在初始化的时候配置disable: true来完成,但是不能满足动态改变的需求

级联的Select 组建

希望能扩展下select 组建 出一个级联的Select 组建, 会比较常用。 文档中的级联demo的用法,不是很好用。

  • 能根据json数据自动生成级联的select
  • 也能通过ajax获取数据

templatable 28行 Cannot read property 'toJSON' of null

templatable.js中:model || (model = this.get("model"));

最后找到select.js文件里:
this.model = convertSelect(trigger[0], this.get('classPrefix'));
把这改成:
this.set('model', convertSelect(trigger[0], this.get('classPrefix')));后正常同样的还有:

this.model = completeModel(this.model, this.get('classPrefix'));

关于进行尺寸同步和事件同步以及数据同步更新的建议

mmonitormng 这个系统最近使用了该select组件 不过因为是后引入的 而原有select的业务逻辑使用较复杂,有vm预先载入的,有JS动态创建或者options插入的,以及后续交互过程中需要动态更新options的;通过在TTI之后查找所有select元素并逐个进行对象实例化,目前可以正常使用,但是因为原元素宽高各不相同,会导致页面大面积的rerender,另外原有的select的事件绑定和options状态(选中、新增)更新都无法同步到select组件上,目前尺寸问题通过全局设定高优先级样式应用固定值临时解决了,事件和数据的同步只能逐个改原有代码了…
希望可以支持实现以上问题,实现事件双向通知或数据双向同步,达到透明替换原始元素的目标~

triggerTemplate 参数是否必要

如果原来 trigger 是 select,那么会替换成一个 a 标签。

<select>
    <option value="value">text</option>
</select>

上面的 trigger 会被转化成

<a href="#" class="ui-select-trigger">text</a>

但不知道是否需要支持模版,这个 trigger 是否有改变模版的场景。

其实可以通过折中的方案解决,就是 trigger 不传 select,而直接使用 DOM。

之前定义了个属性为 triggerTemplate,现在已经废弃,如有需要再添加。

change 事件的触发时机

在级联功能的时候,syncModel 后希望触发 change 事件,而在页面初始化渲染模板的时候不希望触发 change 事件。

change 触发的时机应该这样定义:组件初始化时不应该触发,而在之后只要 selectedIndex 切换就应该触发。

在级联状态下,使用select标签时

demo使用的a标签作为级联的下级
但是想上下级都使用select标签 而非 select 与 a,就有个问题出现了

因为判断下级是 a 则 生成 input type=hidden name=xxx
判断下级是select 则不生成

导致的问题就存在了,syncModel 方法,没有model to option, 我只看到了 convertSelect,也就是 option to model.

直接的表现就是 model 虽然变化,ul li 也变化,但是原始 select的option 并没有变化。

这导致 给后台传参数时候,始终是 第一次 render时候的值。

说了这么多,我想到两个解决方法:

  1. 放弃操作option dom,新增一个hidden,给原始的select 新建一个 data-name ,并赋给hidden的name。后面的处理fang方式就如同使用了a标签

2.操作option,这种方式,比较麻烦,并且也有可能违背了你某些方法的初衷。

请考虑一下,谢谢了

滚动条出现后会换行

滚动条出现宽度有可能不够,要加个 padding

ps:统一考虑下,是否要加个 maxHeight 的参数

trigger 和浮层应该等宽

原生的 select trigger 和浮层是等宽的,所以应该支持这个功能。

初始化后获取浮层的宽度,然后设置 trigger 的宽度,其他样式不设置。

destroy的bug

src/select.js

156-158行的destroy方法

destroy: function() {
    this.element.remove();
},

没有调用父类的destroy :(

关于 advanced-select

现在看起来功能已经不是 select 了,所以extend select 写,下周我来改

主要 feature

  1. model 和 tpl 支持多层数据
  2. trigger 填充自定义
  3. selectedIndex 也要支持多级
  4. 单个 option 也支持 disabled

change的时候希望得到上一次选择的值

RT,现在change时间的 唯一参数是现在选择的item
很多情况下, 上一个选择的item也是很有用的 ,建议加上,让这个事件使用起来更方便

自己提前保存这种方法使用起来比较麻烦。。

@afc163

spm 无法下载了。。

spm -v
v1.1.2

spm install select
Start installing ...
HTTP HEAD 200 http://modules.seajs.org
Downloading: http://modules.seajs.org/info.json
Downloaded: http://modules.seajs.org/info.json
Downloading: http://modules.seajs.org/arale/info.json
Downloading: http://modules.seajs.org/gallery/info.json
Downloaded: http://modules.seajs.org/arale/info.json
Downloaded: http://modules.seajs.org/gallery/info.json
Module select get error!
Total time: 0.17s
Finished at: Wed Nov 21 2012 11:15:36 GMT+0800 (CST)
Final Memory: 6M/12M

这是为啥。。。没有推上去吗?

支持 data-api

对于原生 select 比较实用,使用方法也比较简单,也不需要遍历后对每个 DOM 进行实例化。

当model传入时有多条记录selected=true 有bug

当model传入时有多条记录selected=true 有bug,比如传入4条数据,1,3,4的selected属性为true,这个时候组件默认选中的是第三项而不是第四项。看了下select的源码,发现completeModel函数中for (j = 0, ll = selectIndexArray.length; j < ll; j++) {
newModel[j].selected = "false";
}
按理说这里 不应该是newModel[j].selected = "false"; 而是newModel[selectIndexArray[j]].selected = "false";吧?

change 事件在初始化的时候就会触发

初始化的时候不应该触发 change 事件

原来将 change 事件放到 _onRenderSelectedIndex 中,而初始化时必须设置 selectedIndex,所以会触发。

可以将 change 事件放到 select 方法中。

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.