为Spinner创建setError()

时间:2010-09-20 09:05:26

标签: android spinner

如何为setError()创建TextView/EditText(类似于Spinner)函数?以下不起作用:

我尝试在构造函数中扩展Spinner类:

ArrayAdapter<String> aa = new ArrayAdapter<String>(getContext(),
                    android.R.layout.simple_spinner_item, android.R.id.text1,
                    items);
            aa.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
            setAdapter(aa);
             tv = (TextView) findViewById(android.R.id.text1);
            // types_layout_list_tv

            ctv = (CheckedTextView) aa.getDropDownView(1, null, null);
            tv2 = (TextView) aa.getView(1, null, null);

setError方法:

    public void setError(String str) {
        if (tv != null)
            tv.setError(str);
        if(tv2!=null)
            tv2.setError(str);
        if (ctv != null)
            ctv.setError(str);
    }

8 个答案:

答案 0 :(得分:39)

与@Gábor的解决方案类似,但我不需要创建自己的适配器。我只是在我的验证功能中调用以下代码(即单击提交按钮)

        TextView errorText = (TextView)mySpinner.getSelectedView();                  
        errorText.setError("anything here, just to add the icon");
        errorText.setTextColor(Color.RED);//just to highlight that this is an error
        errorText.setText("my actual error text");//changes the selected item text to this

答案 1 :(得分:20)

我有一个解决方案并不涉及创建额外的编辑字段,但您需要照常使用自己的SpinnerAdapter

确保您在适配器TextView中使用的布局中至少有一个getView()(无论如何,您通常都会这样做。)

将以下功能添加到您的适配器(将name更改为TextView的ID):

public void setError(View v, CharSequence s) {
  TextView name = (TextView) v.findViewById(R.id.name);
  name.setError(s);
}

以这种方式从您的代码中调用setError()

YourAdapter adapter = (YourAdapter)spinner.getAdapter();
View view = spinner.getSelectedView();
adapter.setError(view, getActivity().getString(R.string.error_message));

基本上,与任何其他控件一样,只有您在适配器上调用它,并且您还必须提供视图。

这将在微调器上显示错误图标,就像其他控件一样。

答案 2 :(得分:6)

这可以在不使用自定义布局或适配器的情况下完成。

((TextView)spinner.getChildAt(0)).setError("Message");

此方法的唯一缺点是,当点击图标时,带有错误文本的小弹出窗口将不会显示。

答案 3 :(得分:5)

我建议你在你的微调器后面放一个空的EditText

EditText

的xml集上
android:enabled="false"
    android:inputType="none"

现在,当您想为您的微调器设置错误时,只需将该错误设置为EditText

切记不要将EditText设置为invisibille / gone。它不会那样工作。

另请注意,通过此方法,您可以准确确定错误的显示位置。

答案 4 :(得分:1)

感谢Gabor提供的出色解决方案。为了促进你的观点,我的解决方案是:

自定义适配器

    public class RequiredSpinnerAdapter<T> extends ArrayAdapter<T> {
        public RequiredSpinnerAdapter(Context context, int textViewResourceId,
                                      java.util.List<T> objects) {
            super(context, textViewResourceId, objects);
        }

        int textViewId = 0;

        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            View view = super.getView(position, convertView, parent);
            if (view instanceof TextView) {
                textViewId = view.getId();
            }
            return view;
        }

        public View getDropDownView(int position, View convertView, ViewGroup parent) {
            View row = super.getView(position, convertView, parent);
            return (row);
        }

        public void setError(View v, CharSequence s) {
            if(textViewId != 0){
                TextView name = (TextView) v.findViewById(textViewId);
                name.setError(s);
            }
        }
    }

使用适配器进行Spinner

ArrayAdapter<String> arrayAdapter = new RequiredSpinnerAdapter<String>(PropertyAdd.this, R.layout.checked, status_arr);
    marketstatus_spinner.setAdapter(arrayAdapter);
    marketstatus_spinner.setOnItemSelectedListener(new OnItemSelectedListener() {
        @Override
        public void onItemSelected(AdapterView<?> arg0, View arg1,
                                   int arg2, long arg3) {

            // Put code here
        }

        @Override
        public void onNothingSelected(AdapterView<?> arg0) {
           // Put code here
        }
    });

检查验证

private boolean checkValidation() {
    if(marketstatus_spinner.getSelectedItem().toString().equals("")){
        RequiredSpinnerAdapter adapter = (RequiredSpinnerAdapter)marketstatus_spinner.getAdapter();
        View view = marketstatus_spinner.getSelectedView();
        adapter.setError(view, "Please select a value");

        return false;
    }
}

答案 5 :(得分:0)

我猜Spinner不适合放这种方法。如果是Spinner,你应该选择一个值,并且应该在适配器的级别上过滤Spinner中的值。因此,用户只能选择Spinner中的那些值。

答案 6 :(得分:0)

您可以创建自己的适配器(扩展BaseAdapter实现SpinnerAdapter)。这样,您就可以访问微调器中显示的TextView。 (getView和createViewFromResource方法 - 示例:ArrayAdapter)当您添加一个空列表项以允许用户将该字段保持为空(直到它成为必需项)(微调器中的第一项)时,您可以将其TextView存储为私有适配器中的成员。然后,当需要从Activity或Fragment调用setError(“...”)时,可以在可以将其传递给空TextView的适配器上调用它。

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    return createViewFromResource(position, convertView, parent, mTextViewId);
}

private View createViewFromResource(int position, View convertView, ViewGroup parent, int resource) {
    View view;
    TextView text;

    if (convertView == null) {
        view = inflater.inflate(resource, parent, false);
    } else {
        view = convertView;
    }

    try {
        text = (TextView) view;
    } catch (ClassCastException e) {
        Log.e(TAG, "You must supply a resource ID for a TextView", e);
        throw new IllegalStateException("MyAdapter requires the resource ID to be a TextView", e);
    }

    MyItem i = getItem(position);
    String s = (null != i) ? i.toString() : "";
    text.setText(s);

    if ("".equals(s) && null == mEmptyText) {
        this.mEmptyText = text;
    }

    return view;
}

public void setError(String errorMessage) {
    if (null != mEmptyText) {
        mEmptyText.setError(errorMessage);
    } else {
        Log.d(TAG, "mEmptyText is null");
    }
}

答案 7 :(得分:0)

实际上就是这样,您只需要在视图中只有一个import collections, re fields = {'productId':'Product ID', 'score':'Rating', 'helpfulness':'Number Voting', 'text':'Review'} pattern = r'/([^:]*):\s?(.*)' kv = re.compile(pattern) data = collections.defaultdict(list) with open('file.txt') as f: reviews = f.read() for match in kv.finditer(reviews): key, value = match.groups() if key in fields: data[fields[key]].append(value) df = pd.DataFrame.from_dict(data) ,然后如果所选视图中的主视图为{TextView,则使用getSelectedView()从您的微调器中获取所选视图{1}}然后将您的视图直接投放到TextViewTextView,如下所示:

setError

否则,如果Textview不是直接在主视图中,那么您需要通过ID找到它并再次投射它并((TextView) jobCategory.getSelectedView()).setError("Field Required"); 这样:

setError