1

I'm developing for Android API v11. There is a large RelativeLayout area (like a canvas) that should be filled with a number of buttons, programmatically. Each button represents a video, and I've extended the android.widget.Button class with my VideoViewButton.

Here's what I'm doing now in the main activity:

private void addButtonForVideo(int videoId) {
    Log.d(TAG, "Adding button for video " + videoId);
    VideoButtonView button = new VideoButtonView(this, videoId);
    RelativeLayout layout = (RelativeLayout) findViewById(R.id.layout_napping);

    layout.addView(button, params);
    mVideoButtons.add(button);
}

Here, mVideoButtons just contains all buttons so I can reference them later.

The buttons themselves are however placed at the top left of the RelativeLayout, one over the other. What I need to do is place each button to the right of the previous one, so they fill up the screen.

I've tried this, where I check if the video ID is not 0 (meaning, a button already exists). I then get the ID of the previously placed button and say that I want the next button to be placed right of that previous one:

private void addButtonForVideo(int videoId) {
    Log.d(TAG, "Adding button for video " + videoId);
    VideoButtonView button = new VideoButtonView(this, videoId);
    RelativeLayout layout = (RelativeLayout) findViewById(R.id.layout_napping);

    RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(
            ViewGroup.LayoutParams.WRAP_CONTENT,
            ViewGroup.LayoutParams.WRAP_CONTENT
    );

    // align to right of previous button
    if (videoId != 0) {
        VideoButtonView previousButton = mVideoButtons.get(videoId - 1);
        params.addRule(RelativeLayout.RIGHT_OF, previousButton.getId());
    }

    layout.addView(button, params);
    mVideoButtons.add(button);
}

However, it's not working — the buttons are still placed on top of each other. How can I get them to show next to the previous one instead?

slhck
  • 36,575
  • 28
  • 148
  • 201
  • Can you show the constructor of the `VideoButtonView` where you call `setId`? And what is the type of `mVideoButtons`? – Rajesh Mar 06 '14 at 14:48
  • @Rajesh Gotcha, I never call `setId` in the constructor. Never occurred to me that this was necessary to do. Can you post that as an answer, please? – slhck Mar 06 '14 at 14:51

2 Answers2

1

You need to call setId with the videoId in the constructor of the VideoButtonView for this to work.

Make sure that setId contains a positive number, so for example if videoIds start with 0, use:

public VideoButtonView(Context context, int videoId) {
    super(context);
    this.setId(videoId + 1);
    // other code to set layout
}
slhck
  • 36,575
  • 28
  • 148
  • 201
Rajesh
  • 15,724
  • 7
  • 46
  • 95
  • It didn't work for me when taking `0` as an ID, but every positive number works here. I amended your answer to include that. Thanks for your help. – slhck Mar 06 '14 at 14:57
  • Yes, 0 is not a valid identifier. – Rajesh Mar 06 '14 at 14:57
0

I suggest not using the Relative Layout for placing object programmatically. Use Linear Layouts instead and organize the content using LinearLayout.LayoutParams

To do this with LinearLayout, just make sure you set the orientation to HORIZONTAL

private void addButtonForVideo(int videoId) {
Log.d(TAG, "Adding button for video " + videoId);
VideoButtonView button = new VideoButtonView(this, videoId);
LinearLayout layout = (LinearLayout) findViewById(R.id.layout_napping);

LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(
        LinearLayout.LayoutParams.MATCHPARENT,
        LinearLayout.LayoutParams.WRAP_CONTENT,
);

LinearLayout buttonWrapper = new LinearLayout();
buttonWrapper.setLayoutParams(params);
buttonWrapper.setOrientation(LinearLayout.HORIZONTAL);

// align to right of previous button
if (videoId != 0) {
    VideoButtonView previousButton = mVideoButtons.get(videoId - 1);
}

buttonWrapper.addView(button);
layout.addView(buttonWrapper);
mVideoButtons.add(button);

}

Just remember to place the first button in the ButtonWrapper before placing the second in there.

With a linear layout, the next child will either appear below, or next to the previous child depending on the direction and the orientation given for the layout. here, each button will sit next to each other and the wrapper will extend the full length of the layout it sits in.

Best of luck!

JRad the Bad
  • 511
  • 5
  • 25
  • This *might* work, but I know that for some reason I couldn't use a LinearLayout in this particular context. – slhck Mar 06 '14 at 15:06