Skip to content

Commit

Permalink
Merge pull request #2704 from nextcloud/pr/quentinguidee/2572
Browse files Browse the repository at this point in the history
Put the children of AppNavigationItem outside of the main item
  • Loading branch information
GretaD authored May 25, 2022
2 parents f8be409 + eca26a9 commit f8b6231
Showing 1 changed file with 112 additions and 102 deletions.
214 changes: 112 additions & 102 deletions src/components/AppNavigationItem/AppNavigationItem.vue
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ prevent the user from collapsing the items.
<AppNavigationItem title="Item with children" :allowCollapse="true" :open="true">
<template>
<AppNavigationItem title="AppNavigationItemChild1" />
<AppNavigationItem class="active" title="AppNavigationItemChild2" />
<AppNavigationItem title="AppNavigationItemChild2" />
<AppNavigationItem title="AppNavigationItemChild3" />
<AppNavigationItem title="AppNavigationItemChild4" />
</template>
Expand Down Expand Up @@ -111,109 +111,111 @@ Just set the `pinned` prop.
</docs>

<template>
<!-- Navigation item, can be either an <li> or a <router-link> depending on the props -->
<nav-element v-bind="navElement"
<li class="app-navigation-entry-wrapper"
:class="{
'app-navigation-entry--no-icon': !isIconShown,
'app-navigation-entry--opened': opened,
'app-navigation-entry--pinned': pinned,
'app-navigation-entry--editing' : editingActive,
'app-navigation-entry--deleted': undo,
'app-navigation-entry--collapsible': collapsible,
'active': isActive
}"
class="app-navigation-entry">
<!-- Icon and title -->
<a v-if="!undo"
class="app-navigation-entry-link"
:aria-description="ariaDescription"
href="#"
@click="onClick">

<!-- icon if not collapsible -->
<!-- never show the icon over the collapsible if mobile -->
<div :class="{ 'icon-loading-small': loading, [icon]: icon && isIconShown }"
class="app-navigation-entry-icon">
<slot v-show="!loading && isIconShown" name="icon" />
}">
<nav-element v-bind="navElement"
:class="{
'app-navigation-entry--no-icon': !isIconShown,
'app-navigation-entry--editing': editingActive,
'app-navigation-entry--deleted': undo,
'active': isActive,
}"
class="app-navigation-entry">
<!-- Icon and title -->
<a v-if="!undo"
class="app-navigation-entry-link"
:aria-description="ariaDescription"
href="#"
@click="onClick">

<!-- icon if not collapsible -->
<!-- never show the icon over the collapsible if mobile -->
<div :class="{ 'icon-loading-small': loading, [icon]: icon && isIconShown }"
class="app-navigation-entry-icon">
<slot v-show="!loading && isIconShown" name="icon" />
</div>
<span v-if="!editingActive" class="app-navigation-entry__title" :title="title">
{{ title }}
</span>
<div v-if="editingActive" class="editingContainer">
<InputConfirmCancel ref="editingInput"
v-model="editingValue"
:placeholder="editPlaceholder !== '' ? editPlaceholder : title"
@cancel="cancelEditing"
@confirm="handleEditingDone" />
</div>
</a>

<AppNavigationIconCollapsible v-if="collapsible" :open="opened" @click.prevent.stop="toggleCollapse" />
<!-- undo entry -->
<div v-if="undo" class="app-navigation-entry__deleted">
<div class="app-navigation-entry__deleted-description">
{{ title }}
</div>
</div>
<span v-if="!editingActive" class="app-navigation-entry__title" :title="title">
{{ title }}
</span>
<div v-if="editingActive" class="editingContainer">
<InputConfirmCancel ref="editingInput"
v-model="editingValue"
:placeholder="editPlaceholder !== '' ? editPlaceholder : title"
@cancel="cancelEditing"
@confirm="handleEditingDone" />
</div>
</a>

<AppNavigationIconCollapsible v-if="collapsible" :open="opened" @click.prevent.stop="toggleCollapse" />
<!-- undo entry -->
<div v-if="undo" class="app-navigation-entry__deleted">
<div class="app-navigation-entry__deleted-description">
{{ title }}
</div>
</div>

