first
This commit is contained in:
34
node_modules/vue-router/src/composables/globals.js
generated
vendored
Normal file
34
node_modules/vue-router/src/composables/globals.js
generated
vendored
Normal file
@ -0,0 +1,34 @@
|
||||
import {
|
||||
getCurrentInstance,
|
||||
shallowReactive,
|
||||
effectScope
|
||||
} from 'vue'
|
||||
import { throwNoCurrentInstance } from './utils'
|
||||
|
||||
export function useRouter () {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
throwNoCurrentInstance('useRouter')
|
||||
}
|
||||
|
||||
return getCurrentInstance().proxy.$root.$router
|
||||
}
|
||||
|
||||
export function useRoute () {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
throwNoCurrentInstance('useRoute')
|
||||
}
|
||||
|
||||
const root = getCurrentInstance().proxy.$root
|
||||
if (!root._$route) {
|
||||
const route = effectScope(true).run(() =>
|
||||
shallowReactive(Object.assign({}, root.$router.currentRoute))
|
||||
)
|
||||
root._$route = route
|
||||
|
||||
root.$router.afterEach(to => {
|
||||
Object.assign(route, to)
|
||||
})
|
||||
}
|
||||
|
||||
return root._$route
|
||||
}
|
68
node_modules/vue-router/src/composables/guards.js
generated
vendored
Normal file
68
node_modules/vue-router/src/composables/guards.js
generated
vendored
Normal file
@ -0,0 +1,68 @@
|
||||
import { getCurrentInstance, onUnmounted } from 'vue'
|
||||
import { throwNoCurrentInstance } from './utils'
|
||||
import { useRouter } from './globals'
|
||||
|
||||
export function onBeforeRouteUpdate (guard) {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
throwNoCurrentInstance('onBeforeRouteUpdate')
|
||||
}
|
||||
|
||||
return useFilteredGuard(guard, isUpdateNavigation)
|
||||
}
|
||||
function isUpdateNavigation (to, from, depth) {
|
||||
const toMatched = to.matched
|
||||
const fromMatched = from.matched
|
||||
return (
|
||||
toMatched.length >= depth &&
|
||||
toMatched
|
||||
.slice(0, depth + 1)
|
||||
.every((record, i) => record === fromMatched[i])
|
||||
)
|
||||
}
|
||||
|
||||
function isLeaveNavigation (to, from, depth) {
|
||||
const toMatched = to.matched
|
||||
const fromMatched = from.matched
|
||||
return toMatched.length < depth || toMatched[depth] !== fromMatched[depth]
|
||||
}
|
||||
|
||||
export function onBeforeRouteLeave (guard) {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
throwNoCurrentInstance('onBeforeRouteLeave')
|
||||
}
|
||||
|
||||
return useFilteredGuard(guard, isLeaveNavigation)
|
||||
}
|
||||
|
||||
const noop = () => {}
|
||||
function useFilteredGuard (guard, fn) {
|
||||
const instance = getCurrentInstance()
|
||||
const router = useRouter()
|
||||
|
||||
let target = instance.proxy
|
||||
// find the nearest RouterView to know the depth
|
||||
while (
|
||||
target &&
|
||||
target.$vnode &&
|
||||
target.$vnode.data &&
|
||||
target.$vnode.data.routerViewDepth == null
|
||||
) {
|
||||
target = target.$parent
|
||||
}
|
||||
|
||||
const depth =
|
||||
target && target.$vnode && target.$vnode.data
|
||||
? target.$vnode.data.routerViewDepth
|
||||
: null
|
||||
|
||||
if (depth != null) {
|
||||
const removeGuard = router.beforeEach((to, from, next) => {
|
||||
return fn(to, from, depth) ? guard(to, from, next) : next()
|
||||
})
|
||||
|
||||
onUnmounted(removeGuard)
|
||||
return removeGuard
|
||||
}
|
||||
|
||||
return noop
|
||||
}
|
3
node_modules/vue-router/src/composables/index.js
generated
vendored
Normal file
3
node_modules/vue-router/src/composables/index.js
generated
vendored
Normal file
@ -0,0 +1,3 @@
|
||||
export * from './guards'
|
||||
export * from './globals'
|
||||
export * from './useLink'
|
113
node_modules/vue-router/src/composables/useLink.js
generated
vendored
Normal file
113
node_modules/vue-router/src/composables/useLink.js
generated
vendored
Normal file
@ -0,0 +1,113 @@
|
||||
import { computed, unref } from 'vue'
|
||||
import { guardEvent } from '../components/link'
|
||||
import { throwNoCurrentInstance } from './utils'
|
||||
import { useRouter, useRoute } from './globals'
|
||||
|
||||
function includesParams (outer, inner) {
|
||||
for (const key in inner) {
|
||||
const innerValue = inner[key]
|
||||
const outerValue = outer[key]
|
||||
if (typeof innerValue === 'string') {
|
||||
if (innerValue !== outerValue) return false
|
||||
} else {
|
||||
if (
|
||||
!Array.isArray(outerValue) ||
|
||||
outerValue.length !== innerValue.length ||
|
||||
innerValue.some((value, i) => value !== outerValue[i])
|
||||
) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
// helpers from vue router 4
|
||||
|
||||
function isSameRouteLocationParamsValue (a, b) {
|
||||
return Array.isArray(a)
|
||||
? isEquivalentArray(a, b)
|
||||
: Array.isArray(b)
|
||||
? isEquivalentArray(b, a)
|
||||
: a === b
|
||||
}
|
||||
|
||||
function isEquivalentArray (a, b) {
|
||||
return Array.isArray(b)
|
||||
? a.length === b.length && a.every((value, i) => value === b[i])
|
||||
: a.length === 1 && a[0] === b
|
||||
}
|
||||
|
||||
export function isSameRouteLocationParams (a, b) {
|
||||
if (Object.keys(a).length !== Object.keys(b).length) return false
|
||||
|
||||
for (const key in a) {
|
||||
if (!isSameRouteLocationParamsValue(a[key], b[key])) return false
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
export function useLink (props) {
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
throwNoCurrentInstance('useLink')
|
||||
}
|
||||
|
||||
const router = useRouter()
|
||||
const currentRoute = useRoute()
|
||||
|
||||
const resolvedRoute = computed(() => router.resolve(unref(props.to), currentRoute))
|
||||
|
||||
const activeRecordIndex = computed(() => {
|
||||
const route = resolvedRoute.value.route
|
||||
const { matched } = route
|
||||
const { length } = matched
|
||||
const routeMatched = matched[length - 1]
|
||||
const currentMatched = currentRoute.matched
|
||||
if (!routeMatched || !currentMatched.length) return -1
|
||||
const index = currentMatched.indexOf(routeMatched)
|
||||
if (index > -1) return index
|
||||
// possible parent record
|
||||
const parentRecord = currentMatched[currentMatched.length - 2]
|
||||
|
||||
return (
|
||||
// we are dealing with nested routes
|
||||
length > 1 &&
|
||||
// if the parent and matched route have the same path, this link is
|
||||
// referring to the empty child. Or we currently are on a different
|
||||
// child of the same parent
|
||||
parentRecord && parentRecord === routeMatched.parent
|
||||
)
|
||||
})
|
||||
|
||||
const isActive = computed(
|
||||
() =>
|
||||
activeRecordIndex.value > -1 &&
|
||||
includesParams(currentRoute.params, resolvedRoute.value.route.params)
|
||||
)
|
||||
const isExactActive = computed(
|
||||
() =>
|
||||
activeRecordIndex.value > -1 &&
|
||||
activeRecordIndex.value === currentRoute.matched.length - 1 &&
|
||||
isSameRouteLocationParams(currentRoute.params, resolvedRoute.value.route.params)
|
||||
)
|
||||
|
||||
const navigate = e => {
|
||||
const href = resolvedRoute.value.route
|
||||
if (guardEvent(e)) {
|
||||
return props.replace
|
||||
? router.replace(href)
|
||||
: router.push(href)
|
||||
}
|
||||
return Promise.resolve()
|
||||
}
|
||||
|
||||
return {
|
||||
href: computed(() => resolvedRoute.value.href),
|
||||
route: computed(() => resolvedRoute.value.route),
|
||||
isExactActive,
|
||||
isActive,
|
||||
navigate
|
||||
}
|
||||
}
|
11
node_modules/vue-router/src/composables/utils.js
generated
vendored
Normal file
11
node_modules/vue-router/src/composables/utils.js
generated
vendored
Normal file
@ -0,0 +1,11 @@
|
||||
import { getCurrentInstance } from 'vue'
|
||||
|
||||
// dev only warn if no current instance
|
||||
|
||||
export function throwNoCurrentInstance (method) {
|
||||
if (!getCurrentInstance()) {
|
||||
throw new Error(
|
||||
`[vue-router]: Missing current instance. ${method}() must be called inside <script setup> or setup().`
|
||||
)
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user