nhn / gpm.unity

A brand of NHN providing free services required for game development.

Home Page:https://gameplatform.nhncloud.com/en/

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

InfiniteScroll 검색 리스트 데이터만 노출

Randomdog7153 opened this issue · comments

Service

  • WebView
  • AssetManagement
  • Communicator
  • LogViewer
  • Manager
  • UI
  • Profiler
  • Adapter
  • DLST

Version

Write the version that you are currently using.
GPM 2.2.5
Common 2.3.1
UI 2.7.3

Summary

A clear and concise description of what the question is.
InfiniteScroll 검색 리스트 데이터만 보이게 하는 법 문의 드립니다.

Screenshots

If applicable, add screenshots to help explain your question.

Additional context

Add any other context about the problem here.
클릭한 버튼마다 보여지는 데이터들을 다르게 하려고합니다. dataList는 초기화 없이 전체 리스트에서 인덱스를 구하기 위해 초기화를 하지 않았고, InfiniteScroll 속성인 스크롤리스트는 Clear를 해주고 새 데이터를 넣었습니다.
클릭한 버튼마다 보여지는 데이터들을 다르게 하는 것은 성공했습니다만, 데이터를 삭제하는 부분에서 인덱스 오류가 계속해서 납니다. 혹시 dataList도 초기화를 하고 다시 리스트를 넣어줘야하는 건가요?

스크롤리스트는 RemoveData(data);만 해주었습니다.


제가 삭제를 한 후 반영을 위해 UpdateAllData를 실행해주는데, 이 부분에서 스크롤리스트 아이템쪽에서 삭제되기전 인덱스를 가지고 있는 경우가 있어, UpdateData를 하는 과정에서 리스트에 존재하지 않는 인덱스가 넣어지는 문제였습니다.

@Randomdog7153
안녕하세요
GPM을 사용해 주셔서 감사드립니다.

담당자가 추선 연휴로 부재중이어서 연휴 끝나고 확인이 가능할 것 같습니다.
참고 부탁드립니다.

감사합니다.

@Randomdog7153
안녕하세요. 휴가로 확인이 늦었습니다.

문제가 해결된 것으로 확인됩니다.
해결이 안되셨거나 다른 문제가 있으시면 편하게 말씀 부탁드립니다.

감사합니다.

@smflt-nhn
안녕하세요.

문제가 해결된 줄 알았으나.. 확인해보니 해결이 깔끔하게 되지 않았습니다.
InfiniteScroll 에 존재하는 RemoveData를 사용해 스크롤에서 데이터를 삭제시켜주었습니다만,

클릭한 버튼마다 보여지는 데이터들을 다르게 하는 부분을 한번 실행시켜준 뒤, 다시 모든 데이터를 보여주는 버튼을 클릭 할 경우 위에서 말한 인덱스 관련 에러가 납니다.

RemoveData를 실행시켜준 후 GetItemCount 로 확인해보니 삭제시키기 전 Count와 삭제 시킨 후 Count 가 동일하더군요.
GetDataIndex 도 확인해보니, 정상적인 경우에는 인덱스가 찍히고 삭제된 후 -1 로 바뀌는 걸 확인했습니다.
에러가 나는 경우에는 인덱스가 -1 로 찍혀있었습니다. 이런 경우에는 삭제시킬 data를 잘못넣은건가요?

아래는 리스트 삭제시키는 함수 입니다.

public void RemoveShot()
{
    if (dataList.Count <= 0)
    {
        return;
    }

    if(isClubList == true)
    {
        clubShotList.Remove(PM._practicePlayer.ShotList[AnalysisManager.instance.deleteListIndex]);
    }
    PM._practicePlayer.ShotList.Remove(PM._practicePlayer.ShotList[AnalysisManager.instance.deleteListIndex]);
    AnalysisShotData data = dataList[AnalysisManager.instance.deleteListIndex]; // 전체 데이터에서 인덱스 통해 가져오기
    shotScrollList.RemoveData(data); // 인피니티 스크롤뷰에서의 삭제

    dataList.Remove(data);

    index = dataList.Count;

    ReLoadShotNo();
    InfiniteScrollReboot();
}

