简体   繁体   English

软键盘不能持续将焦点从AutoCompleteTextView更改为EditText

[英]Soft Keyboard does not persist on focus change from AutoCompleteTextView to EditText

On pressing the next button on the soft keyboard on my AutoCompleteTextView (whether data is entered or not), I have attempted to change focus to the next EditText and keep the soft keyboard. 在我的AutoCompleteTextView上按下软键盘上的下一个按钮(无论是否输入数据)时,我试图将焦点更改为下一个EditText并保持软键盘。 Focus changes, but the soft keyboard goes away. 焦点改变,但软键盘消失。 I've attempted to use an InputMethodManager to no avail. 我试图使用InputMethodManager无效。 Is there something fundamentally incorrect about what I'm doing? 我所做的事情有根本上不正确的地方吗?

public class AuthorizeLoadActivity extends AppCompatActivity {

TextView operatorNameValue;
ImageButton cameraButton;
TextView ticketNumberValue;
TextView saleNameValue;
Spinner haulerSpinner;
Spinner saleProductSpinner;
Spinner destinationSpinner;
AutoCompleteTextView driverAutoCompleteTextView;
EditText trailerEditText;
Spinner trailerDropSpinner;
Button cancelButton;
Button saveAuthorizationButton;
Button addACommentButton;
String barcodeValue;
ArrayList<SaleObject> savedArrayList;
SaleObject currentSaleObject;
ArrayList<String> haulerNameArrayList = new ArrayList<>();
ArrayList<String> saleProductNameArrayList = new ArrayList<>();
ArrayList<Integer> haulerIDArrayList = new ArrayList<>();
ArrayList<Integer> saleProductIDArrayList = new ArrayList<>();
ArrayList<String> destinationArrayList = new ArrayList<>();
ArrayList<AuthorizationObject> authorizationArrayList = new ArrayList<>();
ArrayList<String> driverArrayList = new ArrayList<>();

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

    //link instance of menu_main
    Toolbar mainToolbar = findViewById(R.id.toolbar);
    setSupportActionBar(mainToolbar);

    //Enable Up Button to return you to home page
    ActionBar actionBar = getSupportActionBar();
    if (actionBar != null) {
        actionBar.setDisplayHomeAsUpEnabled(true);
    }

    barcodeValue = getIntent().getStringExtra("barcodeValue");

    //Link UI to XML
    operatorNameValue = findViewById(R.id.operatorNameValue);
    cameraButton = findViewById(R.id.cameraButton);
    ticketNumberValue = findViewById(R.id.ticketNumberValue);
    saleNameValue = findViewById(R.id.saleNameSpinner);
    haulerSpinner = findViewById(R.id.ticketNumberTextView);
    saleProductSpinner = findViewById(R.id.saleProductSpinner);
    destinationSpinner = findViewById(R.id.buyerSpinner);
    driverAutoCompleteTextView = findViewById(R.id.driverAutoComplete);
    trailerEditText = findViewById(R.id.trailerNumberEditText);
    trailerDropSpinner = findViewById(R.id.trailerDropSpinner);
    cancelButton = findViewById(R.id.cancelButton);
    saveAuthorizationButton = findViewById(R.id.saveLoadButton);
    addACommentButton = findViewById(R.id.addACommentButton);

    //set Security Number Value to barcode information previously collected
    ticketNumberValue.setText(barcodeValue);

    //Reduce EditText/AutoCompleteTextView text sizes if using phone rather than tablet
    boolean tabletSize = getResources().getBoolean(R.bool.isTablet);
    if (!tabletSize) {
        driverAutoCompleteTextView.setTextSize(10);
        trailerEditText.setTextSize(10);
    }

    //Check files for existent drivers and pull them back into an ArrayList
    //Check internal storage for driver data
    try {
        //Set target file to drivers.txt
        File targetFile = new File(getFilesDir(), "drivers.txt");
        //Create new file input stream
        FileInputStream fis = new FileInputStream(targetFile);
        //Create new object input stream, using fis
        ObjectInputStream ois = new ObjectInputStream(fis);
        //write object input stream to object
        //noinspection unchecked
        driverArrayList = (ArrayList<String>) ois.readObject();
        //close object output stream
        ois.close();
        //close file output stream
        fis.close();
    } catch (ClassNotFoundException | IOException e) {
        e.printStackTrace();
    }

