unity怎么通过lua加载一个游戏对象

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了unity怎么通过lua加载一个游戏对象相关的知识,希望对你有一定的参考价值。

参考技术A 创建新的Unity工程并且导入SLua框架 使用已经注入UnityEngie引擎的状态机对象LuaSvr调用Lua脚本 AppDelegate.cs using UnityEngine; using System.Collections; using SLua; public class Main : MonoBehaviour private LuaSvr lua_svr; // Us。

Unity lua红点系统

红点基本上是游戏中必备的吧,红点遍地有,所以需要一套统一的红点系统来管理。

lua中判断Unity对象是否为空

--判断unity对象是否为空, 如果你有些对象是在c#删掉了,lua不知道
function IsNil(uobj)
    if (uobj == nil) then
        return true
    end
    if (uobj:Equals(nil)) then
        return true
    end
    return false
end

红点注册

new_tip_register = {}
local this = new_tip_register

local LASTNUMBER = 99999

--红点枚举(第一步:注册红点枚举)
Enum_New = {
    NEW_ALL = 999999, --遍历所有用

    ------------------------------------红点-----------------------------------
    NEW_CHANGESTATE_MAIN = 1, --主界面右下角切换按钮

    NEW_FACTION_MAIN = 2, --主界面帮会按钮(主界面帮会入口ID)
    NEW_FACTION_MEMBER = 3, --帮会成员
    NEW_FACTION_MAIN_RED_PACKET = 4, --帮会成员红包按钮
    NEW_FACTION_MEMBER_RECRUIT = 5, --帮会成员招募按钮
    NEW_FACTION_MEMBER_BUILDING = 6, --帮会建筑
    NEW_FACTION_BUILD = 7, --帮会大厅
    NEW_FACTION_BUILD_WEALFAREPANEL = 8, --帮会福利
    NEW_FACTION_BUILD_SIGNE = 9, --帮会签到
    NEW_FACTION_BUILD_WEALFAREBOX = 10, --福利宝箱
    NEW_FACTION_BUILD_ACCOUNT = 11, --帮会建筑账房
    NEW_FACTION_BUILD_ACCOUNT_WELFARE_ONE = 12, --帮会建筑福利
    NEW_FACTION_BUILD_ACCOUNT_WELFARE_TWO = 13,

    NEW_FACTION_MAIN_PANDECT = 14, --帮会总览
    NEW_FACTION_LEVEL_UP = 15, --总览界面升级按钮
    --帮会大厅下的升级按钮
    NEW_FACTION_HALL_MAIN = 16, --帮会主厅(大厅)
    NEW_FACTION_HALL_SHOP = 17, --帮会商店(大厅)
    NEW_FACTION_HALL_BINGJIA = 18, --帮会兵甲(大厅)
    NEW_FACTION_HALL_FANGJU = 19, --帮会防具(大厅)
    NEW_FACTION_HALL_SHOUSHI = 20, --帮会首饰(大厅)
    NEW_FACTION_HALL_SHOP_SELL = 21, --帮会商店物品上架
    NEW_FACTION_BUILD_FACTIONSKILL = 22, --帮会技能
}

--[[--(第二步:注册红点枚举关系)
 * @Description: 红点关系列表(主要控制根节点红点状态,父节点状态会根据子节点状态刷新)
]]
local EnumNewList = {
    --主界面右下角切换按钮
    [Enum_New.NEW_CHANGESTATE_MAIN] = {
        --帮会
        [Enum_New.NEW_FACTION_MAIN] = {
            [Enum_New.NEW_FACTION_MAIN_PANDECT] = --总览
            {
                [Enum_New.NEW_FACTION_LEVEL_UP] = LASTNUMBER, --升级
            },
            [Enum_New.NEW_FACTION_MEMBER] = {   --成员
                [Enum_New.NEW_FACTION_MEMBER_RECRUIT] = LASTNUMBER, --招募
                [Enum_New.NEW_FACTION_MAIN_RED_PACKET] = LASTNUMBER, --红包
            },
            [Enum_New.NEW_FACTION_MEMBER_BUILDING] = {         --建筑
                [Enum_New.NEW_FACTION_BUILD] = {    --大厅
                    [Enum_New.NEW_FACTION_HALL_MAIN] = LASTNUMBER,
                    [Enum_New.NEW_FACTION_HALL_SHOP] = LASTNUMBER,
                    [Enum_New.NEW_FACTION_HALL_BINGJIA] = LASTNUMBER,
                    [Enum_New.NEW_FACTION_HALL_FANGJU] = LASTNUMBER,
                    [Enum_New.NEW_FACTION_HALL_SHOUSHI] = LASTNUMBER,
                },
                [Enum_New.NEW_FACTION_BUILD_ACCOUNT] = {    --账房
                    [Enum_New.NEW_FACTION_BUILD_ACCOUNT_WELFARE_ONE] = LASTNUMBER,
                },
                [Enum_New.NEW_FACTION_HALL_SHOP_SELL] = LASTNUMBER,
            },

            [Enum_New.NEW_FACTION_BUILD_WEALFAREPANEL] = {  --福利
                [Enum_New.NEW_FACTION_BUILD_SIGNE] = LASTNUMBER, --签到
                [Enum_New.NEW_FACTION_BUILD_FACTIONSKILL] = LASTNUMBER, --帮会技能
                [Enum_New.NEW_FACTION_BUILD_WEALFAREBOX] = --宝箱
                {
                    [Enum_New.NEW_FACTION_BUILD_ACCOUNT_WELFARE_TWO] = LASTNUMBER,
                },
            },
        },
    }
}

