This is a read-only snapshot of the ComputerCraft forums, taken in April 2020.
Sewbacca's profile picture

Rendering a line (OOP design)

Started by Sewbacca, 04 December 2016 - 09:36 PM
Sewbacca #1
Posted 04 December 2016 - 10:36 PM
Hey guys,
I am working on a window framework.
First, we have a (window (not from the original window API)).
(You have to use the : opperator for methods)

object data:
  • new()
  • render(number line)
  • window -> Table structured like the the tables in the window API
  • children -> Array, containing objects like this (children container)
  • parent -> Parent object
  • width/height
  • cursorX/cursorY
  • positionX/positionY -> in the parent container

I am strugling with the render method.


line = {
  text = text,,
  tCol = tCol,
  bCol = bCol
}
Here are my ideas, how to render a line:

Main: render the full line and blit it on the screen.

First idea:
  • Collect lines, displayed on the screen (for loop through object.chlidren)
  • render the lines, fitting into the screen and being ontop (object:render(line))
  • render own line (concat the lines)
But then you have to iterate through all childrens and their childrens and theirs…

Second idea:

Report changes on the screen and render them, but then you have to iterate also through all the childrens and then the program renders the line (I wanna have a process doing this).

Third idea after a long time: Ask a pro

Do you have any performance saving ideas?

Thanks in advance
Sewbacca
Edited on 04 December 2016 - 09:44 PM
KingofGamesYami #2
Posted 04 December 2016 - 11:31 PM
I heavily optimized the rendering of stitch, as it causes a lot of problems. For example, dropping my (in game) FPS to 0.

The witchcraft I utilized is tables, locals, and keeping track of which lines (y values) have been changed since last render. I had to account for multiple screens, which makes this even messier (you won't have to).

In case you want to look at it, here's the commented source code of my internal "update" function
Spoiler

local function update()
    if not bVisible then
        return
    end
    local currentY = 1 --how far down are we in the buffer?
    for y = 1, #tMonitors do --iterate through the rows of monitors
        local currentX, height = 1, tMonitorSizes[ y ][ 1 ][ 2 ] --how far right are we in the buffer, how high is the current monitor row?
        for x = 1, #tMonitors[ y ] do --iterate through the columns of monitors
            local mon = tMonitors[ y ][ x ] --the current monitor object
            local width = tMonitorSizes[ y ][ x ][ 1 ] --width of the current column
            for y = currentY, currentY + height do --iterate through the buffer, starting at the last pixel of the last monitor plus one, ending at the last pixel of this monitor
                if internalUpdatedLines[ y ] then --if the line was updated, we'll blit the entire line (CC updates this way, so no performance loss)
                    mon.setCursorPos( 1, y - currentY + 1 )
                    mon.blit( string_sub( internalText[ y ], currentX, currentX + width ), string_sub( internalTextColor[ y ], currentX, currentX + width ), string_sub( internalBackgroundColor[ y ], currentX, currentX + width ) )
                end
            end
            currentX = currentX + width --add the width of the current monitor column to the currentX value
        end
        currentY = currentY + height --add the height of the current monitor row to the currentY value
    end
    internalUpdatedLines = {} --reset the lines which need to be drawn
end
Bomb Bloke #3
Posted 05 December 2016 - 10:36 AM
So if I understand correctly, you don't intend to store writes to a child window within the parent window's buffer, and you also want to prevent writes to a parent window rendering on top of child windows?

My first thought is "more trouble than it's worth", but if I were to do such a thing, I'd rig each window to have a table tracking which of its children are "on top" for every character location within their bounds. This way, you only need to re-calculate things when a child window actually moves. Forget this "iterate through all children whenever anything is rendered" business.
Sewbacca #4
Posted 05 December 2016 - 11:42 AM
Maybe it would work.
KingGamesOfYami: You don't uses container, right?