    //Setup autoCompleteTextView list with drivers
    ArrayAdapter<String> driverAdapter = new ArrayAdapter<>(this, android.R.layout.simple_dropdown_item_1line, driverArrayList);
    driverAutoCompleteTextView.setAdapter(driverAdapter);

    //show AutoComplete information without having to type first.
    driverAutoCompleteTextView.setOnFocusChangeListener(new View.OnFocusChangeListener() {
        @Override
        public void onFocusChange(View view, boolean hasFocus) {
            if (hasFocus) {
                driverAutoCompleteTextView.showDropDown();
            } else {
                driverAutoCompleteTextView.dismissDropDown();
            }
        }
    });

    //move to next editText when soft keyboard next button is pressed.
    driverAutoCompleteTextView.setOnKeyListener(new View.OnKeyListener() {

        public boolean onKey(View v, int keyCode, KeyEvent event) {
            // If the event is a key-down event on the "enter" button
            if ((event.getAction() == KeyEvent.ACTION_DOWN) &&
                    (keyCode == KeyEvent.KEYCODE_ENTER)) {
                // remove focus from driverAutoCompleteTextView
                driverAutoCompleteTextView.clearFocus();
                // give focus to trailerEditText
                trailerEditText.setFocusableInTouchMode(true);
                trailerEditText.requestFocus();

                showKeyboard(trailerEditText);

                return true;
            }
            return false;
        }

    });

