Unity 之 ToLua框架中UI.Dropdown组件动态添加Options

举报
陈言必行 发表于 2021/08/13 22:14:46 2021/08/13
【摘要】 前言 最近使用ToLua框架使用Unity中的Dropdown组件,其他属性都还好和在C#中使用的形式差不多,只是修改成了Lua的语法习惯就可以了,但是我有个需求,是要需要实现动态添加Dropdown中的Options,这个就很做起来废了半天劲,后来发现是被坑了,本文就说说在ToLua框架中使用Dropdown动态添加Options。 Unity 之...

前言

最近使用ToLua框架使用Unity中的Dropdown组件,其他属性都还好和在C#中使用的形式差不多,只是修改成了Lua的语法习惯就可以了,但是我有个需求,是要需要实现动态添加Dropdown中的Options,这个就很做起来废了半天劲,后来发现是被坑了,本文就说说在ToLua框架中使用Dropdown动态添加Options。

一,在C#中动态添加Options

1.获取Dropdown组件,然后动态添加options:

  //创建Dropdown自定义预制体,并获取其组件 Dropdown dropDown= GetPoolItem(rowRoot, "CreateRoom_Dropdown").GetComponent<Dropdown>(); Dropdown.OptionData data = new Dropdown.OptionData(); data.text = "下拉选项1"; dropDown.options.Add(data);

  
 
  • 1
  • 2
  • 3
  • 4
  • 5

或者你也可以这么写:

	List<Dropdown.OptionData> listOptions = new List<Dropdown.OptionData>(); listOptions.Add(new Dropdown.OptionData("下拉选项2")); listOptions.Add(new Dropdown.OptionData("下拉选项3")); dropDown.AddOptions(listOptions);

  
 
  • 1
  • 2
  • 3
  • 4

2.其他属性获取简介推荐查看:
Unity 之 UGUI Dropdown组件使用简析


二,在Lua中动态添加Options

1.首先要在CustomSettings中添加_GT(typeof(Dropdown.OptionData))
CustomSettings
2.在工程中点击Lua --> Generate All 重新打出Warp包
Generate
3.然后你在工程LuaFramework --> Source --> Generate 目录下可以找到名字为UnityEngine_UI_Dropdown_OptionDataWrap的C#文件,然后看下Register方法,开始使用:

	public static void Register(LuaState L)
	{
		L.BeginClass(typeof(UnityEngine.UI.Dropdown.OptionData), typeof(System.Object));
		L.RegFunction("New", _CreateUnityEngine_UI_Dropdown_OptionData);
		L.RegFunction("__tostring", ToLua.op_ToString);
		L.RegVar("text", get_text, set_text);
		L.RegVar("image", get_image, set_image);
		L.EndClass();
	}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

4.使用Lua动态添加添加Options

在文件头做个引用

local OptionData = UnityEngine.UI.Dropdown.OptionData 

  
 
  • 1

按照C#中写的步骤使用Lua的形势写:

function CreateDropdown(ctrlNodel,rowParent)
	-- 这里改成你自己的获取组件的方式
	local newDorpDown = resMgr:LoadPrefab(PrefabsPath.."CreateRoom_Dropdown",rowParent):GetComponent("Dropdown");
	-- 这是一个错误写法 正确需要用.调用
	local data = OptionData:New();
	data.text = "下拉选项1";
	newDorpDown.options:Add(data);
end

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

按照这个流程写是没有问题的,如果你这时候运行后成功设置了options属性了,那么你就不用往下看了;如果你没有运行成功,请你断点调试或者在代码中间打几个日志。经查:我发现代码是在local data = OptionData:New();这行就执行出了问题,就没有向下执行了。


三,在Lua中使用需要注意的

不知道为什么在New的时候执行逻辑会有问题,上面介绍过了,在UnityEngine_UI_Dropdown_OptionDataWrap
这个类里面,Lua中调用的New方法实际上走的是C#中的_CreateUnityEngine_UI_Dropdown_OptionData这个方法,看上面Register这个方法这样写的:

