taro-hooks
Version:
为 Taro 而设计的 Hooks Library
118 lines • 3.51 kB
JavaScript
import { startDeviceMotionListening, stopDeviceMotionListening, onDeviceMotionChange, offDeviceMotionChange } from '@tarojs/taro';
import { useRef, useEffect, useState } from '@taro-hooks/core';
import usePromise from '../usePromise';
import { generateGeneralFail } from '../utils/tool';
function _await(value, then, direct) {
if (direct) {
return then ? then(value) : value;
}
if (!value || !value.then) {
value = Promise.resolve(value);
}
return then ? value.then(then) : value;
}
function _catch(body, recover) {
try {
var result = body();
} catch (e) {
return recover(e);
}
if (result && result.then) {
return result.then(void 0, recover);
}
return result;
}
function _async(f) {
return function () {
for (var args = [], i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
}
try {
return Promise.resolve(f.apply(this, args));
} catch (e) {
return Promise.reject(e);
}
};
}
function useMotion(autoListen, interval) {
var _useState = useState(),
motion = _useState[0],
setMotion = _useState[1];
var listenStatus = useRef(false);
var callbackQueen = useRef([]);
var privateListener = function privateListener(callbackMotion) {
setMotion(callbackMotion);
callbackQueen.current.forEach(function (callback) {
return callback == null ? void 0 : callback(callbackMotion);
});
};
var add = function add(callback) {
if (!listenStatus.current) {
onDeviceMotionChange(privateListener);
listenStatus.current = true;
}
callbackQueen.current = [].concat(callbackQueen.current, [callback]);
return Promise.resolve(generateGeneralFail('add', 'success'));
};
var off = function off(callback) {
if (callbackQueen.current.length === 1) {
offDeviceMotionChange(privateListener);
listenStatus.current = false;
}
callbackQueen.current = callbackQueen.current.filter(function (queenCallback) {
return queenCallback === callback;
});
return Promise.resolve(generateGeneralFail('off', 'success'));
};
var startAsync = usePromise(startDeviceMotionListening);
var start = function start(optionInterval) {
var _ref;
var option = {
interval: (_ref = optionInterval != null ? optionInterval : interval) != null ? _ref : 'normal'
};
return startAsync(option).then(function () {
return true;
}, function () {
return false;
});
};
var stopAsync = usePromise(stopDeviceMotionListening);
var stop = function stop() {
return stopAsync().then(function () {
var _callbackQueen$curren;
// clear callbackQueen
(_callbackQueen$curren = callbackQueen.current) == null ? void 0 : _callbackQueen$curren.map == null ? void 0 : _callbackQueen$curren.map(function (callback) {
return off(callback);
});
return true;
});
};
var manualListenMotion = _async(function () {
return _catch(function () {
return _await(start(interval), function (result) {
if (result && !listenStatus.current) {
add(privateListener);
}
});
}, function () {
return generateGeneralFail('manualListenMotion');
});
});
useEffect(function () {
if (autoListen) {
manualListenMotion();
}
return function () {
if (autoListen) {
stop();
}
};
}, [autoListen, interval]);
return [motion, {
start: start,
stop: stop,
add: add,
off: off
}];
}
export default useMotion;