【问题标题】:My app stops when I search any location in SearchView当我在 SearchView 中搜索任何位置时,我的应用程序停止
【发布时间】:2021-03-01 19:58:44
【问题描述】:

我试图运行与以下 youtube 视频中所示相同的代码... Here is the Link

但是当我尝试运行它时,地图会加载,但是当我搜索任何查询(位置)时它会停止...... 下面是代码:

MainActivity.java

package com.example.maps;


import androidx.appcompat.app.AppCompatActivity;
import androidx.fragment.app.FragmentActivity;

import android.location.Address;
import android.location.Geocoder;
import android.os.Bundle;
import android.widget.SearchView;

import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;

import java.io.IOException;
import java.util.List;

public class MainActivity extends FragmentActivity implements OnMapReadyCallback {
GoogleMap gmap;
SupportMapFragment supportMapFragment;
SearchView searchView;


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    searchView=findViewById(R.id.sv_location);
    supportMapFragment=(SupportMapFragment) getSupportFragmentManager()
            .findFragmentById(R.id.pickup);

    searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
        @Override
        public boolean onQueryTextSubmit(String query) {
            String location = searchView.getQuery().toString();
            List<Address> addressList=null;

            if(location != null || !location.equals("")){
                Geocoder geocoder=new Geocoder(MainActivity.this);
                try {
                    addressList=geocoder.getFromLocationName(location,1);

                    Address address = addressList.get(0);
                    LatLng latLng=new LatLng(address.getLatitude(),address.getLongitude());
                    gmap.addMarker(new MarkerOptions().position(latLng).title(location));
                    gmap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng,10));

                }catch (IOException e){
                    e.printStackTrace();
                }

            }
            return false;
        }

        @Override
        public boolean onQueryTextChange(String newText) {
            return false;
        }
    });
    supportMapFragment.getMapAsync(this);
}

@Override
public void onMapReady(GoogleMap googleMap) {

}
}

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <fragment
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/pickup"
        android:name="com.google.android.gms.maps.SupportMapFragment"/>

    <SearchView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:id="@+id/sv_location"
        android:queryHint="Search.."
        android:iconifiedByDefault="false"
        android:layout_margin="10dp"
        android:elevation="5dp"
        android:background="@drawable/bg_round"/>
</RelativeLayout>

当我在SearchView 中搜索任何位置时出现以下错误:

I/Choreographer: Skipped 299 frames!  The application may be doing too much work on its main thread.
D/AndroidRuntime: Shutting down VM
E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.maps, PID: 6141
    java.lang.NullPointerException: Attempt to invoke virtual method 'com.google.android.gms.maps.model.Marker com.google.android.gms.maps.GoogleMap.addMarker(com.google.android.gms.maps.model.MarkerOptions)' on a null object reference
        at com.example.maps.MainActivity$1.onQueryTextSubmit(MainActivity.java:50)
        at android.widget.SearchView.onSubmitQuery(SearchView.java:1259)
        at android.widget.SearchView.-wrap8(Unknown Source:0)
        at android.widget.SearchView$5.onEditorAction(SearchView.java:1236)
        at android.widget.TextView.onEditorAction(TextView.java:5911)
        at com.android.internal.widget.EditableInputConnection.performEditorAction(EditableInputConnection.java:138)
        at com.android.internal.view.IInputConnectionWrapper.executeMessage(IInputConnectionWrapper.java:360)
        at com.android.internal.view.IInputConnectionWrapper$MyHandler.handleMessage(IInputConnectionWrapper.java:85)
        at android.os.Handler.dispatchMessage(Handler.java:106)
        at android.os.Looper.loop(Looper.java:164)
        at android.app.ActivityThread.main(ActivityThread.java:6494)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)

【问题讨论】:

    标签: java android android-studio


    【解决方案1】:

    你还没有初始化gmap。你可以像video

    public void onMapReady(GoogleMap googleMap) {
        gmap = googleMap;
    }
    

    【讨论】:

    • 谢谢它的工作,但是现在当我再次搜索位置然后一次又一次地创建标记时..但我想从上次搜索的位置删除标记并将其放置到新位置位置..那么你能建议我吗...?
    • 我在下面的答案评论中提供了链接
    • 那么我应该使用 gmap.clear() 函数来删除标记吗?
    【解决方案2】:

    您正在使用访问 gmap 对象而不进行初始化。所以在 onMapReady

    中初始化它
    package com.example.maps;
    
    
    import androidx.appcompat.app.AppCompatActivity;
    import androidx.fragment.app.FragmentActivity;
    
    import android.location.Address;
    import android.location.Geocoder;
    import android.os.Bundle;
    import android.widget.SearchView;
    
    import com.google.android.gms.maps.CameraUpdateFactory;
    import com.google.android.gms.maps.GoogleMap;
    import com.google.android.gms.maps.OnMapReadyCallback;
    import com.google.android.gms.maps.SupportMapFragment;
    import com.google.android.gms.maps.model.LatLng;
    import com.google.android.gms.maps.model.MarkerOptions;
    
    import java.io.IOException;
    import java.util.List;
    
    public class MainActivity extends FragmentActivity implements OnMapReadyCallback {
    GoogleMap gmap;
    SupportMapFragment supportMapFragment;
    SearchView searchView;
    
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        searchView=findViewById(R.id.sv_location);
        supportMapFragment=(SupportMapFragment) getSupportFragmentManager()
                .findFragmentById(R.id.pickup);
    
        searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
            @Override
            public boolean onQueryTextSubmit(String query) {
                String location = searchView.getQuery().toString();
                List<Address> addressList=null;
    
                if(location != null || !location.equals("")){
                    Geocoder geocoder=new Geocoder(MainActivity.this);
                    try {
                        addressList=geocoder.getFromLocationName(location,1);
    
                        Address address = addressList.get(0);
                        LatLng latLng=new LatLng(address.getLatitude(),address.getLongitude());
                        gmap.addMarker(new MarkerOptions().position(latLng).title(location));
                        gmap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng,10));
    
                    }catch (IOException e){
                        e.printStackTrace();
                    }
    
                }
                return false;
            }
    
            @Override
            public boolean onQueryTextChange(String newText) {
                return false;
            }
        });
        supportMapFragment.getMapAsync(this);
    }
    
    @Override
    public void onMapReady(GoogleMap googleMap) {
    gmap = googleMap;
    }
    

    您可以使用清除地图

    gmap.clear();
    

    【讨论】:

    • 但是现在当我再次搜索位置然后再次创建标记时..但是我想从上次搜索的位置删除标记并将其放置到新位置..那么你能建议我...?
    • @smith,你有答案how to remove marker?
    • @WahdatKashmiri,您的答案适用于清除,但使用它并不总是好的做法
    • @Tuqay 你能建议我在我的代码中使用什么其他的好习惯吗?
    • @smith 这真的取决于您的用例。如果您不再需要并且想要删除多个标记,那么最好的选择是使用clear()。但是如果你想保存其中的一些,那么remove()会是一个更好的选择
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-08-28
    • 1970-01-01
    • 1970-01-01
    • 2011-09-05
    • 2012-09-22
    • 1970-01-01
    相关资源
    最近更新 更多