ajout exo tp5
This commit is contained in:
@@ -21,3 +21,19 @@ Le but est de comprendre le code pour prendre en main Riot.js
|
||||
- Ajoutez le nombre de tâches restantes.
|
||||
- Modifiez le code pour que les tâches soient stockées localement (utilisez l'objet `localStorage`).
|
||||
|
||||
#### Ex2
|
||||
Voici un [exemple](./src/ex2) d'application (radar chart) écrite avec riot.js.
|
||||
<div align="center">
|
||||
<img src="./img/radar.png">
|
||||
</div>
|
||||
|
||||
- Complétez les méthodes `add` et `remove`.
|
||||
- Créez un nouveau composant `slider.riot`, qui vous utiliserez dans app.riot
|
||||
|
||||
#### Ex3
|
||||
L'api DummyJSON permet de manipuler des données fictives. Ecrire, avec riotjs, une application qui permet :
|
||||
|
||||
- de récuperer depuis l'url `https://dummyjson.com/products` une liste de produits
|
||||
- pour chaque produit, afficher le titre, prix et image.
|
||||
- ajouter un filtre `prix < 100`, et un bouton `voir détails`.
|
||||
|
||||
|
||||
BIN
R4.01_R4.A.10/td_tp/tp5/img/radar.png
Normal file
BIN
R4.01_R4.A.10/td_tp/tp5/img/radar.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 28 KiB |
18
R4.01_R4.A.10/td_tp/tp5/src/ex2/README.md
Normal file
18
R4.01_R4.A.10/td_tp/tp5/src/ex2/README.md
Normal file
@@ -0,0 +1,18 @@
|
||||
# Riot4 Radar Chart
|
||||
|
||||
## Usage
|
||||
|
||||
First of all, plz execute this commands.
|
||||
|
||||
```cmd
|
||||
$ cd ../
|
||||
$ yarn install
|
||||
$ yarn radar
|
||||
```
|
||||
|
||||
Perhaps the browser will open automatically and the application should start.
|
||||
|
||||
URL: [http://127.0.0.1:8080/](http://127.0.0.1:8080/)
|
||||
|
||||
## Demo
|
||||
demo: [CodeSandbox](https://codesandbox.io/embed/riot4-template-0f6i0)
|
||||
62
R4.01_R4.A.10/td_tp/tp5/src/ex2/app.riot
Normal file
62
R4.01_R4.A.10/td_tp/tp5/src/ex2/app.riot
Normal file
@@ -0,0 +1,62 @@
|
||||
<app>
|
||||
<h2>{ props.title }</h2>
|
||||
<div id="radar">
|
||||
|
||||
<!-- Use the component -->
|
||||
|
||||
<svg
|
||||
is="polygraph"
|
||||
stats={ state.stats } />
|
||||
|
||||
|
||||
<!-- controls -->
|
||||
|
||||
<div>
|
||||
<div each={ (stat, index) in state.stats }>
|
||||
<label>{ stat.label }</label>
|
||||
<input type="range"
|
||||
onchange={ changeValue }
|
||||
min="0"
|
||||
max="100"
|
||||
data-index={ index }
|
||||
value={ stat.value }>
|
||||
<span>{ stat.value }</span>
|
||||
<button onclick={ remove } class="remove" value={ index }>X</button>
|
||||
</div>
|
||||
|
||||
<!-- add item -->
|
||||
<form id="add">
|
||||
<input type="text"
|
||||
name="newlabel"
|
||||
value={ state.newLabel }
|
||||
oninput={ inputStat }>
|
||||
<button onclick={ add }>Add a Stat</button>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
state: {
|
||||
newLabel: '',
|
||||
stats: []
|
||||
},
|
||||
onBeforeMount(props, state) {
|
||||
state.stats = props.stats
|
||||
},
|
||||
add(e) {
|
||||
// TODO
|
||||
},
|
||||
remove(stat) {
|
||||
// TODO
|
||||
},
|
||||
inputStat(e) {
|
||||
this.state.newLabel = e.target.value
|
||||
},
|
||||
changeValue(e) {
|
||||
this.state.stats[e.target.dataset.index].value = e.target.value
|
||||
this.update()
|
||||
}
|
||||
}
|
||||
</script>
|
||||
</app>
|
||||
31
R4.01_R4.A.10/td_tp/tp5/src/ex2/components/polygraph.riot
Normal file
31
R4.01_R4.A.10/td_tp/tp5/src/ex2/components/polygraph.riot
Normal file
@@ -0,0 +1,31 @@
|
||||
<polygraph>
|
||||
<g>
|
||||
<polygon points={ points() }></polygon>
|
||||
<circle cx="200" cy="200" r="160"></circle>
|
||||
<text
|
||||
each={ (stat, index) in state.stats }
|
||||
index={ index }
|
||||
stat={ stat }
|
||||
total={ state.stats.length }
|
||||
is="text" />
|
||||
</g>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
state: {
|
||||
stats: []
|
||||
},
|
||||
onBeforeMount(props, state) {
|
||||
state.stats = props.stats
|
||||
},
|
||||
// a computed property for the polygon's points
|
||||
points() {
|
||||
const total = this.state.stats.length
|
||||
return this.state.stats.map((stat, i) => {
|
||||
const point = valueToPoint(stat.value, i, total)
|
||||
return point.x + ',' + point.y
|
||||
}).join(' ')
|
||||
}
|
||||
}
|
||||
</script>
|
||||
</polygraph>
|
||||
25
R4.01_R4.A.10/td_tp/tp5/src/ex2/components/text.riot
Normal file
25
R4.01_R4.A.10/td_tp/tp5/src/ex2/components/text.riot
Normal file
@@ -0,0 +1,25 @@
|
||||
<text x={ state.point.x } y={ state.point.y }>
|
||||
{ props.stat.label }
|
||||
|
||||
<script>
|
||||
export default {
|
||||
state: {
|
||||
point: ''
|
||||
},
|
||||
onBeforeMount(props, state) {
|
||||
state.point = valueToPoint(
|
||||
+props.stat.value + 10,
|
||||
props.index,
|
||||
props.total
|
||||
)
|
||||
},
|
||||
onBeforeUpdate(props, state) {
|
||||
state.point = valueToPoint(
|
||||
+props.stat.value + 10,
|
||||
props.index,
|
||||
props.total
|
||||
)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
</text>
|
||||
13
R4.01_R4.A.10/td_tp/tp5/src/ex2/helper.js
Normal file
13
R4.01_R4.A.10/td_tp/tp5/src/ex2/helper.js
Normal file
@@ -0,0 +1,13 @@
|
||||
const valueToPoint = (value, index, total) => {
|
||||
const x = 0
|
||||
const y = -value * 1.6
|
||||
const angle = Math.PI * 2 / total * index
|
||||
const cos = Math.cos(angle)
|
||||
const sin = Math.sin(angle)
|
||||
const tx = x * cos - y * sin + 200
|
||||
const ty = x * sin + y * cos + 200
|
||||
return {
|
||||
x: tx,
|
||||
y: ty
|
||||
}
|
||||
}
|
||||
42
R4.01_R4.A.10/td_tp/tp5/src/ex2/index.html
Normal file
42
R4.01_R4.A.10/td_tp/tp5/src/ex2/index.html
Normal file
@@ -0,0 +1,42 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Riot.js Radar Chart</title>
|
||||
<link rel="stylesheet" href="style.css">
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/riot/10.0.1/riot+compiler.min.js"></script>
|
||||
<script src="helper.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<!-- app -->
|
||||
|
||||
<app></app>
|
||||
|
||||
<!-- tags -->
|
||||
<script data-src="app.riot" type="riot"></script>
|
||||
<script data-src="components/polygraph.riot" type="riot"></script>
|
||||
<script data-src="components/text.riot" type="riot"></script>
|
||||
<script>
|
||||
riot
|
||||
.compile()
|
||||
.then(() => {
|
||||
riot.mount('app', {
|
||||
title: 'Riot.js Radar Chart',
|
||||
stats: [
|
||||
{ label: 'A', value: 100 },
|
||||
{ label: 'B', value: 100 },
|
||||
{ label: 'C', value: 100 },
|
||||
{ label: 'D', value: 100 },
|
||||
{ label: 'E', value: 100 },
|
||||
{ label: 'F', value: 100 }
|
||||
]
|
||||
})
|
||||
})
|
||||
.catch(e => {
|
||||
console.error(e)
|
||||
})
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
46
R4.01_R4.A.10/td_tp/tp5/src/ex2/style.css
Normal file
46
R4.01_R4.A.10/td_tp/tp5/src/ex2/style.css
Normal file
@@ -0,0 +1,46 @@
|
||||
body {
|
||||
font-family: Helvetica Neue, Arial, sans-serif;
|
||||
}
|
||||
#radar{
|
||||
display : flex;
|
||||
}
|
||||
|
||||
svg {
|
||||
width:400px;
|
||||
height:400px;
|
||||
}
|
||||
polygon {
|
||||
fill: #ED1646;
|
||||
opacity: .75;
|
||||
}
|
||||
|
||||
circle {
|
||||
fill: transparent;
|
||||
stroke: #999;
|
||||
}
|
||||
|
||||
text {
|
||||
font-family: Futura, Helvetica Neue, Arial, sans-serif;
|
||||
font-size: 10px;
|
||||
fill: #666;
|
||||
}
|
||||
|
||||
label {
|
||||
display: inline-block;
|
||||
margin-left: 10px;
|
||||
width: 20px;
|
||||
}
|
||||
|
||||
#raw {
|
||||
/* position: absolute;
|
||||
top: 0;
|
||||
left: 300px;*/
|
||||
}
|
||||
|
||||
#add {
|
||||
margin-top: 1em;
|
||||
}
|
||||
|
||||
.remove {
|
||||
margin: 0 4px;
|
||||
}
|
||||
Reference in New Issue
Block a user