---------------外调-----------------
--获得红点枚举树结构
function this.GetEnumNewList()
    return EnumNewList
end
----------------------------------

红点系统

--第一步:红点枚举
--new_tip_register
--第二步:绑定红点显示节点
--new_tip_register
require "logic/common/new_tip_register"

new_tip_system = {}
local this = new_tip_system

--变量声明
local newInfoList = nil
local LASTNUMBER = 99999

--内部方法声明
local InitNewTable = nil
local FreshAllRootNewState = nil
local SetActiveNew = nil
local RefreshCharacterAttr = nil
local SetOrGetStateEnum = nil
local PrintTrueLeaf = nil
local GetSubTree = nil
local curHeroLevel = nil
local EnumNewList = nil 
---------------外调开始-----------
function new_tip_system.Init()
    EnumNewList = {}
    EnumNewList = new_tip_register.GetEnumNewList()
    newInfoList = {}
    InitNewTable(EnumNewList)
    Notifier.regist(cmdName.MSG_REFRESH_CHARACTER_ATTR,RefreshCharacterAttr)
end

function new_tip_system.UnInit()
    newInfoList = nil
    EnumNewList = nil
    Notifier.remove(cmdName.MSG_REFRESH_CHARACTER_ATTR,RefreshCharacterAttr)
end

--[[--(第三步:注册刷新红点状态或gameobject)
 * @Description: 注册红点状态  注意:父节点只需要设置gameobject,如果设置了状态也会被根节点状态改变掉
 @isActive  是否显示(可为空)
 @objNew  红点GameObject(可为空)
 @level   等级限制入口(比如入口等级,如果有等级限制Gameobject显影的时候设置等级,没有不设置)
]]
function new_tip_system.RegisterNewState(enumNew,isActive,objNew,level)
    -- Trace("RegisterNewState:"..tostring(enumNew).."  newInfoList:"..tostring(objNew).." isActive:"..tostring(isActive))
    if curHeroLevel == nil then
        curHeroLevel = data_center.GetPlayerUintValue(U_ACTOR_BASE_GRADE_ATTR)
    end
    if newInfoList ~= nil and newInfoList[enumNew] ~= nil then
        local isNeedFresh = false
        if isActive ~= nil then
            if newInfoList[enumNew].state ~= isActive then
                SetOrGetStateEnum(enumNew,isActive)
                isNeedFresh = true
            end
        end

        if not IsNil(objNew) then
            newInfoList[enumNew].objNew = objNew
            newInfoList[enumNew].widgetNew = componentGet(objNew.transform,typeof(UIWidget))
        end

        if level ~= nil then
            newInfoList[enumNew].level = level
            isNeedFresh = true
        end

        if isNeedFresh then
            FreshAllRootNewState(EnumNewList,enumNew)
            Notifier.dispatchCmd(cmdName.MSG_NEW_TIP_CHANGE,enumNew)
        end
        
        SetActiveNew(enumNew,SetOrGetStateEnum(enumNew))
    end
end

function new_tip_system.RemoveRegisterNewState(enumNew)
    if newInfoList[enumNew] ~= nil then
        SetActiveNew(enumNew,false)

        newInfoList[enumNew].objNew = nil
        newInfoList[enumNew].widgetNew = nil
    end
end

--[[--
 * @Description: 获取红点状态
]]
function new_tip_system.GetNewState(enumNew)
    if not table.IsNullOrEmpty(newInfoList) and not table.IsNullOrEmpty(newInfoList[enumNew]) then
        return newInfoList[enumNew].state
    end
    return false
end

--[[--
 * @Description: 打印使所给节点为true的叶节点
]]
function new_tip_system.PrintTreeTrueLeaf(enumNew)
    local subTree = GetSubTree(EnumNewList,enumNew)
    if subTree == nil then
        Trace(string.format("节点%s不存在",enumNew))
    elseif SetOrGetStateEnum(enumNew) ~= true then
        Trace(string.format("节点%s不为true",enumNew))
    elseif subTree == LASTNUMBER then
         Trace(string.format("节点%s为叶节点",enumNew))
    elseif subTree ~= LASTNUMBER then
         Trace("被查找的中间节点:"..tostring(enumNew))
        PrintTrueLeaf(subTree)
    end
