인프런 커뮤니티 질문&답변

인프런 수강님의 프로필 이미지

작성한 질문수

[2024 최신] [코드팩토리] [초급] Flutter 3.0 앱 개발 - 10개의 프로젝트로 오늘 초보 탈출!

탭 할때마다 컨트롤 보여주고 감추기

GestureDetector onTap이 올바르게 동작하지 않습니다.

24.09.12 11:57 작성

·

19

0

안녕하세요.

좋은 강의 잘 듣고 있습니다.

 

VideoPlayer을 포함한 위젯을 VideoPlayerWidget으로 Stateful 위젯으로 구현했습니다.

그리고 자식 위젯으로 아래 코드와 같이 GestureDetector > ApstectRatio > Stack 으로 구성하였습니다.

Stack의 자식 위젯으로는 VideoPlayer, _PlayButtons, _Bottom 위젯을 가지고 있습니다.

 

이 때, VideoPlayer가 포함되어 있으면 GestureDetector의 onTap 메서드가 호출되지 않으며, VideoPlayer를 제외하는 경우 onTap 메서드가 호출되고 있습니다.

 

관련해서 자식의 터치 이벤트도 감지하기 위해 GestureDetector에 behavior 프로퍼티로 HitTestBehavior.opaque 값을 할당했지만, 그래도 VideoPlayer가 존재하는 경우 올바르게 동작하지 않고 있습니다.

 

혹시 어떤 부분이 문제인지 알 수 있을까요...?

감사합니다.

 

아래 코드는 VideoPlayerWidget의 build 메서드입니다.

@override
Widget build(BuildContext context) {
  return GestureDetector(
    behavior: HitTestBehavior.opaque,
    onTap: (){
      print("onTap");
    },
    child: !isInitalized
        ? const CircularProgressIndicator()
        : AspectRatio(
            aspectRatio: videoPlayerController.value.aspectRatio,
            child: Stack(
                children: [
              VideoPlayer(videoPlayerController),
             _PlayButtons(
                onLeft: onLeft,
                onPlay: onPlay,
                onRight: onRight,
                isPlaying: videoPlayerController.value.isPlaying,
              ),
                _Bottom(
                posMinutes: videoPlayerController.value.position.inMinutes,
                posSeconds: videoPlayerController.value.position.inSeconds,
                durationMinuets:
                    videoPlayerController.value.duration.inMinutes,
                durationSeconds:
                    videoPlayerController.value.duration.inSeconds,
                onSliderChanged: onSliderChanged,
              ),
              // _PickPicture(onPress: widget.onPickPicture,)
            ])),
  );
}

답변 2

0

코드팩토리님의 프로필 이미지
코드팩토리
지식공유자

2024. 09. 12. 12:42

안녕하세요!

혹시 특정 위젯이 터치를 가리는 현상은 아닐까요?

예를들어서 제일 위에있는 위젯이 아래 위젯을 감싸는데 터치는 아래 위젯에서 감지해야하는 경우입니다.

혹시 강의 코드랑 완전 같은데 아예 눌리지 않는걸까요? 이 경우 다시 말씀주세요! 아닌경우 위에 말씀드린 상황 확인 해보시면 좋을 것 같습니다. 보통 Stack에서 특정 위젯 빼고 실행해야 눌리는 경우 이 경우가 많습니다.

감사합니다!

0

인프런 AI 인턴님의 프로필 이미지

2024. 09. 12. 12:01

안녕하세요, 인프런 AI 인턴입니다. 인프런 수강님.

GestureDetector의 onTap 함수가 VideoPlayer가 포함된 경우 정상적으로 동작하지 않는 문제에 대해 문의주셨군요. 이 경우, Flutter에서 자식 위젯이 터치 이벤트를 가로챌 수 있기 때문에 발생하는 문제일 수 있습니다.

관련된 질문과 유사한 해결 방법이 아래 링크에 있습니다:

이 두 게시물에서는 Stack 위젯과 GestureDetector의 동작에 관련된 문제가 다뤄집니다. 특히, 위젯의 터치 이벤트가 자식 위젯에서 제대로 전달되지 않는 경우 해결 방법이 포함되어 있습니다.

간단히 정리하면, Stack 안의 VideoPlayer가 터치 이벤트를 가로채고 있어 GestureDetector의 onTap이 호출되지 않는 것입니다. 이를 해결하기 위해 VideoPlayer 위젯에도 GestureDetector를 추가하여 터치 이벤트를 처리할 수 있도록 개선해야 합니다.

예제 코드로 터치 이벤트를 처리할 수 있는 방법을 아래와 같이 시도해 볼 수 있습니다:

@override
Widget build(BuildContext context) {
  return GestureDetector(
    behavior: HitTestBehavior.opaque,
    onTap: (){
      print("onTap");
    },
    child: !isInitalized
        ? const CircularProgressIndicator()
        : AspectRatio(
            aspectRatio: videoPlayerController.value.aspectRatio,
            child: Stack(
                children: [
              GestureDetector(
                onTap: () {
                  // VideoPlayer를 터치했을 때의 로직을 여기에 추가
                  print("VideoPlayer tapped");
                },
                child: VideoPlayer(videoPlayerController),
              ),
             _PlayButtons(
                onLeft: onLeft,
                onPlay: onPlay,
                onRight: onRight,
                isPlaying: videoPlayerController.value.isPlaying,
              ),
                _Bottom(
                posMinutes: videoPlayerController.value.position.inMinutes,
                posSeconds: videoPlayerController.value.position.inSeconds,
                durationMinuets:
                    videoPlayerController.value.duration.inMinutes,
                durationSeconds:
                    videoPlayerController.value.duration.inSeconds,
                onSliderChanged: onSliderChanged,
              ),
              // _PickPicture(onPress: widget.onPickPicture,)
            ])),
  );
}

이 방법을 통해 자식 위젯인 VideoPlayer에서 터치 이벤트를 처리하면서도 부모 GestureDetector의 onTap 이벤트도 동작할 수 있도록 개선할 수 있습니다.

저는 질문자님의 이해를 돕고자 지식공유자님의 기존 답변을 참고하여 유사한 답변 링크를 추천해드리고 있습니다.
현재 베타 기능으로 답변이 만족스럽지 않을 수 있는 점 양해 부탁드립니다. 🙏
추가적으로 궁금한 점이 있으시면, 이어서 질문해 주세요. 곧 지식공유자께서 답변해 주실 것입니다.