~baltix/+junk/irrlicht-test

« back to all changes in this revision

Viewing changes to examples/18.SplitScreen/main.cpp

  • Committer: Mantas Kriaučiūnas
  • Date: 2011-07-18 13:06:25 UTC
  • Revision ID: mantas@akl.lt-20110718130625-c5pvifp61e7kj1ol
Included whole irrlicht SVN libraries to work around launchpad recipe issue with quilt, see https://answers.launchpad.net/launchpad/+question/165193

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/** Example 018 Splitscreen
 
2
 
 
3
A tutorial by Max Winkel.
 
4
 
 
5
In this tutorial we'll learn how to use splitscreen (e.g. for racing-games)
 
6
with Irrlicht. We'll create a viewport divided
 
7
into 4 parts, wtih 3 fixed cameras and one user-controlled.
 
8
 
 
9
Ok, let's start with the headers (I think there's
 
10
nothing to say about it)
 
11
*/
 
12
 
 
13
#include <irrlicht.h>
 
14
#include "driverChoice.h"
 
15
 
 
16
#ifdef _MSC_VER
 
17
#pragma comment(lib, "Irrlicht.lib")
 
18
#endif
 
19
 
 
20
//Namespaces for the engine
 
21
using namespace irr;
 
22
using namespace core;
 
23
using namespace video;
 
24
using namespace scene;
 
25
 
 
26
/*
 
27
Now we'll define the resolution in a constant for use in
 
28
initializing the device and setting up the viewport. In addition
 
29
we set up a global variable saying splitscreen is active or not.
 
30
*/
 
31
//Resolution
 
32
const int ResX=800;
 
33
const int ResY=600;
 
34
const bool fullScreen=false;
 
35
 
 
36
//Use SplitScreen?
 
37
bool SplitScreen=true;
 
38
 
 
39
/*
 
40
Now we need four pointers to our cameras which are created later:
 
41
*/
 
42
//cameras
 
43
ICameraSceneNode *camera[4]={0,0,0,0};
 
44
/*
 
45
In our event-receiver we switch the SplitScreen-variable,
 
46
whenever the user press the S-key. All other events are sent
 
47
to the FPS camera.
 
48
*/
 
49
 
 
50
class MyEventReceiver : public IEventReceiver
 
51
{
 
52
        public:
 
53
                virtual bool OnEvent(const SEvent& event)
 
54
                {
 
55
                        //Key S enables/disables SplitScreen
 
56
                        if (event.EventType == irr::EET_KEY_INPUT_EVENT &&
 
57
                                event.KeyInput.Key == KEY_KEY_S && event.KeyInput.PressedDown)
 
58
                        {
 
59
                                SplitScreen = !SplitScreen;
 
60
                                return true;
 
61
                        }
 
62
                        //Send all other events to camera4
 
63
                        if (camera[3])
 
64
                                return camera[3]->OnEvent(event);
 
65
                        return false;
 
66
                }
 
67
};
 
68
 
 
69
/*
 
70
Ok, now the main-function:
 
71
First, we initialize the device, get the SourceManager and
 
72
VideoDriver, load an animated mesh from .md2 and a map from
 
73
.pk3. Because that's old stuff, I won't explain every step.
 
74
Just take care of the maps position.
 
75
*/
 
76
int main()
 
