Đo lường mức độ tương tác của người dùng

Hướng dẫn này giải thích cách đo lường tín hiệu tương tác cho Thẻ tuỳ chỉnh của Chrome. Nếu ứng dụng của bạn thường xuyên hiển thị các đường liên kết tới nội dung web cho người dùng, chẳng hạn như trong một nguồn cấp tin tức, thì bạn cần biết được đường liên kết nào có giá trị và đường liên kết nào không mang lại giá trị cho người dùng. Trong Thẻ tuỳ chỉnh, bạn có thể đo lường mức độ tương tác của người dùng theo từng phiên thông qua số lượng thao tác, các thay đổi về hướng cuộn và chiều sâu cuộn. Để xem các tín hiệu tương tác trong thực tế, hãy tham khảo ứng dụng minh hoạ Thẻ tuỳ chỉnh trên GitHub.

Bản minh hoạ tín hiệu tương tác trên Thẻ tuỳ chỉnh.

Thẻ tuỳ chỉnh cung cấp hai lệnh gọi lại khác nhau để đo lường mức độ tương tác của người dùng:

  • CustomTabsCallback để theo dõi các sự kiện điều hướng cơ bản, chẳng hạn như "NAVIGATION_STARTED" hoặc "NAVIGATION_FINISHED".
  • EngagementSignalsCallback để theo dõi mức độ tương tác của người dùng đối với trang cụ thể, chẳng hạn như hướng cuộn hoặc tỷ lệ phần trăm cuộn.

Cả hai đều cần có CustomTabsServiceConnection hoạt động. Xem hướng dẫn về CustomTabsService trước để biết thông tin chi tiết về cách kết nối với CustomTabsService.

Để đo lường mức độ tương tác của người dùng, trước tiên, hãy tạo một CustomTabsCallback và một thực thể EngagementSignalsCallback. CustomTabsCallback nhận được một hằng số navigationEvent để mô tả kiểu điều hướng đã xảy ra:

private CustomTabsCallback mCustomTabsCallback = new CustomTabsCallback() {
    @Override
    public void onNavigationEvent(int navigationEvent, @Nullable Bundle extras) {
        String event;
        switch (navigationEvent) {
            case CustomTabsCallback.NAVIGATION_ABORTED:
                event = "NAVIGATION_ABORTED";
                break;
            case CustomTabsCallback.NAVIGATION_FAILED:
                event = "NAVIGATION_FAILED";
                break;
            case CustomTabsCallback.NAVIGATION_FINISHED:
                event = "NAVIGATION_FINISHED";
                break;
            case CustomTabsCallback.NAVIGATION_STARTED:
                event = "NAVIGATION_STARTED";
                break;
            case CustomTabsCallback.TAB_SHOWN:
                event = "TAB_SHOWN";
                break;
            case CustomTabsCallback.TAB_HIDDEN:
                event = "TAB_HIDDEN";
                break;
            default:
                event = String.valueOf(navigationEvent);
        }
        Log.d(TAG, "onNavigationEvent (navigationEvent=" + event + ')');
        mTextNavigation.setText("onNavigationEvent " + event);
    }
};

EngagementSignalsCallback hỗ trợ 3 lệnh gọi lại:

onVerticalScrollEvent()
Được gọi mỗi khi người dùng thay đổi hướng cuộn, trong đó isDirectionUp (đối số đầu tiên) cho biết hướng.
  1. onGreatestScrollPercentageIncreased: Thẻ tuỳ chỉnh cho biết độ sâu cuộn trong khoảng thời gian 5%, tối đa 100% khi người dùng đến cuối trang. Lệnh gọi lại chỉ được gọi khi người dùng ngừng cuộn. Giá trị được đặt lại về 0% với mỗi lần điều hướng mới.
  2. onSessionEnded: Thẻ tuỳ chỉnh kích hoạt sự kiện này khi sự kiện ngừng gửi tín hiệu tương tác (ví dụ: sau khi người dùng đóng Thẻ tuỳ chỉnh). didUserInteract sẽ đúng nếu người dùng tương tác với trang bằng bất kỳ cách nào (cuộn sách, nhấp vào nút, v.v.).
private EngagementSignalsCallback mEngagementSignalsCallback = new EngagementSignalsCallback() {
    @Override
    public void onVerticalScrollEvent(boolean isDirectionUp, @NonNull Bundle extras) {
        Log.d(TAG, "onVerticalScrollEvent (isDirectionUp=" + isDirectionUp + ')');
        mTextVerticalScroll.setText("vertical scroll " + (isDirectionUp ? "UP" : "DOWN"));
    }

    @Override
    public void onGreatestScrollPercentageIncreased(int scrollPercentage, @NonNull Bundle extras) {
        Log.d(TAG, "scroll percentage: " + scrollPercentage + "%");
        mTextGreatestPercentage.setText("scroll percentage: " + scrollPercentage + "%");
    }

    @Override
    public void onSessionEnded(boolean didUserInteract, @NonNull Bundle extras) {
        Log.d(TAG, "onSessionEnded (didUserInteract=" + didUserInteract + ')');
        mTextSessionEnd.setText(didUserInteract ? "session ended with user interaction" : "session ended without user interaction");
    }
};

Cả CustomTabsCallbackEngagementSignalsCallback đều yêu cầu kết nối dịch vụ Thẻ tuỳ chỉnh đang hoạt động. Sau khi dịch vụ được kết nối, bạn có thể tạo CustomTabsSession mới bằng cách gọi CustomTabsClient.newSession() và truyền CustomTabsCallback.

Sau đó, bạn nên gọi isEngagementSignalsApiAvailable() để kiểm tra xem trình duyệt hiện tại có hỗ trợ các tín hiệu tương tác hay không. Nếu được hỗ trợ, bạn có thể đăng ký EngagementSignalsCallback qua CustomTabsSession.setEngagementSignalsCallback().

private CustomTabsClient mCustomTabsClient;
private CustomTabsSession mCustomTabsSession;

private final CustomTabsServiceConnection mServiceConnectionCallback = new CustomTabsServiceConnection() {

    @Override
    public void onCustomTabsServiceConnected(@NonNull ComponentName name, @NonNull CustomTabsClient client) {
        mCustomTabsClient = client;
        mCustomTabsSession = mCustomTabsClient.newSession(mCustomTabsCallback);
        try {
            boolean engagementSignalsApiAvailable = mCustomTabsSession.isEngagementSignalsApiAvailable(Bundle.EMPTY);
            if (!engagementSignalsApiAvailable) {
                Log.d(TAG, "CustomTab Engagement signals not available, make sure to use the " +
                        "latest Chrome version and enable via chrome://flags/#cct-real-time-engagement-signals");
                return;
            }
            mCustomTabsSession.setEngagementSignalsCallback(mEngagementSignalsCallback, Bundle.EMPTY);
        } catch (RemoteException e) {
            Log.w(TAG, "The Service died while responding to the request.", e);
        } catch (UnsupportedOperationException e) {
            Log.w(TAG, "Engagement Signals API isn't supported by the browser.", e);
        }
    }

    @Override
    public void onServiceDisconnected(ComponentName name) {
        mCustomTabsClient = null;
        mConnection = null;
        mCustomTabsSession = null;
    }
};

Việc duy nhất bạn cần làm là liên kết CustomTabsService:

@Override
protected void onStart() {
    super.onStart();
    bindCustomTabsService();
}

private void bindCustomTabsService() {
    String packageName = CustomTabsHelper.getPackageNameToUse(this);
    if (packageName == null) return;
    CustomTabsClient.bindCustomTabsService(this, packageName, mConnection);
}