summaryrefslogtreecommitdiff
path: root/addons/website/static/src/snippets/s_rating
diff options
context:
space:
mode:
authorstephanchrst <stephanchrst@gmail.com>2022-05-10 21:51:50 +0700
committerstephanchrst <stephanchrst@gmail.com>2022-05-10 21:51:50 +0700
commit3751379f1e9a4c215fb6eb898b4ccc67659b9ace (patch)
treea44932296ef4a9b71d5f010906253d8c53727726 /addons/website/static/src/snippets/s_rating
parent0a15094050bfde69a06d6eff798e9a8ddf2b8c21 (diff)
initial commit 2
Diffstat (limited to 'addons/website/static/src/snippets/s_rating')
-rw-r--r--addons/website/static/src/snippets/s_rating/000.scss55
-rw-r--r--addons/website/static/src/snippets/s_rating/001.scss15
-rw-r--r--addons/website/static/src/snippets/s_rating/options.js151
3 files changed, 221 insertions, 0 deletions
diff --git a/addons/website/static/src/snippets/s_rating/000.scss b/addons/website/static/src/snippets/s_rating/000.scss
new file mode 100644
index 00000000..968ee7d3
--- /dev/null
+++ b/addons/website/static/src/snippets/s_rating/000.scss
@@ -0,0 +1,55 @@
+
+.s_rating:not([data-vcss]) {
+ $star: "\f005";
+ $star-o: "\f006";
+ $circle: "\f111";
+ $circle-o: "\f10c";
+ $heart: "\f004";
+ $heart-o: "\f08a";
+ @mixin s_rating_generate_icons($off, $on) {
+ .fa:before {
+ content: $off;
+ }
+ @for $counter from 5 to 0 {
+ &.s_rating_#{$counter} {
+ .fa:nth-of-type(-n+#{$counter}):before {
+ content: $on;
+ }
+ }
+ }
+ }
+ > .s_rating_stars { @include s_rating_generate_icons($star-o, $star); }
+ > .s_rating_squares { @include s_rating_generate_icons($circle-o, $circle); }
+ > .s_rating_hearts { @include s_rating_generate_icons($heart-o, $heart); }
+ > .s_rating_bar {
+ .fa {
+ display: none;
+ }
+ .s_rating_bar {
+ display: flex;
+ height: $progress-height;
+ background-color: $gray-300;
+ &:before {
+ content: "";
+ display: flex;
+ flex-direction: column;
+ justify-content: center;
+ @include transition($progress-bar-transition);
+ @include gradient-striped();
+ background-size: $progress-height $progress-height;
+ background-color: theme-color('primary');
+ animation: progress-bar-stripes $progress-bar-animation-timing;
+ }
+ }
+ @for $counter from 5 to 0 {
+ &.s_rating_#{$counter} {
+ .s_rating_bar:before {
+ width: percentage($counter/5);
+ }
+ }
+ }
+ }
+ > .s_rating_1x { .fa { font-size: 1em; }; }
+ > .s_rating_2x { .fa { font-size: 2em; }; }
+ > .s_rating_3x { .fa { font-size: 3em; }; }
+}
diff --git a/addons/website/static/src/snippets/s_rating/001.scss b/addons/website/static/src/snippets/s_rating/001.scss
new file mode 100644
index 00000000..a1fc87c0
--- /dev/null
+++ b/addons/website/static/src/snippets/s_rating/001.scss
@@ -0,0 +1,15 @@
+
+.s_rating[data-vcss="001"] {
+ &.s_rating_inline {
+ display: flex;
+ align-items: center;
+
+ .s_rating_title {
+ margin: 0;
+ margin-right: 0.5em;
+ }
+ .s_rating_icons {
+ margin-left: auto;
+ }
+ }
+}
diff --git a/addons/website/static/src/snippets/s_rating/options.js b/addons/website/static/src/snippets/s_rating/options.js
new file mode 100644
index 00000000..b24d7daf
--- /dev/null
+++ b/addons/website/static/src/snippets/s_rating/options.js
@@ -0,0 +1,151 @@
+odoo.define('website.s_rating_options', function (require) {
+'use strict';
+
+const weWidgets = require('wysiwyg.widgets');
+const options = require('web_editor.snippets.options');
+
+options.registry.Rating = options.Class.extend({
+ /**
+ * @override
+ */
+ start: function () {
+ this.iconType = this.$target[0].dataset.icon;
+ this.faClassActiveCustomIcons = this.$target[0].dataset.activeCustomIcon || '';
+ this.faClassInactiveCustomIcons = this.$target[0].dataset.inactiveCustomIcon || '';
+ return this._super.apply(this, arguments);
+ },
+
+ //--------------------------------------------------------------------------
+ // Options
+ //--------------------------------------------------------------------------
+
+ /**
+ * Displays the selected icon type.
+ *
+ * @see this.selectClass for parameters
+ */
+ setIcons: function (previewMode, widgetValue, params) {
+ this.iconType = widgetValue;
+ this._renderIcons();
+ this.$target[0].dataset.icon = widgetValue;
+ delete this.$target[0].dataset.activeCustomIcon;
+ delete this.$target[0].dataset.inactiveCustomIcon;
+ },
+ /**
+ * Allows to select a font awesome icon with media dialog.
+ *
+ * @see this.selectClass for parameters
+ */
+ customIcon: async function (previewMode, widgetValue, params) {
+ return new Promise(resolve => {
+ const dialog = new weWidgets.MediaDialog(
+ this,
+ {noImages: true, noDocuments: true, noVideos: true, mediaWidth: 1920},
+ $('<i/>')
+ );
+ this._saving = false;
+ dialog.on('save', this, function (attachments) {
+ this._saving = true;
+ const customClass = 'fa ' + attachments.className;
+ const $activeIcons = this.$target.find('.s_rating_active_icons > i');
+ const $inactiveIcons = this.$target.find('.s_rating_inactive_icons > i');
+ const $icons = params.customActiveIcon === 'true' ? $activeIcons : $inactiveIcons;
+ $icons.removeClass().addClass(customClass);
+ this.faClassActiveCustomIcons = $activeIcons.length > 0 ? $activeIcons.attr('class') : customClass;
+ this.faClassInactiveCustomIcons = $inactiveIcons.length > 0 ? $inactiveIcons.attr('class') : customClass;
+ this.$target[0].dataset.activeCustomIcon = this.faClassActiveCustomIcons;
+ this.$target[0].dataset.inactiveCustomIcon = this.faClassInactiveCustomIcons;
+ this.$target[0].dataset.icon = 'custom';
+ this.iconType = 'custom';
+ resolve();
+ });
+ dialog.on('closed', this, function () {
+ if (!this._saving) {
+ resolve();
+ }
+ });
+ dialog.open();
+ });
+ },
+ /**
+ * Sets the number of active icons.
+ *
+ * @see this.selectClass for parameters
+ */
+ activeIconsNumber: function (previewMode, widgetValue, params) {
+ this.nbActiveIcons = parseInt(widgetValue);
+ this._createIcons();
+ },
+ /**
+ * Sets the total number of icons.
+ *
+ * @see this.selectClass for parameters
+ */
+ totalIconsNumber: function (previewMode, widgetValue, params) {
+ this.nbTotalIcons = Math.max(parseInt(widgetValue), 1);
+ this._createIcons();
+ },
+
+ //--------------------------------------------------------------------------
+ // Private
+ //--------------------------------------------------------------------------
+
+ /**
+ * @override
+ */
+ _computeWidgetState: function (methodName, params) {
+ switch (methodName) {
+ case 'setIcons': {
+ return this.$target[0].dataset.icon;
+ }
+ case 'activeIconsNumber': {
+ this.nbActiveIcons = this.$target.find('.s_rating_active_icons > i').length;
+ return this.nbActiveIcons;
+ }
+ case 'totalIconsNumber': {
+ this.nbTotalIcons = this.$target.find('.s_rating_icons i').length;
+ return this.nbTotalIcons;
+ }
+ }
+ return this._super(...arguments);
+ },
+ /**
+ * Creates the icons.
+ *
+ * @private
+ */
+ _createIcons: function () {
+ const $activeIcons = this.$target.find('.s_rating_active_icons');
+ const $inactiveIcons = this.$target.find('.s_rating_inactive_icons');
+ this.$target.find('.s_rating_icons i').remove();
+ for (let i = 0; i < this.nbTotalIcons; i++) {
+ if (i < this.nbActiveIcons) {
+ $activeIcons.append('<i/> ');
+ } else {
+ $inactiveIcons.append('<i/> ');
+ }
+ }
+ this._renderIcons();
+ },
+ /**
+ * Renders icons with selected fonts.
+ *
+ * @private
+ */
+ _renderIcons: function () {
+ const icons = {
+ 'fa-star': 'fa-star-o',
+ 'fa-thumbs-up': 'fa-thumbs-o-up',
+ 'fa-circle': 'fa-circle-o',
+ 'fa-square': 'fa-square-o',
+ 'fa-heart': 'fa-heart-o'
+ };
+ const faClassActiveIcons = (this.iconType === "custom") ? this.faClassActiveCustomIcons : 'fa ' + this.iconType;
+ const faClassInactiveIcons = (this.iconType === "custom") ? this.faClassInactiveCustomIcons : 'fa ' + icons[this.iconType];
+ const $activeIcons = this.$target.find('.s_rating_active_icons > i');
+ const $inactiveIcons = this.$target.find('.s_rating_inactive_icons > i');
+ $activeIcons.removeClass().addClass(faClassActiveIcons);
+ $inactiveIcons.removeClass().addClass(faClassInactiveIcons);
+ },
+});
+});