我需要制作类似于此的屏幕。我认为它有autocompletetextview和listview来显示返回的结果。此处使用Google Place API自动建议地点,并相应地更新listview适配器。 请各种帮助表示赞赏。 提前谢谢。
在AutoComplete上检查了Android示例项目的位置。但它没有任何listview来显示结果。相反,它在autocompletetextview微调器中显示结果。我们可以对该项目进行任何修改
答案 0 :(得分:12)
您可以使用EditText
和ListView
而不是AutoCompleteTextView
来完全实现此目的。在EditText
中输入字符,通过调用ListView
网络服务过滤GooglePlacesAutomplete
中的结果。以下是代码:
这是您的layoout文件(EditText
与ListView
)
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#ffffff"
tools:context="com.example.siddarthshikhar.liftsharesample.EnterLocationActivity">
<EditText
android:paddingLeft="@dimen/activity_horizontal_margin"
android:layout_width="250dp"
android:layout_height="35dp"
android:textColorHint="#ffffff"
android:id="@+id/edEnterLocation"
android:textColor="#ffffff"
android:textSize="@dimen/abc_text_size_medium_material"
android:layout_alignParentLeft="true"
android:backgroundTint="#00000000"
android:gravity="start|center">
<requestFocus />
</EditText>
<ListView android:id="@+id/listView1" android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/filterLayout"/>
</RelativeLayout>
在相应的Activity中,访问此EditText并应用Filterable。您必须使用GooglePlacesAutompleteAdapter
。
以下是GooglePlacesAutompleteAdapter
:
public class GooglePlacesAutocompleteAdapter extends ArrayAdapter implements Filterable {
private static final String LOG_TAG = "Google Places Autocomplete";
private static final String PLACES_API_BASE = "https://maps.googleapis.com/maps/api/place";
private static final String TYPE_AUTOCOMPLETE = "/autocomplete";
private static final String OUT_JSON = "/json";
private static final String API_KEY = "your_api_key";
private ArrayList<String> resultList;
private Context context = null;
public GooglePlacesAutocompleteAdapter(Context context, int textViewResourceId) {
super(context, textViewResourceId);
this.context = context;
}
@Override
public int getCount() {
if(resultList != null)
return resultList.size();
else
return 0;
}
@Override
public String getItem(int index) {
return resultList.get(index);
}
public ArrayList<String> autocomplete(String input) {
ArrayList<String> resultList = null;
ArrayList<String> descriptionList = null;
HttpURLConnection conn = null;
StringBuilder jsonResults = new StringBuilder();
try {
StringBuilder sb = new StringBuilder(PLACES_API_BASE + TYPE_AUTOCOMPLETE + OUT_JSON);
sb.append("?key=" + API_KEY);
sb.append("&components=country:in");
sb.append("&input=" + URLEncoder.encode(input, "utf8"));
URL url = new URL(sb.toString());
conn = (HttpURLConnection) url.openConnection();
InputStreamReader in = new InputStreamReader(conn.getInputStream());
// Load the results into a StringBuilder
int read;
char[] buff = new char[1024];
while ((read = in.read(buff)) != -1) {
jsonResults.append(buff, 0, read);
}
} catch (MalformedURLException e) {
Log.e(LOG_TAG, "Error processing Places API URL", e);
return resultList;
} catch (IOException e) {
Log.e(LOG_TAG, "Error connecting to Places API", e);
return resultList;
} finally {
if (conn != null) {
conn.disconnect();
}
}
try {
// Create a JSON object hierarchy from the results
Log.d("yo",jsonResults.toString());
JSONObject jsonObj = new JSONObject(jsonResults.toString());
JSONArray predsJsonArray = jsonObj.getJSONArray("predictions");
// Extract the Place descriptions from the results
resultList = new ArrayList(predsJsonArray.length());
descriptionList = new ArrayList(predsJsonArray.length());
for (int i = 0; i < predsJsonArray.length(); i++) {
resultList.add(predsJsonArray.getJSONObject(i).toString());
descriptionList.add(predsJsonArray.getJSONObject(i).getString("description"));
}
saveArray(resultList.toArray(new String[resultList.size()]), "predictionsArray", getContext());
} catch (JSONException e) {
Log.e(LOG_TAG, "Cannot process JSON results", e);
}
return descriptionList;
}
@Override
public Filter getFilter() {
Filter filter = new Filter() {
@Override
protected FilterResults performFiltering(CharSequence constraint) {
FilterResults filterResults = new FilterResults();
if (constraint != null) {
// Retrieve the autocomplete results.
resultList = autocomplete(constraint.toString());
// Assign the data to the FilterResults
filterResults.values = resultList;
filterResults.count = resultList.size();
}
return filterResults;
}
@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
if (results != null && results.count > 0) {
setImageVisibility();
notifyDataSetChanged();
} else {
notifyDataSetInvalidated();
}
}
};
return filter;
}
}
访问适配器并将getFilter()
应用于相应EditText
中的Activity
。以下内容将添加到您之前创建的布局中的活动中:
dataAdapter = new GooglePlacesAutocompleteAdapter(EnterLocationActivity.this, R.layout.adapter_google_places_autocomplete){
listView = (ListView) findViewById(R.id.listView1);
// Assign adapter to ListView
listView.setAdapter(dataAdapter);
//enables filtering for the contents of the given ListView
listView.setTextFilterEnabled(true);
etEnterLocation.addTextChangedListener(new TextWatcher() {
public void afterTextChanged(Editable s) {
}
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
public void onTextChanged(CharSequence s, int start, int before, int count) {
dataAdapter.getFilter().filter(s.toString());
}
});
这应该让你去。您可以根据需要修改布局。这基本上会在ListView
。
答案 1 :(得分:3)
Here就是如何做到这一点的一个例子。
您可以从适配器获取任何AutocompletePrediction
。只需从getItem(int position)
的{{1}}拨打AutoCompleteTextView
,然后根据需要使用点击预测中的所有数据。
链接相关代码:
AdapterView.OnItemClickListener
答案 2 :(得分:1)
您可以通过在布局中添加以下代码,以更简单的方式实现自动完成textview
<fragment
android:id="@+id/place_autocomplete_fragment"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:name="com.google.android.gms.location.places.ui.PlaceAutocompleteFragment"
/>
要使用上述代码,您需要在Google develepor控制台中为您的应用配置一些设置。请参阅Android Places autocomplete example以获取完整示例