    //Initiate the barcode reader to replace security number value field
    cameraButton.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
        }
    });

    cancelButton.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            finish();
        }
    });

    saveAuthorizationButton.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            if (haulerSpinner.getSelectedItemPosition() != 0 && saleProductSpinner.getSelectedItemPosition() != 0 && destinationSpinner.getSelectedItemPosition() != 0 && !driverAutoCompleteTextView.getText().toString().equals("") && !trailerEditText.getText().toString().equals("")) {
                //Get all of the pertinent data
                String currentOperatorID = currentSaleObject.getlbOperatorID();
                String currentSaleName = currentSaleObject.getTimberSaleName();
                Integer currentTimberSaleID = currentSaleObject.getTimberSaleID();
                Integer currentProductID = saleProductIDArrayList.get(saleProductSpinner.getSelectedItemPosition());
                String currentProductName = saleProductNameArrayList.get(saleProductSpinner.getSelectedItemPosition());
                Integer currentHaulerID = haulerIDArrayList.get(haulerSpinner.getSelectedItemPosition());
                String currentHaulerName = haulerNameArrayList.get(haulerSpinner.getSelectedItemPosition());
                String currentDestination = destinationArrayList.get(destinationSpinner.getSelectedItemPosition());
                String currentDriver = driverAutoCompleteTextView.getText().toString();
                String currentTrailerNumber = trailerEditText.getText().toString();
                Boolean currentTrailerDrop = trailerDropSpinner.getSelectedItemPosition() != 0;

                //If new driver, add driver name to drivers.text
                Boolean driverAlreadyExists = false;
                for (int i = 0; i < driverArrayList.size(); i++) {
                    if (driverArrayList.get(i).equals(currentDriver)) {
                        driverAlreadyExists = true;
                    }
                }
                if (!driverAlreadyExists) {
                    //add new driver to driverArrayList
                    driverArrayList.add(currentDriver);

                    //write driver list back to drivers.txt
                    try {
                        //Set target file to drivers.txt
                        File targetFile = new File(getFilesDir(), "drivers.txt");
                        //Create new file output stream
                        FileOutputStream fos = new FileOutputStream(targetFile);
                        //Create new object output stream, using fos
                        ObjectOutputStream oos = new ObjectOutputStream(fos);
                        //write object to object output stream
                        oos.writeObject(driverArrayList);
                        //close object output stream
                        oos.close();
                        //close file output stream
                        fos.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }

                //Get GPS values
                LocationManager mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
                double[] gpsValues = getLastBestLocation(mLocationManager);

                //if GPS data exists...
                if (gpsValues != null) {
                    double currentLatitude = gpsValues[0];
                    double currentLongitude = gpsValues[1];

                    //Create an authorization object with the data
                    AuthorizationObject currentAuthorization = new AuthorizationObject(currentOperatorID, currentTimberSaleID, currentSaleName, currentProductID, currentProductName, currentHaulerID, currentHaulerName, ticketNumberValue.getText().toString(), currentDestination, currentDriver, currentTrailerNumber, currentTrailerDrop, currentLatitude, currentLongitude);

                    //Check files for existent authorizations and pull them back as AuthorizationObjects
                    //Check internal storage for authorization data
                    try {
                        //Set target file to authorizations.txt
                        File targetFile = new File(getFilesDir(), "authorizations.txt");
                        //Create new file input stream
                        FileInputStream fis = new FileInputStream(targetFile);
                        //Create new object input stream, using fis
                        ObjectInputStream ois = new ObjectInputStream(fis);
                        //write object input stream to object
                        //noinspection unchecked
                        authorizationArrayList = (ArrayList<AuthorizationObject>) ois.readObject();
                        //close object output stream
                        ois.close();
                        //close file output stream
                        fis.close();
                    } catch (ClassNotFoundException | IOException e) {
                        e.printStackTrace();
                    }

                    //add authorization to authorizationArrayList
                    authorizationArrayList.add(currentAuthorization);

                    //write authorization list back to authorizations.txt
                    try {
                        //Set target file to authorizations.txt
                        File targetFile = new File(getFilesDir(), "authorizations.txt");
                        //Create new file output stream
                        FileOutputStream fos = new FileOutputStream(targetFile);
                        //Create new object output stream, using fos
                        ObjectOutputStream oos = new ObjectOutputStream(fos);
                        //write object to object output stream
                        oos.writeObject(authorizationArrayList);
                        //close object output stream
                        oos.close();
                        //close file output stream
                        fos.close();
                    } catch (IOException e) {
                        e.printStackTrace();
                    }

                    Intent authorizeLoadToMainIntent = new Intent(AuthorizeLoadActivity.this, MainActivity.class);
                    authorizeLoadToMainIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
                    startActivity(authorizeLoadToMainIntent);
                } else {
                    //TODO: Build better GPS permissions thing.
                    Toast.makeText(AuthorizeLoadActivity.this, "Must allow location permissions", Toast.LENGTH_SHORT).show();
                }

            } else {
                //TODO: Build more robust error-handling than just a toast.
                Toast.makeText(AuthorizeLoadActivity.this, "Fill out all fields", Toast.LENGTH_SHORT).show();
            }
        }
    });

    addACommentButton.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

        }
    });

    //Check internal storage for sale data
    try {
        //Set target file to sales.txt
        File targetFile = new File(getFilesDir(), "sales.txt");
        //Create new file input stream
        FileInputStream fis = new FileInputStream(targetFile);
        //Create new object input stream, using fis
        ObjectInputStream ois = new ObjectInputStream(fis);
        //write object input stream to object
        //noinspection unchecked
        savedArrayList = (ArrayList<SaleObject>) ois.readObject();
        //close object output stream
        ois.close();
        //close file output stream
        fis.close();
    } catch (ClassNotFoundException | IOException e) {
        e.printStackTrace();
    }

    //Start off with non-values in the spinners so I can ensure that users actually interacted with them
    haulerNameArrayList.add("");
    saleProductNameArrayList.add("");
    haulerIDArrayList.add(0);
    saleProductIDArrayList.add(0);
    destinationArrayList.add("");
    //Get range values to check against entered (or scanned) string
    for (int i = 0; i < savedArrayList.size(); i++) {
        ArrayList<RangeObject> currentSaleObjectRanges = savedArrayList.get(i).getRanges();
        for (int j = 0; j < currentSaleObjectRanges.size(); j++) {
            RangeObject currentRange = currentSaleObjectRanges.get(j);
            Integer startValue = currentRange.getStart();
            Integer endValue = currentRange.getEnd();
            //Check if editText string is an Integer
            try {
                Integer editTextInteger = Integer.parseInt(barcodeValue);
                //If it is:
                //If editTextInteger falls between the two of the range:
                if (editTextInteger >= startValue && editTextInteger <= endValue) {
                    currentSaleObject = savedArrayList.get(i);
                    //Set UI elements to correspond with current sale info.
                    operatorNameValue.setText(currentSaleObject.getLbOperatorName());
                    saleNameValue.setText(currentSaleObject.getTimberSaleName());
                    //Create ArrayList for contract objects and get all of their information.
                    //Essentially iterates through all contracts of currentSaleObject and creates an arrayList of contracts.
                    //This (single next line) was auto-generated by Android Studio. Was a for loop.
                    ArrayList<ContractObject> contractArrayList = new ArrayList<>(currentSaleObject.getContract());
                    //iterate through contractArrayList and get the values for the different fields
                    for (int k = 0; k < contractArrayList.size(); k++) {
                        ContractObject currentContract = contractArrayList.get(k);
                        haulerNameArrayList.add(currentContract.getHaulerName());
                        saleProductNameArrayList.add(currentContract.getSaleProductName());
                        haulerIDArrayList.add(currentContract.getHaulerID());
                        saleProductIDArrayList.add(currentContract.getSaleProductID());
                        destinationArrayList.add(currentContract.getDestinationName());
                    }

                    //remove duplicates in each arrayList for spinners
                    HashSet<String> haulerNameHashSet = new HashSet<>(haulerNameArrayList);
                    haulerNameArrayList.clear();
                    haulerNameArrayList.addAll(haulerNameHashSet);

                    HashSet<Integer> haulerIDHashSet = new HashSet<>(haulerIDArrayList);
                    haulerIDArrayList.clear();
                    haulerIDArrayList.addAll(haulerIDHashSet);

                    HashSet<String> productNameHashSet = new HashSet<>(saleProductNameArrayList);
                    saleProductNameArrayList.clear();
                    saleProductNameArrayList.addAll(productNameHashSet);

                    HashSet<Integer> productIDHashSet = new HashSet<>(saleProductIDArrayList);
                    saleProductIDArrayList.clear();
                    saleProductIDArrayList.addAll(productIDHashSet);

                    HashSet<String> destinationHashSet = new HashSet<>(destinationArrayList);
                    destinationArrayList.clear();
                    destinationArrayList.addAll(destinationHashSet);

                    //Set spinner values
                    //set simple adapters for spinners
                    ArrayAdapter<String> haulerSpinnerAdapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_dropdown_item, haulerNameArrayList);
                    haulerSpinner.setAdapter(haulerSpinnerAdapter);

                    ArrayAdapter<String> saleProductSpinnerAdapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_dropdown_item, saleProductNameArrayList);
                    saleProductSpinner.setAdapter(saleProductSpinnerAdapter);

                    ArrayAdapter<String> destinationSpinnerAdapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_dropdown_item, destinationArrayList);
                    destinationSpinner.setAdapter(destinationSpinnerAdapter);

                    //autofill spinner value if only one value is left after removing duplicates.
                    if (haulerNameArrayList.size() == 2) {
                        haulerSpinner.setSelection(1);
                    }
                    if (saleProductNameArrayList.size() == 2) {
                        saleProductSpinner.setSelection(1);
                    }
                    if (destinationArrayList.size() == 2) {
                        destinationSpinner.setSelection(1);
                    }

                }

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

        }

    }

}

