Awareness API显着延迟了活动回调

时间:2017-01-06 07:19:05

标签: android google-fit google-awareness

我创建了一个类和一个BroadcastReceiver,以便在行走或跑步结束时从感知api获取回调。 我没有得到及时的回调,起初认为这是因为我已经注册了一个“停止”回调,但是当我把手机放下一点之后,我确实得到了几个回调!但这远离我停止行走的时间。停止后至少5分钟。 有时即使Google Fit应用记录了活动,我也不会收到回调。

由于我至少有几次回调,我知道注册是可以的。为什么这些电话会延迟,有时会丢失?

作为背景参考,我在主要活动的onStart中注册这些回调,即当时在活动的onstart内调用initiateAwareness。我永远不会注销他们。 我不打算在生产中这样使用它,它只是用于测试。此外,我尝试使用应用程序上下文注册围栏失败了。

这是我为设置Google客户端和围栏注册而设置的帮助程序类。

public class AwarenessHelper {


public static final String WALKING_ENDED_FENCE = "walkingEndedKey";
public static final String RUNNING_ENDED_FENCE = "runningEndedKey";
public static final String TYPE_2_WALKING = "duringWalkingKey";
public static final String TYPE_2_RUNNING = "duringRunningKey";

private String tag = AwarenessHelper.class.getSimpleName();

public void initiateAwareness(final Activity context)
{
    final GoogleApiClient googleApiClient = buildClient(context);
    Log.d(tag, "Initiating blocking connect");
    googleApiClient.registerConnectionCallbacks(new GoogleApiClient.ConnectionCallbacks() {
        @Override
        public void onConnected(@Nullable Bundle bundle) {
            if ( googleApiClient.isConnected() )
            {
                Log.d(tag, "Client connected, initiating awareness fence registration");
                registerAwarenessFences(context, googleApiClient);
            }
            else
            {
                Log.d(tag, "Couldn't connect");
            }

        }

        @Override
        public void onConnectionSuspended(int i) {

        }


    });

    googleApiClient.connect();
}

private void registerAwarenessFences(Context context, GoogleApiClient mGoogleApiClient) {
    Awareness.FenceApi.updateFences(
            mGoogleApiClient,
            new FenceUpdateRequest.Builder()
                    .addFence(WALKING_ENDED_FENCE, DetectedActivityFence.stopping(DetectedActivityFence.WALKING), getBroadcastPendingIntent(context))
                    .addFence(RUNNING_ENDED_FENCE, DetectedActivityFence.stopping(DetectedActivityFence.RUNNING), getBroadcastPendingIntent(context))
                    .addFence(TYPE_2_WALKING, DetectedActivityFence.during(DetectedActivityFence.WALKING), getBroadcastPendingIntent(context))
                    .addFence(TYPE_2_RUNNING, DetectedActivityFence.stopping(DetectedActivityFence.RUNNING), getBroadcastPendingIntent(context))
                    .build())
            .setResultCallback(new ResultCallback<Status>() {
                @Override
                public void onResult(@NonNull Status status) {
                    if (status.isSuccess()) {
                        Log.i(tag, "Fence was successfully registered.");
                    } else {
                        Log.e(tag, "Fence could not be registered: " + status);
                    }
                }
            });
}

private GoogleApiClient buildClient(final Activity activity)
{
    GoogleApiClient client = new GoogleApiClient.Builder(activity)
            .addApi(Awareness.API)
            .addOnConnectionFailedListener(new GoogleApiClient.OnConnectionFailedListener() {
                @Override
                public void onConnectionFailed(@NonNull ConnectionResult connectionResult) {
                    if ( connectionResult.hasResolution() && connectionResult.getErrorCode() == CommonStatusCodes.SIGN_IN_REQUIRED )
                    {
                        try {
                            connectionResult.startResolutionForResult(activity, GOOGLE_FIT_AUTHORIZATION_REQUEST_CODE);
                        } catch (IntentSender.SendIntentException e) {
                            e.printStackTrace();
                        }
                    }
                }
            })
            .build();
    return client;
}

private PendingIntent getBroadcastPendingIntent(Context context)
{
    Intent intent = new Intent(AWARENESS_BROADCAST_ACTION);
    PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);

