From f7352312079c95cff10cacf23bdc41ce00f25e72 Mon Sep 17 00:00:00 2001 From: Ilya Oleshko Date: Tue, 13 Aug 2019 14:21:38 +0300 Subject: [PATCH] web: Components: Added ability to adjust height of DropDown component. Added for Components react-window library. Fixed DropDown readme. --- web/ASC.Web.Client/yarn.lock | 40 ++++++- web/ASC.Web.Components/package.json | 1 + .../src/components/drop-down/index.js | 107 ++++++++++++++++-- web/ASC.Web.Components/yarn.lock | 10 +- .../stories/drop-down/base/README.md | 3 +- 5 files changed, 146 insertions(+), 15 deletions(-) diff --git a/web/ASC.Web.Client/yarn.lock b/web/ASC.Web.Client/yarn.lock index 6b2b0d2d6d..5d9bfb8c9a 100644 --- a/web/ASC.Web.Client/yarn.lock +++ b/web/ASC.Web.Client/yarn.lock @@ -1871,10 +1871,12 @@ asap@~2.0.3, asap@~2.0.6: postcss "^7.0.16" prop-types "^15.7.2" rc-tree "^2.1.0" + react-autosize-textarea "^7.0.0" react-custom-scrollbars "^4.2.1" react-datepicker "^2.7.0" react-lifecycles-compat "^3.0.4" react-toastify "^5.3.2" + react-window "^1.8.5" reactstrap "^8.0.0" styled-components "^4.3.2" @@ -1965,6 +1967,11 @@ autoprefixer@^9.4.9: postcss "^7.0.17" postcss-value-parser "^4.0.0" +autosize@^4.0.2: + version "4.0.2" + resolved "https://registry.yarnpkg.com/autosize/-/autosize-4.0.2.tgz#073cfd07c8bf45da4b9fd153437f5bafbba1e4c9" + integrity sha512-jnSyH2d+qdfPGpWlcuhGiHmqBJ6g3X+8T+iRwFrHPLVcdoGJE/x6Qicm6aDHfTsbgZKxyV8UU/YB2p4cjKDRRA== + aws-sign2@~0.7.0: version "0.7.0" resolved "https://registry.yarnpkg.com/aws-sign2/-/aws-sign2-0.7.0.tgz#b46e890934a9591f2d2f6f86d7e6a9f1b3fe76a8" @@ -2860,6 +2867,11 @@ compression@^1.5.2: safe-buffer "5.1.2" vary "~1.1.2" +computed-style@~0.1.3: + version "0.1.4" + resolved "https://registry.yarnpkg.com/computed-style/-/computed-style-0.1.4.tgz#7f344fd8584b2e425bedca4a1afc0e300bb05d74" + integrity sha1-fzRP2FhLLkJb7cpKGvwOMAuwXXQ= + concat-map@0.0.1: version "0.0.1" resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" @@ -6345,6 +6357,13 @@ levn@^0.3.0, levn@~0.3.0: prelude-ls "~1.1.2" type-check "~0.3.2" +line-height@^0.3.1: + version "0.3.1" + resolved "https://registry.yarnpkg.com/line-height/-/line-height-0.3.1.tgz#4b1205edde182872a5efa3c8f620b3187a9c54c9" + integrity sha1-SxIF7d4YKHKl76PI9iCzGHqcVMk= + dependencies: + computed-style "~0.1.3" + load-json-file@^1.0.0: version "1.1.0" resolved "https://registry.yarnpkg.com/load-json-file/-/load-json-file-1.1.0.tgz#956905708d58b4bab4c2261b04f59f31c99374c0" @@ -6625,7 +6644,7 @@ mem@^4.0.0: mimic-fn "^2.0.0" p-is-promise "^2.0.0" -memoize-one@^5.0.0: +"memoize-one@>=3.1.1 <6", memoize-one@^5.0.0: version "5.0.5" resolved "https://registry.yarnpkg.com/memoize-one/-/memoize-one-5.0.5.tgz#8cd3809555723a07684afafcd6f756072ac75d7e" integrity sha512-ey6EpYv0tEaIbM/nTDOpHciXUvd+ackQrJgEzBwemhZZIWZjcyodqEcrmqDy2BKRTM3a65kKBV4WtLXJDt26SQ== @@ -8473,7 +8492,7 @@ prompts@^2.0.1: kleur "^3.0.2" sisteransi "^1.0.0" -prop-types@15.x, prop-types@^15.5.10, prop-types@^15.5.4, prop-types@^15.5.8, prop-types@^15.6.0, prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: +prop-types@15.x, prop-types@^15.5.10, prop-types@^15.5.4, prop-types@^15.5.6, prop-types@^15.5.8, prop-types@^15.6.0, prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: version "15.7.2" resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.7.2.tgz#52c41e75b8c87e72b9d9360e0206b99dcbffa6c5" integrity sha512-8QQikdH7//R2vurIJSutZ1smHYTcLpRWEOlHnzcWHmBYrOGUysKwSsrC89BCiFj3CbrfJ/nXFdJepOVrY1GCHQ== @@ -8683,6 +8702,15 @@ react-app-polyfill@^1.0.1: regenerator-runtime "0.13.2" whatwg-fetch "3.0.0" +react-autosize-textarea@^7.0.0: + version "7.0.0" + resolved "https://registry.yarnpkg.com/react-autosize-textarea/-/react-autosize-textarea-7.0.0.tgz#4f633e4238de7ba73c1da8fdc307353c50f1c5ab" + integrity sha512-rGQLpGUaELvzy3NKzp0kkcppaUtZTptsyR0PGuLotaJDjwRbT0DpD000yCzETpXseJQ/eMsyVGDDHXjXP93u8w== + dependencies: + autosize "^4.0.2" + line-height "^0.3.1" + prop-types "^15.5.6" + react-custom-scrollbars@^4.2.1: version "4.2.1" resolved "https://registry.yarnpkg.com/react-custom-scrollbars/-/react-custom-scrollbars-4.2.1.tgz#830fd9502927e97e8a78c2086813899b2a8b66db" @@ -8905,6 +8933,14 @@ react-transition-group@^2.3.1, react-transition-group@^2.6.1: prop-types "^15.6.2" react-lifecycles-compat "^3.0.4" +react-window@^1.8.5: + version "1.8.5" + resolved "https://registry.yarnpkg.com/react-window/-/react-window-1.8.5.tgz#a56b39307e79979721021f5d06a67742ecca52d1" + integrity sha512-HeTwlNa37AFa8MDZFZOKcNEkuF2YflA0hpGPiTT9vR7OawEt+GZbfM6wqkBahD3D3pUjIabQYzsnY/BSJbgq6Q== + dependencies: + "@babel/runtime" "^7.0.0" + memoize-one ">=3.1.1 <6" + react@^16.8.6: version "16.8.6" resolved "https://registry.yarnpkg.com/react/-/react-16.8.6.tgz#ad6c3a9614fd3a4e9ef51117f54d888da01f2bbe" diff --git a/web/ASC.Web.Components/package.json b/web/ASC.Web.Components/package.json index 88f9188816..ac468e2e6a 100644 --- a/web/ASC.Web.Components/package.json +++ b/web/ASC.Web.Components/package.json @@ -37,6 +37,7 @@ "react-datepicker": "^2.7.0", "react-lifecycles-compat": "^3.0.4", "react-toastify": "^5.3.2", + "react-window": "^1.8.5", "reactstrap": "^8.0.0", "styled-components": "^4.3.2" }, diff --git a/web/ASC.Web.Components/src/components/drop-down/index.js b/web/ASC.Web.Components/src/components/drop-down/index.js index 055bbf6508..fcd07fad77 100644 --- a/web/ASC.Web.Components/src/components/drop-down/index.js +++ b/web/ASC.Web.Components/src/components/drop-down/index.js @@ -1,6 +1,9 @@ -import React from 'react' +import React, { memo, useCallback } from 'react' import styled, { css } from 'styled-components' import PropTypes from 'prop-types' +import Scrollbar from '../scrollbar' +import DropDownItem from '../drop-down-item' +import { FixedSizeList } from "react-window" const StyledDropdown = styled.div` font-family: 'Open Sans',sans-serif,Arial; @@ -9,7 +12,7 @@ const StyledDropdown = styled.div` font-size: 13px; ${props => props.maxHeight && ` - max-height: ${props.maxHeight}; + max-height: ${props.maxHeight}px; overflow-y: auto; `} @@ -42,30 +45,112 @@ const Arrow = styled.div` background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M9.27954 1.12012C10.8122 -0.295972 13.1759 -0.295971 14.7086 1.12012L18.8406 4.93793C19.5796 5.62078 20.5489 6 21.5551 6H24H0H2.43299C3.4392 6 4.40845 5.62077 5.1475 4.93793L9.27954 1.12012Z' fill='%23206FA4'/%3E%3C/svg%3E"); `; -const DropDown = React.memo(props => { - //console.log("DropDown render"); +const CustomScrollbars = ({ onScroll, forwardedRef, style, children }) => { + const refSetter = useCallback(scrollbarsRef => { + if (scrollbarsRef) { + forwardedRef(scrollbarsRef.view); + } else { + forwardedRef(null); + } + }, [forwardedRef]); + return ( - - {props.withArrow && } - {props.children} - + + {children} + + ); +}; + +const CustomScrollbarsVirtualList = React.forwardRef((props, ref) => ( + +)); + +const Row = memo(({ data, index, style }) => { + const option = data[index]; + + return ( + ); }); +class DropDown extends React.PureComponent { + + constructor(props) { + super(props); + + this.state = { + width: 100 + }; + + this.dropDown = React.createRef(); + }; + + setDropDownWidthState = () => { + if (this.dropDown.current) { + this.setState({ + width: this.dropDown.current.offsetWidth + }); + } + } + + componentDidMount () { + this.setDropDownWidthState(); + }; + + componentDidUpdate(prevProps) { + if (this.props.opened !== prevProps.opened || this.props.isOpen !== prevProps.isOpen) { + this.setDropDownWidthState(); + } + }; + + render() { + const {maxHeight, withArrow, directionX, children} = this.props; + const dropDownMaxHeightProp = maxHeight ? { height: maxHeight + 'px' } : {}; + //console.log("DropDown render"); + return ( + + {withArrow && } + {maxHeight + ? + {Row} + + : children} + + ); + } +}; + DropDown.propTypes = { directionX: PropTypes.oneOf(['left', 'right']), directionY: PropTypes.oneOf(['bottom', 'top']), withArrow: PropTypes.bool, manualWidth: PropTypes.string, manualY: PropTypes.string, - maxHeight: PropTypes.string + maxHeight: PropTypes.number }; DropDown.defaultProps = { directionX: 'left', directionY: 'bottom', - withArrow: false, - maxHeight: null + withArrow: false }; export default DropDown \ No newline at end of file diff --git a/web/ASC.Web.Components/yarn.lock b/web/ASC.Web.Components/yarn.lock index 145c9a0659..ebbd85ce3b 100644 --- a/web/ASC.Web.Components/yarn.lock +++ b/web/ASC.Web.Components/yarn.lock @@ -5181,7 +5181,7 @@ mem@^4.0.0: mimic-fn "^2.0.0" p-is-promise "^2.0.0" -memoize-one@^5.0.0: +"memoize-one@>=3.1.1 <6", memoize-one@^5.0.0: version "5.0.5" resolved "https://registry.yarnpkg.com/memoize-one/-/memoize-one-5.0.5.tgz#8cd3809555723a07684afafcd6f756072ac75d7e" integrity sha512-ey6EpYv0tEaIbM/nTDOpHciXUvd+ackQrJgEzBwemhZZIWZjcyodqEcrmqDy2BKRTM3a65kKBV4WtLXJDt26SQ== @@ -6794,6 +6794,14 @@ react-value@0.2.0: resolved "https://registry.yarnpkg.com/react-value/-/react-value-0.2.0.tgz#04d6e3351add34e9365d4597f207e2a13ba85564" integrity sha512-geq4OA3sksC3AyZQ6SmkpoKCVEfXt1kKjylSf5XUzYAR5kBHBfOkEnS+9gpxuHbpMAlIBFobToirkxF5pxiZeQ== +react-window@^1.8.5: + version "1.8.5" + resolved "https://registry.yarnpkg.com/react-window/-/react-window-1.8.5.tgz#a56b39307e79979721021f5d06a67742ecca52d1" + integrity sha512-HeTwlNa37AFa8MDZFZOKcNEkuF2YflA0hpGPiTT9vR7OawEt+GZbfM6wqkBahD3D3pUjIabQYzsnY/BSJbgq6Q== + dependencies: + "@babel/runtime" "^7.0.0" + memoize-one ">=3.1.1 <6" + react@16.8.6: version "16.8.6" resolved "https://registry.yarnpkg.com/react/-/react-16.8.6.tgz#ad6c3a9614fd3a4e9ef51117f54d888da01f2bbe" diff --git a/web/ASC.Web.Storybook/stories/drop-down/base/README.md b/web/ASC.Web.Storybook/stories/drop-down/base/README.md index c458be6222..c3a094fd30 100644 --- a/web/ASC.Web.Storybook/stories/drop-down/base/README.md +++ b/web/ASC.Web.Storybook/stories/drop-down/base/README.md @@ -24,4 +24,5 @@ Is a dropdown with any number of action | `directionX` | `oneOf` | - | `left`, `right` | `left` | Sets the opening direction relative to the parent | | `directionY` | `oneOf` | - | `top`, `bottom` | `bottom` | Sets the opening direction relative to the parent | | `manualWidth` | `string` | - | - | - | Required if you need to specify the exact width of the component, for example 100%| -| `manualTop` | `string` | - | - | - | Required if you need to specify the exact distance from the parent component| \ No newline at end of file +| `manualY` | `string` | - | - | - | Required if you need to specify the exact distance from the parent component| +| `maxHeight` | `number` | - | - | - | Required if the scrollbar is displayed | \ No newline at end of file