setInterval 을 한 컴포넌트에서 선언하고 다른 컴포넌트에서 멈추게 할 때, 안 먹는 경우가 있다.
예를 들어 어떠한 문제가 말생하여 해당 문제인 부분을 사용자가 어떠한 행동을 할때 까지 계속 깜빡이게 하고, 행동이 완료되면
해당 Interval 을 null 로 하여 멈추게 할 때 멈추지 않고 setInterval 이 중복되는 문제가 발생하는데 이는 interval 을 설정한 객체를 같은 객체를 보지 못 하고 생겨나는 문제이다. 예를들어
const isOrdered = ref<any>(null);
isOrdered.value = setInterval(()=>mapStore.blinkIcon(+data.sensorInfo.sensorSeq), 2000)
위 코드에서 isOrdered 의 값에 계속 다른 Interval 이 할당되어 setInterval 이 계~속 중복되는 문제이다.
그리고 사용자가 어떠한 동작을 하면 아래 함수가 실행되며 깜빡임이 멈추는 코드이다.
const postOrderRequest = () => {
clearInterval(isOrdered.value)
}
원인은 isOrdered.value에 setInterval의 반환값이 제대로 저장되지 않아서 발생하는 것 이다.
setInterval의 반환값은 number 타입의 ID인데, 이를 clearInterval에 전달하여 해당 인터벌을 정지할 수 있다.
그래서 반드시 체크해줘야할 부분이 2개 있다.
1. isOrdered가 올바른 setInterval ID를 받는지 확인해야 함.
2. clearInterval이 올바르게 호출되는지 확인해야 합니다.
// isOrdered 변수를 ref로 선언합니다.
const isOrdered = ref<number | null>(null);
let currentStyle = true;
const blinkIcon = (sensorSeq: number) => {
const targetFeature = featureObj.value!.getSource().getFeatures().find((el: any) => "sensor_" + sensorSeq === el.values_.id);
if (targetFeature) {
if (currentStyle) {
targetFeature.setStyle(newStyle);
} else {
targetFeature.setStyle(oldStyle);
}
}
currentStyle = !currentStyle;
};
// 특정 상황일 때 setInterval 설정
const startBlinking = () => {
if (isOrdered.value === null) {
isOrdered.value = setInterval(() => mapStore.blinkIcon(+data.sensorInfo.sensorSeq), 2000);
}
};
// 사용자가 버튼을 누르면 setInterval 정지
const postOrderRequest = () => {
if (isOrdered.value !== null) {
clearInterval(isOrdered.value);
isOrdered.value = null;
}
};
문제의 원인은 주로 두 가지였다.
원래 isOrdered는 ref<any>(null)
로 선언되어 있었지만, setInterval이 반환하는 값은 number이다. 타입이 일치하지 않으면 의도한 대로 작동하지 않을 수 있다. isOrdered를 ref<number | null>(null)
로 선언함으로써 타입을 명확히 하여 문제를 해결
setInterval이 실행될 때마다 반환된 ID를 isOrdered.value에 저장해야 하는데, 이를 명확히 하지 않으면 clearInterval에서 올바른 ID를 전달하지 못해 인터벌이 제대로 정지되지 않을 수 있다.
또한, clearInterval 후에 isOrdered.value를 null로 재설정하지 않으면 인터벌이 중복 실행될 수 있다. 이를 통해 새로운 인터벌이 설정되기 전에 이전 인터벌이 정지되도록 보장했다.