added done state (not yet reactive)
This commit is contained in:
parent
463fd5eee7
commit
91f09beede
|
|
@ -1,42 +1,12 @@
|
|||
<script setup lang="ts">
|
||||
import * as d3 from "d3";
|
||||
import {onMounted, ref} from "vue";
|
||||
import {computed, onMounted, reactive} from "vue";
|
||||
import * as _ from 'underscore'
|
||||
import {useCircleStore} from "@/stores/circle";
|
||||
|
||||
|
||||
const props = defineProps<{
|
||||
circleData: {
|
||||
default: {
|
||||
id: 10,
|
||||
title: 'Analyse des letzten Falles',
|
||||
slug: 'analyse',
|
||||
type: 'learnpath.Circle',
|
||||
translation_key: '2ca5ba7a-98b8-4511-ba50-bc190714886d',
|
||||
learning_sequences: [
|
||||
{
|
||||
id: 11,
|
||||
title: 'Starten',
|
||||
done: true,
|
||||
},
|
||||
{
|
||||
id: 13,
|
||||
title: 'Beobachten',
|
||||
done: true,
|
||||
},
|
||||
{
|
||||
id: 18,
|
||||
title: 'Anwenden',
|
||||
done: true,
|
||||
},
|
||||
{
|
||||
id: 30,
|
||||
title: 'Üben',
|
||||
done: false,
|
||||
},
|
||||
],
|
||||
},
|
||||
type: object
|
||||
},
|
||||
circleStore: {},
|
||||
width: {
|
||||
default: 500,
|
||||
type: number,
|
||||
|
|
@ -51,34 +21,53 @@ const props = defineProps<{
|
|||
}>()
|
||||
|
||||
|
||||
function calculatePieData(circle) {
|
||||
let learningSequences = _.filter(circle.children, (child) => {
|
||||
return child.type === 'learnpath.LearningSequence';
|
||||
})
|
||||
let pieWeights = new Array(Math.max(learningSequences.length, 1)).fill(1)
|
||||
let pieGenerator = d3.pie()
|
||||
let pieData = pieGenerator(pieWeights)
|
||||
console.log(pieData)
|
||||
_.forEach(pieData, (pie) => {
|
||||
pie.title = learningSequences[parseInt(pie.index)].title
|
||||
pie.icon = learningSequences[parseInt(pie.index)].icon
|
||||
pie.startAngle = pie.startAngle + Math.PI
|
||||
pie.endAngle = pie.endAngle + Math.PI
|
||||
pie.arrowStartAngle = pie.endAngle + (pie.startAngle - pie.endAngle) / 2
|
||||
pie.arrowEndAngle = pie.startAngle + (pie.startAngle - pie.endAngle) / 2
|
||||
pie.done = true
|
||||
})
|
||||
pieData = pieData.reverse()
|
||||
return pieData
|
||||
function someFinished(learningSequence) {
|
||||
return props.circleStore.flatChildren.filter((lc) => {
|
||||
return lc.completed && lc.parentLearningSequence?.translation_key === learningSequence.translation_key;
|
||||
}).length > 0;
|
||||
}
|
||||
|
||||
|
||||
const pieData = computed(() => {
|
||||
const circle = props.circleStore.circleData, completionData = props.circleStore.completionData
|
||||
console.log('initial of compute pie data ', circle, completionData)
|
||||
|
||||
if (circle && completionData) {
|
||||
console.log('initial of compute pie data ', circle, completionData)
|
||||
let learningSequences = _.filter(circle.children, (child) => {
|
||||
return child.type === 'learnpath.LearningSequence';
|
||||
})
|
||||
|
||||
const completionDataByPageId = _.object(_.map(completionData, function (item) {
|
||||
console.log(item)
|
||||
return [item.page_key, item]
|
||||
}))
|
||||
|
||||
let pieWeights = new Array(Math.max(learningSequences.length, 1)).fill(1)
|
||||
let pieGenerator = d3.pie()
|
||||
let angles = pieGenerator(pieWeights)
|
||||
_.forEach(angles, (pie) => {
|
||||
const thisLearningSequence = learningSequences[parseInt(pie.index)]
|
||||
pie.title = thisLearningSequence.title
|
||||
pie.icon = thisLearningSequence.icon
|
||||
pie.startAngle = pie.startAngle + Math.PI
|
||||
pie.endAngle = pie.endAngle + Math.PI
|
||||
pie.arrowStartAngle = pie.endAngle + (pie.startAngle - pie.endAngle) / 2
|
||||
pie.arrowEndAngle = pie.startAngle + (pie.startAngle - pie.endAngle) / 2
|
||||
console.log(someFinished(thisLearningSequence))
|
||||
pie.done = someFinished(thisLearningSequence)
|
||||
})
|
||||
angles = angles.reverse()
|
||||
return angles
|
||||
}
|
||||
return {}
|
||||
})
|
||||
|
||||
onMounted(async () => {
|
||||
const root = ref(null)
|
||||
console.log(root?.value)
|
||||
let pieData = calculatePieData(props.circleData),
|
||||
width = 450, //props.width,
|
||||
const width = 450, //props.width,
|
||||
height = 450, //props.height,
|
||||
radius: number = Math.min(width, height) / 2.4
|
||||
radius: number = Math.min(width, height) / 2.4,
|
||||
arrowStrokeWidth = 2
|
||||
|
||||
const blue900 = '#00224D',
|
||||
blue700 = '#1A5197',
|
||||
|
|
@ -95,8 +84,7 @@ onMounted(async () => {
|
|||
|
||||
const g = svg.append('g').attr('transform', 'translate(' + width / 2 + ',' + height / 2 + ')')
|
||||
|
||||
const arrowStrokeWidth = 2
|
||||
|
||||
// Append markter as definition to the svg
|
||||
svg.append("svg:defs").append("svg:marker")
|
||||
.attr("id", "triangle")
|
||||
.attr("refX", 11)
|
||||
|
|
@ -111,11 +99,9 @@ onMounted(async () => {
|
|||
.attr('stroke-width', arrowStrokeWidth)
|
||||
.attr('stroke', gray500)
|
||||
|
||||
// Generate the pie
|
||||
const pie = d3.pie()
|
||||
|
||||
// Generate the pie diagram wede
|
||||
const wedge = d3
|
||||
const wedgeGenerator = d3
|
||||
.arc()
|
||||
.innerRadius(radius / 2.5)
|
||||
.padAngle(12 / 360)
|
||||
|
|
@ -125,21 +111,8 @@ onMounted(async () => {
|
|||
// Generate the arrows
|
||||
const arrowRadius = radius * 1.1
|
||||
|
||||
const arrow = d3
|
||||
.arc()
|
||||
.innerRadius(arrowRadius)
|
||||
.outerRadius(arrowRadius + arrowStrokeWidth)
|
||||
.padAngle(20 / 360)
|
||||
.startAngle(d => {
|
||||
return d.arrowStartAngle
|
||||
})
|
||||
.endAngle(d => {
|
||||
return d.arrowEndAngle
|
||||
})
|
||||
|
||||
|
||||
//Generate groups
|
||||
const learningSequences = g.selectAll('.learningSegmentArc').data(pieData).enter().append('g')
|
||||
const learningSequences = g.selectAll('.learningSegmentArc').data(pieData.value).enter().append('g')
|
||||
.attr('class', 'learningSegmentArc')
|
||||
.attr('role', 'button')
|
||||
.attr('fill', gray300)
|
||||
|
|
@ -153,6 +126,7 @@ onMounted(async () => {
|
|||
.attr('fill', (d) => {
|
||||
return d.done ? sky400 : gray100
|
||||
})
|
||||
|
||||
})
|
||||
.on('mouseout', function (d, i) {
|
||||
d3.select(this)
|
||||
|
|
@ -171,7 +145,7 @@ onMounted(async () => {
|
|||
})
|
||||
|
||||
|
||||
learningSequences.append('path').attr('d', wedge)
|
||||
learningSequences.append('path').attr('d', wedgeGenerator)
|
||||
|
||||
|
||||
const learningSequenceText = learningSequences
|
||||
|
|
@ -182,7 +156,7 @@ onMounted(async () => {
|
|||
return d.title
|
||||
})
|
||||
.attr("transform", function (d) {
|
||||
let translate = wedge.centroid(d)
|
||||
let translate = wedgeGenerator.centroid(d)
|
||||
translate = [translate[0], translate[1] + 20]
|
||||
return "translate(" + translate + ")";
|
||||
})
|
||||
|
|
@ -198,24 +172,36 @@ onMounted(async () => {
|
|||
.attr("width", iconWidth)
|
||||
.attr("height", iconWidth)
|
||||
.attr("transform", function (d) {
|
||||
let translate = wedge.centroid(d)
|
||||
let translate = wedgeGenerator.centroid(d)
|
||||
translate = [translate[0] - iconWidth / 2, translate[1] - iconWidth]
|
||||
return "translate(" + translate + ")";
|
||||
})
|
||||
|
||||
|
||||
//Generate groups
|
||||
// Create Arrows
|
||||
const arrow = d3
|
||||
.arc()
|
||||
.innerRadius(arrowRadius)
|
||||
.outerRadius(arrowRadius + arrowStrokeWidth)
|
||||
.padAngle(20 / 360)
|
||||
.startAngle(d => {
|
||||
return d.arrowStartAngle
|
||||
})
|
||||
.endAngle(d => {
|
||||
return d.arrowEndAngle
|
||||
})
|
||||
|
||||
|
||||
const arrows = g
|
||||
.selectAll('.arrow')
|
||||
.data(pieData)
|
||||
.data(pieData.value)
|
||||
.enter()
|
||||
.append('g')
|
||||
.attr('class', 'arrow')
|
||||
.attr('marker-end', 'url(#triangle)')
|
||||
|
||||
|
||||
// remove last arrow
|
||||
d3.selection.prototype.last = function () {
|
||||
console.log('last', this)
|
||||
let last = this.size() - 1;
|
||||
return d3.select(this.nodes()[last]);
|
||||
};
|
||||
|
|
@ -224,7 +210,6 @@ onMounted(async () => {
|
|||
const all_arows = g.selectAll('.arrow')
|
||||
all_arows.last().remove()
|
||||
|
||||
|
||||
//Draw arrow paths
|
||||
arrows.append('path').attr('fill', gray500).attr('d', arrow)
|
||||
|
||||
|
|
|
|||
|
|
@ -240,10 +240,6 @@ export default {
|
|||
const arcs = this.svg
|
||||
.selectAll('g')
|
||||
.selectAll('.learningSegmentArc')
|
||||
.attr('fill', (d) => {
|
||||
let color = 'red'
|
||||
return color
|
||||
})
|
||||
.data((d) => {
|
||||
return d.pieData
|
||||
})
|
||||
|
|
@ -344,7 +340,7 @@ export default {
|
|||
|
||||
|
||||
<template>
|
||||
<div class="svg-container h-full content-start ">
|
||||
<div class="svg-container h-full content-start">
|
||||
<svg class="learning-path-visualization h-full" :viewBox="viewBox">
|
||||
</svg>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -45,8 +45,8 @@ onMounted(async () => {
|
|||
{{ circleStore.circleData.title }}
|
||||
</h1>
|
||||
|
||||
<div v-if="circleStore.circleData.learningSequences">
|
||||
<CircleDiagram :circle-data="circleStore.circleData"></CircleDiagram>
|
||||
<div v-if="circleStore.circleData.learningSequences && circleStore.completionData" class="w-full mt-8">
|
||||
<CircleDiagram :circle-store="circleStore"></CircleDiagram>
|
||||
</div>
|
||||
|
||||
<div class="border-t-2 border-gray-500 mt-4 lg:hidden">
|
||||
|
|
|
|||
Loading…
Reference in New Issue