diff --git a/packages/vuetify/src/components/VDataTable/VDataTable.sass b/packages/vuetify/src/components/VDataTable/VDataTable.sass new file mode 100644 index 00000000000..bdf23ec43ef --- /dev/null +++ b/packages/vuetify/src/components/VDataTable/VDataTable.sass @@ -0,0 +1,293 @@ +// Imports +@import '../../styles/styles.sass' +@import './_variables.scss' +@import './_mixins.sass' + +// Theme +.v-data-table.theme--light + @include data-table-theme($material-light) +.v-data-table.theme--dark + @include data-table-theme($material-dark) + +.v-data-table-virtual + position: relative + padding-right: 17px + + &__scroller + position: absolute + top: 0 + right: 0 + height: 100% + width: 17px + overflow-x: hidden + + &__wrapper + width: 100% + height: 100% + overflow-x: auto + overflow-y: hidden + +.v-table-regular + &__wrapper + overflow-y: auto + +.v-data-table + table + width: 100% + max-width: 100% + border-collapse: collapse + // border-spacing: 0 + + colgroup + .divider + border-right: 1px solid lightgrey + + &--dense + td + height: 24px + th + height: 32px + + &--fixed + .v-data-table__wrapper + overflow-y: auto + + thead + th + position: sticky + top: 0 + z-index: 10 + + .v-table__header, .v-data-footer + margin-right: 17px + + &--mobile + tr, td, th + display: block + + td, th + padding: 14px + + &__progress + height: auto !important + + th + height: auto !important + border: none !important + padding: 0 + + .v-progress-linear + margin: 0 + +td, th + padding: 0 16px + +.v-row + &__header + font-weight: 600 + + &__value + text-align: right + +.v-simple-checkbox + align-self: center + position: relative + user-select: none + cursor: pointer + + &--disabled + cursor: default + +.v-data-table-header + &--mobile + th + height: initial + + > div + display: flex + + .v-simple-checkbox + margin-right: 24px + + .v-select + margin-top: 0 + + th + font-weight: 500 + font-size: 12px + transition: .3s map-get($transition, 'swing') + white-space: nowrap + user-select: none + position: relative + + .resize-handle + z-index: 10 + position: absolute + right: -4px + top: 0 + height: 100% + width: 8px + cursor: ew-resize + + &:hover + background: grey + + .sortable + pointer-events: auto + cursor: pointer + outline: 0 + + i + font-size: 18px + display: inline-block + opacity: 0 + transition: .3s map-get($transition, 'swing') + + &:focus, + &:hover + i + opacity: .6 + + &.active + transform: none + + i + opacity: 1 + + &.desc + i + transform: rotate(-180deg) + +.v-data-table__body + .v-row + transition: background $primary-transition + will-change: background + + .v-cell + font-weight: 400 + font-size: 13px + +td, th + > .v-input + margin-top: 0 + padding-top: 0 + + .v-input--selection-controls__input + margin-right: 0 + +td + height: 48px + +th + height: 48px + + .badge + display: inline-flex + justify-content: center + border: 0px + border-radius: 50% + background-color: lightgrey // TODO: theme + min-width: 16px + min-height: 16px + height: 16px + width: 16px + color: white // TODO: theme + font-size: 0.8rem + +th + font-weight: bold + +tr > th + white-space: normal + +.v-row, .v-row-expandable + &:not(:last-child) + .v-cell + border-bottom: 1px solid rgba(0,0,0,.12) // TODO: theme + +.v-cell, .v-head + word-break: break-word + overflow: hidden + text-overflow: ellipsis + +/** Actions */ +.v-data-footer + display: flex + flex-wrap: wrap + justify-content: flex-end + align-items: center + font-size: 12px + + .v-btn + color: inherit + + &:first-of-type + margin-right: 7px + + &:last-of-type + margin-left: 7px + + &__range-controls + display: flex + align-items: center + min-height: 48px + + &__pagination + display: block + text-align: center + margin: 0 32px 0 24px + + &__select + display: flex + align-items: center + justify-content: flex-end + margin-right: 14px + white-space: nowrap + + .v-select + flex: 0 1 0 + margin: 13px 0 13px 34px + padding: 0 + position: initial + + .v-select__selections + flex-wrap: nowrap + + .v-select__selection--comma + font-size: 12px + +.v-row-expandable + &__wrapper + transition: all 0.3s ease-out + +.v-data-table__expand + &-row + border: none !important + + &-col + padding: 0 !important + height: 0px !important + + &--expanded + border-bottom: 1px solid rgba(0,0,0,0.12) // TODO: theme + + &-content + transition: height $primary-transition + + > .card + border-radius: 0 + box-shadow: none + +.v-row-group + &__header, &__summary + background: lightgrey + + td + height: 35px + +.expand__icon + user-select: none + cursor: pointer + + &--active + transform: rotate(-180deg) diff --git a/packages/vuetify/src/components/VDataTable/VDataTable.ts b/packages/vuetify/src/components/VDataTable/VDataTable.ts index 67ce3498ad6..a7926cc5ab5 100644 --- a/packages/vuetify/src/components/VDataTable/VDataTable.ts +++ b/packages/vuetify/src/components/VDataTable/VDataTable.ts @@ -1,4 +1,4 @@ -import '../../stylus/components/_data-table.styl' +import './VDataTable.sass' // Types import { VNode, VNodeChildrenArrayContents, VNodeChildren } from 'vue' @@ -357,7 +357,7 @@ export default VDataIterator.extend({ }) }, genBody (props: DataProps): VNode | string | VNodeChildren { - if (this.$scopedSlots.body) return this.$scopedSlots.body!(this.createSlotProps(props)) + if (this.$scopedSlots.body) return this.$scopedSlots.body!(props) return this.$createElement('tbody', [ this.genSlots('body.prepend', props), diff --git a/packages/vuetify/src/components/VDataTable/_mixins.sass b/packages/vuetify/src/components/VDataTable/_mixins.sass new file mode 100644 index 00000000000..880d1c8f71a --- /dev/null +++ b/packages/vuetify/src/components/VDataTable/_mixins.sass @@ -0,0 +1,56 @@ +@mixin data-table-theme($material) + background-color: map-get($material, 'cards') + color: map-deep-get($material, 'text', 'primary') + + &--fixed + thead th + background: white + border-bottom: 0px !important + box-shadow: inset 0 -1px 0 rgba(map-get($material, 'fg-color'), map-get($material, 'divider-percent')) + + thead + tr + + &:last-child th + border-bottom: 1px solid rgba(map-get($material, 'fg-color'), map-get($material, 'divider-percent')) + + th + // box-shadow: inset 0 -1px 0 rgba(map-get($material, 'fg-color'), map-get($material, 'divider-percent')) + color: rgba(map-get($material, 'text-color'), map-get($material, 'secondary-text-percent')) + + &.sortable + i + color: rgba(map-get($material, 'fg-color'), map-get($material, 'disabledORhints-text-percent')) + + &:hover + color: rgba(map-get($material, 'fg-color'), map-get($material, 'primary-text-percent')) + + &.active + color: rgba(map-get($material, 'fg-color'), map-get($material, 'primary-text-percent')) + + i + color: rgba(map-get($material, 'fg-color'), map-get($material, 'primary-text-percent')) + + tbody + tr + &:not(:last-child) + border-bottom: 1px solid rgba(map-get($material, 'fg-color'), map-get($material, 'divider-percent')) + + &.active + background: map-deep-get($material, 'table', 'active') + + &:hover:not(.datatable__expand-row) + background: map-deep-get($material, 'table', 'hover') + + &.expanded + border-bottom: 0 + + &.expanded__row + background: map-deep-get($material, 'table', 'active') + + &.expanded__content + box-shadow: inset 0px 4px 8px -5px rgba(50, 50, 50, 0.75), inset 0px -4px 8px -5px rgba(50, 50, 50, 0.75) + + .v-table__footer + .v-row + border-top: 1px solid rgba(map-get($material, 'fg-color'), map-get($material, 'divider-percent')) diff --git a/packages/vuetify/src/components/VDataTable/_variables.scss b/packages/vuetify/src/components/VDataTable/_variables.scss new file mode 100644 index 00000000000..e69de29bb2d diff --git a/packages/vuetify/src/stylus/components/_tables.styl b/packages/vuetify/src/stylus/components/_tables.styl deleted file mode 100644 index d03a982a254..00000000000 --- a/packages/vuetify/src/stylus/components/_tables.styl +++ /dev/null @@ -1,100 +0,0 @@ -@import '../bootstrap' -@import '../theme' - -/* Theme */ -v-table($material) - background-color: $material.cards - color: $material.text.primary - - thead - tr - &:first-child - border-bottom: 1px solid rgba($material.fg-color, $material.divider-percent) - - th - color: rgba($material.text-color, $material.secondary-text-percent) - - tbody - tr - &:not(:last-child) - border-bottom: 1px solid rgba($material.fg-color, $material.divider-percent) - - &[active] - background: $material.table.active - - &:hover:not(.v-datatable__expand-row) - background: $material.table.hover - - tfoot - tr - border-top: 1px solid rgba($material.fg-color, $material.divider-percent) - -theme(v-table, "v-table") - -.v-table - &__overflow - width: 100% - overflow-x: auto - overflow-y: hidden - -table.v-table - border-radius: 2px - border-collapse: collapse - border-spacing: 0 - width: 100% - max-width: 100% - - thead, tbody - td, th - &:not(:nth-child(1)), &:first-child - padding: 0 24px - - thead - tr - height: 56px - - th - font-weight: 500 - font-size: 12px - transition: .3s $transition.swing - white-space: nowrap - user-select: none - - &.sortable - pointer-events: auto - - > div - width: 100% - - tbody - tr - transition: background $primary-transition - will-change: background - - td, th - height: 48px - - td - font-weight: 400 - font-size: 13px - - .input-group--selection-controls - padding: 0 - - .input-group__details - display: none - - &.checkbox - .v-icon - left: 50% - transform: translateX(-50%) - - .input-group--selection-controls__ripple - left: 50% - transform: translate(-50%, -50%) - - tfoot - tr - height: 48px - td - padding: 0 24px