remote-calibrator 0.3.0-rc.3 → 0.5.0-beta.10

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.
Files changed (58) hide show
  1. package/CHANGELOG.md +35 -3
  2. package/README.md +34 -49
  3. package/homepage/example.css +4 -3
  4. package/homepage/example.js +42 -22
  5. package/homepage/index.html +19 -4
  6. package/i18n/fetch-languages-sheets.js +11 -1
  7. package/lib/RemoteCalibrator.min.js +1 -1
  8. package/lib/RemoteCalibrator.min.js.LICENSE.txt +19 -2
  9. package/lib/RemoteCalibrator.min.js.map +1 -1
  10. package/netlify.toml +1 -1
  11. package/package.json +25 -24
  12. package/src/WebGazer4RC/package-lock.json +198 -143
  13. package/src/WebGazer4RC/package.json +2 -2
  14. package/src/WebGazer4RC/src/index.mjs +161 -52
  15. package/src/WebGazer4RC/test/webgazer_test.js +1 -1
  16. package/src/check/checkScreenSize.js +84 -0
  17. package/src/components/buttons.js +21 -4
  18. package/src/components/input.js +82 -0
  19. package/src/components/keyBinder.js +5 -6
  20. package/src/components/language.js +5 -0
  21. package/src/components/mediaPermission.js +21 -0
  22. package/src/components/onCanvas.js +2 -2
  23. package/src/components/sound.js +30 -2
  24. package/src/components/swalOptions.js +6 -3
  25. package/src/components/utils.js +27 -1
  26. package/src/components/video.js +9 -6
  27. package/src/const.js +15 -0
  28. package/src/core.js +103 -48
  29. package/src/css/buttons.scss +34 -7
  30. package/src/css/components.scss +57 -0
  31. package/src/css/distance.scss +71 -1
  32. package/src/css/gaze.css +9 -5
  33. package/src/css/main.css +22 -6
  34. package/src/css/panel.scss +33 -3
  35. package/src/css/screenSize.css +6 -5
  36. package/src/css/swal.css +1 -1
  37. package/src/css/video.scss +19 -0
  38. package/src/distance/distance.js +194 -41
  39. package/src/distance/distanceCheck.js +241 -0
  40. package/src/distance/distanceTrack.js +165 -68
  41. package/src/{interpupillaryDistance.js → distance/interPupillaryDistance.js} +27 -19
  42. package/src/gaze/gaze.js +4 -7
  43. package/src/gaze/gazeAccuracy.js +9 -4
  44. package/src/gaze/gazeCalibration.js +14 -4
  45. package/src/gaze/gazeTracker.js +40 -9
  46. package/src/i18n.js +1 -1
  47. package/src/index.js +7 -2
  48. package/src/media/two-side-arrow.svg +1 -0
  49. package/src/media/two-sided-horizontal.svg +1 -0
  50. package/src/media/two-sided-vertical.svg +3 -0
  51. package/src/panel.js +130 -65
  52. package/src/screenSize.js +38 -5
  53. package/webpack.config.js +7 -4
  54. package/media/measureDistance.png +0 -0
  55. package/media/panel.png +0 -0
  56. package/media/screenSize.png +0 -0
  57. package/media/trackGaze.png +0 -0
  58. package/src/displaySize.js +0 -28
@@ -7,6 +7,34 @@ const feedbackSynth = new Synth({
7
7
  envelope: { attack: 0.001, decay: 0.001, sustain: 1, release: 0.001 },
8
8
  }).connect(new Volume(-17).toDestination())
9
9
 
