Android实现EditText输入自动格式为DD/MM/YYYY崩溃问题求助
问题原因
- 核心崩溃原因是数组索引越界:当输入完2位字符后,
str的长度为2,转换为字符数组后只有索引0、1两个有效位置,你直接尝试给索引2的位置赋值/,超出了数组的最大长度,触发崩溃。 - 第二个潜在问题:没有处理空指针和长度判断边界,用户删除字符等场景也可能触发异常。
修复后的完整实现
editText?.addTextChangedListener(object : TextWatcher { // 用标记位替代频繁增删监听器,性能更稳定 private var isFormatting = false override fun beforeTextChanged(charSequence: CharSequence?, start: Int, count: Int, after: Int) {} override fun onTextChanged(charSequence: CharSequence?, start: Int, before: Int, count: Int) {} override fun afterTextChanged(editable: Editable?) { editable ?: return // 正在格式化中直接返回,避免无限循环 if (isFormatting) return // 先移除所有已有的斜杠,拿到纯数字输入 val input = editable.toString().replace("/", "") if (input.isEmpty()) { isFormatting = true editable.clear() isFormatting = false return } val sb = StringBuilder() // 按规则拼接斜杠 for (i in input.indices) { when (i) { // 第2位数字后加第一个斜杠 2 -> { sb.append('/') sb.append(input[i]) } // 第4位数字后加第二个斜杠 4 -> { sb.append('/') sb.append(input[i]) } // 最多保留8位纯数字,对应完整的DDMMYYYY格式 in 0..7 -> sb.append(input[i]) } } isFormatting = true // 直接替换输入框内容,不需要重新setText editable.replace(0, editable.length, sb.toString()) // 光标定位到输入末尾 editText?.setSelection(sb.length) isFormatting = false } })
额外优化建议
- 可以给EditText加上
android:inputType="number"属性,限制用户只能输入数字,避免非数字字符干扰格式 - 如需做日期合法性校验,可以在用户输入完成后单独增加逻辑,判断月份是否在1-12区间、日期是否和月份匹配等
- 上述方案用
isFormatting标记位替代了反复移除、添加监听器的操作,性能更稳定,也能避免部分场景下的内存泄漏风险
内容的提问来源于stack exchange,提问作者Sparsh Dutta
相关产品推荐
相关产品推荐

