ダニーBuonocore:
私は、カスタムビューのプロパティにフラグメントののviewmodelから結合双方向の達成に苦労しています。双方向バインディング問題はありませんString
しEditText
、そして私のカスタムで一方向結合作品の罰金がSearchView
。私が変更された場合でも"@{vm.entry.item}"
に"@={vm.entry.item}"
カスタムビューで、プロジェクトをコンパイルし、そしてスローません。
エラー:シンボルインポートcom.test.test.databinding.FragmentTestBindingImplを見つけることができません。
私のようなチュートリアル読んでいるこのいずれかを今しばらくの間、及びをいじるしようとしたBindingAdapter
のが、運を持っていません。私は何かを明らかに欠けているように感じます。
Kotlin
data class TestModel(
var item: String? = null,
var quantity: String? = null
)
class TestViewModel : ViewModel() {
val entry = TestModel()
}
class TestFragment : Fragment() {
private val vm: TestViewModel by lazy {
ViewModelProvider(this).get(TestViewModel::class.java)
}
override fun onCreateView(
inflater: LayoutInflater,
parent: ViewGroup?,
savedInstanceState: Bundle?
): View {
val binding: FragmentTestBinding =
DataBindingUtil.inflate(inflater, R.layout.fragment_test, parent, false)
binding.setVariable(BR.vm, vm)
binding.lifecycleOwner = viewLifecycleOwner
return binding.root
}
}
class SearchView(context: Context, attrs: AttributeSet) : FrameLayout(context, attrs, 0) {
var selected: String? = null
init {
inflate(context, R.layout.view_search, this)
val input: AutoCompleteTextView = findViewById(R.id.search_input)
input.threshold = 1
input.setAdapter(SearchAdapter(context))
input.setOnItemClickListener { adapterView, _, position, _ ->
val item: SearchModel = adapterView.getItemAtPosition(position) as SearchModel
input.setText(item.name)
selected = item.code
}
}
}
フラグメントレイアウト
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<data>
<variable
name="vm"
type="com.test.test.ui.TestViewModel" />
</data>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<com.test.test.ui.views.SearchView
android:id="@+id/test_search"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:selected="@={vm.entry.item}" />
<EditText
android:id="@+id/test_edit_text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@={vm.entry.quantity}" />
</LinearLayout>
</layout>
SearchViewレイアウト
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="@dimen/paddingDouble"
android:orientation="horizontal">
<AutoCompleteTextView
android:id="@+id/search_input"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</merge>
ダニーBuonocore:
答え判明はしていたドキュメント全体の時間(クレイジー、右?)。
キーお持ち帰りはそれをラップするために十分ではないということであるように思わ[Inverse]BindingAdapter
コンパニオンオブジェクトの関数を。彼らはまたの注釈が付けする必要が@JvmStatic。
私のフルカスタムビューは現在のようになります。
class SearchView(context: Context, attrs: AttributeSet) : FrameLayout(context, attrs, 0) {
var selected: String? = null
init {
inflate(context, R.layout.view_search, this)
}
companion object {
@BindingAdapter("selectedAttrChanged")
@JvmStatic
fun setListener(view: SearchView, listener: InverseBindingListener) {
val input: AutoCompleteTextView = view.findViewById(R.id.search_input)
input.threshold = 1
input.setAdapter(SearchAdapter(view.context))
input.setOnItemClickListener { adapterView, _, position, _ ->
val item: SearchModel = adapterView.getItemAtPosition(position) as SearchModel
input.setText(item.name)
selected = item.code
listener.onChange()
}
}
@BindingAdapter("selected")
@JvmStatic
fun setTextValue(view: SearchView, value: String?) {
if (value != view.selected) view.selected = value
}
@InverseBindingAdapter(attribute = "selected")
@JvmStatic
fun getTextValue(view: SearchView): String? = view.selected
}
}