10
- export const soundFeedback = () => {
11
- feedbackSynth.triggerAttackRelease(2000, 0.05)
10
+ const softFeedbackSynth = new Synth({
11
+ oscillator: {
12
+ type: 'sine',
13
+ },
14
+ }).connect(new Volume(-5).toDestination())
15
+
16
+ export const soundFeedback = (style = 0) => {
17
+ switch (style) {
18
+ case 0:
19
+ feedbackSynth.triggerAttackRelease(2000, 0.05)
20
+ return
21
+
22
+ case 1:
23
+ // Negative feedback
24
+ feedbackSynth.triggerAttackRelease(500, 0.5)
25
+ return
26
+
27
+ case 2:
28
+ // Purr
29
+ feedbackSynth.triggerAttackRelease(200, 0.6)
30
+ return
31
+
32
+ case 3:
33
+ softFeedbackSynth.triggerAttackRelease(200, 0.2)
34
+ return
35
+
36
+ default:
37
+ feedbackSynth.triggerAttackRelease(2000, 0.05)
38
+ return
39
+ }
12
40
  }
@@ -1,8 +1,8 @@
1
1
  import { phrases } from '../i18n'
2
2
 
3
- export const swalInfoOptions = RC => {
3
+ export const swalInfoOptions = (RC, { showIcon }) => {
4
4
  return {
5
- icon: 'info',
5
+ icon: showIcon ? 'info' : undefined,
6
6
  allowEscapeKey: false,
7
7
  allowEnterKey: false,
8
8
  allowOutsideClick: false,
@@ -10,6 +10,7 @@ export const swalInfoOptions = RC => {
10
10
  confirmButtonText: phrases.RC_ok[RC.L],
11
11
  showClass: {
12
12
  popup: 'animate__animated animate__fadeInUp',
13
+ icon: '',
13
14
  // backdrop: 'animate__animated animate__fadeIn',
14
15
  },
15
16
  hideClass: {
@@ -19,9 +20,11 @@ export const swalInfoOptions = RC => {
19
20
  iconColor: RC._CONST.COLOR.ORANGE,
20
21
  confirmButtonColor: '#aaa',
21
22
  customClass: {
23
+ popup: 'my__swal2__container',
22
24
  icon: 'my__swal2__icon',
23
25
  title: 'my__swal2__title',
24
- htmlContainer: 'my__swal2__html',
26
+ htmlContainer: 'my__swal2__html' + ` rc-lang-${RC.LD.toLowerCase()}`,
27
+ confirmButton: 'rc-button rc-go-button',
25
28
  },
26
29
  }
27
30
  }
@@ -68,6 +68,12 @@
68
68
  }
69
69
  })()
70
70
 
71
+ export function safeExecuteFunc(f, ...a) {
72
+ if (f && typeof f === 'function')
73
+ if (a.length) f(...a)
74
+ else f()
75
+ }
76
+
71
77
  // http://stackoverflow.com/questions/951021/what-is-the-javascript-version-of-sleep
72
78
  export function sleep(time) {
73
79
  return new Promise(resolve => setTimeout(resolve, time))
@@ -86,16 +92,33 @@ export function getFullscreen() {
86
92
  const element = document.documentElement
87
93
  if (element.requestFullscreen) {
88
94
  element.requestFullscreen()
95
+ return true
89
96
  } else if (element.mozRequestFullScreen) {
90
97
  element.mozRequestFullScreen()
98
+ return true
91
99
  } else if (element.webkitRequestFullscreen) {
92
100
  element.webkitRequestFullscreen()
101
+ return true
93
102
  } else if (element.msRequestFullscreen) {
94
103
  element.msRequestFullscreen()
104
+ return true
105
+ } else {
106
+ return false
95
107
  }
108
+ } else {
109
+ return false
96
110
  }
97
111
  }
98
112
 
113
+ export function isFullscreen() {
114
+ return (
115
+ Math.abs(window.innerHeight - screen.height) < 5 &&
116
+ Math.abs(window.innerWidth - screen.width) < 5 &&
117
+ window.screenX < 5 &&
118
+ window.screenY < 5
119
+ )
120
+ }
121
+
99
122
  /* -------------------------------------------------------------------------- */
100
123
 
101
124
  export function constructInstructions(
@@ -127,7 +150,7 @@ export function dist2d(aX, aY, bX, bY) {
127
150
  return Math.sqrt(Math.pow(aX - bX, 2) + Math.pow(aY - bY, 2))
128
151
  }
129
152
 
130
- // https://stackoverflow.com/a/12646864/11069914
153
+ // https://stackoverflow.com/a/12646864
131
154
  export function shuffle(array) {
132
155
  for (let i = array.length - 1; i > 0; i--) {
133
156
  const j = Math.floor(Math.random() * (i + 1))
@@ -148,6 +171,9 @@ export const median = arr => {
148
171
  return arr.length % 2 !== 0 ? num[mid] : (num[mid - 1] + num[mid]) / 2
149
172
  }
150
173
 
174
+ // https://stackoverflow.com/a/41452260
175
+ export const average = array => array.reduce((a, b) => a + b) / array.length
176
+
151
177
  /**
152
178
  *
153
179
  * BLUR ALL
@@ -1,4 +1,6 @@
1
- // Only one video for all functions
1
+ /* Only one video for all functions */
2
+
3
+ import { safeExecuteFunc } from './utils'
2
4
 
3
5
  export function addVideoElementsToBody() {
4
6
  let v = document.querySelector('video')
@@ -33,7 +35,7 @@ export function startVideo(videoElement, callback) {
33
35
  videoElement.play()
34
36
 
35
37
  // ! CALLBACK
36
- if (callback) callback(stream)
38
+ safeExecuteFunc(callback, stream)
37
39
  },
38
40
  err => console.error(err)
39
41
  )
@@ -82,17 +84,18 @@ export function checkWebgazerReady(RC, pipWidthPx, opacity, WG, callback) {
82
84
  // Set position
83
85
  setDefaultVideoPosition(RC, v)
84
86
 
85
- // Give callback after 2 sec
87
+ // Give callback after 0.5 sec
86
88
  setTimeout(() => {
89
+ RC.videoOpacity()
87
90
  if (RC.isMobile.value)
88
91
  v.style.transition = `right 0.5s, top 0.5s, width 0.5s, height 0.5s, border-radius 0.5s`
89
92
  else
90
93
  v.style.transition = `left 0.5s, bottom 0.5s, width 0.5s, height 0.5s, border-radius 0.5s`
91
- callback()
92
- }, 1000)
94
+ safeExecuteFunc(callback)
95
+ }, 700)
93
96
  clearInterval(c)
94
97
  }
95
- }, 200)
98
+ }, 50)
96
99
  }
