diff --git a/package.json b/package.json
index 6f67e4229..1e9064583 100644
--- a/package.json
+++ b/package.json
@@ -12,6 +12,7 @@
"@babel/polyfill": "7.6.0",
"@fui/babel-preset-fineui": "^2.0.0",
"@fui/eslint-plugin": "^1.0.19",
+ "@juggle/resize-observer": "^3.4.0",
"@types/node": "15.6.1",
"@typescript-eslint/eslint-plugin": "2.33.0",
"@typescript-eslint/parser": "2.33.0",
@@ -91,4 +92,4 @@
"@types/yargs": "17.0.13",
"yargs": "17.6.2"
}
-}
\ No newline at end of file
+}
diff --git a/src/core/platform/web/config.js b/src/core/platform/web/config.js
index 66440ccf8..e4812bd7b 100644
--- a/src/core/platform/web/config.js
+++ b/src/core/platform/web/config.js
@@ -1,286 +1,315 @@
+import { Plugin } from "../../6.plugin";
+
// 工程配置
-!(function () {
- // 注册布局
- // adapt类布局优先级规则
- // 1、支持flex的浏览器下使用flex布局
- // 2、不支持flex的浏览器下使用inline布局
- // 3、当列宽既需要自动列宽又需要自适应列宽时,inline布局也处理不了了。当横向出滚动条时使用table布局,不出滚动条时使用float布局
- var _isSupportFlex, _isSupportGrid;
- var isSupportFlex = function () {
- if (_isSupportFlex == null) {
- _isSupportFlex = !!(BI.isSupportCss3 && BI.isSupportCss3("flex"));
- }
- return _isSupportFlex;
- };
- var isSupportGrid = function () {
- if (_isSupportGrid == null) {
- _isSupportGrid = !!(BI.isSupportCss3 && BI.isSupportCss3("grid"));
- }
- return _isSupportGrid;
- };
- // 判断浏览器是否支持sticky 属性
- var isSupportSticky = (function () {
- var vendorList = ["", "-webkit-", "-ms-", "-moz-", "-o-"],
- vendorListLength = vendorList.length,
- stickyElement = document.createElement("div");
- for (var i = 0; i < vendorListLength; i++) {
- stickyElement.style.position = vendorList[i] + "sticky";
- if (stickyElement.style.position !== "") {
- return true;
- }
- }
- return false;
- })();
- BI.Plugin.configWidget("bi.horizontal", function (ob) {
- var supportFlex = isSupportFlex();
- // // 在横向自适应场景下我们需要使用table的自适应撑出滚动条的特性(flex处理不了这种情况)
- // // 主要出现在center_adapt或者horizontal_adapt的场景,或者主动设置horizontalAlign的场景
- // if (ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch) {
- // return BI.extend({}, ob, {type: "bi.table_adapt"});
- // }
- if (supportFlex) {
- return BI.extend({}, ob, { type: "bi.flex_horizontal" });
- }
- return BI.extend({
- scrollx: true
- }, ob, { type: "bi.inline" });
- });
- BI.Plugin.configWidget("bi.vertical", function (ob) {
- if (ob.horizontalAlign === BI.HorizontalAlign.Left || ob.horizontalAlign === BI.HorizontalAlign.Right) {
- if (isSupportFlex()) {
- return BI.extend({}, ob, { type: "bi.flex_vertical" });
- }
- return BI.extend({}, ob, {
- horizontalAlign: BI.HorizontalAlign.Stretch,
- type: "bi.vertical",
- items: BI.map(ob.items, function (i, item) {
- return {
- type: "bi.inline",
- horizontalAlign: ob.horizontalAlign,
- items: [item]
- };
- })
- });
- }
- if (ob.verticalAlign === BI.VerticalAlign.Stretch) {
- if (isSupportFlex()) {
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Stretch,
- }, ob, { type: "bi.flex_vertical" });
- }
- }
- return ob;
- });
- BI.Plugin.configWidget("bi.inline", function (ob) {
- // 当列宽既需要自动列宽又需要自适应列宽时,inline布局也处理不了了,降级table处理吧
- var hasAutoAndFillColumnSize = false;
- if (ob.columnSize && ob.columnSize.length > 0) {
- if ((ob.columnSize.indexOf("") >= 0 || ob.columnSize.indexOf("auto") >= 0) && ob.columnSize.indexOf("fill") >= 0) {
- hasAutoAndFillColumnSize = true;
- }
- } else {
- var hasAuto = false, hasFill = false;
- BI.each(ob.items, function (i, item) {
- if (item.width === "fill") {
- hasFill = true;
- } else if (BI.isNull(item.width) || item.width === "" || item.width === "auto") {
- hasAuto = true;
- }
- });
- hasAutoAndFillColumnSize = hasAuto && hasFill;
- }
+// 注册布局
+// adapt类布局优先级规则
+// 1、支持flex的浏览器下使用flex布局
+// 2、不支持flex的浏览器下使用inline布局
+// 3、当列宽既需要自动列宽又需要自适应列宽时,inline布局也处理不了了。当横向出滚动条时使用table布局,不出滚动条时使用float布局
+let _isSupportFlex, _isSupportGrid;
- if (hasAutoAndFillColumnSize) {
- // 宽度是不是受限
- if ((ob.scrollable !== true && ob.scrollx !== true) || ob.horizontalAlign === BI.HorizontalAlign.Stretch) {
- return BI.extend({
- verticalAlign: BI.VerticalAlign.Top
- }, ob, { type: "bi.horizontal_float_fill" });
- }
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Stretch
- }, ob, { type: "bi.table_adapt" });
- }
- if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
- return BI.extend({}, ob, { type: "bi.responsive_inline" });
- }
- return ob;
- });
- BI.Plugin.configWidget("bi.center_adapt", function (ob) {
- var supportFlex = isSupportFlex();
- // var isAdapt = !ob.horizontalAlign || ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
- // if (!isAdapt || justOneItem) {
- if (supportFlex) {
- return BI.extend({}, ob, { type: "bi.flex_center_adapt" });
- }
- return BI.extend({}, ob, { type: "bi.inline_center_adapt" });
- // }
- // return ob;
- });
- BI.Plugin.configWidget("bi.vertical_adapt", function (ob) {
- var supportFlex = isSupportFlex();
- // var isAdapt = ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
- // if (!isAdapt || justOneItem) {
- if (supportFlex) {
- return BI.extend({}, ob, { type: "bi.flex_vertical_center_adapt" });
- }
- return BI.extend({}, ob, { type: "bi.inline_vertical_adapt" });
- // }
- // return ob;
- });
- BI.Plugin.configWidget("bi.horizontal_adapt", function (ob) {
- var justOneItem = (ob.items && ob.items.length <= 1);
- var isAdapt = !ob.horizontalAlign || ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
- var verticalAlignTop = !ob.verticalAlign || ob.verticalAlign === BI.VerticalAlign.TOP;
- if (verticalAlignTop && justOneItem) {
- return BI.extend({}, ob, { type: "bi.horizontal_auto" });
- }
- var supportFlex = isSupportFlex();
- // 在横向自适应场景下我们需要使用table的自适应撑出滚动条的特性(flex处理不了这种情况)
- // 主要出现在center_adapt或者horizontal_adapt的场景,或者主动设置horizontalAlign的场景
- if (isAdapt) {
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Center
- }, ob, { type: "bi.table_adapt" });
- }
- if (supportFlex) {
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Center,
- scrollx: false
- }, ob, { type: "bi.flex_horizontal" });
- }
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Center
- }, ob, { type: "bi.table_adapt" });
- });
- BI.Plugin.configWidget("bi.horizontal_float", function (ob) {
- if (isSupportFlex()) {
- return BI.extend({}, ob, { type: "bi.flex_horizontal_adapt" });
- }
- if (ob.items && ob.items.length <= 1) {
- return BI.extend({}, ob, { type: "bi.inline_horizontal_adapt" });
- }
- return ob;
- });
+function isSupportFlex() {
+ if (!_isSupportFlex) {
+ _isSupportFlex = !!(BI.isSupportCss3 && BI.isSupportCss3("flex"));
+ }
+
+ return _isSupportFlex;
+}
+
+function isSupportGrid() {
+ if (!_isSupportGrid) {
+ _isSupportGrid = !!(BI.isSupportCss3 && BI.isSupportCss3("grid"));
+ }
+
+ return _isSupportGrid;
+}
- BI.Plugin.configWidget("bi.horizontal_fill", function (ob) {
+// 判断浏览器是否支持sticky 属性
+const isSupportSticky = (function () {
+ const vendorList = ["", "-webkit-", "-ms-", "-moz-", "-o-"],
+ vendorListLength = vendorList.length,
+ stickyElement = document.createElement("div");
+ for (let i = 0; i < vendorListLength; i++) {
+ stickyElement.style.position = `${vendorList[i]}sticky`;
+ if (stickyElement.style.position !== "") {
+ return true;
+ }
+ }
+
+ return false;
+}());
+
+
+const configWidget = Plugin.configWidget;
+
+configWidget("bi.horizontal", ob => {
+ const supportFlex = isSupportFlex();
+ // // 在横向自适应场景下我们需要使用table的自适应撑出滚动条的特性(flex处理不了这种情况)
+ // // 主要出现在center_adapt或者horizontal_adapt的场景,或者主动设置horizontalAlign的场景
+ // if (ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch) {
+ // return BI.extend({}, ob, {type: "bi.table_adapt"});
+ // }
+ if (supportFlex) {
+ return BI.extend({}, ob, { type: "bi.flex_horizontal" });
+ }
+
+ return BI.extend({
+ scrollx: true,
+ }, ob, { type: "bi.inline" });
+});
+configWidget("bi.vertical", ob => {
+ if (ob.horizontalAlign === BI.HorizontalAlign.Left || ob.horizontalAlign === BI.HorizontalAlign.Right) {
if (isSupportFlex()) {
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Stretch,
- verticalAlign: BI.VerticalAlign.Stretch,
- scrollx: false
- }, ob, { type: "bi.flex_horizontal" });
- }
- if ((ob.horizontalAlign && ob.horizontalAlign !== BI.HorizontalAlign.Stretch) || (ob.scrollable === true || ob.scrollx === true)) {
- // 宽度不受限,要用table布局
- return BI.extend({
- horizontalAlign: BI.HorizontalAlign.Stretch,
- verticalAlign: BI.VerticalAlign.Stretch
- }, ob, { type: "bi.table_adapt" });
+ return BI.extend({}, ob, { type: "bi.flex_vertical" });
}
- return BI.extend({}, ob, { type: "bi.horizontal_float_fill" });
- });
- BI.Plugin.configWidget("bi.vertical_fill", function (ob) {
+
+ return BI.extend({}, ob, {
+ horizontalAlign: BI.HorizontalAlign.Stretch,
+ type: "bi.vertical",
+ items: BI.map(ob.items, (i, item) => {
+ return {
+ type: "bi.inline",
+ horizontalAlign: ob.horizontalAlign,
+ items: [item],
+ };
+ }),
+ });
+ }
+ if (ob.verticalAlign === BI.VerticalAlign.Stretch) {
if (isSupportFlex()) {
return BI.extend({
horizontalAlign: BI.HorizontalAlign.Stretch,
- verticalAlign: BI.VerticalAlign.Stretch,
- scrolly: false
}, ob, { type: "bi.flex_vertical" });
}
- if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
- // 有滚动条,降级到table布局处理
- return BI.extend({}, ob, {
- type: "bi.td",
- items: BI.map(ob.items, function (i, item) {
- return [item];
- })
- });
- }
- var hasAuto = false;
- if (ob.rowSize && ob.rowSize.length > 0) {
- if (ob.rowSize.indexOf("") >= 0 || ob.rowSize.indexOf("auto") >= 0) {
+ }
+
+ return ob;
+});
+configWidget("bi.inline", ob => {
+ // 当列宽既需要自动列宽又需要自适应列宽时,inline布局也处理不了了,降级table处理吧
+ let hasAutoAndFillColumnSize = false;
+ if (ob.columnSize && ob.columnSize.length > 0) {
+ if ((ob.columnSize.indexOf("") >= 0 || ob.columnSize.indexOf("auto") >= 0) && ob.columnSize.indexOf("fill") >= 0) {
+ hasAutoAndFillColumnSize = true;
+ }
+ } else {
+ let hasAuto = false, hasFill = false;
+ BI.each(ob.items, (i, item) => {
+ if (item.width === "fill") {
+ hasFill = true;
+ } else if (BI.isNull(item.width) || item.width === "" || item.width === "auto") {
hasAuto = true;
}
- } else {
- BI.each(ob.items, function (i, item) {
- if (BI.isNull(item.height) || item.height === "") {
- hasAuto = true;
- }
- });
- }
- if (hasAuto) {
- // 有自动高的时候
- return BI.extend({}, ob, { type: "bi.vtape_auto" });
- }
- return BI.extend({}, ob, { type: "bi.vtape" });
- });
- BI.Plugin.configWidget("bi.horizontal_sticky", function (ob) {
- if (!isSupportSticky) {
- return BI.extend({ scrollx: true }, ob, { type: "bi.horizontal_fill" });
- }
- });
- BI.Plugin.configWidget("bi.vertical_sticky", function (ob) {
- if (!isSupportSticky) {
- return BI.extend({ scrolly: true }, ob, { type: "bi.vertical_fill" });
- }
- });
+ });
+ hasAutoAndFillColumnSize = hasAuto && hasFill;
+ }
- BI.Plugin.configWidget("bi.left_right_vertical_adapt", function (ob) {
- if (isSupportFlex()) {
- // IE下其实也是可以使用flex布局的,只要排除掉出现滚动条的情况
- // if (!BI.isIE() || (ob.scrollable !== true && ob.scrolly !== true)) {
- return BI.extend({}, ob, { type: "bi.flex_left_right_vertical_adapt" });
- // }
+ if (hasAutoAndFillColumnSize) {
+ // 宽度是不是受限
+ if ((ob.scrollable !== true && ob.scrollx !== true) || ob.horizontalAlign === BI.HorizontalAlign.Stretch) {
+ return BI.extend({
+ verticalAlign: BI.VerticalAlign.Top,
+ }, ob, { type: "bi.horizontal_float_fill" });
}
- return ob;
- });
- BI.Plugin.configWidget("bi.flex_horizontal", function (ob) {
- if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
- if (ob.hgap > 0 || ob.lgap > 0 || ob.rgap > 0) {
- if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
- return BI.extend({}, ob, { type: "bi.responsive_flex_scrollable_horizontal" });
- }
- return BI.extend({}, ob, { type: "bi.flex_scrollable_horizontal" });
+
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Stretch,
+ }, ob, { type: "bi.table_adapt" });
+ }
+ if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
+ return BI.extend({}, ob, { type: "bi.responsive_inline" });
+ }
+
+ return ob;
+});
+configWidget("bi.center_adapt", ob => {
+ const supportFlex = isSupportFlex();
+ // var isAdapt = !ob.horizontalAlign || ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
+ // if (!isAdapt || justOneItem) {
+ if (supportFlex) {
+ return BI.extend({}, ob, { type: "bi.flex_center_adapt" });
+ }
+
+ return BI.extend({}, ob, { type: "bi.inline_center_adapt" });
+ // }
+ // return ob;
+});
+configWidget("bi.vertical_adapt", ob => {
+ const supportFlex = isSupportFlex();
+ // var isAdapt = ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
+ // if (!isAdapt || justOneItem) {
+ if (supportFlex) {
+ return BI.extend({}, ob, { type: "bi.flex_vertical_center_adapt" });
+ }
+
+ return BI.extend({}, ob, { type: "bi.inline_vertical_adapt" });
+ // }
+ // return ob;
+});
+
+configWidget("bi.horizontal_adapt", ob => {
+ const justOneItem = (ob.items && ob.items.length <= 1);
+ const isAdapt = !ob.horizontalAlign || ob.horizontalAlign === BI.HorizontalAlign.Center || ob.horizontalAlign === BI.HorizontalAlign.Stretch;
+ const verticalAlignTop = !ob.verticalAlign || ob.verticalAlign === BI.VerticalAlign.TOP;
+ if (verticalAlignTop && justOneItem) {
+ return BI.extend({}, ob, { type: "bi.horizontal_auto" });
+ }
+ const supportFlex = isSupportFlex();
+ // 在横向自适应场景下我们需要使用table的自适应撑出滚动条的特性(flex处理不了这种情况)
+ // 主要出现在center_adapt或者horizontal_adapt的场景,或者主动设置horizontalAlign的场景
+ if (isAdapt) {
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Center,
+ }, ob, { type: "bi.table_adapt" });
+ }
+ if (supportFlex) {
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Center,
+ scrollx: false,
+ }, ob, { type: "bi.flex_horizontal" });
+ }
+
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Center,
+ }, ob, { type: "bi.table_adapt" });
+});
+
+configWidget("bi.horizontal_float", ob => {
+ if (isSupportFlex()) {
+ return BI.extend({}, ob, { type: "bi.flex_horizontal_adapt" });
+ }
+ if (ob.items && ob.items.length <= 1) {
+ return BI.extend({}, ob, { type: "bi.inline_horizontal_adapt" });
+ }
+
+ return ob;
+});
+
+configWidget("bi.horizontal_fill", ob => {
+ if (isSupportFlex()) {
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Stretch,
+ verticalAlign: BI.VerticalAlign.Stretch,
+ scrollx: false,
+ }, ob, { type: "bi.flex_horizontal" });
+ }
+ if ((ob.horizontalAlign && ob.horizontalAlign !== BI.HorizontalAlign.Stretch) || (ob.scrollable === true || ob.scrollx === true)) {
+ // 宽度不受限,要用table布局
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Stretch,
+ verticalAlign: BI.VerticalAlign.Stretch,
+ }, ob, { type: "bi.table_adapt" });
+ }
+
+ return BI.extend({}, ob, { type: "bi.horizontal_float_fill" });
+});
+configWidget("bi.vertical_fill", ob => {
+ if (isSupportFlex()) {
+ return BI.extend({
+ horizontalAlign: BI.HorizontalAlign.Stretch,
+ verticalAlign: BI.VerticalAlign.Stretch,
+ scrolly: false,
+ }, ob, { type: "bi.flex_vertical" });
+ }
+ if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
+ // 有滚动条,降级到table布局处理
+ return BI.extend({}, ob, {
+ type: "bi.td",
+ items: BI.map(ob.items, (i, item) => [item]),
+ });
+ }
+ let hasAuto = false;
+ if (ob.rowSize && ob.rowSize.length > 0) {
+ if (ob.rowSize.indexOf("") >= 0 || ob.rowSize.indexOf("auto") >= 0) {
+ hasAuto = true;
+ }
+ } else {
+ BI.each(ob.items, (i, item) => {
+ if (BI.isNull(item.height) || item.height === "") {
+ hasAuto = true;
}
- }
- if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
- return BI.extend({}, ob, { type: "bi.responsive_flex_horizontal" });
- }
- });
- BI.Plugin.configWidget("bi.flex_vertical", function (ob) {
- if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
- if (ob.hgap > 0 || ob.lgap > 0 || ob.rgap > 0) {
- return BI.extend({}, ob, { type: "bi.flex_scrollable_vertical" });
+ });
+ }
+ if (hasAuto) {
+ // 有自动高的时候
+ return BI.extend({}, ob, { type: "bi.vtape_auto" });
+ }
+
+ return BI.extend({}, ob, { type: "bi.vtape" });
+});
+configWidget("bi.horizontal_sticky", ob => {
+ if (!isSupportSticky) {
+ return BI.extend({ scrollx: true }, ob, { type: "bi.horizontal_fill" });
+ }
+});
+configWidget("bi.vertical_sticky", ob => {
+ if (!isSupportSticky) {
+ return BI.extend({ scrolly: true }, ob, { type: "bi.vertical_fill" });
+ }
+});
+
+configWidget("bi.left_right_vertical_adapt", ob => {
+ if (isSupportFlex()) {
+ // IE下其实也是可以使用flex布局的,只要排除掉出现滚动条的情况
+ // if (!BI.isIE() || (ob.scrollable !== true && ob.scrolly !== true)) {
+ return BI.extend({}, ob, { type: "bi.flex_left_right_vertical_adapt" });
+ // }
+ }
+
+ return ob;
+});
+configWidget("bi.flex_horizontal", ob => {
+ if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
+ if (ob.hgap > 0 || ob.lgap > 0 || ob.rgap > 0) {
+ if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
+ return BI.extend({}, ob, { type: "bi.responsive_flex_scrollable_horizontal" });
}
- }
- });
- BI.Plugin.configWidget("bi.table", function (ob) {
- if (!isSupportGrid()) {
- return BI.extend({}, ob, { type: "bi.td" });
- }
- return ob;
- });
+ return BI.extend({}, ob, { type: "bi.flex_scrollable_horizontal" });
+ }
+ }
+ if (BI.Providers.getProvider("bi.provider.system").getResponsiveMode()) {
+ return BI.extend({}, ob, { type: "bi.responsive_flex_horizontal" });
+ }
+});
+configWidget("bi.flex_vertical", ob => {
+ if (ob.scrollable === true || ob.scrollx === true || ob.scrolly === true) {
+ if (ob.hgap > 0 || ob.lgap > 0 || ob.rgap > 0) {
+ return BI.extend({}, ob, { type: "bi.flex_scrollable_vertical" });
+ }
+ }
+});
- BI.Plugin.configWidget("bi.radio", function (ob) {
- if (BI.isIE() && BI.getIEVersion() <= 9) {
- return BI.extend({}, ob, { type: "bi.image_radio" });
- }
- return ob;
- });
+configWidget("bi.table", ob => {
+ if (!isSupportGrid()) {
+ return BI.extend({}, ob, { type: "bi.td" });
+ }
- BI.Plugin.configWidget("bi.checkbox", function (ob) {
- if (BI.isIE() && BI.getIEVersion() <= 9) {
- return BI.extend({}, ob, { type: "bi.image_checkbox" });
- }
+ return ob;
+});
+
+configWidget("bi.radio", ob => {
+ if (BI.isIE() && BI.getIEVersion() <= 9) {
+ return BI.extend({}, ob, { type: "bi.image_radio" });
+ }
+
+ return ob;
+});
+
+configWidget("bi.checkbox", ob => {
+ if (BI.isIE() && BI.getIEVersion() <= 9) {
+ return BI.extend({}, ob, { type: "bi.image_checkbox" });
+ }
+
+ return ob;
+});
+
+configWidget("bi.half_icon_button", ob => {
+ if (BI.isIE() && BI.getIEVersion() < 9) {
return ob;
- });
+ }
+
+ return BI.extend({}, ob, { type: "bi.half_button" });
+});
+
- BI.Plugin.configWidget("bi.half_icon_button", function (ob) {
- if (BI.isIE() && BI.getIEVersion() < 9) {
- return ob;
- }
- return BI.extend({}, ob, { type: "bi.half_button" });
- });
-}());
diff --git a/src/core/platform/web/detectElementResize.js b/src/core/platform/web/detectElementResize.js
index 502ebb0ee..7be166fd9 100644
--- a/src/core/platform/web/detectElementResize.js
+++ b/src/core/platform/web/detectElementResize.js
@@ -1,571 +1,15 @@
-/**
- * Detect Element Resize.
- * A minimal library which polyfills the ResizeObserver API and is entirely based on the latest Draft Specification.
- * https://github.com/juggle/resize-observer
- * version: 3.4.0
- **/
-var ResizeObserverPolyfill = (function (exports) {
- 'use strict';
+import { ResizeObserver as ResizeObserverPolyfill } from "@juggle/resize-observer";
- var resizeObservers = [];
+const ResizeObserver = window.ResizeObserver || ResizeObserverPolyfill;
- var hasActiveObservations = function () {
- return resizeObservers.some(function (ro) {
- return ro.activeTargets.length > 0;
- });
- };
-
- var hasSkippedObservations = function () {
- return resizeObservers.some(function (ro) {
- return ro.skippedTargets.length > 0;
- });
- };
-
- var msg = 'ResizeObserver loop completed with undelivered notifications.';
- var deliverResizeLoopError = function () {
- var event;
- if (typeof ErrorEvent === 'function') {
- event = new ErrorEvent('error', {
- message: msg
- });
- } else {
- event = document.createEvent('Event');
- event.initEvent('error', false, false);
- event.message = msg;
- }
- window.dispatchEvent(event);
- };
-
- var ResizeObserverBoxOptions;
- (function (ResizeObserverBoxOptions) {
- ResizeObserverBoxOptions["BORDER_BOX"] = "border-box";
- ResizeObserverBoxOptions["CONTENT_BOX"] = "content-box";
- ResizeObserverBoxOptions["DEVICE_PIXEL_CONTENT_BOX"] = "device-pixel-content-box";
- })(ResizeObserverBoxOptions || (ResizeObserverBoxOptions = {}));
-
- var freeze = function (obj) {
- return Object.freeze(obj);
- };
-
- var ResizeObserverSize = (function () {
- function ResizeObserverSize(inlineSize, blockSize) {
- this.inlineSize = inlineSize;
- this.blockSize = blockSize;
- freeze(this);
- }
-
- return ResizeObserverSize;
- }());
-
- var DOMRectReadOnly = (function () {
- function DOMRectReadOnly(x, y, width, height) {
- this.x = x;
- this.y = y;
- this.width = width;
- this.height = height;
- this.top = this.y;
- this.left = this.x;
- this.bottom = this.top + this.height;
- this.right = this.left + this.width;
- return freeze(this);
- }
-
- DOMRectReadOnly.prototype.toJSON = function () {
- var _a = this, x = _a.x, y = _a.y, top = _a.top, right = _a.right, bottom = _a.bottom, left = _a.left,
- width = _a.width, height = _a.height;
- return { x: x, y: y, top: top, right: right, bottom: bottom, left: left, width: width, height: height };
- };
- DOMRectReadOnly.fromRect = function (rectangle) {
- return new DOMRectReadOnly(rectangle.x, rectangle.y, rectangle.width, rectangle.height);
- };
- return DOMRectReadOnly;
- }());
-
- var isSVG = function (target) {
- return target instanceof SVGElement && 'getBBox' in target;
- };
- var isHidden = function (target) {
- if (isSVG(target)) {
- var _a = target.getBBox(), width = _a.width, height = _a.height;
- return !width && !height;
- }
- var _b = target, offsetWidth = _b.offsetWidth, offsetHeight = _b.offsetHeight;
- return !(offsetWidth || offsetHeight || target.getClientRects().length);
- };
- var isElement = function (obj) {
- var _a;
- if (obj instanceof Element) {
- return true;
- }
- var scope = (_a = obj === null || obj === void 0 ? void 0 : obj.ownerDocument) === null || _a === void 0 ? void 0 : _a.defaultView;
- return !!(scope && obj instanceof scope.Element);
- };
- var isReplacedElement = function (target) {
- switch (target.tagName) {
- case 'INPUT':
- if (target.type !== 'image') {
- break;
- }
- case 'VIDEO':
- case 'AUDIO':
- case 'EMBED':
- case 'OBJECT':
- case 'CANVAS':
- case 'IFRAME':
- case 'IMG':
- return true;
- }
- return false;
- };
-
- var global = typeof window !== 'undefined' ? window : {};
-
- var cache = new WeakMap();
- var scrollRegexp = /auto|scroll/;
- var verticalRegexp = /^tb|vertical/;
- var IE = (/msie|trident/i).test(global.navigator && global.navigator.userAgent);
- var parseDimension = function (pixel) {
- return parseFloat(pixel || '0');
- };
- var size = function (inlineSize, blockSize, switchSizes) {
- if (inlineSize === void 0) {
- inlineSize = 0;
- }
- if (blockSize === void 0) {
- blockSize = 0;
- }
- if (switchSizes === void 0) {
- switchSizes = false;
- }
- return new ResizeObserverSize((switchSizes ? blockSize : inlineSize) || 0, (switchSizes ? inlineSize : blockSize) || 0);
- };
- var zeroBoxes = freeze({
- devicePixelContentBoxSize: size(),
- borderBoxSize: size(),
- contentBoxSize: size(),
- contentRect: new DOMRectReadOnly(0, 0, 0, 0)
- });
- var calculateBoxSizes = function (target, forceRecalculation) {
- if (forceRecalculation === void 0) {
- forceRecalculation = false;
- }
- if (cache.has(target) && !forceRecalculation) {
- return cache.get(target);
- }
- if (isHidden(target)) {
- cache.set(target, zeroBoxes);
- return zeroBoxes;
- }
- var cs = getComputedStyle(target);
- var svg = isSVG(target) && target.ownerSVGElement && target.getBBox();
- var removePadding = !IE && cs.boxSizing === 'border-box';
- var switchSizes = verticalRegexp.test(cs.writingMode || '');
- var canScrollVertically = !svg && scrollRegexp.test(cs.overflowY || '');
- var canScrollHorizontally = !svg && scrollRegexp.test(cs.overflowX || '');
- var paddingTop = svg ? 0 : parseDimension(cs.paddingTop);
- var paddingRight = svg ? 0 : parseDimension(cs.paddingRight);
- var paddingBottom = svg ? 0 : parseDimension(cs.paddingBottom);
- var paddingLeft = svg ? 0 : parseDimension(cs.paddingLeft);
- var borderTop = svg ? 0 : parseDimension(cs.borderTopWidth);
- var borderRight = svg ? 0 : parseDimension(cs.borderRightWidth);
- var borderBottom = svg ? 0 : parseDimension(cs.borderBottomWidth);
- var borderLeft = svg ? 0 : parseDimension(cs.borderLeftWidth);
- var horizontalPadding = paddingLeft + paddingRight;
- var verticalPadding = paddingTop + paddingBottom;
- var horizontalBorderArea = borderLeft + borderRight;
- var verticalBorderArea = borderTop + borderBottom;
- var horizontalScrollbarThickness = !canScrollHorizontally ? 0 : target.offsetHeight - verticalBorderArea - target.clientHeight;
- var verticalScrollbarThickness = !canScrollVertically ? 0 : target.offsetWidth - horizontalBorderArea - target.clientWidth;
- var widthReduction = removePadding ? horizontalPadding + horizontalBorderArea : 0;
- var heightReduction = removePadding ? verticalPadding + verticalBorderArea : 0;
- var contentWidth = svg ? svg.width : parseDimension(cs.width) - widthReduction - verticalScrollbarThickness;
- var contentHeight = svg ? svg.height : parseDimension(cs.height) - heightReduction - horizontalScrollbarThickness;
- var borderBoxWidth = contentWidth + horizontalPadding + verticalScrollbarThickness + horizontalBorderArea;
- var borderBoxHeight = contentHeight + verticalPadding + horizontalScrollbarThickness + verticalBorderArea;
- var boxes = freeze({
- devicePixelContentBoxSize: size(Math.round(contentWidth * devicePixelRatio), Math.round(contentHeight * devicePixelRatio), switchSizes),
- borderBoxSize: size(borderBoxWidth, borderBoxHeight, switchSizes),
- contentBoxSize: size(contentWidth, contentHeight, switchSizes),
- contentRect: new DOMRectReadOnly(paddingLeft, paddingTop, contentWidth, contentHeight)
- });
- cache.set(target, boxes);
- return boxes;
- };
- var calculateBoxSize = function (target, observedBox, forceRecalculation) {
- var _a = calculateBoxSizes(target, forceRecalculation), borderBoxSize = _a.borderBoxSize,
- contentBoxSize = _a.contentBoxSize, devicePixelContentBoxSize = _a.devicePixelContentBoxSize;
- switch (observedBox) {
- case ResizeObserverBoxOptions.DEVICE_PIXEL_CONTENT_BOX:
- return devicePixelContentBoxSize;
- case ResizeObserverBoxOptions.BORDER_BOX:
- return borderBoxSize;
- default:
- return contentBoxSize;
- }
- };
-
- var ResizeObserverEntry = (function () {
- function ResizeObserverEntry(target) {
- var boxes = calculateBoxSizes(target);
- this.target = target;
- this.contentRect = boxes.contentRect;
- this.borderBoxSize = freeze([boxes.borderBoxSize]);
- this.contentBoxSize = freeze([boxes.contentBoxSize]);
- this.devicePixelContentBoxSize = freeze([boxes.devicePixelContentBoxSize]);
- }
-
- return ResizeObserverEntry;
- }());
-
- var calculateDepthForNode = function (node) {
- if (isHidden(node)) {
- return Infinity;
- }
- var depth = 0;
- var parent = node.parentNode;
- while (parent) {
- depth += 1;
- parent = parent.parentNode;
- }
- return depth;
- };
-
- var broadcastActiveObservations = function () {
- var shallowestDepth = Infinity;
- var callbacks = [];
- resizeObservers.forEach(function processObserver(ro) {
- if (ro.activeTargets.length === 0) {
- return;
- }
- var entries = [];
- ro.activeTargets.forEach(function processTarget(ot) {
- var entry = new ResizeObserverEntry(ot.target);
- var targetDepth = calculateDepthForNode(ot.target);
- entries.push(entry);
- ot.lastReportedSize = calculateBoxSize(ot.target, ot.observedBox);
- if (targetDepth < shallowestDepth) {
- shallowestDepth = targetDepth;
- }
- });
- callbacks.push(function resizeObserverCallback() {
- ro.callback.call(ro.observer, entries, ro.observer);
- });
- ro.activeTargets.splice(0, ro.activeTargets.length);
- });
- for (var _i = 0, callbacks_1 = callbacks; _i < callbacks_1.length; _i++) {
- var callback = callbacks_1[_i];
- callback();
- }
- return shallowestDepth;
- };
-
- var gatherActiveObservationsAtDepth = function (depth) {
- resizeObservers.forEach(function processObserver(ro) {
- ro.activeTargets.splice(0, ro.activeTargets.length);
- ro.skippedTargets.splice(0, ro.skippedTargets.length);
- ro.observationTargets.forEach(function processTarget(ot) {
- if (ot.isActive()) {
- if (calculateDepthForNode(ot.target) > depth) {
- ro.activeTargets.push(ot);
- } else {
- ro.skippedTargets.push(ot);
- }
- }
- });
- });
- };
-
- var process = function () {
- var depth = 0;
- gatherActiveObservationsAtDepth(depth);
- while (hasActiveObservations()) {
- depth = broadcastActiveObservations();
- gatherActiveObservationsAtDepth(depth);
- }
- if (hasSkippedObservations()) {
- deliverResizeLoopError();
- }
- return depth > 0;
- };
-
- var trigger;
- var callbacks = [];
- var notify = function () {
- return callbacks.splice(0).forEach(function (cb) {
- return cb();
- });
- };
- var queueMicroTask = function (callback) {
- if (!trigger) {
- var toggle_1 = 0;
- var el_1 = document.createTextNode('');
- var config = { characterData: true };
- new MutationObserver(function () {
- return notify();
- }).observe(el_1, config);
- trigger = function () {
- el_1.textContent = "".concat(toggle_1 ? toggle_1-- : toggle_1++);
- };
- }
- callbacks.push(callback);
- trigger();
- };
-
- var queueResizeObserver = function (cb) {
- queueMicroTask(function ResizeObserver() {
- requestAnimationFrame(cb);
- });
- };
-
- var watching = 0;
- var isWatching = function () {
- return !!watching;
- };
- var CATCH_PERIOD = 250;
- var observerConfig = { attributes: true, characterData: true, childList: true, subtree: true };
- var events = [
- 'resize',
- 'load',
- 'transitionend',
- 'animationend',
- 'animationstart',
- 'animationiteration',
- 'keyup',
- 'keydown',
- 'mouseup',
- 'mousedown',
- 'mouseover',
- 'mouseout',
- 'blur',
- 'focus'
- ];
- var time = function (timeout) {
- if (timeout === void 0) {
- timeout = 0;
- }
- return Date.now() + timeout;
- };
- var scheduled = false;
- var Scheduler = (function () {
- function Scheduler() {
- var _this = this;
- this.stopped = true;
- this.listener = function () {
- return _this.schedule();
- };
- }
-
- Scheduler.prototype.run = function (timeout) {
- var _this = this;
- if (timeout === void 0) {
- timeout = CATCH_PERIOD;
- }
- if (scheduled) {
- return;
- }
- scheduled = true;
- var until = time(timeout);
- queueResizeObserver(function () {
- var elementsHaveResized = false;
- try {
- elementsHaveResized = process();
- } finally {
- scheduled = false;
- timeout = until - time();
- if (!isWatching()) {
- return;
- }
- if (elementsHaveResized) {
- _this.run(1000);
- } else if (timeout > 0) {
- _this.run(timeout);
- } else {
- _this.start();
- }
- }
- });
- };
- Scheduler.prototype.schedule = function () {
- this.stop();
- this.run();
- };
- Scheduler.prototype.observe = function () {
- var _this = this;
- var cb = function () {
- return _this.observer && _this.observer.observe(document.body, observerConfig);
- };
- document.body ? cb() : global.addEventListener('DOMContentLoaded', cb);
- };
- Scheduler.prototype.start = function () {
- var _this = this;
- if (this.stopped) {
- this.stopped = false;
- this.observer = new MutationObserver(this.listener);
- this.observe();
- events.forEach(function (name) {
- return global.addEventListener(name, _this.listener, true);
- });
- }
- };
- Scheduler.prototype.stop = function () {
- var _this = this;
- if (!this.stopped) {
- this.observer && this.observer.disconnect();
- events.forEach(function (name) {
- return global.removeEventListener(name, _this.listener, true);
- });
- this.stopped = true;
- }
- };
- return Scheduler;
- }());
- var scheduler = new Scheduler();
- var updateCount = function (n) {
- !watching && n > 0 && scheduler.start();
- watching += n;
- !watching && scheduler.stop();
- };
-
- var skipNotifyOnElement = function (target) {
- return !isSVG(target)
- && !isReplacedElement(target)
- && getComputedStyle(target).display === 'inline';
- };
- var ResizeObservation = (function () {
- function ResizeObservation(target, observedBox) {
- this.target = target;
- this.observedBox = observedBox || ResizeObserverBoxOptions.CONTENT_BOX;
- this.lastReportedSize = {
- inlineSize: -1,
- blockSize: -1
- };
- }
-
- ResizeObservation.prototype.isActive = function () {
- var size = calculateBoxSize(this.target, this.observedBox, true);
- if (skipNotifyOnElement(this.target)) {
- this.lastReportedSize = size;
- }
- if (this.lastReportedSize.inlineSize !== size.inlineSize
- || this.lastReportedSize.blockSize !== size.blockSize) {
- return true;
- }
- return false;
- };
- return ResizeObservation;
- }());
-
- var ResizeObserverDetail = (function () {
- function ResizeObserverDetail(resizeObserver, callback) {
- this.activeTargets = [];
- this.skippedTargets = [];
- this.observationTargets = [];
- this.observer = resizeObserver;
- this.callback = callback;
- }
-
- return ResizeObserverDetail;
- }());
-
- var observerMap = new WeakMap();
- var getObservationIndex = function (observationTargets, target) {
- for (var i = 0; i < observationTargets.length; i += 1) {
- if (observationTargets[i].target === target) {
- return i;
- }
- }
- return -1;
- };
- var ResizeObserverController = (function () {
- function ResizeObserverController() {
- }
-
- ResizeObserverController.connect = function (resizeObserver, callback) {
- var detail = new ResizeObserverDetail(resizeObserver, callback);
- observerMap.set(resizeObserver, detail);
- };
- ResizeObserverController.observe = function (resizeObserver, target, options) {
- var detail = observerMap.get(resizeObserver);
- var firstObservation = detail.observationTargets.length === 0;
- if (getObservationIndex(detail.observationTargets, target) < 0) {
- firstObservation && resizeObservers.push(detail);
- detail.observationTargets.push(new ResizeObservation(target, options && options.box));
- updateCount(1);
- scheduler.schedule();
- }
- };
- ResizeObserverController.unobserve = function (resizeObserver, target) {
- var detail = observerMap.get(resizeObserver);
- var index = getObservationIndex(detail.observationTargets, target);
- var lastObservation = detail.observationTargets.length === 1;
- if (index >= 0) {
- lastObservation && resizeObservers.splice(resizeObservers.indexOf(detail), 1);
- detail.observationTargets.splice(index, 1);
- updateCount(-1);
- }
- };
- ResizeObserverController.disconnect = function (resizeObserver) {
- var _this = this;
- var detail = observerMap.get(resizeObserver);
- detail.observationTargets.slice().forEach(function (ot) {
- return _this.unobserve(resizeObserver, ot.target);
- });
- detail.activeTargets.splice(0, detail.activeTargets.length);
- };
- return ResizeObserverController;
- }());
-
- var ResizeObserver = (function () {
- function ResizeObserver(callback) {
- if (arguments.length === 0) {
- throw new TypeError("Failed to construct 'ResizeObserver': 1 argument required, but only 0 present.");
- }
- if (typeof callback !== 'function') {
- throw new TypeError("Failed to construct 'ResizeObserver': The callback provided as parameter 1 is not a function.");
- }
- ResizeObserverController.connect(this, callback);
- }
-
- ResizeObserver.prototype.observe = function (target, options) {
- if (arguments.length === 0) {
- throw new TypeError("Failed to execute 'observe' on 'ResizeObserver': 1 argument required, but only 0 present.");
- }
- if (!isElement(target)) {
- throw new TypeError("Failed to execute 'observe' on 'ResizeObserver': parameter 1 is not of type 'Element");
- }
- ResizeObserverController.observe(this, target, options);
- };
- ResizeObserver.prototype.unobserve = function (target) {
- if (arguments.length === 0) {
- throw new TypeError("Failed to execute 'unobserve' on 'ResizeObserver': 1 argument required, but only 0 present.");
- }
- if (!isElement(target)) {
- throw new TypeError("Failed to execute 'unobserve' on 'ResizeObserver': parameter 1 is not of type 'Element");
- }
- ResizeObserverController.unobserve(this, target);
- };
- ResizeObserver.prototype.disconnect = function () {
- ResizeObserverController.disconnect(this);
- };
- ResizeObserver.toString = function () {
- return 'function ResizeObserver () { [polyfill code] }';
- };
- return ResizeObserver;
- }());
-
- return ResizeObserver;
-})();
-
-var ResizeObserver = window.ResizeObserver || ResizeObserverPolyfill;
-
-var addResizeListener = function (element, fn) {
+function addResizeListener(element, fn) {
if (ResizeObserver) {
if (!element.__resizeObserver__) {
- var resizeObserver = new ResizeObserver(function () {
- element.__resizeListeners__.forEach(function (listener) {
+ const resizeObserver = new ResizeObserver((() => {
+ element.__resizeListeners__.forEach(listener => {
BI.$(element).is(":visible") && listener();
});
- });
+ }));
resizeObserver.observe(element);
element.__resizeObserver__ = resizeObserver;
}
@@ -574,16 +18,18 @@ var addResizeListener = function (element, fn) {
}
element.__resizeListeners__.push(fn);
}
-};
-var removeResizeListener = function (element, fn) {
+}
+
+function removeResizeListener(element, fn) {
if (ResizeObserver) {
if (BI.isNull(fn)) {
element.__resizeListeners__ = [];
element.__resizeObserver__ && element.__resizeObserver__.unobserve(element);
element.__resizeObserver__ = null;
+
return;
}
- var index = element.__resizeListeners__.indexOf(fn);
+ const index = element.__resizeListeners__.indexOf(fn);
if (index >= 0) {
element.__resizeListeners__.splice(index, 1);
if (!element.__resizeListeners__.length) {
@@ -592,19 +38,17 @@ var removeResizeListener = function (element, fn) {
}
}
}
-};
+}
export const ResizeDetector = {
- addResizeListener: function (widget, fn) {
+ addResizeListener(widget, fn) {
addResizeListener(widget.element[0], fn);
+
return function () {
removeResizeListener(widget.element[0], fn);
};
- }, removeResizeListener: function (widget, fn) {
+ },
+ removeResizeListener(widget, fn) {
removeResizeListener(widget.element[0], fn);
- }
+ },
};
-
-Object.assign(BI, {
- ResizeDetector
-});
diff --git a/src/core/platform/web/dom.js b/src/core/platform/web/dom.js
index cc9ed0f8d..5835df64f 100644
--- a/src/core/platform/web/dom.js
+++ b/src/core/platform/web/dom.js
@@ -1,758 +1,784 @@
/**
* 对DOM操作的通用函数
- * @type {{}}
*/
-!(function () {
- BI.DOM = BI.DOM || {};
-
- BI.extend(BI.DOM, {
- ready: function (fn) {
- BI.Widget._renderEngine.createElement(document).ready(fn);
- }
+import { each, isEmpty, isNull } from "../../2.base";
+
+export function ready(fn) {
+ BI.Widget._renderEngine.createElement(document).ready(fn);
+}
+
+export function patchProps(fromElement, toElement) {
+ const elemData = BI.jQuery._data(fromElement[0]);
+ const events = elemData.events;
+ each(events, (eventKey, event) => {
+ each(event, (i, handler) => {
+ toElement.on(eventKey + (handler.namespace ? (`.${handler.namespace}`) : ""), handler);
+ });
});
+ const fromChildren = fromElement.children(), toChildren = toElement.children();
+ if (fromChildren.length !== toChildren.length) {
+ throw new Error("不匹配");
+ }
+ each(fromChildren, (i, child) => {
+ patchProps(BI.jQuery(child), BI.jQuery(toChildren[i]));
+ });
+ each(fromElement.data("__widgets"), (i, widget) => {
+ widget.element = toElement;
+ });
+}
- BI.extend(BI.DOM, {
-
- patchProps: function (fromElement, toElement) {
- var elemData = BI.jQuery._data(fromElement[0]);
- var events = elemData.events;
- BI.each(events, function (eventKey, event) {
- BI.each(event, function (i, handler) {
- toElement.on(eventKey + (handler.namespace ? ("." + handler.namespace) : ""), handler);
- });
- });
- var fromChildren = fromElement.children(), toChildren = toElement.children();
- if (fromChildren.length !== toChildren.length) {
- throw new Error("不匹配");
- }
- BI.each(fromChildren, function (i, child) {
- BI.DOM.patchProps(BI.jQuery(child), BI.jQuery(toChildren[i]));
- });
- BI.each(fromElement.data("__widgets"), function (i, widget) {
- widget.element = toElement;
- });
- },
- /**
- * 把dom数组或元素悬挂起来,使其不对html产生影响
- * @param dom
- */
- hang: function (doms) {
- if (BI.isEmpty(doms)) {
- return;
- }
- var frag = BI.Widget._renderEngine.createFragment();
- BI.each(doms, function (i, dom) {
- dom instanceof BI.Widget && (dom = dom.element);
- dom instanceof BI.$ && dom[0] && frag.appendChild(dom[0]);
- });
- return frag;
- },
-
- isExist: function (obj) {
- return BI.Widget._renderEngine.createElement("body").find(obj.element).length > 0;
- },
-
- // 预加载图片
- preloadImages: function (srcArray, onload) {
- var count = 0, images = [];
-
- function complete() {
- count++;
- if (count >= srcArray.length) {
- onload();
- }
- }
-
- BI.each(srcArray, function (i, src) {
- images[i] = new Image();
- images[i].src = src;
- images[i].onload = function () {
- complete();
- };
- images[i].onerror = function () {
- complete();
- };
- });
- },
-
- getTextSizeWidth: function (text, fontSize) {
- var span = BI.Widget._renderEngine.createElement("").addClass("text-width-span").appendTo("body");
-
- if (fontSize == null) {
- fontSize = 12;
- }
- fontSize = fontSize + "px";
-
- span.css("font-size", fontSize).text(text);
+/**
+ * 把dom数组或元素悬挂起来,使其不对html产生影响
+ * @param dom
+ */
+export function hang(doms) {
+ if (isEmpty(doms)) {
+ return;
+ }
+ const frag = BI.Widget._renderEngine.createFragment();
+ each(doms, (i, dom) => {
+ dom instanceof BI.Widget && (dom = dom.element);
+ dom instanceof BI.$ && dom[0] && frag.appendChild(dom[0]);
+ });
- var width = span.width();
- span.remove();
+ return frag;
+}
- return width;
- },
+export function isExist(obj) {
+ return BI.Widget._renderEngine.createElement("body").find(obj.element).length > 0;
+}
- getTextSizeHeight: function (text, fontSize) {
- var span = BI.Widget._renderEngine.createElement("").addClass("text-width-span").appendTo("body");
+// 预加载图片
+export function preloadImages(srcArray, onload) {
+ let count = 0;
+ const images = [];
- if (fontSize == null) {
- fontSize = 12;
- }
- fontSize = fontSize + "px";
-
- span.css("font-size", fontSize).text(text);
-
- var height = span.height();
- span.remove();
-
- return height;
- },
-
- // 获取滚动条的宽度,页面display: none时候获取到的为0
- getScrollWidth: function () {
- if (BI.isNull(this._scrollWidth) || this._scrollWidth === 0) {
- var ul = BI.Widget._renderEngine.createElement("
").width(50).height(50).css({
- position: "absolute",
- top: "-9999px",
- overflow: "scroll"
- }).appendTo("body");
- this._scrollWidth = ul[0].offsetWidth - ul[0].clientWidth;
- ul.destroy();
- }
- return this._scrollWidth;
- },
-
- getImage: function (param, fillStyle, backgroundColor) {
- var canvas = document.createElement("canvas");
- var ratio = 2;
- BI.Widget._renderEngine.createElement("body").append(canvas);
-
- var ctx = canvas.getContext("2d");
- ctx.font = "12px Helvetica Neue,Arial,PingFang SC,Hiragino Sans GB,Microsoft YaHei,微软雅黑,Heiti,黑体,sans-serif";
- var w = ctx.measureText(param).width + 4;
- canvas.width = w * ratio;
- canvas.height = 16 * ratio;
- ctx.font = 12 * ratio + "px Helvetica Neue,Arial,PingFang SC,Hiragino Sans GB,Microsoft YaHei,微软雅黑,Heiti,黑体,sans-serif";
- ctx.fillStyle = fillStyle || "#3685f2";
- ctx.textBaseline = "middle";
- // ctx.fillStyle = "#EAF2FD";
- ctx.fillText(param, 2 * ratio, 9 * ratio);
- BI.Widget._renderEngine.createElement(canvas).destroy();
- var backColor = backgroundColor || "rgba(54, 133, 242, 0.1)";
- // IE可以放大缩小所以要固定最大最小宽高
- return {
- width: w,
- height: 16,
- src: canvas.toDataURL("image/png"),
- style: "background-color: " + backColor + ";vertical-align: middle; margin: 0 1px; width:" + w + "px;height: 16px; max-width:" + w + "px;max-height: 16px; min-width:" + w + "px;min-height: 16px",
- param: param
- };
+ function complete() {
+ count++;
+ if (count >= srcArray.length) {
+ onload();
}
+ }
+
+ each(srcArray, (i, src) => {
+ images[i] = new Image();
+ images[i].src = src;
+ images[i].onload = function () {
+ complete();
+ };
+ images[i].onerror = function () {
+ complete();
+ };
});
-
- BI.extend(BI.DOM, {
-
- getLeftPosition: function (combo, popup, extraWidth, container) {
- var el = combo.element;
- var popupEl = popup.element;
- var elRect = el[0].getBoundingClientRect();
- var popupElRect = popupEl[0].getBoundingClientRect();
- var containerRect = container ? container.getBoundingClientRect() : { left: 0 };
-
- return {
- left: elRect.left - containerRect.left - popupElRect.width - (extraWidth || 0)
- };
- },
-
- getInnerLeftPosition: function (combo, popup, extraWidth) {
- return {
- left: combo.element.offset().left + (extraWidth || 0)
- };
- },
-
- getRightPosition: function (combo, popup, extraWidth, container) {
- var el = combo.element;
- var elRect = el[0].getBoundingClientRect();
- var containerRect = container ? container.getBoundingClientRect() : { left: 0 };
-
- return {
- left: elRect.left + elRect.width - containerRect.left + (extraWidth || 0)
- };
- },
-
- getInnerRightPosition: function (combo, popup, extraWidth) {
- var el = combo.element, viewBounds = popup.element.bounds();
- return {
- left: el.offset().left + el.outerWidth() - viewBounds.width - (extraWidth || 0)
- };
- },
-
- getTopPosition: function (combo, popup, extraHeight, container) {
- var el = combo.element;
- var popupEl = popup.element;
- var elRect = el[0].getBoundingClientRect();
- var popupElRect = popupEl[0].getBoundingClientRect();
- var containerRect = container ? container.getBoundingClientRect() : { top: 0 };
-
- return {
- top: elRect.top - containerRect.top - popupElRect.height - (extraHeight || 0)
- };
- },
-
- getBottomPosition: function (combo, popup, extraHeight, container) {
- var el = combo.element;
- var elRect = el[0].getBoundingClientRect();
- var containerRect = container ? container.getBoundingClientRect() : { top: 0 };
-
- return {
- top: elRect.top - containerRect.top + elRect.height + (extraHeight || 0)
- };
- },
-
- isLeftSpaceEnough: function (combo, popup, extraWidth) {
- return BI.DOM.getLeftPosition(combo, popup, extraWidth).left >= 0;
- },
-
- isInnerLeftSpaceEnough: function (combo, popup, extraWidth) {
- var viewBounds = popup.element.bounds(),
- windowBounds = BI.Widget._renderEngine.createElement("body").bounds();
- return BI.DOM.getInnerLeftPosition(combo, popup, extraWidth).left + viewBounds.width <= windowBounds.width;
- },
-
- isRightSpaceEnough: function (combo, popup, extraWidth) {
- var viewBounds = popup.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- return BI.DOM.getRightPosition(combo, popup, extraWidth).left + viewBounds.width <= viewportBounds.width;
- },
-
- isInnerRightSpaceEnough: function (combo, popup, extraWidth) {
- return BI.DOM.getInnerRightPosition(combo, popup, extraWidth).left >= 0;
- },
-
- isTopSpaceEnough: function (combo, popup, extraHeight) {
- return BI.DOM.getTopPosition(combo, popup, extraHeight).top >= 0;
- },
-
- isBottomSpaceEnough: function (combo, popup, extraHeight) {
- var viewBounds = popup.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- return BI.DOM.getBottomPosition(combo, popup, extraHeight).top + viewBounds.height <= viewportBounds.height;
- },
-
- isRightSpaceLarger: function (combo) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- return viewportBounds.width - comboBounds.right >= comboBounds.left;
- },
-
- isBottomSpaceLarger: function (combo) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- return viewportBounds.height - comboBounds.bottom >= comboBounds.top;
- },
-
- _getLeftAlignPosition: function (combo, popup, extraWidth, container) {
- var comboRect = combo.element[0].getBoundingClientRect(),
- popupRect = popup.element[0].getBoundingClientRect(),
- viewportRect = document.documentElement.getBoundingClientRect(),
- containerRect = container ? container.getBoundingClientRect() : { left: 0 };
- var left = comboRect.left - containerRect.left + extraWidth;
-
- if (comboRect.left + popupRect.width > viewportRect.width) {
- left = viewportRect.width - popupRect.width - containerRect.left;
- }
- return left;
- },
-
- getLeftAlignPosition: function (combo, popup, extraWidth, container) {
- var left = this._getLeftAlignPosition(combo, popup, extraWidth, container);
- var dir = "";
- // 如果放不下,优先使用RightAlign, 如果RightAlign也放不下, 再使用left=0
- var containerRect = container ? container.getBoundingClientRect() : { left: 0 };
- if (left + containerRect.left < 0) {
- left = this._getRightAlignPosition(combo, popup, extraWidth);
- dir = "left";
- }
- if (left + containerRect.left < 0) {
- left = 0 - containerRect.left;
- }
- return {
- left: left,
- dir: dir || "right"
- };
- },
-
- getLeftAdaptPosition: function (combo, popup, extraWidth, container) {
- if (BI.DOM.isLeftSpaceEnough(combo, popup, extraWidth, container)) {
- return BI.DOM.getLeftPosition(combo, popup, extraWidth, container);
- }
- return {
- left: 0
- };
- },
-
- _getRightAlignPosition: function (combo, popup, extraWidth, container) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- viewBounds = popup.element[0].getBoundingClientRect(),
- containerRect = container ? container.getBoundingClientRect() : { left: 0 };
- return comboBounds.left + comboBounds.width - viewBounds.width - extraWidth - containerRect.left;
- },
-
- getRightAlignPosition: function (combo, popup, extraWidth, container) {
- var left = this._getRightAlignPosition(combo, popup, extraWidth, container);
- var dir = "";
- // 如果放不下,优先使用LeftAlign, 如果LeftAlign也放不下, 再使用left=0
- if (left < 0) {
- left = this._getLeftAlignPosition(combo, popup, extraWidth, container);
- dir = "right";
- }
- if (left < 0) {
- left = 0;
- }
- return {
- left: left,
- dir: dir || "left"
- };
- },
-
- getRightAdaptPosition: function (combo, popup, extraWidth, container) {
- if (BI.DOM.isRightSpaceEnough(combo, popup, extraWidth, container)) {
- return BI.DOM.getRightPosition(combo, popup, extraWidth, container);
- }
- return {
- left: document.documentElement.getBoundingClientRect().width - popup.element[0].getBoundingClientRect().width - container.getBoundingClientRect().left
- };
- },
-
- getTopAlignPosition: function (combo, popup, extraHeight, needAdaptHeight, container) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- popupBounds = popup.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect(),
- containerBounds = container ? container.getBoundingClientRect() : { top: 0 };
- var top, adaptHeight, dir;
- if (BI.DOM.isBottomSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
- top = comboBounds.top - containerBounds.top + extraHeight;
- } else if (needAdaptHeight) {
- top = comboBounds.top - containerBounds.top + extraHeight;
- adaptHeight = viewportBounds.height - comboBounds.top;
- } else if (BI.DOM.isTopSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
- // 下方空间不足且不允许调整高度的情况下,优先使用上对齐
- top = comboBounds.top + comboBounds.height - popupBounds.height - containerBounds.top - extraHeight;
- dir = "top";
- } else {
- top = viewportBounds.height - popupBounds.height;
- if (top < extraHeight) {
- adaptHeight = viewportBounds.height - extraHeight;
- }
- }
- if (top < extraHeight) {
- top = extraHeight;
- }
- return adaptHeight ? {
- top: top,
- adaptHeight: adaptHeight,
- dir: dir || "bottom"
- } : {
- top: top,
- dir: dir || "bottom"
- };
- },
-
- getTopAdaptPosition: function (combo, popup, extraHeight, needAdaptHeight, positionRelativeElement) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- popupBounds = popup.element[0].getBoundingClientRect(),
- positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- if (BI.DOM.isTopSpaceEnough(combo, popup, extraHeight)) {
- return BI.DOM.getTopPosition(combo, popup, extraHeight);
- }
- if (needAdaptHeight) {
- return {
- top: 0 - positionRelativeElementRect.top,
- adaptHeight: comboBounds.top - extraHeight
- };
- }
- if (popupBounds.height + extraHeight > viewportBounds.height) {
- return {
- top: 0 - positionRelativeElementRect.top,
- adaptHeight: viewportBounds.height - extraHeight
- };
- }
- return {
- top: 0 - positionRelativeElementRect.top
- };
- },
-
- getBottomAlignPosition: function (combo, popup, extraHeight, needAdaptHeight, container) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- popupBounds = popup.element[0].getBoundingClientRect(),
- windowBounds = BI.Widget._renderEngine.createElement("body").bounds(),
- containerBounds = container ? container.getBoundingClientRect() : { top: 0 };
- var top, adaptHeight, dir;
- if (BI.DOM.isTopSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
- top = comboBounds.top + comboBounds.height - containerBounds.top - popupBounds.height;
- } else if (needAdaptHeight) {
- top = 0 - containerBounds.top;
- adaptHeight = comboBounds.top + comboBounds.height - extraHeight;
- } else if (BI.DOM.isBottomSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
- // 上方空间不足且不允许调整高度的情况下,优先使用下对齐
- top = comboBounds.top - containerBounds.top + extraHeight;
- dir = "bottom";
- } else {
- top = 0;
- if (popupBounds.height + extraHeight > windowBounds.height) {
- adaptHeight = windowBounds.height - extraHeight;
- }
- }
- if (top + containerBounds.top < 0) {
- top = 0;
- }
- return adaptHeight ? {
- top: top,
- adaptHeight: adaptHeight,
- dir: dir || "top"
- } : {
- top: top,
- dir: dir || "top"
- };
- },
-
- getBottomAdaptPosition: function (combo, popup, extraHeight, needAdaptHeight, positionRelativeElement) {
- var comboBounds = combo.element[0].getBoundingClientRect(),
- popupBounds = popup.element[0].getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect(),
- positionRelativeElementRect = positionRelativeElement.getBoundingClientRect();
- if (BI.DOM.isBottomSpaceEnough(combo, popup, extraHeight)) {
- return BI.DOM.getBottomPosition(combo, popup, extraHeight, positionRelativeElement);
- }
- if (needAdaptHeight) {
- return {
- top: comboBounds.top + comboBounds.height + extraHeight - positionRelativeElementRect.top,
- adaptHeight: viewportBounds.height - comboBounds.top - comboBounds.height - extraHeight
- };
- }
- if (popupBounds.height + extraHeight > viewportBounds.height) {
- return {
- top: extraHeight - positionRelativeElementRect.top,
- adaptHeight: viewportBounds.height - extraHeight
- };
- }
- return {
- top: viewportBounds.height - popupBounds.height - extraHeight - positionRelativeElementRect.top
- };
- },
-
- getCenterAdaptPosition: function (combo, popup, positionRelativeElement) {
- var comboRect = combo.element[0].getBoundingClientRect(),
- popupRect = popup.element[0].getBoundingClientRect(),
- positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
- var left;
- if (comboRect.left + comboRect.width / 2 + popupRect.width / 2 > viewportBounds.width) {
- left = viewportBounds.width - popupRect.width - positionRelativeElementRect.left;
- } else {
- left = comboRect.left + (comboRect.width - popupRect.width) / 2 - positionRelativeElementRect.left;
- }
- if (left + positionRelativeElementRect.left < 0) {
- left = 0;
- }
- return {
- left: left
- };
- },
-
- getMiddleAdaptPosition: function (combo, popup, positionRelativeElement) {
- var comboRect = combo.element[0].getBoundingClientRect(),
- popupRect = popup.element[0].getBoundingClientRect(),
- positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
- viewportBounds = document.documentElement.getBoundingClientRect();
-
- var top;
- if (comboRect.top + comboRect.height / 2 + popupRect.height / 2 > viewportBounds.height) {
- top = viewportBounds.height - popupRect.height - positionRelativeElementRect.top;
- } else {
- top = comboRect.top + (comboRect.height - popupRect.height) / 2 - positionRelativeElementRect.top;
- }
- if (top + positionRelativeElementRect.top < 0) {
- top = 0;
- }
- return {
- top: top
- };
- },
-
- getComboPositionByDirections: function (combo, popup, extraWidth, extraHeight, needAdaptHeight, directions, container) {
- extraWidth || (extraWidth = 0);
- extraHeight || (extraHeight = 0);
- var i, direct;
- var leftRight = [], topBottom = [], innerLeftRight = [];
- var isNeedAdaptHeight = false, tbFirst = false, lrFirst = false;
- var left, top, pos, firstDir = directions[0];
- for (i = 0; i < directions.length; i++) {
- direct = directions[i];
- switch (direct) {
- case "left":
- leftRight.push(direct);
- break;
- case "right":
- leftRight.push(direct);
- break;
- case "top":
- topBottom.push(direct);
- break;
- case "bottom":
- topBottom.push(direct);
- break;
- case "innerLeft":
- innerLeftRight.push(direct);
- break;
- case "innerRight":
- innerLeftRight.push(direct);
- break;
- }
- }
- for (i = 0; i < directions.length; i++) {
- direct = directions[i];
- switch (direct) {
- case "left":
- if (!isNeedAdaptHeight) {
- var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? 0 : extraHeight;
- if (BI.DOM.isLeftSpaceEnough(combo, popup, tW)) {
- left = BI.DOM.getLeftPosition(combo, popup, tW, container).left;
- if (topBottom[0] === "bottom") {
- pos = BI.DOM.getTopAlignPosition(combo, popup, tH, needAdaptHeight, container);
- } else {
- pos = BI.DOM.getBottomAlignPosition(combo, popup, tH, needAdaptHeight, container);
- }
- pos.dir = "left," + pos.dir;
- if (tbFirst) {
- pos.change = "left";
- }
- pos.left = left;
- return pos;
- }
- }
- lrFirst = true;
- break;
- case "right":
- if (!isNeedAdaptHeight) {
- var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? extraWidth : extraHeight;
- if (BI.DOM.isRightSpaceEnough(combo, popup, tW)) {
- left = BI.DOM.getRightPosition(combo, popup, tW, container).left;
- if (topBottom[0] === "bottom") {
- pos = BI.DOM.getTopAlignPosition(combo, popup, tH, needAdaptHeight, container);
- } else {
- pos = BI.DOM.getBottomAlignPosition(combo, popup, tH, needAdaptHeight, container);
- }
- pos.dir = "right," + pos.dir;
- if (tbFirst) {
- pos.change = "right";
- }
- pos.left = left;
- return pos;
- }
- }
- lrFirst = true;
- break;
- case "top":
- var tW = lrFirst ? extraHeight : extraWidth, tH = lrFirst ? extraWidth : extraHeight;
- if (BI.DOM.isTopSpaceEnough(combo, popup, tH)) {
- top = BI.DOM.getTopPosition(combo, popup, tH, container).top;
- if (leftRight[0] === "right") {
- pos = BI.DOM.getLeftAlignPosition(combo, popup, tW, container);
- } else {
- pos = BI.DOM.getRightAlignPosition(combo, popup, tW, container);
- }
- pos.dir = "top," + pos.dir;
- if (lrFirst) {
- pos.change = "top";
- }
- pos.top = top;
- return pos;
- }
- if (needAdaptHeight) {
- isNeedAdaptHeight = true;
- }
- tbFirst = true;
- break;
- case "bottom":
- var tW = lrFirst ? extraHeight : extraWidth, tH = lrFirst ? extraWidth : extraHeight;
- if (BI.DOM.isBottomSpaceEnough(combo, popup, tH)) {
- top = BI.DOM.getBottomPosition(combo, popup, tH, container).top;
- if (leftRight[0] === "right") {
- pos = BI.DOM.getLeftAlignPosition(combo, popup, tW, container);
- } else {
- pos = BI.DOM.getRightAlignPosition(combo, popup, tW, container);
- }
- pos.dir = "bottom," + pos.dir;
- if (lrFirst) {
- pos.change = "bottom";
- }
- pos.top = top;
- return pos;
+}
+
+export function getTextSizeWidth(text, fontSize = 12) {
+ const span = BI.Widget._renderEngine.createElement("
").addClass("text-width-span").appendTo("body");
+
+ fontSize = `${fontSize}px`;
+
+ span.css("font-size", fontSize).text(text);
+
+ const width = span.width();
+ span.remove();
+
+ return width;
+}
+
+export function getTextSizeHeight(text, fontSize = 12) {
+ const span = BI.Widget._renderEngine.createElement("
").addClass("text-width-span").appendTo("body");
+
+ fontSize = `${fontSize}px`;
+
+ span.css("font-size", fontSize).text(text);
+
+ const height = span.height();
+ span.remove();
+
+ return height;
+}
+
+// 获取滚动条的宽度,页面display: none时候获取到的为0
+let _scrollWidth = null;
+
+export function getScrollWidth() {
+ if (isNull(_scrollWidth) || _scrollWidth === 0) {
+ const ul = BI.Widget._renderEngine.createElement("
").width(50).height(50)
+ .css({
+ position: "absolute",
+ top: "-9999px",
+ overflow: "scroll",
+ })
+ .appendTo("body");
+ _scrollWidth = ul[0].offsetWidth - ul[0].clientWidth;
+ ul.destroy();
+ }
+
+ return _scrollWidth;
+}
+
+export function getImage(param, fillStyle, backgroundColor) {
+ const canvas = document.createElement("canvas");
+ const ratio = 2;
+ BI.Widget._renderEngine.createElement("body").append(canvas);
+
+ const ctx = canvas.getContext("2d");
+ ctx.font = "12px Helvetica Neue,Arial,PingFang SC,Hiragino Sans GB,Microsoft YaHei,微软雅黑,Heiti,黑体,sans-serif";
+ const w = ctx.measureText(param).width + 4;
+ canvas.width = w * ratio;
+ canvas.height = 16 * ratio;
+ ctx.font = `${12 * ratio}px Helvetica Neue,Arial,PingFang SC,Hiragino Sans GB,Microsoft YaHei,微软雅黑,Heiti,黑体,sans-serif`;
+ ctx.fillStyle = fillStyle || "#3685f2";
+ ctx.textBaseline = "middle";
+ // ctx.fillStyle = "#EAF2FD";
+ ctx.fillText(param, 2 * ratio, 9 * ratio);
+ BI.Widget._renderEngine.createElement(canvas).destroy();
+ const backColor = backgroundColor || "rgba(54, 133, 242, 0.1)";
+
+ // IE可以放大缩小所以要固定最大最小宽高
+ return {
+ width: w,
+ height: 16,
+ src: canvas.toDataURL("image/png"),
+ style: `background-color: ${backColor};vertical-align: middle; margin: 0 1px; width:${w}px;height: 16px; max-width:${w}px;max-height: 16px; min-width:${w}px;min-height: 16px`,
+ param,
+ };
+}
+
+export function getLeftPosition(combo, popup, extraWidth, container) {
+ const el = combo.element;
+ const popupEl = popup.element;
+ const elRect = el[0].getBoundingClientRect();
+ const popupElRect = popupEl[0].getBoundingClientRect();
+ const containerRect = container ? container.getBoundingClientRect() : { left: 0 };
+
+ return {
+ left: elRect.left - containerRect.left - popupElRect.width - (extraWidth || 0),
+ };
+}
+
+export function getInnerLeftPosition(combo, popup, extraWidth) {
+ return {
+ left: combo.element.offset().left + (extraWidth || 0),
+ };
+}
+
+export function getRightPosition(combo, popup, extraWidth, container) {
+ const el = combo.element;
+ const elRect = el[0].getBoundingClientRect();
+ const containerRect = container ? container.getBoundingClientRect() : { left: 0 };
+
+ return {
+ left: elRect.left + elRect.width - containerRect.left + (extraWidth || 0),
+ };
+}
+
+export function getInnerRightPosition(combo, popup, extraWidth) {
+ const el = combo.element, viewBounds = popup.element.bounds();
+
+ return {
+ left: el.offset().left + el.outerWidth() - viewBounds.width - (extraWidth || 0),
+ };
+}
+
+export function getTopPosition(combo, popup, extraHeight, container) {
+ const el = combo.element;
+ const popupEl = popup.element;
+ const elRect = el[0].getBoundingClientRect();
+ const popupElRect = popupEl[0].getBoundingClientRect();
+ const containerRect = container ? container.getBoundingClientRect() : { top: 0 };
+
+ return {
+ top: elRect.top - containerRect.top - popupElRect.height - (extraHeight || 0),
+ };
+}
+
+export function getBottomPosition(combo, popup, extraHeight, container) {
+ const el = combo.element;
+ const elRect = el[0].getBoundingClientRect();
+ const containerRect = container ? container.getBoundingClientRect() : { top: 0 };
+
+ return {
+ top: elRect.top - containerRect.top + elRect.height + (extraHeight || 0),
+ };
+}
+
+export function isLeftSpaceEnough(combo, popup, extraWidth) {
+ return getLeftPosition(combo, popup, extraWidth).left >= 0;
+}
+
+export function isInnerLeftSpaceEnough(combo, popup, extraWidth) {
+ const viewBounds = popup.element.bounds(),
+ windowBounds = BI.Widget._renderEngine.createElement("body").bounds();
+
+ return getInnerLeftPosition(combo, popup, extraWidth).left + viewBounds.width <= windowBounds.width;
+}
+
+export function isRightSpaceEnough(combo, popup, extraWidth) {
+ const viewBounds = popup.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+
+ return getRightPosition(combo, popup, extraWidth).left + viewBounds.width <= viewportBounds.width;
+}
+
+export function isInnerRightSpaceEnough(combo, popup, extraWidth) {
+ return getInnerRightPosition(combo, popup, extraWidth).left >= 0;
+}
+
+export function isTopSpaceEnough(combo, popup, extraHeight) {
+ return getTopPosition(combo, popup, extraHeight).top >= 0;
+}
+
+export function isBottomSpaceEnough(combo, popup, extraHeight) {
+ const viewBounds = popup.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+
+ return getBottomPosition(combo, popup, extraHeight).top + viewBounds.height <= viewportBounds.height;
+}
+
+export function isRightSpaceLarger(combo) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+
+ return viewportBounds.width - comboBounds.right >= comboBounds.left;
+}
+
+export function isBottomSpaceLarger(combo) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+
+ return viewportBounds.height - comboBounds.bottom >= comboBounds.top;
+}
+
+export function _getLeftAlignPosition(combo, popup, extraWidth, container) {
+ const comboRect = combo.element[0].getBoundingClientRect(),
+ popupRect = popup.element[0].getBoundingClientRect(),
+ viewportRect = document.documentElement.getBoundingClientRect(),
+ containerRect = container ? container.getBoundingClientRect() : { left: 0 };
+ let left = comboRect.left - containerRect.left + extraWidth;
+
+ if (comboRect.left + popupRect.width > viewportRect.width) {
+ left = viewportRect.width - popupRect.width - containerRect.left;
+ }
+
+ return left;
+}
+
+export function getLeftAlignPosition(combo, popup, extraWidth, container) {
+ let left = this._getLeftAlignPosition(combo, popup, extraWidth, container);
+ let dir = "";
+ // 如果放不下,优先使用RightAlign, 如果RightAlign也放不下, 再使用left=0
+ const containerRect = container ? container.getBoundingClientRect() : { left: 0 };
+ if (left + containerRect.left < 0) {
+ left = this._getRightAlignPosition(combo, popup, extraWidth);
+ dir = "left";
+ }
+ if (left + containerRect.left < 0) {
+ left = 0 - containerRect.left;
+ }
+
+ return {
+ left,
+ dir: dir || "right",
+ };
+}
+
+export function getLeftAdaptPosition(combo, popup, extraWidth, container) {
+ if (isLeftSpaceEnough(combo, popup, extraWidth, container)) {
+ return getLeftPosition(combo, popup, extraWidth, container);
+ }
+
+ return {
+ left: 0,
+ };
+}
+
+export function _getRightAlignPosition(combo, popup, extraWidth, container) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ viewBounds = popup.element[0].getBoundingClientRect(),
+ containerRect = container ? container.getBoundingClientRect() : { left: 0 };
+
+ return comboBounds.left + comboBounds.width - viewBounds.width - extraWidth - containerRect.left;
+}
+
+export function getRightAlignPosition(combo, popup, extraWidth, container) {
+ let left = this._getRightAlignPosition(combo, popup, extraWidth, container);
+ let dir = "";
+ // 如果放不下,优先使用LeftAlign, 如果LeftAlign也放不下, 再使用left=0
+ if (left < 0) {
+ left = this._getLeftAlignPosition(combo, popup, extraWidth, container);
+ dir = "right";
+ }
+ if (left < 0) {
+ left = 0;
+ }
+
+ return {
+ left,
+ dir: dir || "left",
+ };
+}
+
+export function getRightAdaptPosition(combo, popup, extraWidth, container) {
+ if (isRightSpaceEnough(combo, popup, extraWidth, container)) {
+ return getRightPosition(combo, popup, extraWidth, container);
+ }
+
+ return {
+ left: document.documentElement.getBoundingClientRect().width - popup.element[0].getBoundingClientRect().width - container.getBoundingClientRect().left,
+ };
+}
+
+export function getTopAlignPosition(combo, popup, extraHeight, needAdaptHeight, container) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ popupBounds = popup.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect(),
+ containerBounds = container ? container.getBoundingClientRect() : { top: 0 };
+ let top, adaptHeight, dir;
+ if (isBottomSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
+ top = comboBounds.top - containerBounds.top + extraHeight;
+ } else if (needAdaptHeight) {
+ top = comboBounds.top - containerBounds.top + extraHeight;
+ adaptHeight = viewportBounds.height - comboBounds.top;
+ } else if (isTopSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
+ // 下方空间不足且不允许调整高度的情况下,优先使用上对齐
+ top = comboBounds.top + comboBounds.height - popupBounds.height - containerBounds.top - extraHeight;
+ dir = "top";
+ } else {
+ top = viewportBounds.height - popupBounds.height;
+ if (top < extraHeight) {
+ adaptHeight = viewportBounds.height - extraHeight;
+ }
+ }
+ if (top < extraHeight) {
+ top = extraHeight;
+ }
+
+ return adaptHeight ? {
+ top,
+ adaptHeight,
+ dir: dir || "bottom",
+ } : {
+ top,
+ dir: dir || "bottom",
+ };
+}
+
+export function getTopAdaptPosition(combo, popup, extraHeight, needAdaptHeight, positionRelativeElement) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ popupBounds = popup.element[0].getBoundingClientRect(),
+ positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+ if (isTopSpaceEnough(combo, popup, extraHeight)) {
+ return getTopPosition(combo, popup, extraHeight);
+ }
+ if (needAdaptHeight) {
+ return {
+ top: 0 - positionRelativeElementRect.top,
+ adaptHeight: comboBounds.top - extraHeight,
+ };
+ }
+ if (popupBounds.height + extraHeight > viewportBounds.height) {
+ return {
+ top: 0 - positionRelativeElementRect.top,
+ adaptHeight: viewportBounds.height - extraHeight,
+ };
+ }
+
+ return {
+ top: 0 - positionRelativeElementRect.top,
+ };
+}
+
+export function getBottomAlignPosition(combo, popup, extraHeight, needAdaptHeight, container) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ popupBounds = popup.element[0].getBoundingClientRect(),
+ windowBounds = BI.Widget._renderEngine.createElement("body").bounds(),
+ containerBounds = container ? container.getBoundingClientRect() : { top: 0 };
+ let top, adaptHeight, dir;
+ if (isTopSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
+ top = comboBounds.top + comboBounds.height - containerBounds.top - popupBounds.height;
+ } else if (needAdaptHeight) {
+ top = 0 - containerBounds.top;
+ adaptHeight = comboBounds.top + comboBounds.height - extraHeight;
+ } else if (isBottomSpaceEnough(combo, popup, -1 * comboBounds.height + extraHeight)) {
+ // 上方空间不足且不允许调整高度的情况下,优先使用下对齐
+ top = comboBounds.top - containerBounds.top + extraHeight;
+ dir = "bottom";
+ } else {
+ top = 0;
+ if (popupBounds.height + extraHeight > windowBounds.height) {
+ adaptHeight = windowBounds.height - extraHeight;
+ }
+ }
+ if (top + containerBounds.top < 0) {
+ top = 0;
+ }
+
+ return adaptHeight ? {
+ top,
+ adaptHeight,
+ dir: dir || "top",
+ } : {
+ top,
+ dir: dir || "top",
+ };
+}
+
+export function getBottomAdaptPosition(combo, popup, extraHeight, needAdaptHeight, positionRelativeElement) {
+ const comboBounds = combo.element[0].getBoundingClientRect(),
+ popupBounds = popup.element[0].getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect(),
+ positionRelativeElementRect = positionRelativeElement.getBoundingClientRect();
+ if (isBottomSpaceEnough(combo, popup, extraHeight)) {
+ return getBottomPosition(combo, popup, extraHeight, positionRelativeElement);
+ }
+ if (needAdaptHeight) {
+ return {
+ top: comboBounds.top + comboBounds.height + extraHeight - positionRelativeElementRect.top,
+ adaptHeight: viewportBounds.height - comboBounds.top - comboBounds.height - extraHeight,
+ };
+ }
+ if (popupBounds.height + extraHeight > viewportBounds.height) {
+ return {
+ top: extraHeight - positionRelativeElementRect.top,
+ adaptHeight: viewportBounds.height - extraHeight,
+ };
+ }
+
+ return {
+ top: viewportBounds.height - popupBounds.height - extraHeight - positionRelativeElementRect.top,
+ };
+}
+
+export function getCenterAdaptPosition(combo, popup, positionRelativeElement) {
+ const comboRect = combo.element[0].getBoundingClientRect(),
+ popupRect = popup.element[0].getBoundingClientRect(),
+ positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+ let left;
+ if (comboRect.left + comboRect.width / 2 + popupRect.width / 2 > viewportBounds.width) {
+ left = viewportBounds.width - popupRect.width - positionRelativeElementRect.left;
+ } else {
+ left = comboRect.left + (comboRect.width - popupRect.width) / 2 - positionRelativeElementRect.left;
+ }
+ if (left + positionRelativeElementRect.left < 0) {
+ left = 0;
+ }
+
+ return {
+ left,
+ };
+}
+
+export function getMiddleAdaptPosition(combo, popup, positionRelativeElement) {
+ const comboRect = combo.element[0].getBoundingClientRect(),
+ popupRect = popup.element[0].getBoundingClientRect(),
+ positionRelativeElementRect = positionRelativeElement.getBoundingClientRect(),
+ viewportBounds = document.documentElement.getBoundingClientRect();
+
+ let top;
+ if (comboRect.top + comboRect.height / 2 + popupRect.height / 2 > viewportBounds.height) {
+ top = viewportBounds.height - popupRect.height - positionRelativeElementRect.top;
+ } else {
+ top = comboRect.top + (comboRect.height - popupRect.height) / 2 - positionRelativeElementRect.top;
+ }
+ if (top + positionRelativeElementRect.top < 0) {
+ top = 0;
+ }
+
+ return {
+ top,
+ };
+}
+
+export function getComboPositionByDirections(combo, popup, extraWidth, extraHeight, needAdaptHeight, directions, container) {
+ extraWidth || (extraWidth = 0);
+ extraHeight || (extraHeight = 0);
+ let i, direct;
+ const leftRight = [], topBottom = [], innerLeftRight = [];
+ let isNeedAdaptHeight = false, tbFirst = false, lrFirst = false;
+ let left, top, pos, firstDir = directions[0];
+ for (i = 0; i < directions.length; i++) {
+ direct = directions[i];
+ switch (direct) {
+ case "left":
+ leftRight.push(direct);
+ break;
+ case "right":
+ leftRight.push(direct);
+ break;
+ case "top":
+ topBottom.push(direct);
+ break;
+ case "bottom":
+ topBottom.push(direct);
+ break;
+ case "innerLeft":
+ innerLeftRight.push(direct);
+ break;
+ case "innerRight":
+ innerLeftRight.push(direct);
+ break;
+ default:
+ break;
+ }
+ }
+ for (i = 0; i < directions.length; i++) {
+ direct = directions[i];
+ switch (direct) {
+ case "left":
+ if (!isNeedAdaptHeight) {
+ var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? 0 : extraHeight;
+ if (isLeftSpaceEnough(combo, popup, tW)) {
+ left = getLeftPosition(combo, popup, tW, container).left;
+ if (topBottom[0] === "bottom") {
+ pos = getTopAlignPosition(combo, popup, tH, needAdaptHeight, container);
+ } else {
+ pos = getBottomAlignPosition(combo, popup, tH, needAdaptHeight, container);
}
- if (needAdaptHeight) {
- isNeedAdaptHeight = true;
+ pos.dir = `left,${pos.dir}`;
+ if (tbFirst) {
+ pos.change = "left";
}
- tbFirst = true;
- break;
- case "innerLeft":
- if (!isNeedAdaptHeight) {
- var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? 0 : extraHeight;
- if (BI.DOM.isInnerLeftSpaceEnough(combo, popup, tW)) {
- left = BI.DOM.getInnerLeftPosition(combo, popup, tW).left;
- if (topBottom[0] === "bottom") {
- pos = BI.DOM.getTopAlignPosition(combo, popup, tH, needAdaptHeight);
- } else {
- pos = BI.DOM.getBottomAlignPosition(combo, popup, tH, needAdaptHeight);
- }
- pos.dir = "innerLeft," + pos.dir;
- if (tbFirst) {
- pos.change = "innerLeft";
- }
- pos.left = left;
- return pos;
- }
+ pos.left = left;
+
+ return pos;
+ }
+ }
+ lrFirst = true;
+ break;
+ case "right":
+ if (!isNeedAdaptHeight) {
+ var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? extraWidth : extraHeight;
+ if (isRightSpaceEnough(combo, popup, tW)) {
+ left = getRightPosition(combo, popup, tW, container).left;
+ if (topBottom[0] === "bottom") {
+ pos = getTopAlignPosition(combo, popup, tH, needAdaptHeight, container);
+ } else {
+ pos = getBottomAlignPosition(combo, popup, tH, needAdaptHeight, container);
}
- lrFirst = true;
- break;
- case "innerRight":
- if (!isNeedAdaptHeight) {
- var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? extraWidth : extraHeight;
- if (BI.DOM.isInnerRightSpaceEnough(combo, popup, tW)) {
- left = BI.DOM.getInnerRightPosition(combo, popup, tW).left;
- if (topBottom[0] === "bottom") {
- pos = BI.DOM.getTopAlignPosition(combo, popup, tH, needAdaptHeight);
- } else {
- pos = BI.DOM.getBottomAlignPosition(combo, popup, tH, needAdaptHeight);
- }
- pos.dir = "innerLeft," + pos.dir;
- if (tbFirst) {
- pos.change = "innerRight";
- }
- pos.left = left;
- return pos;
- }
+ pos.dir = `right,${pos.dir}`;
+ if (tbFirst) {
+ pos.change = "right";
}
- break;
+ pos.left = left;
+ return pos;
+ }
}
- }
-
- // 此处为四个方向放不下时挑空间最大的方向去放置, 也就是说我设置了弹出方向为"bottom,left",
- // 最后发现实际弹出方向可能是"top,left",那么此时外界获取popup的方向应该是"top,left"
- switch (directions[0]) {
- case "left":
- case "right":
- if (BI.DOM.isRightSpaceLarger(combo)) {
- left = BI.DOM.getRightAdaptPosition(combo, popup, extraWidth, container).left;
- firstDir = "right";
+ lrFirst = true;
+ break;
+ case "top":
+ var tW = lrFirst ? extraHeight : extraWidth, tH = lrFirst ? extraWidth : extraHeight;
+ if (isTopSpaceEnough(combo, popup, tH)) {
+ top = getTopPosition(combo, popup, tH, container).top;
+ if (leftRight[0] === "right") {
+ pos = getLeftAlignPosition(combo, popup, tW, container);
} else {
- left = BI.DOM.getLeftAdaptPosition(combo, popup, extraWidth, container).left;
- firstDir = "left";
+ pos = getRightAlignPosition(combo, popup, tW, container);
}
- if (topBottom[0] === "bottom") {
- pos = BI.DOM.getTopAlignPosition(combo, popup, extraHeight, needAdaptHeight);
- pos.left = left;
- pos.dir = firstDir + "," + pos.dir;
- return pos;
+ pos.dir = `top,${pos.dir}`;
+ if (lrFirst) {
+ pos.change = "top";
}
- pos = BI.DOM.getBottomAlignPosition(combo, popup, extraHeight, needAdaptHeight);
- pos.left = left;
- pos.dir = firstDir + "," + pos.dir;
+ pos.top = top;
+
return pos;
- default :
- if (BI.DOM.isBottomSpaceLarger(combo)) {
- top = BI.DOM.getBottomAdaptPosition(combo, popup, extraHeight, needAdaptHeight, container).top;
- firstDir = "bottom";
+ }
+ if (needAdaptHeight) {
+ isNeedAdaptHeight = true;
+ }
+ tbFirst = true;
+ break;
+ case "bottom":
+ var tW = lrFirst ? extraHeight : extraWidth, tH = lrFirst ? extraWidth : extraHeight;
+ if (isBottomSpaceEnough(combo, popup, tH)) {
+ top = getBottomPosition(combo, popup, tH, container).top;
+ if (leftRight[0] === "right") {
+ pos = getLeftAlignPosition(combo, popup, tW, container);
} else {
- top = BI.DOM.getTopAdaptPosition(combo, popup, extraHeight, needAdaptHeight, container).top;
- firstDir = "top";
+ pos = getRightAlignPosition(combo, popup, tW, container);
}
- if (leftRight[0] === "right") {
- pos = BI.DOM.getLeftAlignPosition(combo, popup, extraWidth, container);
- pos.top = top;
- pos.dir = firstDir + "," + pos.dir;
- return pos;
+ pos.dir = `bottom,${pos.dir}`;
+ if (lrFirst) {
+ pos.change = "bottom";
}
- pos = BI.DOM.getRightAlignPosition(combo, popup, extraWidth, container);
pos.top = top;
- pos.dir = firstDir + "," + pos.dir;
+
return pos;
- }
- },
-
-
- getComboPosition: function (combo, popup, extraWidth, extraHeight, needAdaptHeight, directions, offsetStyle, positionRelativeElement) {
- extraWidth || (extraWidth = 0);
- extraHeight || (extraHeight = 0);
- var viewportBounds = document.documentElement.getBoundingClientRect();
- var maxHeight = Math.min(popup.attr("maxHeight") || viewportBounds.height, viewportBounds.height);
- popup.resetHeight && popup.resetHeight(maxHeight);
- var position = BI.DOM.getComboPositionByDirections(combo, popup, extraWidth, extraHeight, needAdaptHeight, directions || ["bottom", "top", "right", "left"], positionRelativeElement);
- switch (offsetStyle) {
- case "center":
- if (position.change) {
- var p = BI.DOM.getMiddleAdaptPosition(combo, popup, positionRelativeElement);
- position.top = p.top;
- } else {
- var p = BI.DOM.getCenterAdaptPosition(combo, popup, positionRelativeElement);
- position.left = p.left;
+ }
+ if (needAdaptHeight) {
+ isNeedAdaptHeight = true;
+ }
+ tbFirst = true;
+ break;
+ case "innerLeft":
+ if (!isNeedAdaptHeight) {
+ var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? 0 : extraHeight;
+ if (isInnerLeftSpaceEnough(combo, popup, tW)) {
+ left = getInnerLeftPosition(combo, popup, tW).left;
+ if (topBottom[0] === "bottom") {
+ pos = getTopAlignPosition(combo, popup, tH, needAdaptHeight);
+ } else {
+ pos = getBottomAlignPosition(combo, popup, tH, needAdaptHeight);
+ }
+ pos.dir = `innerLeft,${pos.dir}`;
+ if (tbFirst) {
+ pos.change = "innerLeft";
+ }
+ pos.left = left;
+
+ return pos;
}
- break;
- case "middle":
- if (position.change) {
- var p = BI.DOM.getCenterAdaptPosition(combo, popup, positionRelativeElement);
- position.left = p.left;
- } else {
- var p = BI.DOM.getMiddleAdaptPosition(combo, popup, positionRelativeElement);
- position.top = p.top;
+ }
+ lrFirst = true;
+ break;
+ case "innerRight":
+ if (!isNeedAdaptHeight) {
+ var tW = tbFirst ? extraHeight : extraWidth, tH = tbFirst ? extraWidth : extraHeight;
+ if (isInnerRightSpaceEnough(combo, popup, tW)) {
+ left = getInnerRightPosition(combo, popup, tW).left;
+ if (topBottom[0] === "bottom") {
+ pos = getTopAlignPosition(combo, popup, tH, needAdaptHeight);
+ } else {
+ pos = getBottomAlignPosition(combo, popup, tH, needAdaptHeight);
+ }
+ pos.dir = `innerLeft,${pos.dir}`;
+ if (tbFirst) {
+ pos.change = "innerRight";
+ }
+ pos.left = left;
+
+ return pos;
}
- break;
+ }
+ break;
+ default:
+ break;
+ }
+ }
+
+ // 此处为四个方向放不下时挑空间最大的方向去放置, 也就是说我设置了弹出方向为"bottom,left",
+ // 最后发现实际弹出方向可能是"top,left",那么此时外界获取popup的方向应该是"top,left"
+ switch (directions[0]) {
+ case "left":
+ case "right":
+ if (isRightSpaceLarger(combo)) {
+ left = getRightAdaptPosition(combo, popup, extraWidth, container).left;
+ firstDir = "right";
+ } else {
+ left = getLeftAdaptPosition(combo, popup, extraWidth, container).left;
+ firstDir = "left";
}
- if (needAdaptHeight === true) {
- popup.resetHeight && popup.resetHeight(Math.min(viewportBounds.height - position.top - (positionRelativeElement ? positionRelativeElement.getBoundingClientRect().top : 0), maxHeight));
+ if (topBottom[0] === "bottom") {
+ pos = getTopAlignPosition(combo, popup, extraHeight, needAdaptHeight);
+ pos.left = left;
+ pos.dir = `${firstDir},${pos.dir}`;
+
+ return pos;
}
- return position;
- },
-
- /**
- * 获取position:fixed相对定位的元素
- */
- getPositionRelativeContainingBlock: function (element) {
- if (['html', 'body', '#document'].indexOf((element.nodeName || '').toLowerCase()) >= 0) {
- // $FlowFixMe[incompatible-return]: assume body is always available
- return element.ownerDocument.body;
+ pos = getBottomAlignPosition(combo, popup, extraHeight, needAdaptHeight);
+ pos.left = left;
+ pos.dir = `${firstDir},${pos.dir}`;
+
+ return pos;
+ default :
+ if (isBottomSpaceLarger(combo)) {
+ top = getBottomAdaptPosition(combo, popup, extraHeight, needAdaptHeight, container).top;
+ firstDir = "bottom";
+ } else {
+ top = getTopAdaptPosition(combo, popup, extraHeight, needAdaptHeight, container).top;
+ firstDir = "top";
+ }
+ if (leftRight[0] === "right") {
+ pos = getLeftAlignPosition(combo, popup, extraWidth, container);
+ pos.top = top;
+ pos.dir = `${firstDir},${pos.dir}`;
+
+ return pos;
+ }
+ pos = getRightAlignPosition(combo, popup, extraWidth, container);
+ pos.top = top;
+ pos.dir = `${firstDir},${pos.dir}`;
+
+ return pos;
+ }
+}
+
+
+export function getComboPosition(combo, popup, extraWidth, extraHeight, needAdaptHeight, directions, offsetStyle, positionRelativeElement) {
+ extraWidth || (extraWidth = 0);
+ extraHeight || (extraHeight = 0);
+ const viewportBounds = document.documentElement.getBoundingClientRect();
+ const maxHeight = Math.min(popup.attr("maxHeight") || viewportBounds.height, viewportBounds.height);
+ popup.resetHeight && popup.resetHeight(maxHeight);
+ const position = getComboPositionByDirections(combo, popup, extraWidth, extraHeight, needAdaptHeight, directions || ["bottom", "top", "right", "left"], positionRelativeElement);
+ switch (offsetStyle) {
+ case "center":
+ if (position.change) {
+ var p = getMiddleAdaptPosition(combo, popup, positionRelativeElement);
+ position.top = p.top;
+ } else {
+ var p = getCenterAdaptPosition(combo, popup, positionRelativeElement);
+ position.left = p.left;
+ }
+ break;
+ case "middle":
+ if (position.change) {
+ var p = getCenterAdaptPosition(combo, popup, positionRelativeElement);
+ position.left = p.left;
+ } else {
+ var p = getMiddleAdaptPosition(combo, popup, positionRelativeElement);
+ position.top = p.top;
}
+ break;
+ default:
+ break;
+ }
+ if (needAdaptHeight === true) {
+ popup.resetHeight && popup.resetHeight(Math.min(viewportBounds.height - position.top - (positionRelativeElement ? positionRelativeElement.getBoundingClientRect().top : 0), maxHeight));
+ }
- function isExcept(node) {
- var _computedStyle = getComputedStyle(node);
- var transform = _computedStyle.transform;
- var perspective = _computedStyle.perspective;
- var filter = _computedStyle.filter;
- var willChange = _computedStyle["will-change"];
+ return position;
+}
- return [transform, perspective, filter].some(value => value !== 'none') || (willChange === "transform");
- }
+/**
+ * 获取position:fixed相对定位的元素
+ */
+export function getPositionRelativeContainingBlock(element) {
+ if (["html", "body", "#document"].indexOf((element.nodeName || "").toLowerCase()) >= 0) {
+ // $FlowFixMe[incompatible-return]: assume body is always available
+ return element.ownerDocument.body;
+ }
- if (isExcept(element)) {
- return element;
- }
+ function isExcept(node) {
+ const _computedStyle = getComputedStyle(node);
+ const transform = _computedStyle.transform;
+ const perspective = _computedStyle.perspective;
+ const filter = _computedStyle.filter;
+ const willChange = _computedStyle["will-change"];
- return BI.DOM.getPositionRelativeContainingBlock(element.parentNode);
- },
-
- /**
- * 获取position:fixed相对定位的元素的clientRect
- */
- getPositionRelativeContainingBlockRect: function (element) {
- var positionRelativeElement = BI.DOM.getPositionRelativeContainingBlock(element);
- var rect = positionRelativeElement.getBoundingClientRect();
-
- return {
- ...rect.toJSON(),
- scaleX: rect.width / positionRelativeElement.offsetWidth,
- scaleY: rect.height / positionRelativeElement.offsetHeight
- };
- },
- });
-})();
+ return [transform, perspective, filter].some(value => value !== "none") || (willChange === "transform");
+ }
+
+ if (isExcept(element)) {
+ return element;
+ }
+
+ return getPositionRelativeContainingBlock(element.parentNode);
+}
+
+/**
+ * 获取position:fixed相对定位的元素的clientRect
+ */
+export function getPositionRelativeContainingBlockRect(element) {
+ const positionRelativeElement = getPositionRelativeContainingBlock(element);
+ const rect = positionRelativeElement.getBoundingClientRect();
+
+ return {
+ ...rect.toJSON(),
+ scaleX: rect.width / positionRelativeElement.offsetWidth,
+ scaleY: rect.height / positionRelativeElement.offsetHeight,
+ };
+}
diff --git a/src/core/platform/web/function.js b/src/core/platform/web/function.js
index f05ef923d..2044e4160 100644
--- a/src/core/platform/web/function.js
+++ b/src/core/platform/web/function.js
@@ -1,151 +1,170 @@
// 浏览器相关方法
-BI._.extend(BI, {
- isIE: function () {
- if(!_global.navigator) {
- return false;
- }
- if (this.__isIE == null) {
- this.__isIE = /(msie|trident)/i.test(navigator.userAgent.toLowerCase());
- }
- return this.__isIE;
- },
+import { isString } from "../../2.base";
- getIEVersion: function () {
- if(!_global.navigator) {
- return 0;
- }
- if (this.__IEVersion != null) {
- return this.__IEVersion;
- }
- var version = 0;
- var agent = navigator.userAgent.toLowerCase();
- var v1 = agent.match(/(?:msie\s([\w.]+))/);
- var v2 = agent.match(/(?:trident.*rv:([\w.]+))/);
- if (v1 && v2 && v1[1] && v2[1]) {
- version = Math.max(v1[1] * 1, v2[1] * 1);
- } else if (v1 && v1[1]) {
- version = v1[1] * 1;
- } else if (v2 && v2[1]) {
- version = v2[1] * 1;
- } else {
- version = 0;
- }
- return this.__IEVersion = version;
- },
+let __isIE;
- isIE9Below: function () {
- if (!BI.isIE()) {
- return false;
- }
- return this.getIEVersion() < 9;
- },
+export function isIE() {
+ if (!_global.navigator) {
+ return false;
+ }
+ if (!__isIE) {
+ __isIE = /(msie|trident)/i.test(navigator.userAgent.toLowerCase());
+ }
- isEdge: function () {
- if(!_global.navigator) {
- return false;
- }
- return /edg/i.test(navigator.userAgent.toLowerCase());
- },
+ return __isIE;
+}
- isChrome: function () {
- if(!_global.navigator) {
- return false;
- }
- return /chrome/i.test(navigator.userAgent.toLowerCase());
- },
+let __IEVersion;
- isFireFox: function () {
- if(!_global.navigator) {
- return false;
- }
- return /firefox/i.test(navigator.userAgent.toLowerCase());
- },
+export function getIEVersion() {
+ if (!_global.navigator) {
+ return 0;
+ }
+ if (__IEVersion) {
+ return __IEVersion;
+ }
+ let version = 0;
+ const agent = navigator.userAgent.toLowerCase();
+ const v1 = agent.match(/(?:msie\s([\w.]+))/);
+ const v2 = agent.match(/(?:trident.*rv:([\w.]+))/);
+ if (v1 && v2 && v1[1] && v2[1]) {
+ version = Math.max(v1[1] * 1, v2[1] * 1);
+ } else if (v1 && v1[1]) {
+ version = v1[1] * 1;
+ } else if (v2 && v2[1]) {
+ version = v2[1] * 1;
+ } else {
+ version = 0;
+ }
+ __IEVersion = version;
- isOpera: function () {
- if(!_global.navigator) {
- return false;
- }
- return /opera/i.test(navigator.userAgent.toLowerCase());
- },
+ return __IEVersion;
+}
- isSafari: function () {
- if(!_global.navigator) {
- return false;
- }
- return /safari/i.test(navigator.userAgent.toLowerCase()) && !/chrome/i.test(navigator.userAgent.toLowerCase());
- },
+export function isIE9Below() {
+ if (!isIE()) {
+ return false;
+ }
- isKhtml: function () {
- if(!_global.navigator) {
- return false;
- }
- return /Konqueror|Safari|KHTML/i.test(navigator.userAgent);
- },
+ return getIEVersion() < 9;
+}
- isMac: function () {
- if(!_global.navigator) {
- return false;
- }
- return /macintosh|mac os x/i.test(navigator.userAgent);
- },
+export function isEdge() {
+ if (!_global.navigator) {
+ return false;
+ }
- isWindows: function () {
- if(!_global.navigator) {
- return false;
- }
- return /windows|win32/i.test(navigator.userAgent);
- },
+ return /edg/i.test(navigator.userAgent.toLowerCase());
+}
- isSupportCss3: function (style) {
- if(!_global.document) {
- return false;
- }
- var prefix = ["webkit", "Moz", "ms", "o"],
- i, len,
- humpString = [],
- htmlStyle = document.documentElement.style,
- _toHumb = function (string) {
- if (!BI.isString(string)) {
- return "";
- }
-
- return string.replace(/-(\w)/g, function ($0, $1) {
- return $1.toUpperCase();
- });
- };
-
- for ( i = 0; i < prefix.length; i++) {
- humpString.push(_toHumb(prefix[i] + "-" + style));
- }
- humpString.push(_toHumb(style));
+export function isChrome() {
+ if (!_global.navigator) {
+ return false;
+ }
- for (i = 0, len = humpString.length; i < len; i++) {
- if (humpString[i] in htmlStyle) {
- return true;
- }
- }
+ return /chrome/i.test(navigator.userAgent.toLowerCase());
+}
+
+export function isFireFox() {
+ if (!_global.navigator) {
+ return false;
+ }
+
+ return /firefox/i.test(navigator.userAgent.toLowerCase());
+}
+
+export function isOpera() {
+ if (!_global.navigator) {
+ return false;
+ }
+
+ return /opera/i.test(navigator.userAgent.toLowerCase());
+}
+
+export function isSafari() {
+ if (!_global.navigator) {
+ return false;
+ }
+
+ return /safari/i.test(navigator.userAgent.toLowerCase()) && !/chrome/i.test(navigator.userAgent.toLowerCase());
+}
+
+export function isKhtml() {
+ if (!_global.navigator) {
+ return false;
+ }
+
+ return /Konqueror|Safari|KHTML/i.test(navigator.userAgent);
+}
+
+export function isMac() {
+ if (!_global.navigator) {
+ return false;
+ }
+
+ return /macintosh|mac os x/i.test(navigator.userAgent);
+}
+
+export function isWindows() {
+ if (!_global.navigator) {
return false;
- },
+ }
+
+ return /windows|win32/i.test(navigator.userAgent);
+}
+
+export function isSupportCss3(style) {
+ if (!_global.document) {
+ return false;
+ }
+ const prefix = ["webkit", "Moz", "ms", "o"];
+ const humpString = [];
+ const htmlStyle = document.documentElement.style;
+ let i;
+ let len;
- getSafariVersion: function () {
- if (!_global.navigator) {
- return 0;
+ function _toHumb(string) {
+ if (!isString(string)) {
+ return "";
}
- var agent = navigator.userAgent.toLowerCase();
- var version = agent.match(/version\/([\d.]+)/);
- if (version && version[1]) {
- return version[1] * 1;
+
+ return string.replace(/-(\w)/g, ($0, $1) => $1.toUpperCase());
+ };
+
+ for (i = 0; i < prefix.length; i++) {
+ humpString.push(_toHumb(`${prefix[i]}-${style}`));
+ }
+ humpString.push(_toHumb(style));
+
+ for (i = 0, len = humpString.length; i < len; i++) {
+ if (humpString[i] in htmlStyle) {
+ return true;
}
+ }
+
+ return false;
+}
+
+export function getSafariVersion() {
+ if (!_global.navigator) {
return 0;
- },
-
- getMinimumFontSize: function () {
- // not work for firefox
- const el = document.createElement('div');
- el.style.fontSize = "1px";
- document.body.appendChild(el);
- const size = getComputedStyle(el).fontSize;
- el.remove();
- return parseInt(size);
- }
-});
+ }
+ const agent = navigator.userAgent.toLowerCase();
+ const version = agent.match(/version\/([\d.]+)/);
+ if (version && version[1]) {
+ return version[1] * 1;
+ }
+
+ return 0;
+}
+
+export function getMinimumFontSize() {
+ // not work for firefox
+ const el = document.createElement("div");
+ el.style.fontSize = "1px";
+ document.body.appendChild(el);
+ const size = getComputedStyle(el).fontSize;
+ el.remove();
+
+ return parseInt(size, 10);
+}
diff --git a/src/core/platform/web/index.js b/src/core/platform/web/index.js
new file mode 100644
index 000000000..6dcaf06ba
--- /dev/null
+++ b/src/core/platform/web/index.js
@@ -0,0 +1,4 @@
+export * as DOM from "./dom";
+export * from "./detectElementResize";
+export * from "./function";
+export * from "./load";
diff --git a/src/core/platform/web/load.js b/src/core/platform/web/load.js
index f367b8cf6..7ab3a490a 100644
--- a/src/core/platform/web/load.js
+++ b/src/core/platform/web/load.js
@@ -1,55 +1,56 @@
-BI._.extend(BI, {
- $import: function () {
- var _LOADED = {}; // alex:保存加载过的
- function loadReady (src, must) {
- var $scripts = BI.$("head script, body script");
- BI.$.each($scripts, function (i, item) {
- if (item.src.indexOf(src) != -1) {
- _LOADED[src] = true;
- }
- });
- var $links = BI.$("head link");
- BI.$.each($links, function (i, item) {
- if (item.href.indexOf(src) != -1 && must) {
- _LOADED[src] = false;
- BI.$(item).remove();
- }
- });
+const _LOADED = {}; // alex:保存加载过的
+function loadReady(src, must) {
+ const $scripts = BI.$("head script, body script");
+ BI.$.each($scripts, (i, item) => {
+ if (item.src.indexOf(src) !== -1) {
+ _LOADED[src] = true;
}
+ });
+ const $links = BI.$("head link");
+ BI.$.each($links, (i, item) => {
+ if (item.href.indexOf(src) !== -1 && must) {
+ _LOADED[src] = false;
+ BI.$(item).remove();
+ }
+ });
+}
- // must=true 强行加载
- return function (src, ext, must) {
- loadReady(src, must);
- // alex:如果已经加载过了的,直接return
- if (_LOADED[src] === true) {
- return;
- }
- if (ext === "css") {
- var link = document.createElement("link");
- link.rel = "stylesheet";
- link.type = "text/css";
- link.href = src;
- var head = document.getElementsByTagName("head")[0];
- head.appendChild(link);
- _LOADED[src] = true;
- } else {
- // alex:这里用同步调用的方式,必须等待ajax完成
- BI.$.ajax({
- url: src,
- dataType: "script", // alex:指定dataType为script,jquery会帮忙做globalEval的事情
- async: false,
- cache: true,
- complete: function (res, status) {
- /*
- * alex:发现jquery会很智能地判断一下返回的数据类型是不是script,然后做一个globalEval
- * 所以当status为success时就不需要再把其中的内容加到script里面去了
- */
- if (status == "success") {
- _LOADED[src] = true;
- }
- }
- });
- }
- };
- }()
-});
\ No newline at end of file
+/**
+ *
+ * @param src
+ * @param ext
+ * @param must 强行加载
+ */
+export function $import(src, ext, must) {
+ loadReady(src, must);
+ // alex:如果已经加载过了的,直接return
+ if (_LOADED[src] === true) {
+ return;
+ }
+ if (ext === "css") {
+ const link = document.createElement("link");
+ link.rel = "stylesheet";
+ link.type = "text/css";
+ link.href = src;
+ const head = document.getElementsByTagName("head")[0];
+ head.appendChild(link);
+ _LOADED[src] = true;
+ } else {
+ // alex:这里用同步调用的方式,必须等待ajax完成
+ BI.$.ajax({
+ url: src,
+ dataType: "script", // alex:指定dataType为script,jquery会帮忙做globalEval的事情
+ async: false,
+ cache: true,
+ complete(res, status) {
+ /*
+ * alex:发现jquery会很智能地判断一下返回的数据类型是不是script,然后做一个globalEval
+ * 所以当status为success时就不需要再把其中的内容加到script里面去了
+ */
+ if (status === "success") {
+ _LOADED[src] = true;
+ }
+ },
+ });
+ }
+}