({
accessPath, schema=null, isNested=false, dataDispatch, className,
hasSQLTab, getSQLValue, isTabView=true, viewHelperProps, field,
showError=false, resetKey, focusOnFirstInput=false
})
| 60 | |
| 61 | // The first component of schema view form. |
| 62 | export default function FormView({ |
| 63 | accessPath, schema=null, isNested=false, dataDispatch, className, |
| 64 | hasSQLTab, getSQLValue, isTabView=true, viewHelperProps, field, |
| 65 | showError=false, resetKey, focusOnFirstInput=false |
| 66 | }) { |
| 67 | const [key, setKey] = useState(0); |
| 68 | const subscriberManager = useSchemaStateSubscriber(setKey); |
| 69 | const schemaState = useContext(SchemaStateContext); |
| 70 | const value = useFieldValue(accessPath, schemaState); |
| 71 | const { visible } = useFieldSchema( |
| 72 | field, accessPath, value, viewHelperProps, schemaState, subscriberManager |
| 73 | ); |
| 74 | |
| 75 | const [tabValue, setTabValue] = useState(0); |
| 76 | const formRef = useRef(); |
| 77 | const onScreenTracker = useRef(false); |
| 78 | let isOnScreen = useOnScreen(formRef); |
| 79 | |
| 80 | if (!schema) schema = field.schema; |
| 81 | |
| 82 | // Set focus on the first focusable element. |
| 83 | useEffect(() => { |
| 84 | if (!focusOnFirstInput) return; |
| 85 | setTimeout(() => { |
| 86 | const formEle = formRef.current; |
| 87 | if (!formEle) return; |
| 88 | const activeTabElement = formEle.querySelector( |
| 89 | '[data-test="tabpanel"]:not([hidden])' |
| 90 | ); |
| 91 | if (!activeTabElement) return; |
| 92 | |
| 93 | // Find the first focusable input, which is either: |
| 94 | // * An editable Input element. |
| 95 | // * A select element, which is not disabled. |
| 96 | // * An href element. |
| 97 | // * Any element with 'tabindex', but - tabindex is not set to '-1'. |
| 98 | const firstFocussableElement = activeTabElement.querySelector([ |
| 99 | 'button:not([role="tab"])', |
| 100 | '[href]', |
| 101 | 'input:not(disabled)', |
| 102 | 'select:not(disabled)', |
| 103 | 'textarea', |
| 104 | '[tabindex]:not([tabindex="-1"]):not([data-test="tabpanel"])', |
| 105 | 'div[class="cm-content"]:not([aria-readonly="true"])', |
| 106 | ].join(', ')); |
| 107 | |
| 108 | if (firstFocussableElement) firstFocussableElement.focus(); |
| 109 | }, 200); |
| 110 | }, [tabValue]); |
| 111 | |
| 112 | useEffect(() => { |
| 113 | // Refresh on message changes. |
| 114 | return subscriberManager.current?.add( |
| 115 | schemaState, ['errors', 'message'], 'states', |
| 116 | (newState, prevState) => { |
| 117 | if (_.isUndefined(newState) || _.isUndefined(prevState)) |
| 118 | subscriberManager.current?.signal(); |
| 119 | } |
nothing calls this directly
no test coverage detected