simplify project
This commit is contained in:
commit
6f868b91cf
5 files changed
+409
No files matched your search
@@ -0,0 +1 @@
|
|||||||
|
.idea
|
||||||
+113
@@ -0,0 +1,113 @@
|
|||||||
|
<!doctype html>
|
||||||
|
<html lang="en">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"
|
||||||
|
name="viewport">
|
||||||
|
<meta content="ie=edge" http-equiv="X-UA-Compatible">
|
||||||
|
<title>Dessin d'Enfants</title>
|
||||||
|
<link crossorigin="anonymous" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.1/css/all.min.css"
|
||||||
|
integrity="sha512-DTOQO9RWCH3ppGqcWaEA1BIZOC6xxalwEsw9c2QQeAIftl+Vegovlnee1c9QX4TctnWMn13TZye+giMm8e2LwA=="
|
||||||
|
referrerpolicy="no-referrer" rel="stylesheet"/>
|
||||||
|
<link href="https://cdn.jsdelivr.net/npm/bulma@0.9.4/css/bulma.min.css" rel="stylesheet">
|
||||||
|
<script src="main.js" type="module"></script>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
|
||||||
|
<nav aria-label="main navigation" class="navbar" role="navigation">
|
||||||
|
<div class="navbar-brand">
|
||||||
|
<a class="navbar-item" href="https://bulma.io">
|
||||||
|
<img height="28" src="./logo.jpg">
|
||||||
|
<h1 class="title is-6 ml-">Dessins d'Enfants</h1>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
|
||||||
|
<div class="columns is-centered">
|
||||||
|
<div class="column is-two-thirds">
|
||||||
|
<figure class="image" style="text-align: center;">
|
||||||
|
<svg id="canvas" style="height: 500px; width: 500px; border: solid; border-color: pink;"></svg>
|
||||||
|
</figure>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="columns is-centered">
|
||||||
|
<div class="column is-two-thirds">
|
||||||
|
|
||||||
|
<div class="columns">
|
||||||
|
<div class="column">
|
||||||
|
<div class="field">
|
||||||
|
<label class="label">Centre X du Cercle</label>
|
||||||
|
<div class="control">
|
||||||
|
<input class="input"
|
||||||
|
id="cx"
|
||||||
|
max="500"
|
||||||
|
min="1"
|
||||||
|
placeholder="250"
|
||||||
|
type="number">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="column">
|
||||||
|
<div class="field">
|
||||||
|
<label class="label">Centre Y du Cercle</label>
|
||||||
|
<div class="control">
|
||||||
|
<input class="input"
|
||||||
|
id="cy"
|
||||||
|
max="500"
|
||||||
|
min="1"
|
||||||
|
placeholder="250"
|
||||||
|
type="number">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="column">
|
||||||
|
<div class="field">
|
||||||
|
<label class="label">Rayon du Cercle</label>
|
||||||
|
<div class="control">
|
||||||
|
<input class="input"
|
||||||
|
id="cr"
|
||||||
|
max="500"
|
||||||
|
min="1"
|
||||||
|
placeholder="100"
|
||||||
|
type="number">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="column">
|
||||||
|
<br>
|
||||||
|
<button class="button mt-2" id="draw-circle">Ajouter Cercle</button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
<div class="columns is-centered">
|
||||||
|
<div class="column is-two-thirds">
|
||||||
|
<table class="table table is-fullwidth">
|
||||||
|
<thead>
|
||||||
|
<tr>
|
||||||
|
<th>Id</th>
|
||||||
|
<th>Description</th>
|
||||||
|
<th>Actions</th>
|
||||||
|
</tr>
|
||||||
|
</thead>
|
||||||
|
<tbody id="table-body">
|
||||||
|
</tbody>
|
||||||
|
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
<div class="columns is-centered">
|
||||||
|
<div class="column is-two-thirds">
|
||||||
|
<button class="button mt-2" id="clear-drawing">Tout Effacer</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
Binary file not shown.
|
After Width: | Height: | Size: 79 KiB |
+89
@@ -0,0 +1,89 @@
|
|||||||
|
|
||||||
|
import {drawCircles, populateTable, Circle, Point, randomColor} from "./tp1.js";
|
||||||
|
|
||||||
|
const circles = []
|
||||||
|
|
||||||
|
function getCircleById(circleId){
|
||||||
|
for(const circle of circles){
|
||||||
|
if(circle.getId() === circleId){
|
||||||
|
return circle;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClickUp(circleId){
|
||||||
|
const circle = getCircleById(circleId);
|
||||||
|
const center = circle.getCenter();
|
||||||
|
const newCenter = new Point(center.getX(), center.getY() - 10);
|
||||||
|
circle.setCenter(newCenter);
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClickDown(circleId){
|
||||||
|
const circle = getCircleById(circleId);
|
||||||
|
const center = circle.getCenter();
|
||||||
|
const newCenter = new Point(center.getX(), center.getY() + 10);
|
||||||
|
circle.setCenter(newCenter);
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClickLeft(circleId){
|
||||||
|
const circle = getCircleById(circleId);
|
||||||
|
const center = circle.getCenter();
|
||||||
|
const newCenter = new Point(center.getX() - 10, center.getY());
|
||||||
|
circle.setCenter(newCenter);
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
function onClickRight(circleId){
|
||||||
|
const circle = getCircleById(circleId);
|
||||||
|
const center = circle.getCenter();
|
||||||
|
const newCenter = new Point(center.getX() + 10, center.getY());
|
||||||
|
circle.setCenter(newCenter);
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function onClickPaint(circleId){
|
||||||
|
const circle = getCircleById(circleId);
|
||||||
|
circle.setColor(randomColor(Date.now()))
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
function pointToString(point){
|
||||||
|
return `(${point.getX()}, ${point.getY()})`;
|
||||||
|
}
|
||||||
|
|
||||||
|
function drawNewCircle(){
|
||||||
|
const x = parseInt(document.getElementById("cx").value)
|
||||||
|
const y = parseInt(document.getElementById("cy").value)
|
||||||
|
const r = parseInt(document.getElementById("cr").value)
|
||||||
|
const p = new Point(x, y);
|
||||||
|
const circle = new Circle(p, r, Date.now());
|
||||||
|
circles.push(circle);
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
function clearCircles(){
|
||||||
|
circles.length = 0;
|
||||||
|
renderCircles();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function renderCircles(){
|
||||||
|
drawCircles(document.getElementById("canvas"), circles);
|
||||||
|
populateTable(document.getElementById("table-body"),
|
||||||
|
circles,
|
||||||
|
onClickUp,
|
||||||
|
onClickDown,
|
||||||
|
onClickLeft,
|
||||||
|
onClickRight,
|
||||||
|
onClickPaint);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
document.getElementById("draw-circle").addEventListener("click", drawNewCircle);
|
||||||
|
document.getElementById("clear-drawing").addEventListener("click", clearCircles);
|
||||||
|
|
||||||
+206
@@ -0,0 +1,206 @@
|
|||||||
|
import m from "https://esm.sh/mithril@2.2.2"
|
||||||
|
|
||||||
|
const BLACK = "000000";
|
||||||
|
/**
|
||||||
|
* Classe qui représente un point sur
|
||||||
|
* un plan cartésien. Le point est donc
|
||||||
|
* représenté par deux coordonnées x et y.
|
||||||
|
*/
|
||||||
|
export class Point{
|
||||||
|
#x;
|
||||||
|
#y;
|
||||||
|
constructor(x, y) {
|
||||||
|
this.#x = x;
|
||||||
|
this.#y = y;
|
||||||
|
}
|
||||||
|
getX(){
|
||||||
|
return this.#x;
|
||||||
|
}
|
||||||
|
|
||||||
|
getY(){
|
||||||
|
return this.#y;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Classe qui représente un cercle. Le cercle est
|
||||||
|
* définit par un Point et un rayon.
|
||||||
|
*
|
||||||
|
* Par défaut, le cercle est noir. Mais le cercle peut
|
||||||
|
* changer de couleur.
|
||||||
|
*/
|
||||||
|
export class Circle{
|
||||||
|
#center;
|
||||||
|
#radius;
|
||||||
|
#color;
|
||||||
|
#id;
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param {Point} center le point au centre du cercle
|
||||||
|
* @param {number} radius le rayon du cercle
|
||||||
|
* @param {number} id l'id unique du cercle. C'est au
|
||||||
|
* créateur de l'instance de s'assurer de l'unicité
|
||||||
|
* de l'id.
|
||||||
|
*/
|
||||||
|
constructor(center, radius, id) {
|
||||||
|
this.#center = center;
|
||||||
|
this.#radius = radius;
|
||||||
|
this.#color = BLACK;
|
||||||
|
this.#id = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @returns {Point} le point au centre au cercle
|
||||||
|
*/
|
||||||
|
getCenter(){
|
||||||
|
return this.#center;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @returns {number} le rayon du cercle
|
||||||
|
*/
|
||||||
|
getRadius(){
|
||||||
|
return this.#radius;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @returns {string} la couleur (hexadécimal) du cercle
|
||||||
|
*/
|
||||||
|
getColor(){
|
||||||
|
return this.#color;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {String} color la nouvelle couleur du cercle
|
||||||
|
*/
|
||||||
|
setColor(color){
|
||||||
|
this.#color = color;
|
||||||
|
}
|
||||||
|
|
||||||
|
setCenter(center){
|
||||||
|
this.#center = center;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @returns {number} l'id du cercle
|
||||||
|
*/
|
||||||
|
getId(){
|
||||||
|
return this.#id;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
toString(){
|
||||||
|
return `Cercle(${ this.#radius }, ${ this.getCenter().getX() }, ${ this.getCenter().getY() })`;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Dessine tous les cercles dans un svg. Cette fonction
|
||||||
|
* nettoye le svg avant d'ajouter les cercles.
|
||||||
|
*
|
||||||
|
* @param node {HTMLElement} un element svg
|
||||||
|
* @param circles {Circle[]} Les cercles à dessiner
|
||||||
|
*/
|
||||||
|
export function drawCircles(node, circles){
|
||||||
|
let svgCircles = [];
|
||||||
|
for(const circle of circles){
|
||||||
|
const attr = {
|
||||||
|
cx: circle.getCenter().getX(),
|
||||||
|
cy: circle.getCenter().getY(),
|
||||||
|
r: circle.getRadius(),
|
||||||
|
fill: `#${circle.getColor()}`,
|
||||||
|
|
||||||
|
};
|
||||||
|
svgCircles.push(m("circle", attr))
|
||||||
|
}
|
||||||
|
m.render(node, svgCircles);
|
||||||
|
}
|
||||||
|
|
||||||
|
function identity(x){
|
||||||
|
return x;
|
||||||
|
}
|
||||||
|
|
||||||
|
function functionOrDefault(fn){
|
||||||
|
if(typeof fn === 'function'){
|
||||||
|
return fn;
|
||||||
|
}
|
||||||
|
return identity;
|
||||||
|
}
|
||||||
|
|
||||||
|
function drawIcons(circle,
|
||||||
|
onClickUp,
|
||||||
|
onClickDown,
|
||||||
|
onClickLeft,
|
||||||
|
onClickRight,
|
||||||
|
onClickPaint){
|
||||||
|
return [
|
||||||
|
m("i.fa-solid.fa-arrow-up.is-clickable", {onclick: () => onClickUp(circle.getId())}),
|
||||||
|
m("i.fa-solid.fa-arrow-down.is-clickable", {onclick: () => onClickDown(circle.getId())}),
|
||||||
|
m("i.fa-solid.fa-arrow-left.is-clickable", {onclick: () => onClickLeft(circle.getId())}),
|
||||||
|
m("i.fa-solid.fa-arrow-right.is-clickable", {onclick: () => onClickRight(circle.getId())}),
|
||||||
|
m("i.fa-solid.fa-paint-roller.is-clickable", {onclick: () => onClickPaint(circle.getId())}),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param node {HTMLElement} un element tbody
|
||||||
|
* @param circles {Circle[]} Les cercles
|
||||||
|
* @param pointToString Argument optionnel qui doit être une fonction
|
||||||
|
* qui prend en paramêtre un Point et retourne un String qui
|
||||||
|
* représente le point.
|
||||||
|
* @param onClickUp Argument optionnel qui doit être une fonction
|
||||||
|
* qui sera appelée lorsque la flèche pointant vers le haut
|
||||||
|
* sera cliquée. L'id du cercle sera passé en argument de
|
||||||
|
* la fonction.
|
||||||
|
* @param onClickDown Argument optionnel qui doit être une fonction
|
||||||
|
* qui sera appelée lorsque la flèche pointant vers le bas
|
||||||
|
* sera cliquée. L'id du cercle sera passé en argument de
|
||||||
|
* la fonction.
|
||||||
|
* @param onClickLeft Argument optionnel qui doit être une fonction
|
||||||
|
* qui sera appelée lorsque la flèche pointant vers la gauche
|
||||||
|
* sera cliquée. L'id du cercle sera passé en argument de
|
||||||
|
* la fonction.
|
||||||
|
* @param onClickRight Argument optionnel qui doit être une fonction
|
||||||
|
* qui sera appelée lorsque la flèche pointant vers la droite
|
||||||
|
* sera cliquée. L'id du cercle sera passé en argument de
|
||||||
|
* la fonction.
|
||||||
|
* @param onClickPaint Argument optionnel qui doit être une fonction
|
||||||
|
* qui sera appelée lorsque l'icone peinture
|
||||||
|
* sera cliquée. L'id du cercle sera passé en argument de
|
||||||
|
* la fonction.
|
||||||
|
*/
|
||||||
|
export function populateTable(node,
|
||||||
|
circles,
|
||||||
|
onClickUp=undefined,
|
||||||
|
onClickDown=undefined,
|
||||||
|
onClickLeft=undefined,
|
||||||
|
onClickRight=undefined,
|
||||||
|
onClickPaint=undefined){
|
||||||
|
const rows = [];
|
||||||
|
for(const circle of circles){
|
||||||
|
const row =[m("td", circle.getId()),
|
||||||
|
m("td", circle.toString()),
|
||||||
|
m("td", drawIcons(circle,
|
||||||
|
functionOrDefault(onClickUp),
|
||||||
|
functionOrDefault(onClickDown),
|
||||||
|
functionOrDefault(onClickLeft),
|
||||||
|
functionOrDefault(onClickRight),
|
||||||
|
functionOrDefault(onClickPaint)))];
|
||||||
|
rows.push(m("tr", row))
|
||||||
|
}
|
||||||
|
m.render(node, rows);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Retourne une couleur de gris aléatoire à partir d'un nombre entier.
|
||||||
|
* @param i {number} (entier) qui sera utilisé comme "seed".
|
||||||
|
* @returns {string} une couleur hexadécimale
|
||||||
|
*/
|
||||||
|
export function randomColor(i){
|
||||||
|
const base = (i % 256).toString(16);
|
||||||
|
return `${base}${base}${base}`
|
||||||
|
}
|
||||||
Reference in new issue
Block a user