L.RegFunction("New", _CreateUnityEngine_UI_Dropdown_OptionData);

  
 
  • 1

所以我去查看这个方法:


	[MonoPInvokeCallbackAttribute(typeof(LuaCSFunction))]
	static int _CreateUnityEngine_UI_Dropdown_OptionData(IntPtr L)
	{
		try
		{ int count = LuaDLL.lua_gettop(L); if (count == 0) { UnityEngine.UI.Dropdown.OptionData obj = new UnityEngine.UI.Dropdown.OptionData(); ToLua.PushObject(L, obj); return 1; } else if (count == 1 && TypeChecker.CheckTypes<UnityEngine.Sprite>(L, 1)) { UnityEngine.Sprite arg0 = (UnityEngine.Sprite)ToLua.ToObject(L, 1); UnityEngine.UI.Dropdown.OptionData obj = new UnityEngine.UI.Dropdown.OptionData(arg0); ToLua.PushObject(L, obj); return 1; } else if (count == 1 && TypeChecker.CheckTypes<string>(L, 1)) { string arg0 = ToLua.ToString(L, 1); UnityEngine.UI.Dropdown.OptionData obj = new UnityEngine.UI.Dropdown.OptionData(arg0); ToLua.PushObject(L, obj); return 1; } else if (count == 2) { string arg0 = ToLua.CheckString(L, 1); UnityEngine.Sprite arg1 = (UnityEngine.Sprite)ToLua.CheckObject(L, 2, typeof(UnityEngine.Sprite)); UnityEngine.UI.Dropdown.OptionData obj = new UnityEngine.UI.Dropdown.OptionData(arg0, arg1); ToLua.PushObject(L, obj); return 1; } else { return LuaDLL.luaL_throw(L, "invalid arguments to ctor method: UnityEngine.UI.Dropdown.OptionData.New"); }
		}
		catch (Exception e)
		{ return LuaDLL.toluaL_exception(L, e);
		}
	}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46

这是框架个自动生成的方法啊,看起来没问啊,,,有不带参数的,一个参数的,两个参数的校验,并且有异常校验,简直是完美啊。然而为什么我上面的调用不好用呢,有些想不明白。

我尝试使用一个参数的形式调用:

function CreateDropdown(ctrlNodel,rowParent)
	-- 这里改成你自己的获取组件的方式
	local newDorpDown = resMgr:LoadPrefab(PrefabsPath.."CreateRoom_Dropdown",rowParent):GetComponent("Dropdown");
	local data = OptionData:New("下拉选项1");
	newDorpDown.options:Add(data);
end

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

结果运行起来还是不好使,两个参数的我也尝试了,结果当然还是不行。
我开始怀疑这个自动生成的这Warp文件执行的有问题啊,我在下图位置加了个日志:
日志
运行起来果然有问题,我写的调用的无参数的然而输出的参数个数却是1个:

local data = OptionData:New();

  
 
  • 1

调用
同理我尝试了传一个参数调用,输出的参数个数是2个,事实证明当我使用OptionData:New();这种形式调用的时候,会默认传递一个参数,,,

默认参数,,,嗯,,,思考了下,学习Lua的时候使用冒号(:)调用的时候就会传递一个self啊,,,然后我尝试使用(.)来调用,,,结果就真的没问题了,真是坑啊,,,还是自己没有使用明白啊,,,以此来博文,来加深下印象,希望可以帮到遇到相关问题的你。


修改后调用代码如下:

function CreateDropdown(ctrlNodel,rowParent)
	-- 这里改成你自己的获取组件的方式
	local newDorpDown = resMgr:LoadPrefab(PrefabsPath.."CreateRoom_Dropdown",rowParent):GetComponent("Dropdown");
	local data = OptionData.New("下拉选项1");
	newDorpDown.options:Add(data);
end

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

文章来源: czhenya.blog.csdn.net,作者:陈言必行,版权归原作者所有,如需转载,请联系作者。

原文链接:czhenya.blog.csdn.net/article/details/105552049

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。