Skip to content

Commit

Permalink
- tree + branches, basic strokes
Browse files Browse the repository at this point in the history
  • Loading branch information
Kyrand committed Dec 26, 2022
1 parent 9fa1feb commit 816d65e
Show file tree
Hide file tree
Showing 5 changed files with 154 additions and 53 deletions.
73 changes: 48 additions & 25 deletions src/App.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
import { tweened } from 'svelte/motion'
import { cubicOut } from 'svelte/easing'
import Branch from './components/Tree/Branch.svelte'
import Tree from './components/Tree/Tree.svelte'
import Switch from './components/Switch.svelte'
import Range from './components/Range.svelte'
Expand All @@ -17,19 +17,50 @@
import Legend from './components/Legend.svelte'
let tweenedT = 1
let scale = 1
let duration = 3000
let branches = 10
let branchNum = 5
let branchCount = 4
let t = 1.0
let scaleFac = 0.5
let cx = 0.5,
cy = 0.5,
dx = 0.5,
dy = 1,
bp = 0.5
let cx = rv(-0.2, 0.2),
cy = rv(0.3, 0.7),
dx = rv(-0.2, 0.2),
dy = rv(0.8, 1),
bp = 0.5,
rot = 45
let markers = true
// tweening
let bv = { cx, cy, dx, dy, bp }
let bv = { scaleFac, cx, cy, dx, dy, bp, rot }
let branches
randomizeBranches()
console.log(branches)
//let bv = branches[0]
// functions
function rv(min, max) {
return min + Math.random() * (max - min)
}
function makeRandomBranch() {
return {
scaleFac: rv(0.5, 0.7),
rot: rv(-135, 135),
cx: rv(-1, 1),
cy: rv(0, 1),
dx: rv(-1, 1),
dy: rv(0, 1),
bp: rv(0.5, 1)
}
}
function randomizeBranches() {
branches = [
...Array(branchCount)
.fill(0)
.map(() => makeRandomBranch())
]
}
// $: scaleFac = _scaleFac / 100
// console logs
$: console.log('tweenedT: ', tweenedT)
Expand All @@ -47,28 +78,20 @@
<!-- <Switch bind:flag={stackLines} label="Stack the lines" id="stackLines" />
<Switch bind:flag={normalizeAxes} label="Dynamic y axis" id="normAxes" /> -->
<Range bind:value={duration} min={0} max={5000} label="Transition duration (ms)" />
<RangeF bind:value={scaleFac} label="Scale factor" />
<RangeF bind:value={bv.cx} label="Curve mid x" />
<RangeF bind:value={bv.scaleFac} label="Scale factor" />
<RangeF bind:value={bv.cx} label="Curve mid x" min={-1.0} max={1.0} />
<RangeF bind:value={bv.cy} label="Curve mid y" />
<RangeF bind:value={bv.dx} label="Curve end x" />
<RangeF bind:value={bv.dx} label="Curve end x" min={-1.0} max={1.0} />
<RangeF bind:value={bv.dy} label="Curve end y" />
<RangeF bind:value={bv.bp} label="Branch position" />
<Switch bind:flag={markers} label="Show leaves" />
<button on:click={randomizeBranches}>Randomize branches</button>
</div>
<div class="chart-container">
<LayerCake padding={{ top: 0, right: 0, bottom: 0, left: 0 }}>
<LayerCake>
<Svg>
<g transform="translate(300, 600) rotate(180)">
<Branch
{branches}
{scaleFac}
cx={2 * (bv.cx - 0.5)}
cy={bv.cy}
dx={2 * (bv.dx - 0.5)}
dy={bv.dy}
bp={bv.bp}
/>
<g transform={`translate(300, 600) rotate(180) scale(${scale})`}>
<Tree {...bv} {branches} {branchNum} {markers} />
</g>
<Tweener {t} bind:tweenedT {duration} />
</Svg>
</LayerCake>
</div>
Expand All @@ -78,7 +101,7 @@
<style>
/*
The wrapper div needs to have an explicit width and height in CSS.
It can also be a flexbox child or CSS grid element.
<g transform="translate(300, 600) rotate(180)">
The point being it needs dimensions since the <LayerCake> element will
expand to fill it.
*/
Expand Down
24 changes: 15 additions & 9 deletions src/components/Range.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -14,25 +14,31 @@
<label>{label}</label>
{/if}
<div class="range__wrapper">
<input bind:value type="range" {min} {max} />
<div class="value">{value}</div>
<div class="range__slider">
<input bind:value type="range" {min} {max} />
</div>
<div class="range__value">{value}</div>
</div>
</div>

