Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions packages/base/src/css/OpenUI5PopupStyles.css
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,9 @@
border: none;
overflow: visible;
margin: 0;
}

.sapUiBLy[popover] {
width: 100%;
height: 100%;
}
36 changes: 34 additions & 2 deletions packages/base/src/features/patchPopup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ type OpenUI5Popup = {
getOpenState: () => "CLOSED" | "CLOSING" | "OPEN" | "OPENING",
getContent: () => Control | HTMLElement | null, // this is the OpenUI5 Element/Control instance that opens the Popup (usually sap.m.Popover/sap.m.Dialog)
onFocusEvent: (...args: any[]) => void,
getModal: () => boolean
}
};

Expand All @@ -37,6 +38,22 @@ const addOpenedPopup = (popupInfo: PopupInfo) => {
};

const removeOpenedPopup = (popup: object) => {
if (isNativePopoverOpen()) {
const prevPopup = AllOpenedPopupsRegistry.openedRegistry[AllOpenedPopupsRegistry.openedRegistry.length - 2];
if (prevPopup && prevPopup.type === "OpenUI5" && (prevPopup.instance as any).getModal()) {
const content = (prevPopup.instance as any).getContent()?.getDomRef() as HTMLElement;
const block = document.getElementById("sap-ui-blocklayer-popup");

content?.hidePopover();

if ((prevPopup.instance as any).getModal()) {
block?.showPopover();
}

content?.showPopover();
}
}

const index = AllOpenedPopupsRegistry.openedRegistry.findIndex(el => el.instance === popup);
if (index > -1) {
AllOpenedPopupsRegistry.openedRegistry.splice(index, 1);
Expand Down Expand Up @@ -68,7 +85,14 @@ const hasWebComponentPopupAbove = (popup: object) => {
return false;
};

const openNativePopover = (domRef: HTMLElement) => {
const openNativePopover = (domRef: HTMLElement, popup: object) => {
const block = document.getElementById("sap-ui-blocklayer-popup");

if ((popup as any).getModal() && block) {
block?.setAttribute("popover", "manual");
block?.hidePopover();
block?.showPopover();
}
domRef.setAttribute("popover", "manual");
domRef.showPopover();
};
Expand All @@ -78,6 +102,14 @@ const closeNativePopover = (domRef: HTMLElement) => {
domRef.hidePopover();
domRef.removeAttribute("popover");
}

const lastPopup = AllOpenedPopupsRegistry.openedRegistry[AllOpenedPopupsRegistry.openedRegistry.length - 1];
if (lastPopup.type === "OpenUI5") {
const block = document.getElementById("sap-ui-blocklayer-popup");
if (block && block.hasAttribute("popover")) {
block.hidePopover();
}
}
};

const isNativePopoverOpen = (root: Document | ShadowRoot = document): boolean => {
Expand Down Expand Up @@ -113,7 +145,7 @@ const patchOpen = (Popup: OpenUI5Popup) => {
if (element) {
const domRef = element instanceof HTMLElement ? element : element?.getDomRef();
if (domRef) {
openNativePopover(domRef);
openNativePopover(domRef, this);
}
}
}
Expand Down
118 changes: 118 additions & 0 deletions packages/main/cypress/specs/OpenUI5andWebCPopups.cy.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ function onOpenUI5InitMethod(win) {
press: function () {
new Dialog("openUI5Dialog1", {
title: "OpenUI5 Dialog",
draggable: true,
content: [
new HTML({
content:
Expand Down Expand Up @@ -49,6 +50,12 @@ function onOpenUI5InitMethod(win) {
press: function () {
(document.getElementById("respPopoverNoInitialFocus") as any).open = true;
}
}),
new Button("openWebCDialog", {
text: "Open WebC Dialog",
press: function () {
(document.getElementById("webCDialog1") as any).open = true;
}
})
],
afterClose: function () {
Expand Down Expand Up @@ -112,6 +119,10 @@ function onOpenUI5InitMethod(win) {
openUI5Dialog(win);
});

document.getElementById("openUI5DialogFromWebC").addEventListener("click", function () {
openUI5Dialog(win);
});

document.getElementById("popoverButtonNoFocus").addEventListener("click", function (event) {
openUI5Popover(win, event.target);
});
Expand All @@ -121,6 +132,7 @@ function openUI5Dialog(win) {
(win as any).sap.ui.require(["sap/m/Button", "sap/m/Dialog"], (Button, Dialog) => {
new Dialog("openUI5DialogWithButtons", {
title: "OpenUI5 Dialog",
draggable: true,
content: [
new Button({
text: "Focus stop"
Expand All @@ -130,6 +142,29 @@ function openUI5Dialog(win) {
press: function () {
(document.getElementById("newDialog1") as any).open = true;
}
}),
new Button("openUI5DialogFromUi5", {
text: "Open UI5 Dialog",
press: function () {
openUI5DialogFromUi5(win)
}
})
],
afterClose: function () {
this.destroy();
}
}).open();
});
}

function openUI5DialogFromUi5(win) {
(win as any).sap.ui.require(["sap/m/Button", "sap/m/Dialog"], (Button, Dialog) => {
new Dialog("openUI5DialogFinal", {
title: "OpenUI5 Dialog",
draggable: true,
content: [
new Button({
text: "Focus stop"
})
],
afterClose: function () {
Expand Down Expand Up @@ -204,6 +239,9 @@ describe("ui5 and web components integration", () => {
<Dialog id="newDialog1" headerText="This is an WebC Dialog 2">
<Button id="someButton">Some button</Button>
</Dialog>
<Dialog id="webCDialog1" draggable headerText="This is a WebC Dialog">
<Button id="openUI5DialogFromWebC">Open UI5 Dialog 2</Button>
</Dialog>
<div id="content"></div>
<ResponsivePopover
id="respPopover"
Expand Down Expand Up @@ -605,6 +643,85 @@ describe("ui5 and web components integration", () => {
.should('be.focused');
}

function OpenWebCUI5DialogMixed() {
// Open UI5 Dialog
cy.get("#openUI5Button")
.should('be.visible')
.realClick();

cy.get("#openUI5Dialog1")
.should('be.visible');

// Open WebC Dialog from UI5 Dialog
cy.get("#openWebCDialog")
.should('be.visible')
.realClick();

cy.get("#webCDialog1")
.should('be.visible');

cy.get("#openUI5Dialog1")
.should('not.be.visible');

// Open UI5 Dialog from WebC Dialog
cy.get("#openUI5DialogFromWebC")
.should('be.visible')
.realClick();

cy.get("#webCDialog1")
.should('not.be.visible');

cy.get("#openUI5Dialog1")
.should('not.be.visible');

cy.get("#openUI5DialogWithButtons")
.should('be.visible');

// Open UI5 Dialog from UI5 Dialog
cy.get("#openUI5DialogFromUi5")
.should('be.visible')
.realClick();

cy.get("#openUI5DialogFinal")
.should('be.visible');

cy.get("#openUI5Dialog1")
.should('not.be.visible');

cy.get("#webCDialog1")
.should('not.be.visible');

cy.get("#openUI5DialogWithButtons")
.should('not.be.visible');

// Close all with Escape
cy.realPress("Escape");

cy.get("#openUI5DialogFinal")
.should('not.exist');

cy.get("#openUI5DialogWithButtons")
.should('be.visible');

cy.realPress("Escape");

cy.get("#openUI5DialogWithButtons")
.should('not.exist');

cy.get("#webCDialog1")
.should('be.visible');

cy.realPress("Escape");

cy.get("#openUI5Dialog1")
.should('be.visible');

cy.realPress("Escape");

cy.get("#openWebCDialog")
.should('not.exist');
}

it("Keyboard", () => {
OpenWebCDialog();
OpenWebCDialogOpenOpenUI5Dialog();
Expand All @@ -617,6 +734,7 @@ describe("ui5 and web components integration", () => {
OpenUI5DialogWebCDialog();
OpenUI5DialogWebCPopoverNoFocus();
OpenUI5DialogWebCSelect();
OpenWebCUI5DialogMixed();
// Merge it after OpenUI5 Popup shadow dom focus fix is released
// OpenUI5DialogWebCComboBox();
});
Expand Down
Loading
Loading