Atlaskit Modal Dialog in Server Environment

Hi Everyone,

We have some issues using the Atlaskit Modal Dialog in a server environment and maybe someone else had these issues. Maybe there is a documented way around it that I didn’t found yet.

  • Atlaskit Modal Dialog will not disable keyboard events (e.g. j/k navigation, edit mask)
  • Attach File to issue is still active with an open Dialog
  • as the atlaskit dialog has a fixed z-index of 510 it is behind many atlassian dialogs (e.g. edit issue) as they have a z-index of around 3000

Hi @m.herrmann,

I don’t have a clear answer for making the z-indexes for Atlaskit, AUI, and Jira modals work together, unfortunately.

As for the keyboard shortcuts, you could disable Jira shortcuts while your modal is open. Assuming you’re keeping track of the open state of your modal with component state, the solution might look like the following:

import React, { useState, useEffect } from 'react';
import Modal from '@atlaskit/modal-dialog';

const MyApp = () => {
  const [modalOpen, setModalOpen] = useState(false);
  
  useEffect(() => {
    // create a function that returns true if the modal is open.
    const isModalOpen = () => modalOpen;
    // this will register a function that's checked before executing all keyboard shortcuts.
    // if any of these function returns `true`, the shortcut will not be executed.
    // be sure to add a web-resource dependency on `jira.webresources:key-commands`
    // to guarantee this global variable exists before your code runs!
    AJS.KeyboardShortcuts.addIgnoreCondition(isModalOpen);
    // if your component is removed, ensure you don't accidentally disable keyboard shortcuts forever!
    return () => setModalOpen(false);
  });

  return (
    <>
      {modalOpen && <Modal ... />}
    </>
  );
}

Hope that helps!

Cheers,
Daz

3 Likes

Hi @daz ,

Thanks for the example code and your effort to document it to this extend.
My current workaround work something like this:

import React, { useEffect, useState, useCallback } from 'react';
import Modal from '@atlaskit/modal-dialog';
import Button from '@atlaskit/button';

export const TestModal = () => {
	const [modalOpen, setModalOpen] = useState(false);

	useEffect(() => {
		// create a function that returns true if the modal is open.
		const isModalOpen = () => modalOpen;
		// this will register a function that's checked before executing all keyboard shortcuts.
		// if any of these function returns `true`, the shortcut will not be executed.
		// be sure to add a web-resource dependency on `jira.webresources:key-commands`
		// to guarantee this global variable exists before your code runs!
		AJS.KeyboardShortcut.addIgnoreCondition(isModalOpen);
		// if your component is removed, ensure you don't accidentally disable keyboard shortcuts forever!
		return () => setModalOpen(false);
	}, []);
	const zIndexParentFixRef = useCallback((node) => {
		// check if reference node is an existing html element
		if (node === null || !(node instanceof HTMLElement)) {
			return;
		}
		// get the parent element with the atlaskit-portal css class.
		// this is where the z-index should be modified in the current version,
		// which is not stable and may change in the future
		const atlasKitPortalParent = node.closest('.atlaskit-portal');
		if (!atlasKitPortalParent || !(atlasKitPortalParent instanceof HTMLElement)) {
			return;
		}
		// set z-index to a higher value than the default edit issue dialog
		atlasKitPortalParent.style.zIndex = '3100';
	}, []);

	return (
		<>
			<Button appearance="primary" onClick={() => setModalOpen(true)}>
				Open modal
			</Button>
			{modalOpen && (
				<Modal onClose={() => setModalOpen(false)}>
					<div ref={zIndexParentFixRef}>This is some Modal content</div>
				</Modal>
			)}
		</>
	);
};

As soon as the div inside the modal is rendered, it will use the callback reference to find the atlaskit parent with the z-index and set it to a new value.
Maybe this will help someone who has the same issue.