转换类异常:LinearLayout布局参数

10

我有一个Actionbar和一些Fragment。问题在于我的主屏幕上,左边有一个概述Fragment,右边有一个详细信息Fragment。我的TabListener是动态的,所以我想通过编程方式设置布局的权重。但当我尝试获取LinearLayout的Layoutparams时,我遇到了ClassCastException的问题:

12-22 16:00:37.620: W/System.err(7235): java.lang.ClassCastException: android.widget.FrameLayout$LayoutParams cannot be cast to android.widget.LinearLayout$LayoutParams
12-22 16:00:37.625: W/System.err(7235):     at com.coover.eu.lostandfound.ListSearchFragment.onViewCreated(ListSearchFragment.java:184)
12-22 16:00:37.625: W/System.err(7235):     at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:884)
12-22 16:00:37.630: W/System.err(7235):     at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1080)
12-22 16:00:37.630: W/System.err(7235):     at android.support.v4.app.BackStackRecord.run(BackStackRecord.java:622)
12-22 16:00:37.630: W/System.err(7235):     at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1416)
12-22 16:00:37.630: W/System.err(7235):     at android.support.v4.app.FragmentActivity.onStart(FragmentActivity.java:505)
12-22 16:00:37.630: W/System.err(7235):     at android.app.Instrumentation.callActivityOnStart(Instrumentation.java:1178)
12-22 16:00:37.635: W/System.err(7235):     at android.app.Activity.performStart(Activity.java:5216)
12-22 16:00:37.635: W/System.err(7235):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2083)
12-22 16:00:37.635: W/System.err(7235):     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2135)
12-22 16:00:37.635: W/System.err(7235):     at android.app.ActivityThread.access$700(ActivityThread.java:140)
12-22 16:00:37.635: W/System.err(7235):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1237)
12-22 16:00:37.640: W/System.err(7235):     at android.os.Handler.dispatchMessage(Handler.java:99)
12-22 16:00:37.640: W/System.err(7235):     at android.os.Looper.loop(Looper.java:137)
12-22 16:00:37.640: W/System.err(7235):     at android.app.ActivityThread.main(ActivityThread.java:4921)
12-22 16:00:37.640: W/System.err(7235):     at java.lang.reflect.Method.invokeNative(Native Method)
12-22 16:00:37.640: W/System.err(7235):     at java.lang.reflect.Method.invoke(Method.java:511)
12-22 16:00:37.645: W/System.err(7235):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1038)
12-22 16:00:37.645: W/System.err(7235):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:805)
12-22 16:00:37.645: W/System.err(7235):     at dalvik.system.NativeStart.main(Native Method)
被填充的布局:

The Layout that is inflated:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" 
    android:id="@+id/container_found_list_overview">

    <EditText android:id="@+id/search_box" 
        android:layout_width="fill_parent"
        android:layout_height="50dp"
        android:padding="5dp"
        android:textSize="35sp"
        android:hint="@string/search"
        android:inputType="text"
        android:maxLines="1"/>
    <ListView 
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/overview_list_view">
    </ListView>

</LinearLayout> 

代码:


            LinearLayout myView = (LinearLayout)this.getView().findViewById(R.id.container_found_list_overview);
            Log.d("found container", ""+(myView != null));
            try{
                LayoutParams lp = (LayoutParams) myView.getLayoutParams();
                lp.weight = 1;
                lp.width = 0;
                myView.setLayoutParams(lp);
            }
            catch(RuntimeException e){
                Log.e("cant get layoutparams",e.getMessage());
                e.printStackTrace();
            }

3个回答

32

正在发生的是视图的 LayoutParams 实际上是其 父级 类型。在这种情况下,您获得了一个 FrameLayout$LayoutParams,因为您的 LinearLayout 在 FrameLayout 内部。

为什么是它的父类型?这是因为它们存储对于父级布局很有用的信息。如果您检索 EditText 或 ListView 的布局参数,则会获取 LinearLayout$LayoutParams


非常感谢,现在它可以正常工作了。我使用了layout_gravity而不是layout_weight,并动态更改了宽度。 - Ceryni
啊,好的,谢谢你的建议。这是我在stackoverflow上的第一个问题。 - Ceryni
那么,正确的解决方案是什么呢?例如,如果我想要为相对布局中嵌套的线性布局添加顶部间距,应该怎么做? - halxinate
ن½ ه؛”该ن½؟用RelativeLayout.LayoutParamsم€‚و‌¥و؛گ - dmon

1

异常明确指出您正在尝试将 FrameLayout 强制转换为 LinearLayout。这发生在 ListSearchFragment.java 文件的 onViewCreated() 方法中,第 184 行。因此,请替换为以下内容:

LayoutParams lp = (LayoutParams) myView.getLayoutParams();

使用这个:

LinearLayout.LayoutParams lp = 
                  (LinearLayout.LayoutParams) myView.getLayoutParams();

在你这样做之前,你可以把鼠标悬停在你当前代码中的 LayoutParams 上,看看气泡中显示的实际上是 android.widget.RelativeLayout.LayoutParams,这就是你出现异常的原因。具体见下:

enter image description here


这不起作用。完全相同的异常。看着上面接受的答案-根本不可能。我很愿意知道我错了。 - halxinate

0

这个异常发生的另一个原因(或者说是bug)是:

如果视图的ID也被用于另一个布局中,那么它将尝试为两个布局中使用的父视图强制转换LayoutParams。

解决方案:不要在不同的布局中使用相同的id :)


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接