<style>
.range__wrapper {
display: flex;
display: grid;
grid-template-columns: 3fr 1fr;
align-items: center;
gap: 1em;
}
input {
margin-bottom: 0;
.range__slider {
grid-column: 1;
}
.range__value {
grid-column: 2;
width: 80px;
}
.input,
._value {
display: inline-block;
vertical-align: middle;
input {
margin-bottom: 0;
}
</style>
8 changes: 5 additions & 3 deletions src/components/RangeF.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
export let label = null
let set = false
let range = max - min
let rvalue = rmax * (range * (value - min))
let rvalue = rmax * ((value - min) / range)
$: {
console.log(range, rvalue, rmax)
Expand All @@ -30,13 +30,14 @@
<div class="range__slider">
<input bind:value={rvalue} type="range" min={rmin} max={rmax} />
</div>
<div class="range__value">{value}</div>
<div class="range__value">{value.toFixed(2)}</div>
</div>
</div>

<style>
.range__wrapper {
grid-template-columns: 4fr 1fr;
display: grid;
grid-template-columns: 3fr 1fr;
align-items: center;
gap: 1em;
}
Expand All @@ -47,6 +48,7 @@
.range__value {
grid-column: 2;
width: 80px;
}
input {
Expand Down
57 changes: 41 additions & 16 deletions src/components/Tree/Branch.svelte
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
<script>
export let branches = 2
export let branchNum = 0
export let branches = []
export let scaleFac = 0.5
export let t = 0.5
export let curveFac = 0.5
Expand All @@ -10,37 +11,61 @@
export let dx = 0
export let dy = 1
export let bp = 0.5
export let rot = 45
export let markers = true
export let markerSize = 10
let markerTransform = 'translate(0,0)'
let d
let el,
x = 0,
y = 0,
l,
p
let el, l
$: {
let h = curveHeight
let w = curveWidth
d = `M 0 0 Q ${cx * w} ${cy * h} ${dx * w} ${dy * h}`
let endPt = { x: dx * w, y: dy * h }
markerTransform = `translate(${endPt.x}, ${endPt.y})`
}
$: branchTransform = (b) => {
if (el) {
let l = el.getTotalLength()
let p = el.getPointAtLength(b.bp * l)
let x = p.x
let y = p.y
let transform = `translate(${x}, ${y}) rotate(${b.rot}) scale(${b.scaleFac})`
console.log('transform: ', transform)
return transform
}
}
$: markerPoint = (el) => {
if (el) {
l = el.getTotalLength()
p = el.getPointAtLength(bp * l)
x = p.x
y = p.y
let l = el.getTotalLength()
let endPt = el.getPointAtLength(l)
return
}
}
$: console.log('bp: ', bp)
$: console.log('props: ', $$props)
</script>

<g transform={`translate(0,0)`}>
<!-- <text class="branch">Branch number {branches}</text> -->
<!-- <path bind:this={el} d={`M 0 0 Q 100 200 0 400} stroke="black" fill="transparent" /> -->
<path bind:this={el} {d} stroke="black" fill="transparent" />
<circle r="10" />
<g transform={`translate(${x}, ${y}) rotate(45) scale(${scaleFac})`}>
{#if branches > 0}
<svelte:self branches={branches - 1} {scaleFac} {cx} {cy} {dx} {dy} {bp} />
{/if}
</g>
{#if markers}
<g transform={markerTransform}>
<circle r={markerSize} />
</g>
{/if}
{#if branchNum > 0}
{#each branches as b}
<g class="branch" transform={branchTransform(b)}>
<svelte:self {...b} {branches} {markers} branchNum={branchNum - 1} />
</g>
{/each}
{/if}
</g>
45 changes: 45 additions & 0 deletions src/components/Tree/Tree.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
<script>
import Branch from './Branch.svelte'
export let branches = []
export let branchNum = 3
export let cx = 0.5
export let cy = 0.5
export let dx = 0
export let dy = 1
export let rot = 45
export let curveHeight = 600
export let curveWidth = 600
export let markers = true
let el, d
$: {
let h = curveHeight
let w = curveWidth
d = `M 0 0 Q ${cx * w} ${cy * h} ${dx * w} ${dy * h}`
el = el
}
$: branchTransform = (b) => {
if (el) {
let l = el.getTotalLength()
let p = el.getPointAtLength(b.bp * l)
let x = p.x
let y = p.y
let transform = `translate(${x}, ${y}) rotate(${b.rot}) scale(${b.scaleFac})`
return transform
}
}
</script>

<g transform={`translate(0,0)`}>
<!-- <text class="branch">Branch number {branches}</text> -->
<!-- <path bind:this={el} d={`M 0 0 Q 100 200 0 400} stroke="black" fill="transparent" /> -->
<path bind:this={el} {d} stroke="black" fill="transparent" />

{#each branches as b}
<g class="branch" transform={branchTransform(b)}>
<Branch {...b} {branchNum} {branches} {markers} />
</g>
{/each}
</g>

0 comments on commit 816d65e

Please sign in to comment.