gui-one-nutui-react-taro
Version:
京东风格的轻量级移动端 React 组件库,支持一套代码生成 H5 和小程序
271 lines (270 loc) • 10.5 kB
JavaScript
import _toConsumableArray from "@babel/runtime/helpers/toConsumableArray";
import _slicedToArray from "@babel/runtime/helpers/slicedToArray";
import _defineProperty from "@babel/runtime/helpers/defineProperty";
import _objectWithoutProperties from "@babel/runtime/helpers/objectWithoutProperties";
var _excluded = ["height", "acceptKey", "indexList", "isSticky", "spaceHeight", "titleHeight", "className", "onClickItem", "onClickIndex", "children"];
function ownKeys(object, enumerableOnly) { var keys = Object.keys(object); if (Object.getOwnPropertySymbols) { var symbols = Object.getOwnPropertySymbols(object); enumerableOnly && (symbols = symbols.filter(function (sym) { return Object.getOwnPropertyDescriptor(object, sym).enumerable; })), keys.push.apply(keys, symbols); } return keys; }
function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = null != arguments[i] ? arguments[i] : {}; i % 2 ? ownKeys(Object(source), !0).forEach(function (key) { _defineProperty(target, key, source[key]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(target, Object.getOwnPropertyDescriptors(source)) : ownKeys(Object(source)).forEach(function (key) { Object.defineProperty(target, key, Object.getOwnPropertyDescriptor(source, key)); }); } return target; }
import React__default, { createContext, useRef, useState, useEffect } from 'react';
import Taro from '@tarojs/taro';
import { ScrollView } from '@tarojs/components';
import { c as cn } from './bem-893ad28d.js';
var elevatorContext = createContext({});
var defaultProps = {
height: '200px',
acceptKey: 'title',
indexList: [],
isSticky: false,
spaceHeight: 23,
titleHeight: 35,
className: 'weapp-elevator'
};
var Elevator = function Elevator(props) {
var _defaultProps$props = _objectSpread(_objectSpread({}, defaultProps), props),
height = _defaultProps$props.height,
acceptKey = _defaultProps$props.acceptKey,
indexList = _defaultProps$props.indexList,
isSticky = _defaultProps$props.isSticky,
spaceHeight = _defaultProps$props.spaceHeight,
titleHeight = _defaultProps$props.titleHeight,
className = _defaultProps$props.className,
onClickItem = _defaultProps$props.onClickItem,
onClickIndex = _defaultProps$props.onClickIndex,
children = _defaultProps$props.children,
rest = _objectWithoutProperties(_defaultProps$props, _excluded);
var b = cn('elevator');
var listview = useRef(null);
var initData = {
anchorIndex: 0,
listHeight: [],
listGroup: [],
scrollY: 0,
diff: -1,
fixedTop: 0
};
var touchState = useRef({
y1: 0,
y2: 0
});
var _useState = useState(0),
_useState2 = _slicedToArray(_useState, 2),
scrollY = _useState2[0],
setScrollY = _useState2[1];
var _useState3 = useState({}),
_useState4 = _slicedToArray(_useState3, 2),
currentData = _useState4[0],
setCurrentData = _useState4[1];
var _useState5 = useState(''),
_useState6 = _slicedToArray(_useState5, 2),
currentKey = _useState6[0],
setCurrentKey = _useState6[1];
var _useState7 = useState(0),
_useState8 = _slicedToArray(_useState7, 2),
currentIndex = _useState8[0],
setCurrentIndex = _useState8[1];
var _useState9 = useState(0),
_useState10 = _slicedToArray(_useState9, 2),
codeIndex = _useState10[0],
setCodeIndex = _useState10[1];
var _useState11 = useState(false),
_useState12 = _slicedToArray(_useState11, 2),
scrollStart = _useState12[0],
setScrollStart = _useState12[1];
var state = useRef(initData);
var _useState13 = useState(0),
_useState14 = _slicedToArray(_useState13, 2),
scrollTop = _useState14[0],
setScrollTop = _useState14[1];
// 重置滚动参数
var resetScrollState = function resetScrollState() {
setScrollStart(false);
};
var clientHeight = function clientHeight() {
return listview.current ? listview.current.clientHeight : 0;
};
var getData = function getData(el) {
if (!el.dataset.index) {
return '0';
}
return el.dataset.index;
};
var calculateHeight = function calculateHeight() {
var height = 0;
state.current.listHeight.push(height);
for (var i = 0; i < state.current.listGroup.length; i++) {
var query = Taro.createSelectorQuery();
query.selectAll(".".concat(className, " .elevator__item__").concat(i)).boundingClientRect();
// eslint-disable-next-line no-loop-func
query.exec(function (res) {
if (res[0][0]) height += res[0][0].height;
// console.log(res, res[0][0].height, height, 'res')
state.current.listHeight.push(height);
});
}
};
var scrollTo = function scrollTo(index) {
if (!index && index !== 0) {
return;
}
if (!state.current.listHeight.length) {
calculateHeight();
}
var cacheIndex = index;
if (index < 0) {
cacheIndex = 0;
}
if (index > state.current.listHeight.length - 2) {
cacheIndex = state.current.listHeight.length - 2;
}
setCodeIndex(cacheIndex);
setScrollTop(state.current.listHeight[cacheIndex]);
};
var touchMove = function touchMove(e) {
var firstTouch = e.touches[0];
touchState.current.y2 = firstTouch.pageY;
var delta = (touchState.current.y2 - touchState.current.y1) / spaceHeight || 0;
var cacheIndex = state.current.anchorIndex + Math.floor(delta);
setCodeIndex(cacheIndex);
scrollTo(cacheIndex);
};
var touchEnd = function touchEnd() {
resetScrollState();
};
var touchStart = function touchStart(e) {
setScrollStart(true);
var index = Number(getData(e.target));
var firstTouch = e.touches[0];
touchState.current.y1 = firstTouch.pageY;
state.current.anchorIndex = +index;
setCodeIndex(function (codeIndex) {
return codeIndex + index;
});
scrollTo(index);
};
var handleClickItem = function handleClickItem(key, item) {
onClickItem && onClickItem(key, item);
setCurrentData(item);
setCurrentKey(key);
};
var handleClickIndex = function handleClickIndex(key) {
onClickIndex && onClickIndex(key);
};
var setListGroup = function setListGroup() {
if (listview.current) {
Taro.createSelectorQuery().selectAll(".".concat(className, " .nut-elevator__list__item")).node(function (el) {
state.current.listGroup = _toConsumableArray(Object.keys(el));
calculateHeight();
}).exec();
}
};
var listViewScroll = function listViewScroll(e) {
var listHeight = state.current.listHeight;
if (!listHeight.length) {
calculateHeight();
}
var target = e.target;
var scrollTop = target.scrollTop;
state.current.scrollY = Math.floor(scrollTop);
setScrollY(scrollTop);
for (var i = 0; i < listHeight.length - 1; i++) {
var height1 = listHeight[i];
var height2 = listHeight[i + 1];
if (state.current.scrollY >= height1 && state.current.scrollY < height2) {
setCurrentIndex(i);
state.current.diff = height2 - state.current.scrollY;
return;
}
}
setCurrentIndex(listHeight.length - 2);
};
useEffect(function () {
if (listview.current) {
Taro.nextTick(function () {
setListGroup();
});
}
}, [listview]);
useEffect(function () {
var _state$current = state.current,
listHeight = _state$current.listHeight,
diff = _state$current.diff,
scrollY = _state$current.scrollY;
var fixedTop = diff > 0 && diff < titleHeight ? diff - titleHeight : 0;
if (scrollY + clientHeight() === listHeight[listHeight.length - 1]) {
if (fixedTop !== 0) {
fixedTop = 0;
}
}
if (state.current.fixedTop === fixedTop) return;
state.current.fixedTop = fixedTop;
}, [state.current.diff, titleHeight]);
return React__default.createElement("div", _objectSpread({
className: "".concat(b(), " ").concat(className, " ")
}, rest), isSticky && scrollY > 0 ? React__default.createElement("div", {
className: b('list__fixed')
}, React__default.createElement("span", {
className: "fixed-title"
}, indexList[currentIndex][acceptKey])) : null, React__default.createElement("div", {
className: b('list'),
style: {
height: Number.isNaN(+height) ? height : "".concat(height, "px")
}
}, React__default.createElement(ScrollView, {
scrollTop: scrollTop,
scrollY: true,
className: b('list__inner'),
ref: listview,
onScroll: listViewScroll
}, indexList.map(function (item, idx) {
return React__default.createElement("div", {
className: "".concat(b('list__item'), " elevator__item__").concat(idx),
key: idx
}, React__default.createElement("div", {
className: b('list__item__code')
}, item[acceptKey]), React__default.createElement(React__default.Fragment, null, item.list.map(function (subitem) {
return React__default.createElement("div", {
className: b('list__item__name', {
highcolor: currentData.id === subitem.id && currentKey === item[acceptKey]
}),
key: subitem.id,
onClick: function onClick() {
return handleClickItem(item[acceptKey], subitem);
}
}, children ? React__default.createElement(React__default.Fragment, null, React__default.createElement(elevatorContext.Provider, {
value: subitem
}, children)) : subitem.name);
})));
}))), indexList.length && scrollStart ? React__default.createElement("div", {
className: b('code--current', {
current: true
})
}, indexList[codeIndex][acceptKey]) : null, React__default.createElement("div", {
className: b('bars')
}, React__default.createElement("div", {
className: b('bars__inner'),
onTouchStart: function onTouchStart(event) {
return touchStart(event);
},
onTouchMove: function onTouchMove(event) {
return touchMove(event);
},
onTouchEnd: touchEnd,
style: {
touchAction: 'pan-y'
}
}, indexList.map(function (item, index) {
return React__default.createElement("div", {
className: "".concat(b('bars__inner__item', {
active: item[acceptKey] === indexList[currentIndex][acceptKey]
}), " "),
"data-index": index,
key: index,
onClick: function onClick() {
return handleClickIndex(item[acceptKey]);
}
}, item[acceptKey]);
}))));
};
Elevator.defaultProps = defaultProps;
Elevator.displayName = 'NutElevator';
export { Elevator as E };