热门标签 | HotTags
当前位置:  开发笔记 > Android > 正文

Android中EditTextsetText方法的踩坑实战

这篇文章主要给大家分享了一些关于Android中EditTextsetText方法的踩坑记录,文中通过示例代码介绍的非常详细,对各位Android开发者们具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

1、平平常常中就这样开始

某一天,我准备做一个搜索功能,这个搜索功能呢大概是在主活动A中,用EditText接收输入,当EditText监听到输入框中内容有变化,跳转到活动B中,活动B中准备有搜索历史记录等等,等在活动B中确定好搜索关键词后,跳回到活动A中,执行搜索,并显示搜索结果……一切顺顺利利,然后呢,懵逼了,我回不了活动A了。

当时的情况大致是这样的,

布局文件:activity_main.xml

<&#63;xml version="1.0" encoding="utf-8"&#63;>

 
 

活动A:AcitivityA.java

public class ActivityA extends AppCompatActivity {
 private EditText searchEditText;
 @Override
 protected void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 setContentView(R.layout.activity_main);
 //找到EditText,添加文本监听
 searchEditText=findViewById(R.id.et_search);
 searchEditText.addTextChangedListener(new TextWatcher() {
  @Override
  public void beforeTextChanged(CharSequence s, int start, int count, int after) {
  Log.d("editTextSetText","beforeTextChanged");
  }

  @Override
  public void onTextChanged(CharSequence s, int start, int before, int count) {
  Log.d("editTextSetText","onTextChanged");
  }

  @Override
  public void afterTextChanged(Editable s) {
  Log.d("editTextSetText","afterTextChanged");
  startActivity(new Intent(ActivityA.this,ActivityB.class));
  }
 });
 //接收B活动传递过来的keywords,并显示在输入框中
 String keyword=getIntent().getStringExtra("keywords");
 if(keyword!=null)
  searchEditText.setText(keyword);
 }

活动B布局文件:activity_search.xml

<&#63;xml version="1.0" encoding="utf-8"&#63;>


 

 

活动B:ActivityB.java

public class ActivityB extends AppCompatActivity {
 private EditText editTextKeyWords;

 @Override
 public void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 setContentView(R.layout.activity_search);
 editTextKeyWords = findViewById(R.id.et_search_keywords);
 editTextKeyWords.setOnEditorActionListener(new TextView.OnEditorActionListener() {
  @Override
  public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
  if (actiOnId== EditorInfo.IME_ACTION_SEARCH) {
   //将取得关键字传递到A中
   String keywords = v.getText().toString().trim();
   Intent intent = new Intent(ActivityB.this, ActivityA.class);
   intent.putExtra("keywords", keywords);
   Log.d("editTextSetText", "B keywords:" + keywords);
   startActivity(intent);

   ActivityB.this.finish();
  }
  return false;
  }
 });

 }
}

OK,至此大功告成,我成功复原了当时我大致做法,也还原了当时的Bug:在A中有输入时,跳到B,在B中确定好关键词后,点击搜索(你的搜索在哪里,让你们看下图吧)


看到右下角我圈起来的那个搜索按钮了吗,布局文件照着我那个写,监听就是editTextKeyWords.setOnEditorActionListener(……),布局中重要的是

 android:inputType="text"
 android:singleLine="true"
 android:imeOptiOns="actionSearch"

这个主要是参看这位大大的,当然了,在此这不算重点,重点是我又成功写了个Bug。当时项目挺急的,我弄了半天没弄明白,(我一直以为是A活动因为setText而崩溃了,然而没有log……当然,最终证明似乎不是这样子。),无奈之下,福灵心至,想到:

2、用了setHint()解决了当务之急

无奈之下选择了该方法,问题成功解决,也没什么明显瑕疵,就是心理一直惦记着,这他丫的问题出在什么地方呢,定位当然是定位到了A活动中的searchEditText.setText(keyword)这一句。

后来加了几天班,等稍微有空了,我再回头瞧瞧,莫非,谷歌给我们写了个小bug,结果嘛:事实证明,好像这东西是自己的锅。

3、发现敌踪迹

