简体   繁体   English

Android-在片段中检索和使用视图位置

[英]Android - Retrieve and use views position in fragment

I have a fragment with 4 buttons. 我有一个带有4个按钮的片段。 I want to save each button's position on screen in a hash-map (each button will be mapped to its position on screen). 我想将每个按钮在屏幕上的位置保存在哈希图中(每个按钮将映射到其在屏幕上的位置)。 What is the easiest way of doing it? 最简单的方法是什么? Before using fragments, I used the onWindowFocusChanged method (in Activity) in which I could retrieve the button position. 在使用片段之前,我使用了onWindowFocusChanged方法(在Activity中),可以在其中检索按钮位置。 With fragments I tried to use ViewTreeObserver (with GlobalLayoutListener). 对于片段,我尝试使用ViewTreeObserver(与GlobalLayoutListener一起使用)。 Inside the anonymous class I can retrieve and save (in instance variable) the button position but outside of it these values are gone (equal 0). 在匿名类内部,我可以检索并保存(在实例变量中)按钮的位置,但是在其外部,这些值都消失了(等于0)。 How can it be done? 如何做呢?

Thanks! 谢谢!

EDIT: added a code snippet - 编辑:添加了一个代码段-

public void getViewsPosition(final ArrayList<View> viewArr) {
    for (final View v : viewArr) {
        final ViewTreeObserver vto = v.getViewTreeObserver();
        vto.addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                int[] i = new int[2];
                v.getLocationOnScreen(i);
                _rect = new Rect(i[0], i[1], i[0] + v.getWidth(), i[1]
                        + v.getHeight());
                view_to_rect.put(v, _rect);
                if (Build.VERSION.SDK_INT < 16) {
                    vto.removeGlobalOnLayoutListener(this);
                } else {
                    vto.removeOnGlobalLayoutListener(this);
                }
            }
        });
    }
    Log.i(TAG, "size of view to rect = " + String.valueOf(view_to_rect.size()));
}

where viewArr is an arrayList of all my views in this layout ; 其中viewArr是此布局中我所有视图的arrayList; view_to_rect is an instance variable declared as: view_to_rect是一个实例变量,声明为:

private static Map view_to_rect = new HashMap(); 私人静态地图view_to_rect = new HashMap();

The Log always shows "size of view to rect = 0". 日志始终显示“ rect的视图大小= 0”。

attached also the implementation of onViewCreated: 附加了onViewCreated的实现:

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    Log.i(TAG, "onViewCreated");
    final ViewGroup _mainView = (ViewGroup) getView().findViewById(
            R.id.fragment01);
    getAllViews(viewsList, _mainView);
    Log.i(TAG, "size of view list = " + String.valueOf(viewsList.size()));
    getViewsPosition(viewsList);
}

from where getViewsPosition is called. 从哪里调用getViewsPosition。

Edit#2: I'll try to clarify my intentions. 编辑#2:我将尝试阐明我的意图。 I'm building app with fragment. 我正在用片段构建应用程序。 each fragment, let's say, has 4 buttons. 假设每个片段都有4个按钮。 I want these buttons to listen to touch events so as the user touches a button and moves his finger to another button (without lifting his finger) there will be an audio feedback of the button's name. 我希望这些按钮能够监听触摸事件,以便用户触摸一个按钮并将其手指移至另一个按钮(无需抬起手指)时,将会收到该按钮名称的音频反馈。 For that I need to have all buttons positions so to be able to identify moving from one button to another (in onTouch method). 为此,我需要拥有所有按钮的位置,以便能够识别从一个按钮到另一个按钮的移动(在onTouch方法中)。 And for that I need an instance variable which will keep all buttons positions on screen and I will be able to use it in onTouch. 为此,我需要一个实例变量,该变量将在屏幕上保留所有按钮的位置,并且可以在onTouch中使用它。 The solution you suggested does not solve the problem because outside of 您建议的解决方案无法解决问题,因为

public void getViewsPosition(final ArrayList viewArr) public void getViewsPosition(final ArrayList viewArr)

the size of view_to_rect is still 0. view_to_rect的大小仍为0。

Edit #3: 编辑#3:

Here is the process in which I try to build my collection: 这是我尝试构建集合的过程:

1) Class signature + collection and array definition: 1)类签名+集合和数组定义:

public class Fragment01 extends Fragment implements OnTouchListener,
    OnClickListener{
        private Map<View, Rect> view_to_rect = new HashMap<View, Rect>();
        ArrayList<View> viewsList = new ArrayList<View>();

2) onViewCreated implementation: 2)onViewCreated实现:

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);
    Log.i(TAG, "onViewCreated");
    final ViewGroup _mainView = (ViewGroup) getView().findViewById(
            R.id.fragment01);
    getAllViews(viewsList, _mainView);
    Log.i(TAG, "size of view list = " + String.valueOf(viewsList.size()));
    getViewsPosition(viewsList);
    Log.i(TAG, "size of view to rect = " + String.valueOf(view_to_rect.size()));
}

3) getViewsPosition(...) and onPositioUpdate() methods - 3)getViewsPosition(...)和onPositioUpdate()方法-

public void getViewsPosition(final ArrayList<View> viewArr) {
    for (final View v : viewArr) {
        final ViewTreeObserver vto = v.getViewTreeObserver();
        vto.addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                int[] i = new int[2];
                v.getLocationOnScreen(i);
                _rect = new Rect(i[0], i[1], i[0] + v.getWidth(), i[1]
                        + v.getHeight());
                if (Build.VERSION.SDK_INT < 16) {
                    vto.removeGlobalOnLayoutListener(this);
                } else {
                    vto.removeOnGlobalLayoutListener(this);
                }

                onPositionUpdate();
            }
        });
    }
}

private void onPositionUpdate() {
}

The first Log in onViewCreated(...) is "size of view list = 7". 第一个登录onViewCreated(...)是“视图列表的大小= 7”。

My question is how can I get the second log print out "size of view to rect = 7" ? 我的问题是如何获取第二个日志打印出来的“ rect的视图大小= 7”? it always returns 0. 它总是返回0。

I didn't really, probably, understand how to use your solution with onPositionUpdate() method. 我可能不是很了解如何通过onPositionUpdate()方法使用您的解决方案。 How should it be implemented in order to achieve my goal? 如何实现我的目标?

ViewTreeObserver will be notify only when the view is rendered, What do you you mean by 仅当呈现视图时,才会通知ViewTreeObserver,这是什么意思

"but outside of it these values are gone" “但除此之外,这些价值已经消失了”

You can just get the positions of buttons in the GlobalLayoutListener callback, and save it the instance. 您可以仅获取GlobalLayoutListener回调中按钮的位置,然后将其保存到实例中。 Remember, you can only get the positions on rendered. 请记住,您只能在渲染位置上获得位置。

REMIND: 提醒:

put this code 把这个代码

Log.i(TAG, "size of view to rect = " + String.valueOf(view_to_rect.size())); Log.i(TAG,“ rect的视图大小=” + String.valueOf(view_to_rect.size()));

inside the public void onGlobalLayout() {}, then you will get non-zero. 在public void onGlobalLayout(){}中,那么您将获得非零值。

Why: 为什么:

Only the onGlobalLayout method is called, you can get non-zero. 仅调用onGlobalLayout方法,您可以获取非零值。

         public void onGlobalLayout() {
                int[] i = new int[2];
                v.getLocationOnScreen(i);
                _rect = new Rect(i[0], i[1], i[0] + v.getWidth(), i[1]
                        + v.getHeight());
                view_to_rect.put(v, _rect);
                if (Build.VERSION.SDK_INT < 16) {
                    vto.removeGlobalOnLayoutListener(this);
                } else {
                    vto.removeOnGlobalLayoutListener(this);
                }

                onPositionUpdate();

            }

private void onPositionUpdate()
{
    //do your work with positions
}

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

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