专注于最近的可聚焦兄弟姐妹
Get focus on nearest focusable sibling
在我的 AndroidTV 应用程序中,我有 TableLayout
和 TableRow
。这些行包含 Button
。当用户点击按钮时,该按钮将被禁用。当它发生时,我希望焦点应该转到 TableLayout
.
中最近的可聚焦视图
布局是这样的:
<?xml version="1.0" encoding="utf-8"?>
<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:shrinkColumns="*"
android:stretchColumns="*">
<TableRow
android:id="@+id/input_buttons_row"
android:layout_height="0dp"
android:layout_weight="1"
android:layout_gravity="center"
android:gravity="center"
android:layout_width="match_parent">
<Button
android:id="@+id/it1"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it2"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it3"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it4"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it5"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it6"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it7"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
</TableRow>
</TableLayout>
出现如下:
我在按下按钮时将其禁用。所以,我希望焦点应该转到视图中最近的按钮。示例:如果我按 'Button 5',焦点应转到 'Button 4' 或按钮 6'。我怎样才能做到这一点?
我尝试了 table 行上的请求焦点的各种组合。示例:
mInputButtonsRow.requestFocus(View.FOCUS_DOWN);
也尝试使用 requestFocus(View.FOCUS_BACKWARD)
和 requestFocus(View.FOCUS_FORWARD)
。焦点跳转到行中的第一个或最后一个按钮,而不是最近的可聚焦按钮!
但是,焦点总是转到 'Button 1' 如果它仍然启用。如果不是,它将转到 'Button 2' 等等。如何始终将焦点放在最近的按钮上而不是第一个启用的同级按钮上?
试了好几种方法都做不到。所以,这是对我有用的解决方法。这可能不是最好的方法。我仍然愿意接受更好的解决方案。这是我所做的:
当用户点击按钮时,
// Keep the focus on the same button.
mButton1.requestFocus();
// set it to clickable=false
mButton1.setClickable(false);
// Change the background of the button to the disabled button color.
mButton1.setBackground(getDrawable(R.drawable.disabled_button_background));
//Set a FocusChangeListener on the button to disable the button if the focus is changed from it.
mButton1.setOnFocusChangeListener(getButtonFocuslistener());
FocusChangeListener
如下:
private View.OnFocusChangeListener getButtonFocuslistener() {
return new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
v.setEnabled(false);
}
};
}
现在发生的事情:
当用户点击按钮时,焦点仍然在按钮上,但它的颜色发生了变化,看起来像是被禁用了。由于在其上设置了 clickable=false,因此用户无法再次单击它。当用户将焦点移到任何其他视图时,此按钮将被禁用,因此无法再次获得焦点。所以,我可以实现我想要的。
在我的 AndroidTV 应用程序中,我有 TableLayout
和 TableRow
。这些行包含 Button
。当用户点击按钮时,该按钮将被禁用。当它发生时,我希望焦点应该转到 TableLayout
.
布局是这样的:
<?xml version="1.0" encoding="utf-8"?>
<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:shrinkColumns="*"
android:stretchColumns="*">
<TableRow
android:id="@+id/input_buttons_row"
android:layout_height="0dp"
android:layout_weight="1"
android:layout_gravity="center"
android:gravity="center"
android:layout_width="match_parent">
<Button
android:id="@+id/it1"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it2"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it3"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it4"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it5"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it6"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
<Button
android:id="@+id/it7"
android:layout_weight="1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:background="@drawable/selection_background"
android:focusable="true" />
</TableRow>
</TableLayout>
出现如下:
我在按下按钮时将其禁用。所以,我希望焦点应该转到视图中最近的按钮。示例:如果我按 'Button 5',焦点应转到 'Button 4' 或按钮 6'。我怎样才能做到这一点?
我尝试了 table 行上的请求焦点的各种组合。示例:
mInputButtonsRow.requestFocus(View.FOCUS_DOWN);
也尝试使用 requestFocus(View.FOCUS_BACKWARD)
和 requestFocus(View.FOCUS_FORWARD)
。焦点跳转到行中的第一个或最后一个按钮,而不是最近的可聚焦按钮!
但是,焦点总是转到 'Button 1' 如果它仍然启用。如果不是,它将转到 'Button 2' 等等。如何始终将焦点放在最近的按钮上而不是第一个启用的同级按钮上?
试了好几种方法都做不到。所以,这是对我有用的解决方法。这可能不是最好的方法。我仍然愿意接受更好的解决方案。这是我所做的: 当用户点击按钮时,
// Keep the focus on the same button.
mButton1.requestFocus();
// set it to clickable=false
mButton1.setClickable(false);
// Change the background of the button to the disabled button color.
mButton1.setBackground(getDrawable(R.drawable.disabled_button_background));
//Set a FocusChangeListener on the button to disable the button if the focus is changed from it.
mButton1.setOnFocusChangeListener(getButtonFocuslistener());
FocusChangeListener
如下:
private View.OnFocusChangeListener getButtonFocuslistener() {
return new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
v.setEnabled(false);
}
};
}
现在发生的事情: 当用户点击按钮时,焦点仍然在按钮上,但它的颜色发生了变化,看起来像是被禁用了。由于在其上设置了 clickable=false,因此用户无法再次单击它。当用户将焦点移到任何其他视图时,此按钮将被禁用,因此无法再次获得焦点。所以,我可以实现我想要的。