77
{
 
78
        // ask user for driver
 
79
        video::E_DRIVER_TYPE driverType=driverChoiceConsole();
 
80
        if (driverType==video::EDT_COUNT)
 
81
                return 1;
 
82
 
 
83
        //Instance of the EventReceiver
 
84
        MyEventReceiver receiver;
 
85
 
 
86
        //Initialise the engine
 
87
        IrrlichtDevice *device = createDevice(driverType,
 
88
                        dimension2du(ResX,ResY), 32, fullScreen,
 
89
                        false, false, &receiver);
 
90
        if (!device)
 
91
                return 1;
 
92
 
 
93
        ISceneManager *smgr = device->getSceneManager();
 
94
        IVideoDriver *driver = device->getVideoDriver();
 
95
 
 
96
        //Load model
 
97
        IAnimatedMesh *model = smgr->getMesh("../../media/sydney.md2");
 
98
        if (!model)
 
99
                return 1;
 
100
        IAnimatedMeshSceneNode *model_node = smgr->addAnimatedMeshSceneNode(model);
 
101
        //Load texture
 
102
        if (model_node)
 
103
        {
 
104
                ITexture *texture = driver->getTexture("../../media/sydney.bmp");
 
105
                model_node->setMaterialTexture(0,texture);
 
106
                model_node->setMD2Animation(scene::EMAT_RUN);
 
107
                //Disable lighting (we've got no light)
 
108
                model_node->setMaterialFlag(EMF_LIGHTING,false);
 
109
        }
 
110
 
 
111
        //Load map
 
112
        device->getFileSystem()->addFileArchive("../../media/map-20kdm2.pk3");
 
113
        IAnimatedMesh *map = smgr->getMesh("20kdm2.bsp");
 
114
        if (map)
 
115
        {
 
116
                ISceneNode *map_node = smgr->addOctreeSceneNode(map->getMesh(0));
 
117
                //Set position
 
118
                map_node->setPosition(vector3df(-850,-220,-850));
 
119
        }
 
120
 
 
121
/*
 
122
Now we create our four cameras. One is looking at the model
 
123
from the front, one from the top and one from the side. In
 
124
addition there's a FPS-camera which can be controlled by the
 
125
user.
 
126
*/
 
127
        // Create 3 fixed and one user-controlled cameras
 
128
        //Front
 
129
        camera[0] = smgr->addCameraSceneNode(0, vector3df(50,0,0), vector3df(0,0,0));
 
130
        //Top
 
131
        camera[1] = smgr->addCameraSceneNode(0, vector3df(0,50,0), vector3df(0,0,0));
 
132
        //Left
 
133
        camera[2] = smgr->addCameraSceneNode(0, vector3df(0,0,50), vector3df(0,0,0));
 
134
        //User-controlled
 
135
        camera[3] = smgr->addCameraSceneNodeFPS();
 
136
        // don't start at sydney's position
 
137
        if (camera[3])
 
138
                camera[3]->setPosition(core::vector3df(-50,0,-50));
 
139
 
 
140
/*
 
141
Create a variable for counting the fps and hide the mouse:
 
142
*/
 
143
        //Hide mouse
 
144
        device->getCursorControl()->setVisible(false);
 
145
        //We want to count the fps
 
146
        int lastFPS = -1;
 
147
 
 
148
/*
 
149
There wasn't much new stuff - till now!
 
150
Only by defining four cameras, the game won't be splitscreen.
 
151
To do this you need several steps:
 
152
  - Set the viewport to the whole screen
 
153
  - Begin a new scene (Clear screen)
 
154
 
 
155
  - The following 3 steps are repeated for every viewport in the splitscreen
 
156
    - Set the viewport to the area you wish
 
157
    - Activate the camera which should be "linked" with the viewport
 
158
    - Render all objects
 
159
 
 
160
  - If you have a GUI:
 
161
    - Set the viewport the whole screen
 
162
    - Display the GUI
 
163
  - End scene
 
164
 
 
165
Sounds a little complicated, but you'll see it isn't:
 
166
*/
 
167
 
 
168
        while(device->run())
 
169
        {
 
170
                //Set the viewpoint to the whole screen and begin scene
 
171
                driver->setViewPort(rect<s32>(0,0,ResX,ResY));
 
172
                driver->beginScene(true,true,SColor(255,100,100,100));
 
173
                //If SplitScreen is used
 
174
                if (SplitScreen)
 
175
                {
 
176
                        //Activate camera1
 
177
                        smgr->setActiveCamera(camera[0]);
 
178
                        //Set viewpoint to the first quarter (left top)
 
179
                        driver->setViewPort(rect<s32>(0,0,ResX/2,ResY/2));
 
180
                        //Draw scene
 
181
                        smgr->drawAll();
 
182
                        //Activate camera2
 
183
                        smgr->setActiveCamera(camera[1]);
 
184
                        //Set viewpoint to the second quarter (right top)
 
185
                        driver->setViewPort(rect<s32>(ResX/2,0,ResX,ResY/2));
 
186
                        //Draw scene
 
187
                        smgr->drawAll();
 
188
                        //Activate camera3
 
189
                        smgr->setActiveCamera(camera[2]);
 
190
                        //Set viewpoint to the third quarter (left bottom)
 
191
                        driver->setViewPort(rect<s32>(0,ResY/2,ResX/2,ResY));
 
192
                        //Draw scene
 
193
                        smgr->drawAll();
 
194
                        //Set viewport the last quarter (right bottom)
 
195
                        driver->setViewPort(rect<s32>(ResX/2,ResY/2,ResX,ResY));
 
196
                }
 
197
                //Activate camera4
 
198
                smgr->setActiveCamera(camera[3]);
 
199
                //Draw scene
 
200
                smgr->drawAll();
 
201
                driver->endScene();
 
202
 
 
203
                /*
 
204
                As you can probably see, the image is rendered for every
 
205
                viewport seperately. That means, that you'll loose much performance.
 
206
                Ok, if you're aksing "How do I have to set the viewport
 
207
                to get this or that screen?", don't panic. It's really
 
208
                easy: In the rect-function you define 4 coordinates:
 
209
                - X-coordinate of the corner left top
 
210
                - Y-coordinate of the corner left top
 
211
                - X-coordinate of the corner right bottom
 
212
                - Y-coordinate of the corner right bottom
 
213
 
 
214
                That means, if you want to split the screen into 2 viewports
 
215
                you would give the following coordinates:
 
216
                - 1st viewport: 0,0,ResX/2,ResY
 
217
                - 2nd viewport: ResX/2,0,ResX,ResY
 
218
 
 
219
                If you didn't fully understand, just play arround with the example
 
220
                to check out what happens.
 
221
 
 
222
                Now we just view the current fps and shut down the engine,
 
223
                when the user wants to:
 
224
                */
 
225
                //Get and show fps
 
226
                if (driver->getFPS() != lastFPS)
 
227
                {
 
228
                        lastFPS = driver->getFPS();
 
229
                        core::stringw tmp = L"Irrlicht SplitScreen-Example (FPS: ";
 
230
                        tmp += lastFPS;
 
231
                        tmp += ")";
 
232
                        device->setWindowCaption(tmp.c_str());
 
233
                }
 
234
        }
 
235
        //Delete device
 
236
        device->drop();
 
237
        return 0;
 
238
}
 
239
/*
 
240
That's it! Just compile and play around with the program.
 
241
Note: With the S-Key you can switch between using splitscreen
 
242
and not.
 
243
**/
 
244