3

I'm using LuaInterface for .NET to create Windows Forms objects. This works pretty good except for one thing:

I want to use the Anchor property of Control to make them resize automatically. If I only set one of the Anchors (e.g. only AnchorStyles.Top), it works, but this doesn't really make sense. I have to set more than one Anchor, which is done by combining them with "bit-wise or" (or by just adding them numerically).

In VB.Net both works:

Dim myLabel As New Label()
myLabel.Anchor = AnchorStyles.Top
myLabel.Anchor = AnchorStyles.Top + AnchorStyles.Left + _
                 AnchorStyles.Bottom + AnchorStyles.Right

In Lua, this does work:

luanet.load_assembly("System.Windows.Forms")
local WinForms = luanet.System.Windows.Forms
local myLabel = WinForms.Label()
myLabel.Anchor = WinForms.AnchorStyles.Top

...but this additional line doesn't:

myLabel.Anchor = WinForms.AnchorStyles.Top + WinForms.AnchorStyles.Left + 
               WinForms.AnchorStyles.Bottom + WinForms.AnchorStyles.Right

It gives me the following error:

LuaInterface.LuaException: attempt to perform arithmetic on
field 'Top' (a userdata value)

which is in a sense correct as "LuaInterface treats enumeration values as fields of the corresponding enumeration typ" (says LuaInterface: Scripting the .NET CLR with Lua).


It is also not possible to assign the value as a number:

myLabel.Anchor = 15    -- 15 = 8 + 4 + 2 + 1 = Top+Left+Right+Bottom

This time, the error message is rather unspecific:

LuaInterface.LuaException: function

How can I work around this?

Is there a possibility to typecast the number to the correct enumeration type in Lua?

Mira Weller
  • 2,406
  • 22
  • 27
  • @phoog: It's not a duplicate, as the problem is not how to do bitwise operations, but to convert the result (either if calculated bitwise or via addition) to the correct enum type. I just used the addition here, because it is directly built-in to Lua and bitwise or is not. In VB/C# I use `or` / `|` as well. – Mira Weller Feb 16 '12 at 20:40

1 Answers1

1

I finally figured out how to do this. I used the ToObject method of System.Enum. It takes the enumeration type I want to convert it to, and the integer value to use.

The following is a code snippet from my helper library:

local EnumToObject, WinFormsAnchorStylesType = 
                luanet.get_method_bysig(luanet.System.Enum, "ToObject",
                                             "System.Type", "System.Int32"),
                luanet.System.Windows.Forms.AnchorStyles.Top:GetType()

AnchorTop, AnchorLeft, AnchorRight, AnchorBottom = 1, 4, 8, 2

function Anchor(flags)
  return EnumToObject(WinFormsAnchorStylesType, flags)
end

You use it like this:

Label1 = luanet.System.Windows.Forms.Label()
Label1.Anchor = Anchor(AnchorLeft + AnchorTop + AnchorRight + AnchorBottom)
Mira Weller
  • 2,406
  • 22
  • 27