Join us and get access to hundreds of tutorials and a community of expert Pythonistas.

Unlock This Lesson

This lesson is for members only. Join us and get access to hundreds of tutorials and a community of expert Pythonistas.

Unlock This Lesson

Hint: You can adjust the default video playback speed in your account settings.
Hint: You can set the default subtitles language in your account settings.
Sorry! Looks like there’s an issue with video playback 🙁 This might be due to a temporary outage or because of a configuration issue with your browser. Please see our video player troubleshooting guide to resolve the issue.

Creating a Multipage Stack Layout

00:00 So far, all the layouts that we have covered had one thing in common—that you always see all the widgets that are being placed on this layout. But sometimes, you don’t really want that to happen. For example, sometimes you only want to show a certain widget if the user clicks a button.

00:16 This is what we are going to cover in the next two videos with two slightly more advanced layout managers, and those are called QStackedLayout and QTabWidget.

00:26 And I think the name already implies what the two are doing, but let’s start for this video with QStackedLayout. A QStackedLayout puts different widgets on top of each other and only displays a single one at any given point in time.

00:40 Each of the widgets inside of the QStackedLayout is going to get an index. You can use this index to cycle between different widgets that you want to display. And that way, you could create different pages in your GUI, for example.

00:53 This is exactly what we are going to do in this video, where we have a widget, where it can select one page, and then only one single page is being shown.

01:01 Then inside of each page, you have a couple more widgets that are also being organized inside of a layout manager. So again, we have nested layouts. This one is becoming really important for more complex layouts.

01:13 But there’s one complication you should be aware of before we start coding—that we need a signal to make a QStackedLayout work. So if you have no idea what is signal is, I would refer you back to the PyQt learning path.

01:25 It is explained in quite a bit of detail in there. But besides that, let’s have a look at the code and let’s create all of this. So here, again, you can see the basic setup we have used so far, except now we are importing quite a few more different widgets.

01:41 And let me go through the really important ones. The first one is a QComboBox, and this one is essentially a dropdown menu that we can use to select different pages. Then the actual layout manager is QStackedLayout, and this one is going to put our different widgets on top of each other.

01:58 Inside of QStackedLayout, we have a couple of QWidgets that each have a QFormLayout. I suppose all of that is going to make much more sense when you actually implement it, so let’s go through this step-by-step. The first thing we have to do is to create the actual layout for our parent widget. So let’s call this # Create a top-level layout.

02:22 This one is just going to be a basic QVBoxLayout. It doesn’t have to be anything specific. I’m going to create a new layout variable, and this one is just going to be QVBoxLayout()the same thing you have already seen multiple times. And straightaway, I’m going to set this as self.setLayout() and add in the layout. Now we have set the layout of this QWidget to just be a QVBoxLayout. Now, any widget we are going to add to this layout is going to be added in a vertical way. Now, next up, what I want to do is to create the combo box.

03:00 This is going to be the dropdown menu that we are going to use to select the different pages of our QStackedLayout. And for this, I want to add self.pageCombo.

03:13 Although the name doesn’t really matter, it is important that this combo page is part of the widget itself, not just of the .__init__() method—hence, I’m using self.

03:23 And this one is just supposed to be a QComboBox(), it doesn’t need any arguments, and now we have a QComboBox. And to this one, I want to add two items. So I select it again, .pageCombo, and now we have to .addItems().

03:39 And this is somewhat similar compared to the .addWidget() or .addLayout() that we have seen earlier. Instead, we just add a few entries to this dropdown menu, and this has to be a list. Inside of this list, we need a couple of strings. I just call them 'Page 1' and 'Page 2'. And they have to be separated by a comma, not a dot.

04:01 And just to get started, let me add this combo box to the actual parent layout, so this QVBoxLayout. And just to annotate all of this with comments, I want to add the combo box to the top-level layout.

04:22 And all I have to do in here is to get my layout again, and I want to add a widget, and this is going to be self.pageCombo. And now if I run this, this should already work and give us a basic dropdown menu. There we go!

04:37 We have Page 1 and Page 2. It doesn’t really do anything just yet, but we can take care of that in just a bit. Actually, let’s do it right now.

04:47 So what I want to do, if I set different pages, I want this combo box to send a signal. So let me add self.pageCombo, and the signal I want to use is called .activated.

05:03 This one is going to emit which item we have selected once we’re using the dropdown menu. I’m going to illustrate in a second what that means. And now to use the signal, you have to add .connect(), and now you have to add some kind of function. And in my case, I called this function .switchPage.

05:23 And this is a function—or rather, a method—that we are going to create further down here, so I want to create a new method that I call .switchPage(). And make sure for the argument, it always needs self because we are inside of a class.

05:37 And here’s one important thing for PyQt, that if you use a function inside of a signal, you don’t want to run the function yourself. Instead, you tell this signal that you want to run this function whenever this combo box is being activated.

