canvasframework 0.3.15 → 0.3.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,180 +1,166 @@
1
1
  import Component from '../core/Component.js';
2
+
2
3
  /**
3
- * Case à cocher
4
- * @class
5
- * @extends Component
6
- * @property {boolean} checked - État cochée
7
- * @property {string} label - Texte du label
8
- * @property {string} platform - Plateforme
9
- * @property {number} boxWidth - Largeur de la case
10
- * @property {number} boxHeight - Hauteur de la case
11
- * @property {Function} onChange - Callback au changement
4
+ * Checkbox Material & Cupertino (iOS-like)
12
5
  */
13
6
  class Checkbox extends Component {
14
- /**
15
- * Crée une instance de Checkbox
16
- * @param {CanvasFramework} framework - Framework parent
17
- * @param {Object} [options={}] - Options de configuration
18
- * @param {boolean} [options.checked=false] - État initial
19
- * @param {string} [options.label=''] - Texte du label
20
- * @param {Function} [options.onChange] - Callback au changement
21
- */
22
7
  constructor(framework, options = {}) {
23
8
  super(framework, options);
24
- this.checked = options.checked || false;
9
+
10
+ this.checked = !!options.checked;
25
11
  this.label = options.label || '';
26
12
  this.platform = framework.platform;
27
- this.boxWidth = 24; // Taille de la case
28
- this.boxHeight = 24; // Taille de la case
29
13
  this.onChange = options.onChange;
30
-
31
- // Calculer la largeur totale incluant le label
32
- this.totalWidth = this.label ? this.boxWidth + 8 + this.getTextWidth(this.label) : this.boxWidth;
33
- this.width = this.totalWidth; // Mettre à jour la largeur totale
34
- this.height = this.boxHeight; // Garder la même hauteur
35
-
36
- // Définir onClick
37
- this.onClick = this.handleClick.bind(this);
14
+
15
+ this.boxSize = 22;
16
+ this.padding = 10;
17
+
18
+ this.textWidth = this.label
19
+ ? this.getTextWidth(this.label)
20
+ : 0;
21
+
22
+ // Largeur totale
23
+ this.width =
24
+ this.platform === 'material'
25
+ ? this.boxSize + this.padding + this.textWidth
26
+ : this.textWidth + 28; // place pour checkmark iOS
27
+
28
+ this.height = 28;
29
+
30
+ this.onClick = () => {
31
+ this.checked = !this.checked;
32
+ this.onChange?.(this.checked);
33
+ };
38
34
  }
39
-
40
- /**
41
- * Calcule la largeur du texte
42
- * @param {string} text - Texte à mesurer
43
- * @returns {number} Largeur du texte
44
- * @private
45
- */
35
+
46
36
  getTextWidth(text) {
47
- // Utiliser le contexte temporaire pour mesurer le texte
48
37
  const ctx = this.framework.ctx;
49
38
  ctx.save();
50
- ctx.font = '16px -apple-system, sans-serif';
51
- const width = ctx.measureText(text).width;
39
+ ctx.font = '16px -apple-system, system-ui, sans-serif';
40
+ const w = ctx.measureText(text).width;
52
41
  ctx.restore();
53
- return width;
54
- }
55
-
56
- /**
57
- * Gère le clic sur la checkbox
58
- * @private
59
- */
60
- handleClick() {
61
- this.checked = !this.checked;
62
- if (this.onChange) this.onChange(this.checked);
42
+ return w;
63
43
  }
64
44
 
65
- /**
66
- * Dessine la checkbox
67
- * @param {CanvasRenderingContext2D} ctx - Contexte de dessin
68
- */
69
45
  draw(ctx) {
70
46
  ctx.save();
71
-
72
- // Position de la case
73
- const boxX = this.x;
74
- const boxY = this.y;
75
- const boxCenterX = boxX + this.boxWidth / 2;
76
- const boxCenterY = boxY + this.boxHeight / 2;
77
-
47
+ ctx.font = '16px -apple-system, system-ui, sans-serif';
48
+ ctx.textBaseline = 'middle';
49
+
50
+ const centerY = this.y + this.height / 2;
51
+
78
52
  if (this.platform === 'material') {
79
- // Material Design Checkbox
80
- if (this.checked) {
81
- // Case cochée
82
- ctx.fillStyle = '#6200EE';
83
- ctx.beginPath();
84
- this.roundRect(ctx, boxX, boxY, this.boxWidth, this.boxHeight, 2);
85
- ctx.fill();
86
-
87
- // Coche
88
- ctx.strokeStyle = '#FFFFFF';
89
- ctx.lineWidth = 2;
90
- ctx.beginPath();
91
- ctx.moveTo(boxX + 6, boxY + 12);
92
- ctx.lineTo(boxX + 10, boxY + 16);
93
- ctx.lineTo(boxX + 18, boxY + 8);
94
- ctx.stroke();
95
- } else {
96
- // Case non cochée
97
- ctx.strokeStyle = '#666666';
98
- ctx.lineWidth = 2;
99
- ctx.beginPath();
100
- this.roundRect(ctx, boxX, boxY, this.boxWidth, this.boxHeight, 2);
101
- ctx.stroke();
102
- }
53
+ this.drawMaterial(ctx, centerY);
103
54
  } else {
104
- // Cupertino (iOS) Checkbox
105
- if (this.checked) {
106
- // Case cochée (iOS utilise plutôt un cercle)
107
- ctx.fillStyle = '#007AFF';
108
- ctx.beginPath();
109
- ctx.arc(boxCenterX, boxCenterY, this.boxWidth/2, 0, Math.PI * 2);
110
- ctx.fill();
111
-
112
- // Coche
113
- ctx.strokeStyle = '#FFFFFF';
114
- ctx.lineWidth = 2;
115
- ctx.beginPath();
116
- ctx.moveTo(boxX + 6, boxCenterY);
117
- ctx.lineTo(boxX + 10, boxCenterY + 4);
118
- ctx.lineTo(boxX + 18, boxCenterY - 4);
119
- ctx.stroke();
120
- } else {
121
- // Case non cochée
122
- ctx.strokeStyle = '#C7C7CC';
123
- ctx.lineWidth = 2;
124
- ctx.beginPath();
125
- ctx.arc(boxCenterX, boxCenterY, this.boxWidth/2, 0, Math.PI * 2);
126
- ctx.stroke();
127
- }
55
+ this.drawCupertino(ctx, centerY);
128
56
  }
129
-
130
- // Label
131
- if (this.label) {
132
- ctx.fillStyle = '#000000';
133
- ctx.font = '16px -apple-system, sans-serif';
134
- ctx.textAlign = 'left';
135
- ctx.textBaseline = 'middle';
136
- ctx.fillText(this.label, boxX + this.boxWidth + 8, boxCenterY);
137
- }
138
-
57
+
139
58
  ctx.restore();
140
59
  }
141
60
 
142
- /**
143
- * Dessine un rectangle avec coins arrondis
144
- * @param {CanvasRenderingContext2D} ctx - Contexte de dessin
145
- * @param {number} x - Position X
146
- * @param {number} y - Position Y
147
- * @param {number} width - Largeur
148
- * @param {number} height - Hauteur
149
- * @param {number} radius - Rayon des coins
150
- * @private
151
- */
152
- roundRect(ctx, x, y, width, height, radius) {
61
+ /* ---------------- MATERIAL ---------------- */
62
+
63
+ drawMaterial(ctx, centerY) {
64
+ const x = this.x;
65
+ const y = centerY - this.boxSize / 2;
66
+
67
+ // Box
68
+ ctx.lineWidth = 2;
69
+ ctx.strokeStyle = this.checked ? '#6200EE' : '#757575';
70
+ ctx.fillStyle = this.checked ? '#6200EE' : 'transparent';
71
+
72
+ this.roundRect(ctx, x, y, this.boxSize, this.boxSize, 3);
73
+ if (this.checked) ctx.fill();
74
+ ctx.stroke();
75
+
76
+ // Check
77
+ if (this.checked) {
78
+ ctx.strokeStyle = '#FFF';
79
+ ctx.lineWidth = 2.4;
80
+ ctx.beginPath();
81
+ ctx.moveTo(x + 5, y + 12);
82
+ ctx.lineTo(x + 9, y + 16);
83
+ ctx.lineTo(x + 17, y + 7);
84
+ ctx.stroke();
85
+ }
86
+
87
+ // Label
88
+ ctx.fillStyle = '#000';
89
+ ctx.fillText(
90
+ this.label,
91
+ x + this.boxSize + this.padding,
92
+ centerY
93
+ );
94
+ }
95
+
96
+ /* ---------------- CUPERTINO ---------------- */
97
+
98
+ /* ---------------- CUPERTINO ---------------- */
99
+
100
+ drawCupertino(ctx, centerY) {
101
+ const radius = 10;
102
+ const circleX = this.x + radius;
103
+ const circleY = centerY;
104
+
105
+ // Cercle
106
+ if (this.checked) {
107
+ ctx.fillStyle = '#007AFF'; // Apple blue
153
108
  ctx.beginPath();
154
- ctx.moveTo(x + radius, y);
155
- ctx.lineTo(x + width - radius, y);
156
- ctx.quadraticCurveTo(x + width, y, x + width, y + radius);
157
- ctx.lineTo(x + width, y + height - radius);
158
- ctx.quadraticCurveTo(x + width, y + height, x + width - radius, y + height);
159
- ctx.lineTo(x + radius, y + height);
160
- ctx.quadraticCurveTo(x, y + height, x, y + height - radius);
161
- ctx.lineTo(x, y + radius);
162
- ctx.quadraticCurveTo(x, y, x + radius, y);
109
+ ctx.arc(circleX, circleY, radius, 0, Math.PI * 2);
110
+ ctx.fill();
111
+ } else {
112
+ ctx.strokeStyle = '#C7C7CC'; // iOS gray
113
+ ctx.lineWidth = 2;
114
+ ctx.beginPath();
115
+ ctx.arc(circleX, circleY, radius, 0, Math.PI * 2);
116
+ ctx.stroke();
117
+ }
118
+
119
+ // Checkmark
120
+ if (this.checked) {
121
+ ctx.strokeStyle = '#FFFFFF';
122
+ ctx.lineWidth = 2.2;
123
+ ctx.lineCap = 'round';
124
+ ctx.lineJoin = 'round';
125
+
126
+ ctx.beginPath();
127
+ ctx.moveTo(circleX - 4, circleY);
128
+ ctx.lineTo(circleX - 1, circleY + 3);
129
+ ctx.lineTo(circleX + 5, circleY - 4);
130
+ ctx.stroke();
131
+ }
132
+
133
+ // Label
134
+ ctx.fillStyle = '#000';
135
+ ctx.fillText(
136
+ this.label,
137
+ this.x + radius * 2 + this.padding,
138
+ centerY
139
+ );
140
+ }
141
+
142
+ roundRect(ctx, x, y, w, h, r) {
143
+ ctx.beginPath();
144
+ ctx.moveTo(x + r, y);
145
+ ctx.lineTo(x + w - r, y);
146
+ ctx.quadraticCurveTo(x + w, y, x + w, y + r);
147
+ ctx.lineTo(x + w, y + h - r);
148
+ ctx.quadraticCurveTo(x + w, y + h, x + w - r, y + h);
149
+ ctx.lineTo(x + r, y + h);
150
+ ctx.quadraticCurveTo(x, y + h, x, y + h - r);
151
+ ctx.lineTo(x, y + r);
152
+ ctx.quadraticCurveTo(x, y, x + r, y);
163
153
  ctx.closePath();
164
154
  }
165
-
166
- /**
167
- * Vérifie si un point est dans les limites
168
- * @param {number} x - Coordonnée X
169
- * @param {number} y - Coordonnée Y
170
- * @returns {boolean} True si le point est dans la checkbox
171
- */
155
+
172
156
  isPointInside(x, y) {
173
- return x >= this.x &&
174
- x <= this.x + this.width &&
175
- y >= this.y &&
176
- y <= this.y + this.height;
157
+ return (
158
+ x >= this.x &&
159
+ x <= this.x + this.width &&
160
+ y >= this.y &&
161
+ y <= this.y + this.height
162
+ );
177
163
  }
178
164
  }
179
165
 
180
- export default Checkbox;
166
+ export default Checkbox;
@@ -1,4 +1,9 @@
1
1
  import Component from '../core/Component.js';
2
+ import AndroidDatePickerDialog from '../components/AndroidDatePickerDialog.js';
3
+ import Modal from '../components/Modal.js';
4
+ import IOSDatePickerWheel from '../components/IOSDatePickerWheel.js';
5
+ import Button from '../components/Button.js';
6
+
2
7
  /**
3
8
  * Sélecteur de date (wrapper)
4
9
  * @class
@@ -61,6 +66,8 @@ class DatePicker extends Component {
61
66
  * Ouvre le sélecteur iOS
62
67
  * @private
63
68
  */
69
+
70
+
64
71
  openIOSPicker() {
65
72
  // Créer un modal avec le picker iOS
66
73
  const modal = new Modal(this.framework, {