【问题标题】:How to split a stream correctly into 4 Actions using RxAndroid?如何使用 RxAndroid 将流正确拆分为 4 个操作?
【发布时间】:2018-08-10 05:58:46
【问题描述】:

我第一次尝试接触反应式编程。我正在使用适用于 Android 的 ReactiveLocation 库,并且我有 4 个文本视图需要在收到新位置时填充位置数据。

所以这是在每次位置更新时为我提供位置的代码:

    locationProvider = new ReactiveLocationProvider(getApplicationContext());
    lastKnownLocationObservable = locationProvider.getLastKnownLocation();

    final LocationRequest locationRequest = LocationRequest.create()
            .setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY)
            .setNumUpdates(150)
            .setInterval(100);
    locationUpdatesObservable = locationProvider
            .checkLocationSettings(
                    new LocationSettingsRequest.Builder()
                            .addLocationRequest(locationRequest)
                            .setAlwaysShow(true)  //Refrence: http://stackoverflow.com/questions/29824408/google-play-services-locationservices-api-new-option-never
                            .build()
            )
            .doOnNext(new Action1<LocationSettingsResult>() {
                @Override
                public void call(LocationSettingsResult locationSettingsResult) {
                    Status status = locationSettingsResult.getStatus();
                    if (status.getStatusCode() == LocationSettingsStatusCodes.RESOLUTION_REQUIRED) {
                        try {
                            status.startResolutionForResult(MainActivity.this, REQUEST_CHECK_SETTINGS);
                        } catch (IntentSender.SendIntentException th) {
                            Log.e("MainActivity", "Error opening settings activity.", th);
                        }
                    }
                }
            })
            .flatMap(new Func1<LocationSettingsResult, Observable<Location>>() {
                @Override
                public Observable<Location> call(LocationSettingsResult locationSettingsResult) {
                    return locationProvider.getUpdatedLocation(locationRequest);
                }
            });

我也有这个函数,它将位置拆分为一个由 4 个字符串组成的数组:

public class LocationToStringsArrayListFunc implements Func1<Location, ArrayList<String>> {
    @Override
    public ArrayList<String> call(Location location) {
        ArrayList<String> locationDetails = null;
        if (location != null) {
            locationDetails = new ArrayList<>();
            locationDetails.add(String.valueOf(location.getLatitude()));
            locationDetails.add(String.valueOf(location.getLongitude()));
            locationDetails.add(String.valueOf(location.getTime()));
            locationDetails.add(String.valueOf(location.getSpeed()));
        }
        return locationDetails;
    }
}

最后我有这个动作来用文本填充 TextView:

public class DisplayTextOnViewAction implements Action1<String> {
   private final TextView target;

    public DisplayTextOnViewAction(TextView target) {
        this.target = target;
    }

    @Override
    public void call(String s) {
        target.setText(s);
    }
}

我现在想要的是每次将此流拆分为 4 个视图,我知道对于其中一个,我将执行以下操作:

 mUpdatableLocationSubscription = locationUpdatesObservable 
            .map(new LocationToStringsArrayListFunc())
            .map(new Func1<ArrayList<String>, String>() {

                @Override
                public String call(ArrayList<String> stringArrayList) {
                    return stringArrayList.get(0);
                }
            })
            .subscribe(new DisplayTextOnViewAction(tvLatitudeValue), new ErrorHandler());

如何使用同一流填充其他 3 个 TextView:LongitudeValue、tvLastUpdateValue、tvSpeedValue?

【问题讨论】:

    标签: android rx-java rx-android android-reactivelocation


    【解决方案1】:

    .share() 运算符是您应该查看的。

    有了这个“助手”类:

    public class ListItemFunc extends Func1<ArrayList<String>, String>{
    
        private final int index;
    
        public ListItemFunc(int index) {
            this.index = index;
        }
    
        @Override
        public String call(ArrayList<String> strings) {
            return strings.get(index);
        }
    }
    

    您的代码可能如下所示:

    Observable<ArrayList<String>> sharedObservable =
            locationUpdatesObservable.map(new LocationToStringsArrayListFunc()).share();
    
    latitudeSubscription = sharedObservable
            .map(new ListItemFunc(0))
            .subscribe(new DisplayTextOnViewAction(tvLatitudeValue), new ErrorHandler());
    
    longitudeSubscription = sharedObservable
            .map(new ListItemFunc(1))
            .subscribe(new DisplayTextOnViewAction(tvLongitudeValue), new ErrorHandler());
    
    lastUpdateSubscription = sharedObservable
            .map(new ListItemFunc(2))
            .subscribe(new DisplayTextOnViewAction(tvLastUpdateValue), new ErrorHandler());
    
    speedSubscription = sharedObservable
            .map(new ListItemFunc(3))
            .subscribe(new DisplayTextOnViewAction(tvSpeedValue), new ErrorHandler());
    

    【讨论】:

      猜你喜欢
      • 2020-01-08
      • 2017-06-17
      • 2012-06-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-08-28
      相关资源
      最近更新 更多