05:53 So the only important thing you have to remember is that don’t add brackets when you use functions inside of a signal. Now inside of this .switchPage(), we want to run some kind of code. And later on, we are going to use this to activate the QStackedLayout, but for now, let me just print what is going to happen.

06:10 And really all I want to print is self.pageCombo and then the .currentIndex. And a really important part here is that you need brackets after this, because this is a method. But now, let’s actually run this and see what happens.

06:26 So by default, nothing happens. But let me switch to Page 2, and now we get the index 1. And if I switch back to Page 1, we get the index of 0. So all that this function does—let me close all of this—is that whenever we run this signal, we are running this method here.

06:46 And what this method does is it returns the index I have for 'Page 1', which is 0, or for 'Page 2', which is the index 1.

06:55 And this index we can use to switch between the different stacks on the QStackedLayout. So, let’s create that one actually. But before that, I want to change the comment just to be clear what we’re doing.

07:08 So besides creating the combo box, I also want to connect the combo box and I am doing all of this to switch between pages. So now let me add a bit of space below our combo box, and now we can actually create our stacked layout.

07:26 So I want to create the stacked layout. And then here, again, I want self and I want .stackedLayout(). This is just going to be a variable in which I am going to store my stacked layout. And, well, this works like all the other layouts we have seen before. This is just QStackedLayout.

07:46 So now we have a QStackedLayout that we can add widgets to, and that comes on the next line. And let me add comments here—this might otherwise get quite confusing.

07:56 I want to create the first page, and let’s store this one in a variable that I’m going to call self.page1. And this one, all you need is a QWidget(), so an empty widget that you can put stuff inside. And this widget itself is also going to need a layout, so let’s give it one as well.

08:17 And let’s call this self.page1Layout.

08:22 And for both of them, all you need is a QFormLayout(), so a fairly simple layout. And now, too, there’s .page1Layout. All you have to do is to add a couple of rows with the information you want to add. And, of course, you could also use another kind of layout.

08:39 It’s really up to you.

08:41 And in here, 'Name: ' and QLineEdit().

08:46 It should be a fairly straightforward approach. And let’s duplicate this row and change it to 'Address: '. We can keep the same widget. And a really important thing to not forget is to actually set this layout to be the layout of this QWidget. So what we need is self.page1, and you need .setLayout(), and in here it has to be self.page1Layout.

09:15 Let me talk through it real quick. We first create .page1 with a QWidget(), and then we create a .page1Layout. But by default, those two are not connected at all.

09:26 This only happens further down here, where we actually set this QFormLayout to be the layout for this QWidget. And then to what’s the layout, we are going to add these two rows. And we are almost done for this one widget.

09:38 All we need now is to get our self.stackedLayout and you need to add the widget that is going to be self.page1. Inside of this QWidget, we have all of this information, all of these widgets, and all of this is going to be added to the stacked layout.

09:59 And this would be our first page! So this would be one page, but just having one page feels kind of pointless. So instead what you can do is copy all of this and paste it right below, and we can call this # Create the second page.

10:16 And now all you have to do is replace .page1 with .page2 all over the place, and update this information depending on what you need.

10:28 Let’s say, in this case, this is going to be 'Job: ' and 'Department: ', and at the end, you want to add .page2, not .page1.

10:36 And with that, you have two pages for your layout. This is already getting quite complex. I hope you can still follow. But okay, now what we have to do is to actually add this QStackedLayout to our main widget.

10:52 So what we need to do is get the layout and .addLayout().

10:58 And just to mention it, it is perfectly fine to first add a widget and then a layout. That is no problem at all for PyQt. And what I want to add is self.stackedLayout.

11:10 And now let’s see what happens! Now we have our QComboBox and we have our widget below, and this one is Page 1. Now the problem is we can’t switch between them, because we didn’t add the proper code down here. And now, I don’t want to print the information of what the current index of the combo box is. Instead, I want to use it to influence the stacked layout.

11:35 So I first have to target our self.stackedLayout, and the method you need to make this work is called .setCurrentIndex(). This one just switches between the different pages, so index 0 would be page 1, index 1 would be page 2, and then you could add more and more pages to this. It’s quite a simple system, actually. And let’s add a space between all of this.

11:57 This makes it feel a bit better. Okay! Let’s try all of this! This is still working. I can write some random text in there. Now I can switch to Page 2, and now we can see Job and Department, because we switched to another stack in the QStackedLayout.

12:14 And now we can still add stuff in here. Let me just add random things. And if I went back to Page 1, our information would still be in there. And that way, you could have different pages on your PyQt GUI. And, well, it does look slightly complex, but once you practice this a couple of times, this is actually quite a straightforward system. Now, if you’re struggling with these concepts, this is probably a good lesson to go through again. But in the next lesson, we’re going to look at another way to create a single-page layout.

12:44 This one is going to work with tabs. I will see you then!

Become a Member to join the conversation.