Android-뷰에 동적으로 뷰 추가


148

뷰 레이아웃이 있습니다-

<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:padding="0px"
    android:orientation="vertical">

    <TextView
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:id="@+id/items_header"
        style="@style/Home.ListHeader" />

    <TextView 
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:id="@+id/items_none"
        android:visibility="gone"
        style="@style/TextBlock"
        android:paddingLeft="6px" />

    <ListView 
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:id="@+id/items_list" />


</LinearLayout>

내가하고 싶은 것은 다음과 같은 레이아웃이있는 주요 활동입니다.

<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:padding="0px"
    android:id="@+id/item_wrapper">
</LinearLayout>

내 데이터 모델을 반복하고 첫 번째 레이아웃으로 구성된 여러보기를 기본 레이아웃에 삽입하고 싶습니다. 코드 내에서 컨트롤을 완전히 작성 하여이 작업을 수행 할 수 있다는 것을 알고 있지만 모든 것을 코드에 넣지 않고 레이아웃을 계속 사용할 수 있도록 뷰를 동적으로 빌드하는 방법이 있는지 궁금합니다.


답변:


230

를 사용 LayoutInflater하여 레이아웃 템플릿을 기반으로 뷰를 생성 한 다음 필요한 뷰에 주입합니다.

LayoutInflater vi = (LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View v = vi.inflate(R.layout.your_layout, null);

// fill in any details dynamically here
TextView textView = (TextView) v.findViewById(R.id.a_text_view);
textView.setText("your text");

// insert into main view
ViewGroup insertPoint = (ViewGroup) findViewById(R.id.insert_point);
insertPoint.addView(v, 0, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.FILL_PARENT, ViewGroup.LayoutParams.FILL_PARENT));

뷰를 삽입 할 인덱스를 조정해야 할 수도 있습니다.

또한 LayoutParams를 부모보기에 맞추는 방법에 따라 LayoutParams를 설정하십시오. 예를 들어 FILL_PARENT, 또는 MATCH_PARENT등으로


2
동적으로 생성 된 레이아웃을 기본보기에 배치하려는 위치입니다. 그것은 당신이 당신의 코드에서 채워야 할 비트입니다.
마크 피셔

지금 시도해보고 싶은 사람들을 위해 – 첫 번째 줄에서 보여지는 것과 같은 레이아웃 팽창기는 여전히 해결되지만 작동하지 않는 것 같습니다getLayoutInflater()
Brendan

2
LayoutInflater vi = getLayoutInflater();다른 방법으로는 얻을 수없는 활동 테마를 유지하기 위해 활동에서 사용하십시오 .
akarthik10

1
@MrG SO에 대해 별도의 질문을 제기해야합니다. 이 질문은 프래그먼트가 아니라 동적으로 뷰를 생성하는 방법에 관한 것입니다.
Mark Fisher

2
@Arsh 새로운 질문과 특정 문제가 있으면 여기에 주석 대신에 작동하지 않는 코드를 자세히 설명하는 별도의 SO 질문을 제기하십시오.
Mark Fisher

36

LayoutInflater수업을 참조하십시오 .

LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
ViewGroup parent = (ViewGroup)findViewById(R.id.where_you_want_to_insert);
inflater.inflate(R.layout.the_child_view, parent);

내가 클릭 한 개인 조회수에 onClicklistener를 추가하는 방법 스 니펫을 입력하십시오
Sagar Devanga

20

지정된 레이아웃을 부풀리기 위해 사용자 정의 어댑터가있는 ListView가 실제로 원하는 것처럼 보입니다. ArrayAdapter 및 메소드 notifyDataSetChanged()를 사용하면 뷰 생성 및 렌더링을 완전히 제어 할 수 있습니다.

이 튜토리얼을 살펴보십시오


14

@Mark Fisher의 대답을보다 명확하게하기 위해 삽입 된보기는 레이아웃 폴더 아래에 xml 파일이어야하지만 LinearLayout 등과 같은 레이아웃 (ViewGroup)이 없어야합니다. 내 예 :

res / layout / my_view.xml

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/i_am_id"
    android:text="my name"
    android:textSize="17sp"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_weight="1"/>

그런 다음 삽입 지점은 LinearLayout과 같은 레이아웃이어야합니다.

res / layout / activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/aaa"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <LinearLayout
        android:id="@+id/insert_point"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

    </LinearLayout>

</RelativeLayout>

그런 다음 코드는

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_shopping_cart);

    LayoutInflater inflater = getLayoutInflater();
    View view = inflater.inflate(R.layout.my_view, null);
    ViewGroup main = (ViewGroup) findViewById(R.id.insert_point);
    main.addView(view, 0);
}

이 매우 유사한 답변을 게시하는 이유는 Mark의 솔루션을 구현하려고 할 때 insert_point 및 자식보기에 사용해야하는 xml 파일에 붙어 있기 때문입니다. 먼저 자식보기에서 레이아웃을 사용했는데 완전히 작동하지 않아서 알아내는 데 몇 시간이 걸렸습니다. 내 탐사가 다른 사람들의 시간을 절약 할 수 있기를 바랍니다.


@York Yang for 루프를 사용하여 둘 이상의 뷰를 추가하면 여기에 ID의 vis를 어떻게 추가 할 수 있습니까?
Rahul Kushwaha

5
// Parent layout
LinearLayout parentLayout = (LinearLayout)findViewById(R.id.layout);

// Layout inflater
LayoutInflater layoutInflater = getLayoutInflater();
View view;

for (int i = 1; i < 101; i++){
    // Add the text layout to the parent layout
    view = layoutInflater.inflate(R.layout.text_layout, parentLayout, false);

    // In order to get the view we have to use the new view with text_layout in it
    TextView textView = (TextView)view.findViewById(R.id.text);
    textView.setText("Row " + i);

    // Add the text view to the parent layout
    parentLayout.addView(textView);
}

1
이 코드 스 니펫이 해결책이 될 수 있지만 설명을 포함하면 게시물의 품질을 향상시키는 데 실제로 도움이됩니다. 앞으로 독자들에게 질문에 대한 답변을 제공하므로 해당 사람들이 코드 제안의 이유를 모를 수도 있습니다.
yivi

For 루프를 사용하여 만든 다른 뷰의 ID를 얻는 방법은 무엇입니까?
Rahul Kushwaha
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.