From 0795ba5839c34ef9521fb02ad06cf618f1a9766d Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Tue, 15 Sep 2020 16:11:30 -0700 Subject: [PATCH 01/13] Trying out the splitter --- .../components/ElementMeasurer.tsx | 3 +- Composer/packages/client/package.json | 3 +- .../client/src/components/NavTree.tsx | 75 +++++----- .../packages/client/src/components/Page.tsx | 11 +- .../components/ProjectTree/ProjectTree.tsx | 112 +++++++-------- .../client/src/pages/design/DesignPage.tsx | 113 +++++++-------- .../src/pages/design/PropertyEditor.tsx | 49 +++---- .../packages/server/src/locales/en-US.json | 21 +-- Composer/yarn.lock | 132 ++++++++++++++++-- 9 files changed, 321 insertions(+), 198 deletions(-) diff --git a/Composer/packages/adaptive-flow/src/adaptive-flow-renderer/components/ElementMeasurer.tsx b/Composer/packages/adaptive-flow/src/adaptive-flow-renderer/components/ElementMeasurer.tsx index 02e92a496f..5f076217b0 100644 --- a/Composer/packages/adaptive-flow/src/adaptive-flow-renderer/components/ElementMeasurer.tsx +++ b/Composer/packages/adaptive-flow/src/adaptive-flow-renderer/components/ElementMeasurer.tsx @@ -20,11 +20,12 @@ export const ElementMeasurer: React.FC = ({ children, styl return ( { + onResize={({ bounds }) => { /** * As a parent node, mounted before children mounted. * Avoid flickering issue by filtering out the first onResize event. */ + const { width, height } = bounds ?? { width: 0, height: 0 }; if (width === 0 && height === 0) return; onResize(new Boundary(width, height)); }} diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index 8bb8e2289a..289d92369e 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -26,14 +26,15 @@ "@bfc/indexers": "*", "@bfc/shared": "*", "@bfc/ui-plugin-composer": "*", + "@bfc/ui-plugin-cross-trained": "*", "@bfc/ui-plugin-dialog-schema-editor": "*", "@bfc/ui-plugin-lg": "*", "@bfc/ui-plugin-luis": "*", - "@bfc/ui-plugin-cross-trained": "*", "@bfc/ui-plugin-prompts": "*", "@bfc/ui-plugin-select-dialog": "*", "@bfc/ui-plugin-select-skill-dialog": "*", "@emotion/core": "^10.0.27", + "@geoffcox/react-splitter": "^1.0.2", "@reach/router": "^1.2.1", "@uifabric/fluent-theme": "^7.1.107", "@uifabric/icons": "^7.3.59", diff --git a/Composer/packages/client/src/components/NavTree.tsx b/Composer/packages/client/src/components/NavTree.tsx index d23544cb33..49e87ce530 100644 --- a/Composer/packages/client/src/components/NavTree.tsx +++ b/Composer/packages/client/src/components/NavTree.tsx @@ -3,16 +3,16 @@ /** @jsx jsx */ import { jsx, css } from '@emotion/core'; -import { Resizable, ResizeCallback } from 're-resizable'; +// import { Resizable, ResizeCallback } from 're-resizable'; import { DefaultButton } from 'office-ui-fabric-react/lib/Button'; import { FontWeights, FontSizes } from 'office-ui-fabric-react/lib/Styling'; import { NeutralColors } from '@uifabric/fluent-theme'; import { IButtonStyles } from 'office-ui-fabric-react/lib/Button'; import { mergeStyleSets } from 'office-ui-fabric-react/lib/Styling'; -import { useRecoilValue } from 'recoil'; +// import { useRecoilValue } from 'recoil'; import { navigateTo } from '../utils/navigation'; -import { dispatcherState, userSettingsState } from '../recoilModel'; +// import { dispatcherState, userSettingsState } from '../recoilModel'; // -------------------- Styles -------------------- // @@ -75,43 +75,44 @@ interface INavTreeProps { const NavTree: React.FC = (props) => { const { navLinks, regionName } = props; - const { updateUserSettings } = useRecoilValue(dispatcherState); - const { dialogNavWidth: currentWidth } = useRecoilValue(userSettingsState); + // const { updateUserSettings } = useRecoilValue(dispatcherState); + // const { dialogNavWidth: currentWidth } = useRecoilValue(userSettingsState); - const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - updateUserSettings({ dialogNavWidth: currentWidth + d.width }); - }; + // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { + // updateUserSettings({ dialogNavWidth: currentWidth + d.width }); + // }; + + // + // return ( - -
- {navLinks.map((item) => { - const isSelected = location.pathname.includes(item.url); - - return ( - { - e.preventDefault(); - navigateTo(item.url); - }} - /> - ); - })} -
-
+
+ {navLinks.map((item) => { + const isSelected = location.pathname.includes(item.url); + + return ( + { + e.preventDefault(); + navigateTo(item.url); + }} + /> + ); + })} +
); }; diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index e631a2aef8..ce10ab07ad 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -5,6 +5,7 @@ import { jsx, css } from '@emotion/core'; import React from 'react'; import { FontWeights, FontSizes } from 'office-ui-fabric-react/lib/Styling'; +import { LeftRightSplit } from '@geoffcox/react-splitter'; import { Toolbar, IToolbarItem } from './Toolbar'; import { NavTree, INavTreeItem } from './NavTree'; @@ -101,10 +102,12 @@ const Page: React.FC = (props) => { {onRenderHeaderContent &&
{onRenderHeaderContent()}
}
- -
- {children} -
+ + +
+ {children} +
+
diff --git a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx index 65399c06b3..8f33748c9b 100644 --- a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx +++ b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx @@ -16,13 +16,13 @@ import { FocusZone, FocusZoneDirection } from 'office-ui-fabric-react/lib/FocusZ import cloneDeep from 'lodash/cloneDeep'; import formatMessage from 'format-message'; import { DialogInfo, ITrigger } from '@bfc/shared'; -import { Resizable, ResizeCallback } from 're-resizable'; +// import { Resizable, ResizeCallback } from 're-resizable'; import debounce from 'lodash/debounce'; import { useRecoilValue } from 'recoil'; import { IGroupedListStyles } from 'office-ui-fabric-react/lib/GroupedList'; import { ISearchBoxStyles } from 'office-ui-fabric-react/lib/SearchBox'; -import { dispatcherState, userSettingsState } from '../../recoilModel'; +import { dispatcherState } from '../../recoilModel'; import { createSelectedPath, getFriendlyName } from '../../utils/dialogUtil'; import { containUnsupportedTriggers, triggerNotSupported } from '../../utils/dialogValidator'; @@ -130,8 +130,7 @@ interface IProjectTreeProps { } export const ProjectTree: React.FC = (props) => { - const { onboardingAddCoachMarkRef, updateUserSettings } = useRecoilValue(dispatcherState); - const { dialogNavWidth: currentWidth } = useRecoilValue(userSettingsState); + const { onboardingAddCoachMarkRef } = useRecoilValue(dispatcherState); const groupRef: React.RefObject = useRef(null); const { dialogs, dialogId, selected, onSelect, onDeleteTrigger, onDeleteDialog } = props; @@ -185,41 +184,43 @@ export const ProjectTree: React.FC = (props) => { } }; - const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - updateUserSettings({ dialogNavWidth: currentWidth + d.width }); - }; + // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { + // updateUserSettings({ dialogNavWidth: currentWidth + d.width }); + // }; const itemsAndGroups: { items: any[]; groups: IGroup[] } = createItemsAndGroups(sortedDialogs, dialogId, filter); + // + // + return ( - -
- - -
+ +
= (props) => { 0 {} other {Press down arrow key to navigate the search results} }`, - { dialogNum: itemsAndGroups.groups.length } - )} - aria-live={'polite'} - /> - - } - styles={groupListStyle} - onRenderCell={onRenderCell} - /> - -
- + { dialogNum: itemsAndGroups.groups.length } + )} + aria-live={'polite'} + /> + + } + styles={groupListStyle} + onRenderCell={onRenderCell} + /> + +
); }; diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index 87bb9a8678..536d2c24c6 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -13,6 +13,7 @@ import { ActionButton } from 'office-ui-fabric-react/lib/Button'; import { JsonEditor } from '@bfc/code-editor'; import { EditorExtension, useTriggerApi, PluginConfig } from '@bfc/extension-client'; import { useRecoilValue } from 'recoil'; +import { LeftRightSplit } from '@geoffcox/react-splitter'; import { LoadingSpinner } from '../../components/LoadingSpinner'; import { TestController } from '../../components/TestController/TestController'; @@ -609,64 +610,66 @@ const DesignPage: React.FC
- -
-
- - -
- -
-
- {breadcrumbItems} - {dialogJsonVisible ? ( - { - updateDialog({ id: currentDialog.id, content: data }); - }} - /> - ) : withWarning ? ( - warningIsVisible && ( - { - setWarningIsVisible(false); + + +
+
+ + +
+ +
+
+ {breadcrumbItems} + {dialogJsonVisible ? ( + { + updateDialog({ id: currentDialog.id, content: data }); }} - onOk={() => navTo(`/bot/${projectId}/knowledge-base/all`)} /> - ) - ) : ( - - setFlowEditorFocused(false)} - onFocus={() => setFlowEditorFocused(true)} - /> - - )} + ) : withWarning ? ( + warningIsVisible && ( + { + setWarningIsVisible(false); + }} + onOk={() => navTo(`/bot/${projectId}/knowledge-base/all`)} + /> + ) + ) : ( + + setFlowEditorFocused(false)} + onFocus={() => setFlowEditorFocused(true)} + /> + + )} +
+ + +
- - - -
- -
+ +
+
}> {showCreateDialogModal && ( diff --git a/Composer/packages/client/src/pages/design/PropertyEditor.tsx b/Composer/packages/client/src/pages/design/PropertyEditor.tsx index 2c203b8c30..53b549f196 100644 --- a/Composer/packages/client/src/pages/design/PropertyEditor.tsx +++ b/Composer/packages/client/src/pages/design/PropertyEditor.tsx @@ -9,7 +9,7 @@ import { FormErrors, JSONSchema7, useFormConfig } from '@bfc/extension-client'; import formatMessage from 'format-message'; import isEqual from 'lodash/isEqual'; import debounce from 'lodash/debounce'; -import { Resizable, ResizeCallback } from 're-resizable'; +// import { Resizable, ResizeCallback } from 're-resizable'; import { MicrosoftAdaptiveDialog } from '@bfc/shared'; import { useShell } from '../../shell'; @@ -30,11 +30,11 @@ const PropertyEditor: React.FC = () => { const { api: shellApi, data: shellData } = useShell('PropertyEditor'); const { currentDialog, data: formData = {}, focusPath, focusedSteps, schemas } = shellData; - const currentWidth = shellData?.userSettings?.propertyEditorWidth || 400; + // const currentWidth = shellData?.userSettings?.propertyEditorWidth || 400; - const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - shellApi.updateUserSettings({ propertyEditorWidth: currentWidth + d.width }); - }; + // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { + // shellApi.updateUserSettings({ propertyEditorWidth: currentWidth + d.width }); + // }; const [localData, setLocalData] = useState(formData as MicrosoftAdaptiveDialog); @@ -117,26 +117,27 @@ const PropertyEditor: React.FC = () => { setLocalData(newData); }; + // + // + return ( - -
- -
-
+
+ +
); }; diff --git a/Composer/packages/server/src/locales/en-US.json b/Composer/packages/server/src/locales/en-US.json index 812471d0aa..eefc9ad4bd 100644 --- a/Composer/packages/server/src/locales/en-US.json +++ b/Composer/packages/server/src/locales/en-US.json @@ -140,9 +140,6 @@ "add_new_knowledge_base_on_displayname_7f44609c": { "message": " Add new knowledge base on { displayName }" }, - "add_new_plugin_ae50ed3f": { - "message": "Add new plugin" - }, "add_new_profile_47b225e6": { "message": "Add new profile" }, @@ -482,9 +479,15 @@ "create_132b3be1": { "message": "Create" }, + "create_a_bot_project_73e6ce33": { + "message": "Create a bot project" + }, "create_a_condition_8686fd5": { "message": "Create a condition" }, + "create_a_dialog_9f6c8618": { + "message": "Create a dialog" + }, "create_a_name_for_the_project_which_will_be_used_t_57e9b690": { "message": "Create a name for the project which will be used to name the application: (projectname-environment-LUfilename)" }, @@ -1496,9 +1499,6 @@ "please_select_an_activity_type_92f4a8a1": { "message": "Please select an activity type" }, - "plugin_name_829ac92a": { - "message": "Plugin name" - }, "populate_your_knowledge_base_bb2d3605": { "message": "Populate your Knowledge Base" }, @@ -1727,9 +1727,6 @@ "search_for_extensions_a27c4772": { "message": "Search for extensions" }, - "search_for_plugins_9feaecd1": { - "message": "Search for plugins" - }, "see_log_4b833bf7": { "message": "See Log" }, @@ -1871,6 +1868,12 @@ "spaces_and_special_characters_are_not_allowed_use__48acec3c": { "message": "Spaces and special characters are not allowed. Use letters, numbers, -, or _." }, + "specify_a_name_and_description_for_your_new_dialog_86eb3130": { + "message": "Specify a name and description for your new dialog." + }, + "specify_a_name_description_and_location_for_your_n_667f1438": { + "message": "Specify a name, description, and location for your new bot project." + }, "start_bot_25ecad14": { "message": "Start Bot" }, diff --git a/Composer/yarn.lock b/Composer/yarn.lock index 40d953b014..15f1f034ad 100644 --- a/Composer/yarn.lock +++ b/Composer/yarn.lock @@ -274,6 +274,15 @@ jsesc "^2.5.1" source-map "^0.5.0" +"@babel/generator@^7.11.5": + version "7.11.6" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@babel/generator/-/@babel/generator-7.11.6.tgz#b868900f81b163b4d464ea24545c61cbac4dc620" + integrity sha1-uGiQD4GxY7TUZOokVFxhy6xNxiA= + dependencies: + "@babel/types" "^7.11.5" + jsesc "^2.5.1" + source-map "^0.5.0" + "@babel/generator@^7.2.2", "@babel/generator@^7.3.4", "@babel/generator@^7.4.0": version "7.4.0" resolved "https://registry.yarnpkg.com/@babel/generator/-/generator-7.4.0.tgz#c230e79589ae7a729fd4631b9ded4dc220418196" @@ -757,6 +766,13 @@ dependencies: "@babel/types" "^7.10.4" +"@babel/helper-split-export-declaration@^7.11.0": + version "7.11.0" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@babel/helper-split-export-declaration/-/@babel/helper-split-export-declaration-7.11.0.tgz#f8a491244acf6a676158ac42072911ba83ad099f" + integrity sha1-+KSRJErPamdhWKxCBykRuoOtCZ8= + dependencies: + "@babel/types" "^7.11.0" + "@babel/helper-split-export-declaration@^7.7.4": version "7.7.4" resolved "https://registry.yarnpkg.com/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.7.4.tgz#57292af60443c4a3622cf74040ddc28e68336fd8" @@ -864,10 +880,10 @@ chalk "^2.0.0" js-tokens "^4.0.0" -"@babel/parser@^7.0.0", "@babel/parser@^7.1.0", "@babel/parser@^7.10.4", "@babel/parser@^7.10.5", "@babel/parser@^7.11.3", "@babel/parser@^7.2.2", "@babel/parser@^7.3.4", "@babel/parser@^7.4.0", "@babel/parser@^7.7.0", "@babel/parser@^7.7.4", "@babel/parser@^7.7.5", "@babel/parser@^7.8.6", "@babel/parser@^7.9.0", "@babel/parser@^7.9.6": - version "7.11.3" - resolved "https://registry.yarnpkg.com/@babel/parser/-/parser-7.11.3.tgz#9e1eae46738bcd08e23e867bab43e7b95299a8f9" - integrity sha512-REo8xv7+sDxkKvoxEywIdsNFiZLybwdI7hcT5uEPyQrSMB4YQ973BfC9OOrD/81MaIjh6UxdulIQXkjmiH3PcA== +"@babel/parser@^7.0.0", "@babel/parser@^7.1.0", "@babel/parser@^7.10.4", "@babel/parser@^7.10.5", "@babel/parser@^7.11.3", "@babel/parser@^7.11.5", "@babel/parser@^7.2.2", "@babel/parser@^7.3.4", "@babel/parser@^7.4.0", "@babel/parser@^7.7.0", "@babel/parser@^7.7.4", "@babel/parser@^7.7.5", "@babel/parser@^7.8.6", "@babel/parser@^7.9.0", "@babel/parser@^7.9.6": + version "7.11.5" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@babel/parser/-/@babel/parser-7.11.5.tgz#c7ff6303df71080ec7a4f5b8c003c58f1cf51037" + integrity sha1-x/9jA99xCA7HpPW4wAPFjxz1EDc= "@babel/plugin-proposal-async-generator-functions@^7.2.0": version "7.2.0" @@ -2208,6 +2224,21 @@ globals "^11.1.0" lodash "^4.17.19" +"@babel/traverse@^7.4.5": + version "7.11.5" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@babel/traverse/-/@babel/traverse-7.11.5.tgz#be777b93b518eb6d76ee2e1ea1d143daa11e61c3" + integrity sha1-vnd7k7UY62127i4eodFD2qEeYcM= + dependencies: + "@babel/code-frame" "^7.10.4" + "@babel/generator" "^7.11.5" + "@babel/helper-function-name" "^7.10.4" + "@babel/helper-split-export-declaration" "^7.11.0" + "@babel/parser" "^7.11.5" + "@babel/types" "^7.11.5" + debug "^4.1.0" + globals "^11.1.0" + lodash "^4.17.19" + "@babel/traverse@^7.7.0", "@babel/traverse@^7.9.6": version "7.9.6" resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.9.6.tgz#5540d7577697bf619cc57b92aa0f1c231a94f442" @@ -2271,6 +2302,15 @@ lodash "^4.17.19" to-fast-properties "^2.0.0" +"@babel/types@^7.11.0", "@babel/types@^7.11.5": + version "7.11.5" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@babel/types/-/@babel/types-7.11.5.tgz#d9de577d01252d77c6800cee039ee64faf75662d" + integrity sha1-2d5XfQElLXfGgAzuA57mT691Zi0= + dependencies: + "@babel/helper-validator-identifier" "^7.10.4" + lodash "^4.17.19" + to-fast-properties "^2.0.0" + "@babel/types@^7.3.3", "@babel/types@^7.7.0", "@babel/types@^7.9.6": version "7.9.6" resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.9.6.tgz#2c5502b427251e9de1bd2dff95add646d95cc9f7" @@ -2487,6 +2527,13 @@ dependencies: "@emotion/memoize" "0.7.1" +"@emotion/is-prop-valid@^0.8.8": + version "0.8.8" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@emotion/is-prop-valid/-/@emotion/is-prop-valid-0.8.8.tgz#db28b1c4368a259b60a97311d6a952d4fd01ac1a" + integrity sha1-2yixxDaKJZtgqXMR1qlS1P0BrBo= + dependencies: + "@emotion/memoize" "0.7.4" + "@emotion/memoize@0.7.1": version "0.7.1" resolved "https://registry.yarnpkg.com/@emotion/memoize/-/memoize-0.7.1.tgz#e93c13942592cf5ef01aa8297444dc192beee52f" @@ -2558,7 +2605,7 @@ "@emotion/styled-base" "^10.0.27" babel-plugin-emotion "^10.0.27" -"@emotion/stylis@0.8.5": +"@emotion/stylis@0.8.5", "@emotion/stylis@^0.8.4": version "0.8.5" resolved "https://registry.yarnpkg.com/@emotion/stylis/-/stylis-0.8.5.tgz#deacb389bd6ee77d1e7fcaccce9e16c5c7e78e04" integrity sha512-h6KtPihKFn3T9fuIrwvXXUOwlx3rfUvfZIcP5a6rh8Y7zjE3O06hT5Ss4S/YI1AYhuZ1kjaE/5EaOOI2NqSylQ== @@ -2573,7 +2620,7 @@ resolved "https://registry.yarnpkg.com/@emotion/unitless/-/unitless-0.7.4.tgz#a87b4b04e5ae14a88d48ebef15015f6b7d1f5677" integrity sha512-kBa+cDHOR9jpRJ+kcGMsysrls0leukrm68DmFQoMIWQcXdr2cZvyvypWuGYT7U+9kAExUE7+T7r6G3C3A6L8MQ== -"@emotion/unitless@0.7.5": +"@emotion/unitless@0.7.5", "@emotion/unitless@^0.7.4": version "0.7.5" resolved "https://registry.yarnpkg.com/@emotion/unitless/-/unitless-0.7.5.tgz#77211291c1900a700b8a78cfafda3160d76949ed" integrity sha512-OWORNpfjMsSSUBVrRBVGECkhWcULOAJz9ZW8uK9qgxD+87M7jHRcvh/A96XXNhXTLmKcoYSQtBEX7lHMO7YRwg== @@ -2646,6 +2693,16 @@ "@uifabric/utilities" "^7.23.0" tslib "^1.10.0" +"@geoffcox/react-splitter@^1.0.2": + version "1.0.2" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@geoffcox/react-splitter/-/@geoffcox/react-splitter-1.0.2.tgz#a496625efbcc293640c2dd66489f3a2b28945f73" + integrity sha1-pJZiXvvMKTZAwt1mSJ86KyiUX3M= + dependencies: + "@types/react-measure" "^2.0.6" + "@types/styled-components" "4.1.8" + react-measure "^2.3.0" + styled-components "^5.1.1" + "@hapi/address@2.x.x": version "2.1.2" resolved "https://botbuilder.myget.org/F/botbuilder-declarative/npm/@hapi/address/-/@hapi/address-2.1.2.tgz#1c794cd6dbf2354d1eb1ef10e0303f573e1c7222" @@ -3789,6 +3846,13 @@ dependencies: "@types/react" "*" +"@types/react-measure@^2.0.6": + version "2.0.6" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@types/react-measure/-/@types/react-measure-2.0.6.tgz#d66efad1960ea8b38eef9d8cc3cc857e7767b09e" + integrity sha1-1m760ZYOqLOO752Mw8yFfndnsJ4= + dependencies: + "@types/react" "*" + "@types/react-test-renderer@*": version "16.9.2" resolved "https://registry.yarnpkg.com/@types/react-test-renderer/-/react-test-renderer-16.9.2.tgz#e1c408831e8183e5ad748fdece02214a7c2ab6c5" @@ -3854,6 +3918,15 @@ resolved "https://registry.yarnpkg.com/@types/stack-utils/-/stack-utils-1.0.1.tgz#0a851d3bd96498fa25c33ab7278ed3bd65f06c3e" integrity sha512-l42BggppR6zLmpfU6fq9HEa2oGPEI8yrSPL3GITjfRInppYFahObbIQOQK3UGxEnyQpltZLaPe75046NOZQikw== +"@types/styled-components@4.1.8": + version "4.1.8" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@types/styled-components/-/@types/styled-components-4.1.8.tgz#15c8a53bb4b9066e528fafb7558963dee5690ae0" + integrity sha1-FcilO7S5Bm5Sj6+3VYlj3uVpCuA= + dependencies: + "@types/node" "*" + "@types/react" "*" + csstype "^2.2.0" + "@types/tapable@*": version "1.0.4" resolved "https://registry.yarnpkg.com/@types/tapable/-/tapable-1.0.4.tgz#b4ffc7dc97b498c969b360a41eee247f82616370" @@ -5476,8 +5549,8 @@ binary-extensions@^2.0.0: bl@^1.0.0, bl@^2.2.1: version "2.2.1" - resolved "https://registry.yarnpkg.com/bl/-/bl-2.2.1.tgz#8c11a7b730655c5d56898cdc871224f40fd901d5" - integrity sha512-6Pesp1w0DEX1N550i/uGV/TqucVL4AM/pgThFSN/Qq9si1/DF9aIHs1BxD8V/QU0HoeHO6cQRTAuYnLPKq1e4g== + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/bl/-/bl-2.2.1.tgz#8c11a7b730655c5d56898cdc871224f40fd901d5" + integrity sha1-jBGntzBlXF1WiYzchxIk9A/ZAdU= dependencies: readable-stream "^2.3.5" safe-buffer "^5.1.1" @@ -7191,6 +7264,15 @@ css-to-react-native@^2.2.2: css-color-keywords "^1.0.0" postcss-value-parser "^3.3.0" +css-to-react-native@^3.0.0: + version "3.0.0" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/css-to-react-native/-/css-to-react-native-3.0.0.tgz#62dbe678072a824a689bcfee011fc96e02a7d756" + integrity sha1-YtvmeAcqgkpom8/uAR/JbgKn11Y= + dependencies: + camelize "^1.0.0" + css-color-keywords "^1.0.0" + postcss-value-parser "^4.0.2" + css-tree@1.0.0-alpha.28: version "1.0.0-alpha.28" resolved "https://registry.yarnpkg.com/css-tree/-/css-tree-1.0.0-alpha.28.tgz#8e8968190d886c9477bc8d61e96f61af3f7ffa7f" @@ -10693,6 +10775,13 @@ hmac-drbg@^1.0.0: minimalistic-assert "^1.0.0" minimalistic-crypto-utils "^1.0.1" +hoist-non-react-statics@^3.0.0: + version "3.3.2" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/hoist-non-react-statics/-/hoist-non-react-statics-3.3.2.tgz#ece0acaf71d62c2969c2ec59feff42a4b1a85b45" + integrity sha1-7OCsr3HWLClpwuxZ/v9CpLGoW0U= + dependencies: + react-is "^16.7.0" + homedir-polyfill@^1.0.1: version "1.0.3" resolved "https://registry.yarnpkg.com/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz#743298cef4e5af3e194161fbadcc2151d3a058e8" @@ -13690,8 +13779,8 @@ node-fetch@^2.1.2, node-fetch@^2.6.0, node-fetch@~2.6.0: node-forge@0.9.0, node-forge@^0.10.0: version "0.10.0" - resolved "https://registry.yarnpkg.com/node-forge/-/node-forge-0.10.0.tgz#32dea2afb3e9926f02ee5ce8794902691a676bf3" - integrity sha512-PPmu8eEeG9saEUvI97fm4OYxXVB6bFvyNTyiUOBichBpFG8A1Ljw3bY62+5oOjDEMHRnd0Y7HQ+x7uzxOzC6JA== + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/node-forge/-/node-forge-0.10.0.tgz#32dea2afb3e9926f02ee5ce8794902691a676bf3" + integrity sha1-Mt6ir7Ppkm8C7lzoeUkCaRpna/M= node-int64@^0.4.0: version "0.4.0" @@ -15949,7 +16038,7 @@ react-frame-component@^4.0.2: resolved "https://registry.yarnpkg.com/react-frame-component/-/react-frame-component-4.1.0.tgz#bef04039c6af687314f27b20ef9893d85eefe3e6" integrity sha512-2HkO0iccSjd+xRA+aOxq7Mm50WUmCjdmhbQhOiG6gQTChaW//Y3mdkGeUfVA3YkXvDVbigRDvJd/VTUlqaZWSw== -react-is@^16.12.0, react-is@^16.8.6: +react-is@^16.12.0, react-is@^16.7.0, react-is@^16.8.6: version "16.13.1" resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.13.1.tgz#789729a4dc36de2999dc156dd6c1d9c18cea56a4" integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ== @@ -17040,6 +17129,11 @@ shallow-clone@^0.1.2: lazy-cache "^0.2.3" mixin-object "^2.0.1" +shallowequal@^1.1.0: + version "1.1.0" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/shallowequal/-/shallowequal-1.1.0.tgz#188d521de95b9087404fd4dcb68b13df0ae4e7f8" + integrity sha1-GI1SHelbkIdAT9TctosT3wrk5/g= + shebang-command@^1.2.0: version "1.2.0" resolved "https://registry.yarnpkg.com/shebang-command/-/shebang-command-1.2.0.tgz#44aac65b695b03398968c39f363fee5deafdf1ea" @@ -17791,6 +17885,22 @@ styled-components@^4.1.3: stylis-rule-sheet "^0.0.10" supports-color "^5.5.0" +styled-components@^5.1.1: + version "5.2.0" + resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/styled-components/-/styled-components-5.2.0.tgz#6dcb5aa8a629c84b8d5ab34b7167e3e0c6f7ed74" + integrity sha1-bctaqKYpyEuNWrNLcWfj4Mb37XQ= + dependencies: + "@babel/helper-module-imports" "^7.0.0" + "@babel/traverse" "^7.4.5" + "@emotion/is-prop-valid" "^0.8.8" + "@emotion/stylis" "^0.8.4" + "@emotion/unitless" "^0.7.4" + babel-plugin-styled-components ">= 1" + css-to-react-native "^3.0.0" + hoist-non-react-statics "^3.0.0" + shallowequal "^1.1.0" + supports-color "^5.5.0" + stylehacks@^4.0.0: version "4.0.3" resolved "https://registry.yarnpkg.com/stylehacks/-/stylehacks-4.0.3.tgz#6718fcaf4d1e07d8a1318690881e8d96726a71d5" From 0b74ec0132f57970a3baa1ba67c7f2989a524465 Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Fri, 18 Sep 2020 10:28:17 -0700 Subject: [PATCH 02/13] Improve layout --- Composer/packages/client/package.json | 2 +- .../packages/client/src/components/Page.tsx | 2 +- .../client/src/pages/design/DesignPage.tsx | 70 ++++++++------- .../client/src/pages/design/styles.ts | 8 +- .../client/src/pages/publish/Publish.tsx | 89 ++++++++++--------- Composer/yarn.lock | 8 +- 6 files changed, 92 insertions(+), 87 deletions(-) diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index 289d92369e..abd7b03622 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -34,7 +34,7 @@ "@bfc/ui-plugin-select-dialog": "*", "@bfc/ui-plugin-select-skill-dialog": "*", "@emotion/core": "^10.0.27", - "@geoffcox/react-splitter": "^1.0.2", + "@geoffcox/react-splitter": "^1.0.3", "@reach/router": "^1.2.1", "@uifabric/fluent-theme": "^7.1.107", "@uifabric/icons": "^7.3.59", diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index ce10ab07ad..9d02224ed0 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -73,7 +73,7 @@ export const content = css` padding: 20px; position: relative; overflow: auto; - + height: 100%; label: PageContent; `; diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index 536d2c24c6..01b1f51cca 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -630,42 +630,44 @@ const DesignPage: React.FC
-
- {breadcrumbItems} - {dialogJsonVisible ? ( - { - updateDialog({ id: currentDialog.id, content: data }); - }} - /> - ) : withWarning ? ( - warningIsVisible && ( - { - setWarningIsVisible(false); + +
+ {breadcrumbItems} + {dialogJsonVisible ? ( + { + updateDialog({ id: currentDialog.id, content: data }); }} - onOk={() => navTo(`/bot/${projectId}/knowledge-base/all`)} /> - ) - ) : ( - - setFlowEditorFocused(false)} - onFocus={() => setFlowEditorFocused(true)} - /> - - )} -
- - - + ) : withWarning ? ( + warningIsVisible && ( + { + setWarningIsVisible(false); + }} + onOk={() => navTo(`/bot/${projectId}/knowledge-base/all`)} + /> + ) + ) : ( + + setFlowEditorFocused(false)} + onFocus={() => setFlowEditorFocused(true)} + /> + + )} +
+ + + +
diff --git a/Composer/packages/client/src/pages/design/styles.ts b/Composer/packages/client/src/pages/design/styles.ts index b8cb102df2..8e25443a79 100644 --- a/Composer/packages/client/src/pages/design/styles.ts +++ b/Composer/packages/client/src/pages/design/styles.ts @@ -17,7 +17,7 @@ export const contentWrapper = css` display: flex; flex-direction: column; flex-grow: 1; - + height: 100%; label: DesignPageContent; `; @@ -26,10 +26,9 @@ export const projectContainer = css` flex-direction: column; flex-grow: 0; flex-shrink: 0; - width: 255px; + width: 100%; overflow: auto; border-right: 1px solid #c4c4c4; - label: DesignPageProjectContent; `; @@ -73,6 +72,7 @@ export const editorWrapper = css` flex-direction: row; flex-grow: 1; overflow: hidden; + height: 100%; `; export const visualPanel = css` @@ -80,7 +80,7 @@ export const visualPanel = css` flex-direction: column; flex: 1; border-right: 1px solid #c4c4c4; - + height: 100%; label: DesignPageVisualPanel; `; diff --git a/Composer/packages/client/src/pages/publish/Publish.tsx b/Composer/packages/client/src/pages/publish/Publish.tsx index 1bebfa04a3..7566fb0f3c 100644 --- a/Composer/packages/client/src/pages/publish/Publish.tsx +++ b/Composer/packages/client/src/pages/publish/Publish.tsx @@ -10,6 +10,7 @@ import { Dialog, DialogType } from 'office-ui-fabric-react/lib/Dialog'; import { TextField } from 'office-ui-fabric-react/lib/TextField'; import { PublishTarget } from '@bfc/shared'; import { useRecoilValue } from 'recoil'; +import { LeftRightSplit } from '@geoffcox/react-splitter'; import settingsStorage from '../../utils/dialogSettingStorage'; import { projectContainer } from '../design/styles'; @@ -402,52 +403,54 @@ const Publish: React.FC = (props) => {

{selectedTarget ? selectedTargetName : formatMessage('Publish Profiles')}

-
+
{ - setSelectedTarget(undefined); - onSelectTarget('all'); - }} + aria-label={formatMessage('Navigation panel')} + css={projectContainer} + data-testid="target-list" + role="region" > - {formatMessage('All profiles')} -
- {settings && settings.publishTargets && ( - await onDelete(index)} - onEdit={async (item, target) => await onEdit(item, target)} - onSelect={(item) => { - setSelectedTarget(item); - onSelectTarget(item.name); +
{ + setSelectedTarget(undefined); + onSelectTarget('all'); }} - /> - )} -
-
- - - {!thisPublishHistory || thisPublishHistory.length === 0 ? ( -
No publish history
- ) : null} -
-
+ > + {formatMessage('All profiles')} +
+ {settings && settings.publishTargets && ( + await onDelete(index)} + onEdit={async (item, target) => await onEdit(item, target)} + onSelect={(item) => { + setSelectedTarget(item); + onSelectTarget(item.name); + }} + /> + )} +
+
+ + + {!thisPublishHistory || thisPublishHistory.length === 0 ? ( +
No publish history
+ ) : null} +
+
+ ); diff --git a/Composer/yarn.lock b/Composer/yarn.lock index 15f1f034ad..a0fa23f2ec 100644 --- a/Composer/yarn.lock +++ b/Composer/yarn.lock @@ -2693,10 +2693,10 @@ "@uifabric/utilities" "^7.23.0" tslib "^1.10.0" -"@geoffcox/react-splitter@^1.0.2": - version "1.0.2" - resolved "https://botbuilder.myget.org/F/botbuilder-v4-js-daily/npm/@geoffcox/react-splitter/-/@geoffcox/react-splitter-1.0.2.tgz#a496625efbcc293640c2dd66489f3a2b28945f73" - integrity sha1-pJZiXvvMKTZAwt1mSJ86KyiUX3M= +"@geoffcox/react-splitter@^1.0.3": + version "1.0.3" + resolved "https://registry.yarnpkg.com/@geoffcox/react-splitter/-/react-splitter-1.0.3.tgz#1032eabfa670fdded05b5457cf94aa364233df6e" + integrity sha512-sw69e8q4QNq1eAVhHKFLuIIhO8re8iPVp1g8tWLMkw5T9zVyG/UAbUV9XIh1KOtboSH2KkijeOBU8LTtJRRJDw== dependencies: "@types/react-measure" "^2.0.6" "@types/styled-components" "4.1.8" From 4bf457a407fbfc0a98eb942470a4ae1aa0e56cd8 Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Wed, 23 Sep 2020 13:56:30 -0700 Subject: [PATCH 03/13] Updates and improvements --- Composer/packages/client/package.json | 2 +- .../client/src/components/NavTree.tsx | 1 - .../packages/client/src/components/Page.tsx | 2 +- .../components/ProjectTree/ProjectTree.tsx | 1 - .../client/src/pages/design/DesignPage.tsx | 4 +- .../client/src/pages/design/styles.ts | 5 +- .../client/src/pages/publish/Publish.tsx | 2 +- .../client/src/pages/publish/styles.ts | 1 + Composer/yarn.lock | 52 +++++++++---------- 9 files changed, 35 insertions(+), 35 deletions(-) diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index abd7b03622..78e4d0a43e 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -34,7 +34,7 @@ "@bfc/ui-plugin-select-dialog": "*", "@bfc/ui-plugin-select-skill-dialog": "*", "@emotion/core": "^10.0.27", - "@geoffcox/react-splitter": "^1.0.3", + "@geoffcox/react-splitter": "^1.0.4", "@reach/router": "^1.2.1", "@uifabric/fluent-theme": "^7.1.107", "@uifabric/icons": "^7.3.59", diff --git a/Composer/packages/client/src/components/NavTree.tsx b/Composer/packages/client/src/components/NavTree.tsx index 49e87ce530..71f9cdeaeb 100644 --- a/Composer/packages/client/src/components/NavTree.tsx +++ b/Composer/packages/client/src/components/NavTree.tsx @@ -19,7 +19,6 @@ import { navigateTo } from '../utils/navigation'; const root = css` width: 100%; height: 100%; - border-right: 1px solid #c4c4c4; box-sizing: border-box; overflow-y: auto; overflow-x: hidden; diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index 9d02224ed0..c73a7c1dcd 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -102,7 +102,7 @@ const Page: React.FC = (props) => { {onRenderHeaderContent &&
{onRenderHeaderContent()}
}
- +
{children} diff --git a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx index 8f33748c9b..7e3bbb727b 100644 --- a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx +++ b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx @@ -48,7 +48,6 @@ const searchBox: ISearchBoxStyles = { const root = css` width: 100%; height: 100%; - border-right: 1px solid #c4c4c4; box-sizing: border-box; overflow-y: auto; overflow-x: hidden; diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index 01b1f51cca..e11e2a8049 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -610,7 +610,7 @@ const DesignPage: React.FC
- +
- +
{breadcrumbItems} {dialogJsonVisible ? ( diff --git a/Composer/packages/client/src/pages/design/styles.ts b/Composer/packages/client/src/pages/design/styles.ts index 8e25443a79..98733aa47f 100644 --- a/Composer/packages/client/src/pages/design/styles.ts +++ b/Composer/packages/client/src/pages/design/styles.ts @@ -27,8 +27,9 @@ export const projectContainer = css` flex-grow: 0; flex-shrink: 0; width: 100%; + height: 100%; overflow: auto; - border-right: 1px solid #c4c4c4; + border-right: 1px solid red; label: DesignPageProjectContent; `; @@ -79,7 +80,6 @@ export const visualPanel = css` display: flex; flex-direction: column; flex: 1; - border-right: 1px solid #c4c4c4; height: 100%; label: DesignPageVisualPanel; `; @@ -99,6 +99,7 @@ export const formEditor = css` transition: width 0.2s ease-in-out; overflow-y: scroll; height: 100%; + min-width: 300px; `; export const breadcrumbClass = mergeStyleSets({ diff --git a/Composer/packages/client/src/pages/publish/Publish.tsx b/Composer/packages/client/src/pages/publish/Publish.tsx index 7566fb0f3c..9f61d4ebd6 100644 --- a/Composer/packages/client/src/pages/publish/Publish.tsx +++ b/Composer/packages/client/src/pages/publish/Publish.tsx @@ -403,7 +403,7 @@ const Publish: React.FC = (props) => {

{selectedTarget ? selectedTargetName : formatMessage('Publish Profiles')}

- +
Date: Thu, 24 Sep 2020 12:44:13 -0700 Subject: [PATCH 04/13] Moving to internal code for splitter --- Composer/packages/client/package.json | 4 +- .../packages/client/src/components/Page.tsx | 3 +- .../src/components/Split/LeftRightSplit.tsx | 253 ++++++++++++++++++ .../client/src/pages/design/DesignPage.tsx | 2 +- .../client/src/pages/publish/Publish.tsx | 2 +- Composer/yarn.lock | 57 +--- 6 files changed, 262 insertions(+), 59 deletions(-) create mode 100644 Composer/packages/client/src/components/Split/LeftRightSplit.tsx diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index 78e4d0a43e..b687ed54db 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -50,6 +50,7 @@ "office-ui-fabric-react": "^7.121.11", "prop-types": "^15.7.2", "query-string": "^6.8.2", + "react-measure": "^2.3.0", "re-resizable": "^6.3.2", "react": "16.13.0", "react-app-polyfill": "^0.2.1", @@ -58,7 +59,7 @@ "react-frame-component": "^4.0.2", "react-timeago": "^4.4.0", "recoil": "^0.0.10", - "styled-components": "^4.1.3", + "styled-components": "^5.1.1", "uuid": "^8.3.0", "webpack-bundle-analyzer": "^3.8.0" }, @@ -81,6 +82,7 @@ "@types/react": "16.9.23", "@types/react-dom": "16.9.5", "@types/recoil": "^0.0.1", + "@types/styled-components": "4.1.8", "@types/webpack-env": "^1.15.2", "babel-core": "7.0.0-bridge.0", "babel-eslint": "10.1.0", diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index c73a7c1dcd..9e08bcb5bf 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -5,7 +5,8 @@ import { jsx, css } from '@emotion/core'; import React from 'react'; import { FontWeights, FontSizes } from 'office-ui-fabric-react/lib/Styling'; -import { LeftRightSplit } from '@geoffcox/react-splitter'; + +import { LeftRightSplit } from '../components/Split/LeftRightSplit'; import { Toolbar, IToolbarItem } from './Toolbar'; import { NavTree, INavTreeItem } from './NavTree'; diff --git a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx new file mode 100644 index 0000000000..96125a5253 --- /dev/null +++ b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx @@ -0,0 +1,253 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. + +import * as React from 'react'; +import styled, { css } from 'styled-components'; +import { default as Measure, ContentRect } from 'react-measure'; + +// -------------------- STYLE -------------------- + +const defaultSplitterWidth = 5; + +const fullDivCss = css` + width: 100%; + height: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; +`; + +const MeasureDiv = styled.div` + ${fullDivCss} +`; + +const Root = styled.div.attrs( + ({ leftColWidth, splitterWidth }: { leftColWidth: string; splitterWidth: number }): any => ({ + style: { + gridTemplateColumns: `${leftColWidth} ${splitterWidth}px 1fr`, + }, + }) +)` + ${fullDivCss} + display: grid; + grid-template-rows: 1fr; + grid-template-areas: 'left split right'; +`; + +const Left = styled.div` + height: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: left; +`; + +const Split = styled.div` + height: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: split; + cursor: col-resize; + background: transparent; + &:hover .default-split-visual { + background: gray; + } +`; + +const DefaultSplitVisual = styled.div.attrs(({ splitterWidth }: { splitterWidth: number }): any => ({ + halfWidth: `${splitterWidth / 2}px`, +}))` + height: 100%; + width: 1px; + box-sizing: border-box; + outline: none; + overflow: hidden; + background: silver; + cursor: col-resize; + margin-left: ${(props) => props.halfWidth}; +`; + +const Right = styled.div` + height: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: right; +`; + +// -------------------- UTILITIES -------------------- + +// ensures a value can be used in gridTemplateColumns +// defaults to 'auto' +const toGridWidth = (value?: string | number) => { + if (value === undefined || value === null) { + return 'auto'; + } + + if (typeof value === 'string') { + if (value.trim().length === 0) { + return 'auto'; + } + + if (value.endsWith('px') || value.endsWith('%') || value.endsWith('fr')) { + return value; + } + } + + return `${value}px`; +}; + +// constrains the extend of a pane given split constraints +const constrainPaneExtent = ( + primary: number, + constraints: { + total: number; + splitter: number; + minPrimary?: number; + minSecondary?: number; + } +): number => { + const { total, splitter, minPrimary, minSecondary } = constraints; + + // ensure within total bounds + let newPrimary = Math.max(0, Math.min(primary, total - splitter)); + + // adjust satisfy minSecondary + const secondary = total - (newPrimary + splitter); + if (minSecondary && secondary < minSecondary) { + newPrimary = newPrimary - Math.max(0, minSecondary - secondary); + } + + // adjust to satisfy minPrimary + if (minPrimary && newPrimary < minPrimary) { + newPrimary = minPrimary; + } + + // ensure within total bounds after adjustments + return Math.max(0, Math.min(newPrimary, total - splitter)); +}; + +// -------------------- COMPONENT -------------------- + +type Props = { + initialLeftGridWidth?: string | number; + minLeftPixels?: number; + minRightPixels?: number; + splitterWidth?: number; + renderSplitter?: () => JSX.Element; +}; + +export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Element => { + const { + initialLeftGridWidth: defaultLeftWidth, + minRightPixels, + minLeftPixels, + splitterWidth = defaultSplitterWidth, + renderSplitter, + } = props; + + // -------------------- HOOKS -------------------- + + const [currentContentWidth, setCurrentContentWidth] = React.useState(0); + const [currentLeftWidth, setCurrentLeftWidth] = React.useState(0); + + const [leftWidth, setLeftWidth] = React.useState(() => { + // If the default is a number, then use it or the left minimum as a value. + const numericValue = Number(defaultLeftWidth); + return isNaN(numericValue) ? -1 : Math.max(numericValue, minLeftPixels ?? numericValue); + }); + + const [leftStart, setLeftStart] = React.useState(0); + const [screenStart, setScreenStart] = React.useState(0); + + React.useEffect(() => { + if (leftWidth !== -1) { + const newLeft = constrainLeft(leftWidth); + setLeftWidth(newLeft); + } + }, [currentContentWidth, splitterWidth]); + + // -------------------- MEASUREMENT -------------------- + + const constrainLeft = (value: number): number => { + return constrainPaneExtent(value, { + total: currentContentWidth, + splitter: splitterWidth, + minPrimary: minLeftPixels, + minSecondary: minRightPixels, + }); + }; + + const onContentMeasure = (contentRect: ContentRect) => { + contentRect.bounds && setCurrentContentWidth(contentRect.bounds.width); + }; + + const onLeftMeasure = (contentRect: ContentRect) => { + contentRect.bounds && setCurrentLeftWidth(contentRect.bounds.width); + }; + + // -------------------- MOUSE HANDLERS -------------------- + + const onSplitMouseDown = (event: React.MouseEvent) => { + event.currentTarget.setPointerCapture(1); + setScreenStart(event.screenX); + setLeftStart(currentLeftWidth); + }; + + const onSplitMouseMove = (event: React.MouseEvent) => { + if (event.currentTarget.hasPointerCapture(1)) { + // calculate candidate left + const newLeft = constrainLeft(leftStart + (event.screenX - screenStart)); + setLeftWidth(newLeft); + } + }; + + const onSplitMouseUp = (event: React.MouseEvent) => { + event.currentTarget.releasePointerCapture(1); + }; + + // -------------------- RENDER -------------------- + + // If the left width has never been set + // try using the default as a number and constraining it + let renderLeftWidth = `${leftWidth}px`; + if (leftWidth < 0) { + renderLeftWidth = toGridWidth(defaultLeftWidth); + } + + const children = React.Children.toArray(props.children); + const leftChild = children.length > 0 ? children[0] :
; + const rightChild = children.length > 1 ? children[1] :
; + + const renderSplitVisual = + renderSplitter ?? + (() => { + return ; + }); + + return ( + + {({ measureRef }) => ( + + + + + {({ measureRef: leftRef }) => {leftChild}} + + + + {renderSplitVisual()} + + {rightChild} + + + )} + + ); +}; diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index e11e2a8049..3e0ab06422 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -13,8 +13,8 @@ import { ActionButton } from 'office-ui-fabric-react/lib/Button'; import { JsonEditor } from '@bfc/code-editor'; import { EditorExtension, useTriggerApi, PluginConfig } from '@bfc/extension-client'; import { useRecoilValue } from 'recoil'; -import { LeftRightSplit } from '@geoffcox/react-splitter'; +import { LeftRightSplit } from '../../components/Split/LeftRightSplit'; import { LoadingSpinner } from '../../components/LoadingSpinner'; import { TestController } from '../../components/TestController/TestController'; import { DialogDeleting } from '../../constants'; diff --git a/Composer/packages/client/src/pages/publish/Publish.tsx b/Composer/packages/client/src/pages/publish/Publish.tsx index 9f61d4ebd6..89c3099600 100644 --- a/Composer/packages/client/src/pages/publish/Publish.tsx +++ b/Composer/packages/client/src/pages/publish/Publish.tsx @@ -10,8 +10,8 @@ import { Dialog, DialogType } from 'office-ui-fabric-react/lib/Dialog'; import { TextField } from 'office-ui-fabric-react/lib/TextField'; import { PublishTarget } from '@bfc/shared'; import { useRecoilValue } from 'recoil'; -import { LeftRightSplit } from '@geoffcox/react-splitter'; +import { LeftRightSplit } from '../../components/Split/LeftRightSplit'; import settingsStorage from '../../utils/dialogSettingStorage'; import { projectContainer } from '../design/styles'; import { diff --git a/Composer/yarn.lock b/Composer/yarn.lock index 73911d1590..8232d2e61d 100644 --- a/Composer/yarn.lock +++ b/Composer/yarn.lock @@ -2520,13 +2520,6 @@ dependencies: "@emotion/memoize" "0.7.4" -"@emotion/is-prop-valid@^0.7.3": - version "0.7.3" - resolved "https://registry.yarnpkg.com/@emotion/is-prop-valid/-/is-prop-valid-0.7.3.tgz#a6bf4fa5387cbba59d44e698a4680f481a8da6cc" - integrity sha512-uxJqm/sqwXw3YPA5GXX365OBcJGFtxUVkB6WyezqFHlNe9jqUWH5ur2O2M8dGBz61kn1g3ZBlzUunFQXQIClhA== - dependencies: - "@emotion/memoize" "0.7.1" - "@emotion/is-prop-valid@^0.8.8": version "0.8.8" resolved "https://registry.yarnpkg.com/@emotion/is-prop-valid/-/is-prop-valid-0.8.8.tgz#db28b1c4368a259b60a97311d6a952d4fd01ac1a" @@ -2610,7 +2603,7 @@ resolved "https://registry.yarnpkg.com/@emotion/stylis/-/stylis-0.8.5.tgz#deacb389bd6ee77d1e7fcaccce9e16c5c7e78e04" integrity sha512-h6KtPihKFn3T9fuIrwvXXUOwlx3rfUvfZIcP5a6rh8Y7zjE3O06hT5Ss4S/YI1AYhuZ1kjaE/5EaOOI2NqSylQ== -"@emotion/unitless@0.7.3", "@emotion/unitless@^0.7.0": +"@emotion/unitless@0.7.3": version "0.7.3" resolved "https://registry.yarnpkg.com/@emotion/unitless/-/unitless-0.7.3.tgz#6310a047f12d21a1036fb031317219892440416f" integrity sha512-4zAPlpDEh2VwXswwr/t8xGNDGg8RQiPxtxZ3qQEXyQsBV39ptTdESCjuBvGze1nLMVrxmTIKmnO/nAV8Tqjjzg== @@ -7255,15 +7248,6 @@ css-select@^2.0.0: domutils "^1.7.0" nth-check "^1.0.2" -css-to-react-native@^2.2.2: - version "2.3.0" - resolved "https://registry.yarnpkg.com/css-to-react-native/-/css-to-react-native-2.3.0.tgz#bf80d24ec4a08e430306ef429c0586e6ed5485f7" - integrity sha512-IhR7bNIrCFwbJbKZOAjNDZdwpsbjTN6f1agXeELHDqg1wHPA8c2QLruttKOW7hgMGetkfraRJCIEMrptifBfVw== - dependencies: - camelize "^1.0.0" - css-color-keywords "^1.0.0" - postcss-value-parser "^3.3.0" - css-to-react-native@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/css-to-react-native/-/css-to-react-native-3.0.0.tgz#62dbe678072a824a689bcfee011fc96e02a7d756" @@ -13276,11 +13260,6 @@ mem@^4.0.0: mimic-fn "^2.0.0" p-is-promise "^2.0.0" -memoize-one@^4.0.0: - version "4.1.0" - resolved "https://registry.yarnpkg.com/memoize-one/-/memoize-one-4.1.0.tgz#a2387c58c03fff27ca390c31b764a79addf3f906" - integrity sha512-2GApq0yI/b22J2j9rhbrAlsHb0Qcz+7yWxeLG8h+95sl1XPUgeLimQSOdur4Vw7cUhrBHwaUZxWFZueojqNRzA== - memory-fs@^0.4.0, memory-fs@^0.4.1: version "0.4.1" resolved "https://registry.yarnpkg.com/memory-fs/-/memory-fs-0.4.1.tgz#3a9a20b8462523e447cfbc7e8bb80ed667bfc552" @@ -15716,7 +15695,7 @@ prompts@^2.0.1: kleur "^3.0.2" sisteransi "^1.0.0" -prop-types@^15.5.4, prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: +prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: version "15.7.2" resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.7.2.tgz#52c41e75b8c87e72b9d9360e0206b99dcbffa6c5" integrity sha512-8QQikdH7//R2vurIJSutZ1smHYTcLpRWEOlHnzcWHmBYrOGUysKwSsrC89BCiFj3CbrfJ/nXFdJepOVrY1GCHQ== @@ -16043,11 +16022,6 @@ react-is@^16.12.0, react-is@^16.7.0, react-is@^16.8.6: resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.13.1.tgz#789729a4dc36de2999dc156dd6c1d9c18cea56a4" integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ== -react-is@^16.6.0: - version "16.8.4" - resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.8.4.tgz#90f336a68c3a29a096a3d648ab80e87ec61482a2" - integrity sha512-PVadd+WaUDOAciICm/J1waJaSvgq+4rHE/K70j0PFqKhkTBsPv/82UGQJNXAngz1fOQLLxI6z1sEDmJDQhCTAA== - react-is@^16.8.1: version "16.8.6" resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.8.6.tgz#5bbc1e2d29141c9fbdfed456343fe2bc430a6a16" @@ -17868,23 +17842,6 @@ style-loader@^0.23.1: loader-utils "^1.1.0" schema-utils "^1.0.0" -styled-components@^4.1.3: - version "4.1.3" - resolved "https://registry.yarnpkg.com/styled-components/-/styled-components-4.1.3.tgz#4472447208e618b57e84deaaeb6acd34a5e0fe9b" - integrity sha512-0quV4KnSfvq5iMtT0RzpMGl/Dg3XIxIxOl9eJpiqiq4SrAmR1l1DLzNpMzoy3DyzdXVDMJS2HzROnXscWA3SEw== - dependencies: - "@babel/helper-module-imports" "^7.0.0" - "@emotion/is-prop-valid" "^0.7.3" - "@emotion/unitless" "^0.7.0" - babel-plugin-styled-components ">= 1" - css-to-react-native "^2.2.2" - memoize-one "^4.0.0" - prop-types "^15.5.4" - react-is "^16.6.0" - stylis "^3.5.0" - stylis-rule-sheet "^0.0.10" - supports-color "^5.5.0" - styled-components@^5.1.1: version "5.2.0" resolved "https://registry.yarnpkg.com/styled-components/-/styled-components-5.2.0.tgz#6dcb5aa8a629c84b8d5ab34b7167e3e0c6f7ed74" @@ -17910,16 +17867,6 @@ stylehacks@^4.0.0: postcss "^7.0.0" postcss-selector-parser "^3.0.0" -stylis-rule-sheet@^0.0.10: - version "0.0.10" - resolved "https://registry.yarnpkg.com/stylis-rule-sheet/-/stylis-rule-sheet-0.0.10.tgz#44e64a2b076643f4b52e5ff71efc04d8c3c4a430" - integrity sha512-nTbZoaqoBnmK+ptANthb10ZRZOGC+EmTLLUxeYIuHNkEKcmKgXX1XWKkUBT2Ac4es3NybooPe0SmvKdhKJZAuw== - -stylis@^3.5.0: - version "3.5.4" - resolved "https://registry.yarnpkg.com/stylis/-/stylis-3.5.4.tgz#f665f25f5e299cf3d64654ab949a57c768b73fbe" - integrity sha512-8/3pSmthWM7lsPBKv7NXkzn2Uc9W7NotcwGNpJaa3k7WMM1XDCA4MgT5k/8BIexd5ydZdboXtU90XH9Ec4Bv/Q== - sumchecker@^3.0.1: version "3.0.1" resolved "https://registry.yarnpkg.com/sumchecker/-/sumchecker-3.0.1.tgz#6377e996795abb0b6d348e9b3e1dfb24345a8e42" From 14dc418907b5f89c85e0c7d4d261b60f115b839e Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Thu, 24 Sep 2020 13:42:15 -0700 Subject: [PATCH 05/13] Move to emotion for splitter --- .../src/components/Split/LeftRightSplit.tsx | 48 +++++++++---------- 1 file changed, 23 insertions(+), 25 deletions(-) diff --git a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx index 96125a5253..43abbdd28b 100644 --- a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx +++ b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx @@ -2,7 +2,8 @@ // Licensed under the MIT License. import * as React from 'react'; -import styled, { css } from 'styled-components'; +import styled from '@emotion/styled'; +import { css } from '@emotion/core'; import { default as Measure, ContentRect } from 'react-measure'; // -------------------- STYLE -------------------- @@ -21,18 +22,17 @@ const MeasureDiv = styled.div` ${fullDivCss} `; -const Root = styled.div.attrs( - ({ leftColWidth, splitterWidth }: { leftColWidth: string; splitterWidth: number }): any => ({ - style: { - gridTemplateColumns: `${leftColWidth} ${splitterWidth}px 1fr`, - }, - }) -)` - ${fullDivCss} - display: grid; - grid-template-rows: 1fr; - grid-template-areas: 'left split right'; -`; +const Root = styled.div(({ leftColWidth, splitterWidth }: { leftColWidth: string; splitterWidth: number }) => ({ + width: '100%', + height: '100%', + boxSizing: 'border-box', + outline: 'none', + overflow: 'hidden', + display: 'grid', + gridTemplateRows: '1fr', + gridTemplateAreas: `'left split right'`, + gridTemplateColumns: `${leftColWidth} ${splitterWidth}px 1fr`, +})); const Left = styled.div` height: 100%; @@ -55,18 +55,16 @@ const Split = styled.div` } `; -const DefaultSplitVisual = styled.div.attrs(({ splitterWidth }: { splitterWidth: number }): any => ({ - halfWidth: `${splitterWidth / 2}px`, -}))` - height: 100%; - width: 1px; - box-sizing: border-box; - outline: none; - overflow: hidden; - background: silver; - cursor: col-resize; - margin-left: ${(props) => props.halfWidth}; -`; +const DefaultSplitVisual = styled.div(({ splitterWidth }: { splitterWidth: number }) => ({ + height: '100%', + width: '1px', + boxSizing: 'border-box', + outline: 'none', + overflow: 'hidden', + background: 'silver', + cursor: 'col-resize', + marginLeft: `${splitterWidth / 2}px`, +})); const Right = styled.div` height: 100%; From f2aa7960ef9ce47a8497eb1ec7b7e28e80d2de62 Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Thu, 24 Sep 2020 14:01:32 -0700 Subject: [PATCH 06/13] Added top-bot splitter --- Composer/packages/client/package.json | 3 +- .../src/components/Split/LeftRightSplit.tsx | 35 +-- .../src/components/Split/TopBottomSplit.tsx | 232 ++++++++++++++++++ Composer/yarn.lock | 93 +++++-- 4 files changed, 315 insertions(+), 48 deletions(-) create mode 100644 Composer/packages/client/src/components/Split/TopBottomSplit.tsx diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index b687ed54db..4e0998b722 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -59,7 +59,7 @@ "react-frame-component": "^4.0.2", "react-timeago": "^4.4.0", "recoil": "^0.0.10", - "styled-components": "^5.1.1", + "styled-components": "^4.1.3", "uuid": "^8.3.0", "webpack-bundle-analyzer": "^3.8.0" }, @@ -82,7 +82,6 @@ "@types/react": "16.9.23", "@types/react-dom": "16.9.5", "@types/recoil": "^0.0.1", - "@types/styled-components": "4.1.8", "@types/webpack-env": "^1.15.2", "babel-core": "7.0.0-bridge.0", "babel-eslint": "10.1.0", diff --git a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx index 43abbdd28b..bfa88ce1ed 100644 --- a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx +++ b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx @@ -3,14 +3,11 @@ import * as React from 'react'; import styled from '@emotion/styled'; -import { css } from '@emotion/core'; import { default as Measure, ContentRect } from 'react-measure'; -// -------------------- STYLE -------------------- - const defaultSplitterWidth = 5; -const fullDivCss = css` +const MeasureDiv = styled.div` width: 100%; height: 100%; box-sizing: border-box; @@ -18,10 +15,6 @@ const fullDivCss = css` overflow: hidden; `; -const MeasureDiv = styled.div` - ${fullDivCss} -`; - const Root = styled.div(({ leftColWidth, splitterWidth }: { leftColWidth: string; splitterWidth: number }) => ({ width: '100%', height: '100%', @@ -74,8 +67,6 @@ const Right = styled.div` grid-area: right; `; -// -------------------- UTILITIES -------------------- - // ensures a value can be used in gridTemplateColumns // defaults to 'auto' const toGridWidth = (value?: string | number) => { @@ -126,8 +117,6 @@ const constrainPaneExtent = ( return Math.max(0, Math.min(newPrimary, total - splitter)); }; -// -------------------- COMPONENT -------------------- - type Props = { initialLeftGridWidth?: string | number; minLeftPixels?: number; @@ -145,8 +134,6 @@ export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Eleme renderSplitter, } = props; - // -------------------- HOOKS -------------------- - const [currentContentWidth, setCurrentContentWidth] = React.useState(0); const [currentLeftWidth, setCurrentLeftWidth] = React.useState(0); @@ -159,15 +146,6 @@ export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Eleme const [leftStart, setLeftStart] = React.useState(0); const [screenStart, setScreenStart] = React.useState(0); - React.useEffect(() => { - if (leftWidth !== -1) { - const newLeft = constrainLeft(leftWidth); - setLeftWidth(newLeft); - } - }, [currentContentWidth, splitterWidth]); - - // -------------------- MEASUREMENT -------------------- - const constrainLeft = (value: number): number => { return constrainPaneExtent(value, { total: currentContentWidth, @@ -177,6 +155,13 @@ export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Eleme }); }; + React.useEffect(() => { + if (leftWidth !== -1) { + const newLeft = constrainLeft(leftWidth); + setLeftWidth(newLeft); + } + }, [currentContentWidth, splitterWidth]); + const onContentMeasure = (contentRect: ContentRect) => { contentRect.bounds && setCurrentContentWidth(contentRect.bounds.width); }; @@ -185,8 +170,6 @@ export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Eleme contentRect.bounds && setCurrentLeftWidth(contentRect.bounds.width); }; - // -------------------- MOUSE HANDLERS -------------------- - const onSplitMouseDown = (event: React.MouseEvent) => { event.currentTarget.setPointerCapture(1); setScreenStart(event.screenX); @@ -205,8 +188,6 @@ export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Eleme event.currentTarget.releasePointerCapture(1); }; - // -------------------- RENDER -------------------- - // If the left width has never been set // try using the default as a number and constraining it let renderLeftWidth = `${leftWidth}px`; diff --git a/Composer/packages/client/src/components/Split/TopBottomSplit.tsx b/Composer/packages/client/src/components/Split/TopBottomSplit.tsx new file mode 100644 index 0000000000..b7e5ff42e8 --- /dev/null +++ b/Composer/packages/client/src/components/Split/TopBottomSplit.tsx @@ -0,0 +1,232 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. + +import * as React from 'react'; +import styled from '@emotion/styled'; +import { default as Measure, ContentRect } from 'react-measure'; + +const defaultSplitterHeight = 5; + +const MeasureDiv = styled.div` + width: 100%; + height: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; +`; + +const Root = styled.div(({ topRowHeight, splitterHeight }: { topRowHeight: string; splitterHeight: number }) => ({ + width: '100%', + height: '100%', + boxSizing: 'border-box', + outline: 'none', + overflow: 'hidden', + display: 'grid', + gridTemplateColumns: '1fr', + gridTemplateAreas: `'top' 'split' 'bottom'`, + gridTemplateRows: `${topRowHeight} ${splitterHeight}px 1fr`, +})); + +const Top = styled.div` + width: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: top; +`; + +const Split = styled.div` + width: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: split; + cursor: row-resize; + background: transparent; + &:hover .default-split-visual { + background: gray; + } +`; + +const DefaultSplitVisual = styled.div(({ splitterHeight }: { splitterHeight: number }) => ({ + width: '100%', + height: '1px', + boxSizing: 'border-box', + outline: 'none', + overflow: 'hidden', + background: 'silver', + cursor: 'row-resize', + marginTop: `${splitterHeight / 2}px`, +})); + +const Bottom = styled.div` + width: 100%; + box-sizing: border-box; + outline: none; + overflow: hidden; + grid-area: bottom; +`; + +// ensures a value can be used in gridTemplateColumns +// defaults to '1fr' +const toGridExtent = (value?: string | number) => { + if (value === undefined || value === null) { + return '1fr'; + } + + if (typeof value === 'string') { + if (value.trim().length === 0) { + return '1fr'; + } + + if (value.endsWith('px') || value.endsWith('%') || value.endsWith('fr')) { + return value; + } + } + + return `${value}px`; +}; + +// constrains the extend of a pane given split constraints +const constrainPaneExtent = ( + primary: number, + constraints: { + total: number; + splitter: number; + minPrimary?: number; + minSecondary?: number; + } +): number => { + const { total, splitter, minPrimary, minSecondary } = constraints; + + // ensure within total bounds + let newPrimary = Math.max(0, Math.min(primary, total - splitter)); + + // adjust satisfy minSecondary + const secondary = total - (newPrimary + splitter); + if (minSecondary && secondary < minSecondary) { + newPrimary = newPrimary - Math.max(0, minSecondary - secondary); + } + + // adjust to satisfy minPrimary + if (minPrimary && newPrimary < minPrimary) { + newPrimary = minPrimary; + } + + // ensure within total bounds after adjustments + return Math.max(0, Math.min(newPrimary, total - splitter)); +}; + +type Props = { + initialTopGridHeight?: string | number; + minTopPixels?: number; + minBottomPixels?: number; + splitterHeight?: number; + renderSplitter?: () => JSX.Element; +}; + +export const TopBottomSplit = (props: React.PropsWithChildren): JSX.Element => { + const { + initialTopGridHeight, + minBottomPixels, + minTopPixels, + splitterHeight = defaultSplitterHeight, + renderSplitter, + } = props; + + const [currentContentHeight, setCurrentContentHeight] = React.useState(0); + const [currentTopHeight, setCurrentTopHeight] = React.useState(0); + + const [topHeight, setTopHeight] = React.useState(() => { + // If the default is a number, then use it or the top minimum as a value. + const numericValue = Number(initialTopGridHeight); + return isNaN(numericValue) ? -1 : Math.max(numericValue, minTopPixels ?? numericValue); + }); + + const [topStart, setTopStart] = React.useState(0); + const [screenStart, setScreenStart] = React.useState(0); + + const constrainTop = (value: number): number => { + return constrainPaneExtent(value, { + total: currentContentHeight, + splitter: splitterHeight, + minPrimary: minTopPixels, + minSecondary: minBottomPixels, + }); + }; + + React.useEffect(() => { + if (topHeight != -1) { + const newTop = constrainTop(topHeight); + setTopHeight(newTop); + } + }, [currentContentHeight, splitterHeight]); + + const onContentMeasure = (contentRect: ContentRect) => { + contentRect.bounds && setCurrentContentHeight(contentRect.bounds.height); + }; + + const onTopMeasure = (contentRect: ContentRect) => { + contentRect.bounds && setCurrentTopHeight(contentRect.bounds.height); + }; + + const onSplitMouseDown = (event: React.MouseEvent) => { + event.currentTarget.setPointerCapture(1); + setScreenStart(event.screenY); + setTopStart(currentTopHeight); + }; + + const onSplitMouseMove = (event: React.MouseEvent) => { + if (event.currentTarget.hasPointerCapture(1)) { + // calculate candidate top + const newTop = constrainTop(topStart + (event.screenY - screenStart)); + setTopHeight(newTop); + } + }; + + const onSplitMouseUp = (event: React.MouseEvent) => { + event.currentTarget.releasePointerCapture(1); + }; + + // If the top height has never been set + // try using the default as a number and constraining it + let renderTopHeight = `${topHeight}px`; + if (topHeight < 0) { + renderTopHeight = toGridExtent(initialTopGridHeight); + } + + const children = React.Children.toArray(props.children); + const topChild = children.length > 0 ? children[0] :
; + const bottomChild = children.length > 1 ? children[1] :
; + + const renderSplitVisual = + renderSplitter ?? + (() => { + return ; + }); + + return ( + + {({ measureRef }) => ( + + + + + {({ measureRef: topRef }) => {topChild}} + + + + {renderSplitVisual()} + + {bottomChild} + + + )} + + ); +}; diff --git a/Composer/yarn.lock b/Composer/yarn.lock index 31397bbc5d..f7f5e5bca6 100644 --- a/Composer/yarn.lock +++ b/Composer/yarn.lock @@ -2194,6 +2194,21 @@ "@babel/parser" "^7.7.4" "@babel/types" "^7.7.4" +"@babel/traverse@^7.0.0", "@babel/traverse@^7.4.5": + version "7.11.5" + resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.11.5.tgz#be777b93b518eb6d76ee2e1ea1d143daa11e61c3" + integrity sha512-EjiPXt+r7LiCZXEfRpSJd+jUMnBd4/9OUv7Nx3+0u9+eimMwJmG0Q98lw4/289JCoxSE8OolDMNZaaF/JZ69WQ== + dependencies: + "@babel/code-frame" "^7.10.4" + "@babel/generator" "^7.11.5" + "@babel/helper-function-name" "^7.10.4" + "@babel/helper-split-export-declaration" "^7.11.0" + "@babel/parser" "^7.11.5" + "@babel/types" "^7.11.5" + debug "^4.1.0" + globals "^11.1.0" + lodash "^4.17.19" + "@babel/traverse@^7.1.0", "@babel/traverse@^7.2.2", "@babel/traverse@^7.3.4", "@babel/traverse@^7.4.0": version "7.4.0" resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.4.0.tgz#14006967dd1d2b3494cdd650c686db9daf0ddada" @@ -2224,21 +2239,6 @@ globals "^11.1.0" lodash "^4.17.19" -"@babel/traverse@^7.4.5": - version "7.11.5" - resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.11.5.tgz#be777b93b518eb6d76ee2e1ea1d143daa11e61c3" - integrity sha512-EjiPXt+r7LiCZXEfRpSJd+jUMnBd4/9OUv7Nx3+0u9+eimMwJmG0Q98lw4/289JCoxSE8OolDMNZaaF/JZ69WQ== - dependencies: - "@babel/code-frame" "^7.10.4" - "@babel/generator" "^7.11.5" - "@babel/helper-function-name" "^7.10.4" - "@babel/helper-split-export-declaration" "^7.11.0" - "@babel/parser" "^7.11.5" - "@babel/types" "^7.11.5" - debug "^4.1.0" - globals "^11.1.0" - lodash "^4.17.19" - "@babel/traverse@^7.7.0", "@babel/traverse@^7.9.6": version "7.9.6" resolved "https://registry.yarnpkg.com/@babel/traverse/-/traverse-7.9.6.tgz#5540d7577697bf619cc57b92aa0f1c231a94f442" @@ -2520,7 +2520,7 @@ dependencies: "@emotion/memoize" "0.7.4" -"@emotion/is-prop-valid@^0.8.8": +"@emotion/is-prop-valid@^0.8.1", "@emotion/is-prop-valid@^0.8.8": version "0.8.8" resolved "https://registry.yarnpkg.com/@emotion/is-prop-valid/-/is-prop-valid-0.8.8.tgz#db28b1c4368a259b60a97311d6a952d4fd01ac1a" integrity sha512-u5WtneEAr5IDG2Wv65yhunPSMLIpuKsbuOktRojfrEiEvRyC85LgPMZI63cr7NUqT8ZIGdSVg8ZKGxIug4lXcA== @@ -2613,7 +2613,7 @@ resolved "https://registry.yarnpkg.com/@emotion/unitless/-/unitless-0.7.4.tgz#a87b4b04e5ae14a88d48ebef15015f6b7d1f5677" integrity sha512-kBa+cDHOR9jpRJ+kcGMsysrls0leukrm68DmFQoMIWQcXdr2cZvyvypWuGYT7U+9kAExUE7+T7r6G3C3A6L8MQ== -"@emotion/unitless@0.7.5", "@emotion/unitless@^0.7.4": +"@emotion/unitless@0.7.5", "@emotion/unitless@^0.7.0", "@emotion/unitless@^0.7.4": version "0.7.5" resolved "https://registry.yarnpkg.com/@emotion/unitless/-/unitless-0.7.5.tgz#77211291c1900a700b8a78cfafda3160d76949ed" integrity sha512-OWORNpfjMsSSUBVrRBVGECkhWcULOAJz9ZW8uK9qgxD+87M7jHRcvh/A96XXNhXTLmKcoYSQtBEX7lHMO7YRwg== @@ -7235,6 +7235,15 @@ css-select@^2.0.0: domutils "^1.7.0" nth-check "^1.0.2" +css-to-react-native@^2.2.2: + version "2.3.2" + resolved "https://registry.yarnpkg.com/css-to-react-native/-/css-to-react-native-2.3.2.tgz#e75e2f8f7aa385b4c3611c52b074b70a002f2e7d" + integrity sha512-VOFaeZA053BqvvvqIA8c9n0+9vFppVBAHCp6JgFTtTMU3Mzi+XnelJ9XC9ul3BqFzZyQ5N+H0SnwsWT2Ebchxw== + dependencies: + camelize "^1.0.0" + css-color-keywords "^1.0.0" + postcss-value-parser "^3.3.0" + css-to-react-native@^3.0.0: version "3.0.0" resolved "https://registry.yarnpkg.com/css-to-react-native/-/css-to-react-native-3.0.0.tgz#62dbe678072a824a689bcfee011fc96e02a7d756" @@ -11713,6 +11722,11 @@ is-typedarray@^1.0.0, is-typedarray@~1.0.0: resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a" integrity sha1-5HnICFjfDBsR3dppQPlgEfzaSpo= +is-what@^3.3.1: + version "3.11.2" + resolved "https://registry.yarnpkg.com/is-what/-/is-what-3.11.2.tgz#4ca0c91b236acea48dd6af0a072d6a84aec7a1d4" + integrity sha512-m7LzBsC9TqUhkBrozSmmWfVO7VYnjk9UHu0U+Y8BiJRnc1TYIK/3Qv4DteuiBpn2S4K7n3N4WNC4pe6wEx2xYg== + is-windows@^1.0.1, is-windows@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d" @@ -13244,6 +13258,11 @@ mem@^4.0.0: mimic-fn "^2.0.0" p-is-promise "^2.0.0" +memoize-one@^5.0.0: + version "5.1.1" + resolved "https://registry.yarnpkg.com/memoize-one/-/memoize-one-5.1.1.tgz#047b6e3199b508eaec03504de71229b8eb1d75c0" + integrity sha512-HKeeBpWvqiVJD57ZUAsJNm71eHTykffzcLZVYWiVfQeI1rJtuEaS7hQiEpWfVVk18donPwJEcFKIkCmPJNOhHA== + memory-fs@^0.4.0, memory-fs@^0.4.1: version "0.4.1" resolved "https://registry.yarnpkg.com/memory-fs/-/memory-fs-0.4.1.tgz#3a9a20b8462523e447cfbc7e8bb80ed667bfc552" @@ -13252,6 +13271,13 @@ memory-fs@^0.4.0, memory-fs@^0.4.1: errno "^0.1.3" readable-stream "^2.0.1" +merge-anything@^2.2.4: + version "2.4.4" + resolved "https://registry.yarnpkg.com/merge-anything/-/merge-anything-2.4.4.tgz#6226b2ac3d3d3fc5fb9e8d23aa400df25f98fdf0" + integrity sha512-l5XlriUDJKQT12bH+rVhAHjwIuXWdAIecGwsYjv2LJo+dA1AeRTmeQS+3QBpO6lEthBMDi2IUMpLC1yyRvGlwQ== + dependencies: + is-what "^3.3.1" + merge-deep@^3.0.2: version "3.0.2" resolved "https://registry.yarnpkg.com/merge-deep/-/merge-deep-3.0.2.tgz#f39fa100a4f1bd34ff29f7d2bf4508fbb8d83ad2" @@ -15679,7 +15705,7 @@ prompts@^2.0.1: kleur "^3.0.2" sisteransi "^1.0.0" -prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: +prop-types@^15.5.4, prop-types@^15.6.1, prop-types@^15.6.2, prop-types@^15.7.2: version "15.7.2" resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.7.2.tgz#52c41e75b8c87e72b9d9360e0206b99dcbffa6c5" integrity sha512-8QQikdH7//R2vurIJSutZ1smHYTcLpRWEOlHnzcWHmBYrOGUysKwSsrC89BCiFj3CbrfJ/nXFdJepOVrY1GCHQ== @@ -16001,7 +16027,7 @@ react-frame-component@^4.0.2: resolved "https://registry.yarnpkg.com/react-frame-component/-/react-frame-component-4.1.0.tgz#bef04039c6af687314f27b20ef9893d85eefe3e6" integrity sha512-2HkO0iccSjd+xRA+aOxq7Mm50WUmCjdmhbQhOiG6gQTChaW//Y3mdkGeUfVA3YkXvDVbigRDvJd/VTUlqaZWSw== -react-is@^16.12.0, react-is@^16.7.0, react-is@^16.8.6: +react-is@^16.12.0, react-is@^16.6.0, react-is@^16.7.0, react-is@^16.8.6: version "16.13.1" resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.13.1.tgz#789729a4dc36de2999dc156dd6c1d9c18cea56a4" integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ== @@ -17855,6 +17881,25 @@ style-loader@^0.23.1: loader-utils "^1.1.0" schema-utils "^1.0.0" +styled-components@^4.1.3: + version "4.4.1" + resolved "https://registry.yarnpkg.com/styled-components/-/styled-components-4.4.1.tgz#e0631e889f01db67df4de576fedaca463f05c2f2" + integrity sha512-RNqj14kYzw++6Sr38n7197xG33ipEOktGElty4I70IKzQF1jzaD1U4xQ+Ny/i03UUhHlC5NWEO+d8olRCDji6g== + dependencies: + "@babel/helper-module-imports" "^7.0.0" + "@babel/traverse" "^7.0.0" + "@emotion/is-prop-valid" "^0.8.1" + "@emotion/unitless" "^0.7.0" + babel-plugin-styled-components ">= 1" + css-to-react-native "^2.2.2" + memoize-one "^5.0.0" + merge-anything "^2.2.4" + prop-types "^15.5.4" + react-is "^16.6.0" + stylis "^3.5.0" + stylis-rule-sheet "^0.0.10" + supports-color "^5.5.0" + styled-components@^5.1.1: version "5.2.0" resolved "https://registry.yarnpkg.com/styled-components/-/styled-components-5.2.0.tgz#6dcb5aa8a629c84b8d5ab34b7167e3e0c6f7ed74" @@ -17880,6 +17925,16 @@ stylehacks@^4.0.0: postcss "^7.0.0" postcss-selector-parser "^3.0.0" +stylis-rule-sheet@^0.0.10: + version "0.0.10" + resolved "https://registry.yarnpkg.com/stylis-rule-sheet/-/stylis-rule-sheet-0.0.10.tgz#44e64a2b076643f4b52e5ff71efc04d8c3c4a430" + integrity sha512-nTbZoaqoBnmK+ptANthb10ZRZOGC+EmTLLUxeYIuHNkEKcmKgXX1XWKkUBT2Ac4es3NybooPe0SmvKdhKJZAuw== + +stylis@^3.5.0: + version "3.5.4" + resolved "https://registry.yarnpkg.com/stylis/-/stylis-3.5.4.tgz#f665f25f5e299cf3d64654ab949a57c768b73fbe" + integrity sha512-8/3pSmthWM7lsPBKv7NXkzn2Uc9W7NotcwGNpJaa3k7WMM1XDCA4MgT5k/8BIexd5ydZdboXtU90XH9Ec4Bv/Q== + sumchecker@^3.0.1: version "3.0.1" resolved "https://registry.yarnpkg.com/sumchecker/-/sumchecker-3.0.1.tgz#6377e996795abb0b6d348e9b3e1dfb24345a8e42" From d1c703c45f6044898b4e2f25f75f8bee65101b00 Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Thu, 24 Sep 2020 15:03:55 -0700 Subject: [PATCH 07/13] Set min-max on splitter --- Composer/packages/client/src/components/Page.tsx | 2 +- Composer/packages/client/src/pages/design/DesignPage.tsx | 4 ++-- Composer/packages/client/src/pages/publish/Publish.tsx | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index 9e08bcb5bf..323f5e8192 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -103,7 +103,7 @@ const Page: React.FC = (props) => { {onRenderHeaderContent &&
{onRenderHeaderContent()}
}
- +
{children} diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index 942d13c490..7cde31a9ff 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -581,7 +581,7 @@ const DesignPage: React.FC
- +
- +
{breadcrumbItems} {dialogJsonVisible ? ( diff --git a/Composer/packages/client/src/pages/publish/Publish.tsx b/Composer/packages/client/src/pages/publish/Publish.tsx index 6365519af4..b63f80ada4 100644 --- a/Composer/packages/client/src/pages/publish/Publish.tsx +++ b/Composer/packages/client/src/pages/publish/Publish.tsx @@ -404,7 +404,7 @@ const Publish: React.FC{selectedTarget ? selectedTargetName : formatMessage('Publish Profiles')}
- +
Date: Fri, 25 Sep 2020 09:11:10 -0700 Subject: [PATCH 08/13] Update min-max to numbers --- Composer/packages/client/package.json | 1 - .../client/src/pages/design/DesignPage.tsx | 4 +- .../client/src/pages/publish/Publish.tsx | 2 +- Composer/yarn.lock | 73 ++----------------- 4 files changed, 8 insertions(+), 72 deletions(-) diff --git a/Composer/packages/client/package.json b/Composer/packages/client/package.json index 4e0998b722..9f8aed2dc9 100644 --- a/Composer/packages/client/package.json +++ b/Composer/packages/client/package.json @@ -34,7 +34,6 @@ "@bfc/ui-plugin-select-dialog": "*", "@bfc/ui-plugin-select-skill-dialog": "*", "@emotion/core": "^10.0.27", - "@geoffcox/react-splitter": "^1.0.4", "@reach/router": "^1.2.1", "@uifabric/fluent-theme": "^7.1.107", "@uifabric/icons": "^7.3.59", diff --git a/Composer/packages/client/src/pages/design/DesignPage.tsx b/Composer/packages/client/src/pages/design/DesignPage.tsx index 7cde31a9ff..39132d9cdd 100644 --- a/Composer/packages/client/src/pages/design/DesignPage.tsx +++ b/Composer/packages/client/src/pages/design/DesignPage.tsx @@ -581,7 +581,7 @@ const DesignPage: React.FC
- +
- +
{breadcrumbItems} {dialogJsonVisible ? ( diff --git a/Composer/packages/client/src/pages/publish/Publish.tsx b/Composer/packages/client/src/pages/publish/Publish.tsx index b63f80ada4..a378885ed1 100644 --- a/Composer/packages/client/src/pages/publish/Publish.tsx +++ b/Composer/packages/client/src/pages/publish/Publish.tsx @@ -404,7 +404,7 @@ const Publish: React.FC{selectedTarget ? selectedTargetName : formatMessage('Publish Profiles')}
- +
= 1" - css-to-react-native "^3.0.0" - hoist-non-react-statics "^3.0.0" - shallowequal "^1.1.0" - supports-color "^5.5.0" - stylehacks@^4.0.0: version "4.0.3" resolved "https://registry.yarnpkg.com/stylehacks/-/stylehacks-4.0.3.tgz#6718fcaf4d1e07d8a1318690881e8d96726a71d5" From e7cb067d9e0bae20bef93c924a88cd7d73f2bb86 Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Fri, 25 Sep 2020 09:11:34 -0700 Subject: [PATCH 09/13] Update min-max to numbers --- Composer/packages/client/src/components/Page.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Composer/packages/client/src/components/Page.tsx b/Composer/packages/client/src/components/Page.tsx index 323f5e8192..a8bcb2b962 100644 --- a/Composer/packages/client/src/components/Page.tsx +++ b/Composer/packages/client/src/components/Page.tsx @@ -103,7 +103,7 @@ const Page: React.FC = (props) => { {onRenderHeaderContent &&
{onRenderHeaderContent()}
}
- +
{children} From ae23e6f47366aa5d54bd5872195ed71e19a07c98 Mon Sep 17 00:00:00 2001 From: "Geoff Cox (Microsoft)" Date: Fri, 25 Sep 2020 15:07:20 -0700 Subject: [PATCH 10/13] Update NavTree.tsx --- .../client/src/components/NavTree.tsx | 20 ------------------- 1 file changed, 20 deletions(-) diff --git a/Composer/packages/client/src/components/NavTree.tsx b/Composer/packages/client/src/components/NavTree.tsx index 71f9cdeaeb..6bf12de255 100644 --- a/Composer/packages/client/src/components/NavTree.tsx +++ b/Composer/packages/client/src/components/NavTree.tsx @@ -3,16 +3,13 @@ /** @jsx jsx */ import { jsx, css } from '@emotion/core'; -// import { Resizable, ResizeCallback } from 're-resizable'; import { DefaultButton } from 'office-ui-fabric-react/lib/Button'; import { FontWeights, FontSizes } from 'office-ui-fabric-react/lib/Styling'; import { NeutralColors } from '@uifabric/fluent-theme'; import { IButtonStyles } from 'office-ui-fabric-react/lib/Button'; import { mergeStyleSets } from 'office-ui-fabric-react/lib/Styling'; -// import { useRecoilValue } from 'recoil'; import { navigateTo } from '../utils/navigation'; -// import { dispatcherState, userSettingsState } from '../recoilModel'; // -------------------- Styles -------------------- // @@ -74,23 +71,6 @@ interface INavTreeProps { const NavTree: React.FC = (props) => { const { navLinks, regionName } = props; - // const { updateUserSettings } = useRecoilValue(dispatcherState); - // const { dialogNavWidth: currentWidth } = useRecoilValue(userSettingsState); - - // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - // updateUserSettings({ dialogNavWidth: currentWidth + d.width }); - // }; - - // - // return (
From 10bbe8bbc258fd7825d63a48fc83319a74d7ca9e Mon Sep 17 00:00:00 2001 From: "Geoff Cox (Microsoft)" Date: Fri, 25 Sep 2020 15:08:02 -0700 Subject: [PATCH 11/13] Update ProjectTree.tsx --- .../src/components/ProjectTree/ProjectTree.tsx | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx index 7e3bbb727b..45d4910a26 100644 --- a/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx +++ b/Composer/packages/client/src/components/ProjectTree/ProjectTree.tsx @@ -16,7 +16,6 @@ import { FocusZone, FocusZoneDirection } from 'office-ui-fabric-react/lib/FocusZ import cloneDeep from 'lodash/cloneDeep'; import formatMessage from 'format-message'; import { DialogInfo, ITrigger } from '@bfc/shared'; -// import { Resizable, ResizeCallback } from 're-resizable'; import debounce from 'lodash/debounce'; import { useRecoilValue } from 'recoil'; import { IGroupedListStyles } from 'office-ui-fabric-react/lib/GroupedList'; @@ -183,23 +182,8 @@ export const ProjectTree: React.FC = (props) => { } }; - // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - // updateUserSettings({ dialogNavWidth: currentWidth + d.width }); - // }; - const itemsAndGroups: { items: any[]; groups: IGroup[] } = createItemsAndGroups(sortedDialogs, dialogId, filter); - // - // - return (
Date: Fri, 25 Sep 2020 15:21:55 -0700 Subject: [PATCH 12/13] PR fixes --- .../src/components/Split/LeftRightSplit.tsx | 19 +++++++++++++++++-- .../src/components/Split/TopBottomSplit.tsx | 19 +++++++++++++++++-- 2 files changed, 34 insertions(+), 4 deletions(-) diff --git a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx index bfa88ce1ed..8b88b48e3d 100644 --- a/Composer/packages/client/src/components/Split/LeftRightSplit.tsx +++ b/Composer/packages/client/src/components/Split/LeftRightSplit.tsx @@ -89,11 +89,26 @@ const toGridWidth = (value?: string | number) => { // constrains the extend of a pane given split constraints const constrainPaneExtent = ( + /** + * the requested extend of the primary pane + */ primary: number, constraints: { + /** + * the total extent available for primary, splitter, and secondary + */ total: number; + /** + * the extent of the splitter + */ splitter: number; + /** + * the minimum extend of the primary pane + */ minPrimary?: number; + /** + * the minimum extend of the secondary pane + */ minSecondary?: number; } ): number => { @@ -122,10 +137,10 @@ type Props = { minLeftPixels?: number; minRightPixels?: number; splitterWidth?: number; - renderSplitter?: () => JSX.Element; + renderSplitter?: () => React.ReactNode; }; -export const LeftRightSplit = (props: React.PropsWithChildren): JSX.Element => { +export const LeftRightSplit = (props: React.PropsWithChildren) => { const { initialLeftGridWidth: defaultLeftWidth, minRightPixels, diff --git a/Composer/packages/client/src/components/Split/TopBottomSplit.tsx b/Composer/packages/client/src/components/Split/TopBottomSplit.tsx index b7e5ff42e8..f221bd4642 100644 --- a/Composer/packages/client/src/components/Split/TopBottomSplit.tsx +++ b/Composer/packages/client/src/components/Split/TopBottomSplit.tsx @@ -89,11 +89,26 @@ const toGridExtent = (value?: string | number) => { // constrains the extend of a pane given split constraints const constrainPaneExtent = ( + /** + * the requested extend of the primary pane + */ primary: number, constraints: { + /** + * the total extent available for primary, splitter, and secondary + */ total: number; + /** + * the extent of the splitter + */ splitter: number; + /** + * the minimum extend of the primary pane + */ minPrimary?: number; + /** + * the minimum extend of the secondary pane + */ minSecondary?: number; } ): number => { @@ -122,10 +137,10 @@ type Props = { minTopPixels?: number; minBottomPixels?: number; splitterHeight?: number; - renderSplitter?: () => JSX.Element; + renderSplitter?: () => React.ReactNode; }; -export const TopBottomSplit = (props: React.PropsWithChildren): JSX.Element => { +export const TopBottomSplit = (props: React.PropsWithChildren) => { const { initialTopGridHeight, minBottomPixels, From 996e05cb33eea39a55199500c32bf98db356914b Mon Sep 17 00:00:00 2001 From: GeoffCoxMSFT Date: Mon, 28 Sep 2020 13:09:12 -0700 Subject: [PATCH 13/13] PR fix --- .../client/src/pages/design/PropertyEditor.tsx | 18 ------------------ 1 file changed, 18 deletions(-) diff --git a/Composer/packages/client/src/pages/design/PropertyEditor.tsx b/Composer/packages/client/src/pages/design/PropertyEditor.tsx index 8086590c99..4c605dc421 100644 --- a/Composer/packages/client/src/pages/design/PropertyEditor.tsx +++ b/Composer/packages/client/src/pages/design/PropertyEditor.tsx @@ -9,7 +9,6 @@ import { FormErrors, JSONSchema7, useFormConfig, useShellApi } from '@bfc/extens import formatMessage from 'format-message'; import isEqual from 'lodash/isEqual'; import debounce from 'lodash/debounce'; -// import { Resizable, ResizeCallback } from 're-resizable'; import { MicrosoftAdaptiveDialog } from '@bfc/shared'; import { formEditor } from './styles'; @@ -28,12 +27,6 @@ const PropertyEditor: React.FC = () => { const { shellApi, ...shellData } = useShellApi(); const { currentDialog, data: formData = {}, focusPath, focusedSteps, schemas } = shellData; - // const currentWidth = shellData?.userSettings?.propertyEditorWidth || 400; - - // const handleResize: ResizeCallback = (_e, _dir, _ref, d) => { - // shellApi.updateUserSettings({ propertyEditorWidth: currentWidth + d.width }); - // }; - const [localData, setLocalData] = useState(formData as MicrosoftAdaptiveDialog); const syncData = useRef( @@ -115,17 +108,6 @@ const PropertyEditor: React.FC = () => { setLocalData(newData); }; - // - // - return (