阅片融合分组区分颜色
continuous-integration/drone/push Build is passing
Details
continuous-integration/drone/push Build is passing
Details
parent
17f738aa5d
commit
ba6cb87648
|
|
@ -223,40 +223,67 @@ export async function readEntry(entry) {
|
||||||
|
|
||||||
return files;
|
return files;
|
||||||
}
|
}
|
||||||
|
// 使用FNV-1a哈希算法确保相同GUID产生相同结果
|
||||||
|
function fnv1aHash(str) {
|
||||||
|
const FNV_OFFSET_BASIS = 2166136261;
|
||||||
|
const FNV_PRIME = 16777619;
|
||||||
|
|
||||||
|
let hash = FNV_OFFSET_BASIS;
|
||||||
|
for (let i = 0; i < str.length; i++) {
|
||||||
|
hash ^= str.charCodeAt(i);
|
||||||
|
hash = (hash * FNV_PRIME) >>> 0; // 使用无符号右移确保结果为无符号32位整数
|
||||||
|
}
|
||||||
|
return hash;
|
||||||
|
}
|
||||||
// RGB转十六进制
|
// RGB转十六进制
|
||||||
function rgbToHex(r, g, b) {
|
function rgbToHex(r, g, b) {
|
||||||
return "#" + ((1 << 24) + (r << 16) + (g << 8) + b).toString(16).slice(1).toUpperCase();
|
return "#" + ((1 << 24) + (r << 16) + (g << 8) + b).toString(16).slice(1).toUpperCase();
|
||||||
}
|
}
|
||||||
|
// HSL转RGB函数
|
||||||
|
function hslToRgb(h, s, l) {
|
||||||
|
let r, g, b;
|
||||||
|
|
||||||
|
if (s === 0) {
|
||||||
|
r = g = b = l; // 灰色
|
||||||
|
} else {
|
||||||
|
const hue2rgb = (p, q, t) => {
|
||||||
|
if (t < 0) t += 1;
|
||||||
|
if (t > 1) t -= 1;
|
||||||
|
if (t < 1 / 6) return p + (q - p) * 6 * t;
|
||||||
|
if (t < 1 / 2) return q;
|
||||||
|
if (t < 2 / 3) return p + (q - p) * (2 / 3 - t) * 6;
|
||||||
|
return p;
|
||||||
|
};
|
||||||
|
|
||||||
|
const q = l < 0.5 ? l * (1 + s) : l + s - l * s;
|
||||||
|
const p = 2 * l - q;
|
||||||
|
|
||||||
|
r = hue2rgb(p, q, h + 1 / 3);
|
||||||
|
g = hue2rgb(p, q, h);
|
||||||
|
b = hue2rgb(p, q, h - 1 / 3);
|
||||||
|
}
|
||||||
|
|
||||||
|
return { r, g, b };
|
||||||
|
}
|
||||||
export function guidToColor(guid) {
|
export function guidToColor(guid) {
|
||||||
// 移除GUID中的连字符和花括号(如果有)
|
// 移除GUID中的连字符和花括号(如果有)
|
||||||
const cleanGuid = guid.replace(/[{}()-]/g, '');
|
let cleanGuid = guid.replace(/[{}()-]/g, '');
|
||||||
|
// 计算GUID的哈希值
|
||||||
|
const hash = fnv1aHash(cleanGuid);
|
||||||
|
|
||||||
// 使用GUID的前6个字符作为颜色基础(确保一致性)
|
// 使用哈希值生成HLS颜色(确保高区分度)
|
||||||
const colorBase = cleanGuid.substring(0, 6);
|
// 将哈希值映射到0-1之间
|
||||||
|
const h = (hash & 0xFFFF) / 0xFFFF; // 使用前16位作为色相
|
||||||
// 将每个字符转换为数字并映射到0-255范围
|
const s = ((hash >> 16) & 0xFF) / 0xFF * 0.6 + 0.4; // 饱和度在0.4-1.0之间
|
||||||
let r = 0, g = 0, b = 0;
|
const l = ((hash >> 24) & 0xFF) / 0xFF * 0.4 + 0.4; // 亮度在0.3-0.7之间,避免太暗或太亮
|
||||||
|
|
||||||
for (let i = 0; i < 6; i++) {
|
|
||||||
const charCode = colorBase.charCodeAt(i);
|
|
||||||
if (i < 2) {
|
|
||||||
r = (r * 16 + (charCode % 16)) % 256;
|
|
||||||
} else if (i < 4) {
|
|
||||||
g = (g * 16 + (charCode % 16)) % 256;
|
|
||||||
} else {
|
|
||||||
b = (b * 16 + (charCode % 16)) % 256;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// 确保颜色有足够的饱和度(避免生成过于灰暗的颜色)
|
|
||||||
if (r + g + b < 100) {
|
|
||||||
r = Math.min(255, r + 100);
|
|
||||||
g = Math.min(255, g + 50);
|
|
||||||
} else if (r + g + b > 600) {
|
|
||||||
r = Math.max(0, r - 100);
|
|
||||||
b = Math.max(0, b - 50);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 返回RGB对象
|
// 返回RGB对象
|
||||||
return rgbToHex(r, g, b);
|
let rgb = hslToRgb(h, s, l);
|
||||||
|
let obj = {
|
||||||
|
r: Math.round(rgb.r * 255),
|
||||||
|
g: Math.round(rgb.g * 255),
|
||||||
|
b: Math.round(rgb.b * 255)
|
||||||
|
}
|
||||||
|
let str = rgbToHex(obj.r, obj.g, obj.b)
|
||||||
|
return str;
|
||||||
}
|
}
|
||||||
|
|
@ -86,14 +86,14 @@
|
||||||
:content="`${$t('trials:reading:message:fused')}${item.TableQuestions.Answers[i].SplitOrMergeLesionName}`"
|
:content="`${$t('trials:reading:message:fused')}${item.TableQuestions.Answers[i].SplitOrMergeLesionName}`"
|
||||||
placement="bottom">
|
placement="bottom">
|
||||||
<div
|
<div
|
||||||
v-if="item.TableQuestions.Answers[i].SplitOrMergeType === '1' || item.TableQuestions.Answers[i].SplitOrMergeType === '3'"
|
v-if="item.TableQuestions.Answers[i].SplitOrMergeType === '1' || item.TableQuestions.Answers[i].SplitOrMergeType === '3'">
|
||||||
@click="acvd(item.TableQuestions.Answers[i])">
|
<span class="login-cycle"
|
||||||
<span class="login-cycle" />
|
:style="`background-color:${$GuidToColor(item.TableQuestions.Answers[i].MergeRowId)}`" />
|
||||||
</div>
|
</div>
|
||||||
</el-tooltip>
|
</el-tooltip>
|
||||||
<div v-if="item.TableQuestions.Answers[i].SplitOrMergeType === '4'"
|
<div v-if="item.TableQuestions.Answers[i].SplitOrMergeType === '4'">
|
||||||
@click="acvd(item.TableQuestions.Answers[i])">
|
<span class="login-cycle"
|
||||||
<span class="login-cycle" />
|
:style="`background-color:${$GuidToColor(item.TableQuestions.Answers[i].RowId)}`" />
|
||||||
</div>
|
</div>
|
||||||
<el-tooltip v-if="!!item.TableQuestions.Answers[i].lesionPart" class="item" effect="dark"
|
<el-tooltip v-if="!!item.TableQuestions.Answers[i].lesionPart" class="item" effect="dark"
|
||||||
:content="item.TableQuestions.Answers[i].lesionPart" placement="bottom">
|
:content="item.TableQuestions.Answers[i].lesionPart" placement="bottom">
|
||||||
|
|
@ -337,7 +337,6 @@ export default {
|
||||||
DicomEvent.$off('refreshQuestions')
|
DicomEvent.$off('refreshQuestions')
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
acvd(item) { console.log(item) },
|
|
||||||
handleReadingChart(e) {
|
handleReadingChart(e) {
|
||||||
this.$emit('handleReadingChart', e)
|
this.$emit('handleReadingChart', e)
|
||||||
},
|
},
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue