Skip to content

Commit

Permalink
feat(portal-context): Provider 增加 portal 参数,支持配置全局 container (#3060) (#…
Browse files Browse the repository at this point in the history
…3061)

* feat(container-context): add container package (#3060)

* chore(container-context): 规范代码 (#3060)

* chore(portal-context): 改写名字代码 (#3060)

* chore(portal-context): 规范记录(#3060)

* chore(portal-context): 删除多余代码(#3060)

* chore(portal-context): 删除多余空格(#3060)

---------

Co-authored-by: wanjinping <[email protected]>
  • Loading branch information
fcppddl and wanjinping authored Dec 17, 2024
1 parent 1adc538 commit d1d0086
Show file tree
Hide file tree
Showing 19 changed files with 209 additions and 14 deletions.
12 changes: 12 additions & 0 deletions .changeset/little-rabbits-change.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
---
"@hi-ui/core": minor
"@hi-ui/container-context": minor
"@hi-ui/drawer": minor
"@hi-ui/hiui": minor
"@hi-ui/loading": minor
"@hi-ui/modal": minor
"@hi-ui/preview": minor
"@hi-ui/provider": minor
---

feat(portal-context): Provider 增加 portal 参数,支持配置全局 container (#3060)
3 changes: 2 additions & 1 deletion packages/core/core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
"devDependencies": {},
"dependencies": {
"@hi-ui/core-css": "^4.1.5",
"@hi-ui/locale-context": "^4.0.8"
"@hi-ui/locale-context": "^4.0.8",
"@hi-ui/portal-context": "^4.0.0"
}
}
3 changes: 3 additions & 0 deletions packages/core/core/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -73,3 +73,6 @@ export type HiBaseSizeEnum = ValueOf<typeof HiBaseSizeEnum>
// 将 core 设为 peer:保证 context 实例引用一致性
export { useLocaleContext, LocaleProvider } from '@hi-ui/locale-context'
export type { UseLocaleContext, LocaleProviderProps } from '@hi-ui/locale-context'

export { usePortalContext, PortalProvider } from '@hi-ui/portal-context'
export type { UsePortalContext, PortalProviderProps } from '@hi-ui/portal-context'
6 changes: 4 additions & 2 deletions packages/ui/drawer/src/Drawer.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { forwardRef, useCallback, useEffect } from 'react'
import { cx, getPrefixCls, getPrefixStyleVar } from '@hi-ui/classname'
import { __DEV__ } from '@hi-ui/env'
import { HiBaseHTMLProps } from '@hi-ui/core'
import { HiBaseHTMLProps, usePortalContext } from '@hi-ui/core'
import { CSSTransition } from 'react-transition-group'
import { Portal } from '@hi-ui/portal'
import { useModal, UseModalProps } from '@hi-ui/modal'
Expand Down Expand Up @@ -33,7 +33,7 @@ export const Drawer = forwardRef<HTMLDivElement | null, DrawerProps>(
onExited: onExitedProp,
title,
footer,
container,
container: containerProp,
closeIcon = defaultCloseIcon,
width,
height,
Expand All @@ -51,6 +51,8 @@ export const Drawer = forwardRef<HTMLDivElement | null, DrawerProps>(
) => {
const [transitionVisible, transitionVisibleAction] = useToggle(false)
const [transitionExited, transitionExitedAction] = useToggle(true)
const globalContainer = usePortalContext()?.container
const container = containerProp ?? globalContainer

const { rootProps, getModalProps, getModalWrapperProps } = useModal({
...rest,
Expand Down
7 changes: 5 additions & 2 deletions packages/ui/loading/src/Loading.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { CSSTransition } from 'react-transition-group'
import { cx, getPrefixCls } from '@hi-ui/classname'
import { __DEV__ } from '@hi-ui/env'
import { Portal } from '@hi-ui/portal'
import { HiBaseHTMLProps, HiBaseSizeEnum } from '@hi-ui/core'
import { HiBaseHTMLProps, HiBaseSizeEnum, usePortalContext } from '@hi-ui/core'
import { useLatestCallback } from '@hi-ui/use-latest'
import Spinner from '@hi-ui/spinner'
import { useLoading } from './use-loading'
Expand All @@ -18,7 +18,7 @@ export const Loading = forwardRef<null, LoadingProps>(
className,
children,
role = _role,
container,
container: containerProp,
content,
visible = true,
full = false,
Expand All @@ -38,6 +38,9 @@ export const Loading = forwardRef<null, LoadingProps>(
) => {
const { internalVisible, setInternalVisible } = useLoading({ visible, delay })

const globalContainer = usePortalContext()?.container
const container = containerProp ?? globalContainer

useImperativeHandle(innerRef, () => ({
close: () => setInternalVisible(false),
}))
Expand Down
7 changes: 5 additions & 2 deletions packages/ui/modal/src/Modal.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import React, { useEffect, forwardRef, useCallback, useImperativeHandle } from 'react'
import { cx, getPrefixCls } from '@hi-ui/classname'
import { HiBaseHTMLProps, HiBaseSizeEnum, useLocaleContext } from '@hi-ui/core'
import { HiBaseHTMLProps, HiBaseSizeEnum, useLocaleContext, usePortalContext } from '@hi-ui/core'
import { __DEV__ } from '@hi-ui/env'
import { CSSTransition } from 'react-transition-group'
import { Portal } from '@hi-ui/portal'
Expand Down Expand Up @@ -57,7 +57,7 @@ export const Modal = forwardRef<HTMLDivElement | null, ModalProps>(
onClose,
onCancel,
onConfirm,
container,
container: containerProp,
closeIcon = defaultCloseIcon,
showMask = true,
showHeaderDivider = true,
Expand All @@ -74,6 +74,9 @@ export const Modal = forwardRef<HTMLDivElement | null, ModalProps>(
) => {
const i18n = useLocaleContext()

const globalContainer = usePortalContext()?.container
const container = containerProp ?? globalContainer

const cancelText = isUndef(cancelTextProp) ? i18n.get('modal.cancelText') : cancelTextProp
const confirmText = isUndef(confirmTextProp) ? i18n.get('modal.confirmText') : confirmTextProp

Expand Down
11 changes: 11 additions & 0 deletions packages/ui/portal-context/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# `@hi-ui/portal-context`

> TODO: description
## Usage

```
const PortalContext = require('@hi-ui/portal-context');
// TODO: DEMONSTRATE API
```
5 changes: 5 additions & 0 deletions packages/ui/portal-context/__tests__/portal-context.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
const PortalContext = require('../src')

describe('@hi-ui/portal-context', () => {
it('needs tests', () => {})
})
15 changes: 15 additions & 0 deletions packages/ui/portal-context/hi-docs.config.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# PortalContext 上下文

容器设置上下文。

## 何时使用

组件使用场景中文介绍

## 使用示例

<!-- Inject Stories -->

## Props

<!-- Inject Props -->
1 change: 1 addition & 0 deletions packages/ui/portal-context/jest.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
module.exports = require('../../../jest.config')
54 changes: 54 additions & 0 deletions packages/ui/portal-context/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
{
"name": "@hi-ui/portal-context",
"version": "4.0.0",
"description": "A sub-package for @hi-ui/hiui.",
"keywords": [],
"author": "HiUI <[email protected]>",
"homepage": "https://github.com/XiaoMi/hiui/tree/master/packages/ui/container-context#readme",
"license": "MIT",
"directories": {
"lib": "lib",
"test": "__tests__"
},
"files": [
"lib"
],
"main": "lib/cjs/index.js",
"module": "lib/esm/index.js",
"types": "lib/types/index.d.ts",
"typings": "lib/types/index.d.ts",
"exports": {
".": {
"require": "./lib/cjs/index.js",
"default": "./lib/esm/index.js"
}
},
"publishConfig": {
"access": "public"
},
"repository": {
"type": "git",
"url": "git+https://github.com/XiaoMi/hiui.git"
},
"scripts": {
"test": "jest",
"clean": "rimraf lib",
"prebuild": "yarn clean",
"build:esm": "hi-build ./src/index.ts --format esm -d ./lib/esm",
"build:cjs": "hi-build ./src/index.ts --format cjs -d ./lib/cjs",
"build:types": "tsc --emitDeclarationOnly --declaration --declarationDir lib/types",
"build": "concurrently yarn:build:*"
},
"bugs": {
"url": "https://github.com/XiaoMi/hiui/issues"
},
"dependencies": {},
"peerDependencies": {
"react": ">=16.8.6",
"react-dom": ">=16.8.6"
},
"devDependencies": {
"react": "^17.0.1",
"react-dom": "^17.0.1"
}
}
11 changes: 11 additions & 0 deletions packages/ui/portal-context/src/PortalContext.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { createContext, useContext } from 'react'

export const PortalContext = createContext<UsePortalContext>(null)

export const usePortalContext = () => {
const context = useContext(PortalContext)

return context
}

export type UsePortalContext = { container?: HTMLElement | null | undefined } | null | undefined
18 changes: 18 additions & 0 deletions packages/ui/portal-context/src/PortalProvider.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import React from 'react'
import { PortalContext, UsePortalContext } from './PortalContext'
import { __DEV__ } from '@hi-ui/env'

export const PortalProvider: React.FC<PortalProviderProps> = ({ children, portal }) => {
return <PortalContext.Provider value={portal}>{children}</PortalContext.Provider>
}

export interface PortalProviderProps {
/**
* 指定 portal 的容器
*/
portal?: UsePortalContext
}

if (__DEV__) {
PortalProvider.displayName = 'PortalProvider'
}
4 changes: 4 additions & 0 deletions packages/ui/portal-context/src/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
export * from './PortalContext'
export * from './PortalProvider'

export { PortalProvider as default } from './PortalProvider'
16 changes: 16 additions & 0 deletions packages/ui/portal-context/stories/basic.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import React, { useContext } from 'react'
import { PortalContext } from '../src'

/**
* @title 基础用法
*/
export const Basic = () => {
useContext(PortalContext)

return (
<>
<h1>Basic</h1>
<div className="portal-context-basic__wrap"></div>
</>
)
}
8 changes: 8 additions & 0 deletions packages/ui/portal-context/stories/index.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import React from 'react'

export * from './basic.stories'

export default {
title: 'Private(暂不对外)/PortalContext',
decorators: [(story: Function) => <div>{story()}</div>],
}
4 changes: 4 additions & 0 deletions packages/ui/portal-context/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
{
"extends": "../../../tsconfig.json",
"include": ["./src"]
}
17 changes: 15 additions & 2 deletions packages/ui/preview/src/Preview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { Portal } from '@hi-ui/portal'
import { Watermark, WatermarkProps } from '@hi-ui/watermark'
import { CSSTransition } from 'react-transition-group'
import { useUncontrolledState } from '@hi-ui/use-uncontrolled-state'
import { HiBaseHTMLProps } from '@hi-ui/core'
import { HiBaseHTMLProps, usePortalContext } from '@hi-ui/core'
import { useLatestCallback } from '@hi-ui/use-latest'
import {
ZoomInOutlined,
Expand Down Expand Up @@ -46,11 +46,16 @@ export const Preview = forwardRef<HTMLDivElement | null, PreviewProps>(
src,
watermarkProps,
disabledDownload = false,
container: containerProp,
disabledPortal = false,
},
ref
) => {
const cls = cx(prefixCls, className)

const globalContainer = usePortalContext()?.container
const container = containerProp ?? globalContainer

const [active, setActive] = useUncontrolledState(defaultCurrent || 0, current, onPreviewChange)

const [isMoving, setIsMoving] = useState(false)
Expand Down Expand Up @@ -199,7 +204,7 @@ export const Preview = forwardRef<HTMLDivElement | null, PreviewProps>(
)

return (
<Portal>
<Portal container={container} disabled={disabledPortal}>
<div ref={ref} role={role} className={cls} style={{ ...style, display: 'none' }}>
<CSSTransition
classNames={`${prefixCls}__mask--transition`}
Expand Down Expand Up @@ -352,6 +357,14 @@ export interface PreviewProps extends Omit<HiBaseHTMLProps<'div'>, 'onError'> {
* 当前预览图片索引(受控)
*/
onPreviewChange?: (current: number) => void
/**
* 指定 portal 的容器
*/
container?: HTMLElement | null
/**
* 是否禁用 portal
*/
disabledPortal?: boolean
}

if (__DEV__) {
Expand Down
21 changes: 16 additions & 5 deletions packages/ui/provider/src/Provider.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
import React, { useEffect } from 'react'
import { __DEV__ } from '@hi-ui/env'
import { LocaleProvider, LocaleProviderProps } from '@hi-ui/core'
import {
LocaleProvider,
LocaleProviderProps,
PortalProvider,
PortalProviderProps,
} from '@hi-ui/core'
import { DesignSystemAccentColorEnum, DesignSystemProps } from './types'
import { createSystem, extendsTheme } from './theme'
import { getAccentColorTheme } from './accent-color'
Expand All @@ -13,6 +18,7 @@ export const Provider: React.FC<ProviderProps> & { extends: ProviderExtendsFunc
languages,
accentColor,
theme,
portal,
}) => {
/**
* global css var config
Expand All @@ -31,13 +37,18 @@ export const Provider: React.FC<ProviderProps> & { extends: ProviderExtendsFunc
}, [accentColor, theme])

return (
<LocaleProvider locale={locale} languages={languages}>
{children}
</LocaleProvider>
<PortalProvider portal={portal}>
<LocaleProvider locale={locale} languages={languages}>
{children}
</LocaleProvider>
</PortalProvider>
)
}

export interface ProviderProps extends LocaleProviderProps, ThemeProviderProps {}
export interface ProviderProps
extends LocaleProviderProps,
PortalProviderProps,
ThemeProviderProps {}

interface ThemeProviderProps {
/**
Expand Down

0 comments on commit d1d0086

Please sign in to comment.