Skip to content

Commit 3036d18

Browse files
committed
feat(board/promoted_attributes): improve rendering for color badge
1 parent 5dbe9e7 commit 3036d18

File tree

2 files changed

+30
-24
lines changed

2 files changed

+30
-24
lines changed

apps/client/src/services/css_class_manager.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,11 @@ function getHue(color: ColorInstance) {
7676
}
7777
}
7878

79+
export function getReadableTextColor(bgColor: string) {
80+
const colorInstance = Color(bgColor);
81+
return colorInstance.isLight() ? "#000" : "#fff";
82+
}
83+
7984
export default {
8085
createClassForColor
8186
};

apps/client/src/widgets/attribute_widgets/PromotedAttributesDisplay.tsx

Lines changed: 25 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,10 @@ import { useTriliumEvent } from "../react/hooks";
55
import attributes from "../../services/attributes";
66
import { DefinitionObject } from "../../services/promoted_attribute_definition_parser";
77
import { formatDateTime } from "../../utils/formatters";
8-
import { ComponentChildren } from "preact";
8+
import { ComponentChildren, CSSProperties } from "preact";
99
import Icon from "../react/Icon";
1010
import NoteLink from "../react/NoteLink";
11+
import { getReadableTextColor } from "../../services/css_class_manager";
1112

1213
interface PromotedAttributesDisplayProps {
1314
note: FNote;
@@ -26,15 +27,7 @@ export default function PromotedAttributesDisplay({ note, ignoredAttributes }: P
2627
const promotedDefinitionAttributes = useNoteAttributesWithDefinitions(note, ignoredAttributes);
2728
return promotedDefinitionAttributes?.length > 0 && (
2829
<div className="promoted-attributes">
29-
{promotedDefinitionAttributes?.map((attr) => {
30-
const className = `${attr.type === "label" ? "label" + " " + attr.def.labelType : "relation"}`;
31-
return (
32-
<span key={attr.friendlyName} className={`promoted-attribute type-${className}`}>
33-
{attr.type === "relation" ? formatRelation(attr) : formatLabelValue(attr)}
34-
</span>
35-
);
36-
}
37-
)}
30+
{promotedDefinitionAttributes?.map(attr => buildPromotedAttribute(attr))}
3831
</div>
3932
)
4033

@@ -52,7 +45,21 @@ function useNoteAttributesWithDefinitions(note: FNote, attributesToIgnore: stri
5245
return promotedDefinitionAttributes;
5346
}
5447

55-
function formatLabelValue(attr: AttributeWithDefinitions): ComponentChildren {
48+
function PromotedAttribute({ attr, children, style }: { attr: AttributeWithDefinitions, children: ComponentChildren, style?: CSSProperties }) {
49+
const className = `${attr.type === "label" ? "label" + " " + attr.def.labelType : "relation"}`;
50+
51+
return (
52+
<span key={attr.friendlyName} className={`promoted-attribute type-${className}`} style={style}>
53+
{children}
54+
</span>
55+
)
56+
}
57+
58+
function buildPromotedAttribute(attr: AttributeWithDefinitions): ComponentChildren {
59+
if (attr.type === "relation") {
60+
return <PromotedAttribute attr={attr}><strong>{attr.friendlyName}:</strong> <NoteLink notePath={attr.value} showNoteIcon /></PromotedAttribute>
61+
}
62+
5663
let value = attr.value;
5764
switch (attr.def.labelType) {
5865
case "number":
@@ -61,35 +68,29 @@ function formatLabelValue(attr: AttributeWithDefinitions): ComponentChildren {
6168
if (attr.def.numberPrecision) {
6269
formattedValue = numberValue.toFixed(attr.def.numberPrecision);
6370
}
64-
return <><strong>{attr.friendlyName}:</strong> {formattedValue}</>;
71+
return <PromotedAttribute attr={attr}><strong>{attr.friendlyName}:</strong> {formattedValue}</PromotedAttribute>;
6572
case "date":
6673
case "datetime": {
6774
const date = new Date(value);
6875
const timeFormat = attr.def.labelType !== "date" ? "short" : "none";
69-
return <><strong>{attr.friendlyName}:</strong> {formatDateTime(date, "short", timeFormat)}</>;
76+
return <PromotedAttribute attr={attr}><strong>{attr.friendlyName}:</strong> {formatDateTime(date, "short", timeFormat)}</PromotedAttribute>;
7077
}
7178
case "time": {
7279
const date = new Date(`1970-01-01T${value}Z`);
73-
return <><strong>{attr.friendlyName}:</strong> {formatDateTime(date, "none", "short")}</>;
80+
return <PromotedAttribute attr={attr}><strong>{attr.friendlyName}:</strong> {formatDateTime(date, "none", "short")}</PromotedAttribute>;
7481
}
7582
case "boolean":
76-
return <><Icon icon={value === "true" ? "bx bx-check-square" : "bx bx-square"} /> <strong>{attr.friendlyName}</strong></>;
83+
return <PromotedAttribute attr={attr}><Icon icon={value === "true" ? "bx bx-check-square" : "bx bx-square"} /> <strong>{attr.friendlyName}</strong></PromotedAttribute>;
7784
case "url":
78-
return <><a href={value} target="_blank" rel="noopener noreferrer">{attr.friendlyName}</a></>;
85+
return <PromotedAttribute attr={attr}><a href={value} target="_blank" rel="noopener noreferrer">{attr.friendlyName}</a></PromotedAttribute>;
7986
case "color":
80-
return <><span style={{ color: value }}>{attr.friendlyName}</span></>;
87+
return <PromotedAttribute attr={attr} style={{ backgroundColor: value, color: getReadableTextColor(value) }}>{attr.friendlyName}</PromotedAttribute>;
8188
case "text":
8289
default:
83-
return <><strong>{attr.friendlyName}:</strong> {value}</>;
90+
return <PromotedAttribute attr={attr}><strong>{attr.friendlyName}:</strong> {value}</PromotedAttribute>;
8491
}
8592
}
8693

87-
function formatRelation(attr: AttributeWithDefinitions): ComponentChildren {
88-
return (
89-
<><strong>{attr.friendlyName}:</strong> <NoteLink notePath={attr.value} showNoteIcon /></>
90-
)
91-
}
92-
9394
function getAttributesWithDefinitions(note: FNote, attributesToIgnore: string[] = []): AttributeWithDefinitions[] {
9495
const promotedDefinitionAttributes = note.getAttributeDefinitions();
9596
const result: AttributeWithDefinitions[] = [];

0 commit comments

Comments
 (0)