Merge pull request #11247 from allenve/feat-globalevent-sdk2

feat: 全局广播事件sdk
This commit is contained in:
Allen 2024-11-22 14:49:22 +08:00 committed by GitHub
commit 3d07dd2870
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
10 changed files with 120 additions and 59 deletions

View File

@ -58,7 +58,6 @@
"@swc/core": "^1.3.107", "@swc/core": "^1.3.107",
"@swc/helpers": "^0.5.3", "@swc/helpers": "^0.5.3",
"@swc/jest": "^0.2.34", "@swc/jest": "^0.2.34",
"@types/classnames": "^2.3.4",
"@types/express": "^4.17.14", "@types/express": "^4.17.14",
"@types/jest": "^28.1.0", "@types/jest": "^28.1.0",
"@types/js-yaml": "^4.0.5", "@types/js-yaml": "^4.0.5",

View File

@ -28,7 +28,7 @@ import {
import {SimpleMap} from './utils/SimpleMap'; import {SimpleMap} from './utils/SimpleMap';
import { import {
bindEvent, bindEvent,
bindGlobalEvent, bindGlobalEventForRenderer as bindGlobalEvent,
dispatchEvent, dispatchEvent,
RendererEvent RendererEvent
} from './utils/renderer-event'; } from './utils/renderer-event';

View File

@ -129,6 +129,8 @@ import {StatusScoped} from './StatusScoped';
import styleManager from './StyleManager'; import styleManager from './StyleManager';
import {bindGlobalEvent, dispatchGlobalEvent} from './utils/renderer-event';
// @ts-ignore // @ts-ignore
export const version = '__buildVersion'; export const version = '__buildVersion';
(window as any).amisVersionInfo = { (window as any).amisVersionInfo = {
@ -181,6 +183,9 @@ export {
getClassPrefix, getClassPrefix,
classnames, classnames,
makeClassnames, makeClassnames,
// 全局广播事件
bindGlobalEvent,
dispatchGlobalEvent,
// 多语言相关 // 多语言相关
getDefaultLocale, getDefaultLocale,
setDefaultLocale, setDefaultLocale,

View File

@ -7,6 +7,7 @@ import {createObject, extendObject} from './object';
import debounce from 'lodash/debounce'; import debounce from 'lodash/debounce';
import {resolveVariableAndFilterForAsync} from './resolveVariableAndFilterForAsync'; import {resolveVariableAndFilterForAsync} from './resolveVariableAndFilterForAsync';
import {evalExpression, evalExpressionWithConditionBuilderAsync} from './tpl'; import {evalExpression, evalExpressionWithConditionBuilderAsync} from './tpl';
import type {PlainObject} from '../types';
export interface debounceConfig { export interface debounceConfig {
maxWait?: number; maxWait?: number;
@ -195,7 +196,7 @@ export const bindEvent = (renderer: any) => {
return undefined; return undefined;
}; };
export const bindGlobalEvent = (renderer: any) => { export const bindGlobalEventForRenderer = (renderer: any) => {
if (!renderer) { if (!renderer) {
return undefined; return undefined;
} }
@ -237,6 +238,26 @@ export const bindGlobalEvent = (renderer: any) => {
return void 0; return void 0;
}; };
export const bindGlobalEvent = (
eventName: string,
callback: (data: PlainObject) => void
) => {
if (!BroadcastChannel) {
console.error('BroadcastChannel is not supported in your browser');
return;
}
const bc = new BroadcastChannel(eventName);
bc.onmessage = e => {
const {eventName: name, data} = e.data;
if (name === eventName) {
callback(data);
}
};
return () => bc.close();
};
// 触发事件 // 触发事件
export async function dispatchEvent( export async function dispatchEvent(
e: string | React.MouseEvent<any>, e: string | React.MouseEvent<any>,

View File

@ -67,7 +67,6 @@
"@rollup/plugin-typescript": "^8.3.2", "@rollup/plugin-typescript": "^8.3.2",
"@svgr/rollup": "^6.2.1", "@svgr/rollup": "^6.2.1",
"@types/async": "^2.0.45", "@types/async": "^2.0.45",
"@types/classnames": "^2.2.3",
"@types/codemirror": "5.60.10", "@types/codemirror": "5.60.10",
"@types/deep-diff": "^1.0.0", "@types/deep-diff": "^1.0.0",
"@types/history": "^4.6.0", "@types/history": "^4.6.0",

View File

@ -26,6 +26,25 @@
display: none; display: none;
} }
} }
.add-event-dropdown-global-event {
position: relative;
&::after {
position: absolute;
content: '全局事件';
display: flex;
align-items: center;
padding: 0 6px;
right: 4px;
top: 4px;
bottom: 4px;
font-size: 12px;
color: #fff;
background-color: #2468f2;
border-radius: 4px;
transform: scale(0.8);
transform-origin: center;
}
}
} }
ul { ul {
width: 100%; width: 100%;
@ -71,6 +90,32 @@
} }
} }
} }
.event-label {
display: flex;
align-items: center;
.event-label-key {
flex: 1;
max-width: 100px;
overflow: hidden;
text-overflow: ellipsis;
}
.global-event-tip {
width: 48px;
display: flex;
> span {
transform: scale(0.7);
transform-origin: left;
background-color: #2468f2;
border-radius: 4px;
font-size: 12px;
color: #fff;
padding: 4px 6px;
flex-shrink: 0;
text-align: center;
}
}
}
} }
&-desc { &-desc {
margin: #{px2rem(12px)}; margin: #{px2rem(12px)};
@ -206,9 +251,6 @@
clip-path: inset(-5px 0px 0px 0px); clip-path: inset(-5px 0px 0px 0px);
} }
} }
&-content-withglobalevent {
margin-top: 100px !important;
}
.no-bd-btm { .no-bd-btm {
border-bottom: none; border-bottom: none;
} }