@Randomdog7153

안녕하세요.

해당 덧글 기반으로 예상 원인과 해결방안을 작성하였습니다.

확인 부탁드립니다.

InfiniteScrollData .RemoveData 동작 방식

InfiniteScrollData RemoveData(data) 함수를 호출할 때 아래와 같은 프로세스로 동작합니다.

  1. 스크롤의 데이타 리스트에서 동일한 data가 있는지 비교 - Equals(data)
  2. 해당 Index 리턴 GetDataIndex(data)
  3. 스크롤 리스트에서 해당 Index 삭제

문제 원인

1. 포함되지 않은 데이터 삭제

Equals(data)로 찾지 못하기 때문에 GetDataIndex이 -1가 나오고 삭제되지 않아 GetItemCount 가 동일하게 동작합니다.
스크롤에 포함되지 않은 데이터를 삭제한것으로 판단됩니다

2. 포함되었을 때와 다른 객체 삭제

또는 스크롤에 추가되었을때 와 다른 data로 바뀌었을거라 생각됩니다.

  1. 스크롤에 dataList 추가
  2. dataList 재생성(참조가 아닌 복사로 다른 메모리에 생성)
  3. 동일한 값이라도 스크롤의 data와 다른 메모리 객체

예상 원인과 해결 방법

예상 원인은 2. 포함되었을 때와 다른 객체 삭제로 추정됩니다.

검색 리스트를 필터링 하며 data를 지우고 생성하면서 값은 동일하나 다른 객체라 삭제가 안된것으로 생각됩니다.

해결 방법은 3가지 정도를 선택하시면 될것 같습니다.

1. Index로 관리

인덱스를 완벽하게 관리한다는 가정하에 RemoveData(data);가 아닌 RemoveData(Index); 사용

int deleteIndex = AnalysisManager.instance.deleteListIndex;
RemoveData(deleteIndex);
dataList.dataList.RemoveAt(deleteIndex);

2. Equals 구현

메모리가 다른 객체라도 값으로 비교가 가능하다면 InfiniteScrollData 객체에 IEquatable를 상속하여
Equals을 추가하여 다른 메모리 객체라도 동일한지 비교를 하도록 할수 있습니다.

class AnalysisShotData : InfiniteScrollData, IEquatable<InfiniteScrollData>
    {
        public bool Equals(InfiniteScrollData other)
        {
            if (other is AnalysisShotData otherData)
            {
                // 비교
                return this.value == otherData.value
            }
            return false;
        }
    }

3. data 재활용

dataList를 삭제후 재 추가할 때 new AnalysisShotData()를 하지 않고
기존 관리되는 데이터가 있다면 재활용해 복사가 아닌 참조로 동일한 메모리가 유지된다면 문제가 없을것이라 예상됩니다.

감사합니다.

@smflt-nhn

안녕하세요.

작성해주신 내용을 확인했습니다.

말씀해주신대로 shotScrollList를 초기화한 이후 InsertData를 할 때 new AnalysisShotData를 사용해서 복사하는 방식을 사용하였기에 생긴 문제였던 거 같습니다.
그래서 제시해주신 3가지 방법중 3. data 재활용 이라는 방법을 활용하였습니다.

dataList는 초기화 시켜주지 않기때문에 재활용 해주었습니다.
전체 리스트 로드 부분은

AnalysisShotData data = dataList[i];

클릭한 버튼 별 로드 부분은

AnalysisShotData data = dataList[clubShotList[i].ShotNo-1];

로 수정하였더니 에러없이 작동하는 것을 확인했습니다.

감사합니다.

@Randomdog7153
자체적으로 필터링 할 수 있도록 2.9.0에 기능 추가하여 배포하였습니다.

릴리즈 노트