zyedidia / SFML.jl

A binding of the game and multimedia library SFML for Julia
Other
93 stars 22 forks source link

Vertex array issues: don't appear when drawn, incorrect getbounds result, and segfault when accessing texCoords #10

Closed tom--lee closed 8 years ago

tom--lee commented 8 years ago

I am having trouble drawing VertexArrays. They simply don't appear on the screen. This may or may not be linked to incorrect output from getbounds, and to the fact that when a vertex is access via get_vertex, we get a segfault when accessing the texCoord field. Here is some code that reproduces the issues. The segfaulting line is commented out:

using SFML

function test()

    va = VertexArray()
    SFML.set_primitive_type(va, SFML.triangles)

    #three vertices to make a triangle
    v1 = Vertex(Vector2f(0,0), SFML.green, Vector2f(0,0))
    v2 = Vertex(Vector2f(100,0), SFML.green, Vector2f(0,0))
    v3 = Vertex(Vector2f(100,100), SFML.green, Vector2f(0,0))
    append(va,v1)
    append(va,v2)
    append(va,v3)

    @show getbounds(va) # <-- this gives an incorrect result

    #get the first vertex
    gv = get_vertex(va, 0)

    # the original v1 members can be accessed without issue
    @show v1.position #ok
    @show v1.color #ok
    @show v1.texCoords #ok

    #but when we try to use gv.texCoords we get a segfault
    @show gv.position #ok
    @show gv.color #ok
    # @show gv.texCoords #segfault

    #
    window = RenderWindow("Input Example", 600, 600)
    event = Event()

    #use a circle as a control
    circle = CircleShape()
    set_position(circle, Vector2f(400.0, 400.0))
    set_radius(circle, 30)
    set_fillcolor(circle, SFML.red)

    while isopen(window)
        while pollevent(window, event)
            if get_type(event) == EventType.CLOSED
                close(window)
            end
        end

        clear(window, SFML.black)
        draw(window, circle) #drawn
        draw(window, va) #not drawn :(
        display(window)
    end
end

test()

I have tried and failed to get any further than this. Happy to help debug if I can.

zyedidia commented 8 years ago

I'm not sure what the problem is here, although clearly it's not working. Vertex arrays have never really worked quite right in SFML.jl. Maybe you should try testing them in CSFML or SFML (version 2.2) and see if you get the same sorts of problems. I don't know if it's a Julia, CSFML or SFML.jl problem, although I can't see any bugs in the code.

Could you tell me what you are trying to do with vertex arrays because there may be a way to accomplish the same thing with convex shapes or lines.

tom--lee commented 8 years ago

I can definitely just work with convex shapes and lines. But vertex arrays could let me reduce the number of draw calls and improve performance - not a problem for me yet, but possibly in the future.

zyedidia commented 8 years ago

Ok, I think I've found the reason for the bug, although I still don't know how to fix it. Julia seems to be adding padding to the Vertex type whereas CSFML is expecting no padding. sizeof(Vertex) in Julia returns 24, but in C returns 20. If you know of a way to keep Julia from adding padding to types, please tell me. Otherwise I'll look for other solutions. At worst, I can write some C code which converts the structs to pointers and back.

zyedidia commented 8 years ago

I found a fix for this issue, but it involves making the Vector2f, Color, and Vertex types immutable, and I'm not sure I want to do that. The problem is that since these types aren't immutable, isbits() does not return true for them which means that when they are used in the Vertex type, Julia adds extra type tags and padding. It would be nice if there was a way to have mutable isbits types.

tom--lee commented 8 years ago

Thanks for looking into it! I'm certainly no expert on the intricacies of the interaction between Julia and C, and I don't know any other way to deal with the padding.

Is there any particular reason not to make these types immutable? That seems far more natural to me, since a vector/vertex/color is uniquely defined by its value. In any case, it is good to know I can modify my own fork to get this working if I need it. Thanks again!

dfannius commented 8 years ago

For what it's worth, it seems reasonable to me for those types to be immutable.

jw3126 commented 8 years ago

Are there any reasons against making these and similar types immutable?