diff --git a/app/src/main/java/com/zcshou/database/DataBaseHistoryLocation.java b/app/src/main/java/com/zcshou/database/DataBaseHistoryLocation.java index 69d36e0c..4e0b7c53 100644 --- a/app/src/main/java/com/zcshou/database/DataBaseHistoryLocation.java +++ b/app/src/main/java/com/zcshou/database/DataBaseHistoryLocation.java @@ -55,4 +55,15 @@ public static void saveHistoryLocation(SQLiteDatabase sqLiteDatabase, ContentVal XLog.e("DATABASE: insert error"); } } + + // 修改历史记录名称 + public static void updateHistoryLocation(SQLiteDatabase sqLiteDatabase, String locID, String location) { + try{ + ContentValues contentValues = new ContentValues(); + contentValues.put(DB_COLUMN_LOCATION, location); + sqLiteDatabase.update(TABLE_NAME, contentValues, DB_COLUMN_ID + " = ?", new String[]{locID}); + } catch (Exception e){ + XLog.e("DATABASE: update error"); + } + } } \ No newline at end of file diff --git a/app/src/main/java/com/zcshou/gogogo/FragmentSettings.java b/app/src/main/java/com/zcshou/gogogo/FragmentSettings.java index aa716767..ae7610a2 100644 --- a/app/src/main/java/com/zcshou/gogogo/FragmentSettings.java +++ b/app/src/main/java/com/zcshou/gogogo/FragmentSettings.java @@ -2,7 +2,6 @@ import android.os.Bundle; import android.text.InputType; -import android.text.Selection; import androidx.preference.EditTextPreference; import androidx.preference.ListPreference; @@ -17,6 +16,25 @@ public class FragmentSettings extends PreferenceFragmentCompat { + // Set a non-empty decimal EditTextPreference + private void setupDecimalEditTextPreference(EditTextPreference preference) { + if (preference != null) { + preference.setSummaryProvider((Preference.SummaryProvider) pref -> + getResources().getString(R.string.setting_current_value) + pref.getText()); + preference.setOnBindEditTextListener(editText -> { + editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); + editText.setSelection(editText.length()); + }); + preference.setOnPreferenceChangeListener((pref, newValue) -> { + if (newValue.toString().trim().isEmpty()) { + GoUtils.DisplayToast(this.getContext(), getResources().getString(R.string.app_error_input_null)); + return false; + } + return true; + }); + } + } + @Override public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { // Load the preferences from an XML resource @@ -38,68 +56,16 @@ public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { } EditTextPreference pfWalk = findPreference("setting_walk"); - if (pfWalk != null) { - // 使用自定义 SummaryProvider - pfWalk.setSummaryProvider((Preference.SummaryProvider) preference -> getResources().getString(R.string.setting_current_value) + preference.getText()); - pfWalk.setOnBindEditTextListener(editText -> { - editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); - Selection.setSelection(editText.getText(), editText.length()); - }); - pfWalk.setOnPreferenceChangeListener((preference, newValue) -> { - if (newValue.toString().trim().length() == 0) { - GoUtils.DisplayToast(this.getContext(),getResources().getString(R.string.app_error_input_null)); - return false; - } - return true; - }); - } + setupDecimalEditTextPreference(pfWalk); EditTextPreference pfRun = findPreference("setting_run"); - if (pfRun != null) { - pfRun.setSummaryProvider((Preference.SummaryProvider) preference -> getResources().getString(R.string.setting_current_value) + preference.getText()); - pfRun.setOnBindEditTextListener(editText -> { - editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); - Selection.setSelection(editText.getText(), editText.length()); - }); - pfRun.setOnPreferenceChangeListener((preference, newValue) -> { - if (newValue.toString().trim().length() == 0) { - GoUtils.DisplayToast(this.getContext(),getResources().getString(R.string.app_error_input_null)); - return false; - } - return true; - }); - } + setupDecimalEditTextPreference(pfRun); + EditTextPreference pfBike = findPreference("setting_bike"); - if (pfBike != null) { - pfBike.setSummaryProvider((Preference.SummaryProvider) preference -> getResources().getString(R.string.setting_current_value) + preference.getText()); - pfBike.setOnBindEditTextListener(editText -> { - editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); - Selection.setSelection(editText.getText(), editText.length()); - }); - pfBike.setOnPreferenceChangeListener((preference, newValue) -> { - if (newValue.toString().trim().length() == 0) { - GoUtils.DisplayToast(this.getContext(),getResources().getString(R.string.app_error_input_null)); - return false; - } - return true; - }); - } + setupDecimalEditTextPreference(pfBike); EditTextPreference pfAltitude = findPreference("setting_altitude"); - if (pfAltitude != null) { - pfAltitude.setSummaryProvider((Preference.SummaryProvider) preference -> getResources().getString(R.string.setting_current_value) + preference.getText()); - pfAltitude.setOnBindEditTextListener(editText -> { - editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); - Selection.setSelection(editText.getText(), editText.length()); - }); - pfAltitude.setOnPreferenceChangeListener((preference, newValue) -> { - if (newValue.toString().trim().length() == 0) { - GoUtils.DisplayToast(this.getContext(),getResources().getString(R.string.app_error_input_null)); - return false; - } - return true; - }); - } + setupDecimalEditTextPreference(pfAltitude); SwitchPreferenceCompat pLog = findPreference("setting_log_off"); if (pLog != null) { @@ -120,20 +86,12 @@ public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { } EditTextPreference pfPosHisValid = findPreference("setting_pos_history"); - if (pfPosHisValid != null) { - // 使用自定义 SummaryProvider - pfPosHisValid.setSummaryProvider((Preference.SummaryProvider) preference -> getResources().getString(R.string.setting_current_value) + preference.getText()); - pfPosHisValid.setOnBindEditTextListener(editText -> { - editText.setInputType(InputType.TYPE_NUMBER_FLAG_DECIMAL | InputType.TYPE_CLASS_NUMBER); - Selection.setSelection(editText.getText(), editText.length()); - }); - pfPosHisValid.setOnPreferenceChangeListener((preference, newValue) -> { - if (newValue.toString().trim().length() == 0) { - GoUtils.DisplayToast(this.getContext(),getResources().getString(R.string.app_error_input_null)); - return false; - } - return true; - }); - } + setupDecimalEditTextPreference(pfPosHisValid); + + EditTextPreference pfLatOffset = findPreference("setting_lat_max_offset"); + setupDecimalEditTextPreference(pfLatOffset); + + EditTextPreference pfLonOffset = findPreference("setting_lon_max_offset"); + setupDecimalEditTextPreference(pfLonOffset); } } \ No newline at end of file diff --git a/app/src/main/java/com/zcshou/gogogo/HistoryActivity.java b/app/src/main/java/com/zcshou/gogogo/HistoryActivity.java index 380301db..f8e20060 100644 --- a/app/src/main/java/com/zcshou/gogogo/HistoryActivity.java +++ b/app/src/main/java/com/zcshou/gogogo/HistoryActivity.java @@ -9,6 +9,7 @@ import androidx.appcompat.app.AlertDialog; import androidx.preference.PreferenceManager; +import android.text.InputType; import android.text.TextUtils; import android.util.Log; import android.view.Menu; @@ -19,11 +20,16 @@ import android.widget.SearchView; import android.widget.SimpleAdapter; import android.widget.TextView; +import android.widget.EditText; +import android.widget.PopupMenu; +import android.view.Gravity; import java.math.BigDecimal; import java.math.RoundingMode; import java.util.ArrayList; import java.util.HashMap; +import java.util.Objects; +import java.util.Locale; import java.util.List; import java.util.Map; @@ -255,6 +261,59 @@ public boolean onQueryTextChange(String newText) {// 当搜索内容改变时触 }); } + private void showDeleteDialog(String locID) { + AlertDialog.Builder builder = new AlertDialog.Builder(this); + builder.setTitle("警告"); + builder.setMessage("确定要删除该项历史记录吗?"); + builder.setPositiveButton("确定", (dialog, whichButton) -> { + boolean deleteRet = deleteRecord(Integer.parseInt(locID)); + if (deleteRet) { + GoUtils.DisplayToast(HistoryActivity.this, getResources().getString(R.string.history_delete_ok)); + updateRecordList(); + } + }); + builder.setNegativeButton("取消", null); + + builder.show(); + } + + private void showInputDialog(String locID, String name) { + final EditText input = new EditText(this); + input.setInputType(InputType.TYPE_CLASS_TEXT); + input.setText(name); + + AlertDialog.Builder builder = new AlertDialog.Builder(this); + builder.setTitle("名称"); + builder.setView(input); + builder.setPositiveButton("确认", (dialog, whichButton) -> { + String userInput = input.getText().toString(); + DataBaseHistoryLocation.updateHistoryLocation(mHistoryLocationDB, locID, userInput); + updateRecordList(); + }); + builder.setNegativeButton("取消", null); + + builder.show(); + } + + private String[] randomOffset(String longitude, String latitude) { + String max_offset_default = getResources().getString(R.string.setting_random_offset_default); + double lon_max_offset = Double.parseDouble(Objects.requireNonNull(sharedPreferences.getString("setting_lon_max_offset", max_offset_default))); + double lat_max_offset = Double.parseDouble(Objects.requireNonNull(sharedPreferences.getString("setting_lat_max_offset", max_offset_default))); + double lon = Double.parseDouble(longitude); + double lat = Double.parseDouble(latitude); + + double randomLonOffset = (Math.random() * 2 - 1) * lon_max_offset; // Longitude offset (meters) + double randomLatOffset = (Math.random() * 2 - 1) * lat_max_offset; // Latitude offset (meters) + + lon += randomLonOffset / 111320; // (meters -> longitude) + lat += randomLatOffset / 110574; // (meters -> latitude) + + String offsetMessage = String.format(Locale.US, "经度偏移: %.2f米\n纬度偏移: %.2f米", randomLonOffset, randomLatOffset); + GoUtils.DisplayToast(this, offsetMessage); + + return new String[]{String.valueOf(lon), String.valueOf(lat)}; + } + private void initRecordListView() { noRecordText = findViewById(R.id.record_no_textview); mSearchLayout = findViewById(R.id.search_linear); @@ -270,6 +329,13 @@ private void initRecordListView() { bd09Longitude = latLngStr[0].substring(latLngStr[0].indexOf(':') + 1); bd09Latitude = latLngStr[1].substring(latLngStr[1].indexOf(':') + 1); + // Random offset + if(sharedPreferences.getBoolean("setting_random_offset", false)) { + String[] offsetResult = randomOffset(bd09Longitude, bd09Latitude); + bd09Longitude = offsetResult[0]; + bd09Latitude = offsetResult[1]; + } + if (!MainActivity.showLocation(name, bd09Longitude, bd09Latitude)) { GoUtils.DisplayToast(this, getResources().getString(R.string.history_error_location)); } @@ -277,23 +343,27 @@ private void initRecordListView() { }); mRecordListView.setOnItemLongClickListener((parent, view, position, id) -> { - new AlertDialog.Builder(HistoryActivity.this) - .setTitle("警告")//这里是表头的内容 - .setMessage("确定要删除该项历史记录吗?")//这里是中间显示的具体信息 - .setPositiveButton("确定", - (dialog, which) -> { - String locID = (String) ((TextView) view.findViewById(R.id.LocationID)).getText(); - boolean deleteRet = deleteRecord(Integer.parseInt(locID)); + PopupMenu popupMenu = new PopupMenu(HistoryActivity.this, view); + popupMenu.setGravity(Gravity.END | Gravity.BOTTOM); + popupMenu.getMenu().add("编辑"); + popupMenu.getMenu().add("删除"); + + popupMenu.setOnMenuItemClickListener(item -> { + String locID = ((TextView) view.findViewById(R.id.LocationID)).getText().toString(); + String name = ((TextView) view.findViewById(R.id.LocationText)).getText().toString(); + switch (item.getTitle().toString()) { + case "编辑": + showInputDialog(locID, name); + return true; + case "删除": + showDeleteDialog(locID); + return true; + default: + return false; + } + }); - if (deleteRet) { - GoUtils.DisplayToast(this, getResources().getString(R.string.history_delete_ok)); - updateRecordList(); - } - }) - .setNegativeButton("取消", - (dialog, which) -> { - }) - .show(); + popupMenu.show(); return true; }); diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 2ccefc0b..9403602c 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -65,6 +65,12 @@ 10.0 海拔高度(米) 55.0 + 位置 + 随机偏移 + 仅在使用历史位置时生效 + 10.0 + 经度最大偏移距离(米) + 纬度最大偏移距离(米) 记录 关闭日志 历史记录有效期(天) diff --git a/app/src/main/res/xml/preferences_main.xml b/app/src/main/res/xml/preferences_main.xml index 4b263a80..1b3388d1 100644 --- a/app/src/main/res/xml/preferences_main.xml +++ b/app/src/main/res/xml/preferences_main.xml @@ -44,6 +44,30 @@ + + + + + + +