[Android & OpenGL] Click or Touch없이 Button Event 효과 구현

2022. 1. 5. 19:04Android

Implement Button Click Effect(Animation) artificially in VR

VR Player에서 ControlPanel을 Neumorphism Library를 이용하여 3D에 걸맞는 디자인으로 만들었다.

이제 이 ControlPanel을 사용해 VR Player를 컨트롤 하는 기능을 구현하기에 앞서,UI상에서 시각적으로 버튼이 눌려지는 효과(애니메이션)를 주기위해 인위적인 클릭을 구현하려 한다.

VR의 특성상 모바일폰은 HMD안에 들어있는 상태에서 클릭을 구현해야 하기 때문에 손가락으로 화면을 터치하는 등의 직접적인 터치는 불가능하다.

따라서 viewDirection의 yaw, pitch 각도를 이용하여,특정 각도의 범위안에 들어온 상태에서 터치를 하면 클릭으로 인식되도록 한다.

 

실제로 버튼을 누르지 않아도 Click(Touch) Effect Animation이 나올수 있도록 다음과 같은 여러가지 방법을 시도하였다.

 

Method 1.

  • Simulate touch event programmatically
    MotionEvent를 생성하여 Button에 dispath하는 방법
// get the coordinates of the view
int[] coordinates = new int[2];
pauseButton.getLocationOnScreen(coordinates);
// MotionEvent parameters
long downTime = SystemClock.uptimeMillis();
long eventTime = SystemClock.uptimeMillis();
int x = coordinates[0];
int y = coordinates[1];
int metaState = 0;

MotionEvent motionEvent = MotionEvent.obtain(downTime, eventTime, MotionEvent.ACTION_DOWN, x, y, metaState);
MotionEvent motionEvent2 = MotionEvent.obtain(downTime+500, eventTime+1000, MotionEvent.ACTION_UP, x, y, metaState);

// Dispatch touch event to view
pauseButton.dispatchTouchEvent(motionEvent);
pauseButton.dispatchTouchEvent(motionEvent2);

 

 

how automatically perform touch in android programmatically

I have a RelativeLayout I want to perform a touch event with out touching the screen want to give a Toast message if its actually touched or not.Please throw I have tried with the below it seems not

stackoverflow.com

Click Effect Animation이  작동하는 것이 전혀 보이지 않았다.

 

 

Method 2.

  • Button.callOnClick() or Button.performClick()를 통해 인위적인 OnClick메소드 구현
pauseButton.callOnClick();
pauseButton.performClick();
pauseButton.setPressed(true);
pauseButton.invalidate();
// delay completion till animation completes
pauseButton.postDelayed(new Runnable() {  //delay button
    public void run() {
        pauseButton.setPressed(false);
        pauseButton.invalidate();
        //any other associated action
    }
}, 800);

Button Click Event(Animation)이 연속된 Animation으로 보이지 않고

 Animation 중간 어딘가 랜덤한 지점에서 Stop된 이미지로 보인다.

 

 

Method 3.

  • onNewFrame() 안에서  invalidate() 시켜줌 --> 해결!!!!
@Override
public void onNewFrame(float[] forward, float[] viewDirection) {
    ...
    invalidate();

    super.onNewFrame(forward, viewDirection);
}

 

 

연구소 소장님께 물어본 결과 GLSurfaceView에서 XML을 통해 그려진 ControlPanel을 억지로 그리는 것이기 때문에
UI Handler에서  Click Event Effect를 그리고 있는 것인지 의심된다고 하심.
따라서 Button이 자체적으로 가지고 있는 Button.OnClick() 메소드를 호출하도록 OnClickListener를 설정해주고 
.callOnClick()으로 호출하여 Android Systme에서 Onclick()에 포함된 UI컨트롤 기능을 구현하도록 해야함.

 

public void handleButtonEvent() {
	...
    button.setOnClickListener(onClickListener);
    button.callOnClick();
}
  /** Button OnClickListener
  * For click animation effect **/
    private OnClickListener onClickListener = new OnClickListener() {
        @Override
        public void onClick(View v) {
            v.setPressed(true);
            v.postDelayed(new Runnable() {
                @Override
                public void run() {
                    setButtonPressedFalse(v);
                }}, BUTTON_CLICK_DELAY_TIME
            );
        }
    };

BUTTON_CLICK_DELAY_TIME은 300(ms)으로 설정.

 

결과적으로 직접적인 클릭이나 터치없이도 인위적인 터치 구현 성공

VR(GLSurfaceView)에서 invalidate()를 통해 UI를 업데이트를 해주면

다음과 같이 button click effect animation이 연속적인 animation effect를 볼 수 있다.