标签: android-architecture-components

CompoundView(自定义视图)中的 ViewModel 引用

我正在遵循MVVM使用Android Architecture ComponentsData Binding库的架构。

TL; 博士

ViewModel在复合视图中引用对象是否违反了 MVVM 架构?我查看了 Google 的示例,只看到它在 Activity/Fragment XML 中使用,但没有在自定义视图中使用。

有问题的代码

我有一个复合视图,我想在许多地方重复使用它。它从 XML 实例化。该视图根据用户输入进行填充。我想确保用户输入的任何内容都能在方向更改中幸存下来。请考虑我匆忙编写的以下代码来说明场景:

public class RestaurantActivity extends AppCompatActivity {

    RestaurantViewModel viewModel;

    RestaurantActivityBinding binding;

    @Override
    public void onCreate( Bundle savedInstanceState ) {
        super.onCreate( savedInstanceState );

        binding = DataBindingUtil.setContentView(this, R.layout.restaurant_activity );

        viewModel = ViewModelProviders.of( this ).get( RestaurantViewModel.class );

        //is this "legal" for MVVM
        binding.selectionView.setRestaurantViewModel( viewModel );

        viewModel.extraHotSause.observe ( this, new Observer() {

          @Override
          void onChange(Boolean extraHotSauce ) {
               binding.selectionView.extraHotSauce( extraHotSauce …
Run Code Online (Sandbox Code Playgroud)

android mvvm android-viewmodel android-architecture-components

9
推荐指数
0
解决办法
3027
查看次数

在Fragment的附加ViewModel上没有调用onCleared

ViewModel.OnCleared()当应用程序进入后台时(即使Don't keep activities已启用),当我没有被调用时,我偶然发现了一个问题,但我可以看到Fragment.onDestroy()实际上正在调用它.

以下代码可能有什么问题?如何ViewModel.OnCleared()在这种情况下实际调用?

视图模型:

class ViewModelFirst(application: Application) : AndroidViewModel(application) {

    companion object {
        private const val TAG = "ViewModelFirst"
    }

    init {
        Log.v(TAG, "Created")
    }

    override fun onCleared() {
        super.onCleared()
        Log.v(TAG, "onCleared")
    }
}
Run Code Online (Sandbox Code Playgroud)

分段:

class FragmentFirst : Fragment() {

    companion object {
        private const val TAG = "FragmentFirst"
    }

    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {

        ViewModelProviders.of(this).get(ViewModelFirst::class.java)

        return inflater.inflate(R.layout.fragment_first, container, false)
    }

    override fun onDestroy() {
        super.onDestroy()
        Log.v(TAG, …
Run Code Online (Sandbox Code Playgroud)

android android-viewmodel android-architecture-components

9
推荐指数
1
解决办法
2832
查看次数

如何获取 NavHostFragment

我正在将 Android 的导航架构组件集成到我的应用程序中。我在将数据从活动传递到片段的开头时遇到了一些问题,所以我遵循了这个答案:导航架构组件-将参数数据传递到 startDestination

这个逻辑对我来说似乎很合理,但我正在努力确定如何实际获得 NavHostFragment。Elliot Shrock 使用了这条线——

val navHostFragment = navFragment as NavHostFragment

但我还没有找到一个有效的 Java 等价物。我尝试通过使用获取我的 navHost 的片段 getSupportFragmentManager().findFragmentById(R.id.[mynavhostid])

但此命令返回空值。有任何想法吗?

android android-fragments fragmentmanager android-architecture-components android-architecture-navigation

9
推荐指数
1
解决办法
6894
查看次数

Workmanager中的唯一OneTimeWorkRequest

我们正在使用OneTimeWorkRequest在我们的项目中启动后台任务.

  1. 在应用程序启动时,我们正在启动OneTimeWorkRequest(比如req A)
  2. 取决于用户的操作,我们开始相同的工作请求A.

在某些情况下,如果应用程序在工作请求A正在进行时被杀死,Android会在应用程序重新启动时自动重新启动请求A. 我们再次再次启动请求A. 因此,请求A的两个实例并行运行并导致死锁.

为了避免这种情况,我在app start中执行了以下代码来检查worker是否正在运行但是这总是返回false.

public static boolean isMyWorkerRunning(String tag) {
        List<WorkStatus> status = WorkManager.getInstance().getStatusesByTag(tag).getValue();
        return status != null;
    }
Run Code Online (Sandbox Code Playgroud)

有没有更好的方法来处理这个?

我检查了beginUniqueWork().如果我只有一个请求,是否更昂贵?

编辑2: 这个问题是关于独特的一次性任务.为了启动唯一的Periodic任务,我们有一个单独的API enqueueUniquePeriodicWork().但是我们没有用于启动独特的一次性工作的API.我很困惑在继续对象之间使用或手动检查和启动方法.

在最近的构建中,他们为这个enqueueUniqueWork()添加了新的api.这是他们在发行说明中提到的确切原因.

添加WorkManager.enqueueUniqueWork()API以将唯一的OneTimeWorkRequests排入队列,而无需创建WorkContinuation. https://developer.android.com/jetpack/docs/release-notes

android android-architecture-components android-jetpack android-workmanager

9
推荐指数
2
解决办法
4397
查看次数

无法在后台线程上调用observeForever

我一直在使用这里observeForever()描述的方法来测试Room和LiveData一段时间,并且它运行得很完美.但当我改为Android Studio 3.2(或者如果它是重构,不确定)时,该方法突然停止工作,抛出一个androidx

java.lang.IllegalStateException: Cannot invoke observeForever on a background thread
Run Code Online (Sandbox Code Playgroud)

我们该如何解决这个问题?

android android-room android-livedata android-architecture-components androidx

9
推荐指数
2
解决办法
3613
查看次数

Android JetPack的共享ViewModel生命周期

该文件 https://developer.android.com/topic/libraries/architecture/viewmodel#sharing描述了如何在不同的片段之间共享相同的ViewModel。

我的页面有些复杂 单个“活动”应用程序中其中包含容器和选项卡片段。每个此类页面都有自己的ViewModel,应与所有包含的片段共享。

这里的关键技巧是使用Activity而不是Fragment来保存我的ViewModel。

问题是我的活动可以有多个具有自己的模型的页面,并且始终保持特定页面的视图模型是浪费设备资源。

当用户离开页面时,是否有任何方法可以控制ViewModel的生命周期以销毁它?

我想使用容器片段而不是活动:

model = ViewModelProviders.of(getPageContainerFragment()).get(SharedViewModel.class);
Run Code Online (Sandbox Code Playgroud)

但是发现这个想法不是很好,因为所有子片段都应该了解父元素,而这可能不是很好。

是否有其他方法可以正确处理这种情况?

android model-view android-fragments android-architecture-components android-jetpack

9
推荐指数
1
解决办法
577
查看次数

在嵌套滚动视图中使用时的分页库加载所有数据

我正在使用分页库来加载数据并填充我放置在nestedscrollview 中的recyclerview。但这就像,分页会自动工作,直到从 API 获取所有数据。我知道这是因为nestedscrollview。但不幸的是,我的布局需要滚动视图,因为我在这个片段中有一个不是 recyclerview 的顶部部分。这是我的布局

<android.support.v4.widget.NestedScrollView
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fillViewport="true"
   >
   <android.support.constraint.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

   //have a layout here which scrolls with recyclerview

      <Recyclerview />

   </ConstraintLayout>

</NestedScrollView>
Run Code Online (Sandbox Code Playgroud)

当我不使用nestedscrollview 时,一切正常。googlesamples git repo regsrding 中有一个未解决的问题。

https://github.com/googlesamples/android-architecture-components/issues/215

有谁知道当回收视图位于带有 Android jetpack 分页库的滚动视图中时,我们如何实现分页。我知道我们可以实现传统类型的分页,将侦听器附加到nestedscrollview,但我希望使用架构组件库实现分页。 https://developer.android.com/topic/libraries/architecture/paging/

android android-layout android-architecture-components android-jetpack

9
推荐指数
2
解决办法
2033
查看次数

用于实例化 ViewModel 的首选 Fragment 生命周期方法

android-architecture-components/GithubBrowserSample 存储库中,Fragment#onViewCreated生命周期方法用于ViewModel实例化(具有Fragment范围),用于Fragment使用数据绑定 + LiveData+组合的s ViewModel

来自SearchFragment.kt该回购 ^:

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        searchViewModel = ViewModelProviders.of(this, viewModelFactory)
        ...
    }
Run Code Online (Sandbox Code Playgroud)

是否有任何官方的指南或共识哪个这些Fragment生命周期方法,如onAttachonCreateonViewCreated,或者onActivityCreated是实例化的最佳/最安全的地方FragmentViewModel使用ViewModelProviders.of(fragment, viewModelFactory)方法?(考虑到数据绑定 +LiveData组合,如果这有区别的话)

试图理解将ViewModel实例化放入任何早期生命周期方法(例如onAttach/ )的一般优点/缺点onCreatesuper当然是在调用之后)。

提前致谢。

android android-fragments android-livedata android-viewmodel android-architecture-components

9
推荐指数
2
解决办法
3051
查看次数

Room 数据库中的@ForeignKey 和@Relation 注释有什么区别?

我无法理解这些注释之间的区别。在我的用例中,我想在表之间创建一对多关系。并找到了两个选项:一个是@ForeignKey,另一个是@Relation

我还发现,如果我更新该行(例如使用 OnCoflictStrategy.Replace),我将丢失该行的外键,这是真的吗?

android android-room android-architecture-components

9
推荐指数
2
解决办法
3048
查看次数

BottomSheetDialogFragment 中的 NavigationComponent 导航

Android 的导航组件能否用于在 BottomSheet 内导航(即在单个底部工作表中替换/添加片段)?

我知道如何BottomSheetDialogFragment使用<dialog>导航图中的标签启动一个。例如,下面的代码nav_graph.xml允许用户从一个BottomSheetDialogFragment(fragmentOne)导航到另一个BottomSheetDialogFragment(fragmentTwo)。FragmentTwo 作为第二个BottomSheet 打开,位于FragmentOne 的BottomSheet 之上。

但是,如果我想让 fragmentTwo 替换同一个 BottomSheet 中的 fragmentOne 怎么办?我将如何使用导航图完成此操作?

<navigation android:id="@+id/nav_graph"
        app:startDestination="@id/fragmentOne">

    <dialog android:id="@+id/fragmentOne"
        android:name="com.example.navcomponentapp.FragmentOne"
        android:label="fragment_fragment_one"
        tools:layout="@layout/fragment_fragment_one">

        <action android:id="@+id/action_fragmentOne_to_fragmentTwo2"
            app:destination="@id/fragmentTwo"/>
    </dialog>

    <dialog android:id="@+id/fragmentTwo"
        android:name="com.example.navcomponentapp.FragmentTwo"
        android:label="fragment_fragment_two"
        tools:layout="@layout/fragment_fragment_two"/>
</navigation>
Run Code Online (Sandbox Code Playgroud)

演示(这不是我想要的。我不想在另一个bottomSheet上打开一个bottomSheet

android android-navigation android-architecture-components android-jetpack android-navigation-graph

9
推荐指数
1
解决办法
1915
查看次数