如何在android中动态设置布局

IT小君   2021-10-27T02:32:40

好吧,假设有一个名为MainActivity的 Activity,并且有两个名为layout1layout2 的布局它们都有几个按钮。默认情况下MainActivity布局是layout1,如下所示:

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.layout1);

现在我实际上是通过单击layout1 中一个按钮,第二个布局设置如下:

    someBtn1.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            setContentView(R.layout.layout2);
        }
    });

layout2 中有另一个按钮可以返回到layout1,如下所示:

    someBtn2.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            setContentView(R.layout.layout1);
        }
    });

问题是当我回到layout1然后 someBtn1 的OnClickListener不起作用。看来我需要再次设置OnClickListener someBtn1布局1我如何编写代码以使它们与最佳实践完美配合?

点击广告,支持我们为你提供更好的服务
评论(5)
IT小君

最佳实践是使用片段而不是更改内容视图。

在您的代码中,带有布局的 setContentView 每次都会重新创建(膨胀)所有视图,因此在 someBtn2 单击侦听器中调用 setContentView(R.layout.layout1) 将创建一个没有关联侦听器的新按钮。

如果你不想使用片段,你可以这样做:

private View view1, view2;

public void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  view1 = getLayoutInflater().inflate(R.layout.layout1, null);
  view2 = getLayoutInflater().inflate(R.layout.layout2, null);
  setContentView(view1);

听众将是:

someBtn1.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
        setContentView(view2);
    }
});


someBtn2.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
        setContentView(view1);
    }
});
2021-10-27T02:32:40   回复
IT小君

如果您只想使用当前代码,那么解决您的问题的方法是在布局更改时必须重新声明侦听器,如下所示:

someBtn1.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
        setContentView(R.layout.layout2);

        someBtn2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                setContentView(R.layout.layout1);
            }
        });
    }
});

someBtn2.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View view) {
        setContentView(R.layout.layout1);

        someBtn1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                setContentView(R.layout.layout2);
            }
        });
    }
});

避免两次声明侦听器的另一种方法是声明两种方法来处理布局更改并onClick在每个布局中使用按钮属性,例如:

public void setLayout1(View view) {
    setContentView(R.layout.layout1);
}

public void setLayout2(View view) {
    setContentView(R.layout.layout2);
}

layout1.xml

<Button
    android:id="@+id/someBtn1"
    android:onClick="setLayout2"/>

layout2.xml

<Button
    android:id="@+id/someBtn2"
    android:onClick="setLayout1"/>

但是,如果您想遵循最佳实践,最佳实践不是在同一个活动中混合布局,而是声明两个不同的活动(每个活动都有自己的布局)并根据按钮调用一个或另一个活动点击。假设你在Activity1,想调用Activity2,然后回到Activity1:

Activity1.java

someBtn1.setOnClickListener(new View.OnClickListener() {
     @Override
     public void onClick(View view) {
         startActivity(new Intent(this, Activity2.class));
     }
 });

Activity2.java

someBtn2.setOnClickListener(new View.OnClickListener() {
     @Override
     public void onClick(View view) {
         finish();
     }
 });
2021-10-27T02:32:40   回复
IT小君

一种方法是在 中加载两个视图onCreate(...),然后通过使您不希望的视图不可见来在它们之间切换。类似于以下内容:

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    inflater = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    LayoutParams default_layout_params = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
    View view1 = inflater.inflate(R.layout.layout1, null);
    addContentView(view1, default_layout_params);           
    View view2 = inflater.inflate(R.layout.layout2, null);
    addContentView(view2, default_layout_params);
    view2.setVisibility(View.INVISIBLE);
    view1.setVisibility(View.VISIBLE);
    view1.bringToFront();
2021-10-27T02:32:41   回复
IT小君

在您回调 layout1 时,必须再次设置数据。

您可以将两个布局合并为一个,然后使用 ViewFlipper 在它们之间切换。

2021-10-27T02:32:41   回复
IT小君

当您设置 layout2 时,您还应该将 OnClickListener 设置为 someBtn1,反之亦然,我建议您这样做。但正如之前的答案一样,通常您应该避免以这种方式混合布局。

public class MainActivity extends Activity {

    private final View.OnClickListener setLayout1Listener = new View.OnClickListener() {
        @Override
        public void onClick(View view) {
           setContentView(R.layout.layout2);
           ((Button)findViewById(R.id.Btn2Id)).setOnClickListener(setLayout2Listener);
           //do other stuff
        }
    };

    private final View.OnClickListener setLayout2Listener = new View.OnClickListener() {
        @Override
        public void onClick(View view) {
           setContentView(R.layout.layout1);
           ((Button)findViewById(R.id.Btn1Id)).setOnClickListener(setLayout1Listener);
           //do other stuff
        }
    };



    @Override
    public void onCreate(final Bundle savedInstance) {

        super.onCreate(savedInstanceState);
        setContentView(R.layout.layout1);
        ((Button)findViewById(R.id.Btn1Id)).setOnClickListener(setLayout1Listener);
        //do other stuff
    }
}
2021-10-27T02:32:41   回复