View File

@ -56,7 +56,6 @@
"@rollup/plugin-typescript": "^8.3.2", "@rollup/plugin-typescript": "^8.3.2",
"@svgr/rollup": "^6.2.1", "@svgr/rollup": "^6.2.1",
"@types/async": "^2.0.45", "@types/async": "^2.0.45",
"@types/classnames": "^2.2.3",
"@types/codemirror": "5.60.10", "@types/codemirror": "5.60.10",
"@types/deep-diff": "^1.0.0", "@types/deep-diff": "^1.0.0",
"@types/history": "^4.6.0", "@types/history": "^4.6.0",

View File

@ -1092,7 +1092,7 @@ export class EventControl extends React.Component<
getComponents, getComponents,
allComponents, allComponents,
render, render,
globalEvents, globalEvents = [],
subscribeSchemaSubmit subscribeSchemaSubmit
} = this.props; } = this.props;
const { const {
@ -1167,65 +1167,51 @@ export class EventControl extends React.Component<
disabled: false, disabled: false,
className: 'block w-full add-event-dropdown', className: 'block w-full add-event-dropdown',
closeOnClick: true, closeOnClick: true,
buttons: events.map(item => ({ buttons: [
type: 'button', ...events.map(item => ({
disabledTip: '您已添加该事件', type: 'button',
tooltipPlacement: 'left', disabledTip: '您已添加该事件',
disabled: Object.keys(onEvent).includes(item.eventName), tooltipPlacement: 'left',
actionType: '', disabled: Object.keys(onEvent).includes(item.eventName),
label: item.eventLabel, actionType: '',
onClick: this.addEvent.bind( label: item.eventLabel,
this, onClick: this.addEvent.bind(
item, this,
Object.keys(onEvent).includes(item.eventName) item,
) Object.keys(onEvent).includes(item.eventName)
})) )
})),
...globalEvents.map(item => ({
type: 'button',
disabledTip: '您已添加该全局事件',
tooltipPlacement: 'left',
disabled: Object.keys(onEvent).includes(item.name),
actionType: '',
className: 'add-event-dropdown-global-event',
label: item.label,
onClick: this.addGlobalEvent.bind(
this,
item,
Object.keys(onEvent).includes(item.name)
)
}))
]
}, },
{ {
popOverContainer: null // amis 渲染挂载节点会使用 this.target popOverContainer: null // amis 渲染挂载节点会使用 this.target
} }
)} )}
{globalEvents
? render(
'dropdown',
{
type: 'dropdown-button',
level: 'enhance',
label: '添加全局事件',
disabled: false,
className: 'block w-full add-event-dropdown mt-2',
closeOnClick: true,
buttons: globalEvents.map(item => ({
type: 'button',
disabledTip: '您已添加该事件',
tooltipPlacement: 'left',
disabled: Object.keys(onEvent).includes(item.name),
actionType: '',
label: item.label,
onClick: this.addGlobalEvent.bind(
this,
item,
Object.keys(onEvent).includes(item.name)
)
}))
},
{
popOverContainer: null // amis 渲染挂载节点会使用 this.target
}
)
: null}
</header> </header>
<ul <ul
className={cx({ className={cx({
'ae-event-control-content': true, 'ae-event-control-content': true,
'ae-event-control-content-oldentry': showOldEntry, 'ae-event-control-content-oldentry': showOldEntry
'ae-event-control-content-withglobalevent': globalEvents?.length
})} })}
ref={this.dragRef} ref={this.dragRef}
> >
{eventKeys.length ? ( {eventKeys.length ? (
eventKeys.map((eventKey, eventIndex) => { eventKeys.map((eventKey, eventIndex) => {
const globalEvent = globalEvents.find(i => i.name === eventKey);
return ( return (
<li className="event-item" key={`content_${eventIndex}`}> <li className="event-item" key={`content_${eventIndex}`}>
<div <div
@ -1252,7 +1238,18 @@ export class EventControl extends React.Component<
) )
}} }}
> >
<div>{getEventLabel(events, eventKey) || eventKey}</div> {!globalEvent ? (
<div>{getEventLabel(events, eventKey) || eventKey}</div>
) : (
<div className="event-label">
<span className="global-event-tip">
<span></span>
</span>
<span className="event-label-key">
{globalEvent.label || eventKey}
</span>
</div>
)}
</TooltipWrapper> </TooltipWrapper>
<div className="event-item-header-toolbar"> <div className="event-item-header-toolbar">
<div <div

View File

@ -1745,7 +1745,7 @@ export class Evaluator {
* @param {date} date * @param {date} date
* @param {string} unit 'day''month''year' `week` * @param {string} unit 'day''month''year' `week`
* @param {string} format * @param {string} format
* @returns {date | string} , format * @returns {any} , format
*/ */
fnSTARTOF(date: Date, unit?: any, format?: string) { fnSTARTOF(date: Date, unit?: any, format?: string) {
const md = moment(this.normalizeDate(date)).startOf(unit || 'day'); const md = moment(this.normalizeDate(date)).startOf(unit || 'day');
@ -1760,7 +1760,7 @@ export class Evaluator {
* @param {date} date * @param {date} date
* @param {string} unit 'day''month''year' `week` * @param {string} unit 'day''month''year' `week`
* @param {string} format * @param {string} format
* @returns {date | string} , format * @returns {any} , format
*/ */
fnENDOF(date: Date, unit?: any, format?: string) { fnENDOF(date: Date, unit?: any, format?: string) {
const md = moment(this.normalizeDate(date)).endOf(unit || 'day'); const md = moment(this.normalizeDate(date)).endOf(unit || 'day');

View File

@ -37,7 +37,6 @@
"@rollup/plugin-url": "^7.0.0", "@rollup/plugin-url": "^7.0.0",
"@svgr/rollup": "^6.4.0", "@svgr/rollup": "^6.4.0",
"@types/async": "^2.0.45", "@types/async": "^2.0.45",
"@types/classnames": "^2.2.3",
"@types/codemirror": "^5.60.5", "@types/codemirror": "^5.60.5",
"@types/deep-diff": "^1.0.0", "@types/deep-diff": "^1.0.0",
"@types/history": "^4.6.0", "@types/history": "^4.6.0",
@ -71,4 +70,4 @@
"react": ">=16.8.6", "react": ">=16.8.6",
"react-dom": ">=16.8.6" "react-dom": ">=16.8.6"
} }
} }