14f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale/*
24f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * Copyright (C) 2015 The Android Open Source Project
34f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale *
44f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * Licensed under the Apache License, Version 2.0 (the "License");
54f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * you may not use this file except in compliance with the License.
64f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * You may obtain a copy of the License at
74f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale *
84f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale *      http://www.apache.org/licenses/LICENSE-2.0
94f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale *
104f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * Unless required by applicable law or agreed to in writing, software
114f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * distributed under the License is distributed on an "AS IS" BASIS,
124f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
134f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * See the License for the specific language governing permissions and
144f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * limitations under the License
154f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale */
164f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
174f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwalepackage android.view;
184f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
194f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwaleimport android.os.Looper;
204f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
214f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale/**
224f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * Similar to {@link InputEventReceiver}, but batches events to vsync boundaries when possible.
234f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale * @hide
244f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale */
254f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwalepublic class BatchedInputEventReceiver extends InputEventReceiver {
264f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    Choreographer mChoreographer;
274f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    private boolean mBatchedInputScheduled;
284f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
294f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    public BatchedInputEventReceiver(
304f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            InputChannel inputChannel, Looper looper, Choreographer choreographer) {
314f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        super(inputChannel, looper);
324f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        mChoreographer = choreographer;
334f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
344f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
354f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    @Override
364f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    public void onBatchedInputEventPending() {
374f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        scheduleBatchedInput();
384f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
394f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
404f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    @Override
414f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    public void dispose() {
424f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        unscheduleBatchedInput();
434f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        super.dispose();
444f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
454f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
464f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    void doConsumeBatchedInput(long frameTimeNanos) {
474f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        if (mBatchedInputScheduled) {
484f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            mBatchedInputScheduled = false;
494f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            if (consumeBatchedInputEvents(frameTimeNanos) && frameTimeNanos != -1) {
504f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                // If we consumed a batch here, we want to go ahead and schedule the
514f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                // consumption of batched input events on the next frame. Otherwise, we would
524f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                // wait until we have more input events pending and might get starved by other
534f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                // things occurring in the process. If the frame time is -1, however, then
544f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                // we're in a non-batching mode, so there's no need to schedule this.
554f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                scheduleBatchedInput();
564f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            }
574f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        }
584f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
594f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
604f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    private void scheduleBatchedInput() {
614f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        if (!mBatchedInputScheduled) {
624f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            mBatchedInputScheduled = true;
634f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            mChoreographer.postCallback(Choreographer.CALLBACK_INPUT, mBatchedInputRunnable, null);
644f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        }
654f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
664f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
674f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    private void unscheduleBatchedInput() {
684f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        if (mBatchedInputScheduled) {
694f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            mBatchedInputScheduled = false;
704f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            mChoreographer.removeCallbacks(
714f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale                    Choreographer.CALLBACK_INPUT, mBatchedInputRunnable, null);
724f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        }
734f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
744f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale
754f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    private final class BatchedInputRunnable implements Runnable {
764f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        @Override
774f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        public void run() {
784f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale            doConsumeBatchedInput(mChoreographer.getFrameTimeNanos());
794f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale        }
804f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    }
814f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale    private final BatchedInputRunnable mBatchedInputRunnable = new BatchedInputRunnable();
824f52bc6f78085bc40110bce5cc485f715223556eWale Ogunwale}
83