diff --git a/app/assets/javascripts/admin/addon/components/color-input.gjs b/app/assets/javascripts/admin/addon/components/color-input.gjs
index 0fecbc0cebc..140c47be3c9 100644
--- a/app/assets/javascripts/admin/addon/components/color-input.gjs
+++ b/app/assets/javascripts/admin/addon/components/color-input.gjs
@@ -32,16 +32,16 @@ export default class ColorInput extends Component {
}
@computed("hexValueWithFallback")
- get normalizedValue() {
- return this.normalize(this.hexValueWithFallback);
+ get valueForPicker() {
+ return this.normalize(this.hexValueWithFallback, { forPicker: true });
}
- normalize(color) {
+ normalize(color, { forPicker = false } = {}) {
if (this._valid(color)) {
if (!color.startsWith("#")) {
color = "#" + color;
}
- if (color.length === 4) {
+ if (color.length === 4 && (!this.skipNormalize || forPicker)) {
color =
"#" +
color
@@ -109,8 +109,8 @@ export default class ColorInput extends Component {
diff --git a/app/assets/javascripts/discourse/app/components/edit-category-general.gjs b/app/assets/javascripts/discourse/app/components/edit-category-general.gjs
index 1c62170ba4b..65e3b89b641 100644
--- a/app/assets/javascripts/discourse/app/components/edit-category-general.gjs
+++ b/app/assets/javascripts/discourse/app/components/edit-category-general.gjs
@@ -129,6 +129,10 @@ export default class EditCategoryGeneral extends Component {
updateColor(field, newColor) {
const color = newColor.replace("#", "");
+ if (color === field.value) {
+ return;
+ }
+
if (field.name === "color") {
const whiteDiff = this.colorDifference(color, CATEGORY_TEXT_COLORS[0]);
const blackDiff = this.colorDifference(color, CATEGORY_TEXT_COLORS[1]);
@@ -160,6 +164,41 @@ export default class EditCategoryGeneral extends Component {
return rDiff + gDiff + bDiff;
}
+ @action
+ validateColor(name, color, { addError }) {
+ color = color.trim();
+
+ let title;
+ if (name === "color") {
+ title = i18n("category.background_color");
+ } else if (name === "text_color") {
+ title = i18n("category.foreground_color");
+ } else {
+ throw new Error(`unknown title for category attribute ${name}`);
+ }
+
+ if (!color) {
+ addError(name, {
+ title,
+ message: i18n("category.color_validations.cant_be_empty"),
+ });
+ }
+
+ if (color.length !== 3 && color.length !== 6) {
+ addError(name, {
+ title,
+ message: i18n("category.color_validations.incorrect_length"),
+ });
+ }
+
+ if (!/^[0-9A-Fa-f]+$/.test(color)) {
+ addError(name, {
+ title,
+ message: i18n("category.color_validations.non_hexdecimal"),
+ });
+ }
+ }
+
get categoryDescription() {
if (this.args.category.description) {
return htmlSafe(this.args.category.description);
@@ -318,6 +357,8 @@ export default class EditCategoryGeneral extends Component {
@name="color"
@title={{i18n "category.background_color"}}
@format="full"
+ @validate={{this.validateColor}}
+ @validation="required"
as |field|
>
@@ -328,6 +369,7 @@ export default class EditCategoryGeneral extends Component {
@valid={{@category.colorValid}}
@ariaLabelledby="background-color-label"
@onChangeColor={{fn this.updateColor field}}
+ @skipNormalize={{true}}
/>
@@ -353,7 +397,8 @@ export default class EditCategoryGeneral extends Component {
validator())) {
return;
}
- this.model.setProperties(transientData);
-
+ this.model.setProperties(data);
this.set("saving", true);
this.model
diff --git a/app/assets/javascripts/discourse/app/form-kit/components/fk/form.gjs b/app/assets/javascripts/discourse/app/form-kit/components/fk/form.gjs
index 7ca5ebd0b85..fd9b07495e9 100644
--- a/app/assets/javascripts/discourse/app/form-kit/components/fk/form.gjs
+++ b/app/assets/javascripts/discourse/app/form-kit/components/fk/form.gjs
@@ -225,7 +225,7 @@ class FKForm extends Component {
try {
this.isSubmitting = true;
- await this.validate(this.fields.values());
+ await this.validate([...this.fields.values()]);
if (this.formData.isValid) {
this.formData.save();
diff --git a/app/assets/javascripts/discourse/app/templates/edit-category/tabs.gjs b/app/assets/javascripts/discourse/app/templates/edit-category/tabs.gjs
index e63e4a2f35c..6986a0183f2 100644
--- a/app/assets/javascripts/discourse/app/templates/edit-category/tabs.gjs
+++ b/app/assets/javascripts/discourse/app/templates/edit-category/tabs.gjs
@@ -1,4 +1,3 @@
-import { fn } from "@ember/helper";
import { getOwner } from "@ember/owner";
import { htmlSafe } from "@ember/template";
import RouteTemplate from "ember-route-template";
@@ -93,6 +92,7 @@ export default RouteTemplate(
@@ -119,12 +119,10 @@ export default RouteTemplate(
{{/if}}