Skip to main content

Navigating with a Menu

Lesson 18 from: Building a Twitter App

Tony Hillerson

Navigating with a Menu

Lesson 18 from: Building a Twitter App

Tony Hillerson

buy this class

$00

$00
Sale Ends Soon!

starting under

$13/month*

Unlock this classplus 2200+ more >

Lesson Info

18. Navigating with a Menu

Next Lesson: Posting Tweets

Lesson Info

Navigating with a Menu

Now let's Ah, let the basic tasks stuff ferment a little bit in our minds, go onto a different topic. So let's talk about navigation. Um, in android navigation between multiple parts of of a more complex application we've been building so far is done with a menu. Um, so when you click, every every android device needs to have a menu button, and when you click that menu button, um, the activity gets notified and it's allowed to create a menu. Then you can see that our applications gonna have a very simple to to item menu for now, um, one allowing you to get to the home timeline and one allowing you to get to the post page, which we will create in a little bit. But for now, let's create the menu. So what we need to do for this for this step is to create the menu structure in an XML file and then, um, figure out whenever the user presses that menu button in all of our activities and then create the menu. So let me talk about something really quickly. Um, we're gonna be creating this post ...

activity in a little bit. It doesn't exist yet. We'll be making it in a little bit. Um, actually think it may exist, but we just We haven't done anything with the I just assumed that that thing is gonna be there when we need it. And that will be where the user can go to post new tweets. They can hit menu and go post, and then they will be able to post a tweet. And then once they post, um, taken, they can go back to the status list activity, I think will automatically return them there. But if they were on the post screen and they don't want toe, they want to check something else in the tweets. They can hit the menu button and and go back to the status list screen for their home. What we call home here, um, instead, so they can have navigate through the application that way. But one thing that we need to do every time that we show, um, one of these activities from the menu, we need to do it with an intent. Um, just like we've done in the past to create new, uh, activities from another activity like we do when you click a tweet to get the detail from the tweet like we did last week. Ah, you open up that new activity with an intent. But the problem is that the default way that you create activities using an intent doesn't take into account whether or not that activity is already running or a copy of the or an instance of that activity is already running. So let's let's go through this case here that we see on the screen on the left. Let's say the users navigated to the post activity from the status activity. So what happens is these activities air sort of like in history of the users navigation through the application like a deck of cards. And now the post activity is sitting on top of the status list activity which was already running, and then once they from the menu, if they were to click, um, home, that home button is going to be taking them to the status list activity from the post act activity. But what Androids going to do in the default case where we just start a new intent? Um, for that activity is creating new activity. So now we're gonna have to status list activities running, Um, which won't really bugged the user yet. They won't see that until they hit the Even when they hit the back button, that's just gonna do exactly what they expect. It's gonna go back from the new stats, last list activity to the previous post screen, and then they hit it again. It will go to status list activity, and that will be like that will be what they expect. But we'll have too much. We'll have memory consumed. We have resource is consumed by having to those sitting around. So we don't want to do it that way. We want to do, um we wanted to tell Android to open the new activity and a slightly different way that'll little minimize using system resource is, um So again, this is the standard way that the that the intent would work if we opened it up from the menu. Um, and this is what we will do instead. Ah, we will create the intent with a flag. And the flag is a type defined by android called flag activity. Clear top. So if you set that on an intent and you create an intent that opens a new activity from a class, and we'll look at the code for this interest. Second, um, then it will search through the history for all the instances of that activity that are still running that are already running, and it will bring that little, like cut the deck. It'll get rid of everything that's sitting on top of that one that's previous in history and move back to their so in this, just like in the previous case, if the user started out on the post activity, um, from the status list activity, then they click the home button on the menu when we which we will create in a second, um, which will take them to the status list activity. But instead we say flag activity clear top. Then the post activity will get popped off the stack of that menu of that history, and we'll just go back to the previously running status list activity. So, um, let's go into the code, and then we come back to the slides again to kind of make that make a little bit more sense. Um, so just keep that in mind. Let's go look at how the menu is constructed first, we kind of have a base for that. And then we'll go understand this navigation stuff. So what I've done here ah, and which he would do to create the contents of a menu are in resource is menu rez menu. You create a menu XML or whatever you want to name the file, but it needs to be in the menu directory. Inside. Resource is, you could have multiple menus to find in XML, but the way that you define them is with the menu tag your on line one and then inside the menu tag, you can have groups and then inside the group's you're gonna have items and each one of the groups need to have I ds and the items need to have ideas as well, just like they would inside of a view hierarchy. And then the items have, in addition to the idea that you have a title, which is in this case, we want home timeline. Ah, in a little bit, we'll create one with Post. So, um, that men you see if I can look at the layout it shows shows up here in this visual editor as Well, um, and you can see that you can add other items to that group and have other other things in there. So when I run this code, I see running as android application that we see that what we've defined in the menu is a home button. Once this application starts up, now I'll come back to the application as we know it. But when I press, once the tweets are loaded, once I press menu, then you can see that the menu opens up. Here is his home timeline, and that's how the menu works. You probably pretty experience with that already, um, using that either in the emulator or an actual device. So let's see how how the menu button pressing, actually. And actually ah, kicks all that off when we go to activities. Um, it's good a status list activity and see from there how the activity knows that the menu button was pressed. So we find in the code right place. I think I put this down on the bottom. Okay, so in status list activity inside, step for I've overridden a class called on Create Options Menu. This is the call back that an activity will get when the user presses the menu button and it will be passed an instance of a menu class and, um, that menu classes where we will put the menu options. So this is what's happening here is the menu brightness press. The menu menu is not actually created yet. We need to create the menu. So we're gonna get this something called a menu inflator, which is accessible through this getter. Get menu inflator, which is on an activity already. So we need to do is get that inflator. And then we need to inflate the menu from the the XML that we just looked at into eso a menu. Inflator has a has a a method called inflate, which takes a resource for that that has, like the menu tags and and stuff, and then the menu to inflate that resource into. And then we once that's all inflated into the menu. Then we just returned, true that, yes, we we were successfully able to create the menu. So this is this is the call back that happens when the menu button is pressed for the first time in the menu is not created yet, and So we go through the steps of creating the menu that we want to see on this activity. Then there's a second call back which will happen after this call back, or if the menu has already created it will happen. It will be the only one that will happen. So this create this menu isn't created every time. It's only created lazily on when it's actually needed. Um, this callback will happen when the user actually presses something on the menu. Um, and then in this case, so here. So here's a problem with Java. Everybody knows the job is a single inheritance language. I can't, um it's hard for me to define common menu creation code on the activity or common, like callback code. It would be nice if I had something like ruby modules or scholar mix ins here to be able to push all this stuff off into a class that I'll use on all my activities, because if in my act my application, I have the same menu on every activity, I still have to on every activity or a super class of the activity through this on create options menu stuff. But the problem is that often my super class is used up like here on the definition of status list activity. If I have a list activity, I can't use that super class. So I would have to make a super class that, um, of status list activity, that extended list activity. And if I had map activities that used a map activity super class, that I would have to make a super class for them and then if I just had plain old activities, then I would have toe have a super class there. So basically, you're kind of stuck with doing this this menu song and dance in a lot of different in all your activities, Which is kind of a pain if you have only one menu to show for all those activities. Um, but that's just kind of one of the limitations of Java. So you have to do this on create menu option or concrete options menu on every activity that you want a menu on. But luckily we can still use a little bit of, um so So I created this menu, help her class to actually do the work of when a menu button is pressed That's just something I created one sort of strategy to cut down on code duplication. And if I cover over this menu helper and hit F three, you'll see it's just a knob Jek to that has a static, static method that returns what I want. Um, so this is the code again that handles a a button press of the menu. And basically, what I do is ah, passing a context. You can see I passing this back here on status list activity and then I pass in the item that was clicked because basically what I want to do here is decide if I'm already on the activity that that the menu item points to that was just pressed. I don't want to do anything. So if I'm already on the post page and the user opens the menu and press, send me to the post page, um, I don't want to open a new post page. I wanna stay on the one that already on. So that's what all this code is designed to do. It's basically casts this class into something cast the class of the context. I'm passing into something that extends activity and then I get that class than I check to see if the classes in this case, a status list activity. If the menu item was pressed, um, for the home button on the men or the home home tweets or home statuses. Home timeline? I think I call it, yeah, Home timeline. So if this home timeline method is pressed and we're on the status less activity, I don't want to do anything because we're already there. But otherwise, if we're not there like if, as we'll see in a little bit, they they press a different menu item for the post screen, then, um then the requesting class will not be a status list. Activity will be a post activity. Um, so in that case, I can go ahead and open up the status list activity. So here's what I was talking about in the in the slides created intent, just like normal. I have to pass into context anyway, so it's a good thing I passed in this context. Then I pass in the class that I want to go to one advocate towards. That's all as normal. But then I do this intense set flags thing, and that will that basically says, I want to open this activity Android. But if the activity is already running, go back in the stack of all the activities that are open and use that one instead. Basically lop off any history after that, Um, so that will reuse that activity instead of starting a new one. And it's not like it's I mean, Android knows how to manage all those activities on that history stack. Really? Well, it'll close them down if it's using up. Too much resource is, um, but in this case, there may be some things about state that we don't want to, um, that we don't want to lose on where. We don't want to put on a different instance of the activity. So say I had some sort of home dashboard or something, and I use the menu to navigate to a new activity. And then I used the menu to navigate back to my dashboard. But it opens a new version, a new instance, and I make some change about that that shows me some different state that wasn't on the previous instance of that activity. And then I had back button twice. It will navigate away from that home dashboard back to some other view that was in the intermediate there. And then if I had a back button again, um, it will navigate away from that intermediate view back to the previous instance. Just like in this history here that was open, um, of the status list activity or this dashboard activity And that state, whatever I changed about that screen won't be there. So it'll be kind of confusing to the user like, Hey, I thought I just changed this thing. And it'll just because be because they're stale baited there, so we don't want to confuse the user. In that case, we want to use something like this. Flag activity. Clear top to make sure that we're always using one instance of whatever activity want to see. Okay, hopefully, that's all making sense. We have now, once we construct the menu, Um, the first time the menu button is pressed, then there will only be called that one time. Um And then once this button is pressed, this menu helper open activity from menu item will be called and will decide if we actually want to take any action at all based on the activity were clicking the button from. And then in this case, we're just gonna be opening up status list activity. So let me show you, um status, detail activity. If I go back to the emulator and I go click on one of these tweets, I go to the detail for this tweet. And if I had menu, the home timeline shows up there as well. So that means I have to back here in the code status detail activity down here in the bottom, I have to do this same many things. So it almost looks exactly the same on create options. Menu needs to create the menu from from the inflator if it's not already created. And then I'll use the menu helper in that case, too. So you can see this is where I cut down on some. They're gained some code we use. I didn't actually have the same code there. It's using that helper toe. Consolidate the code. Okay, so that's using menus. Is there any questions about what we look through there before we get onto posting? I don't have any questions. What Ruth does from the checkroom. I Tony, um just really quickly when using the flag activity. Clear top is the activity you start brought to the foreground by moving it to the stack or by stopping the other activities that are in the way. I mean those those activities may not be stopped right away, but that's that's kind of out of your hands. You know, you just rely on Android to do that. And but otherwise, basically, yes, what you said was true. Those activities air popped off the stack and we moved back towards the last running instance of whatever activity we were moving towards. And is the flag activity clear? Top? Is that the same as Android Launch mode? Equal single top in the android manifest dot xml? Does it accomplish the same thing? That's that's a good question. Let me think about I don't remember. I don't remember in detail what single top does I think it is. It is an indication to always keep that one on top. Is that what it is? I don't know. Let's let's move that into deformed because I don't I don't feel like I have the right answer to that. I mean, I don't know what the difference is off hand, but I think that the outcome may be the same, though. Okay, right. And other other intent flags that people should be aware of that they would use frequently related to managing that stack. I can't think of any off the top of my head. Let's go look at ah, this code and then see what other ones there are by doing this and eclipse, I'll just hit. Clear that code out. And then, um, I'm I got not getting any code completion here. Here we go. There we go. So there's a bunch. Okay, there's a bunch of flags for activities, especially. So, um, well, some of this stuff has to do with, um opening sort of other types of activities like, um, like this new task, one that that has to do with, um Actually, that wasn't what I thought it was. At first, there's there's a there's a bunch of there's definitely a bunch of them. I don't know if I can describe anyone of these that you use all the time, but here's a couple more. They have to do with the navigations flag. Single top. If set, the activity will not be launched if it is already running at the top of the history stack. But that's only if it's at the tops of this flag activity. Um, clear top. Ah, that's that will actually clear things off the stack and that that's actually want what we want to dio, um, this single top, which may be partial, partial, partially the answers of the previous question, which will not. They will not launch if it's already running at the top of the history stack. And then there's also something like reordered to front so that just reorders the tasks or reorders activities instead. Um, previous is top if said, and this intend is being used to launch a new activity from an existing one. The current activity will not be counted as the top activity for deciding whether the new activity should be delivered to the top instead of starting a new one. That's like gibberish. That's really confusing. So there's a lot of different options you have for dealing with just the navigation, um, through activities. But some of these air it's okay. So, like flag activity, new animation, let's say I do some task and I want a pop pop off to a previous activity or open a new one immediately. Instead of showing like this sliding in from the from the right animation or whatever animation you defined, you can say don't animate this time. Yeah, so that's something you could study on the on the side or we could talk about in the forms.

RELATED ARTICLES

RELATED ARTICLES