Lua (实现无线滑动列表)

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档


前言

提示:这里可以添加本文要记录的大概内容:
Lua实现无线滑动列表,本篇的滑动是根据Scroll View拖动 Content 来实现无限滑动


提示:以下是本篇文章正文内容,下面案例可供参考

一、无线滑动是什么

当你的Scroll View 中要展示大量数据时候,但是Scroll View的可视范围就只有一块 。那么你是要将所有的数据都实例化,还是只实例化 可视范围内的 物体,这就是无线滑动的需求

二、使用步骤

1.面对对象 创建一个类

代码如下(示例):

初始化类中需要的数据
local cutom = Obj_Plus.class()

function cutom:ctor()
   --实例化Itme的路径
    self.itemResName=nil;
    
    --履带对象
    self.content=nil;
    
    --可视范围高
    self.viewProtH=0;
    
    --当前实例化的格子对象
    --封装了几个模拟字典的方法
    self.nowShowItems={

        ContainsKey=function (key)
            local flag=false;
                        if self.nowShowItems[key]~=nil then
                            flag=true;
                        end
            return flag;
        end;
        Remove=function (key)
                    self.nowShowItems[key]=nil;
        end;
       Add=function (key,value)
        self.nowShowItems[key]=value;
       end;
    };
    
    --数据来源
    self.items={};
    
    --记录上一次显示的最小索引范围
    self.oldMinIndex=0;
    
    --记录上一次显示的最大索引范围
    self.oldMaxIndex=0;
    
    --格子的宽高
    self.itemW=0;
    self.itemH=0;
   
    --格子的行列
    self.col=0;

    --格子排序的类型
    self.type=nil;
   --格子的宽高
   self.intervalW=nil;
   self.intervalH=nil;

end

2. 初始化所有信息

#代码如下(示例):

--初始化实例化 Item路径  
function InitResName(self,name)
    self.itemResName=name;
end

---初始化履带长度
function InitInfos(self,items)
    self.items=items;
    --初始化履带长度Content的高
    self.content.sizeDelta =  Vector2(0, Mathf.CeilToInt(#items/ self.col) * (self.itemH+self.intervalW))
    --end
end


--[[<summary>
    /// 初始化格子间隔大小 以及 有几行几列
    /// </summary>
    /// <param name="w">格子宽</param>
    /// <param name="h">格子高</param>
    /// <param name="col">列数</param>
    /// <param name="intw">间隔宽</param>
    /// <param name="inth">间隔高</param>
   
   --]]
function InitSizeAndCol(self, w,h,col,intw,inth)
    self.itemW=w;
    self.itemH=h;
    self.col=col;
    self.intervalW=intw;
    self.intervalH=inth;
end

--初始化 可视范围 以及
function InitContentAndSvn(self,trans,h)
    self.viewProtH=h;
    self.content=trans;
end

3.更新可视化范围的内容 (重点)

-- 跟新格子显示的方法

function CheckShowOrHide(self)
    --检测哪些格子应该显示出来
    local minIndex = math.floor((self.content.anchoredPosition.y / (self.itemH+self.intervalH)) *self.col);
    local maxIndex = math.floor(((self.content.anchoredPosition.y + self.viewProtH) / (self.itemH+self.intervalH)) * self.col + self.col - 1);

        if minIndex < 1 then
            minIndex=1;
        end
        if (minIndex ~= self.oldMinIndex or maxIndex ~= self.oldMaxIndex) then
            --在记录索引之前 
            --根据上一次索引和这一次心酸出来的索引 用来判断 那些改移除

            --移除上一节溢出
                for i =self.oldMinIndex , self.oldMaxIndex do
                        if self.nowShowItems.ContainsKey(i) then
                            if(self.nowShowItems[i]~=nil)then
                                Destroy(self.nowShowItems[i]);
                               
                                self.nowShowItems.Remove(i);
                            end
                        end
                end

            --移除下一节溢出
            for i =maxIndex+1 , self.oldMaxIndex do
                if self.nowShowItems.ContainsKey(i) then
                    if(self.nowShowItems[i]~=nil)then
                        Destroy(self.nowShowItems[i]);
                        print(2);
                        self.nowShowItems.Remove(i);
                    end
                end
            end
        end
        self.oldMinIndex = minIndex;
        self.oldMaxIndex = maxIndex;
    
        for i = minIndex, maxIndex do
           
            if self.nowShowItems.ContainsKey(i) then

            else
               
              --根据这个关键索引 用来设置位置  初始化道具信息
               local  index=i;
                self.nowShowItems.Add(index,nil);
               local go=GameObject.Instantiate(Resources.Load(self.itemResName));
                go.transform:SetParent(self.content,false);
                go.transform.localScale=Vector3.one;
                local x=(math.floor(index-1)%self.col)*(self.itemW+self.intervalW);
                local y=-math.floor((index-1)/self.col)* (self.itemH+self.intervalH);
                local v3=Vector3(x,y,0);
                go.transform.localPosition=v3;
                local c= BagItem.new(go);
                c:Info(self.items[index]);
                
              
                 if self.nowShowItems[index]~=nil then
                    self.nowShowItems[index]=go;
                else
                    self.nowShowItems[index]=go;
                end
            end
        end
end

4.测试

需要注意的点 是更新方法实在 Update中每帧执行的

local listint={};

local can=GameObject.Find("Content");
local a = Custom.new();
function LuaStart()
    print(1);
   
    for i = 1, 100 do
        -- body
        listint[i]=i;
    end

    a:InitResName("BagItem");
    a:InitSizeAndCol(100, 100, 3,20,20);
    a:InitContentAndSvn(can.transform, 320)
     a:InitInfos(listint);
end;

function LuaUpdate()
    a:CheckShowOrHide();
end

5.总结

这里知识实现了无限滑动列表 但是并没有通过对象池进行缓存 ,只是简单的生成在删除,如果需要内存优化个位可以 自行优化
好了, 今天就是这样, 希望对大家有所帮助.

  • 3
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值