Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

In this Discussion

A simple text class

RooRoo
edited May 2012 in General Posts: 2

I made this simple class the create text.


Text = class()

function Text:init(string, x, y)
    -- optional parameters
    self.string = string or ""
    self.x = x or 0
    self.y = y or 0
    -- Codea defaults
    self.fill = fill()
    self.font = font()
    self.fontSize = fontSize()
    self.textAlign = textAlign()
    self.textMode = textMode()
    self.textWrapWidth = textWrapWidth()
end

function Text:draw()
    pushStyle()
    
    resetStyle()
    
    if self.fill then
        fill(self.fill)
    else
        noFill()
    end
    
    fontSize(self.fontSize)
    font(self.font)
    
    textAlign(self.textAlign)
    textMode(self.textMode)
    textWrapWidth(self.textWrapWidth)
    text(self.string, self.x, self.y)
    
    popStyle()
end

I can set all the text's properties and it uses pushStyle() resetStyle() and popStyle() to preserve the properties when drawing. The optional parameters allow me to create a valid object and then set the properties at a later time and all the properties are initially set with Codea's defaults.

Now I'm trying to set width and height for the class, but I'm having difficulty. The text's dimensions are accessed using the textSize() function however, the return value are dependent of the style properties applied to it. Therefore, I need to apply the styles before I can set the dimension of my width and height. I thought of simply placing the set of the width and height in the draw function before the pushStyle(). But, if a programmer needs to use the text's dimensions in another object declaration they won't be properly set. I also, thought to call the draw function once from the constructor to insure the values are set (dispute this being a silly idea), but even then if a programmer sets the font size after he or she creates the object the dimensions will not be corrected until after the next draw call. Any thoughts or ideas on a solution?

Also, a side note, I was thinking about creating a game making library for Codea. I've used Flixel for a while now and would like to create something similar for Codea. If anyone has ideas or wants to get the ball rolling let me know.

Thanks

Tagged:

Comments

  • SimeonSimeon Admin Mod
    Posts: 5,054

    So are you thinking of providing width and height purely as getters? You could try the following:

    function Text:size()
        pushStyle()
    
        -- Set all the styles
    
        local w,h = textSize( self.string )
    
        popStyle()
    
        return w,h
    end
    

    Or maybe you could do the following:

    function Text:__index( key )
        if key == "width" then
            local w,_ = self:size()
            return w
        elseif key == "height" then
            local _,h = self:size()
            return h
        end
    end
    

    This would allow you to access myText.width and myText.height, each access would compute the size from scratch. You could get clever and cache the size once computed, and then set a dirty flag if one of the Text object's properties changes.

  • RooRoo
    Posts: 2

    With your code I get error: [string "function setup()..."]:9: attempt to call method 'draw' (a nil value) Pausing playback. Think it has to do with the __index function not calling functions properly.

  • SimeonSimeon Admin Mod
    edited May 2012 Posts: 5,054

    Sorry @Roo that's a big oversight on my part.

    Unfortunately rawset and rawget are disabled in Codea. I'll be re-enabling them after Codea 1.4 but it makes overriding __index impossibly awkward. (Or just impossible)

    The __index method should return rawget(self, key) at the end, and __newindex should do rawset(self, key,value) but of course, they can't.

    Edit: Though what about the Text:size() method, do you see any disadvantages to it?

Sign In or Register to comment.