    return pendingIntent;
}
}

这是BroadcastReceiver:

public class AwarenessHelper {


    public static final String WALKING_ENDED_FENCE = "walkingEndedKey";
    public static final String RUNNING_ENDED_FENCE = "runningEndedKey";
    public static final String TYPE_2_WALKING = "duringWalkingKey";
    public static final String TYPE_2_RUNNING = "duringRunningKey";

    private String tag = AwarenessHelper.class.getSimpleName();

    public void initiateAwareness(final Activity context)
    {
        final GoogleApiClient googleApiClient = buildClient(context);
        Log.d(tag, "Initiating blocking connect");
        googleApiClient.registerConnectionCallbacks(new GoogleApiClient.ConnectionCallbacks() {
            @Override
            public void onConnected(@Nullable Bundle bundle) {
                if ( googleApiClient.isConnected() )
                {
                    Log.d(tag, "Client connected, initiating awareness fence registration");
                    registerAwarenessFences(context, googleApiClient);
                }
                else
                {
                    Log.d(tag, "Couldn't connect");
                }

            }

            @Override
            public void onConnectionSuspended(int i) {

            }


        });

        googleApiClient.connect();
    }

    private void registerAwarenessFences(Context context, GoogleApiClient mGoogleApiClient) {
        Awareness.FenceApi.updateFences(
                mGoogleApiClient,
                new FenceUpdateRequest.Builder()
                        .addFence(WALKING_ENDED_FENCE, DetectedActivityFence.stopping(DetectedActivityFence.WALKING), getBroadcastPendingIntent(context))
                        .addFence(RUNNING_ENDED_FENCE, DetectedActivityFence.stopping(DetectedActivityFence.RUNNING), getBroadcastPendingIntent(context))
                        .addFence(TYPE_2_WALKING, DetectedActivityFence.during(DetectedActivityFence.WALKING), getBroadcastPendingIntent(context))
                        .addFence(TYPE_2_RUNNING, DetectedActivityFence.stopping(DetectedActivityFence.RUNNING), getBroadcastPendingIntent(context))
                        .build())
                .setResultCallback(new ResultCallback<Status>() {
                    @Override
                    public void onResult(@NonNull Status status) {
                        if (status.isSuccess()) {
                            Log.i(tag, "Fence was successfully registered.");
                        } else {
                            Log.e(tag, "Fence could not be registered: " + status);
                        }
                    }
                });
    }

    private GoogleApiClient buildClient(final Activity activity)
    {
        GoogleApiClient client = new GoogleApiClient.Builder(activity)
                .addApi(Awareness.API)
                .addOnConnectionFailedListener(new GoogleApiClient.OnConnectionFailedListener() {
                    @Override
                    public void onConnectionFailed(@NonNull ConnectionResult connectionResult) {
                        if ( connectionResult.hasResolution() && connectionResult.getErrorCode() == CommonStatusCodes.SIGN_IN_REQUIRED )
                        {
                            try {
                                connectionResult.startResolutionForResult(activity, GOOGLE_FIT_AUTHORIZATION_REQUEST_CODE);
                            } catch (IntentSender.SendIntentException e) {
                                e.printStackTrace();
                            }
                        }
                    }
                })
                .build();
        return client;
    }

    private PendingIntent getBroadcastPendingIntent(Context context)
    {
        Intent intent = new Intent(AWARENESS_BROADCAST_ACTION);
        PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intent, 0);

        return pendingIntent;
    }
}

我收到通知,但经过一段时间的延迟,有时根本没有。 我多次开始活动,所以也许围栏一遍又一遍地注册?这是一个相关的事实吗? 服务或广播接收器上下文是否适合初始化感知客户端和围栏?

1 个答案:

答案 0 :(得分:0)

Awareness订阅很少获得ActivityRecognition次更新,因此您在几分钟后收到回复并不是出乎意料。

一般情况下,如果没有取消注册,你也应该担心有太多的围栏。

也没有理由为每个围栏单独pendingIntent;你可以有一个pendingIntent并添加所有围栏。使用fence key extra来区分每个栅栏的结果。再次,当它有意义时,unregister。否则,即使您的应用程序消失,围栏也可能会徘徊。