   domPollingIntervalId: null
   domPollingPaused: false
   displayMinimapOnLeft: false
+
+  #    ##     ##  #######   #######  ##    ##  ######
+  #    ##     ## ##     ## ##     ## ##   ##  ##    ##
+  #    ##     ## ##     ## ##     ## ##  ##   ##
+  #    ######### ##     ## ##     ## #####     ######
+  #    ##     ## ##     ## ##     ## ##  ##         ##
+  #    ##     ## ##     ## ##     ## ##   ##  ##    ##
+  #    ##     ##  #######   #######  ##    ##  ######
 
   createdCallback: ->
     @subscriptions = new CompositeDisposable


    @minimap

  setDisplayCodeHighlights: (@displayCodeHighlights) ->
    @requestForcedUpdate() if @attached

  initializeContent: ->
    @initializeCanvas()

    @shadowRoot = @createShadowRoot()

    @shadowRoot.appendChild(@canvas)

    @visibleArea = document.createElement('div')
    @visibleArea.classList.add('minimap-visible-area')
    @shadowRoot.appendChild(@visibleArea)

    @controls = document.createElement('div')
    @controls.classList.add('minimap-controls')
    @shadowRoot.appendChild(@controls)

    @canvas.addEventListener 'mousedown', l = (e) => @mousePressedOverCanvas(e)
    @subscriptions.add new Disposable =>
      @canvas.removeEventListener 'mousedown', l

  initializeScrollIndicator: ->
    @scrollIndicator = document.createElement('div')
    @scrollIndicator.classList.add 'minimap-scroll-indicator'
    @controls.appendChild(@scrollIndicator)

  disposeScrollIndicator: ->
    @controls.removeChild(@scrollIndicator)
    @scrollIndicator = undefined

  initializeOpenQuickSettings: ->
    @openQuickSettings = document.createElement('div')
    @openQuickSettings.classList.add 'open-minimap-quick-settings'
    @controls.appendChild(@openQuickSettings)
    @openQuickSettings.addEventListener 'mousedown', (e) =>
      e.preventDefault()
      e.stopPropagation()
      
      if @quickSettingsView?
        @quickSettingsView.destroy()
        @quickSettingsSubscription.dispose()
      else
        MinimapQuickSettingsView ?= require './minimap-quick-settings-view'
        @quickSettingsView = new MinimapQuickSettingsView(this)
        @quickSettingsSubscription = @quickSettingsView.onDidDestroy =>
          @quickSettingsView = null

        @quickSettingsView.attach()
        {top, left} = @getBoundingClientRect()
        @quickSettingsView.css({
          top: top + 'px'
          left: (left - @quickSettingsView.width()) + 'px'
        })

  disposeOpenQuickSettings: ->
    @controls.removeChild(@openQuickSettings)
    @openQuickSettings = undefined

  pauseDOMPolling: ->
    @domPollingPaused = true
    @resumeDOMPollingAfterDelay ?= debounce(@resumeDOMPolling, 100)
    @resumeDOMPollingAfterDelay()

  resumeDOMPolling: ->
    @domPollingPaused = false

  resumeDOMPollingAfterDelay: null

  pollDOM: ->
    return if @domPollingPaused or @updateRequested

    if @width isnt @clientWidth or @height isnt @clientHeight
      @measureHeightAndWidth()
      @requestForcedUpdate()

  measureHeightAndWidth: ->
    @height = @clientHeight
    @width = @clientWidth
    canvasWidth = @width

    return unless @isVisible()

    if @adjustToSoftWrap
      lineLength = atom.config.get('editor.preferredLineLength')
      softWrap = atom.config.get('editor.softWrap')
      width = lineLength * @minimap.getCharWidth()

      @marginRight = width - @width if softWrap and lineLength and width < @width
      canvasWidth = width
    else
      delete @marginRight

    if canvasWidth isnt @canvas.width or @height isnt @canvas.height
      @canvas.width = canvasWidth * devicePixelRatio
      @canvas.height = (@height + @minimap.getLineHeight()) * devicePixelRatio

  getTextEditor: -> @minimap.getTextEditor()

  getTextEditorElement: ->
    @editorElement ?= atom.views.getView(@getTextEditor())

  getTextEditorElementRoot: ->
    editorElement = @getTextEditorElement()

    editorElement.shadowRoot ? editorElement

  getDummyDOMRoot: (shadowRoot) ->
    if shadowRoot
      @getTextEditorElementRoot()
    else
      @getTextEditorElement()

  requestUpdate: ->
    return if @frameRequested


    @updateCanvas()

  setDisplayCodeHighlights: (@displayCodeHighlights) ->
    @requestForcedUpdate() if @attached

  pauseDOMPolling: ->
    @domPollingPaused = true
    @resumeDOMPollingAfterDelay ?= debounce(@resumeDOMPolling, 100)
    @resumeDOMPollingAfterDelay()

  resumeDOMPolling: ->
    @domPollingPaused = false

  resumeDOMPollingAfterDelay: null

  pollDOM: ->
    return if @domPollingPaused or @updateRequested

    if @width isnt @clientWidth or @height isnt @clientHeight
      @measureHeightAndWidth()
      @requestForcedUpdate()

  measureHeightAndWidth: ->
    @height = @clientHeight
    @width = @clientWidth
    canvasWidth = @width

    return unless @isVisible()

    if @adjustToSoftWrap
      lineLength = atom.config.get('editor.preferredLineLength')
      softWrap = atom.config.get('editor.softWrap')
      width = lineLength * @minimap.getCharWidth()

      @marginRight = width - @width if softWrap and lineLength and width < @width
      canvasWidth = width
    else
      delete @marginRight

    if canvasWidth isnt @canvas.width or @height isnt @canvas.height
      @canvas.width = canvasWidth * devicePixelRatio
      @canvas.height = (@height + @minimap.getLineHeight()) * devicePixelRatio

  #    ######## ##     ## ######## ##    ## ########  ######
  #    ##       ##     ## ##       ###   ##    ##    ##    ##
  #    ##       ##     ## ##       ####  ##    ##    ##
  #    ######   ##     ## ######   ## ## ##    ##     ######
  #    ##        ##   ##  ##       ##  ####    ##          ##
  #    ##         ## ##   ##       ##   ###    ##    ##    ##
  #    ########    ###    ######## ##    ##    ##     ######

  observeConfig: (configs={}) ->
    for config, callback of configs
      @subscriptions.add atom.config.observe config, callback

  mousePressedOverCanvas: ({pageY, target}) ->
    y = pageY - target.getBoundingClientRect().top
    row = Math.floor(y / @minimap.getLineHeight()) + @minimap.getFirstVisibleScreenRow()