<!-- Counter and Actions -->
<div v-if="hasUtils && !editingActive" class="app-navigation-entry__utils">
<div v-if="$slots.counter"
class="app-navigation-entry__counter-wrapper">
<slot name="counter" />
</div>
<Actions menu-align="right"
:placement="menuPlacement"
:open="menuOpen"
:force-menu="forceMenu"
:default-icon="menuIcon"
@update:open="onMenuToggle">
<template #icon>
<!-- @slot Slot for the custom menu icon -->
<slot name="menu-icon" />
</template>
<ActionButton v-if="editable && !editingActive"
:aria-label="editButtonAriaLabel"
@click="handleEdit">
<template #icon>
<Pencil :size="20" decorative />
</template>
{{ editLabel }}
</ActionButton>
<ActionButton v-if="undo"
:aria-label="undoButtonAriaLabel"
@click="handleUndo">
<!-- Counter and Actions -->
<div v-if="hasUtils && !editingActive" class="app-navigation-entry__utils">
<div v-if="$slots.counter"
class="app-navigation-entry__counter-wrapper">
<slot name="counter" />
</div>
<Actions menu-align="right"
:placement="menuPlacement"
:open="menuOpen"
:force-menu="forceMenu"
:default-icon="menuIcon"
@update:open="onMenuToggle">
<template #icon>
<Undo :size="20" decorative />
<!-- @slot Slot for the custom menu icon -->
<slot name="menu-icon" />
</template>
</ActionButton>
<slot name="actions" />
</Actions>
</div>
<ActionButton v-if="editable && !editingActive"
:aria-label="editButtonAriaLabel"
@click="handleEdit">
<template #icon>
<Pencil :size="20" decorative />
</template>
{{ editLabel }}
</ActionButton>
<ActionButton v-if="undo"
:aria-label="undoButtonAriaLabel"
@click="handleUndo">
<template #icon>
<Undo :size="20" decorative />
</template>
</ActionButton>
<slot name="actions" />
</Actions>
</div>

<!-- Anything (virtual) that should be mounted in the component, like a related modal -->
<slot name="extra" />
</nav-element>
<!-- Children elements -->
<ul v-if="canHaveChildren && hasChildren" class="app-navigation-entry__children">
<slot />
</ul>

<!-- Anything (virtual) that should be mounted in the component, like a related modal -->
<slot name="extra" />
</nav-element>
</li>
</template>

<script>
import AppNavigationIconCollapsible from './AppNavigationIconCollapsible.vue'
import InputConfirmCancel from './InputConfirmCancel.vue'
import { directive as ClickOutside } from 'v-click-outside'
import Actions from '../Actions/index.js'
import ActionButton from '../ActionButton/index.js'
import AppNavigationIconCollapsible from './AppNavigationIconCollapsible.vue'
import isMobile from '../../mixins/isMobile/index.js'
import InputConfirmCancel from './InputConfirmCancel.vue'
import { t } from '../../l10n.js'
import Pencil from 'vue-material-design-icons/Pencil'
import Undo from 'vue-material-design-icons/Undo'
import { directive as ClickOutside } from 'v-click-outside'
export default {
name: 'AppNavigationItem',
Expand Down Expand Up @@ -400,18 +402,17 @@ export default {
}
},
// This is used to decide which outer element type to use
// li or router-link
navElement() {
if (this.to) {
return {
is: 'router-link',
tag: 'li',
tag: 'div',
to: this.to,
exact: this.exact,
}
}
return {
is: 'li',
is: 'div',
}
},
isActive() {
Expand Down Expand Up @@ -495,6 +496,20 @@ export default {
min-height: $clickable-area;
padding-right: 8px;
&-wrapper {
position: relative;
display: flex;
flex-shrink: 0;
flex-wrap: wrap;
box-sizing: border-box;
width: 100%;
&.app-navigation-entry--collapsible:not(.app-navigation-entry--opened) > ul {
// NO ANIMATE because if not really hidden, we can still tab through it
display: none;
}
}
// When .active class is applied, change color background of link and utils. The
// !important prevents the focus state to override the active state.
&.active {
Expand All @@ -513,12 +528,9 @@ export default {
}
/* hide deletion/collapse of subitems */
&.app-navigation-entry--deleted,
&.app-navigation-entry--collapsible:not(.app-navigation-entry--opened) {
> ul {
// NO ANIMATE because if not really hidden, we can still tab through it
display: none;
}
&.app-navigation-entry--deleted > ul {
// NO ANIMATE because if not really hidden, we can still tab through it
display: none;
}
&:not(.app-navigation-entry--editing) {
Expand Down Expand Up @@ -565,21 +577,19 @@ export default {
margin: auto;
}
}
}
/* Second level nesting for lists */
.app-navigation-entry__children {
position: relative;
display: flex;
flex: 0 1 auto;
flex-direction: column;
width: 100%;
.app-navigation-entry__children {
position: relative;
display: flex;
flex: 0 1 auto;
flex-direction: column;
width: 100%;
.app-navigation-entry {
display: inline-flex;
flex-wrap: wrap;
padding-left: $icon-size;
padding-right: 0;
}
.app-navigation-entry {
display: inline-flex;
flex-wrap: wrap;
padding-left: $icon-size;
}
}
Expand Down

0 comments on commit f8b6231

Please sign in to comment.