事情是这样的,拿到的需求是,当用户修改输入框内的内容的时候,只要检测到有修改就自动把对应的标签变成红色,如图:
就是这种效果,这些效果我也实现了的,接下来描述遇到的问题:
问题复现:
在操作第一条数据的时候一切都是正常的,然后在操作第二条数据的时候就出现了这种情况
然后我调试了再检查了一下:
我发现当第二条的相关数据与第一条内的数据一致的时候就显示正常了,然后我判断这个渲染标题颜色的高亮规则肯定是拿了第一条数据做对比了,以上的代码完全是用ChatGPT来完成的,用的是Vue的全局指令来进行渲染的,以下是源代码:
export default {
inserted(el, binding, vnode) {
initializeState(el, binding, vnode);
},
update(el, binding, vnode, oldVnode) {
// 只有当currentDataItemId改变时,我们才重新初始化状态。
if (vnode.context.currentDataItemId !== oldVnode.context.currentDataItemId) {
initializeState(el, binding, vnode);
}
},
unbind(el) {
// 如果有observer,则停止观察
if (el._observer) {
el._observer.disconnect();
}
const labelElement = el.querySelector('label');
if (labelElement) {
labelElement.style.color = '';
}
},
};
function areValuesEqual(value1, value2) {
return JSON.stringify(value1) === JSON.stringify(value2);
}
function initializeState(el, binding, vnode) {
const propName = binding.expression;
const currentUid = vnode.context._uid;
const key = `${currentUid}_${propName}`;
console.log(`Initializing state for key=${key}`);
// 尝试从组件状态中获取editedStates
let editedStates = vnode.context.editedStates;
// 获取当前数据项的唯一标识符,例如ID或其他能区分数据项的字段
const currentDataItemId = vnode.context.currentDataItemId;
// 如果不存在,则创建一个新对象并存储在组件状态中
if (!editedStates) {
vnode.context.editedStates = editedStates = {};
}
// 创建或获取当前数据项的编辑状态
let localEditedState = editedStates[currentDataItemId];
if (!localEditedState) {
localEditedState = editedStates[currentDataItemId] = {};
}
vnode.context.$on('reset-form', () => {
// 重置表单状态
localEditedState[key] = {
edited: false,
initialValue: JSON.stringify(binding.value),
};
console.log(`Resetting state for ${key}`);
// 还原标签颜色
el.querySelector('label').style.color = '';
});
// 只在第一次插入时设置初始值
if (!localEditedState[key]) {
const initialValue = JSON.stringify(binding.value);
console.log(`Setting initial value: key=${key}, initialValue=${initialValue}`);
localEditedState[key] = {
edited: false,
initialValue: initialValue,
};
}
const updateLabelColor = (newVal) => {
const propertyState = localEditedState[key];
let newValue = newVal;
if (newVal === undefined || newVal === '') {
newValue = propertyState.initialValue === JSON.stringify('') ? '' : undefined;
} else {
newValue = JSON.stringify(newVal);
}
console.log(`updateLabelColor: key=${key}, newValue=${newValue}, initialValue=${propertyState.initialValue}`);
if (newValue !== propertyState.initialValue) {
propertyState.edited = true;
console.log(`Setting color to red for ${key}`);
el.querySelector('label').style.color = 'red';
} else {
propertyState.edited = false;
console.log(`Setting color to default for ${key}`);
el.querySelector('label').style.color = '';
}
};
vnode.context.$watch(propName, (newVal, oldVal) => {
vnode.context.$nextTick(() => {
if (!areValuesEqual(newVal, oldVal)) {
console.log(`$watch triggered for ${key}, new value: ${JSON.stringify(newVal)}`);
updateLabelColor(newVal);
}
});
}, { deep: true });
if (el.classList.contains('el-select')) {
const selectElement = el.querySelector('.el-select-dropdown');
if (selectElement) {
const observer = new MutationObserver(() => {
const newValue = vnode.context[propName];
console.log(`MutationObserver triggered for ${key}, new value: ${JSON.stringify(newValue)}`);
updateLabelColor(newValue);
});
observer.observe(selectElement, {
attributes: true,
childList: true,
subtree: true,
});
// 将observer存储在元素上,以便以后停止观察
el._observer = observer;
}
}
}
能帮远程一下吗,不太懂..