]> git.ipfire.org Git - thirdparty/bootstrap.git/commitdiff
Fix: `isVisible` function behavior in case of a `<details>` element, on chrome 97...
authorRyan Berliner <22206986+RyanBerliner@users.noreply.github.com>
Thu, 13 Jan 2022 08:55:05 +0000 (03:55 -0500)
committerGitHub <noreply@github.com>
Thu, 13 Jan 2022 08:55:05 +0000 (10:55 +0200)
js/src/util/index.js
js/tests/unit/util/index.spec.js

index 8bd614d40c48b3ec0341d974cc0331e7b7ac2e8f..4e52fd3eb0bfc6e95eca99ec6f7630f483852778 100644 (file)
@@ -128,7 +128,26 @@ const isVisible = element => {
     return false
   }
 
-  return getComputedStyle(element).getPropertyValue('visibility') === 'visible'
+  const elementIsVisible = getComputedStyle(element).getPropertyValue('visibility') === 'visible'
+  // Handle `details` element as its content may falsie appear visible when it is closed
+  const closedDetails = element.closest('details:not([open])')
+
+  if (!closedDetails) {
+    return elementIsVisible
+  }
+
+  if (closedDetails !== element) {
+    const summary = element.closest('summary')
+    if (summary && summary.parentNode !== closedDetails) {
+      return false
+    }
+
+    if (summary === null) {
+      return false
+    }
+  }
+
+  return elementIsVisible
 }
 
 const isDisabled = element => {
index 52e64faa91aeac054316ffb0e24be0a17ac4f36b..9d8c5ed98627b28ccd259b35a21f5886d8ca6209 100644 (file)
@@ -320,6 +320,42 @@ describe('Util', () => {
 
       expect(Util.isVisible(div)).toBeFalse()
     })
+
+    it('should return true if its a closed details element', () => {
+      fixtureEl.innerHTML = '<details id="element"></details>'
+
+      const div = fixtureEl.querySelector('#element')
+
+      expect(Util.isVisible(div)).toBeTrue()
+    })
+
+    it('should return true if the element is visible inside an open details element', () => {
+      fixtureEl.innerHTML = [
+        '<details open>',
+        '  <div id="element"></div>',
+        '</details>'
+      ].join('')
+
+      const div = fixtureEl.querySelector('#element')
+
+      expect(Util.isVisible(div)).toBeTrue()
+    })
+
+    it('should return true if the element is a visible summary in a closed details element', () => {
+      fixtureEl.innerHTML = [
+        '<details>',
+        '  <summary id="element-1">',
+        '    <span id="element-2"></span>',
+        '  </summary>',
+        '</details>'
+      ].join('')
+
+      const element1 = fixtureEl.querySelector('#element-1')
+      const element2 = fixtureEl.querySelector('#element-2')
+
+      expect(Util.isVisible(element1)).toBeTrue()
+      expect(Util.isVisible(element2)).toBeTrue()
+    })
   })
 
   describe('isDisabled', () => {