end
---------------外调结束-----------

---------------内部函数开始-----------
function InitNewTable(newList)
    for k,v in pairs(newList) do
        local newItem = {}
        newItem.objNew = nil
        newItem.state = false
        newInfoList[k] = newItem

        if v ~= LASTNUMBER then
            InitNewTable(v)
        end
    end
end

--[[--
 * @Description: 刷新变更子节点所有父节点红点的状态
   @newList:关系列表
   @enumNew:变更红点枚举
]]
function FreshAllRootNewState(newList,enumNew)
    -- Trace("FreshAllRootNewState--------------:"..tostring(enumNew))
    local result = false
    local enumNewTarget = nil
    for k,v in pairs(newList) do
        local active = false
        local target = nil
        if v ~= LASTNUMBER then
            if k ~= enumNew then
                local tmpTarget = nil
                active,tmpTarget = FreshAllRootNewState(v,enumNew)

                active = SetOrGetStateEnum(k,active)

                if tmpTarget ~= nil then
                    target = k
                    --刷新目标父节点状态
                    SetActiveNew(k,active)
                end
            else
                active = SetOrGetStateEnum(k)
                target = k
            end
        else
            active = SetOrGetStateEnum(k)

            if k == enumNew then
                target = k
            end
        end

        if enumNew == Enum_New.NEW_ALL then
            SetActiveNew(k,active)
        end
        --优化:减少搜索次数  找到变更节点并且result为true可以直接break(结果已知不用向下查找)
        if active then
            result = true

            if enumNewTarget ~= nil then
                break
            end
        end

        if target ~= nil then
            enumNewTarget = target

            if result then
                break
            end
        end
    end

    return result,enumNewTarget
end

function SetActiveNew(typeEnum,isActive)
    if not IsNil(newInfoList[typeEnum].objNew) then
        newInfoList[typeEnum].objNew:SetActive(isActive)
    end
end

--[[--
 * @Description: 设置或获取红点状态(并根据等级返回最终状态,实际状态还保存)
]]
function SetOrGetStateEnum(typeEnum,state)
    if state ~= nil then
        newInfoList[typeEnum].state = state
    else
        state = newInfoList[typeEnum].state
    end

    if newInfoList[typeEnum].level ~= nil and newInfoList[typeEnum].level > curHeroLevel then
        state = false
    end
    return state
end

--[[--
 * @Description: 玩家等级改变刷新红点入口
]]
function RefreshCharacterAttr(param)
    if param ~= nil then
        for k,v in pairs(param) do
            if k == U_ACTOR_BASE_GRADE_ATTR then
                curHeroLevel = data_center.GetPlayerUintValue(U_ACTOR_BASE_GRADE_ATTR)
                FreshAllRootNewState(EnumNewList,Enum_New.NEW_ALL)
                break
            end
        end
    end
end

--[[--
 * @Description: 获得对应节点的子树
]]
function GetSubTree(newList,enumNew)
    for k,v in pairs(newList) do
        if k == enumNew then
            return v
        elseif v ~= LASTNUMBER then
            local ret = GetSubTree(v,enumNew)
            if ret ~= nil then
                return ret
            end
        end
    end
end

--[[--
 * @Description: 打印状态为true的叶节点
]]
function PrintTrueLeaf(newList)
    for k,v in pairs(newList) do
        if v ~= LASTNUMBER then
            PrintTrueLeaf(v)
        else
            if SetOrGetStateEnum(k) == true then
                 Trace("为true的叶节点:"..tostring(k))
            end
        end
    end
end

说明和使用

使用时需要注意Enum_New中的数值是唯一的,不要重复了,不然可能会导致子节点的红点状态变更了,但父节点的没得到相应的刷新。

使用时调用new_tip_system.RegisterNewState(enumNew,isActive,objNew,level)即可,父节点的状态会随着子节点的状态的改变而改变。

以上是关于unity怎么通过lua加载一个游戏对象的主要内容,如果未能解决你的问题,请参考以下文章

游戏开发框架自制Unity通用游戏框架UnityXFramework,详细教程(Unity3D技能树 | tolua | 框架 | 热更新)

游戏开发框架自制Unity通用游戏框架UnityXFramework,详细教程(Unity3D技能树 | tolua | 框架 | 热更新)

为啥Unity没有实现iOS平台代码热更新

新人求助.unity3d能不能用lua来写代码

lua如何继承unity类

如何通过脚本在 Unity 中重新定位和调整游戏对象的大小?