Android spinner закрыть
у меня есть активность со спиннером, и мне было интересно, можно ли закрыть спиннер программно, если пользователь открыл его.
вся история в том, что в фоновом режиме я запускаю процесс в отдельном потоке. Когда процесс завершен, я вызываю обработчик основного действия и, в зависимости от результата, выполняю некоторые задачи. Именно тогда я хочу закрыть счетчик, это пользователь открыл его.
блесны-в основном.XML макет:
<Spinner android:id="@+id/birthPlaceSpinner" android:layout_weight="1"
android:layout_height="wrap_content" android:prompt="@string/select"
android:layout_width="fill_parent" />
и это обработчик:
private class BirthplaceChangedHandler extends Handler {
@Override
public void handleMessage(Message msg) {
String placeFilterStr = birthPlaceFilterText.getText().toString();
if ("".equals(placeFilterStr) || placeFilterStr == null || validNewAddresses.isEmpty()) {
birthPlaceSpinner.setEnabled(false);
hideGeoLocationInformation();
} else {
birthPlaceSpinner.setEnabled(true);
}
adapter = new ArrayAdapter<String>(getApplicationContext(), R.layout.multiline_spinner_dropdown_item, validNewAddressesStr)
birthPlaceSpinner.setAdapter(adapter);
}
}
Ура!
8 ответов
Я не вижу способа сделать это-нет метод Spinner
, чтобы закрыть его. "Открытая" часть a Spinner
Это AlertDialog
на Android 1.x и 2.x, и я не совсем уверен, как он реализуется на Honeycomb при использовании голографической темы.
единственным выходом будет клонировать источник Spinner
и добавьте код самостоятельно, чтобы закрыть диалог. Но, опять же, он не будет работать на Honeycomb или выше, пока вы не сможете видеть и клонировать это код тоже.
помимо этого, я бы подумал, что вы хотите бедный UX. Если пользователь открыл Spinner
, они, скорее всего, активно изучает Spinner
содержание и делает выбор. Выдернуть это из-под их пальца, в лучшем случае, смутит их. Просьба рассмотреть альтернативный подход.
кроме того, не используйте getApplicationContext()
если вы не знаете почему вы используете getApplicationContext()
. Вам не нужно и даже не хотите getApplicationContext()
при создании ArrayAdapter
.
это работает для меня:
class SomeAdapter extends BaseAdapter implements SpinnerAdapter {
//......
public View getDropDownView(int position, View convertView, ViewGroup parent) {
View view = convertView;
if (view == null) {
//......
}
view.setOnClickListener(new ItemOnClickListener(parent));
return view;
}
//.....
}
и нажмите кнопку слушателя:
class ItemOnClickListener implements View.OnClickListener {
private View _parent;
public ItemOnClickListener(ViewGroup parent) {
_parent = parent;
}
@Override
public void onClick(View view) {
//.......
// close the dropdown
View root = _parent.getRootView();
root.dispatchKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_BACK));
root.dispatchKeyEvent(new KeyEvent(KeyEvent.ACTION_UP, KeyEvent.KEYCODE_BACK));
}
}
Ну это немного сложнее, чем я думал.
я добавляю шаг за шагом детали здесь. Попробуй последовать за ним. Я смог достичь этого на уровне api 10.
и это решение предполагает, что вы должны закрыть диалоговое окно приглашения программно, когда пользователь нажимает кнопку "Домой" или если вам нужно перейти к следующему действию без взаимодействия с пользователем
первый шаг-создать пользовательский счетчик, расширив класс Spinner. Допустим, я создал класс CustomSpinner в пакете com.БЦ.sampleapp
мой класс CustomSpinner выглядит так,
package com.bts.sampleapp;
import android.content.Context;
import android.util.AttributeSet;
import android.widget.Spinner;
public class CustomSpinner extends Spinner{
Context context=null;
public CustomSpinner(Context context) {
super(context);
this.context=context;
}
public CustomSpinner(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public CustomSpinner(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public void onDetachedFromWindow() {
super.onDetachedFromWindow();
}
}
теперь в вашем Xml-файле замените элемент Spinner на этот пользовательский spinner,
<com.bts.sampleapp.CustomSpinner
android:id="@+id/spin"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
следующим шагом является инициализация и установка адаптера на этот счетчик в вашем классе активности,
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
CustomSpinner spin=null;
spin=(CustomSpinner)findViewById(R.id.spin);
spin.setAdapter(spinnerAdapter); //you can set your adapter here.
}
последний шаг, чтобы закрыть диалоговое окно, когда пользователь нажимает на HomeButton или Когда действие переходит в фоновый режим. Для этого мы переопределяем onPause () следующим образом:
@Override
protected void onPause() {
Log.i("Life Cycle", "onPause");
spin.onDetachedFromWindow();
super.onPause();
}
теперь в onPause () вызовите метод spin.onDetachedFromWindow();
который выполняет работу по закрытию диалогового окна приглашения для вас.
теперь, когда это сказано, вызов spin.onDetachedFromWindow();
из любой точки вашей деятельности должен помочь вам закрыть счетчик программно. Поэтому, если это то, что вы хотите, удалите onpause()
.
public static void hideSpinnerDropDown(Spinner spinner) {
try {
Method method = Spinner.class.getDeclaredMethod("onDetachedFromWindow");
method.setAccessible(true);
method.invoke(spinner);
} catch (Exception e) {
e.printStackTrace();
}
}
Я думаю, что вы должны отказаться от использования Spinner
и вместо того, чтобы использовать ImageView
С Анимации (т. е. <animation-list>
), чтобы создать свой собственный счетчик. Вы просто установите ImageView
фон, чтобы быть вашим кадром анимации drawable.
затем вы можете легко сделать что-то такой начать и остановить его.
Как насчет клонирования нажатия клавиши "Назад"?
хорошо, я просто попробовал
[current activity].dispatchKeyEvent(new KeyEvent(KeyEvent.ACTION_DOWN,KeyEvent.KEYCODE_BACK));
и он не сделал ничего, что я мог видеть,затем нажал физическую клавишу "Назад", и падение исчезло. Также попытался сделать ACTION_UP сразу после down-никакого эффекта.
вы хотели бы закрыть свои блесны из любого места. Инъекция ключа для заднего нажатия-хорошее решение, но здесь вы закрываете все виды сразу.
как насчет setPressed (false)?
Ссылка на сайт:
закрыть выпадающий список блесны, когда два из всех в groupview нажаты одновременно
в противном случае:
Попробуйте сделать спиннер focusable
и focusableInTouchMode
, и использовать clearFocus()
на нем. Попробуйте сосредоточиться на представлении под ним, используя requestFocus()
метод.
Проверьте, закрывается ли раскрывающийся список spinner