0

我正在尝试创建一个自定义表面视图,每次视图出现在屏幕上时,视图都会自行开始播放视频。我想知道当视图显示在 UI 上并被用户看到时,会通知 View 中的什么方法。我正在使用 viewpager,因此 SurfaceCreated 不起作用,因为视图是在它们显示在屏幕上之前创建的。

4

1 回答 1

1

当视频出现在屏幕上时,如何在视图寻呼机中自动启动视频

这是根本问题。OP,明智地,想尝试隔离它的点,在某种意义上“出现在屏幕上”。问题是这可能意味着很多事情:

当我第一次听到这个问题时,我认为一个很好的案例是onAttachedToWindow- 查看文档。对于根据原始标题阅读此问题的人来说,这就是您想要的。

大多数情况下,视图会在 Activity 的 onCreate 中膨胀并创建(例如,如果您使用了 setContentView)。

OP 对 surfaceCreated 回调也没有运气。因此,我们在上面的评论中考虑了 OP 是否会对三个抽签阶段感兴趣layoutmeasure并且draw。在 android 中实际“在屏幕上放置视图”有两个阶段 - 测量和布局通道 - 请参见此处

问题是,原来 OP 正在将他的视图动画到屏幕上,所以问题变成了如何判断动画后视图何时“到达”屏幕上。

重要的一点是:您实际上想在绘图过程中检测到更晚的阶段,这是可以理解的!动画通过许多调用来工作,而这些调用invalidate又需要许多draws 用于该视图Canvas- 所以您想要播放视频的阶段绝不是视图首次显示在 UI 中的时候。

这种特殊情况的解决方案

在您的实例上使用动画侦听ViewAnimator器(例如ViewPager)。为了不必在活动中打扰它们,我会推出你自己的视图,然后使用AdapterAndroid 非常喜欢的类型模式来管理不断变化的数据:

一个非常仓促的实现将是:

public class VideoStartingViewFliper extends ViewFlipper {
private final Animation fromRight;
private final Animation toLeft;
private final Animation fromLeft;
private final Animation toRight;
private VideoViewAdapter mAdapter;

public VideoStartingViewFliper(final Context context, final AttributeSet attrs) {
    super(context, attrs);
    fromRight = new YourChoiceOfAnimation();
    fromRight.setAnimationListener(videoStartingAnimationListener);

    toLeft = new YourChoiceOfAnimation();
    toLeft.setAnimationListener(videoStartingAnimationListener);

    fromLeft = new YourChoiceOfAnimation();
    fromLeft.setAnimationListener(videoStartingAnimationListener);

    toRight = new YourChoiceOfAnimation();
    toRight.setAnimationListener(videoStartingAnimationListener);
}

static interface VideoViewAdapter {

    public String getVideoPath(int childId);

}

public void setVideoViewAdapter(final VideoViewAdapter adapter) {
    mAdapter = adapter;
}

// or even call this showNextVideo and don't override!
@Override
public void showNext() {
    setInAnimation(fromRight);
    setOutAnimation(toLeft);
    super.showNext();
}

@Override
public void showPrevious() {
    setInAnimation(fromLeft);
    setOutAnimation(toRight);
    super.showPrevious();

}

private final AnimationListener videoStartingAnimationListener = new AnimationListener() {

    @Override
    public void onAnimationStart(final Animation animation) {
        final VideoView video = ((VideoView) getCurrentView());
        video.stopPlayback();
    }

    @Override
    public void onAnimationRepeat(final Animation animation) {

    }

    @Override
    public void onAnimationEnd(final Animation animation) {
        final VideoView video = ((VideoView) getCurrentView());
        // check null here!
        video.setVideoPath(mAdapter.getVideoPath(getCurrentView().getId()));
        video.start();
    }
};
}

希望这可以帮助。

于 2013-07-24T17:57:00.700 回答