I want to create a chatroom application, where the chat window might potentially run for many hours and display 100.000 messages. It's not feasible to display all of these messages with a v-for directive, because the VDOM will be huge and the application will become slow. Instead I would like to use a message template and a render function, to render each incoming message into an HTML string or an ordinary DOM object, and then simply append (with plain JS) that static content to the message log <div>. That will keep the chatroom application snappy and responsive for almost forever.
I can generate the renderer function, using Vue.compile(msgTemplate), but calling the renderer function (after binding it to a component) only gives me a VDOM JS object, not any HTML that I can use. I would need to transform this JS object into ordinary HTML myself, but that wouldn't be future-proof, because maybe in future versions of Vue.js the structure of the VDOM JS Object will change, and then my plugin will stop working. So I need the Vue.js library to do this transformation for me.
Thank you.
var res = Vue.compile(msgTemplate);
var vdom = res.renderer.bind(this)();
var htmlString = Vue.toHTML(vdom);
You should use a virtual list solution that renders only what is visible. Here's something that solves your use case: https://github.com/Akryum/vue-virtual-scroller
if you really need to convert it to a string you can use the vue-server-renderer but I really recommend you to use a virtual scrolling list
@posva No, I cannot use vue-server-renderer, because it doesn't compile with Webpack. It only works on the server.
I'll check the virtual scroller you showed me here, to see if it's good enough.
The virtual scroller requires that each element have the same height, in order to prevent display glitches. That is not the case with chat messages. Also vue-server-renderer won't work.
So why did you close this ticket? Did you find my idea not interesting?
If you want to directly generate real DOM, I don't see why there's the need to even go through Vue's rendering pipeline. Just use plain HTML string concatenation would give you more control and better performance.
It's possible to implement virtual scrolling that can handle dynamic height, but currently there's no solid Vue implementation yet. Still, we consider this a problem that should be dealt with in userland rather than in core.