【问题标题】:OnClick Position in String in TextView文本视图中字符串中的 OnClick 位置
【发布时间】:2018-10-19 22:20:53
【问题描述】:

我不知道该怎么做,但我想知道当一个人单击 TextView 上的某个位置时,是否有办法在 TextView 中的字符串中获取位置(索引)。所以,如果有人点击下面的TextView:

Hello I'm Vinay Hiremath.

在第一个“H”上,onClick 事件将获得整数 0。或者,如果有人单击“V”,它将获得 10,依此类推。

任何帮助,像往常一样,非常感谢。如果这在Android Developers 上公然公开,请随意称我为白痴并扔石头。

【问题讨论】:

标签: android indexing onclick textview


【解决方案1】:

所以我最终通过 James Moore 的评论 here 中的链接解决了这个问题。我最终在该链接中使用了 Tony Blues 的解决方案。该解决方案是这样的:

1.) 为 TextView 设置一个 onTouchListener。

2.) 获取 TextView 的布局。

3.) 通过事件获取触摸的x,y坐标。

4.) 根据该事件查找行和偏移量(索引)。

以下代码示例是如何在给定名为 manip 的 TextView 的情况下记录(详细)触摸的索引:

manip.setOnTouchListener(new View.OnTouchListener() {
    public boolean onTouch(View v, MotionEvent event) {
        Layout layout = ((TextView) v).getLayout();
        int x = (int)event.getX();
        int y = (int)event.getY();
        if (layout!=null){
            int line = layout.getLineForVertical(y);
            int offset = layout.getOffsetForHorizontal(line, x);
            Log.v("index", ""+offset);
        }
        return true;
    }
});

编辑:Rahul Mandaliya 提醒我注意,如果文本视图上有填充,此代码将失败。不幸的是,我已经很长时间没有编写任何 Android 代码了,所以我不确定如何更新这个答案来解决这个问题。直观地说,如果您知道填充值,您似乎可以对点击事件进行某种检查。很抱歉不能在这个边缘案例上提供更多帮助。 :-(

【讨论】:

  • 这仅适用于 textivew 的布局宽度和高度为环绕内容时。如果您将宽度或高度填充为父级,则选择其他偏移量
  • @RahulMandaliya 选择了哪个偏移量?我会更新我的答案 - 我已经很久没有做过任何 Android 的东西了。 :-P
  • 只需在您的文本视图上添加填充,然后单击外部文本,您必须为文本视图添加条件,例如 if(offset
  • 啊,我明白了。因此,如果在实际文本内容之外(在某些填充上)单击,则此代码将失败。这就是你说的吗?只是澄清一下。
  • @Vinay 非常感谢。你的回答拯救了我的一天!
【解决方案2】:

如果您遵循已接受的答案,您可能会注意到每次用户触摸屏幕时都会引发多次onTouch 事件。使用event.getAction() 找出正在处理的操作。这取决于引发事件的用户行为。例如,对于屏幕上的简单触摸,onTouch 事件将触发两次,动作为ACTION_DOWNACTION_UP。对于触摸和移动,您将获得不同的动作,具体取决于移动(在控件内,从外到内,反之亦然)。更多详情请查看MotionEvent

以下代码是已接受答案的修改版本,仅处理 ACTION_DOWN 操作:

manip.setOnTouchListener(new View.OnTouchListener() {
  public boolean onTouch(View v, MotionEvent event) {
    if (event.getAction() == MotionEvent.ACTION_DOWN) {
      Layout layout = ((TextView) v).getLayout();
      int x = (int)event.getX();
      int y = (int)event.getY();
      if (layout!=null){
          int line = layout.getLineForVertical(y);
          int offset = layout.getOffsetForHorizontal(line, x);
          Log.v("index", ""+offset);
          }
    }
    return true;
  }
});

【讨论】:

  • 我的支持。在这一点上,我已经有一段时间没有接触任何与 Android 相关的东西了,但这似乎是有道理的。 :-)
【解决方案3】:

1) 列出清单。

2)将此字符串拆分为单独的字符。

3) 采取 setOnItemClickListener(new OnItemClickListener() ) 事件。

4) 通过 get args 显示每个字符的 Toast。

它会帮助你。

【讨论】:

  • 如果 Octavian 的答案对我有用,那么我将使用它(它更符合我的需求),但 +1 是一种创造性/不同的解决这个问题的方法。 ;-)
【解决方案4】:

因为我没有机会测试它,所以要加一点盐。

TextViewandroid:textIsSelectable 属性设置为true,然后使用getSelectionStart()getSelectionEnd() 方法。

我真的只是在做一个有根据的猜测。

【讨论】:

  • 非常感谢 Octavian 的精彩指导!如果它有效,这实际上对我希望在我的应用程序中使用的未来功能非常有帮助。但是,每当我将“android:textIsSelectable="true"” 放入我的 XML 布局中时,它都会告诉我“在包 'android' 中找不到属性 'textIsSelectable' 的资源标识符”。你知道这可能意味着什么吗?看起来有人在这里遇到了同样的问题:androidforums.com/application-development/… 但没有得到答案。任何帮助表示赞赏。
  • 作为旁注,我知道这个问题是关于完全不同的事情,所以,一旦我弄清楚整个“textIsSelectable”问题,无论你是否可以帮助我,如果你的答案有效,我会给你信用并将其标记为这个问题的答案。我总是把功劳归于应得的地方。
  • 哦。看来这个问题是由于我没有告诉你方法 isTextSelectable() 来自 API 级别 11 (Honeycomb)。我不确定它是否有效。我得自己试试。
【解决方案5】:

根据上面的正确答案,我添加了更多功能。这样它也会显示你点击的字母,如果你在边界外点击它会停止错误,如果你不把它放在try catch,应用程序会崩溃。

manip.setOnTouchListener(new View.OnTouchListener() {
  public boolean onTouch(View v, MotionEvent event) {
    if (event.getAction() == MotionEvent.ACTION_DOWN) {
      Layout layout = ((TextView) v).getLayout();
      int x = (int)event.getX();
      int y = (int)event.getY();
      if (layout!=null){
          int line = layout.getLineForVertical(y);
          int offset = layout.getOffsetForHorizontal(line, x);
           try{
              char texts = textView.getText().charAt(offset);
              Toast.makeText(MainActivity.this,"the offset are "+offset+"letter are "+texts,Toast.LENGTH_SHORT).show();
            }catch (Exception e){
              Toast.makeText(MainActivity.this,"the error are "+e,Toast.LENGTH_SHORT).show();
            }
          }
    }
    return true;
  }
});

【讨论】:

    猜你喜欢
    • 2013-04-19
    • 2014-06-28
    • 2021-01-18
    • 2022-11-22
    • 2013-03-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多