GlideJS destroy() function causes 'resize' event error.
Hi,
So I'm having issues with the destroy functionality. I want the carousel to be initialized on mobile phones, and on resize if the window width is bigger than the JSON init property, destroy the carousel. It looks as follows:
initCarousel() {
if(this.config.init >= this.windowWidth) {
this.carousel = new Glide(this.el, this.config);
this.carousel.on('resize', function() {
this.windowWidth = window.innerWidth;
if(this.config.init < this.windowWidth && this.carousel != undefined) {
this.carousel.destroy();
}
}.bind(this));
this.carousel.mount();
}
}
Here you can see I create the carousel if the init property (640px in this case) is larger or equal to the window width. Then I add a resize event listener which checks if the window is bigger than the init property. If so: destroy.
It destroys it just fine. But as soon as the carousel gets destroyed I get the following error in the console:
Uncaught TypeError: Cannot read property 'resize' of undefined
at EventsBinder.off (glide.esm.js?fe9b:1951)
at Object.unbind (glide.esm.js?fe9b:2006)
at eval (glide.esm.js?fe9b:2015)
at eval (glide.esm.js?fe9b:556)
at Array.forEach (<anonymous>)
at EventsBus.emit (glide.esm.js?fe9b:555)
at Glide$$1.destroy (glide.esm.js?fe9b:699)
at VlCarousel.eval (module.gallery.js?e992:30)
at eval (glide.esm.js?fe9b:556)
at Array.forEach (<anonymous>)
Do I need to unbind this resize event somewhere?
@Danielvandervelden can you try ::-
this.carousel._e.on('resize' ......
The Eventbus is attached to this._e on the Glide class hence this syntax
I experienced the same error, when I tried to mount and destroy slider depending on window's width. Pseudocode:
{
constructor() {
this.carousel = new Glide(this.element);
this.attachListeners();
this.toggle();
}
mount() {
this.carousel.mount();
this.destroyed = false;
}
unmount() {
if (this.carousel) {
this.carousel.destroy();
this.destroyed = true;
}
}
attachListeners() {
window.addEventListener('resize', this.resize);
}
resize = debounce(() => {
this.toggle();
}, 200);
toggle() {
if (window.innerWidth > 1024) {
this.unmount();
} else if (this.destroyed) {
this.mount();
}
}
}
This uncaught error breaks carousel destroying process, so carousel is randomly destroyed. I'm not sure how to make a workaround. Any help would be grateful.
EDIT
It looks like Event's Binder destroy() is called one extra time, just before calling off(). Probably Resize component is calling destroy() too many times.
Hi, I'm facing the same error and I don't manage to find any solution Did someone find one or a workaround to this problem? Any help would be appreciated
if (window.matchMedia('(min-width: 768px)').matches) {
glide.update({startAt: 0, perView: 1, gap: 0, peek: 0}).disable();
} else {
glide.enable();
}
it seems that reseting glide settings with update() and then applying disable() helped me.
Any plan to fix this? I still have the same issue atm.
Same problem here. Any suggestions for a woraround?
I tend to run a slider.destroy() when the parent of the slider becomes hidden, and mount the slider again when the container becomes visible. I've experienced the same problem and I've found this issue is caused by the this.listeners getting removed from the GlideJS instance when the slider is destroyed.
Link: https://github.com/glidejs/glide/blob/master/src/core/event/events-binder.js#L56
So far I thought that destroy and mount a slider again would make sense but now I have a doubt. Is the destroy action a way to put the Slider in an unknown state or this has something to do with the instance of the GlideJS class?
Because if it is allowed to run slider.destroy().mount() then, I think the current behavior is a bug. The documentation is also saying 👇
Destroy instance and undo all modifications which have been made to the DOM. It also unbinds added event listeners.
It also unbinds added event listeners.
Which does not mean deleting the instance property listeners, hence to me the solution would be to change the line from
delete this.listeners
to
this.listeners = {}
Nonetheless the document also say
Destroy instance
If this is intend as Class instance, then the behavior could even be correct, even though I think it would be partially correct. I have no knowledge about the entire project but in this case the object instance should become undefined which is probably something the GlideJS cannot do.
I think the slider.mount().destroy() make sense even though the procedure appear to more like a reset or onhold, depends by the use cases, but it should not put the instance of the GlideJS object in an incorrect state which is what is happening.
Looking at the constructor make me think that, the aforementioned solution would be the solution to go with.
Link: https://github.com/glidejs/glide/blob/master/src/core/event/events-binder.js#L7