Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/trunk/src/core/input/InputBuffer.cc @ 2783

Last change on this file since 2783 was 2662, checked in by rgrieder, 16 years ago

Merged presentation branch back to trunk.

  • Property svn:eol-style set to native
File size: 7.3 KB
Line 
1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *                    > www.orxonox.net <
4 *
5 *
6 *   License notice:
7 *
8 *   This program is free software; you can redistribute it and/or
9 *   modify it under the terms of the GNU General Public License
10 *   as published by the Free Software Foundation; either version 2
11 *   of the License, or (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 *
22 *   Author:
23 *      Fabian 'x3n' Landau
24 *   Co-authors:
25 *      Reto Grieder
26 *
27 */
28
29#include "InputBuffer.h"
30
31#include <iostream>
32
33#include "util/Clipboard.h"
34#include "core/CoreIncludes.h"
35#include "core/ConfigValueIncludes.h"
36
37namespace orxonox
38{
39    InputBuffer::InputBuffer()
40    {
41        RegisterRootObject(InputBuffer);
42
43        this->buffer_ = "";
44        this->cursor_ = 0;
45        this->allowedChars_ = "abcdefghijklmnopqrstuvwxyz \
46                               ABCDEFGHIJKLMNOPQRSTUVWXYZ \
47                               äëïöüÄËÏÖÜáâàéêèíîìóôòúûù \
48                               0123456789 \
49                               \\\"(){}[]<>.:,;_-+*/=!?|$&%^~#";
50
51        this->lastKey_ = KeyCode::Unassigned;
52        this->timeSinceKeyPressed_ = 0.0f;
53        this->timeSinceKeyRepeated_ = 0.0f;
54        this->keysToRepeat_ = 0;
55
56        setConfigValues();
57    }
58
59    InputBuffer::InputBuffer(const std::string allowedChars)
60    {
61        RegisterRootObject(InputBuffer);
62
63        this->allowedChars_ = allowedChars;
64        this->buffer_ = "";
65        this->cursor_ = 0;
66
67        this->lastKey_ = KeyCode::Unassigned;
68        this->timeSinceKeyPressed_ = 0.0f;
69        this->timeSinceKeyRepeated_ = 0.0f;
70        this->keysToRepeat_ = 0;
71
72        setConfigValues();
73    }
74
75    InputBuffer::~InputBuffer()
76    {
77        for (std::list<BaseInputBufferListenerTuple*>::const_iterator it = this->listeners_.begin();
78            it != this->listeners_.end(); ++it)
79            delete *it;
80    }
81
82    void InputBuffer::setConfigValues()
83    {
84        SetConfigValue(keyRepeatDeleay_, 0.4).description("Key repeat deleay of the input buffer");
85        SetConfigValue(keyRepeatTime_, 0.022).description("Key repeat time of the input buffer");
86
87        if (keyRepeatDeleay_ < 0.0)
88        {
89            ResetConfigValue(keyRepeatDeleay_);
90        }
91        if (keyRepeatTime_ < 0.0)
92        {
93            ResetConfigValue(keyRepeatTime_);
94        }
95    }
96
97    void InputBuffer::set(const std::string& input, bool update)
98    {
99        this->clear(false);
100        this->insert(input, update);
101    }
102
103    void InputBuffer::insert(const std::string& input, bool update)
104    {
105        for (unsigned int i = 0; i < input.size(); ++i)
106        {
107            this->insert(input[i], false);
108
109            if (update)
110                this->updated(input[i], false);
111        }
112
113        if (update)
114            this->updated();
115    }
116
117    void InputBuffer::insert(const char& input, bool update)
118    {
119        if (this->charIsAllowed(input))
120        {
121            this->buffer_.insert(this->cursor_, 1, input);
122            ++this->cursor_;
123        }
124
125        if (update)
126            this->updated(input, true);
127    }
128
129    void InputBuffer::clear(bool update)
130    {
131        this->buffer_ = "";
132        this->cursor_ = 0;
133
134        if (update)
135            this->updated();
136    }
137
138    void InputBuffer::removeBehindCursor(bool update)
139    {
140        if (this->cursor_ > 0)
141        {
142            --this->cursor_;
143            this->buffer_.erase(this->cursor_, 1);
144
145            if (update)
146                this->updated();
147        }
148    }
149
150    void InputBuffer::removeAtCursor(bool update)
151    {
152        if (this->cursor_ < this->buffer_.size())
153        {
154            this->buffer_.erase(this->cursor_, 1);
155
156            if (update)
157                this->updated();
158        }
159    }
160
161    void InputBuffer::updated()
162    {
163        for (std::list<BaseInputBufferListenerTuple*>::iterator it = this->listeners_.begin(); it != this->listeners_.end(); ++it)
164        {
165            if ((*it)->bListenToAllChanges_)
166                (*it)->callFunction();
167        }
168    }
169
170    void InputBuffer::updated(const char& update, bool bSingleInput)
171    {
172        for (std::list<BaseInputBufferListenerTuple*>::iterator it = this->listeners_.begin(); it != this->listeners_.end(); ++it)
173        {
174            if ((!(*it)->trueKeyFalseChar_) && ((*it)->bListenToAllChanges_ || ((*it)->char_ == update)) && (!(*it)->bOnlySingleInput_ || bSingleInput))
175                (*it)->callFunction();
176        }
177    }
178
179    bool InputBuffer::charIsAllowed(const char& input)
180    {
181        if (this->allowedChars_ == "")
182            return true;
183        else
184            return (this->allowedChars_.find(input) != std::string::npos);
185    }
186
187
188    void InputBuffer::processKey(const KeyEvent &evt)
189    {
190        if (evt.isModifierDown(KeyboardModifier::Alt) && evt.key == KeyCode::Tab)
191            return;
192
193        for (std::list<BaseInputBufferListenerTuple*>::iterator it = this->listeners_.begin(); it != this->listeners_.end(); ++it)
194        {
195            if ((*it)->trueKeyFalseChar_ && ((*it)->key_ == evt.key))
196                (*it)->callFunction();
197        }
198
199        if (evt.isModifierDown(KeyboardModifier::Ctrl))
200        {
201            if (evt.key == KeyCode::V)
202                this->insert(fromClipboard());
203            else if (evt.key == KeyCode::C)
204                toClipboard(this->buffer_);
205            else if (evt.key == KeyCode::X)
206            {
207                toClipboard(this->buffer_);
208                this->clear();
209            }
210        }
211        else if (evt.isModifierDown(KeyboardModifier::Shift))
212        {
213            if (evt.key == KeyCode::Insert)
214                this->insert(fromClipboard());
215            else if (evt.key == KeyCode::Delete)
216            {
217                toClipboard(this->buffer_);
218                this->clear();
219            }
220        }
221
222        this->insert((char)evt.text);
223    }
224
225    /**
226        @brief This tick() function is called by the InputManager if the InputBuffer is active.
227        @param dt Delta time
228    */
229    void InputBuffer::tickInput(float dt)
230    {
231        timeSinceKeyPressed_ += dt;
232        if (keysToRepeat_ < 10 && timeSinceKeyPressed_ > keyRepeatDeleay_)
233        {
234            // initial time out has gone by, start repeating keys
235            while (timeSinceKeyPressed_ - timeSinceKeyRepeated_ > keyRepeatTime_)
236            {
237                timeSinceKeyRepeated_ += keyRepeatTime_;
238                keysToRepeat_++;
239            }
240        }
241    }
242
243    void InputBuffer::keyPressed(const KeyEvent &evt)
244    {
245        lastKey_ = evt.key;
246        timeSinceKeyPressed_ = 0.0;
247        timeSinceKeyRepeated_ = keyRepeatDeleay_;
248        keysToRepeat_ = 0;
249
250        processKey(evt);
251    }
252
253    void InputBuffer::keyHeld(const KeyEvent& evt)
254    {
255        if (evt.key == lastKey_)
256        {
257            while (keysToRepeat_)
258            {
259                processKey(evt);
260                keysToRepeat_--;
261            }
262        }
263    }
264}
Note: See TracBrowser for help on using the repository browser.