diff options
| author | stephanchrst <stephanchrst@gmail.com> | 2022-05-10 21:51:50 +0700 |
|---|---|---|
| committer | stephanchrst <stephanchrst@gmail.com> | 2022-05-10 21:51:50 +0700 |
| commit | 3751379f1e9a4c215fb6eb898b4ccc67659b9ace (patch) | |
| tree | a44932296ef4a9b71d5f010906253d8c53727726 /addons/hr_timesheet/static/src | |
| parent | 0a15094050bfde69a06d6eff798e9a8ddf2b8c21 (diff) | |
initial commit 2
Diffstat (limited to 'addons/hr_timesheet/static/src')
7 files changed, 309 insertions, 0 deletions
diff --git a/addons/hr_timesheet/static/src/js/qr_code_action.js b/addons/hr_timesheet/static/src/js/qr_code_action.js new file mode 100644 index 00000000..15419a1f --- /dev/null +++ b/addons/hr_timesheet/static/src/js/qr_code_action.js @@ -0,0 +1,19 @@ +odoo.define('hr_timesheet.qr_code_action', function (require) { + "use strict"; + +const AbstractAction = require('web.AbstractAction'); +const core = require('web.core'); +const config = require('web.config'); + +const QRModalAction = AbstractAction.extend({ + template: 'hr_timesheet_qr_code', + xmlDependencies: ['/hr_timesheet/static/src/xml/qr_modal_template.xml'], + + init: function(parent, action){ + this._super.apply(this, arguments); + this.url = _.str.sprintf("/report/barcode/?type=QR&value=%s&width=256&height=256&humanreadable=1", action.params.url); + }, +}); + +core.action_registry.add('timesheet_qr_code_modal', QRModalAction); +}); diff --git a/addons/hr_timesheet/static/src/js/task_with_hours.js b/addons/hr_timesheet/static/src/js/task_with_hours.js new file mode 100644 index 00000000..d2ed5a64 --- /dev/null +++ b/addons/hr_timesheet/static/src/js/task_with_hours.js @@ -0,0 +1,36 @@ +odoo.define('hr_timesheet.task_with_hours', function (require) { +"use strict"; + +var field_registry = require('web.field_registry'); +var relational_fields = require('web.relational_fields'); +var FieldMany2One = relational_fields.FieldMany2One; + +var TaskWithHours = FieldMany2One.extend({ + /** + * @override + */ + init: function () { + this._super.apply(this, arguments); + this.additionalContext.hr_timesheet_display_remaining_hours = true; + }, + /** + * @override + */ + _getDisplayNameWithoutHours: function (value) { + return value.split(' ‒ ')[0]; + }, + /** + * @override + * @private + */ + _renderEdit: function (){ + this.m2o_value = this._getDisplayNameWithoutHours(this.m2o_value); + this._super.apply(this, arguments); + }, +}); + +field_registry.add('task_with_hours', TaskWithHours); + +return TaskWithHours; + +});
\ No newline at end of file diff --git a/addons/hr_timesheet/static/src/js/timesheet_config_form_view.js b/addons/hr_timesheet/static/src/js/timesheet_config_form_view.js new file mode 100644 index 00000000..3ab983ba --- /dev/null +++ b/addons/hr_timesheet/static/src/js/timesheet_config_form_view.js @@ -0,0 +1,55 @@ +odoo.define('hr_timesheet.res.config.form', function (require) { + "use strict"; + + const core = require('web.core'); + const config = require('web.config'); + const viewRegistry = require('web.view_registry'); + const BaseSetting = require('base.settings'); + + const _t = core._t; + + const TimesheetConfigQRCodeMixin = { + async _renderView() { + const self = this; + await this._super(...arguments); + const google_url = "https://play.google.com/store/apps/details?id=com.odoo.OdooTimesheets"; + const apple_url = "https://apps.apple.com/be/app/awesome-timesheet/id1078657549"; + const action_desktop = { + name: _t('Download our App'), + type: 'ir.actions.client', + tag: 'timesheet_qr_code_modal', + target: 'new', + }; + this.$el.find('img.o_config_app_store').on('click', function(event) { + event.preventDefault(); + if (!config.device.isMobile) { + self.do_action(_.extend(action_desktop, {params: {'url': apple_url}})); + } else { + self.do_action({type: 'ir.actions.act_url', url: apple_url}); + } + }); + this.$el.find('img.o_config_play_store').on('click', function(event) { + event.preventDefault(); + if (!config.device.isMobile) { + self.do_action(_.extend(action_desktop, {params: {'url': google_url}})); + } else { + self.do_action({type: 'ir.actions.act_url', url: google_url}); + } + }); + }, + }; + + + var TimesheetConfigFormRenderer = BaseSetting.Renderer.extend(TimesheetConfigQRCodeMixin); + const BaseSettingView = viewRegistry.get('base_settings'); + var TimesheetConfigFormView = BaseSettingView.extend({ + config: _.extend({}, BaseSettingView.prototype.config, { + Renderer : TimesheetConfigFormRenderer, + }), + }); + + viewRegistry.add('hr_timesheet_config_form', TimesheetConfigFormView); + + return {TimesheetConfigQRCodeMixin, TimesheetConfigFormRenderer, TimesheetConfigFormView}; + +}); diff --git a/addons/hr_timesheet/static/src/js/timesheet_factor.js b/addons/hr_timesheet/static/src/js/timesheet_factor.js new file mode 100644 index 00000000..def165e0 --- /dev/null +++ b/addons/hr_timesheet/static/src/js/timesheet_factor.js @@ -0,0 +1,20 @@ +odoo.define('hr_timesheet.timesheet_factor', function (require) { +'use strict'; + +const timesheetUomFields = require('hr_timesheet.timesheet_uom'); +const fieldUtils = require('web.field_utils'); +const fieldRegistry = require('web.field_registry'); + +fieldRegistry.add('timesheet_factor', timesheetUomFields.FieldTimesheetFactor); + +fieldUtils.format.timesheet_factor = function(value, field, options) { + const formatter = fieldUtils.format[timesheetUomFields.FieldTimesheetFactor.prototype.formatType]; + return formatter(value, field, options); +}; + +fieldUtils.parse.timesheet_factor = function(value, field, options) { + const parser = fieldUtils.parse[timesheetUomFields.FieldTimesheetFactor.prototype.formatType]; + return parser(value, field, options); +}; + +}); diff --git a/addons/hr_timesheet/static/src/js/timesheet_uom.js b/addons/hr_timesheet/static/src/js/timesheet_uom.js new file mode 100644 index 00000000..982caa46 --- /dev/null +++ b/addons/hr_timesheet/static/src/js/timesheet_uom.js @@ -0,0 +1,164 @@ +odoo.define('hr_timesheet.timesheet_uom', function (require) { +'use strict'; + +const basicFields = require('web.basic_fields'); +const fieldUtils = require('web.field_utils'); + +const fieldRegistry = require('web.field_registry'); + +// We need the field registry to be populated, as we bind the +// timesheet_uom widget on existing field widgets. +require('web._field_registry'); + +const session = require('web.session'); + +/** + * Extend the float factor widget to set default value for timesheet + * use case. The 'factor' is forced to be the UoM timesheet + * conversion from the session info. + **/ +const FieldTimesheetFactor = basicFields.FieldFloatFactor.extend({ + formatType: 'float_factor', + /** + * Override init to tweak options depending on the session_info + * + * @constructor + * @override + */ + init: function(parent, name, record, options) { + this._super(parent, name, record, options); + + // force factor in format and parse options + if (session.timesheet_uom_factor) { + this.nodeOptions.factor = session.timesheet_uom_factor; + this.parseOptions.factor = session.timesheet_uom_factor; + } + }, +}); + + +/** + * Extend the float toggle widget to set default value for timesheet + * use case. The 'range' is different from the default one of the + * native widget, and the 'factor' is forced to be the UoM timesheet + * conversion. + **/ +const FieldTimesheetToggle = basicFields.FieldFloatToggle.extend({ + formatType: 'float_factor', + /** + * Override init to tweak options depending on the session_info + * + * @constructor + * @override + */ + init: function(parent, name, record, options) { + options = options || {}; + var fieldsInfo = record.fieldsInfo[options.viewType || 'default']; + var attrs = options.attrs || (fieldsInfo && fieldsInfo[name]) || {}; + + var hasRange = _.contains(_.keys(attrs.options || {}), 'range'); + + this._super(parent, name, record, options); + + // Set the timesheet widget options: the range can be customized + // by setting the option on the field in the view. The factor + // is forced to be the UoM conversion factor. + if (!hasRange) { + this.nodeOptions.range = [0.00, 1.00, 0.50]; + } + this.nodeOptions.factor = session.timesheet_uom_factor; + }, +}); + + +/** + * Extend float time widget + */ +const FieldTimesheetTime = basicFields.FieldFloatTime.extend({ + init: function () { + this._super.apply(this, arguments); + + if (session.timesheet_uom_factor) { + this.nodeOptions.factor = session.timesheet_uom_factor; + this.parseOptions.factor = session.timesheet_uom_factor; + } + } +}); + + +/** + * Binding depending on Company Preference + * + * determine wich widget will be the timesheet one. + * Simply match the 'timesheet_uom' widget key with the correct + * implementation (float_time, float_toggle, ...). The default + * value will be 'float_factor'. +**/ +const widgetName = 'timesheet_uom' in session ? + session.timesheet_uom.timesheet_widget : 'float_factor'; + +let FieldTimesheetUom = null; + +if (widgetName === 'float_toggle') { + FieldTimesheetUom = FieldTimesheetToggle; +} else if (widgetName === 'float_time') { + FieldTimesheetUom = FieldTimesheetTime; +} else { + FieldTimesheetUom = ( + fieldRegistry.get(widgetName) && + fieldRegistry.get(widgetName).extend({}) + ) || FieldTimesheetFactor; +} +fieldRegistry.add('timesheet_uom', FieldTimesheetUom); + +// widget timesheet_uom_no_toggle is the same as timesheet_uom but without toggle. +// We can modify easly huge amount of days. +let FieldTimesheetUomWithoutToggle = null; +if (widgetName === 'float_toggle') { + FieldTimesheetUomWithoutToggle = FieldTimesheetFactor; +} else { + FieldTimesheetUomWithoutToggle = FieldTimesheetTime; +} +fieldRegistry.add('timesheet_uom_no_toggle', FieldTimesheetUomWithoutToggle); + + +// bind the formatter and parser method, and tweak the options +const _tweak_options = function(options) { + if (!_.contains(options, 'factor')) { + options.factor = session.timesheet_uom_factor; + } + return options; +}; + +fieldUtils.format.timesheet_uom = function(value, field, options) { + options = _tweak_options(options || {}); + const formatter = fieldUtils.format[FieldTimesheetUom.prototype.formatType]; + return formatter(value, field, options); +}; + +fieldUtils.parse.timesheet_uom = function(value, field, options) { + options = _tweak_options(options || {}); + const parser = fieldUtils.parse[FieldTimesheetUom.prototype.formatType]; + return parser(value, field, options); +}; + +fieldUtils.format.timesheet_uom_no_toggle = function(value, field, options) { + options = _tweak_options(options || {}); + const formatter = fieldUtils.format[FieldTimesheetUom.prototype.formatType]; + return formatter(value, field, options); +}; + +fieldUtils.parse.timesheet_uom_no_toggle = function(value, field, options) { + options = _tweak_options(options || {}); + const parser = fieldUtils.parse[FieldTimesheetUom.prototype.formatType]; + return parser(value, field, options); +}; + +return { + FieldTimesheetUom, + FieldTimesheetFactor, + FieldTimesheetTime, + FieldTimesheetToggle +}; + +}); diff --git a/addons/hr_timesheet/static/src/scss/timesheets_task_form.scss b/addons/hr_timesheet/static/src/scss/timesheets_task_form.scss new file mode 100644 index 00000000..8a7e3b78 --- /dev/null +++ b/addons/hr_timesheet/static/src/scss/timesheets_task_form.scss @@ -0,0 +1,4 @@ +.o_form_subtask_button { + border: none; + padding-left: 0px; +} diff --git a/addons/hr_timesheet/static/src/xml/qr_modal_template.xml b/addons/hr_timesheet/static/src/xml/qr_modal_template.xml new file mode 100644 index 00000000..2d91c266 --- /dev/null +++ b/addons/hr_timesheet/static/src/xml/qr_modal_template.xml @@ -0,0 +1,11 @@ +<?xml version="1.0" encoding="UTF-8"?> +<templates id="template" xml:space="preserve"> +<t t-name="hr_timesheet_qr_code"> + <div style="text-align:center;"> + <t t-if="widget.url"> + <h3>Scan this QR code to get the Awesome Timesheet app:</h3><br/><br/> + <img class="border border-dark rounded" t-att-src="widget.url"/> + </t> + </div> +</t> +</templates> |
