Skip to content
GitLab
Explore
Projects
Groups
Snippets
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
Bootstrap
bootstrap
Commits
8a37045b
Commit
8a37045b
authored
6 years ago
by
Johann-S
Committed by
XhmikosR
6 years ago
Browse files
Options
Download
Email Patches
Plain Diff
move util in a util folder with the sanitizer
parent
8affe84c
main
cleanup-floating-forms
cssvar-function
dependabot/npm_and_yarn/stylelint-and-stylelint-config-twbs-bootstrap-15.3.0
extend-snippets
feat/data-target
floating-always-visible
floating-labels-icons
fod-main-banner
form-controls-with-icons
github/fork/719media/patch-13
github/fork/719media/patch-14
github/fork/719media/patch-9
github/fork/ChellyAhmed/fix-typo-reboot.md
github/fork/ChellyAhmed/offcanvas-scroll-back
github/fork/CtrlAltLilith/main
github/fork/Elysiome/offcanvas-optional-window-resizing
github/fork/JanSargsyan/main
github/fork/LunicLynx/support-different-line-height-for-buttons
github/fork/Psixodelik/main
github/fork/Ronid1/ronid1/offcanvas_static_backdrop
github/fork/RyanBerliner/tooltip-accessibility
github/fork/SantiagoPVazquez/Feature-default-border-bottom-to-dropdown-item
github/fork/Sir-Genius/utils
github/fork/Sumit-Singh-8/main
github/fork/Viktor-VERA2020/offcanvas-slide
github/fork/Zivangu9/input-group-for-form-control-plaintext
github/fork/alpadev/alpadev/call-dispose-on-component-reinstantiation
github/fork/astagi/fix/tree-shake-modules
github/fork/compnerd/dark-accordion-icon
github/fork/derSascha/dropdown-dont-close-on-input-click
github/fork/dev-ph1l/main
github/fork/donquixote/issue-33861-utl-mixin
github/fork/florianlacreuse/mixin-make-row-gutter-y
github/fork/gregorw/main
github/fork/iteggmbh/transitionend-dispose-race
github/fork/jdelStrother/patch-1
github/fork/jonnysp/form-floating
github/fork/jonnysp/independent-offcanvas
github/fork/jonnysp/theme-dark-on-card-and-modal-fix
github/fork/josefdlange/floating-label-placeholder-opacity
github/fork/julien-deramond/enhance-change-version.js
github/fork/julien-deramond/main-jd-fix-offset-content
github/fork/julien-deramond/main-jd-issue-with-utitlies
github/fork/julien-deramond/main-xmr-pa11y-ci-jd-add-hideElements
github/fork/kyletsang/fix-tooltip-padding
github/fork/lacutah/CheckboxCenteringDocumentation
github/fork/lekoala/patch-3
github/fork/louismaximepiton/main-kld-lmp-collapse-proposal
github/fork/louismaximepiton/main-lmp-card-inner-border-radius-fix
github/fork/louismaximepiton/main-lmp-carousel-multiple-images
github/fork/louismaximepiton/main-lmp-css-var-init
github/fork/louismaximepiton/main-lmp-disabled-floating-label-fix
github/fork/louismaximepiton/main-lmp-input-range-fix
github/fork/louismaximepiton/main-lmp-shift-color
github/fork/louismaximepiton/main-lmp-table-active-tr-fix
github/fork/maciek-szn/switch
github/fork/michael-roth/feature/19964-multiple-tab-targets
github/fork/mistic100/dom-utils
github/fork/nkdas91/accordion
github/fork/nstungcom/fix-missing-modal-open-class
github/fork/oraliahdz/animation-utilities
github/fork/pine3ree/patch-7
github/fork/pouwerkerk/unindent-scss-docs-shortcode
github/fork/smares/smares-no-scolling-on-modal-close
github/fork/tgm-git/patch-1
gs-forms
gs-toasts-with-animated-progress-bar
gs/add-history-helper
gs/change-version-dir-on-docs
gs/data-must-set-onlu-one-instance
gs/docs/fix-drop-down-error
gs/event-handler-2
gs/make-docs-js-build
gs/make-simple-attribute-toggler
gs/popover-fix-doc
gs/provide-steConfig-method
gs/scrollspy-smoothscroll-option-use-browser-history
gs/streamline-jqueryInterface
gs/support-drop-down-in-navbar
gs/test-js-generic-trigger
gs/try-web-components
gs/tweak-collapse-js-selector
gs/use-event-handler-in-cocmponent
gs/use-rollup-replace-for-version
jo-docs-thanks-page
jo-ssr-friendly
logical-props-spacing-utils
main-fod-disabled-form-check-label
main-fod-nested-accordion
main-fod-simpler-table-structure
main-fod-table-separator
main-fod-utilities-contrast
main-jd-abbr-title
main-jd-add-chips
main-jd-add-doc-for-sass-custom-colors
main-jd-add-enable-host-to-handle-web-components
main-jd-browserstack-fine-tune
main-jd-browserstack-updates
main-jd-docs-consistent-usage-of-css-sections-step-2
main-jd-fix-docs-headers-in-white
main-jd-fix-highlight-docs-border-radius
main-jd-fix-placeholder-color-background-params-for-img-markup
main-jd-glossary-experiment
main-jd-postcss-drop-empty-css-vars
main-jd-proto-doc-astro
main-jd-skip-navigation-component
main-jd-stackblitz-for-examples
main-jd-upgrade-browserlistrc
main-jd-use-host
main-lmp-dark-theme-customization
main-lmp-handle-scroll-target
main-lmp-tab-fix
main-mc-opensearch
main-xmr-bundlewatch-action
main-xmr-eslint-plugin-compat
main-xmr-hugo-docs-vendor
main-xmr-hugo-rm-ver
main-xmr-linkinator-prod
main-xmr-min-mangle
main-xmr-pa11y-ci
more-darkmode-examples
nested-dropdowns
patrickhlauke-issue37428
patrickhlauke-use-of-color-tweaks
pr/34102
pr/37590
previous-next-docs-links
sticky-thead
utilities-functions-mixin
v530-dev
v6-postcss-custom-media
v6-spinner-dots
v6/gs/use-floating-ui-in-place-of-popper
xmr/dev
xmr/docs-png
xmr/docs-svgs
xmr/hugo-reorg-files
xmr/js-2
xmr/markdownlint
xmr/prepare-530-alpha2
xmr/xo
v5.3.0-alpha1
v5.2.3
v5.2.2
v5.2.1
v5.2.0
v5.2.0-beta1
v5.1.3
v5.1.2
v5.1.1
v5.1.0
v5.0.2
v5.0.1
v5.0.0
v5.0.0-beta3
v5.0.0-beta2
v5.0.0-beta1
v5.0.0-alpha3
v5.0.0-alpha2
v5.0.0-alpha1
5 merge requests
!31948
Examples/Floating-labels: fix bad behavior with autofill
,
!30064
test
,
!29779
Responsive sizing
,
!28882
fix custom-select-indicator in IE10
,
!28721
Hot test
Changes
34
Hide whitespace changes
Inline
Side-by-side
Showing
20 changed files
.eslintrc.json
+1
-1
.eslintrc.json
build/build-plugins.js
+33
-30
build/build-plugins.js
js/src/alert.js
+11
-6
js/src/alert.js
js/src/button.js
+3
-2
js/src/button.js
js/src/carousel.js
+23
-13
js/src/carousel.js
js/src/collapse.js
+30
-21
js/src/collapse.js
js/src/dom/eventHandler.js
+3
-2
js/src/dom/eventHandler.js
js/src/dom/polyfill.js
+4
-2
js/src/dom/polyfill.js
js/src/dom/selectorEngine.js
+4
-2
js/src/dom/selectorEngine.js
js/src/dropdown.js
+18
-12
js/src/dropdown.js
js/src/index.js
+0
-2
js/src/index.js
js/src/modal.js
+32
-23
js/src/modal.js
js/src/popover.js
+3
-2
js/src/popover.js
js/src/scrollspy.js
+13
-8
js/src/scrollspy.js
js/src/tab.js
+17
-9
js/src/tab.js
js/src/toast.js
+14
-9
js/src/toast.js
js/src/tooltip.js
+30
-17
js/src/tooltip.js
js/src/util.js
+0
-179
js/src/util.js
js/src/util/index.js
+177
-0
js/src/util/index.js
js/src/util/sanitizer.js
+43
-41
js/src/util/sanitizer.js
with
459 additions
and
381 deletions
+459
-381
.eslintrc.json
+
1
-
1
View file @
8a37045b
...
...
@@ -130,7 +130,7 @@
"func-call-spacing"
:
"error"
,
"func-name-matching"
:
"error"
,
"func-names"
:
"off"
,
"func-style"
:
[
"error"
,
"declaration"
]
,
"func-style"
:
"off"
,
"id-blacklist"
:
"error"
,
"id-length"
:
"off"
,
"id-match"
:
"error"
,
...
...
This diff is collapsed.
Click to expand it.
build/build-plugins.js
+
33
-
30
View file @
8a37045b
...
...
@@ -41,23 +41,25 @@ const bsPlugins = {
ScrollSpy
:
path
.
resolve
(
__dirname
,
'
../js/src/scrollspy.js
'
),
Tab
:
path
.
resolve
(
__dirname
,
'
../js/src/tab.js
'
),
Toast
:
path
.
resolve
(
__dirname
,
'
../js/src/toast.js
'
),
Tooltip
:
path
.
resolve
(
__dirname
,
'
../js/src/tooltip.js
'
),
Util
:
path
.
resolve
(
__dirname
,
'
../js/src/util.js
'
)
Tooltip
:
path
.
resolve
(
__dirname
,
'
../js/src/tooltip.js
'
)
}
const
rootPath
=
TEST
?
'
../js/coverage/dist/
'
:
'
../js/dist/
'
if
(
TEST
)
{
bsPlugins
.
Util
=
path
.
resolve
(
__dirname
,
'
../js/src/util/index.js
'
)
bsPlugins
.
Sanitizer
=
path
.
resolve
(
__dirname
,
'
../js/src/util/sanitizer.js
'
)
}
const
defaultPluginConfig
=
{
external
:
[
bsPlugins
.
Data
,
bsPlugins
.
EventHandler
,
bsPlugins
.
SelectorEngine
,
bsPlugins
.
Util
bsPlugins
.
SelectorEngine
],
globals
:
{
[
bsPlugins
.
Data
]:
'
Data
'
,
[
bsPlugins
.
EventHandler
]:
'
EventHandler
'
,
[
bsPlugins
.
SelectorEngine
]:
'
SelectorEngine
'
,
[
bsPlugins
.
Util
]:
'
Util
'
[
bsPlugins
.
SelectorEngine
]:
'
SelectorEngine
'
}
}
...
...
@@ -65,7 +67,9 @@ function getConfigByPluginKey(pluginKey) {
if
(
pluginKey
===
'
Data
'
||
pluginKey
===
'
Manipulator
'
||
pluginKey
===
'
Util
'
pluginKey
===
'
Polyfill
'
||
pluginKey
===
'
Util
'
||
pluginKey
===
'
Sanitizer
'
)
{
return
{
external
:
[],
...
...
@@ -76,21 +80,10 @@ function getConfigByPluginKey(pluginKey) {
if
(
pluginKey
===
'
EventHandler
'
||
pluginKey
===
'
SelectorEngine
'
)
{
return
{
external
:
[
bsPlugins
.
Polyfill
,
bsPlugins
.
Util
bsPlugins
.
Polyfill
],
globals
:
{
[
bsPlugins
.
Polyfill
]:
'
Polyfill
'
,
[
bsPlugins
.
Util
]:
'
Util
'
}
}
}
if
(
pluginKey
===
'
Polyfill
'
)
{
return
{
external
:
[
bsPlugins
.
Util
],
globals
:
{
[
bsPlugins
.
Util
]:
'
Util
'
[
bsPlugins
.
Polyfill
]:
'
Polyfill
'
}
}
}
...
...
@@ -125,14 +118,12 @@ function getConfigByPluginKey(pluginKey) {
external
:
[
bsPlugins
.
Data
,
bsPlugins
.
SelectorEngine
,
bsPlugins
.
Tooltip
,
bsPlugins
.
Util
bsPlugins
.
Tooltip
],
globals
:
{
[
bsPlugins
.
Data
]:
'
Data
'
,
[
bsPlugins
.
SelectorEngine
]:
'
SelectorEngine
'
,
[
bsPlugins
.
Tooltip
]:
'
Tooltip
'
,
[
bsPlugins
.
Util
]:
'
Util
'
[
bsPlugins
.
Tooltip
]:
'
Tooltip
'
}
}
}
...
...
@@ -142,14 +133,12 @@ function getConfigByPluginKey(pluginKey) {
external
:
[
bsPlugins
.
Data
,
bsPlugins
.
EventHandler
,
bsPlugins
.
Manipulator
,
bsPlugins
.
Util
bsPlugins
.
Manipulator
],
globals
:
{
[
bsPlugins
.
Data
]:
'
Data
'
,
[
bsPlugins
.
EventHandler
]:
'
EventHandler
'
,
[
bsPlugins
.
Manipulator
]:
'
Manipulator
'
,
[
bsPlugins
.
Util
]:
'
Util
'
[
bsPlugins
.
Manipulator
]:
'
Manipulator
'
}
}
}
...
...
@@ -161,14 +150,28 @@ function build(plugin) {
const
config
=
getConfigByPluginKey
(
plugin
)
const
external
=
config
.
external
const
globals
=
config
.
globals
let
pluginPath
=
rootPath
const
utilObjects
=
[
'
Util
'
,
'
Sanitizer
'
]
const
pluginPath
=
[
const
domObjects
=
[
'
Data
'
,
'
EventHandler
'
,
'
Manipulator
'
,
'
Polyfill
'
,
'
SelectorEngine
'
].
includes
(
plugin
)
?
`
${
rootPath
}
/dom/`
:
rootPath
]
if
(
utilObjects
.
includes
(
plugin
))
{
pluginPath
=
`
${
rootPath
}
/util/`
}
if
(
domObjects
.
includes
(
plugin
))
{
pluginPath
=
`
${
rootPath
}
/dom/`
}
const
pluginFilename
=
`
${
plugin
.
toLowerCase
()}
.js`
...
...
This diff is collapsed.
Click to expand it.
js/src/alert.js
+
11
-
6
View file @
8a37045b
...
...
@@ -5,10 +5,16 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getSelectorFromElement
,
getTransitionDurationFromElement
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -83,7 +89,7 @@ class Alert {
// Private
_getRootElement
(
element
)
{
const
selector
=
Util
.
getSelectorFromElement
(
element
)
const
selector
=
getSelectorFromElement
(
element
)
let
parent
=
false
if
(
selector
)
{
...
...
@@ -109,11 +115,11 @@ class Alert {
return
}
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
element
)
EventHandler
.
one
(
element
,
Util
.
TRANSITION_END
,
(
event
)
=>
this
.
_destroyElement
(
element
,
event
))
Util
.
emulateTransitionEnd
(
element
,
transitionDuration
)
.
one
(
element
,
TRANSITION_END
,
(
event
)
=>
this
.
_destroyElement
(
element
,
event
))
emulateTransitionEnd
(
element
,
transitionDuration
)
}
_destroyElement
(
element
)
{
...
...
@@ -170,7 +176,6 @@ EventHandler
* add .alert to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Alert
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/button.js
+
3
-
2
View file @
8a37045b
...
...
@@ -5,10 +5,12 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -180,7 +182,6 @@ EventHandler.on(document, Event.BLUR_DATA_API, Selector.DATA_TOGGLE_CARROT, (eve
* add .button to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Button
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/carousel.js
+
23
-
13
View file @
8a37045b
...
...
@@ -5,11 +5,22 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getSelectorFromElement
,
getTransitionDurationFromElement
,
isVisible
,
makeArray
,
reflow
,
triggerTransitionEnd
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -143,7 +154,7 @@ class Carousel {
nextWhenVisible
()
{
// Don't call next when the page isn't visible
// or the carousel or its parent isn't visible
if
(
!
document
.
hidden
&&
Util
.
isVisible
(
this
.
_element
))
{
if
(
!
document
.
hidden
&&
isVisible
(
this
.
_element
))
{
this
.
next
()
}
}
...
...
@@ -160,7 +171,7 @@ class Carousel {
}
if
(
SelectorEngine
.
findOne
(
Selector
.
NEXT_PREV
,
this
.
_element
))
{
Util
.
triggerTransitionEnd
(
this
.
_element
)
triggerTransitionEnd
(
this
.
_element
)
this
.
cycle
(
true
)
}
...
...
@@ -233,7 +244,7 @@ class Carousel {
...
Default
,
...
config
}
Util
.
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
return
config
}
...
...
@@ -320,7 +331,7 @@ class Carousel {
}
}
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
ITEM_IMG
,
this
.
_element
)).
forEach
((
itemImg
)
=>
{
makeArray
(
SelectorEngine
.
find
(
Selector
.
ITEM_IMG
,
this
.
_element
)).
forEach
((
itemImg
)
=>
{
EventHandler
.
on
(
itemImg
,
Event
.
DRAG_START
,
(
e
)
=>
e
.
preventDefault
())
})
...
...
@@ -356,7 +367,7 @@ class Carousel {
_getItemIndex
(
element
)
{
this
.
_items
=
element
&&
element
.
parentNode
?
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
ITEM
,
element
.
parentNode
))
?
makeArray
(
SelectorEngine
.
find
(
Selector
.
ITEM
,
element
.
parentNode
))
:
[]
return
this
.
_items
.
indexOf
(
element
)
...
...
@@ -459,7 +470,7 @@ class Carousel {
if
(
this
.
_element
.
classList
.
contains
(
ClassName
.
SLIDE
))
{
nextElement
.
classList
.
add
(
orderClassName
)
Util
.
reflow
(
nextElement
)
reflow
(
nextElement
)
activeElement
.
classList
.
add
(
directionalClassName
)
nextElement
.
classList
.
add
(
directionalClassName
)
...
...
@@ -472,10 +483,10 @@ class Carousel {
this
.
_config
.
interval
=
this
.
_config
.
defaultInterval
||
this
.
_config
.
interval
}
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
activeElement
)
const
transitionDuration
=
getTransitionDurationFromElement
(
activeElement
)
EventHandler
.
one
(
activeElement
,
Util
.
TRANSITION_END
,
()
=>
{
.
one
(
activeElement
,
TRANSITION_END
,
()
=>
{
nextElement
.
classList
.
remove
(
directionalClassName
)
nextElement
.
classList
.
remove
(
orderClassName
)
nextElement
.
classList
.
add
(
ClassName
.
ACTIVE
)
...
...
@@ -496,7 +507,7 @@ class Carousel {
},
0
)
})
Util
.
emulateTransitionEnd
(
activeElement
,
transitionDuration
)
emulateTransitionEnd
(
activeElement
,
transitionDuration
)
}
else
{
activeElement
.
classList
.
remove
(
ClassName
.
ACTIVE
)
nextElement
.
classList
.
add
(
ClassName
.
ACTIVE
)
...
...
@@ -557,7 +568,7 @@ class Carousel {
}
static
_dataApiClickHandler
(
event
)
{
const
selector
=
Util
.
getSelectorFromElement
(
this
)
const
selector
=
getSelectorFromElement
(
this
)
if
(
!
selector
)
{
return
...
...
@@ -603,7 +614,7 @@ EventHandler
.
on
(
document
,
Event
.
CLICK_DATA_API
,
Selector
.
DATA_SLIDE
,
Carousel
.
_dataApiClickHandler
)
EventHandler
.
on
(
window
,
Event
.
LOAD_DATA_API
,
()
=>
{
const
carousels
=
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_RIDE
))
const
carousels
=
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_RIDE
))
for
(
let
i
=
0
,
len
=
carousels
.
length
;
i
<
len
;
i
++
)
{
Carousel
.
_carouselInterface
(
carousels
[
i
],
Data
.
getData
(
carousels
[
i
],
DATA_KEY
))
}
...
...
@@ -616,7 +627,6 @@ EventHandler.on(window, Event.LOAD_DATA_API, () => {
* add .carousel to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Carousel
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/collapse.js
+
30
-
21
View file @
8a37045b
...
...
@@ -5,11 +5,21 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getSelectorFromElement
,
getTransitionDurationFromElement
,
isElement
,
makeArray
,
reflow
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -69,16 +79,16 @@ class Collapse {
this
.
_isTransitioning
=
false
this
.
_element
=
element
this
.
_config
=
this
.
_getConfig
(
config
)
this
.
_triggerArray
=
Util
.
makeArray
(
SelectorEngine
.
find
(
this
.
_triggerArray
=
makeArray
(
SelectorEngine
.
find
(
`[data-toggle="collapse"][href="#
${
element
.
id
}
"],`
+
`[data-toggle="collapse"][data-target="#
${
element
.
id
}
"]`
))
const
toggleList
=
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_TOGGLE
))
const
toggleList
=
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_TOGGLE
))
for
(
let
i
=
0
,
len
=
toggleList
.
length
;
i
<
len
;
i
++
)
{
const
elem
=
toggleList
[
i
]
const
selector
=
Util
.
getSelectorFromElement
(
elem
)
const
filterElement
=
Util
.
makeArray
(
SelectorEngine
.
find
(
selector
))
const
selector
=
getSelectorFromElement
(
elem
)
const
filterElement
=
makeArray
(
SelectorEngine
.
find
(
selector
))
.
filter
((
foundElem
)
=>
foundElem
===
element
)
if
(
selector
!==
null
&&
filterElement
.
length
)
{
...
...
@@ -130,7 +140,7 @@ class Collapse {
let
activesData
if
(
this
.
_parent
)
{
actives
=
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
ACTIVES
,
this
.
_parent
))
actives
=
makeArray
(
SelectorEngine
.
find
(
Selector
.
ACTIVES
,
this
.
_parent
))
.
filter
((
elem
)
=>
{
if
(
typeof
this
.
_config
.
parent
===
'
string
'
)
{
return
elem
.
getAttribute
(
'
data-parent
'
)
===
this
.
_config
.
parent
...
...
@@ -201,11 +211,11 @@ class Collapse {
const
capitalizedDimension
=
dimension
[
0
].
toUpperCase
()
+
dimension
.
slice
(
1
)
const
scrollSize
=
`scroll
${
capitalizedDimension
}
`
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_element
)
EventHandler
.
one
(
this
.
_element
,
Util
.
TRANSITION_END
,
complete
)
EventHandler
.
one
(
this
.
_element
,
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
this
.
_element
.
style
[
dimension
]
=
`
${
this
.
_element
[
scrollSize
]}
px`
}
...
...
@@ -224,7 +234,7 @@ class Collapse {
this
.
_element
.
style
[
dimension
]
=
`
${
this
.
_element
.
getBoundingClientRect
()[
dimension
]}
px`
Util
.
reflow
(
this
.
_element
)
reflow
(
this
.
_element
)
this
.
_element
.
classList
.
add
(
ClassName
.
COLLAPSING
)
this
.
_element
.
classList
.
remove
(
ClassName
.
COLLAPSE
)
...
...
@@ -234,7 +244,7 @@ class Collapse {
if
(
triggerArrayLength
>
0
)
{
for
(
let
i
=
0
;
i
<
triggerArrayLength
;
i
++
)
{
const
trigger
=
this
.
_triggerArray
[
i
]
const
selector
=
Util
.
getSelectorFromElement
(
trigger
)
const
selector
=
getSelectorFromElement
(
trigger
)
if
(
selector
!==
null
)
{
const
elem
=
SelectorEngine
.
findOne
(
selector
)
...
...
@@ -257,10 +267,10 @@ class Collapse {
}
this
.
_element
.
style
[
dimension
]
=
''
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_element
)
EventHandler
.
one
(
this
.
_element
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
EventHandler
.
one
(
this
.
_element
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
}
setTransitioning
(
isTransitioning
)
{
...
...
@@ -285,7 +295,7 @@ class Collapse {
...
config
}
config
.
toggle
=
Boolean
(
config
.
toggle
)
// Coerce string values
Util
.
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
return
config
}
...
...
@@ -297,7 +307,7 @@ class Collapse {
_getParent
()
{
let
parent
if
(
Util
.
isElement
(
this
.
_config
.
parent
))
{
if
(
isElement
(
this
.
_config
.
parent
))
{
parent
=
this
.
_config
.
parent
// it's a jQuery object
...
...
@@ -311,7 +321,7 @@ class Collapse {
const
selector
=
`[data-toggle="collapse"][data-parent="
${
this
.
_config
.
parent
}
"]`
Util
.
makeArray
(
SelectorEngine
.
find
(
selector
,
parent
))
makeArray
(
SelectorEngine
.
find
(
selector
,
parent
))
.
forEach
((
element
)
=>
{
this
.
_addAriaAndCollapsedClass
(
Collapse
.
_getTargetFromElement
(
element
),
...
...
@@ -342,7 +352,7 @@ class Collapse {
// Static
static
_getTargetFromElement
(
element
)
{
const
selector
=
Util
.
getSelectorFromElement
(
element
)
const
selector
=
getSelectorFromElement
(
element
)
return
selector
?
SelectorEngine
.
findOne
(
selector
)
:
null
}
...
...
@@ -394,8 +404,8 @@ EventHandler.on(document, Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (
}
const
triggerData
=
Manipulator
.
getDataAttributes
(
this
)
const
selector
=
Util
.
getSelectorFromElement
(
this
)
const
selectorElements
=
Util
.
makeArray
(
SelectorEngine
.
find
(
selector
))
const
selector
=
getSelectorFromElement
(
this
)
const
selectorElements
=
makeArray
(
SelectorEngine
.
find
(
selector
))
selectorElements
.
forEach
((
element
)
=>
{
const
data
=
Data
.
getData
(
element
,
DATA_KEY
)
...
...
@@ -422,7 +432,6 @@ EventHandler.on(document, Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (
* add .collapse to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Collapse
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/dom/eventHandler.js
+
3
-
2
View file @
8a37045b
...
...
@@ -5,8 +5,10 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
}
from
'
../util/index
'
import
Polyfill
from
'
./polyfill
'
import
Util
from
'
../util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -248,7 +250,6 @@ const EventHandler = {
const
typeEvent
=
event
.
replace
(
stripNameRegex
,
''
)
const
inNamespace
=
event
!==
typeEvent
const
isNative
=
nativeEvents
.
indexOf
(
typeEvent
)
>
-
1
const
$
=
Util
.
jQuery
let
jQueryEvent
let
bubbles
=
true
...
...
This diff is collapsed.
Click to expand it.
js/src/dom/polyfill.js
+
4
-
2
View file @
8a37045b
...
...
@@ -5,7 +5,9 @@
* --------------------------------------------------------------------------
*/
import
Util
from
'
../util
'
import
{
getUID
}
from
'
../util/index
'
/* istanbul ignore next */
const
Polyfill
=
(()
=>
{
...
...
@@ -48,7 +50,7 @@ const Polyfill = (() => {
const
hasId
=
Boolean
(
this
.
id
)
if
(
!
hasId
)
{
this
.
id
=
Util
.
getUID
(
'
scope
'
)
this
.
id
=
getUID
(
'
scope
'
)
}
let
nodeList
=
null
...
...
This diff is collapsed.
Click to expand it.
js/src/dom/selectorEngine.js
+
4
-
2
View file @
8a37045b
...
...
@@ -6,7 +6,9 @@
*/
import
Polyfill
from
'
./polyfill
'
import
Util
from
'
../util
'
import
{
makeArray
}
from
'
../util/index
'
/**
* ------------------------------------------------------------------------
...
...
@@ -44,7 +46,7 @@ const SelectorEngine = {
return
null
}
const
children
=
Util
.
makeArray
(
element
.
children
)
const
children
=
makeArray
(
element
.
children
)
return
children
.
filter
((
child
)
=>
this
.
matches
(
child
,
selector
))
},
...
...
This diff is collapsed.
Click to expand it.
js/src/dropdown.js
+
18
-
12
View file @
8a37045b
...
...
@@ -5,12 +5,19 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
getSelectorFromElement
,
isElement
,
makeArray
,
noop
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
Popper
from
'
popper.js
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -159,7 +166,7 @@ class Dropdown {
if
(
this
.
_config
.
reference
===
'
parent
'
)
{
referenceElement
=
parent
}
else
if
(
Util
.
isElement
(
this
.
_config
.
reference
))
{
}
else
if
(
isElement
(
this
.
_config
.
reference
))
{
referenceElement
=
this
.
_config
.
reference
// Check if it's jQuery element
...
...
@@ -182,9 +189,9 @@ class Dropdown {
// only needed because of broken event delegation on iOS
// https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html
if
(
'
ontouchstart
'
in
document
.
documentElement
&&
!
Util
.
makeArray
(
SelectorEngine
.
closest
(
parent
,
Selector
.
NAVBAR_NAV
)).
length
)
{
Util
.
makeArray
(
document
.
body
.
children
)
.
forEach
((
elem
)
=>
EventHandler
.
on
(
elem
,
'
mouseover
'
,
null
,
Util
.
noop
()))
!
makeArray
(
SelectorEngine
.
closest
(
parent
,
Selector
.
NAVBAR_NAV
)).
length
)
{
makeArray
(
document
.
body
.
children
)
.
forEach
((
elem
)
=>
EventHandler
.
on
(
elem
,
'
mouseover
'
,
null
,
noop
()))
}
this
.
_element
.
focus
()
...
...
@@ -272,7 +279,7 @@ class Dropdown {
...
config
}
Util
.
typeCheckConfig
(
typeCheckConfig
(
NAME
,
config
,
this
.
constructor
.
DefaultType
...
...
@@ -389,7 +396,7 @@ class Dropdown {
return
}
const
toggles
=
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_TOGGLE
))
const
toggles
=
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_TOGGLE
))
for
(
let
i
=
0
,
len
=
toggles
.
length
;
i
<
len
;
i
++
)
{
const
parent
=
Dropdown
.
_getParentFromElement
(
toggles
[
i
])
const
context
=
Data
.
getData
(
toggles
[
i
],
DATA_KEY
)
...
...
@@ -425,8 +432,8 @@ class Dropdown {
// If this is a touch-enabled device we remove the extra
// empty mouseover listeners we added for iOS support
if
(
'
ontouchstart
'
in
document
.
documentElement
)
{
Util
.
makeArray
(
document
.
body
.
children
)
.
forEach
((
elem
)
=>
EventHandler
.
off
(
elem
,
'
mouseover
'
,
null
,
Util
.
noop
()))
makeArray
(
document
.
body
.
children
)
.
forEach
((
elem
)
=>
EventHandler
.
off
(
elem
,
'
mouseover
'
,
null
,
noop
()))
}
toggles
[
i
].
setAttribute
(
'
aria-expanded
'
,
'
false
'
)
...
...
@@ -439,7 +446,7 @@ class Dropdown {
static
_getParentFromElement
(
element
)
{
let
parent
const
selector
=
Util
.
getSelectorFromElement
(
element
)
const
selector
=
getSelectorFromElement
(
element
)
if
(
selector
)
{
parent
=
SelectorEngine
.
findOne
(
selector
)
...
...
@@ -482,7 +489,7 @@ class Dropdown {
return
}
const
items
=
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
VISIBLE_ITEMS
,
parent
))
const
items
=
makeArray
(
SelectorEngine
.
find
(
Selector
.
VISIBLE_ITEMS
,
parent
))
if
(
!
items
.
length
)
{
return
...
...
@@ -535,7 +542,6 @@ EventHandler
* add .dropdown to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Dropdown
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/index.js
+
0
-
2
View file @
8a37045b
...
...
@@ -16,10 +16,8 @@ import ScrollSpy from './scrollspy'
import
Tab
from
'
./tab
'
import
Toast
from
'
./toast
'
import
Tooltip
from
'
./tooltip
'
import
Util
from
'
./util
'
export
{
Util
,
Alert
,
Button
,
Carousel
,
...
...
This diff is collapsed.
Click to expand it.
js/src/modal.js
+
32
-
23
View file @
8a37045b
...
...
@@ -5,11 +5,21 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getSelectorFromElement
,
getTransitionDurationFromElement
,
isVisible
,
makeArray
,
reflow
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -184,10 +194,10 @@ class Modal {
if
(
transition
)
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_element
)
EventHandler
.
one
(
this
.
_element
,
Util
.
TRANSITION_END
,
(
event
)
=>
this
.
_hideModal
(
event
))
Util
.
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
EventHandler
.
one
(
this
.
_element
,
TRANSITION_END
,
(
event
)
=>
this
.
_hideModal
(
event
))
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
}
else
{
this
.
_hideModal
()
}
...
...
@@ -228,7 +238,7 @@ class Modal {
...
Default
,
...
config
}
Util
.
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
return
config
}
...
...
@@ -252,7 +262,7 @@ class Modal {
}
if
(
transition
)
{
Util
.
reflow
(
this
.
_element
)
reflow
(
this
.
_element
)
}
this
.
_element
.
classList
.
add
(
ClassName
.
SHOW
)
...
...
@@ -272,10 +282,10 @@ class Modal {
}
if
(
transition
)
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_dialog
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_dialog
)
EventHandler
.
one
(
this
.
_dialog
,
Util
.
TRANSITION_END
,
transitionComplete
)
Util
.
emulateTransitionEnd
(
this
.
_dialog
,
transitionDuration
)
EventHandler
.
one
(
this
.
_dialog
,
TRANSITION_END
,
transitionComplete
)
emulateTransitionEnd
(
this
.
_dialog
,
transitionDuration
)
}
else
{
transitionComplete
()
}
...
...
@@ -364,7 +374,7 @@ class Modal {
})
if
(
animate
)
{
Util
.
reflow
(
this
.
_backdrop
)
reflow
(
this
.
_backdrop
)
}
this
.
_backdrop
.
classList
.
add
(
ClassName
.
SHOW
)
...
...
@@ -378,10 +388,10 @@ class Modal {
return
}
const
backdropTransitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_backdrop
)
const
backdropTransitionDuration
=
getTransitionDurationFromElement
(
this
.
_backdrop
)
EventHandler
.
one
(
this
.
_backdrop
,
Util
.
TRANSITION_END
,
callback
)
Util
.
emulateTransitionEnd
(
this
.
_backdrop
,
backdropTransitionDuration
)
EventHandler
.
one
(
this
.
_backdrop
,
TRANSITION_END
,
callback
)
emulateTransitionEnd
(
this
.
_backdrop
,
backdropTransitionDuration
)
}
else
if
(
!
this
.
_isShown
&&
this
.
_backdrop
)
{
this
.
_backdrop
.
classList
.
remove
(
ClassName
.
SHOW
)
...
...
@@ -393,9 +403,9 @@ class Modal {
}
if
(
this
.
_element
.
classList
.
contains
(
ClassName
.
FADE
))
{
const
backdropTransitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_backdrop
)
EventHandler
.
one
(
this
.
_backdrop
,
Util
.
TRANSITION_END
,
callbackRemove
)
Util
.
emulateTransitionEnd
(
this
.
_backdrop
,
backdropTransitionDuration
)
const
backdropTransitionDuration
=
getTransitionDurationFromElement
(
this
.
_backdrop
)
EventHandler
.
one
(
this
.
_backdrop
,
TRANSITION_END
,
callbackRemove
)
emulateTransitionEnd
(
this
.
_backdrop
,
backdropTransitionDuration
)
}
else
{
callbackRemove
()
}
...
...
@@ -439,7 +449,7 @@ class Modal {
// while $(DOMNode).css('padding-right') returns the calculated value or 0 if not set
// Adjust fixed content padding
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
FIXED_CONTENT
))
makeArray
(
SelectorEngine
.
find
(
Selector
.
FIXED_CONTENT
))
.
forEach
((
element
)
=>
{
const
actualPadding
=
element
.
style
.
paddingRight
const
calculatedPadding
=
window
.
getComputedStyle
(
element
)[
'
padding-right
'
]
...
...
@@ -448,7 +458,7 @@ class Modal {
})
// Adjust sticky content margin
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
STICKY_CONTENT
))
makeArray
(
SelectorEngine
.
find
(
Selector
.
STICKY_CONTENT
))
.
forEach
((
element
)
=>
{
const
actualMargin
=
element
.
style
.
marginRight
const
calculatedMargin
=
window
.
getComputedStyle
(
element
)[
'
margin-right
'
]
...
...
@@ -469,7 +479,7 @@ class Modal {
_resetScrollbar
()
{
// Restore fixed content padding
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
FIXED_CONTENT
))
makeArray
(
SelectorEngine
.
find
(
Selector
.
FIXED_CONTENT
))
.
forEach
((
element
)
=>
{
const
padding
=
Manipulator
.
getDataAttribute
(
element
,
'
padding-right
'
)
if
(
typeof
padding
!==
'
undefined
'
)
{
...
...
@@ -479,7 +489,7 @@ class Modal {
})
// Restore sticky content and navbar-toggler margin
Util
.
makeArray
(
SelectorEngine
.
find
(
`
${
Selector
.
STICKY_CONTENT
}
`
))
makeArray
(
SelectorEngine
.
find
(
`
${
Selector
.
STICKY_CONTENT
}
`
))
.
forEach
((
element
)
=>
{
const
margin
=
Manipulator
.
getDataAttribute
(
element
,
'
margin-right
'
)
if
(
typeof
margin
!==
'
undefined
'
)
{
...
...
@@ -546,7 +556,7 @@ class Modal {
EventHandler
.
on
(
document
,
Event
.
CLICK_DATA_API
,
Selector
.
DATA_TOGGLE
,
function
(
event
)
{
let
target
const
selector
=
Util
.
getSelectorFromElement
(
this
)
const
selector
=
getSelectorFromElement
(
this
)
if
(
selector
)
{
target
=
SelectorEngine
.
findOne
(
selector
)
...
...
@@ -569,7 +579,7 @@ EventHandler.on(document, Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (
}
EventHandler
.
one
(
target
,
Event
.
HIDDEN
,
()
=>
{
if
(
Util
.
isVisible
(
this
))
{
if
(
isVisible
(
this
))
{
this
.
focus
()
}
})
...
...
@@ -589,7 +599,6 @@ EventHandler.on(document, Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (
* ------------------------------------------------------------------------
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Modal
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/popover.js
+
3
-
2
View file @
8a37045b
...
...
@@ -5,10 +5,12 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Tooltip
from
'
./tooltip
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -177,7 +179,6 @@ class Popover extends Tooltip {
* ------------------------------------------------------------------------
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Popover
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/scrollspy.js
+
13
-
8
View file @
8a37045b
...
...
@@ -5,11 +5,17 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
getSelectorFromElement
,
getUID
,
makeArray
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -118,12 +124,12 @@ class ScrollSpy {
this
.
_scrollHeight
=
this
.
_getScrollHeight
()
const
targets
=
Util
.
makeArray
(
SelectorEngine
.
find
(
this
.
_selector
))
const
targets
=
makeArray
(
SelectorEngine
.
find
(
this
.
_selector
))
targets
.
map
((
element
)
=>
{
let
target
const
targetSelector
=
Util
.
getSelectorFromElement
(
element
)
const
targetSelector
=
getSelectorFromElement
(
element
)
if
(
targetSelector
)
{
target
=
SelectorEngine
.
findOne
(
targetSelector
)
...
...
@@ -174,13 +180,13 @@ class ScrollSpy {
if
(
typeof
config
.
target
!==
'
string
'
)
{
let
id
=
config
.
target
.
id
if
(
!
id
)
{
id
=
Util
.
getUID
(
NAME
)
id
=
getUID
(
NAME
)
config
.
target
.
id
=
id
}
config
.
target
=
`#
${
id
}
`
}
Util
.
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
typeCheckConfig
(
NAME
,
config
,
DefaultType
)
return
config
}
...
...
@@ -284,7 +290,7 @@ class ScrollSpy {
}
_clear
()
{
Util
.
makeArray
(
SelectorEngine
.
find
(
this
.
_selector
))
makeArray
(
SelectorEngine
.
find
(
this
.
_selector
))
.
filter
((
node
)
=>
node
.
classList
.
contains
(
ClassName
.
ACTIVE
))
.
forEach
((
node
)
=>
node
.
classList
.
remove
(
ClassName
.
ACTIVE
))
}
...
...
@@ -321,7 +327,7 @@ class ScrollSpy {
*/
EventHandler
.
on
(
window
,
Event
.
LOAD_DATA_API
,
()
=>
{
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_SPY
))
makeArray
(
SelectorEngine
.
find
(
Selector
.
DATA_SPY
))
.
forEach
((
spy
)
=>
new
ScrollSpy
(
spy
,
Manipulator
.
getDataAttributes
(
spy
)))
})
...
...
@@ -331,7 +337,6 @@ EventHandler.on(window, Event.LOAD_DATA_API, () => {
* ------------------------------------------------------------------------
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
ScrollSpy
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/tab.js
+
17
-
9
View file @
8a37045b
...
...
@@ -5,10 +5,18 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getSelectorFromElement
,
getTransitionDurationFromElement
,
makeArray
,
reflow
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -80,11 +88,11 @@ class Tab {
let
target
let
previous
const
listElement
=
SelectorEngine
.
closest
(
this
.
_element
,
Selector
.
NAV_LIST_GROUP
)
const
selector
=
Util
.
getSelectorFromElement
(
this
.
_element
)
const
selector
=
getSelectorFromElement
(
this
.
_element
)
if
(
listElement
)
{
const
itemSelector
=
listElement
.
nodeName
===
'
UL
'
||
listElement
.
nodeName
===
'
OL
'
?
Selector
.
ACTIVE_UL
:
Selector
.
ACTIVE
previous
=
Util
.
makeArray
(
SelectorEngine
.
find
(
itemSelector
,
listElement
))
previous
=
makeArray
(
SelectorEngine
.
find
(
itemSelector
,
listElement
))
previous
=
previous
[
previous
.
length
-
1
]
}
...
...
@@ -153,11 +161,11 @@ class Tab {
)
if
(
active
&&
isTransitioning
)
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
active
)
const
transitionDuration
=
getTransitionDurationFromElement
(
active
)
active
.
classList
.
remove
(
ClassName
.
SHOW
)
EventHandler
.
one
(
active
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
active
,
transitionDuration
)
EventHandler
.
one
(
active
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
active
,
transitionDuration
)
}
else
{
complete
()
}
...
...
@@ -183,7 +191,7 @@ class Tab {
element
.
setAttribute
(
'
aria-selected
'
,
true
)
}
Util
.
reflow
(
element
)
reflow
(
element
)
if
(
element
.
classList
.
contains
(
ClassName
.
FADE
))
{
element
.
classList
.
add
(
ClassName
.
SHOW
)
...
...
@@ -193,7 +201,7 @@ class Tab {
const
dropdownElement
=
SelectorEngine
.
closest
(
element
,
Selector
.
DROPDOWN
)
if
(
dropdownElement
)
{
Util
.
makeArray
(
SelectorEngine
.
find
(
Selector
.
DROPDOWN_TOGGLE
))
makeArray
(
SelectorEngine
.
find
(
Selector
.
DROPDOWN_TOGGLE
))
.
forEach
((
dropdown
)
=>
dropdown
.
classList
.
add
(
ClassName
.
ACTIVE
))
}
...
...
@@ -242,9 +250,9 @@ EventHandler.on(document, Event.CLICK_DATA_API, Selector.DATA_TOGGLE, function (
* ------------------------------------------------------------------------
* jQuery
* ------------------------------------------------------------------------
* add .tab to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Tab
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/toast.js
+
14
-
9
View file @
8a37045b
...
...
@@ -5,10 +5,16 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
getTransitionDurationFromElement
,
typeCheckConfig
}
from
'
./util/index
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -104,10 +110,10 @@ class Toast {
this
.
_element
.
classList
.
remove
(
ClassName
.
HIDE
)
this
.
_element
.
classList
.
add
(
ClassName
.
SHOWING
)
if
(
this
.
_config
.
animation
)
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_element
)
EventHandler
.
one
(
this
.
_element
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
EventHandler
.
one
(
this
.
_element
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
}
else
{
complete
()
}
...
...
@@ -153,7 +159,7 @@ class Toast {
...
typeof
config
===
'
object
'
&&
config
?
config
:
{}
}
Util
.
typeCheckConfig
(
typeCheckConfig
(
NAME
,
config
,
this
.
constructor
.
DefaultType
...
...
@@ -179,10 +185,10 @@ class Toast {
this
.
_element
.
classList
.
remove
(
ClassName
.
SHOW
)
if
(
this
.
_config
.
animation
)
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
_element
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
_element
)
EventHandler
.
one
(
this
.
_element
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
EventHandler
.
one
(
this
.
_element
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
this
.
_element
,
transitionDuration
)
}
else
{
complete
()
}
...
...
@@ -221,7 +227,6 @@ class Toast {
* add .toast to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Toast
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/tooltip.js
+
30
-
17
View file @
8a37045b
...
...
@@ -5,16 +5,27 @@
* --------------------------------------------------------------------------
*/
import
{
jQuery
as
$
,
TRANSITION_END
,
emulateTransitionEnd
,
findShadowRoot
,
getTransitionDurationFromElement
,
getUID
,
isElement
,
makeArray
,
noop
,
typeCheckConfig
}
from
'
./util/index
'
import
{
DefaultWhitelist
,
sanitizeHtml
}
from
'
./
tools
/sanitizer
'
}
from
'
./
util
/sanitizer
'
import
Data
from
'
./dom/data
'
import
EventHandler
from
'
./dom/eventHandler
'
import
Manipulator
from
'
./dom/manipulator
'
import
Popper
from
'
popper.js
'
import
SelectorEngine
from
'
./dom/selectorEngine
'
import
Util
from
'
./util
'
/**
* ------------------------------------------------------------------------
...
...
@@ -257,7 +268,7 @@ class Tooltip {
if
(
this
.
isWithContent
()
&&
this
.
_isEnabled
)
{
const
showEvent
=
EventHandler
.
trigger
(
this
.
element
,
this
.
constructor
.
Event
.
SHOW
)
const
shadowRoot
=
Util
.
findShadowRoot
(
this
.
element
)
const
shadowRoot
=
findShadowRoot
(
this
.
element
)
const
isInTheDom
=
shadowRoot
!==
null
?
shadowRoot
.
contains
(
this
.
element
)
:
this
.
element
.
ownerDocument
.
documentElement
.
contains
(
this
.
element
)
...
...
@@ -267,7 +278,7 @@ class Tooltip {
}
const
tip
=
this
.
getTipElement
()
const
tipId
=
Util
.
getUID
(
this
.
constructor
.
NAME
)
const
tipId
=
getUID
(
this
.
constructor
.
NAME
)
tip
.
setAttribute
(
'
id
'
,
tipId
)
this
.
element
.
setAttribute
(
'
aria-describedby
'
,
tipId
)
...
...
@@ -323,8 +334,8 @@ class Tooltip {
// only needed because of broken event delegation on iOS
// https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html
if
(
'
ontouchstart
'
in
document
.
documentElement
)
{
Util
.
makeArray
(
document
.
body
.
children
).
forEach
((
element
)
=>
{
EventHandler
.
on
(
element
,
'
mouseover
'
,
Util
.
noop
())
makeArray
(
document
.
body
.
children
).
forEach
((
element
)
=>
{
EventHandler
.
on
(
element
,
'
mouseover
'
,
noop
())
})
}
...
...
@@ -343,9 +354,9 @@ class Tooltip {
}
if
(
this
.
tip
.
classList
.
contains
(
ClassName
.
FADE
))
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
this
.
tip
)
EventHandler
.
one
(
this
.
tip
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
this
.
tip
,
transitionDuration
)
const
transitionDuration
=
getTransitionDurationFromElement
(
this
.
tip
)
EventHandler
.
one
(
this
.
tip
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
this
.
tip
,
transitionDuration
)
}
else
{
complete
()
}
...
...
@@ -381,8 +392,8 @@ class Tooltip {
// If this is a touch-enabled device we remove the extra
// empty mouseover listeners we added for iOS support
if
(
'
ontouchstart
'
in
document
.
documentElement
)
{
Util
.
makeArray
(
document
.
body
.
children
)
.
forEach
((
element
)
=>
EventHandler
.
off
(
element
,
'
mouseover
'
,
Util
.
noop
))
makeArray
(
document
.
body
.
children
)
.
forEach
((
element
)
=>
EventHandler
.
off
(
element
,
'
mouseover
'
,
noop
))
}
this
.
_activeTrigger
[
Trigger
.
CLICK
]
=
false
...
...
@@ -390,9 +401,10 @@ class Tooltip {
this
.
_activeTrigger
[
Trigger
.
HOVER
]
=
false
if
(
this
.
tip
.
classList
.
contains
(
ClassName
.
FADE
))
{
const
transitionDuration
=
Util
.
getTransitionDurationFromElement
(
tip
)
EventHandler
.
one
(
tip
,
Util
.
TRANSITION_END
,
complete
)
Util
.
emulateTransitionEnd
(
tip
,
transitionDuration
)
const
transitionDuration
=
getTransitionDurationFromElement
(
tip
)
EventHandler
.
one
(
tip
,
TRANSITION_END
,
complete
)
emulateTransitionEnd
(
tip
,
transitionDuration
)
}
else
{
complete
()
}
...
...
@@ -507,7 +519,7 @@ class Tooltip {
return
document
.
body
}
if
(
Util
.
isElement
(
this
.
config
.
container
))
{
if
(
isElement
(
this
.
config
.
container
))
{
return
this
.
config
.
container
}
...
...
@@ -705,7 +717,7 @@ class Tooltip {
config
.
content
=
config
.
content
.
toString
()
}
Util
.
typeCheckConfig
(
typeCheckConfig
(
NAME
,
config
,
this
.
constructor
.
DefaultType
...
...
@@ -795,8 +807,9 @@ class Tooltip {
* ------------------------------------------------------------------------
* jQuery
* ------------------------------------------------------------------------
* add .tooltip to jQuery only if jQuery is present
*/
const
$
=
Util
.
jQuery
if
(
typeof
$
!==
'
undefined
'
)
{
const
JQUERY_NO_CONFLICT
=
$
.
fn
[
NAME
]
$
.
fn
[
NAME
]
=
Tooltip
.
_jQueryInterface
...
...
This diff is collapsed.
Click to expand it.
js/src/util.js
deleted
100644 → 0
+
0
-
179
View file @
8affe84c
/**
* --------------------------------------------------------------------------
* Bootstrap (v4.3.1): util.js
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
* --------------------------------------------------------------------------
*/
/**
* ------------------------------------------------------------------------
* Private TransitionEnd Helpers
* ------------------------------------------------------------------------
*/
const
MAX_UID
=
1000000
const
MILLISECONDS_MULTIPLIER
=
1000
// Shoutout AngusCroll (https://goo.gl/pxwQGp)
function
toType
(
obj
)
{
return
{}.
toString
.
call
(
obj
).
match
(
/
\s([
a-z
]
+
)
/i
)[
1
].
toLowerCase
()
}
/**
* --------------------------------------------------------------------------
* Public Util Api
* --------------------------------------------------------------------------
*/
const
Util
=
{
TRANSITION_END
:
'
transitionend
'
,
getUID
(
prefix
)
{
do
{
// eslint-disable-next-line no-bitwise
prefix
+=
~~
(
Math
.
random
()
*
MAX_UID
)
// "~~" acts like a faster Math.floor() here
}
while
(
document
.
getElementById
(
prefix
))
return
prefix
},
getSelectorFromElement
(
element
)
{
let
selector
=
element
.
getAttribute
(
'
data-target
'
)
if
(
!
selector
||
selector
===
'
#
'
)
{
const
hrefAttr
=
element
.
getAttribute
(
'
href
'
)
selector
=
hrefAttr
&&
hrefAttr
!==
'
#
'
?
hrefAttr
.
trim
()
:
''
}
try
{
return
document
.
querySelector
(
selector
)
?
selector
:
null
}
catch
(
err
)
{
return
null
}
},
getTransitionDurationFromElement
(
element
)
{
if
(
!
element
)
{
return
0
}
// Get transition-duration of the element
let
transitionDuration
=
window
.
getComputedStyle
(
element
).
transitionDuration
let
transitionDelay
=
window
.
getComputedStyle
(
element
).
transitionDelay
const
floatTransitionDuration
=
parseFloat
(
transitionDuration
)
const
floatTransitionDelay
=
parseFloat
(
transitionDelay
)
// Return 0 if element or transition duration is not found
if
(
!
floatTransitionDuration
&&
!
floatTransitionDelay
)
{
return
0
}
// If multiple durations are defined, take the first
transitionDuration
=
transitionDuration
.
split
(
'
,
'
)[
0
]
transitionDelay
=
transitionDelay
.
split
(
'
,
'
)[
0
]
return
(
parseFloat
(
transitionDuration
)
+
parseFloat
(
transitionDelay
))
*
MILLISECONDS_MULTIPLIER
},
reflow
(
element
)
{
return
element
.
offsetHeight
},
triggerTransitionEnd
(
element
)
{
element
.
dispatchEvent
(
new
Event
(
Util
.
TRANSITION_END
))
},
isElement
(
obj
)
{
return
(
obj
[
0
]
||
obj
).
nodeType
},
emulateTransitionEnd
(
element
,
duration
)
{
let
called
=
false
const
durationPadding
=
5
const
emulatedDuration
=
duration
+
durationPadding
function
listener
()
{
called
=
true
element
.
removeEventListener
(
Util
.
TRANSITION_END
,
listener
)
}
element
.
addEventListener
(
Util
.
TRANSITION_END
,
listener
)
setTimeout
(()
=>
{
if
(
!
called
)
{
Util
.
triggerTransitionEnd
(
element
)
}
},
emulatedDuration
)
},
typeCheckConfig
(
componentName
,
config
,
configTypes
)
{
for
(
const
property
in
configTypes
)
{
if
(
Object
.
prototype
.
hasOwnProperty
.
call
(
configTypes
,
property
))
{
const
expectedTypes
=
configTypes
[
property
]
const
value
=
config
[
property
]
const
valueType
=
value
&&
Util
.
isElement
(
value
)
?
'
element
'
:
toType
(
value
)
if
(
!
new
RegExp
(
expectedTypes
).
test
(
valueType
))
{
throw
new
Error
(
`
${
componentName
.
toUpperCase
()}
: `
+
`Option "
${
property
}
" provided type "
${
valueType
}
" `
+
`but expected type "
${
expectedTypes
}
".`
)
}
}
}
},
makeArray
(
nodeList
)
{
if
(
!
nodeList
)
{
return
[]
}
return
[].
slice
.
call
(
nodeList
)
},
isVisible
(
element
)
{
if
(
!
element
)
{
return
false
}
if
(
element
.
style
!==
null
&&
element
.
parentNode
!==
null
&&
typeof
element
.
parentNode
.
style
!==
'
undefined
'
)
{
return
element
.
style
.
display
!==
'
none
'
&&
element
.
parentNode
.
style
.
display
!==
'
none
'
&&
element
.
style
.
visibility
!==
'
hidden
'
}
return
false
},
findShadowRoot
(
element
)
{
if
(
!
document
.
documentElement
.
attachShadow
)
{
return
null
}
// Can find the shadow root otherwise it'll return the document
if
(
typeof
element
.
getRootNode
===
'
function
'
)
{
const
root
=
element
.
getRootNode
()
return
root
instanceof
ShadowRoot
?
root
:
null
}
if
(
element
instanceof
ShadowRoot
)
{
return
element
}
// when we don't find a shadow root
if
(
!
element
.
parentNode
)
{
return
null
}
return
Util
.
findShadowRoot
(
element
.
parentNode
)
},
noop
()
{
// eslint-disable-next-line no-empty-function
return
function
()
{}
},
get
jQuery
()
{
return
window
.
jQuery
}
}
export
default
Util
This diff is collapsed.
Click to expand it.
js/src/util/index.js
0 → 100644
+
177
-
0
View file @
8a37045b
/**
* --------------------------------------------------------------------------
* Bootstrap (v4.3.1): util/index.js
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
* --------------------------------------------------------------------------
*/
const
MAX_UID
=
1000000
const
MILLISECONDS_MULTIPLIER
=
1000
const
TRANSITION_END
=
'
transitionend
'
const
jQuery
=
window
.
jQuery
// Shoutout AngusCroll (https://goo.gl/pxwQGp)
const
toType
=
(
obj
)
=>
({}.
toString
.
call
(
obj
).
match
(
/
\s([
a-z
]
+
)
/i
)[
1
].
toLowerCase
())
/**
* --------------------------------------------------------------------------
* Public Util Api
* --------------------------------------------------------------------------
*/
const
getUID
=
(
prefix
)
=>
{
do
{
// eslint-disable-next-line no-bitwise
prefix
+=
~~
(
Math
.
random
()
*
MAX_UID
)
// "~~" acts like a faster Math.floor() here
}
while
(
document
.
getElementById
(
prefix
))
return
prefix
}
const
getSelectorFromElement
=
(
element
)
=>
{
let
selector
=
element
.
getAttribute
(
'
data-target
'
)
if
(
!
selector
||
selector
===
'
#
'
)
{
const
hrefAttr
=
element
.
getAttribute
(
'
href
'
)
selector
=
hrefAttr
&&
hrefAttr
!==
'
#
'
?
hrefAttr
.
trim
()
:
''
}
try
{
return
document
.
querySelector
(
selector
)
?
selector
:
null
}
catch
(
err
)
{
return
null
}
}
const
getTransitionDurationFromElement
=
(
element
)
=>
{
if
(
!
element
)
{
return
0
}
// Get transition-duration of the element
let
{
transitionDuration
,
transitionDelay
}
=
window
.
getComputedStyle
(
element
)
const
floatTransitionDuration
=
parseFloat
(
transitionDuration
)
const
floatTransitionDelay
=
parseFloat
(
transitionDelay
)
// Return 0 if element or transition duration is not found
if
(
!
floatTransitionDuration
&&
!
floatTransitionDelay
)
{
return
0
}
// If multiple durations are defined, take the first
transitionDuration
=
transitionDuration
.
split
(
'
,
'
)[
0
]
transitionDelay
=
transitionDelay
.
split
(
'
,
'
)[
0
]
return
(
parseFloat
(
transitionDuration
)
+
parseFloat
(
transitionDelay
))
*
MILLISECONDS_MULTIPLIER
}
const
triggerTransitionEnd
=
(
element
)
=>
{
element
.
dispatchEvent
(
new
Event
(
TRANSITION_END
))
}
const
isElement
=
(
obj
)
=>
(
obj
[
0
]
||
obj
).
nodeType
const
emulateTransitionEnd
=
(
element
,
duration
)
=>
{
let
called
=
false
const
durationPadding
=
5
const
emulatedDuration
=
duration
+
durationPadding
function
listener
()
{
called
=
true
element
.
removeEventListener
(
TRANSITION_END
,
listener
)
}
element
.
addEventListener
(
TRANSITION_END
,
listener
)
setTimeout
(()
=>
{
if
(
!
called
)
{
triggerTransitionEnd
(
element
)
}
},
emulatedDuration
)
}
const
typeCheckConfig
=
(
componentName
,
config
,
configTypes
)
=>
{
Object
.
keys
(
configTypes
)
.
forEach
((
property
)
=>
{
const
expectedTypes
=
configTypes
[
property
]
const
value
=
config
[
property
]
const
valueType
=
value
&&
isElement
(
value
)
?
'
element
'
:
toType
(
value
)
if
(
!
new
RegExp
(
expectedTypes
).
test
(
valueType
))
{
throw
new
Error
(
`
${
componentName
.
toUpperCase
()}
: `
+
`Option "
${
property
}
" provided type "
${
valueType
}
" `
+
`but expected type "
${
expectedTypes
}
".`
)
}
})
}
const
makeArray
=
(
nodeList
)
=>
{
if
(
!
nodeList
)
{
return
[]
}
return
[].
slice
.
call
(
nodeList
)
}
const
isVisible
=
(
element
)
=>
{
if
(
!
element
)
{
return
false
}
if
(
element
.
style
&&
element
.
parentNode
&&
element
.
parentNode
.
style
)
{
return
element
.
style
.
display
!==
'
none
'
&&
element
.
parentNode
.
style
.
display
!==
'
none
'
&&
element
.
style
.
visibility
!==
'
hidden
'
}
return
false
}
const
findShadowRoot
=
(
element
)
=>
{
if
(
!
document
.
documentElement
.
attachShadow
)
{
return
null
}
// Can find the shadow root otherwise it'll return the document
if
(
typeof
element
.
getRootNode
===
'
function
'
)
{
const
root
=
element
.
getRootNode
()
return
root
instanceof
ShadowRoot
?
root
:
null
}
if
(
element
instanceof
ShadowRoot
)
{
return
element
}
// when we don't find a shadow root
if
(
!
element
.
parentNode
)
{
return
null
}
return
findShadowRoot
(
element
.
parentNode
)
}
// eslint-disable-next-line no-empty-function
const
noop
=
()
=>
function
()
{}
const
reflow
=
(
element
)
=>
element
.
offsetHeight
export
{
jQuery
,
TRANSITION_END
,
getUID
,
getSelectorFromElement
,
getTransitionDurationFromElement
,
triggerTransitionEnd
,
isElement
,
emulateTransitionEnd
,
typeCheckConfig
,
makeArray
,
isVisible
,
findShadowRoot
,
noop
,
reflow
}
This diff is collapsed.
Click to expand it.
js/src/
tools
/sanitizer.js
→
js/src/
util
/sanitizer.js
+
43
-
41
View file @
8a37045b
/**
* --------------------------------------------------------------------------
* Bootstrap (v4.3.1):
tools
/sanitizer.js
* Bootstrap (v4.3.1):
util
/sanitizer.js
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
* --------------------------------------------------------------------------
*/
import
Util
from
'
../util
'
import
{
makeArray
}
from
'
./index
'
const
uriAttrs
=
[
'
background
'
,
...
...
@@ -20,40 +22,6 @@ const uriAttrs = [
const
ARIA_ATTRIBUTE_PATTERN
=
/^aria-
[\w
-
]
*$/i
export
const
DefaultWhitelist
=
{
// Global attributes allowed on any supplied element below.
'
*
'
:
[
'
class
'
,
'
dir
'
,
'
id
'
,
'
lang
'
,
'
role
'
,
ARIA_ATTRIBUTE_PATTERN
],
a
:
[
'
target
'
,
'
href
'
,
'
title
'
,
'
rel
'
],
area
:
[],
b
:
[],
br
:
[],
col
:
[],
code
:
[],
div
:
[],
em
:
[],
hr
:
[],
h1
:
[],
h2
:
[],
h3
:
[],
h4
:
[],
h5
:
[],
h6
:
[],
i
:
[],
img
:
[
'
src
'
,
'
alt
'
,
'
title
'
,
'
width
'
,
'
height
'
],
li
:
[],
ol
:
[],
p
:
[],
pre
:
[],
s
:
[],
small
:
[],
span
:
[],
sub
:
[],
sup
:
[],
strong
:
[],
u
:
[],
ul
:
[]
}
/**
* A pattern that recognizes a commonly useful subset of URLs that are safe.
*
...
...
@@ -68,7 +36,7 @@ const SAFE_URL_PATTERN = /^(?:(?:https?|mailto|ftp|tel|file):|[^&:/?#]*(?:[/?#]|
*/
const
DATA_URL_PATTERN
=
/^data:
(?:
image
\/(?:
bmp|gif|jpeg|jpg|png|tiff|webp
)
|video
\/(?:
mpeg|mp4|ogg|webm
)
|audio
\/(?:
mp3|oga|ogg|opus
))
;base64,
[
a-z0-9+
/]
+=*$/i
function
allowedAttribute
(
attr
,
allowedAttributeList
)
{
const
allowedAttribute
=
(
attr
,
allowedAttributeList
)
=>
{
const
attrName
=
attr
.
nodeName
.
toLowerCase
()
if
(
allowedAttributeList
.
indexOf
(
attrName
)
!==
-
1
)
{
...
...
@@ -91,8 +59,42 @@ function allowedAttribute(attr, allowedAttributeList) {
return
false
}
export
const
DefaultWhitelist
=
{
// Global attributes allowed on any supplied element below.
'
*
'
:
[
'
class
'
,
'
dir
'
,
'
id
'
,
'
lang
'
,
'
role
'
,
ARIA_ATTRIBUTE_PATTERN
],
a
:
[
'
target
'
,
'
href
'
,
'
title
'
,
'
rel
'
],
area
:
[],
b
:
[],
br
:
[],
col
:
[],
code
:
[],
div
:
[],
em
:
[],
hr
:
[],
h1
:
[],
h2
:
[],
h3
:
[],
h4
:
[],
h5
:
[],
h6
:
[],
i
:
[],
img
:
[
'
src
'
,
'
alt
'
,
'
title
'
,
'
width
'
,
'
height
'
],
li
:
[],
ol
:
[],
p
:
[],
pre
:
[],
s
:
[],
small
:
[],
span
:
[],
sub
:
[],
sup
:
[],
strong
:
[],
u
:
[],
ul
:
[]
}
export
function
sanitizeHtml
(
unsafeHtml
,
whiteList
,
sanitizeFn
)
{
if
(
unsafeHtml
.
length
===
0
)
{
if
(
!
unsafeHtml
.
length
)
{
return
unsafeHtml
}
...
...
@@ -103,19 +105,19 @@ export function sanitizeHtml(unsafeHtml, whiteList, sanitizeFn) {
const
domParser
=
new
window
.
DOMParser
()
const
createdDocument
=
domParser
.
parseFromString
(
unsafeHtml
,
'
text/html
'
)
const
whitelistKeys
=
Object
.
keys
(
whiteList
)
const
elements
=
Util
.
makeArray
(
createdDocument
.
body
.
querySelectorAll
(
'
*
'
))
const
elements
=
makeArray
(
createdDocument
.
body
.
querySelectorAll
(
'
*
'
))
for
(
let
i
=
0
,
len
=
elements
.
length
;
i
<
len
;
i
++
)
{
const
el
=
elements
[
i
]
const
elName
=
el
.
nodeName
.
toLowerCase
()
if
(
whitelistKeys
.
indexOf
(
el
.
nodeName
.
toLowerCase
()
)
===
-
1
)
{
if
(
whitelistKeys
.
indexOf
(
el
Name
)
===
-
1
)
{
el
.
parentNode
.
removeChild
(
el
)
continue
}
const
attributeList
=
Util
.
makeArray
(
el
.
attributes
)
const
attributeList
=
makeArray
(
el
.
attributes
)
const
whitelistedAttributes
=
[].
concat
(
whiteList
[
'
*
'
]
||
[],
whiteList
[
elName
]
||
[])
attributeList
.
forEach
((
attr
)
=>
{
...
...
This diff is collapsed.
Click to expand it.
Prev
1
2
Next
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment
Menu
Explore
Projects
Groups
Snippets