<div class="col-12">
<h3 class="col-md-12"> Graph</h3>
<h4 class="col-md-12">Works dynamically with v-for tags in each section</h4>
<div class="chart col-md-12">
<div class="chart-y">
<span class="chart-y__count"><span>5</span></span>
<span class="chart-y__count"><span>4</span></span>
<span class="chart-y__count"><span>3</span></span>
<span class="chart-y__count"><span>2</span></span>
<span class="chart-y__count"><span>1</span></span>
<span class="chart-y__count"><span>0</span></span>
</div>
<div class="chart-x">
<div class="chart-x__value" :data-chart="1" @mouseover="graphHover($event)"
@mouseleave="graphHover($event)" @mousemove="mouseMove($event)">
<span class="chart-x__value-graph" :class="{'is-unloaded': animation === 1}" :style="{height: ((1 / 5 ) * 100) + '%' }"></span>
<span class="tooltip">
<span><strong>År:</strong>år</span>
<span><strong>Omsætning:</strong> 1</span>
</span>
</div>
<div class="chart-x__value" :data-chart="3" @mouseover="graphHover($event)"
@mouseleave="graphHover($event)" @mousemove="mouseMove($event)">
<span class="chart-x__value-graph" :class="{'is-unloaded': animation === 1}" :style="{height: ((3 / 5 ) * 100) + '%' }"></span>
<span class="tooltip">
<span><strong>År:</strong>år</span>
<span><strong>Omsætning:</strong> 3</span>
</span>
</div>
<div class="chart-x__value" :data-chart="1" @mouseover="graphHover($event)"
@mouseleave="graphHover($event)" @mousemove="mouseMove($event)">
<span class="chart-x__value-graph" :class="{'is-unloaded': animation === 1}" :style="{height: ((2 / 5 ) * 100) + '%' }"></span>
<span class="tooltip">
<span><strong>År:</strong>år</span>
<span><strong>Omsætning:</strong> 2</span>
</span>
</div>
</div>
<div class="chart__labels">
<span :style="{width: (3 * 100) / 3 + '%'}" class="chart__labels-item">år1</span>
<span :style="{width: (3 * 100) / 3 + '%'}" class="chart__labels-item">år2</span>
<span :style="{width: (3 * 100) / 3 + '%'}" class="chart__labels-item">år3</span>
</div>
</div>
</div>
$color-blue-big-stone: #181F3A;
$color-blue-cerulean: #0999E8;
$border-color: #E5E8F2;
$color-green-shamrock: #3CD98F;
// main chart
.chart {
width: 100%;
height: 450px;
position: relative;
padding-left: 3rem;
padding-bottom: 3rem;
box-sizing: border-box;
margin-top: 2rem;
&--expand {
padding-left: 6rem;
.chart-x {
width: calc(100% - 6rem);
left: 6rem;
}
.chart-labels {
width: calc(100% - 8rem);
left: 8rem;
}
}
}
//chart y axis
.chart-y {
width: 100%;
position: absolute;
bottom: 3rem;
height: calc(100% - 3rem);
left: 0;
display: flex;
justify-content: space-between;
align-items: flex-end;
flex-direction: column;
// chart y count
&__count {
border-bottom: 1px dotted rgba($color-blue-big-stone, .2);
width: calc(100% - 3rem);
padding-left: 1.5rem;
right: 0;
position: relative;
}
&__count span {
position: absolute;
left: -2rem;
}
&__count:first-child {
border-top: 1px dotted rgba($color-blue-big-stone, .2);
border-bottom: none;
}
&__count:last-child {
border-bottom: 1px solid rgba(24,31,58,.3);
}
}
// chart x axis
.chart-x {
width: calc(100% - 3rem);
height: calc(100% - 3rem);
left: 3rem;
bottom: 3rem;
position: absolute;
display: inline-flex;
justify-content: space-around;
z-index: 5;
// chart x-value
&__value {
width: 100%;
position: relative;
}
&__value-graph {
content: '';
background-color: $color-blue-cerulean;
position: absolute;
bottom: 0;
width: 10px;
border-radius: 5px 5px 0 0;
left: 50%;
transform: translateX(-50%);
pointer-events: none;
transition: all .5s cubic-bezier(0,1,.82,.86);
}
}
// chart labels
.chart__labels {
height: 100%;
position: absolute;
bottom: 0rem;
width: calc(100% - 3rem);
left: 3rem;
display: flex;
justify-content: space-around;
align-items: flex-end;
flex-direction: row;
// chart labels item
&-item {
height: 100%;
margin: 0 auto;
position: relative;
display: flex;
align-items: flex-end;
justify-content: center;
}
&-item::after {
content: '';
position: absolute;
left: 0;
width: 100%;
height: calc(100% -3rem);
top: 0;
border-left: 1px dotted rgba($color-blue-big-stone, .1);
margin-bottom: 3rem;
}
&-item:last-child {
&::after {
border-right: 1px dotted rgba($color-blue-big-stone, .1);
}
}
&-item:first-child {
&::after {
border-left: 1px solid rgba($color-blue-big-stone, .3);
}
}
}
.is-unloaded {
// important to overrule in-line styling.
height: 0% !important;
}
// tooltop (visible on hover)
.tooltip {
width: auto;
height: 65px;
background: #fff;
display: none;
justify-content: space-around;
align-items: flex-start;
-webkit-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
-moz-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
pointer-events: none;
position: absolute;
flex-direction: column;
padding-left: 6px;
padding-right: 6px;
border-radius: 5px;
border: 1px solid $border-color;
z-index: 10000;
&::after {
content: '';
width: 10px;
height: 10px;
z-index: 1;
position: absolute;
top: 0;
background: white;
top: -5px;
transform: rotate(45deg);
-webkit-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
-moz-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
border: 1px solid $border-color;
border-bottom: none;
border-right: none;
}
span {
font-size: 1.2rem;
}
&.is-visible {
display: flex;
}
}
graphHover(event: Event) {
const target = event.target as HTMLElement;
const child = target.firstChild as HTMLElement;
const tooltip = target.children[1] as HTMLElement;
if (child !== null) {
if (!child.classList.contains("active")) {
child.classList.add("active");
tooltip.classList.add("active");
} else {
child.classList.remove("active");
tooltip.classList.remove("active");
}
}
}
mouseMove(event: MouseEvent) {
const target = event.target as HTMLElement;
const tooltip = target.children[1] as HTMLElement;
tooltip.style.top = (event.offsetY + 25) + 'px';
tooltip.style.left = (event.offsetX) + 'px';
}
<div class="col-12">
<h3 class="col-md-12"> Linear Graph</h3>
<h4 class="col-md-12">Works dynamically with v-for tags in each section</h4>
<div class="chart-line" :style="{height: (6 * 60) + 'px'}">
<div class="chart-line-x">
<span class="chart-line-x__count"><span>1</span></span>
<span class="chart-line-x__count"><span>2</span></span>
<span class="chart-line-x__count"><span>3</span></span>
<span class="chart-line-x__count"><span>4</span></span>
<span class="chart-line-x__count"><span>5</span></span>
<span class="chart-line-x__count"><span>6</span></span>
</div>
<div class="chart-line__values">
<div class="chart-line__values-value"
:data-line="3"
@mouseover="graphHover($event)"
@mouseleave="graphHover($event)"
@mousemove="mouseMove($event)">
<span class="chart-line__graph" :class="{'is-unloaded': unloaded === 0}" :style="{width: ((5 / 6) * 100) + '%' }" ></span>
<span class="tooltip">
<span><strong>Antal:</strong>5</span>
<span><strong>Navn:</strong> navn</span>
</span>
<span class="chart-line__values-label">navn</span>
</div>
<div class="chart-line__values-value"
:data-line="3"
@mouseover="graphHover($event)"
@mouseleave="graphHover($event)"
@mousemove="mouseMove($event)">
<span class="chart-line__graph" :class="{'is-unloaded': unloaded === 0}" :style="{width: ((3 / 6) * 100) + '%' }" ></span>
<span class="tooltip">
<span><strong>Antal:</strong>3</span>
<span><strong>Navn:</strong> navn</span>
</span>
<span class="chart-line__values-label">navn</span>
</div>
<div class="chart-line__values-value"
:data-line="3"
@mouseover="graphHover($event)"
@mouseleave="graphHover($event)"
@mousemove="mouseMove($event)">
<span class="chart-line__graph" :class="{'is-unloaded': unloaded === 0}" :style="{width: ((1 / 6) * 100) + '%' }" ></span>
<span class="tooltip">
<span><strong>Antal:</strong>1</span>
<span><strong>Navn:</strong> navn</span>
</span>
<span class="chart-line__values-label">navn</span>
</div>
</div>
</div>
</div>
$color-blue-big-stone: #181F3A;
$color-blue-cerulean: #0999E8;
$border-color: #E5E8F2;
$color-green-shamrock: #3CD98F;
// main chart
.chart {
width: 100%;
height: 450px;
position: relative;
padding-left: 3rem;
padding-bottom: 3rem;
box-sizing: border-box;
margin-top: 2rem;
&--expand {
padding-left: 6rem;
.chart-x {
width: calc(100% - 6rem);
left: 6rem;
}
.chart-labels {
width: calc(100% - 8rem);
left: 8rem;
}
}
}
// tooltop (visible on hover)
.tooltip {
width: auto;
height: 65px;
background: #fff;
display: none;
justify-content: space-around;
align-items: flex-start;
-webkit-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
-moz-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
pointer-events: none;
position: absolute;
flex-direction: column;
padding-left: 6px;
padding-right: 6px;
border-radius: 5px;
border: 1px solid $border-color;
z-index: 10000;
&::after {
content: '';
width: 10px;
height: 10px;
z-index: 1;
position: absolute;
top: 0;
background: white;
top: -5px;
transform: rotate(45deg);
-webkit-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
-moz-box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
box-shadow: 0px 8px 17px -5px rgba(0,0,0,0.29);
border: 1px solid $border-color;
border-bottom: none;
border-right: none;
}
span {
font-size: 1.2rem;
}
&.is-visible {
display: flex;
}
}
// Line chart
.chart-line {
width: 100%;
position: relative;
padding-bottom: 3rem;
box-sizing: border-box;
margin-top: 1rem;
}
// Line chart x axis
.chart-line-x {
display: inline-flex;
bottom: 0;
position: absolute;
width: 100%;
height: 100%;
justify-content: center;
align-items: flex-start;
// chart line x count
&__count {
width: 100%;
right: 0;
border-right: 1px dotted rgba(24,31,58,.2);
border-bottom: none;
display: flex;
align-items: flex-end;
height: calc(100% - 30px);
justify-content: flex-end;
padding-left: .5rem;
box-sizing: border-box;
position: relative;
border-bottom: 1px dotted rgba(24,31,58,.2);
border-top: 1px dotted rgba(24,31,58,.2);
}
&__count:first-child {
border-left: 1px dotted rgba(24,31,58,.2);
}
&__count span {
position: absolute;
bottom: -3rem;
}
&:first-child .chart-line-x__count {
span {
right: .5rem;
}
.first {
left: .5rem;
}
}
}
// Line chart values
.chart-line__values {
width: 100%;
height: calc(100% - 3rem);
bottom: 3rem;
position: absolute;
display: inline-flex;
justify-content: space-around;
flex-direction: column;
z-index: 5;
&-value {
height: 100%;
position: relative;
}
&-label {
pointer-events: none;
transform: translateY(.75rem);
position: absolute;
padding-left: 1rem;
text-transform: capitalize;
font-size: 1.3rem;
}
}
// Line chart coloured graph
.chart-line__graph {
content: '';
height: 8px;
background-color: $color-green-shamrock;
position: absolute;
left: 0;
border-radius: 200px;
pointer-events: none;
transform: translateY(2.5rem);
transition: all .3s cubic-bezier(0,1,.82,.86);
}
graphHover(event: Event) {
const target = event.target as HTMLElement;
const child = target.firstChild as HTMLElement;
const tooltip = target.children[1] as HTMLElement;
if (child !== null) {
if (!child.classList.contains("active")) {
child.classList.add("active");
tooltip.classList.add("active");
} else {
child.classList.remove("active");
tooltip.classList.remove("active");
}
}
}
mouseMove(event: MouseEvent) {
const target = event.target as HTMLElement;
const tooltip = target.children[1] as HTMLElement;
tooltip.style.top = (event.offsetY + 25) + 'px';
tooltip.style.left = (event.offsetX) + 'px';
}