private void showKeyboard(View view) {
    InputMethodManager manager = (InputMethodManager) this.getSystemService(Activity.INPUT_METHOD_SERVICE);

    manager.showSoftInput(view, 0);
}

//add action items to toolbar
@Override
public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.menu_main, menu);
    return true;
}

//add action item functionality
public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {

        case R.id.action_filter:
            // User chose the filter item, do stuff...
            return true;

        case R.id.action_first:
            // User chose the first item, do stuff...
            return true;

        case R.id.action_second:
            // User chose the second item, do stuff...
            return true;

        case R.id.action_third:
            // User chose the third item, do stuff...
            return true;

        default:
            // If we got here, the user's action was not recognized.
            // Invoke the superclass to handle it.
            return super.onOptionsItemSelected(item);
    }
}

//Used to bring over scan information from the barcode reader
public void onActivityResult(int requestCode, int resultCode, Intent intent) {
    IntentResult scanningResult = IntentIntegrator.parseActivityResult(requestCode, resultCode, intent);
    if (scanningResult != null) {
        //set scanned data to security number value
        barcodeValue = scanningResult.getContents();
        ticketNumberValue.setText(barcodeValue);

    } else {
        Toast toast = Toast.makeText(getApplicationContext(),
                "No scan data received!", Toast.LENGTH_SHORT);
        toast.show();
    }

}

