I've been trying to move my code across to the DrawerLayout
as suggested by android here as SlidingDrawer
is deprecated.
My problem is that so far DrawerLayout
seems to be either very badly implemented, has unhelpful error messages (no defensive programming) and/or isn't explained well enough in the documentation.
the isDrawerOpen()
method is described here:
public boolean isDrawerOpen (View drawer)
Check if the given drawer view is currently in an open state. To be considered "open" the drawer must have settled into its fully visible state. To check for partial visibility use isDrawerVisible(android.view.View).
Parameters: drawer - Drawer view to check
Returns: true if the given drawer view is in an open state
Each of the methods isDrawerOpen(View drawer)
, openDrawer(View drawer)
and closeDrawer(View drawer)
don't work when passed: The DrawerLayout
in question or either of it's children. I have no idea what I'm supposed to feed into these methods to allow them to function. Can someone let me know?
See below for entire problem description with implementation.
I have a layout like so:
<android.support.v4.widget.DrawerLayout
android:id="@+id/mainmenuPanel"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<FrameLayout
android:id="@+id/dualPane"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<FrameLayout
android:id="@+id/menuPane"
android:layout_width="300dp"
android:layout_height="match_parent" />
</android.support.v4.widget.DrawerLayout>
And in my code I have the following method hooked up to a button:
protected void onCreate(Bundle savedInstanceState) {
...
mMenuPanel = (DrawerLayout) findViewById(R.id.mainmenuPanel);
....
}
public boolean isDrawerOpen() {
if(mMenuPanel != null) {
return mMenuPanel.isDrawerOpen(mMenuPanel);
}
return false;
}
However if you give it itself as an argument (which would be redundant in the extreme) you get the following error:
E/AndroidRuntime(11241): java.lang.ClassCastException:
android.widget.FrameLayout$LayoutParams cannot be cast to
android.support.v4.widget.DrawerLayout$LayoutParams
(Which as you'll notice, doesn't give you any information about what you did wrong. It is instead a symtom of the problem).
Other answers here or here are either incomprehensible or very closely tied to the question without much explanation. Even so I've tried adding a faux LinearLayout
or one the DrawerLayout
s children and each give this error:
E/AndroidRuntime(11424): java.lang.IllegalArgumentException:
View android.widget.FrameLayout{420f5ea8 V.E..... ........
0,0-800,1172 #7f060038 app:id/menuPane} is not a drawer
Can anyone explain what these methods actually need to have passed to them to work?
And, the answer:
The second child (aka, the "Drawer") is what needs to be passed to the methods. My problem was that by the time I had figured that out I'd reduced the layout to as simple as possible implementation to test - I'd removed the gravity from the "drawer". Without a gravity, you get the above completely unrelated error messages.
I can confirm I got the code to work using the following setup:
mMenuPanel.isDrawerOpen(findViewById(R.id.drawer));
and with the layout:
<android.support.v4.widget.DrawerLayout
android:id="@+id/mainmenuPanel"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<FrameLayout
android:id="@+id/content"
android:layout_width="match_parent"
android:layout_height="match_parent" />
<FrameLayout
android:id="@+id/drawer"
android:layout_width="300dp"
android:layout_height="match_parent"
android:layout_gravity="start"/> <!-- This line was the problem!!!!!!!-->
</android.support.v4.widget.DrawerLayout>
if you want to avoid references to views or layouts in order to call isDrawerOpen, another way can be applied.
In this case you have to indicate the Gravity:
mDrawerLayout.isDrawerOpen(Gravity.START);
Being mDrawerLayout a reference to your DrawerLayout.
as you said, don't forget android:layout_gravity="start"
In your Activity if you have a reference to the DrawerLayout and in this case the FrameLayout with the id R.id.menuPane you can also do...
DrawerLayout mMenuPanel = (DrawerLayout) findViewById(R.id.mainmenuPanel);
FrameLayout mMenuPane = (FrameLayout) findViewById(R.id.menuPane);
mMenuPanel.isDrawerOpen(mMenuPane);
Basically you have to pass in a reference to the view being used as the drawer within the DrawerLayout, which will always be mMenuPanel.getChildAt(1) anyways.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With