每当您打开穿戴应用程序时,同步 Android 穿戴与 Phone

Sync Android Wear with Phone whenever you open the wear app

我正在尝试为 android phone 和 wear 实现一个基本的天气应用程序。该应用程序从 Web API 获取数据,然后将其显示在 phone 上。现在,如果该应用程序在 Wear 上打开,然后您在 Phone 上打开它,它会同步两者的天气。如果你改变 phone 上的天气,它也会改变穿着。每当您打开磨损应用程序时,我想让磨损应用程序从 phone 获取天气,我试图通过消息使磨损 "ping" 成为 phone 来实现这一点,然后phone 通过数据映射发送信息。这有效,除了 wear 没有从 phone 接收数据映射,尽管 phone 说它已经发送了数据映射。

穿主Activity:

 @Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_data_map);
    final WatchViewStub stub = (WatchViewStub) findViewById(R.id.watch_view_stub);

    stub.setOnLayoutInflatedListener(new WatchViewStub.OnLayoutInflatedListener() {
        @Override
        public void onLayoutInflated(WatchViewStub stub) {
            mTextView = (TextView) stub.findViewById(R.id.text);
            sendMessage("Ping");
            Log.i("OnLayoutInflated","LAYOUT INFLATED");
        }
    });

    setAmbientEnabled();

    // Register the local broadcast receiver
    IntentFilter messageFilter = new IntentFilter(Intent.ACTION_SEND);
    MessageReceiver messageReceiver = new MessageReceiver();
    LocalBroadcastManager.getInstance(this).registerReceiver(messageReceiver, messageFilter);

}


@Override
protected void onPause() {

    super.onPause();
    if (wearCommsManager.isConnected()) {
        wearCommsManager.disconnectClient();
    }
}

@Override
protected void onResume() {
    super.onResume();

    if (wearCommsManager == null) {
        wearCommsManager = new WearCommsManager(this);
    }
    if (messageSender == null) {
        messageSender = new WearMessageSender(wearCommsManager);
    }
    verifyCommsConnection();
}
protected void sendMessage(final String message) {
    AsyncTask<Void, Void, Void> task = new AsyncTask<Void, Void, Void>() {

        @Override
        protected Void doInBackground(Void... params) {;
            messageSender.processRequest(message);
            return null;
        }
    };
    task.execute();
}


private void verifyCommsConnection() {
    new WearCommsManager(this).verifyCommsConnection(new WearCommsManager.CommsCallback() {
        @Override
        public void onSuccess() {

        }

        @Override
        public void onFailure() {
            Log.e("ERROR","CONNECTION FAILED");
        }

    });
}



public class MessageReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {

        Bundle data = intent.getBundleExtra("datamap");
        // Display received data in UI
        String display =
                 data.getString("city") + "\n" +
                 data.getString("temperature") + "\n" +
                 data.getString("wind_speed") + "\n" +
                 data.getString("cloud_percent")+"\n"+
                 data.getString("lastupdate");
        mTextView.setText(display);
    }
}

佩戴监听器:

public class ListenerService extends WearableListenerService{

private static final String WEARABLE_DATA_PATH = "/wearable_data";


@Override
public void onCreate() {

    super.onCreate();
}

@Override
public void onDataChanged(DataEventBuffer dataEvents) {

    DataMap dataMap;
    for (DataEvent event : dataEvents) {
        Log.v("myTag", "DataMap received on watch: " + DataMapItem.fromDataItem(event.getDataItem()).getDataMap());
        // Check the data type
        if (event.getType() == DataEvent.TYPE_CHANGED) {
            // Check the data path
            String path = event.getDataItem().getUri().getPath();
            if (path.equals(WEARABLE_DATA_PATH)) {}
            dataMap = DataMapItem.fromDataItem(event.getDataItem()).getDataMap();


            // Broadcast DataMap contents to wearable activity for display
            // The content has the golf hole number and distances to the front,
            // middle and back pin placements.

            Intent messageIntent = new Intent();
            messageIntent.setAction(Intent.ACTION_SEND);
            messageIntent.putExtra("datamap", dataMap.toBundle());
            LocalBroadcastManager.getInstance(this).sendBroadcast(messageIntent);

        }
    }
}
}

Phone 主要 Activity:

public class DataMapActivity extends AppCompatActivity implements
        GoogleApiClient.ConnectionCallbacks,
        GoogleApiClient.OnConnectionFailedListener{
private TextView cityName;
private TextView temp;
private ImageView iconView;
private TextView description;
private TextView humidity;
private TextView pressure;
private TextView wind;
private TextView sunrise;
private TextView sunset;
private TextView updated;

Weather weather = new Weather();

GoogleApiClient googleClient;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_data_map);

    cityName = (TextView) findViewById(R.id.cityText);
    iconView = (ImageView) findViewById(R.id.thumbnailIcon);
    temp = (TextView) findViewById(R.id.tempText);
    description = (TextView) findViewById(R.id.CloudText);
    humidity = (TextView) findViewById(R.id.HumidText);
    pressure = (TextView) findViewById(R.id.PressureText);
    wind = (TextView) findViewById(R.id.WindText);
    sunrise = (TextView) findViewById(R.id.RiseText);
    sunset = (TextView) findViewById(R.id.SetText);
    updated = (TextView) findViewById(R.id.UpdateText);
    CityPreference cityPreference=new CityPreference(DataMapActivity.this);
    System.out.println(cityPreference.getCity());
    renderWeatherData(cityPreference.getCity());

    IntentFilter messageFilter = new IntentFilter(Intent.ACTION_SEND);
    MessageReceiver messageReceiver = new MessageReceiver();
    LocalBroadcastManager.getInstance(this).registerReceiver(messageReceiver, messageFilter);

    // Build a new GoogleApiClient for the the Wearable API
    googleClient = new GoogleApiClient.Builder(this)
            .addApi(Wearable.API)
            .addConnectionCallbacks(this)
            .addOnConnectionFailedListener(this)
            .build();
}

public void renderWeatherData(String city) {
    WeatherTask weatherTask = new WeatherTask();
    weatherTask.execute(new String[]{city + "&units=metric"});
}

private class WeatherTask extends AsyncTask<String, Void, Weather> {
    @Override
    protected Weather doInBackground(String... params) {
        String data = ((new WeatherHttpClient()).getWeatherData(params[0]));
        System.out.println(data);
        weather = JSONParser.getWeather(data);
        return weather;
    }

    @Override
    protected void onPostExecute(Weather weather) {

        super.onPostExecute(weather);
        if(weather.currentCondition.getIcon() != null){
            new DownloadImageAsyncTask().execute(weather.currentCondition.getIcon());
        }
        cityName.setText(weather.place.getCity() + "," + weather.place.getCountry());
        temp.setText("" + (int)weather.currentCondition.getTemperature() + "°C");
        wind.setText("Wind Speed: " + weather.wind.getSpeed()+"m/s" + " Degree: " + weather.wind.getDegree());
        description.setText("Clouds: " + weather.clouds.getPrecipitation() + "%, " + weather.currentCondition.getDescription());
        pressure.setText("Pressure: " + weather.currentCondition.getPressure()+"hpa");
        humidity.setText("Humidity: " + weather.currentCondition.getHumidity()+"%");
        Date mydate = new Date(weather.place.getSunrise() * 1000);
        SimpleDateFormat dateformat = new SimpleDateFormat("HH:mm");
        dateformat.setTimeZone(TimeZone.getTimeZone("GMT+3"));
        String date = dateformat.format(mydate);
        sunrise.setText("Sunrise: " + date);
        mydate = new Date(weather.place.getSunset() * 1000);
        date = dateformat.format(mydate);
        sunset.setText("Sunset: " + date);
        mydate = new Date(weather.place.getLastupdate() * 1000);
        dateformat = new SimpleDateFormat("dd.MM.yyyy, HH:mm, z");
        dateformat.setTimeZone(TimeZone.getDefault());
        date = dateformat.format(mydate);
        updated.setText("Last Updated: " + date);
        sendWear();

        //This part synchronizes perfectly with wear 

    }

}

private void sendWear(){
    String WEARABLE_DATA_PATH = "/wear_data";

    // Create a DataMap object and send it to the data layer
    DataMap dataMap = new DataMap();
    dataMap.putString("lastupdate", updated.getText().toString());
    dataMap.putString("city", cityName.getText().toString());
    dataMap.putString("temperature", temp.getText().toString());
    dataMap.putString("wind_speed", wind.getText().toString());
    dataMap.putString("cloud_percent", description.getText().toString());
    //Requires a new thread to avoid blocking the UI
    new SendToDataLayerThread(WEARABLE_DATA_PATH, dataMap).start();
}

public class MessageReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {

       String s= intent.getStringExtra("Pinger");
        if(s!=null) {
            new SendToWearAsyncTask().execute();

        }
    }
}

private class SendToWearAsyncTask extends AsyncTask<Void,Void,Void>{
    @Override
    protected void onPostExecute(Void aVoid) {
        super.onPostExecute(aVoid);
        sendWear();
         //this part wear doesn't receive the datamap
    }

    @Override
    protected Void doInBackground(Void... params) {
        return null;
    }
}

确保 applicationID were the same in the build.gradle for mobile and wear app. Also make sure that the buildTypes part and the signingConfigs part are the same in both apps. You can also send 每次更改时都进行验证。