private double[] getLastBestLocation(LocationManager mLocationManager) {
    if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
        // TODO: Consider calling this to handle no GPS permissions
        //    ActivityCompat#requestPermissions
        // here to request the missing permissions, and then overriding
        //   public void onRequestPermissionsResult(int requestCode, String[] permissions,
        //                                          int[] grantResults)
        // to handle the case where the user grants the permission. See the documentation
        // for ActivityCompat#requestPermissions for more details.
        Toast.makeText(this, "You don't have location permissions enabled", Toast.LENGTH_SHORT).show();
        return null;
    } else {
        Location locationGPS = mLocationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
        Location locationNet = mLocationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);

        long GPSLocationTime = 0;
        if (null != locationGPS) {
            GPSLocationTime = locationGPS.getTime();
        }

        long NetLocationTime = 0;

        if (null != locationNet) {
            NetLocationTime = locationNet.getTime();
        }

        if (0 < GPSLocationTime - NetLocationTime) {
            if (locationGPS != null) {
                return new double[]{locationGPS.getLatitude(), locationGPS.getLongitude()};
            } else {
                return null;
                //TODO: Handle nulls, here.
            }
        } else {
            if (locationNet != null) {
                return new double[]{locationNet.getLatitude(), locationNet.getLongitude()};
            } else {
                return null;
                //TODO: Handle nulls, here.
            }
        }
    }
}

} }

If you want the soft keyboard to show up, then do this 如果要显示软键盘,请执行此操作

driverAutoCompleteTextView.setOnKeyListener(new View.OnKeyListener() {

    public boolean onKey(View v, int keyCode, KeyEvent event) {
        // If the event is a key-down event on the "enter" button
        if ((event.getAction() == KeyEvent.ACTION_DOWN) &&
                (keyCode == KeyEvent.KEYCODE_ENTER))
        {
            // remove focus from driverAutoCompleteTextView
            driverAutoCompleteTextView.clearFocus();
            // give focus to trailerEditText
            trailerEditText.setFocusable(true);
            trailerEditText.setFocusableInTouchMode(true);
            boolean isFocused = trailerEditText.requestFocus();
            Log.d("myTag","isFocused is: "+isFocused);
            Log.d("myTag","driver auto complete text view focused: "+driverAutoCompleteTextView.isFocused());
            showKeyboard(trailerEditText);

            return true;
        }
        return false;
    }
}); 

private void showKeyboard(View view){
    InputMethodManager manager = (InputMethodManager) this.getSystemService(Activity.INPUT_METHOD_SERVICE);

    manager.showSoftInput(view,InputMethodManager.SHOW_IMPLICIT);
}

This is quick and dirty but it should work. 这既快速又肮脏,但可以正常工作。 Also, you should add trailerEditText.setFocusableInTouchMode(true) in your onCreate method or in your xml. 另外,您应该在onCreate方法或xml中添加trailerEditText.setFocusableInTouchMode(true)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM