【问题标题】:onScrollChange() is not being called for every pixel scrolled on ScrollViewScrollView 上滚动的每个像素都不会调用 onScrollChange()
【发布时间】:2017-11-06 12:31:57
【问题描述】:

我想在每滚动 50 像素后添加新的子视图,但声明 Log.d("scroll",scrollY+":"+oldScrollY); 缺少一些值,即 scrollY = 149scrollY = 151 存在于 Log 但 @987654325 @ 不见了。所以代码不会为scrollY = 150 运行,也不会添加新的子视图。

虽然对于scrollY 的大多数值,它应该正常工作,但对于scrollY 的少数值,事件没有被触发。

我该如何解决这个问题?或者有没有其他方法可以实现这一点。

public class MainActivity extends AppCompatActivity implements ScrollViewListener {

    RelativeLayout parent;
    TextView height;
    ObservableScrollView scrollView;
    int position=1;
    View view1,view2;

    @RequiresApi(api = Build.VERSION_CODES.M)
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        parent = (RelativeLayout) findViewById(R.id.parent);
        scrollView = (ObservableScrollView) findViewById(R.id.scroll_view);

        LayoutInflater inflater = LayoutInflater.from(this);
        view1 = inflater.inflate(R.layout.education,null, false);
        view1.setId(R.id.parent+position);

        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
                                                                             ViewGroup.LayoutParams.WRAP_CONTENT);
        params.addRule(RelativeLayout.LEFT_OF,R.id.divider);
        params.topMargin = 100;
        params.rightMargin = 3;
        parent.addView(view1, params);
        position++;

        final Animation leftAnimation = new TranslateAnimation(view1.getX()-50,view1.getX(),view1.getY()+100,view1.getY());
        leftAnimation.setDuration(1000);
        view1.setAnimation(leftAnimation);

        scrollView.setOnScrollChangeListener(new View.OnScrollChangeListener() {
            @Override
            public void onScrollChange(View view, int scrollX, int scrollY, int oldScrollX, int oldScrollY) {
                Log.d("scroll",scrollY+":"+oldScrollY);
                if((scrollY-oldScrollY)>0 && scrollY%50 == 0)
                {
                    Log.d("scroll","abcghfg");

                    if(position%2==0)
                    {
                        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
                                ViewGroup.LayoutParams.WRAP_CONTENT);
                        params.addRule(RelativeLayout.RIGHT_OF,R.id.divider);
                       // params.topMargin = (position-1)*(view1.getLayoutParams().height)+position*100;
                        params.topMargin = 30;
                        params.leftMargin = 3;
                        params.addRule(RelativeLayout.BELOW,parent.getChildAt(position-1).getId());
                        Log.d("scroll","abc");
                        view2 = LayoutInflater.from(MainActivity.this).inflate(R.layout.education,null,false);
                        view2.setId(R.id.parent+position);

                        Animation rightAimation = new TranslateAnimation(view2.getX()+50,view2.getX(),view2.getY()+100,view2.getY());
                        rightAimation.setDuration(1000);
                        view2.startAnimation(rightAimation);

                        parent.addView(view2, params);
                    }
                    else
                    {
                        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
                                ViewGroup.LayoutParams.WRAP_CONTENT);
                        params.addRule(RelativeLayout.LEFT_OF,R.id.divider);
                        //params.topMargin = (position-1)*(view1.getLayoutParams().height)+position*100;
                        params.topMargin = 30;
                        params.rightMargin = 3;
                        params.addRule(RelativeLayout.BELOW,parent.getChildAt(position-1).getId());
                        Log.d("scroll","def");
                        view2 = LayoutInflater.from(MainActivity.this).inflate(R.layout.education,null,false);
                        view2.setId(R.id.parent+position);

                        Animation animation = new TranslateAnimation(view2.getX()-50,view2.getX(),view2.getY()+100,view2.getY());
                        animation.setDuration(1000);
                        view2.startAnimation(animation);

                        parent.addView(view2, params);
                    }
                    position++;
                }
            }
        });
    }
}

提前致谢。

【问题讨论】:

    标签: android android-scrollview onscrollchanged


    【解决方案1】:

    Android 不会渲染滚动中的每个像素,因为这会影响性能。如果滚动速度非常慢,您会看到每个像素都会调用回调,但如果滚动速度很快,则会在渲染触发时调用。

    在您的情况下,您需要检查自上次渲染最后一个视图以来它是否渲染了 50 或更多像素。

    【讨论】:

    • 你是对的。但是,如果直接从 49 像素滚动到 201 像素,则会出现问题,那么那些应该在 50、100、150 和 200 像素处添加的视图将被遗漏。没有其他解决方案可以在 android 中绘制这样的 UI,它可以在滚动时平滑地添加新视图(不取决于滚动速度),就像我们在网站中看到的那样
    • 我又面临一个问题。当我回到顶部时快速向下滚动后,有时所有子视图(以前添加)都会被删除。
    • 您有什么理由不使用 RecyclerView?
    • 我如何使用 RecyclerView?我实际上是在一条垂直线的左侧和右侧添加这些视图,或者在其他视图下方添加一个
    • 您可以有一个具有左右视图的行,并定义一个将在适配器的 onBindView 中可见。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-11-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-01
    相关资源
    最近更新 更多