From b7f37303cee5d897b9417b1cf46c1632acfb5595 Mon Sep 17 00:00:00 2001 From: simaQ Date: Sun, 19 Apr 2015 16:25:56 +0800 Subject: [PATCH 1/4] version 1.0.0 --- .editorconfig | 9 ++ .gitignore | 28 ++++ .jscsrc | 27 ++++ .jshintrc | 28 ++++ .npmignore | 29 ++++ .travis.yml | 14 ++ HISTORY.md | 0 README.md | 148 ++++++++++++++++++- assets/index.less | 117 +++++++++++++++ examples/simple.html | 1 + examples/simple.js | 8 ++ index.js | 1 + lib/Slider.js | 334 +++++++++++++++++++++++++++++++++++++++++++ package.json | 56 ++++++++ tests/index.spec.js | 75 ++++++++++ tests/runner.html | 1 + 16 files changed, 874 insertions(+), 2 deletions(-) create mode 100644 .editorconfig create mode 100644 .gitignore create mode 100644 .jscsrc create mode 100644 .jshintrc create mode 100644 .npmignore create mode 100644 .travis.yml create mode 100644 HISTORY.md create mode 100644 assets/index.less create mode 100644 examples/simple.html create mode 100644 examples/simple.js create mode 100644 index.js create mode 100644 lib/Slider.js create mode 100644 package.json create mode 100644 tests/index.spec.js create mode 100644 tests/runner.html diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 000000000..604c94ef4 --- /dev/null +++ b/.editorconfig @@ -0,0 +1,9 @@ +# top-most EditorConfig file +root = true + +# Unix-style newlines with a newline ending every file +[*.{js,css}] +end_of_line = lf +insert_final_newline = true +indent_style = space +indent_size = 2 diff --git a/.gitignore b/.gitignore new file mode 100644 index 000000000..f8d8a67bd --- /dev/null +++ b/.gitignore @@ -0,0 +1,28 @@ +*.iml +*.log +.idea/ +.ipr +.iws +*~ +~* +*.diff +*.patch +*.bak +.DS_Store +Thumbs.db +.project +.*proj +.svn/ +*.swp +*.swo +*.pyc +*.pyo +.build +node_modules +_site +sea-modules +spm_modules +.cache +dist +assets/**/*.css +build/ \ No newline at end of file diff --git a/.jscsrc b/.jscsrc new file mode 100644 index 000000000..20b0f4dc0 --- /dev/null +++ b/.jscsrc @@ -0,0 +1,27 @@ +{ + "requireCurlyBraces": ["if", "else", "for", "while", "do", "try", "catch"], + "requireSpaceAfterKeywords": ["if", "else", "for", "while", "do", "switch", "return", "try", "catch"], + "requireSpacesInFunctionExpression": { + "beforeOpeningCurlyBrace": true + }, + "disallowSpacesInsideArrayBrackets": true, + "disallowSpacesInsideObjectBrackets": true, + "disallowSpacesInsideParentheses": true, + "disallowQuotedKeysInObjects": "allButReserved", + "disallowSpaceAfterObjectKeys": true, + "requireSpaceBeforeBinaryOperators": ["-", "/", "*", "=", "==", "===", "!=", "!==", ">", ">=", "<", "<=" ], + "requireSpacesInConditionalExpression": { + "afterTest": true, + "beforeConsequent": true, + "afterConsequent": true, + "beforeAlternate": true + }, + "requireSpaceAfterBinaryOperators": ["/", "*", "=", "==", "===", "!=", "!==", ">", ">=", "<", "<="], + "disallowKeywords": [ "with" ], + "disallowSpaceAfterPrefixUnaryOperators": [ "!" , "++", "--", "+", "-", "~"], + "disallowSpaceBeforePostfixUnaryOperators": ["++", "--", ","], + "disallowMultipleLineBreaks": true, + "disallowKeywordsOnNewLine": ["else"], + "safeContextKeyword": "self", + "excludeFiles": ["lib/**/parser.js"] +} \ No newline at end of file diff --git a/.jshintrc b/.jshintrc new file mode 100644 index 000000000..ef5e85e5e --- /dev/null +++ b/.jshintrc @@ -0,0 +1,28 @@ +{ + "camelcase": true, + "curly": true, + "eqeqeq": true, + "freeze": true, + "indent": 4, + "latedef": "nofunc", + "quotmark": "false", + "nonew": true, + "newcap": false, + "immed": true, + "noarg": true, + "eqnull": true, + "trailing": true, + "undef": true, + "unused": true, + "browser": true, + "node": true, + "esnext": true, + "globals": { + "describe": false, + "expect": false, + "beforeEach": false, + "afterEach": false, + "modulex": false, + "it": false + } +} \ No newline at end of file diff --git a/.npmignore b/.npmignore new file mode 100644 index 000000000..e43e0f4e4 --- /dev/null +++ b/.npmignore @@ -0,0 +1,29 @@ +bower_components/ +build/ +*.cfg +node_modules/ +nohup.out +*.iml +.idea/ +.ipr +.iws +*~ +~* +*.diff +*.log +*.patch +*.bak +.DS_Store +Thumbs.db +.project +.*proj +.svn/ +*.swp +out/ +.build +node_modules +_site +sea-modules +spm_modules +.cache +dist \ No newline at end of file diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 000000000..2fde59c31 --- /dev/null +++ b/.travis.yml @@ -0,0 +1,14 @@ +language: node_js +notifications: + email: + - yiminghe@gmail.com +node_js: +- 0.12 +before_script: +- npm start & +- npm install mocha-phantomjs -g +- phantomjs --version +script: +- npm test +- npm run-script browser-test +- npm run-script browser-test-cover \ No newline at end of file diff --git a/HISTORY.md b/HISTORY.md new file mode 100644 index 000000000..e69de29bb diff --git a/README.md b/README.md index 57f09a88e..76cd0a077 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,146 @@ -# slider -react slider component +# rc-slider +--- + +slider ui component for react + +[![NPM version][npm-image]][npm-url] +[![SPM version](http://spmjs.io/badge/rc-slider)](http://spmjs.io/package/rc-slider) +[![build status][travis-image]][travis-url] +[![Test coverage][coveralls-image]][coveralls-url] +[![gemnasium deps][gemnasium-image]][gemnasium-url] +[![node version][node-image]][node-url] +[![npm download][download-image]][download-url] +[![Sauce Test Status](https://saucelabs.com/buildstatus/rc-slider)](https://saucelabs.com/u/rc-slider) + +[![Sauce Test Status](https://saucelabs.com/browser-matrix/rc-slider.svg)](https://saucelabs.com/u/rc-slider) + +[npm-image]: http://img.shields.io/npm/v/rc-slider.svg?style=flat-square +[npm-url]: http://npmjs.org/package/rc-slider +[travis-image]: https://img.shields.io/travis/react-component/slider.svg?style=flat-square +[travis-url]: https://travis-ci.org/react-component/slider +[coveralls-image]: https://img.shields.io/coveralls/react-component/slider.svg?style=flat-square +[coveralls-url]: https://coveralls.io/r/react-component/slider?branch=master +[gemnasium-image]: http://img.shields.io/gemnasium/react-component/slider.svg?style=flat-square +[gemnasium-url]: https://gemnasium.com/react-component/slider +[node-image]: https://img.shields.io/badge/node.js-%3E=_0.10-green.svg?style=flat-square +[node-url]: http://nodejs.org/download/ +[download-image]: https://img.shields.io/npm/dm/rc-slider.svg?style=flat-square +[download-url]: https://npmjs.org/package/rc-slider + +## Screenshots + + + + + + + + +## Feature + +* support ie8,ie8+,chrome,firefox,safari + +### Keyboard + + + +## install + +[![rc-slider](https://nodei.co/npm/rc-slider.png)](https://npmjs.org/package/rc-slider) + +## Usage + +```js +var Rcslider = require('rc-slider'); +var React = require('react'); +React.render(, container); + +## API + +### props + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
nametypedefaultdescription
classNameStringrc-slideradditional css class of root dom node
minnumber0The minimum value of the slider
maxnumber100The maximum value of the slider
stepnumber1Value to be added or subtracted on each step the slider makes. Must be greater than zero. max - min should be evenly divisible by the step value.
valuenumber0Determines the initial positions of the handles.
marksarray[]mark every step for the slider, it will ignore the `step` parameter if it has been defined
indexnumber0For step or marks slider, determine the initial positions of the handles.
disabledbooleanfalseIf true the handles can't be moved.
+ +## Development + +``` +npm install +npm start +``` + +## Example + +http://localhost:8088/examples/ + +online example: http://react-component.github.io/slider/build/examples/ + +## Test Case + +http://localhost:8088/tests/runner.html?coverage + +## Coverage + +http://localhost:8088/node_modules/rc-server/node_modules/node-jscover/lib/front-end/jscoverage.html?w=http://localhost:8088/tests/runner.html?coverage + +## License + +rc-slider is released under the MIT license. diff --git a/assets/index.less b/assets/index.less new file mode 100644 index 000000000..60b2d6156 --- /dev/null +++ b/assets/index.less @@ -0,0 +1,117 @@ +@prefixClass: rc-slider; + +// color +@sliderColor: #999; +@trackColor: #b2e9fd; +@normalHandleColor: #d9d9d9; +@activeHandleColor: #2db7f5; +@disabledColor: #e9e9e9; + +.@{prefixClass} { + position: relative; + height: 4px; + width: 100%; + border-radius: 2px; + background-color: @sliderColor; + + &-track { + position: absolute; + height: 4px; + border-radius: 2px; + background-color: @trackColor; + z-index: 1; + } + + &-handle { + position: absolute; + margin-left: -7px; + margin-top: -5px; + width: 10px; + height: 10px; + cursor: default; + border-radius: 50%; + border: solid 2px @normalHandleColor; + background-color: #fff; + z-index: 2; + &:hover, &:active, &.active { + border-color: @activeHandleColor; + } + &:active { + background-color: @activeHandleColor; + box-shadow: 0 0 3px 0 rgb(45, 183, 245, .75); + } + } + + &-mark { + position: absolute; + top: 10px; + left: 0px; + width: 100%; + height: 20px; + font-size: 12px; + z-index: 3; + } + + &-mark-text { + position: absolute; + display: inline-block; + line-height: 1.5; + height: 20px; + vertical-align: middle; + text-align: center; + cursor: pointer; + &:first-child { + text-align: left; + } + } + + &-step { + position: absolute; + width: 100%; + height: 4px; + background: transparent; + z-index: 1; + .dot { + position: absolute; + top: -2px; + margin-left: -4px; + width: 4px; + height: 4px; + border: 2px solid #fff; + cursor: pointer; + border-radius: 50%; + vertical-align: middle; + &:first-child { + margin-left: -2px; + } + &:last-child { + margin-left: -6px; + } + } + } + + &-disabled { + color: @disabledColor; + background-color: @disabledColor; + + .@{prefixClass}-track { + background-color: @disabledColor; + } + + .@{prefixClass}-handle { + border-color: @disabledColor; + background-color: @disabledColor; + cursor: not-allowed; + + &:hover, &:active { + border-color: @disabledColor; + background-color: @disabledColor; + box-shadow: none; + } + } + + .@{prefixClass}-mark-text, .dot { + cursor: not-allowed!important; + } + } +} \ No newline at end of file diff --git a/examples/simple.html b/examples/simple.html new file mode 100644 index 000000000..b3a425249 --- /dev/null +++ b/examples/simple.html @@ -0,0 +1 @@ +placeholder \ No newline at end of file diff --git a/examples/simple.js b/examples/simple.js new file mode 100644 index 000000000..13aa1df6c --- /dev/null +++ b/examples/simple.js @@ -0,0 +1,8 @@ +/** @jsx React.DOM */ +// use jsx to render html, do not modify simple.html +require('rc-slider/assets/index.css'); +var Slider = require('rc-slider'); +var React = require('react'); +// React.render(, document.getElementById('__react-content')); +// React.render(, document.getElementById('__react-content')); +React.render(, document.getElementById('__react-content')); diff --git a/index.js b/index.js new file mode 100644 index 000000000..de274eb06 --- /dev/null +++ b/index.js @@ -0,0 +1 @@ +module.exports = require('./lib/Slider'); diff --git a/lib/Slider.js b/lib/Slider.js new file mode 100644 index 000000000..3f9149fdf --- /dev/null +++ b/lib/Slider.js @@ -0,0 +1,334 @@ +/** @jsx React.DOM */ +var React = require('react'); + +function pauseEvent(e) { + if (e.stopPropagation) e.stopPropagation(); + if (e.preventDefault) e.preventDefault(); + e.cancelBubble = true; + e.returnValue = false; + return false; +} + +var Slider = React.createClass({ + propTypes: { + min: React.PropTypes.number, + max: React.PropTypes.number, + step: React.PropTypes.number, + value: React.PropTypes.number, + index: React.PropTypes.number, + marks: React.PropTypes.array, + className: React.PropTypes.string, + disabled: React.PropTypes.bool, + onBeforeChange: React.PropTypes.func, + onChange: React.PropTypes.func, + onAfterChange: React.PropTypes.func + }, + + getDefaultProps: function () { + return { + min: 0, + max: 100, + step: 1, + value: 0, + marks: [], + className: 'rc-slider', + disabled: false, + index: 0 + }; + }, + + getInitialState: function () { + var props = this.props; + var value = props.value; + var marksLen = props.marks.length; + if(marksLen>0) { + value = ((props.max-props.min) / (marksLen-1))*(props.index); + value = value.toFixed(5); + } + + return { + upperBound: 0, + sliderLength: 0, + value: value, + active: props.disabled ? '' : ((value>0 || props.index>0) ? 'active' : '') + }; + }, + + componentWillReceiveProps: function (newProps) { + var value = newProps.value; + this.state.value = this._trimAlignValue(value, newProps); + }, + + componentDidMount: function () { + window.addEventListener('resize', this.handleResize); + this.handleResize(); + }, + + componentWillUnmount: function () { + window.removeEventListener('resize', this.handleResize); + }, + + getValue: function () { + return this.state.value; + }, + + getIndex: function () { + var props = this.props; + if (props.marks.length === 0) return; + var value = this.state.value; + var unit = (props.max - props.min) / (props.marks.length-1); + return Math.floor(value/unit); + }, + + _trimAlignValue: function (val, props) { + props = props || this.props; + + var step = props.marks.length>0 ? (props.max-props.min) / (props.marks.length-1) : props.step; + + if (val <= props.min) val = props.min; + if (val >= props.max) val = props.max; + + var valModStep = (val - props.min) % step; + var alignValue = val - valModStep; + + if (Math.abs(valModStep) * 2 >= step) { + alignValue += (valModStep > 0) ? step : (-step); + } + + return parseFloat(alignValue.toFixed(5)); + }, + + _calcOffset: function (value) { + var ratio = (value - this.props.min) / (this.props.max - this.props.min); + return ratio * this.state.upperBound; + }, + + _calcValue: function (offset) { + var ratio = offset / this.state.upperBound; + return ratio * (this.props.max - this.props.min) + this.props.min; + }, + + _calValueByPos: function (position, callback) { + var pixelOffset = position - this.state.sliderStart; + // pixelOffset -= (this.state.handleSize / 2); + + var nextValue = this._trimAlignValue(this._calcValue(pixelOffset)); + + this.setState({value: nextValue, active: 'active'}, callback.bind(this)); + }, + + _triggerEvents: function (event) { + if (this.props[event]) { + this.props[event](this.state.value); + } + }, + + _addEventHandles: function (eventMap) { + for (var key in eventMap) { + document.addEventListener(key, eventMap[key], false); + } + }, + + _removeEventHandles: function (eventMap) { + for (var key in eventMap) { + document.removeEventListener(key, eventMap[key], false); + } + }, + + _getMouseEventMap: function () { + return { + 'mousemove': this._onMouseMove, + 'mouseup': this._onMouseUp + } + }, + + _start: function (position) { + if (document.activeElement) document.activeElement.blur(); + + this._triggerEvents('onBeforeChange'); + + this.setState({ + startValue: this.state.value, + startPosition: position + }); + }, + + _end: function (eventMap) { + this._removeEventHandles(eventMap); + this.setState(this._triggerEvents.bind(this, 'onAfterChange')); + }, + + _onMouseUp: function () { + this._end(this._getMouseEventMap()); + }, + + _onMouseMove: function (e) { + var position = e['pageX']; + + var props = this.props; + var state = this.state; + + var value = state.value; + var oldValue = value; + + var diffPosition = position - state.startPosition; + + var diffValue = diffPosition / (state.sliderLength) * (props.max - props.min); + var newValue = this._trimAlignValue(state.startValue + diffValue); + + value = newValue; + + if (newValue !== oldValue) { + this.setState({value: value, active: 'active'} ,this._triggerEvents.bind(this, 'onChange')); + } + }, + + handleResize: function () { + var slider = this.refs.slider.getDOMNode(); + var rect = slider.getBoundingClientRect(); + + var sliderMin = rect['left']; + var sliderMax = rect['right']; + this.setState({ + upperBound: slider['clientWidth'], + sliderLength: Math.abs(sliderMax - sliderMin), + sliderStart: sliderMin + }); + }, + + handleMouseDown: function () { + return function (e) { + if (this.props.disabled) return; + var position = e['pageX']; + this._start(position); + this._addEventHandles(this._getMouseEventMap()); + pauseEvent(e); + }.bind(this); + }, + + handleSliderMouseDown: function (e) { + if (this.props.disabled) return; + var position = e['pageX']; + this._calValueByPos(position, function () { + this._triggerEvents('onChange'); + this._start(position); + this._addEventHandles(this._getMouseEventMap()); + }.bind(this)); + pauseEvent(e); + }, + + renderSteps: function () { + var props = this.props; + var marksLen = props.marks.length; + var stepNum = marksLen> 0 ? marksLen : Math.floor((props.max-props.min)/props.step)+1; + var unit = this.state.sliderLength / (stepNum-1); + + var stepClassName = props.className + '-step'; + + var elements = []; + for(var i=0; i + ); + } + + return ( +
+ {elements} +
+ ); + }, + + renderMark: function(i) { + var marks = this.props.marks; + var marksLen = marks.length; + var unit = this.state.sliderLength / (marksLen-1); + var offset = unit*i; + + var style = { + width: (unit/2).toFixed(5) + 'px' + }; + + if(i===(marksLen-1)) { + style['right'] = '0'; + style['width'] = 'auto'; + }else{ + style['left'] = (i>0 ? (offset - (unit/4)).toFixed(5) : offset)+ 'px'; + } + var className = this.props.className + '-mark-text '; + + return ( + {this.props.marks[i]} + ); + }, + + renderMarks: function() { + var marks = this.props.marks; + var marksLen = marks.length; + var elements = []; + for(var i=0; i + {elements} + + ); + }, + + renderHandle: function (offset) { + var handleStyle = { + left: offset + 'px' + }; + var className = this.props.className + '-handle ' + this.state.active; + + return ( + + ); + }, + + renderTrack: function (offset) { + var style = { + left: 0, + width: offset + }; + var trackClassName = this.props.className + '-track'; + return ( +
+ ); + }, + + render: function () { + var state = this.state; + var props = this.props; + + var value = state.value; + var offset = this._calcOffset(value); + + var track = this.renderTrack(offset); + var handles = this.renderHandle(offset); + var steps = (props.step>1 || props.marks.length>0) ? this.renderSteps() : null; + var sliderMarks = (props.marks.length>0) ? this.renderMarks() : null; + + var sliderClassName = props.className + (props.disabled ? ' '+props.className+ '-disabled' : ''); + + return ( +
+ {track} + {handles} + {steps} + {sliderMarks} +
+ ); + } +}); + +module.exports = Slider; diff --git a/package.json b/package.json new file mode 100644 index 000000000..1e819f147 --- /dev/null +++ b/package.json @@ -0,0 +1,56 @@ +{ + "name": "rc-slider", + "version": "1.0.0", + "description": "slider ui component for react", + "keywords": [ + "react", + "react-component", + "react-slider", + "slider" + ], + "homepage": "http://github.com/react-component/slider", + "author": "sima.zhang1990@gmail.com", + "repository": { + "type": "git", + "url": "git@github.com:react-component/slider.git" + }, + "bugs": { + "url": "http://github.com/react-component/slider/issues" + }, + "licenses": "MIT", + "spm": { + "dependencies": { + "react": "*" + } + }, + "config":{ + "port": 8000 + }, + "scripts": { + "build": "rc-tools run build", + "less": "rc-tools run less", + "gh-pages": "rc-tools run gh-pages", + "history": "rc-tools run history", + "start": "node-dev --harmony node_modules/.bin/rc-server", + "publish": "spm publish && rc-tools run tag", + "lint": "rc-tools run lint", + "test": "", + "saucelabs": "rc-tools run saucelabs", + "browser-test": "rc-tools run browser-test", + "browser-test-cover": "rc-tools run browser-test-cover" + }, + "devDependencies": { + "expect.js": "0.3.x", + "precommit-hook": "1.x", + "rc-server": "2.x", + "rc-tools": "2.x", + "react": "0.13.x", + "node-dev":"2.x", + "jquery": "^1.11.2", + "css-loader": "^0.9.1" + }, + "precommit": [ + "lint", + "less" + ] +} diff --git a/tests/index.spec.js b/tests/index.spec.js new file mode 100644 index 000000000..525794f13 --- /dev/null +++ b/tests/index.spec.js @@ -0,0 +1,75 @@ +/** @jsx React.DOM */ +var expect = require('expect.js'); +var Slider = require('../index.js'); +var React = require('react'); +var TestUtils = React.addons.TestUtils; +var Simulate = TestUtils.Simulate; +var $ = require('jquery'); + +describe('rc-slider', function () { + this.timeout(5000); + var div = document.createElement('div'); + document.body.appendChild(div); + + afterEach(function () { + React.unmountComponentAtNode(div); + }); + + it('should render a simple slider with value correctly!', function () { + var slider = React.render( + , + div + ); + var node = $(div); + expect(node.find('.rc-slider').length).to.be(1); + expect(node.find('.rc-slider-handle').length).to.be(1); + expect(node.find('.rc-slider-track').length).to.be(1); + expect(slider.getValue()).to.be(40); + var trackWidth = node.find('.rc-slider-track')[0].style.width; + expect(trackWidth).to.eql(node.find('.rc-slider-handle')[0].style.left); + }); + + it('should render a slider with correct numbers of step!', function () { + var slider = React.render( + , + div + ); + var node = $(div); + expect(node.find('.rc-slider').length).to.be(1); + expect(node.find('.rc-slider-handle').length).to.be(1); + expect(node.find('.rc-slider-track').length).to.be(1); + expect(node.find('.dot').length).to.be(6); + expect(slider.getValue()).to.be(0); + }); + + it('should render a slider with marks correctly!', function () { + var slider = React.render( + , + div + ); + var node = $(div); + expect(node.find('.rc-slider').length).to.be(1); + expect(node.find('.rc-slider-handle').length).to.be(1); + expect(node.find('.rc-slider-track').length).to.be(1); + expect(node.find('.dot').length).to.be(slider.props.marks.length); + expect(node.find('.rc-slider-mark').length).to.be(1); + expect(node.find('.rc-slider-mark-text').length).to.be(slider.props.marks.length); + expect(slider.getIndex()).to.be(3); + }); + + it('should mouseDown works!', function (done) { + var slider = React.render( + , + div + ); + var selectedStep = slider.refs.step3.getDOMNode(); + + Simulate.mouseDown(selectedStep); + + setTimeout( function() { + expect(slider.state.active).to.be('active'); + done(); + }, 200); + }); + +}); \ No newline at end of file diff --git a/tests/runner.html b/tests/runner.html new file mode 100644 index 000000000..7bd069c80 --- /dev/null +++ b/tests/runner.html @@ -0,0 +1 @@ +stub \ No newline at end of file From fc2ab37e8ab0a23c28865bc0dc3002f5b26e6d70 Mon Sep 17 00:00:00 2001 From: simaQ Date: Sun, 19 Apr 2015 16:37:28 +0800 Subject: [PATCH 2/4] correct code style --- examples/simple.js | 2 +- lib/Slider.js | 144 +++++++++++++++++++++++++-------------------- 2 files changed, 81 insertions(+), 65 deletions(-) diff --git a/examples/simple.js b/examples/simple.js index 13aa1df6c..29b1b4e44 100644 --- a/examples/simple.js +++ b/examples/simple.js @@ -3,6 +3,6 @@ require('rc-slider/assets/index.css'); var Slider = require('rc-slider'); var React = require('react'); -// React.render(, document.getElementById('__react-content')); +// React.render(, document.getElementById('__react-content')); // React.render(, document.getElementById('__react-content')); React.render(, document.getElementById('__react-content')); diff --git a/lib/Slider.js b/lib/Slider.js index 3f9149fdf..44f323748 100644 --- a/lib/Slider.js +++ b/lib/Slider.js @@ -2,8 +2,12 @@ var React = require('react'); function pauseEvent(e) { - if (e.stopPropagation) e.stopPropagation(); - if (e.preventDefault) e.preventDefault(); + if (e.stopPropagation) { + e.stopPropagation(); + } + if (e.preventDefault) { + e.preventDefault(); + } e.cancelBubble = true; e.returnValue = false; return false; @@ -24,7 +28,7 @@ var Slider = React.createClass({ onAfterChange: React.PropTypes.func }, - getDefaultProps: function () { + getDefaultProps: function() { return { min: 0, max: 100, @@ -37,12 +41,12 @@ var Slider = React.createClass({ }; }, - getInitialState: function () { + getInitialState: function() { var props = this.props; var value = props.value; var marksLen = props.marks.length; - if(marksLen>0) { - value = ((props.max-props.min) / (marksLen-1))*(props.index); + if (marksLen > 0) { + value = ((props.max - props.min) / (marksLen - 1)) * (props.index); value = value.toFixed(5); } @@ -50,43 +54,49 @@ var Slider = React.createClass({ upperBound: 0, sliderLength: 0, value: value, - active: props.disabled ? '' : ((value>0 || props.index>0) ? 'active' : '') + active: props.disabled ? '' : ((value > 0 || props.index > 0) ? 'active' : '') }; }, - componentWillReceiveProps: function (newProps) { + componentWillReceiveProps: function(newProps) { var value = newProps.value; this.state.value = this._trimAlignValue(value, newProps); }, - componentDidMount: function () { + componentDidMount: function() { window.addEventListener('resize', this.handleResize); this.handleResize(); }, - componentWillUnmount: function () { + componentWillUnmount: function() { window.removeEventListener('resize', this.handleResize); }, - getValue: function () { + getValue: function() { return this.state.value; }, - getIndex: function () { + getIndex: function() { var props = this.props; - if (props.marks.length === 0) return; + if (props.marks.length === 0) { + return; + } var value = this.state.value; - var unit = (props.max - props.min) / (props.marks.length-1); - return Math.floor(value/unit); + var unit = (props.max - props.min) / (props.marks.length - 1); + return Math.floor(value / unit); }, - _trimAlignValue: function (val, props) { + _trimAlignValue: function(val, props) { props = props || this.props; - var step = props.marks.length>0 ? (props.max-props.min) / (props.marks.length-1) : props.step; + var step = props.marks.length > 0 ? (props.max - props.min) / (props.marks.length - 1) : props.step; - if (val <= props.min) val = props.min; - if (val >= props.max) val = props.max; + if (val <= props.min) { + val = props.min; + } + if (val >= props.max) { + val = props.max; + } var valModStep = (val - props.min) % step; var alignValue = val - valModStep; @@ -98,12 +108,12 @@ var Slider = React.createClass({ return parseFloat(alignValue.toFixed(5)); }, - _calcOffset: function (value) { + _calcOffset: function(value) { var ratio = (value - this.props.min) / (this.props.max - this.props.min); return ratio * this.state.upperBound; }, - _calcValue: function (offset) { + _calcValue: function(offset) { var ratio = offset / this.state.upperBound; return ratio * (this.props.max - this.props.min) + this.props.min; }, @@ -117,13 +127,13 @@ var Slider = React.createClass({ this.setState({value: nextValue, active: 'active'}, callback.bind(this)); }, - _triggerEvents: function (event) { + _triggerEvents: function(event) { if (this.props[event]) { this.props[event](this.state.value); } }, - _addEventHandles: function (eventMap) { + _addEventHandles: function(eventMap) { for (var key in eventMap) { document.addEventListener(key, eventMap[key], false); } @@ -135,15 +145,17 @@ var Slider = React.createClass({ } }, - _getMouseEventMap: function () { + _getMouseEventMap: function() { return { - 'mousemove': this._onMouseMove, - 'mouseup': this._onMouseUp - } + mousemove: this._onMouseMove, + mouseup: this._onMouseUp + }; }, - _start: function (position) { - if (document.activeElement) document.activeElement.blur(); + _start: function(position) { + if (document.activeElement) { + document.activeElement.blur(); + } this._triggerEvents('onBeforeChange'); @@ -153,17 +165,17 @@ var Slider = React.createClass({ }); }, - _end: function (eventMap) { + _end: function(eventMap) { this._removeEventHandles(eventMap); this.setState(this._triggerEvents.bind(this, 'onAfterChange')); }, - _onMouseUp: function () { + _onMouseUp: function() { this._end(this._getMouseEventMap()); }, - _onMouseMove: function (e) { - var position = e['pageX']; + _onMouseMove: function(e) { + var position = e.pageX; var props = this.props; var state = this.state; @@ -183,33 +195,37 @@ var Slider = React.createClass({ } }, - handleResize: function () { + handleResize: function() { var slider = this.refs.slider.getDOMNode(); var rect = slider.getBoundingClientRect(); - var sliderMin = rect['left']; - var sliderMax = rect['right']; + var sliderMin = rect.left; + var sliderMax = rect.right; this.setState({ - upperBound: slider['clientWidth'], + upperBound: slider.clientWidth, sliderLength: Math.abs(sliderMax - sliderMin), sliderStart: sliderMin }); }, - handleMouseDown: function () { - return function (e) { - if (this.props.disabled) return; - var position = e['pageX']; + handleMouseDown: function() { + return function(e) { + if (this.props.disabled) { + return; + } + var position = e.pageX; this._start(position); this._addEventHandles(this._getMouseEventMap()); pauseEvent(e); }.bind(this); }, - handleSliderMouseDown: function (e) { - if (this.props.disabled) return; - var position = e['pageX']; - this._calValueByPos(position, function () { + handleSliderMouseDown: function(e) { + if (this.props.disabled) { + return; + } + var position = e.pageX; + this._calValueByPos(position, function() { this._triggerEvents('onChange'); this._start(position); this._addEventHandles(this._getMouseEventMap()); @@ -217,18 +233,18 @@ var Slider = React.createClass({ pauseEvent(e); }, - renderSteps: function () { + renderSteps: function() { var props = this.props; var marksLen = props.marks.length; - var stepNum = marksLen> 0 ? marksLen : Math.floor((props.max-props.min)/props.step)+1; - var unit = this.state.sliderLength / (stepNum-1); + var stepNum = marksLen > 0 ? marksLen : Math.floor((props.max - props.min) / props.step) + 1; + var unit = this.state.sliderLength / (stepNum - 1); var stepClassName = props.className + '-step'; var elements = []; - for(var i=0; i @@ -245,18 +261,18 @@ var Slider = React.createClass({ renderMark: function(i) { var marks = this.props.marks; var marksLen = marks.length; - var unit = this.state.sliderLength / (marksLen-1); - var offset = unit*i; + var unit = this.state.sliderLength / (marksLen - 1); + var offset = unit * i; var style = { - width: (unit/2).toFixed(5) + 'px' + width: (unit / 2).toFixed(5) + 'px' }; - if(i===(marksLen-1)) { - style['right'] = '0'; - style['width'] = 'auto'; - }else{ - style['left'] = (i>0 ? (offset - (unit/4)).toFixed(5) : offset)+ 'px'; + if (i === (marksLen - 1)) { + style.right = '0'; + style.width = 'auto'; + }else { + style.left = (i > 0 ? (offset - (unit / 4)).toFixed(5) : offset) + 'px'; } var className = this.props.className + '-mark-text '; @@ -269,7 +285,7 @@ var Slider = React.createClass({ var marks = this.props.marks; var marksLen = marks.length; var elements = []; - for(var i=0; i1 || props.marks.length>0) ? this.renderSteps() : null; - var sliderMarks = (props.marks.length>0) ? this.renderMarks() : null; + var steps = (props.step > 1 || props.marks.length > 0) ? this.renderSteps() : null; + var sliderMarks = (props.marks.length > 0) ? this.renderMarks() : null; var sliderClassName = props.className + (props.disabled ? ' '+props.className+ '-disabled' : ''); From f8108e66f45f5618e3e657def64e2ce2db47432e Mon Sep 17 00:00:00 2001 From: Emma Date: Sun, 19 Apr 2015 16:41:39 +0800 Subject: [PATCH 3/4] Update README.md --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index 76cd0a077..728552aff 100644 --- a/README.md +++ b/README.md @@ -54,6 +54,7 @@ slider ui component for react var Rcslider = require('rc-slider'); var React = require('react'); React.render(, container); +``` ## API From d9916055af4a87097c684c2ca98559fac7fc850e Mon Sep 17 00:00:00 2001 From: simaQ Date: Sun, 19 Apr 2015 16:47:07 +0800 Subject: [PATCH 4/4] update README.md --- README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 728552aff..7334a994e 100644 --- a/README.md +++ b/README.md @@ -130,17 +130,17 @@ npm start ## Example -http://localhost:8088/examples/ +http://localhost:8000/examples/ online example: http://react-component.github.io/slider/build/examples/ ## Test Case -http://localhost:8088/tests/runner.html?coverage +http://localhost:8000/tests/runner.html?coverage ## Coverage -http://localhost:8088/node_modules/rc-server/node_modules/node-jscover/lib/front-end/jscoverage.html?w=http://localhost:8088/tests/runner.html?coverage +http://localhost:8000/node_modules/rc-server/node_modules/node-jscover/lib/front-end/jscoverage.html?w=http://localhost:8088/tests/runner.html?coverage ## License