summaryrefslogtreecommitdiff
path: root/addons/timer/static/src/js
diff options
context:
space:
mode:
Diffstat (limited to 'addons/timer/static/src/js')
-rw-r--r--addons/timer/static/src/js/timer.js63
-rw-r--r--addons/timer/static/src/js/timer_mixin.js115
-rw-r--r--addons/timer/static/src/js/timer_toggle_button.js76
3 files changed, 254 insertions, 0 deletions
diff --git a/addons/timer/static/src/js/timer.js b/addons/timer/static/src/js/timer.js
new file mode 100644
index 00000000000..0042ebfaead
--- /dev/null
+++ b/addons/timer/static/src/js/timer.js
@@ -0,0 +1,63 @@
+odoo.define('timer.timer', function (require) {
+"use strict";
+
+var fieldRegistry = require('web.field_registry');
+var AbstractField = require('web.AbstractField');
+var Timer = require('timer.Timer');
+
+var TimerFieldWidget = AbstractField.extend({
+
+ /**
+ * @override
+ * @private
+ */
+ isSet: function () {
+ return true;
+ },
+ /**
+ * @override
+ * @private
+ */
+ _render: function () {
+ this._super.apply(this, arguments);
+ this._startTimeCounter();
+ },
+ /**
+ * @override
+ */
+ destroy: function () {
+ this._super.apply(this, arguments);
+ clearInterval(this.timer);
+ },
+ /**
+ * @private
+ */
+ _startTimeCounter: async function () {
+ if (this.record.data.timer_start) {
+ const serverTime = this.record.data.timer_pause || await this._getServerTime();
+ this.time = Timer.createTimer(0, this.record.data.timer_start, serverTime);
+ this.$el.text(this.time.toString());
+ this.timer = setInterval(() => {
+ if (this.record.data.timer_pause) {
+ clearInterval(this.timer);
+ } else {
+ this.time.addSecond();
+ this.$el.text(this.time.toString());
+ }
+ }, 1000);
+ } else if (!this.record.data.timer_pause){
+ clearInterval(this.timer);
+ }
+ },
+ _getServerTime: function () {
+ return this._rpc({
+ model: 'timer.timer',
+ method: 'get_server_time',
+ args: []
+ });
+ }
+});
+
+fieldRegistry.add('timer_timer', TimerFieldWidget);
+
+});
diff --git a/addons/timer/static/src/js/timer_mixin.js b/addons/timer/static/src/js/timer_mixin.js
new file mode 100644
index 00000000000..779d06dbe4a
--- /dev/null
+++ b/addons/timer/static/src/js/timer_mixin.js
@@ -0,0 +1,115 @@
+odoo.define('timer.Timer', function (require) {
+"use strict";
+
+ /**
+ * This class improves the timer display using the
+ * unit_amount field on account.analytic.line.
+ */
+ class Timer {
+ constructor(hours, minutes, seconds) {
+ this.hours = hours;
+ this.minutes = minutes;
+ this.seconds = seconds;
+ }
+
+ /**
+ * Convert float to time
+ * @param {number} float
+ */
+ static convertFloatToTime(float) {
+ if (float === 0) {
+ return new Timer(0, 0, 0);
+ }
+
+ let minutes = float % 1;
+ const hours = float - minutes;
+ minutes *= 60;
+
+ return new Timer(hours, Math.round(minutes), 0);
+ }
+
+ /**
+ * Create timer
+ * @param {number} unit_amount
+ * @param {String} timer_start
+ * @param {String} serverTime
+ */
+ static createTimer(unit_amount, timer_start, serverTime) {
+ const timer = this.convertFloatToTime(unit_amount);
+
+ timer.addTime(
+ moment.utc(
+ moment.utc(serverTime)
+ .diff(moment.utc(timer_start))
+ ).format("HH:mm:ss")
+ );
+
+ return timer;
+ }
+
+ addHours(hours) {
+ this.hours += hours;
+ }
+
+ addMinutes(minutes) {
+ minutes += this.minutes;
+
+ this.minutes = minutes % 60;
+ this.addHours(Math.floor(minutes / 60));
+ }
+
+ addSeconds(seconds) {
+ seconds += this.seconds;
+ this.seconds = seconds % 60;
+ this.addMinutes(Math.floor(seconds / 60));
+ }
+
+ display2digits(number) {
+ return number > 9 ? "" + number : "0" + number;
+ }
+
+ addSecond() {
+ this.seconds += 1;
+ if (this.seconds === 60) {
+ this.minutes += 1;
+ this.seconds = 0;
+
+ if (this.minutes === 60) {
+ this.hours += 1;
+ this.minutes = 0;
+ }
+ }
+ }
+
+ addTime(time) {
+ if (typeof time == 'string' && time.indexOf(':') !== -1) {
+ let [hour, minute, second] = time.split(':');
+
+ hour = parseInt(hour);
+ minute = parseInt(minute);
+ second = parseInt(second);
+
+ this.addSeconds(second);
+ this.addMinutes(minute);
+ this.addHours(hour);
+ }
+ }
+
+ convertToFloat() {
+ return (this.hours * 60 + this.minutes) * 60 / 3600;
+ }
+
+ toString() {
+ const time = {
+ hours: this.display2digits(this.hours),
+ minutes: this.display2digits(this.minutes),
+ seconds: this.display2digits(this.seconds)
+ };
+
+ return `${time.hours}:${time.minutes}:${time.seconds}`;
+ }
+ }
+
+ return Timer;
+
+});
diff --git a/addons/timer/static/src/js/timer_toggle_button.js b/addons/timer/static/src/js/timer_toggle_button.js
new file mode 100644
index 00000000000..544c6219940
--- /dev/null
+++ b/addons/timer/static/src/js/timer_toggle_button.js
@@ -0,0 +1,76 @@
+odoo.define('timer.timer_toggle_button', function (require) {
+"use strict";
+
+const fieldRegistry = require('web.field_registry');
+const { FieldToggleBoolean } = require("web.basic_fields");
+
+/**
+ * The TimerToggleButton is used to display correctly the button
+ * to start or stop a timer for a timesheet in kanban, list and grid
+ * views.
+ */
+const TimerToggleButton = FieldToggleBoolean.extend({
+ /**
+ * @override
+ * @private
+ */
+ _render: function () {
+ // When the is_timer_running field is false, then the button is used to start the timer
+ const title = this.value ? 'stop' : 'play';
+ const name = this.value ? 'action_timer_stop' : 'action_timer_start';
+ const label = this.value ? 'stop' : 'start';
+
+ this.$('i')
+ .addClass('fa')
+ .toggleClass('fa-stop-circle o-timer-stop-button', this.value)
+ .toggleClass('fa-play-circle o-timer-play-button', !this.value)
+ .attr('title', title);
+
+ this.$el.addClass('o-timer-button');
+ this.$el.attr('title', title);
+ this.$el.attr('name', name);
+ this.$el.attr('aria-label', label);
+ this.$el.attr('aria-pressed', this.value);
+ this.$el.attr('type', 'button');
+ this.$el.attr('role', 'button');
+ },
+ /**
+ * Toggle the button
+ *
+ * When the user click on this button,
+ * - the action "action_timer_start" is called
+ * into the account.analytic.line model,
+ * if the value of is_timer_running field is set on false.
+ * - the action "action_timer_stop" is called
+ * into the account.analytic.line model,
+ * if the value of is_timer_running field is set on true.
+ * Then we change the value of the is_timer_running.
+ * @override
+ * @private
+ * @param {MouseEvent} event
+ */
+ _onToggleButton: async function (event) {
+ event.stopPropagation();
+ const result = await this._rpc({
+ model: this.model,
+ method: this._getActionButton(),
+ args: [this.res_id]
+ });
+
+ this.trigger_up('timer_changed', {
+ id: this.res_id,
+ is_timer_running: !this.value
+ });
+
+ this._setValue(!this.value);
+ },
+ _getActionButton: function () {
+ return this.value ? 'action_timer_stop' : 'action_timer_start';
+ }
+});
+
+fieldRegistry.add('timer_toggle_button', TimerToggleButton);
+
+return TimerToggleButton;
+
+});