当时我实在onResume()调用searchEditText.setText(keyword)这几句的,所以问题显得比我上面写的要隐蔽些。当然,有空了之后,我进入setText方法,一步步执行,当然了,没发现明显问题。只是我偶尔会发现它会不经意间往beforeTextChanged等这一两个方法中眺一下,那么想一想我在里面又做了什么……,似乎我发现问题所在了。那么有了猜测,对该方法添加log,我们队log做下修改,使其能明确地显示程序执行顺序,修改代码如下:

ActivityA.java

public class ActivityA extends AppCompatActivity {
 private EditText searchEditText;
 public static int executeOrder=0;//表示log执行顺序,进而推测代码执行顺序
 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  setContentView(R.layout.activity_main);
  Log.d("editTextSetText","after setContentView "+executeOrder++);
  //找到EditText,添加文本监听
  searchEditText=findViewById(R.id.et_search);
  searchEditText.addTextChangedListener(new TextWatcher() {
   @Override
   public void beforeTextChanged(CharSequence s, int start, int count, int after) {
    Log.d("editTextSetText","beforeTextChanged "+executeOrder++);
   }

   @Override
   public void onTextChanged(CharSequence s, int start, int before, int count) {
    Log.d("editTextSetText","onTextChanged "+executeOrder++);
   }

   @Override
   public void afterTextChanged(Editable s) {
    Log.d("editTextSetText","afterTextChanged "+executeOrder++);
    startActivity(new Intent(ActivityA.this,ActivityB.class));
   }
  });
  //接收B活动传递过来的keywords,并显示在输入框中
  String keyword=getIntent().getStringExtra("keywords");
  if(keyword!=null) {
   searchEditText.setText(keyword);
   Log.d("editTextSetText","after set text "+executeOrder++);
   /*searchEditText.setHint(keyword);*/
  }
 }
}

ActivityB.java

public class ActivityB extends AppCompatActivity {
 private EditText editTextKeyWords;

 @Override
 public void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  setContentView(R.layout.activity_search);
  Log.d("editTextSetText", "B after setContentView " +ActivityA.executeOrder++);
  editTextKeyWords = findViewById(R.id.et_search_keywords);
  editTextKeyWords.setOnEditorActionListener(new TextView.OnEditorActionListener() {
   @Override
   public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
    if (actiOnId== EditorInfo.IME_ACTION_SEARCH) {
      //将取得关键字传递到A中
      String keywords = v.getText().toString().trim();
      Intent intent = new Intent(ActivityB.this, ActivityA.class);
      intent.putExtra("keywords", keywords);
      Log.d("editTextSetText", "B keywords:" + keywords+" " +ActivityA.executeOrder++);
      startActivity(intent);
      ActivityB.this.finish();
    }
    return false;
   }
  });
 }
}

执行一遍,log如下:


上述log显示,做如下解读:

1、 启动应用,执行初始化,打印 0

2、输入内容,执行1,2,3,到启动活动B

3、活动B初始化执行 4

5、 活动B中点击搜索 5,并启动活动A

6、A再一次初始化 执行6

7、问题出来了,为什么会执行7、8、9,此时我们并没有EditText输入内容,但是监听触发了。

8、 执行9之后,启动活动B,执行11没问题,但是10的顺序按理说应该在6之后、紧接着6.

尽管未能完全解读这个执行顺序,但是,写的程序陷入了一个类似死循环的bug是没有问题的,这也就解开了为什么返回不了A活动的问题,并不是不能返回A,而是返回A之后又跳转到B了。

进一步调试,在关键节点增加log,我们再setText前后增加log

if(keyword!=null) {
   Log.d("editTextSetText","after set text "+executeOrder++);
   searchEditText.setText(keyword);
   Log.d("editTextSetText","after set text "+executeOrder++);
   /*searchEditText.setHint(keyword);*/
  }

log信息:


关键点我已经标出来了,在7和11间,有了监听方法的执行,说明:EditText的setText方法会触发 文本变化的监听,这就是此次踩坑的根源。

4、 捕获凶手:setText()方法会触发EditText文本变化的监听

5、解决方案:将setText设置在设置监听之前,或者用setHint也可以。

如上,找出问题症结之后,解决办法就很简单了,我们将setText写在设置监听之前就可以避免该坑,或者干脆用setHint方法。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,如果有疑问大家可以留言交流,谢谢大家对的支持。


