0

monaco editor 0.27.0

Based on this post I'm trying to sync the vertical scroll bar of monaco editor with a div of different height.

window.editor.onDidScrollChange(function (e) {
 if (e.scrollTopChanged) {
   var other = $('#html-out').get(0);
   // 168 = e.scrollTop - (e.scrollHeight-$(window).height())-34
   var percentage = e.scrollTop / (e.scrollHeight - $(window).height()+168); 
   other.scrollTop = percentage * (other.scrollHeight - other.offsetHeight);
   }
});

168 is based on the guess work because e.offsetHeight is not available. Although it's working as good as it has to but I would like to implement this correctly?

Regards

Prashant
  • 833
  • 1
  • 11
  • 17

1 Answers1

1

I also met this problem a few days ago.

Here is my solution

Here is three needed variable

  1. clientHeight, is the scroll block height
    1. For monaco, you should wrap it with a div, and get it by divRef.current.clientHeight
    2. For div, you can simplely use divRef.current.clientHeight
  2. scrollHeight, is the whole scrollable content height
    1. For monaco, you can get it by editor.getScrollHeight()
    2. For div, you can use divRef.current.scrollHeight
  3. scrollTop, is the top of scrollbar
    1. For monaco, you can get it by editor.getScrollTop()
    2. For div, you can use divRef.current.scrollTop
type ScrollNode = {
    clientHeight: number
    scrollHeight: number
    scrollTop?: number
}

Then

  1. Calculate the above height of scroll bar in clientHeight
  2. Calculate the below height of scroll bar in clientHeight
  3. Then you can get three percenage of clientHeight (A/B/C of (A+B+C))
  4. Then the A part percentage is what you want of the unknown block(div/monaco) scrollTop of clientHeight, C part is for scrollBottom of clientHeight
 ┌ A ┐┌  B  ┐┌   C   ┐
|-----+++++++---------|
const computeScrollTopPercent = (known: Required<ScrollNode>, unknown: ScrollNode): number => {
    let knownTopPercent = known.scrollTop / known.scrollHeight
    let knownScrollbarPercent = known.clientHeight / known.scrollHeight
    let knownTopPercentExcludeScrollbar = knownTopPercent / (1 - knownScrollbarPercent)[enter image description here][1]

    let unknownScrollbarPercent = unknown.clientHeight / unknown.scrollHeight
    let unknownTopPercent = (1 - unknownScrollbarPercent) * knownTopPercentExcludeScrollbar
    return unknownTopPercent
    // let accuracy = 100000
    // return Math.round(unknownTopPercent * accuracy) / accuracy
}
Hyia
  • 11
  • 2