提交 f0ec1e1b 编写于 作者: fxy060608's avatar fxy060608

refactor(v3): createSelectorQuery

上级 a7367daa
......@@ -7140,6 +7140,129 @@ var serviceContext = (function () {
}
}
const callbacks$1 = {};
function createCallbacks (namespace) {
let scopedCallbacks = callbacks$1[namespace];
if (!scopedCallbacks) {
scopedCallbacks = {
id: 1,
callbacks: Object.create(null)
};
callbacks$1[namespace] = scopedCallbacks;
}
return {
get (id) {
return scopedCallbacks.callbacks[id]
},
pop (id) {
const callback = scopedCallbacks.callbacks[id];
if (callback) {
delete scopedCallbacks.callbacks[id];
}
return callback
},
push (callback) {
const id = scopedCallbacks.id++;
scopedCallbacks.callbacks[id] = callback;
return id
}
}
}
const requestComponentInfoCallbacks = createCallbacks('requestComponentInfo');
function requestComponentInfo (pageInstance, queue, callback) {
UniServiceJSBridge.publishHandler('requestComponentInfo', {
reqId: requestComponentInfoCallbacks.push(callback),
reqs: queue
}, pageInstance.$page.id);
}
function parseDataset (attr) {
const dataset = {};
Object.keys(attr || {}).forEach(key => {
if (key.indexOf('data') === 0) {
let str = key.replace('data', '');
str = str.charAt(0).toLowerCase() + str.slice(1);
dataset[str] = attr[key];
}
});
return dataset
}
function findAttrs (ids, elm, result) {
let nodes = elm.children;
if (!Array.isArray(nodes)) {
return false
}
for (let i = 0; i < nodes.length; i++) {
let node = nodes[i];
if (node.attr) {
let index = ids.indexOf(node.attr.id);
if (index >= 0) {
result[index] = {
id: ids[index],
ref: node.ref,
dataset: parseDataset(node.attr)
};
if (ids.length === 1) {
break
}
}
}
if (node.children) {
findAttrs(ids, node, result);
}
}
}
function getSelectors (queue) {
let ids = [];
for (let i = 0; i < queue.length; i++) {
const selector = queue[i].selector;
if (selector.indexOf('#') === 0) {
ids.push(selector.substring(1));
}
}
return ids
}
function getComponentRectAll (dom, attrs, index, result, callback) {
const attr = attrs[index];
dom.getComponentRect(attr.ref, option => {
option.size.id = attr.id;
option.size.dataset = attr.dataset;
result.push(option.size);
index += 1;
if (index < attrs.length) {
getComponentRectAll(dom, attrs, index, result, callback);
} else {
callback(result);
}
});
}
function requestComponentInfo$1 (pageInstance, queue, callback) {
// TODO 重构,逻辑不对,queue 里的每一项可能有单独的作用域查找(即 component)
const vm = pageInstance.$vm;
const dom = vm._$weex.requireModule('dom');
const selectors = getSelectors(queue);
let outAttrs = new Array(selectors.length);
findAttrs(selectors, vm.$el, outAttrs);
getComponentRectAll(dom, outAttrs, 0, [], (result) => {
callback(result);
});
}
function requestComponentInfo$2 (pageInstance, queue, callback) {
pageInstance.$page.meta.isNVue
? requestComponentInfo$1(pageInstance, queue, callback)
: requestComponentInfo(pageInstance, queue, callback);
}
var api = /*#__PURE__*/Object.freeze({
......@@ -7257,7 +7380,8 @@ var serviceContext = (function () {
setTabBarItem: setTabBarItem$2,
setTabBarStyle: setTabBarStyle$2,
hideTabBar: hideTabBar$2,
showTabBar: showTabBar$2
showTabBar: showTabBar$2,
requestComponentInfo: requestComponentInfo$2
});
const Emitter = new Vue();
......@@ -7482,9 +7606,9 @@ var serviceContext = (function () {
'error',
'waiting'
];
const callbacks$1 = {};
const callbacks$2 = {};
eventNames$1.forEach(name => {
callbacks$1[name] = [];
callbacks$2[name] = [];
});
const props$1 = [
......@@ -7548,7 +7672,7 @@ var serviceContext = (function () {
errMsg,
errCode
}) => {
callbacks$1[state].forEach(callback => {
callbacks$2[state].forEach(callback => {
if (typeof callback === 'function') {
callback(state === 'error' ? {
errMsg,
......@@ -7600,7 +7724,7 @@ var serviceContext = (function () {
eventNames$1.forEach(item => {
const name = item[0].toUpperCase() + item.substr(1);
BackgroundAudioManager.prototype[`on${name}`] = function (callback) {
callbacks$1[item].push(callback);
callbacks$2[item].push(callback);
};
});
......@@ -7614,10 +7738,10 @@ var serviceContext = (function () {
getBackgroundAudioManager: getBackgroundAudioManager
});
const callbacks$2 = [];
const callbacks$3 = [];
onMethod('onAccelerometerChange', function (res) {
callbacks$2.forEach(callbackId => {
callbacks$3.forEach(callbackId => {
invoke(callbackId, res);
});
});
......@@ -7629,7 +7753,7 @@ var serviceContext = (function () {
*/
function onAccelerometerChange (callbackId) {
// TODO 当没有 start 时,添加 on 需要主动 start?
callbacks$2.push(callbackId);
callbacks$3.push(callbackId);
if (!isEnable) {
startAccelerometer();
}
......@@ -7684,10 +7808,10 @@ var serviceContext = (function () {
onBLECharacteristicValueChange: onBLECharacteristicValueChange$1
});
const callbacks$3 = [];
const callbacks$4 = [];
onMethod('onCompassChange', function (res) {
callbacks$3.forEach(callbackId => {
callbacks$4.forEach(callbackId => {
invoke(callbackId, res);
});
});
......@@ -7699,7 +7823,7 @@ var serviceContext = (function () {
*/
function onCompassChange (callbackId) {
// TODO 当没有 start 时,添加 on 需要主动 start?
callbacks$3.push(callbackId);
callbacks$4.push(callbackId);
if (!isEnable$1) {
startCompass();
}
......@@ -7730,23 +7854,23 @@ var serviceContext = (function () {
stopCompass: stopCompass
});
const callbacks$4 = [];
const callbacks$5 = [];
onMethod('onNetworkStatusChange', res => {
callbacks$4.forEach(callbackId => {
callbacks$5.forEach(callbackId => {
invoke(callbackId, res);
});
});
function onNetworkStatusChange (callbackId) {
callbacks$4.push(callbackId);
callbacks$5.push(callbackId);
}
var require_context_module_1_9 = /*#__PURE__*/Object.freeze({
onNetworkStatusChange: onNetworkStatusChange
});
const callbacks$5 = {
const callbacks$6 = {
pause: [],
resume: [],
start: [],
......@@ -7760,7 +7884,7 @@ var serviceContext = (function () {
const state = res.state;
delete res.state;
delete res.errMsg;
callbacks$5[state].forEach(callback => {
callbacks$6[state].forEach(callback => {
if (typeof callback === 'function') {
callback(res);
}
......@@ -7768,7 +7892,7 @@ var serviceContext = (function () {
});
}
onError (callback) {
callbacks$5.error.push(callback);
callbacks$6.error.push(callback);
}
onFrameRecorded (callback) {
......@@ -7780,16 +7904,16 @@ var serviceContext = (function () {
}
onPause (callback) {
callbacks$5.pause.push(callback);
callbacks$6.pause.push(callback);
}
onResume (callback) {
callbacks$5.resume.push(callback);
callbacks$6.resume.push(callback);
}
onStart (callback) {
callbacks$5.start.push(callback);
callbacks$6.start.push(callback);
}
onStop (callback) {
callbacks$5.stop.push(callback);
callbacks$6.stop.push(callback);
}
pause () {
invokeMethod('operateRecorder', {
......@@ -8090,7 +8214,7 @@ var serviceContext = (function () {
const socketTasks$1 = Object.create(null);
const socketTasksArray = [];
const callbacks$6 = Object.create(null);
const callbacks$7 = Object.create(null);
onMethod('onSocketTaskStateChange', ({
socketTaskId,
state,
......@@ -8111,8 +8235,8 @@ var serviceContext = (function () {
if (state === 'open') {
socketTask.readyState = socketTask.OPEN;
}
if (socketTask === socketTasksArray[0] && callbacks$6[state]) {
invoke(callbacks$6[state], state === 'message' ? {
if (socketTask === socketTasksArray[0] && callbacks$7[state]) {
invoke(callbacks$7[state], state === 'message' ? {
data
} : {});
}
......@@ -8171,19 +8295,19 @@ var serviceContext = (function () {
}
function onSocketOpen (callbackId) {
callbacks$6.open = callbackId;
callbacks$7.open = callbackId;
}
function onSocketError (callbackId) {
callbacks$6.error = callbackId;
callbacks$7.error = callbackId;
}
function onSocketMessage (callbackId) {
callbacks$6.message = callbackId;
callbacks$7.message = callbackId;
}
function onSocketClose (callbackId) {
callbacks$6.close = callbackId;
callbacks$7.close = callbackId;
}
var require_context_module_1_13 = /*#__PURE__*/Object.freeze({
......@@ -8484,19 +8608,132 @@ var serviceContext = (function () {
createAnimation: createAnimation
});
const callbacks$7 = [];
class NodesRef {
constructor (selectorQuery, component, selector, single) {
this._selectorQuery = selectorQuery;
this._component = component;
this._selector = selector;
this._single = single;
}
boundingClientRect (callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single, {
id: true,
dataset: true,
rect: true,
size: true
},
callback);
return this._selectorQuery
}
fields (fields, callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single,
fields,
callback
);
return this._selectorQuery
}
scrollOffset (callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single, {
id: true,
dataset: true,
scrollOffset: true
},
callback
);
return this._selectorQuery
}
}
class SelectorQuery {
constructor (page) {
this._page = page;
this._queue = [];
this._queueCb = [];
}
exec (callback) {
invokeMethod('requestComponentInfo', this._page, this._queue, res => {
const queueCbs = this._queueCb;
res.forEach((result, index) => {
const queueCb = queueCbs[index];
if (isFn(queueCb)) {
queueCb.call(this, result);
}
});
isFn(callback) && callback.call(this, res);
});
}
['in'] (component) {
// app-plus 平台传递 id
this._component = component._$id || component;
return this
}
select (selector) {
return new NodesRef(this, this._component, selector, true)
}
selectAll (selector) {
return new NodesRef(this, this._component, selector, false)
}
selectViewport () {
return new NodesRef(this, 0, '', true)
}
_push (selector, component, single, fields, callback) {
this._queue.push({
component,
selector,
single,
fields
});
this._queueCb.push(callback);
}
}
function createSelectorQuery (context) {
if (context) {
return new SelectorQuery(context)
}
const pages = getCurrentPages();
const len = pages.length;
if (!len) {
UniServiceJSBridge.emit('onError', 'createSelectorQuery:fail');
}
return new SelectorQuery(pages[len - 1])
}
var require_context_module_1_17 = /*#__PURE__*/Object.freeze({
createSelectorQuery: createSelectorQuery
});
const callbacks$8 = [];
onMethod('onKeyboardHeightChange', res => {
callbacks$7.forEach(callbackId => {
callbacks$8.forEach(callbackId => {
invoke(callbackId, res);
});
});
function onKeyboardHeightChange (callbackId) {
callbacks$7.push(callbackId);
callbacks$8.push(callbackId);
}
var require_context_module_1_17 = /*#__PURE__*/Object.freeze({
var require_context_module_1_18 = /*#__PURE__*/Object.freeze({
onKeyboardHeightChange: onKeyboardHeightChange
});
......@@ -8508,7 +8745,7 @@ var serviceContext = (function () {
return {}
}
var require_context_module_1_18 = /*#__PURE__*/Object.freeze({
var require_context_module_1_19 = /*#__PURE__*/Object.freeze({
pageScrollTo: pageScrollTo$1
});
......@@ -8532,42 +8769,42 @@ var serviceContext = (function () {
const hideTabBarRedDot$1 = removeTabBarBadge$1;
const callbacks$8 = [];
const callbacks$9 = [];
onMethod('onTabBarMidButtonTap', res => {
callbacks$8.forEach(callbackId => {
callbacks$9.forEach(callbackId => {
invoke(callbackId, res);
});
});
function onTabBarMidButtonTap (callbackId) {
callbacks$8.push(callbackId);
callbacks$9.push(callbackId);
}
var require_context_module_1_19 = /*#__PURE__*/Object.freeze({
var require_context_module_1_20 = /*#__PURE__*/Object.freeze({
removeTabBarBadge: removeTabBarBadge$1,
showTabBarRedDot: showTabBarRedDot$1,
hideTabBarRedDot: hideTabBarRedDot$1,
onTabBarMidButtonTap: onTabBarMidButtonTap
});
const callbacks$9 = [];
const callbacks$a = [];
onMethod('onViewDidResize', res => {
callbacks$9.forEach(callbackId => {
callbacks$a.forEach(callbackId => {
invoke(callbackId, res);
});
});
function onWindowResize (callbackId) {
callbacks$9.push(callbackId);
callbacks$a.push(callbackId);
}
function offWindowResize (callbackId) {
// 此处和微信平台一致查询不到去掉最后一个
callbacks$9.splice(callbacks$9.indexOf(callbackId), 1);
callbacks$a.splice(callbacks$a.indexOf(callbackId), 1);
}
var require_context_module_1_20 = /*#__PURE__*/Object.freeze({
var require_context_module_1_21 = /*#__PURE__*/Object.freeze({
onWindowResize: onWindowResize,
offWindowResize: offWindowResize
});
......@@ -8594,10 +8831,11 @@ var serviceContext = (function () {
'./network/upload-file.js': require_context_module_1_14,
'./storage/storage.js': require_context_module_1_15,
'./ui/create-animation.js': require_context_module_1_16,
'./ui/keyboard.js': require_context_module_1_17,
'./ui/page-scroll-to.js': require_context_module_1_18,
'./ui/tab-bar.js': require_context_module_1_19,
'./ui/window.js': require_context_module_1_20,
'./ui/create-selector-query.js': require_context_module_1_17,
'./ui/keyboard.js': require_context_module_1_18,
'./ui/page-scroll-to.js': require_context_module_1_19,
'./ui/tab-bar.js': require_context_module_1_20,
'./ui/window.js': require_context_module_1_21,
};
var req = function req(key) {
......@@ -8635,10 +8873,10 @@ var serviceContext = (function () {
pageIds = [pageIds];
}
const evalJSCode =
`typeof UniViewJSBridge !== 'undefined' && UniViewJSBridge.subscribeHandler("${eventType}",${args})`;
`typeof UniViewJSBridge !== 'undefined' && UniViewJSBridge.subscribeHandler("${eventType}",${args},__PAGE_ID__)`;
pageIds.forEach(id => {
const webview = plus.webview.getWebviewById(String(id));
webview && webview.evalJS(evalJSCode);
webview && webview.evalJS(evalJSCode.replace('__PAGE_ID__', id));
});
}
......@@ -8750,36 +8988,6 @@ var serviceContext = (function () {
on('onWebInvokeAppService', onWebInvokeAppService);
}
const callbacks$a = {};
function createCallbacks (namespace) {
let scopedCallbacks = callbacks$a[namespace];
if (!scopedCallbacks) {
scopedCallbacks = {
id: 1,
callbacks: Object.create(null)
};
callbacks$a[namespace] = scopedCallbacks;
}
return {
get (id) {
return scopedCallbacks.callbacks[id]
},
pop (id) {
const callback = scopedCallbacks.callbacks[id];
if (callback) {
delete scopedCallbacks.callbacks[id];
}
return callback
},
push (callback) {
const id = scopedCallbacks.id++;
scopedCallbacks.callbacks[id] = callback;
return id
}
}
}
function initSubscribe (subscribe, {
getApp,
getCurrentPages
......
......@@ -9929,7 +9929,8 @@ var handleData = (_handleData = {}, _defineProperty(_handleData, _constants__WEB
pageId = _data2[0],
pagePath = _data2[1];
new PageVueComponent({
var page = getCurrentPages()[0];
page.$vm = new PageVueComponent({
mpType: 'page',
pageId: pageId,
pagePath: pagePath
......@@ -12615,10 +12616,26 @@ function getNodeInfo(el, fields) {
return info;
}
function getElm(component, pageVm) {
if (!component) {
return pageVm.$el;
}
if (typeof component === 'string') {
var componentVm = pageVm._$vd.getVm(component);
if (!componentVm) {
throw new Error("Not Found\uFF1APage[".concat(pageVm.$page.id, "][").concat(component, "]"));
}
return componentVm.$el;
}
return component.$el;
}
function getNodesInfo(pageVm, component, selector, single, fields) {
/* eslint-disable no-mixed-operators */
// TODO 判断 component 是否是 _$id,如果是,从 pageVm 中递归查找该组件实例
var $el = component && component.$el || pageVm.$el;
var $el = getElm(component, pageVm);
if (single) {
var node = $el && ($el.matches(selector) ? $el : $el.querySelector(selector));
......@@ -12653,15 +12670,15 @@ function requestComponentInfo(_ref, pageId) {
reqs = _ref.reqs;
var pages = getCurrentPages(); // 跨平台时,View 层也应该实现该方法,举例 App 上,View 层的 getCurrentPages 返回长度为1的当前页面数组
var pageVm = pages.find(function (page) {
var page = pages.find(function (page) {
return page.$page.id === pageId;
});
if (!pageVm) {
// TODO 是否需要 defer
if (!page) {
throw new Error("Not Found\uFF1APage[".concat(pageId, "]"));
}
var pageVm = page.$vm;
var result = [];
reqs.forEach(function (_ref2) {
var component = _ref2.component,
......
import {
isFn
} from 'uni-shared'
import createCallbacks from 'uni-helpers/callbacks'
const requestComponentInfoCallbacks = createCallbacks('requestComponentInfo')
import {
invokeMethod
} from '../../platform'
class NodesRef {
constructor (selectorQuery, component, selector, single) {
......@@ -54,24 +53,15 @@ class NodesRef {
}
}
function requestComponentInfo (pageId, queue, callback) {
const reqId = requestComponentInfoCallbacks.push(callback)
UniServiceJSBridge.publishHandler('requestComponentInfo', {
reqId,
reqs: queue
}, pageId)
}
class SelectorQuery {
constructor (pageId) {
this.pageId = pageId
constructor (page) {
this._page = page
this._queue = []
this._queueCb = []
}
exec (callback) {
requestComponentInfo(this.pageId, this._queue, res => {
invokeMethod('requestComponentInfo', this._page, this._queue, res => {
const queueCbs = this._queueCb
res.forEach((result, index) => {
const queueCb = queueCbs[index]
......@@ -83,9 +73,9 @@ class SelectorQuery {
})
}
['in'] (component) {
// TODO 跨平台,非 h5 平台传递 component._$id
this._component = component
['in'] (component) {
// app-plus 平台传递 id
this._component = component._$id || component
return this
}
......@@ -114,12 +104,12 @@ class SelectorQuery {
export function createSelectorQuery (context) {
if (context) {
return new SelectorQuery(context.$page.id)
return new SelectorQuery(context)
}
const app = getApp()
if (app.$route && app.$route.params.__id__) {
return new SelectorQuery(app.$route.params.__id__)
} else {
const pages = getCurrentPages()
const len = pages.length
if (!len) {
UniServiceJSBridge.emit('onError', 'createSelectorQuery:fail')
}
return new SelectorQuery(pages[len - 1])
}
......@@ -73,10 +73,22 @@ function getNodeInfo (el, fields) {
return info
}
function getElm (component, pageVm) {
if (!component) {
return pageVm.$el
}
if (typeof component === 'string') {
const componentVm = pageVm._$vd.getVm(component)
if (!componentVm) {
throw new Error(`Not Found:Page[${pageVm.$page.id}][${component}]`)
}
return componentVm.$el
}
return component.$el
}
function getNodesInfo (pageVm, component, selector, single, fields) {
/* eslint-disable no-mixed-operators */
// TODO 判断 component 是否是 _$id,如果是,从 pageVm 中递归查找该组件实例
const $el = component && component.$el || pageVm.$el
const $el = getElm(component, pageVm)
if (single) {
const node = $el && ($el.matches(selector) ? $el : $el.querySelector(selector))
if (node) {
......@@ -106,13 +118,14 @@ export function requestComponentInfo ({
}, pageId) {
const pages = getCurrentPages() // 跨平台时,View 层也应该实现该方法,举例 App 上,View 层的 getCurrentPages 返回长度为1的当前页面数组
const pageVm = pages.find(page => page.$page.id === pageId)
const page = pages.find(page => page.$page.id === pageId)
if (!pageVm) {
// TODO 是否需要 defer
if (!page) {
throw new Error(`Not Found:Page[${pageId}]`)
}
const pageVm = page.$vm
const result = []
reqs.forEach(function ({
component,
......
......@@ -2,4 +2,4 @@ export * from './context/live-pusher'
export * from './context/map'
export * from './context/video'
export * from './ui/create-selector-query'
export * from './ui/request-component-info'
import {
isFn
} from 'uni-shared'
class NodesRef {
constructor (selectorQuery, component, selector, single) {
this._selectorQuery = selectorQuery
this._component = component
this._selector = selector
this._single = single
}
boundingClientRect (callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single, {
id: true,
dataset: true,
rect: true,
size: true
},
callback)
return this._selectorQuery
}
fields (fields, callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single,
fields,
callback
)
return this._selectorQuery
}
scrollOffset (callback) {
this._selectorQuery._push(
this._selector,
this._component,
this._single, {
id: true,
dataset: true,
scrollOffset: true
},
callback
)
return this._selectorQuery
}
}
function processDataset (attr) {
const dataset = {}
Object.keys(attr || {}).forEach(key => {
if (key.indexOf('data') === 0) {
let str = key.replace('data', '')
str = str.charAt(0).toLowerCase() + str.slice(1)
dataset[str] = attr[key]
}
})
return dataset
}
function findAttrs (ids, elm, result) {
let nodes = elm.children
if (!Array.isArray(nodes)) {
return false
}
for (let i = 0; i < nodes.length; i++) {
let node = nodes[i]
if (node.attr) {
let index = ids.indexOf(node.attr.id)
if (index >= 0) {
result[index] = {
id: ids[index],
ref: node.ref,
dataset: processDataset(node.attr)
}
if (ids.length === 1) {
break
}
}
}
if (node.children) {
findAttrs(ids, node, result)
}
}
}
function getSelectors (queue) {
let ids = []
for (let i = 0; i < queue.length; i++) {
const selector = queue[i].selector
if (selector.indexOf('#') === 0) {
ids.push(selector.substring(1))
}
}
return ids
}
function getComponentRectAll (dom, attrs, index, result, callback) {
const attr = attrs[index]
dom.getComponentRect(attr.ref, option => {
option.size.id = attr.id
option.size.dataset = attr.dataset
result.push(option.size)
index += 1
if (index < attrs.length) {
getComponentRectAll(dom, attrs, index, result, callback)
} else {
callback(result)
}
})
}
function requestComponentInfo (dom, component, queue, callback) {
const selectors = getSelectors(queue)
let outAttrs = new Array(selectors.length)
findAttrs(selectors, component.$el, outAttrs)
getComponentRectAll(dom, outAttrs, 0, [], (result) => {
callback(result)
})
}
class SelectorQuery {
constructor (pageId) {
this.pageId = pageId
this._queue = []
this._queueCb = []
}
exec (callback) {
if (!this._component) {
return
}
this._dom = this._component._$weex.requireModule('dom')
requestComponentInfo(this._dom, this._component, this._queue, res => {
const queueCbs = this._queueCb
res.forEach((result, index) => {
const queueCb = queueCbs[index]
if (isFn(queueCb)) {
queueCb.call(this, result)
}
})
isFn(callback) && callback.call(this, res)
})
}
['in'] (component) {
if (!component) {
return console.warn('uni.createSelectorQuery 必须传入当前 vm 对象(this)')
}
this._component = component
return this
}
select (selector) {
return new NodesRef(this, this._component, selector, true)
}
selectAll (selector) {
return new NodesRef(this, this._component, selector, false)
}
selectViewport () {
return new NodesRef(this, 0, '', true)
}
_push (selector, component, single, fields, callback) {
this._queue.push({
component,
selector,
single,
fields
})
this._queueCb.push(callback)
}
}
export function createSelectorQuery () {
return new SelectorQuery()
function parseDataset (attr) {
const dataset = {}
Object.keys(attr || {}).forEach(key => {
if (key.indexOf('data') === 0) {
let str = key.replace('data', '')
str = str.charAt(0).toLowerCase() + str.slice(1)
dataset[str] = attr[key]
}
})
return dataset
}
function findAttrs (ids, elm, result) {
let nodes = elm.children
if (!Array.isArray(nodes)) {
return false
}
for (let i = 0; i < nodes.length; i++) {
let node = nodes[i]
if (node.attr) {
let index = ids.indexOf(node.attr.id)
if (index >= 0) {
result[index] = {
id: ids[index],
ref: node.ref,
dataset: parseDataset(node.attr)
}
if (ids.length === 1) {
break
}
}
}
if (node.children) {
findAttrs(ids, node, result)
}
}
}
function getSelectors (queue) {
let ids = []
for (let i = 0; i < queue.length; i++) {
const selector = queue[i].selector
if (selector.indexOf('#') === 0) {
ids.push(selector.substring(1))
}
}
return ids
}
function getComponentRectAll (dom, attrs, index, result, callback) {
const attr = attrs[index]
dom.getComponentRect(attr.ref, option => {
option.size.id = attr.id
option.size.dataset = attr.dataset
result.push(option.size)
index += 1
if (index < attrs.length) {
getComponentRectAll(dom, attrs, index, result, callback)
} else {
callback(result)
}
})
}
export function requestComponentInfo (pageInstance, queue, callback) {
// TODO 重构,逻辑不对,queue 里的每一项可能有单独的作用域查找(即 component)
const vm = pageInstance.$vm
const dom = vm._$weex.requireModule('dom')
const selectors = getSelectors(queue)
let outAttrs = new Array(selectors.length)
findAttrs(selectors, vm.$el, outAttrs)
getComponentRectAll(dom, outAttrs, 0, [], (result) => {
callback(result)
})
}
......@@ -61,3 +61,5 @@ export {
from './ui/pull-down-refresh'
export * from './ui/tab-bar'
export * from './ui/request-component-info'
import {
requestComponentInfo as requestVueComponentInfo
} from 'uni-platforms/h5/service/api/ui/request-component-info'
import {
requestComponentInfo as requestNVueComponentInfo
} from 'uni-platforms/app-plus-nvue/service/api/ui/request-component-info'
export function requestComponentInfo (pageInstance, queue, callback) {
pageInstance.$page.meta.isNVue
? requestNVueComponentInfo(pageInstance, queue, callback)
: requestVueComponentInfo(pageInstance, queue, callback)
}
......@@ -7,9 +7,9 @@ export function publishHandler (eventType, args, pageIds) {
pageIds = [pageIds]
}
const evalJSCode =
`typeof UniViewJSBridge !== 'undefined' && UniViewJSBridge.subscribeHandler("${eventType}",${args})`
`typeof UniViewJSBridge !== 'undefined' && UniViewJSBridge.subscribeHandler("${eventType}",${args},__PAGE_ID__)`
pageIds.forEach(id => {
const webview = plus.webview.getWebviewById(String(id))
webview && webview.evalJS(evalJSCode)
webview && webview.evalJS(evalJSCode.replace('__PAGE_ID__', id))
})
}
......@@ -50,7 +50,8 @@ const handleData = {
},
[PAGE_CREATED]: function onPageCreated (data) {
const [pageId, pagePath] = data
new PageVueComponent({
const page = getCurrentPages()[0]
page.$vm = new PageVueComponent({
mpType: 'page',
pageId,
pagePath
......
import createCallbacks from 'uni-helpers/callbacks'
const requestComponentInfoCallbacks = createCallbacks('requestComponentInfo')
export function requestComponentInfo (pageInstance, queue, callback) {
UniServiceJSBridge.publishHandler('requestComponentInfo', {
reqId: requestComponentInfoCallbacks.push(callback),
reqs: queue
}, pageInstance.$page.id)
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册