推荐阅读
  • Android 九宫格布局详解及实现:人人网应用示例
    本文深入探讨了人人网Android应用中独特的九宫格布局设计,解析其背后的GridView实现原理,并提供详细的代码示例。这种布局方式不仅美观大方,而且在现代Android应用中较为少见,值得开发者借鉴。 ... [详细]
  • 优化ListView性能
    本文深入探讨了如何通过多种技术手段优化ListView的性能,包括视图复用、ViewHolder模式、分批加载数据、图片优化及内存管理等。这些方法能够显著提升应用的响应速度和用户体验。 ... [详细]
  • 深入解析Android自定义View面试题
    本文探讨了Android Launcher开发中自定义View的重要性,并通过一道经典的面试题,帮助开发者更好地理解自定义View的实现细节。文章不仅涵盖了基础知识,还提供了实际操作建议。 ... [详细]
  • 国内BI工具迎战国际巨头Tableau,稳步崛起
    尽管商业智能(BI)工具在中国的普及程度尚不及国际市场,但近年来,随着本土企业的持续创新和市场推广,国内主流BI工具正逐渐崭露头角。面对国际品牌如Tableau的强大竞争,国内BI工具通过不断优化产品和技术,赢得了越来越多用户的认可。 ... [详细]
  • 本文详细介绍如何使用arm-eabi-gdb调试Android平台上的C/C++程序。通过具体步骤和实用技巧,帮助开发者更高效地进行调试工作。 ... [详细]
  • 深入理解 Oracle 存储函数:计算员工年收入
    本文介绍如何使用 Oracle 存储函数查询特定员工的年收入。我们将详细解释存储函数的创建过程,并提供完整的代码示例。 ... [详细]
  • 本文总结了2018年的关键成就,包括职业变动、购车、考取驾照等重要事件,并分享了读书、工作、家庭和朋友方面的感悟。同时,展望2019年,制定了健康、软实力提升和技术学习的具体目标。 ... [详细]
  • 在计算机技术的学习道路上,51CTO学院以其专业性和专注度给我留下了深刻印象。从2012年接触计算机到2014年开始系统学习网络技术和安全领域,51CTO学院始终是我信赖的学习平台。 ... [详细]
  • CSS 布局:液态三栏混合宽度布局
    本文介绍了如何使用 CSS 实现液态的三栏布局,其中各栏具有不同的宽度设置。通过调整容器和内容区域的属性,可以实现灵活且响应式的网页设计。 ... [详细]
  • Linux 系统启动故障排除指南:MBR 和 GRUB 问题
    本文详细介绍了 Linux 系统启动过程中常见的 MBR 扇区和 GRUB 引导程序故障及其解决方案,涵盖从备份、模拟故障到恢复的具体步骤。 ... [详细]
  • 如何在WPS Office for Mac中调整Word文档的文字排列方向
    本文将详细介绍如何使用最新版WPS Office for Mac调整Word文档中的文字排列方向。通过这些步骤,用户可以轻松更改文本的水平或垂直排列方式,以满足不同的排版需求。 ... [详细]
  • 理解存储器的层次结构有助于程序员优化程序性能,通过合理安排数据在不同层级的存储位置,提升CPU的数据访问速度。本文详细探讨了静态随机访问存储器(SRAM)和动态随机访问存储器(DRAM)的工作原理及其应用场景,并介绍了存储器模块中的数据存取过程及局部性原理。 ... [详细]
  • 360SRC安全应急响应:从漏洞提交到修复的全过程
    本文详细介绍了360SRC平台处理一起关键安全事件的过程,涵盖从漏洞提交、验证、排查到最终修复的各个环节。通过这一案例,展示了360在安全应急响应方面的专业能力和严谨态度。 ... [详细]
  • 几何画板展示电场线与等势面的交互关系
    几何画板是一款功能强大的物理教学软件,具备丰富的绘图和度量工具。它不仅能够模拟物理实验过程,还能通过定量分析揭示物理现象背后的规律,尤其适用于难以在实际实验中展示的内容。本文将介绍如何使用几何画板演示电场线与等势面之间的关系。 ... [详细]
  • 本文介绍如何通过Windows批处理脚本定期检查并重启Java应用程序,确保其持续稳定运行。脚本每30分钟检查一次,并在需要时重启Java程序。同时,它会将任务结果发送到Redis。 ... [详细]
author-avatar
子幽
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有