All files / web/src/components/shared PageLayout.vue

0% Statements 0/18
100% Branches 1/1
100% Functions 1/1
0% Lines 0/18

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103                                                                                                                                                                                                             
<script setup lang="ts">
import { computed } from 'vue'
 
interface Props {
  variant?: 'default' | 'fullheight' | 'split'
  noPadding?: boolean
  noHeader?: boolean
}
 
const props = withDefaults(defineProps<Props>(), {
  variant: 'default',
  noPadding: false,
  noHeader: false
})
 
const layoutClasses = computed(() => ({
  'page-layout': true,
  [`page-layout--${props.variant}`]: true,
  'page-layout--no-padding': props.noPadding
}))
</script>
 
<template>
  <div :class="layoutClasses">
    <header v-if="!noHeader && $slots.header" class="page-layout__header">
      <slot name="header" />
    </header>
 
    <main class="page-layout__content">
      <slot />
    </main>
 
    <footer v-if="$slots.footer" class="page-layout__footer">
      <slot name="footer" />
    </footer>
  </div>
</template>
 
<style lang="scss" scoped>
.page-layout {
  display: flex;
  flex-direction: column;
  height: 100%;
  background: var(--rf-color-bg-page);
 
  &--default {
    .page-layout__content {
      flex: 1;
      padding: var(--rf-page-padding, var(--rf-spacing-xl));
      overflow-y: auto;
    }
  }
 
  &--fullheight {
    .page-layout__content {
      flex: 1;
      min-height: 0;
      display: flex;
      flex-direction: column;
    }
  }
 
  &--split {
    overflow: hidden;
 
    .page-layout__content {
      flex: 1;
      min-height: 0;
      display: flex;
      flex-direction: column;
      overflow: hidden;
    }
  }
 
  &--no-padding {
    .page-layout__content {
      padding: 0;
    }
  }
 
  &__header {
    flex-shrink: 0;
    background: var(--rf-color-bg-container);
    border-bottom: 1px solid var(--rf-color-border-lighter);
  }
 
  &__footer {
    flex-shrink: 0;
    background: var(--rf-color-bg-container);
    border-top: 1px solid var(--rf-color-border-lighter);
    padding: var(--rf-spacing-lg) var(--rf-spacing-xl);
  }
}
 
html.dark {
  .page-layout {
    &__header,
    &__footer {
      background: var(--rf-color-bg-container);
    }
  }
}
</style>