97
100
 
98
101
  export function setDefaultVideoPosition(RC, v) {
package/src/const.js CHANGED
@@ -12,6 +12,8 @@ RemoteCalibrator.prototype._CONST = Object.freeze({
12
12
  MARGIN: 10,
13
13
  BORDER: 8,
14
14
  },
15
+ PPI_DONT_USE: 127.7,
16
+ PD_DONT_USE: 6.4,
15
17
  },
16
18
  S: {
17
19
  AUTO: 'AUTO',
@@ -24,5 +26,18 @@ RemoteCalibrator.prototype._CONST = Object.freeze({
24
26
  LIGHT_GREY: '#cccccc',
25
27
  ORANGE: '#ff9a00',
26
28
  DARK_RED: '#ac0d0d',
29
+ RED: '#ee0000',
30
+ },
31
+ LTR: 'LTR',
32
+ RTL: 'RTL',
33
+ VIEW_METHOD: {
34
+ B: 'BlindSpot',
35
+ F: 'FaceMesh',
36
+ },
37
+ IN_TO_CM: 2.54,
38
+ UNITS: {
39
+ CM: 'cm',
40
+ IN_D: 'inDecimal',
41
+ IN_F: 'inFractional',
27
42
  },
28
43
  })
package/src/core.js CHANGED
@@ -13,16 +13,27 @@ import {
13
13
  getFullscreen,
14
14
  blurAll,
15
15
  constructInstructions,
16
+ isFullscreen,
17
+ safeExecuteFunc,
16
18
  } from './components/utils'
17
19
  import { looseSetLanguage } from './components/language'
18
20
  import { phrases } from './i18n'
21
+ import isEqual from 'react-fast-compare'
19
22
 
20
23
  class RemoteCalibrator {
21
24
  constructor() {
22
25
  this._initialized = false
23
26
 
24
- this._hasPanel = false
25
- this._panelFinished = false
27
+ this._id = null
28
+
29
+ this._lang = null // A single string, e.g., 'en-US'
30
+ this._langData = []
31
+
32
+ this._panelStatus = {
33
+ hasPanel: false,
34
+ panelFinished: false,
35
+ panelResolveIntervals: [],
36
+ }
26
37
  this._panel = {
27
38
  panel: null,
28
39
  panelObserver: null,
@@ -33,10 +44,30 @@ class RemoteCalibrator {
33
44
  panelResolve: null,
34
45
  }
35
46
 
36
- this._id = null
47
+ // Calibration check
48
+ this._participantCheckEquipment = {
49
+ has: null,
50
+ equipment: null,
51
+ unit: null,
52
+ }
37
53
 
38
- this._lang = null // A single string, e.g., 'en-US'
39
- this._langData = []
54
+ // Are we calibrating for setting up gaze or distance tracking?
55
+ this._trackingSetupFinishedStatus = {
56
+ gaze: true,
57
+ distance: true,
58
+ }
59
+ this._distanceTrackNudging = {
60
+ distanceCorrecting: null, // setInterval
61
+ distanceCorrectEnabled: false, // Whether to correct or not, used for endNudger
62
+ distanceDesired: null,
63
+ distanceAllowedRatio: null,
64
+ }
65
+ this._tackingVideoFrameTimestamps = {
66
+ gaze: 0,
67
+ distance: 0,
68
+ }
69
+
70
+ // ! DATA
40
71
 
41
72
  this._environmentData = []
42
73
 
@@ -52,11 +83,20 @@ class RemoteCalibrator {
52
83
  // Status
53
84
  this._fullscreenData = []
54
85
 
86
+ // Check
87
+ this._equipmentData = []
88
+
89
+ ////
90
+
55
91
  this._background = {
56
92
  element: null,
57
93
  instructionElement: null,
58
94
  }
59
95
 
96
+ this._nudger = {
97
+ element: null,
98
+ }
99
+
60
100
  this._params = {
61
101
  backgroundColor: '#eee',
62
102
  videoOpacity: 0.8,
@@ -64,6 +104,11 @@ class RemoteCalibrator {
64
104
  }
65
105
 
66
106
  this.deviceDetector = new DeviceDetector()
107
+
108
+ window.console.log(
109
+ `%c\nEasyEyes Remote Calibrator ${this.version.value}\n`,
110
+ `color: ${this._CONST.COLOR.ORANGE}`
111
+ )
67
112
  }
68
113
 
69
114
  /* --------------------------------- GETTERS -------------------------------- */
@@ -76,6 +121,10 @@ class RemoteCalibrator {
76
121
  return this._background.instructionElement
77
122
  }
78
123
 
124
+ get nudger() {
125
+ return this._nudger.element
126
+ }
127
+
79
128
  // PARAMS
80
129
 
81
130
  get params() {
@@ -127,6 +176,10 @@ class RemoteCalibrator {
127
176
  return this._lang
128
177
  }
129
178
 
179
+ get LD() {
180
+ return this.languageDirection.value
181
+ }
182
+
130
183
  get language() {
131
184
  return this._helper_get(this._langData, 'language')
132
185
  }
@@ -150,40 +203,36 @@ class RemoteCalibrator {
150
203
  // Status
151
204
 
152
205
  get isFullscreen() {
153
- return {
154
- value:
155
- Math.abs(window.innerHeight - screen.height) < 5 &&
156
- Math.abs(window.innerWidth - screen.width) < 5 &&
157
- window.screenX < 5 &&
158
- window.screenY < 5,
159
- timestamp: new Date(),
160
- }
206
+ if (
207
+ !this.fullscreenData.length ||
208
+ !isEqual(isFullscreen(), this._helper_get(this._fullscreenData).value)
209
+ )
210
+ this.newFullscreenData = {
211
+ value: isFullscreen(),
212
+ timestamp: new Date(),
213
+ }
214
+ return this._helper_get(this._fullscreenData)
161
215
  }
162
216
 
163
217
  // Environment
164
218
 
165
219
  get bot() {
166
- if (!this._environmentData.length) this.environment()
167
220
  return this._helper_get(this._environmentData, 'bot')
168
221
  }
169
222
 
170
223
  get browser() {
171
- if (!this._environmentData.length) this.environment()
172
224
  return this._helper_get(this._environmentData, 'browser')
173
225
  }
174
226
 
175
227
  get browserVersion() {
176
- if (!this._environmentData.length) this.environment()
177
228
  return this._helper_get(this._environmentData, 'browserVersion')
178
229
  }
179
230
 
180
231
  get deviceType() {
181
- if (!this._environmentData.length) this.environment()
182
232
  return this._helper_get(this._environmentData, 'deviceType')
183
233
  }
184
234
 
185
235
  get isMobile() {
186
- if (!this._environmentData.length) this.environment()
187
236
  const d = this._helper_get(this._environmentData, 'deviceType')
188
237
  return {
189
238
  value: d.value !== 'desktop',
@@ -192,64 +241,60 @@ class RemoteCalibrator {
192
241
  }
193
242
 
194
243
  get model() {
195
- if (!this._environmentData.length) this.environment()
196
244
  return this._helper_get(this._environmentData, 'model')
197
245
  }
198
246
 
199
247
  get manufacturer() {
200
- if (!this._environmentData.length) this.environment()
201
248
  return this._helper_get(this._environmentData, 'manufacturer')
202
249
  }
203
250
 
204
251
  get engine() {
205
- if (!this._environmentData.length) this.environment()
206
252
  return this._helper_get(this._environmentData, 'engine')
207
253
  }
208
254
 
209
255
  get system() {
210
- if (!this._environmentData.length) this.environment()
211
256
  return this._helper_get(this._environmentData, 'system')
212
257
  }
213
258
 
214
259
  get systemFamily() {
215
- if (!this._environmentData.length) this.environment()
216
260
  return this._helper_get(this._environmentData, 'systemFamily')
217
261
  }
218
262
 
219
263
  get description() {
220
- if (!this._environmentData.length) this.environment()
221
264
  return this._helper_get(this._environmentData, 'description')
222
265
  }
223
266
 
224
267
  get fullDescription() {
225
- if (!this._environmentData.length) this.environment()
226
268
  return this._helper_get(this._environmentData, 'fullDescription')
227
269
  }
228
270
 
229
271
  get userLanguage() {
230
- if (!this._environmentData.length) this.environment()
231
272
  return this._helper_get(this._environmentData, 'userLanguage')
232
273
  }
233
274
 
275
+ get equipment() {
276
+ return this._helper_get(this._equipmentData)
277
+ }
278
+
234
279
  // Screen
235
280
 
236
281
  get displayWidthPx() {
237
- if (!this._displayData.length) this.displaySize()
282
+ this._displaySize()
238
283
  return this._helper_get(this._displayData, 'displayWidthPx')
239
284
  }
240
285
 
241
286
  get displayHeightPx() {
242
- if (!this._displayData.length) this.displaySize()
287
+ this._displaySize()
243
288
  return this._helper_get(this._displayData, 'displayHeightPx')
244
289
  }
245
290
 
246
291
  get windowWidthPx() {
247
- if (!this._displayData.length) this.displaySize()
292
+ this._displaySize()
248
293
  return this._helper_get(this._displayData, 'windowWidthPx')
249
294
  }
250
295
 
251
296
  get windowHeightPx() {
252
- if (!this._displayData.length) this.displaySize()
297
+ this._displaySize()
253
298
  return this._helper_get(this._displayData, 'windowHeightPx')
254
299
  }
255
300
 
@@ -327,7 +372,7 @@ class RemoteCalibrator {
327
372
  return this._gazePositionData
328
373
  }
329
374
 
330
- get fullScreenData() {
375
+ get fullscreenData() {
331
376
  return this._fullscreenData
332
377
  }
333
378
 
@@ -410,6 +455,13 @@ class RemoteCalibrator {
410
455
  set newLanguageData(data) {
411
456
  this._langData.push(data)
412
457
  }
458
+
459
+ /**
460
+ * @param {{ value: { has: boolean; unit: string; equipment: string; }; timestamp: Date; }} data
461
+ */
462
+ set newEquipmentData(data) {
463
+ this._equipmentData.push(data)
464
+ }
413
465
  }
414
466
 
415
467
  /**
@@ -436,7 +488,8 @@ RemoteCalibrator.prototype.init = function (options = {}, callback) {
436
488
  timestamp: new Date(),
437
489
  }
438
490
 
439
- this.environment()
491
+ this._environment()
492
+ this._displaySize()
440
493
 
441
494
  if (this._CONST.S.AUTO === options.language)
442
495
  // AUTO
@@ -444,7 +497,7 @@ RemoteCalibrator.prototype.init = function (options = {}, callback) {
444
497
  else this.newLanguageData = looseSetLanguage(options.language)
445
498
  this._lang = this.language.value
446
499
 
447
- if (callback && typeof callback === 'function') callback(this._id)
500
+ safeExecuteFunc(callback, this._id)
448
501
  }
449
502
  }
450
503
 
@@ -453,13 +506,20 @@ RemoteCalibrator.prototype.init = function (options = {}, callback) {
453
506
  * Get the environment data, e.g. browser type
454
507
  *
455
508
  */
456
- RemoteCalibrator.prototype.environment = function (callback) {
509
+ RemoteCalibrator.prototype._environment = function () {
457
510
  if (this.checkInitialized()) {
458
511
  blurAll()
459
512
 
460
513
  const device = this.deviceDetector.parse(platform.ua)
461
514
  const bot = device.bot
462
515
 
516
+ if (!device.device)
517
+ device.device = {
518
+ type: null,
519
+ model: null,
520
+ brand: null,
521
+ }
522
+
463
523
  const data = {
464
524
  value: {
465
525
  bot: bot
@@ -482,8 +542,6 @@ RemoteCalibrator.prototype.environment = function (callback) {
482
542
  }
483
543
 
484
544
  this.newEnvironmentData = data
485
-
486
- if (callback) callback(data)
487
545
  }
488
546
  }
489
547
 
@@ -503,25 +561,20 @@ RemoteCalibrator.prototype.checkInitialized = function () {
503
561
  * @param {Boolean} f Get fullscreen or not from options
504
562
  */
505
563
  RemoteCalibrator.prototype.getFullscreen = function (f = true) {
506
- if (
507
- window.fullScreen ||
508
- (window.innerWidth === screen.width && window.innerHeight === screen.height)
509
- ) {
564
+ if (isFullscreen()) {
510
565
  return true
511
566
  }
512
567
 
513
- if (f && !debug) getFullscreen()
568
+ this.newFullscreenData = {
569
+ value: f && !debug ? getFullscreen() : false,
570
+ timestamp: new Date(),
571
+ }
514
572
 
515
573
  // Minimize address bar on mobile devices
516
574
  // ! Experimental
517
575
  if (this.isMobile.value) window.scrollBy(0, 1)
518
576
 
519
- this.newFullscreenData = {
520
- value: f && !debug,
521
- timestamp: new Date(),
522
- }
523
-
524
- return f && !debug
577
+ return this.isFullscreen
525
578
  }
526
579
 
527
580
  /**
@@ -548,6 +601,7 @@ RemoteCalibrator.prototype._addBackground = function (inner) {
548
601
  if (!b) {
549
602
  b = document.createElement('div')
550
603
  b.id = 'calibration-background'
604
+ b.className = 'calibration-background' + ` rc-lang-${this.LD.toLowerCase()}`
551
605
 
552
606
  document.body.classList.add('lock-view')
553
607
  document.body.appendChild(b)
@@ -556,8 +610,9 @@ RemoteCalibrator.prototype._addBackground = function (inner) {
556
610
  }
557
611
 
558
612
  if (inner) b.innerHTML = inner
559
-
560
613
  this._background.element = b
614
+
615
+ return this.background
561
616
  }
562
617
 
563
618
  /**
@@ -1,29 +1,56 @@
1
1
  .rc-buttons {
2
+ z-index: 10;
3
+ }
4
+
5
+ .rc-absolute-buttons {
2
6
  position: fixed;
7
+ text-align: right;
3
8
  bottom: 1.25rem;
4
9
  right: 1.25rem;
5
- z-index: 900000;
6
10
  }
7
11
 
8
12
  .rc-button {
9
- text-align: center;
13
+ text-align: center !important;
10
14
  border: none !important;
11
- background: #ffffffee;
12
15
  line-height: 150% !important;
13
16
  font-size: 1rem !important;
14
17
  font-weight: 700 !important;
15
- color: #333;
16
18
  padding: 1rem 1.5rem !important;
17
19
  margin: 0.25rem !important;
18
20
  border-radius: 7px !important;
19
21
  cursor: pointer;
22
+ }
23
+
24
+ .rc-go-button {
25
+ background: #ff9a00aa !important;
26
+ color: #fff !important;
27
+
28
+ &:hover {
29
+ background: #ff9a00 !important;
30
+ }
31
+
32
+ &:active {
33
+ background: #d68200 !important;
34
+ }
35
+ }
36
+
37
+ .rc-cancel-button,
38
+ .rc-custom-button {
39
+ background: #ffffffee !important;
40
+ color: #333 !important;
20
41
 
21
42
  &:hover {
22
- background: #ddd;
43
+ background: #ddd !important;
23
44
  }
24
45
 
25
46
  &:active {
26
- background: #aaa;
27
- color: #000;
47
+ background: #aaa !important;
48
+ color: #000 !important;
28
49
  }
29
50
  }
51
+
52
+ .rc-button:disabled {
53
+ background: #ddd !important;
54
+ color: #999 !important;
55
+ cursor: default !important;
56
+ }
@@ -0,0 +1,57 @@
1
+ .my__swal2__container .swal2-select {
2
+ font-family: inherit !important;
3
+ border-radius: 5px !important;
4
+ border: 2px solid #aaa !important;
5
+ outline: none !important;
6
+ }
7
+
8
+ /* -------------------------------------------------------------------------- */
9
+ /* Measure Input */
10
+ /* -------------------------------------------------------------------------- */
11
+
12
+ .rc-form {
13
+ font-size: 2rem;
14
+ font-family: inherit;
15
+
16
+ .rc-form-inputs {
17
+ display: flex;
18
+ justify-content: space-between !important;
19
+ margin: 1rem 0;
20
+
21
+ .rc-form-input,
22
+ span {
23
+ flex-grow: 1;
24
+ padding: 0.5rem;
25
+ font-family: inherit;
26
+ font-size: inherit;
27
+ }
28
+
29
+ span {
30
+ font-weight: 700;
31
+ }
32
+ }
33
+
34
+ .rc-form-input {
35
+ border: 2px solid #aaa;
36
+ outline: none;
37
+ border-radius: 5px;
38
+ width: min(100%, 10rem);
39
+
40
+ &.rc-input-error {
41
+ border-color: #ac0d0d !important;
42
+ color: #ac0d0d !important;
43
+ }
44
+ }
45
+ }
46
+
47
+ .arrow-two-sided-svg {
48
+ position: fixed;
49
+ width: 100%;
50
+ bottom: 10%;
51
+ left: 0;
52
+ right: 0;
53
+
54
+ .arrow-two-sided {
55
+ fill: #ff9a00;
56
+ }
57
+ }