keyHandling.cc 23.3 KB
Newer Older
1
/*===========================================================================*\
Jan Möbius's avatar
Jan Möbius committed
2 3
*                                                                            *
*                              OpenFlipper                                   *
Martin Schultz's avatar
Martin Schultz committed
4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
 *           Copyright (c) 2001-2015, RWTH-Aachen University                 *
 *           Department of Computer Graphics and Multimedia                  *
 *                          All rights reserved.                             *
 *                            www.openflipper.org                            *
 *                                                                           *
 *---------------------------------------------------------------------------*
 * This file is part of OpenFlipper.                                         *
 *---------------------------------------------------------------------------*
 *                                                                           *
 * Redistribution and use in source and binary forms, with or without        *
 * modification, are permitted provided that the following conditions        *
 * are met:                                                                  *
 *                                                                           *
 * 1. Redistributions of source code must retain the above copyright notice, *
 *    this list of conditions and the following disclaimer.                  *
 *                                                                           *
 * 2. Redistributions in binary form must reproduce the above copyright      *
 *    notice, this list of conditions and the following disclaimer in the    *
 *    documentation and/or other materials provided with the distribution.   *
 *                                                                           *
 * 3. Neither the name of the copyright holder nor the names of its          *
 *    contributors may be used to endorse or promote products derived from   *
 *    this software without specific prior written permission.               *
 *                                                                           *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS       *
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED *
 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A           *
 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER *
 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,  *
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,       *
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR        *
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF    *
 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING      *
 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS        *
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.              *
Jan Möbius's avatar
Jan Möbius committed
39
*                                                                            *
40 41 42
\*===========================================================================*/

/*===========================================================================*\
Jan Möbius's avatar
Jan Möbius committed
43 44 45 46 47
*                                                                            *
*   $Revision$                                                       *
*   $LastChangedBy$                                                *
*   $Date$                     *
*                                                                            *
48 49
\*===========================================================================*/

Dirk Wilden's avatar
Dirk Wilden committed
50 51 52
#include "CoreWidget.hh"

#include <OpenFlipper/BasePlugin/KeyInterface.hh>
Jan Möbius's avatar
 
Jan Möbius committed
53

Dirk Wilden's avatar
Dirk Wilden committed
54 55 56 57 58 59 60 61 62 63 64
//-----------------------------------------------------------------------------

KeyBinding CoreWidget::getKeyBinding(QObject* _plugin, int _keyIndex ){
  if (_plugin == 0)
    return coreKeys_[_keyIndex];

  for (uint i=0; i < plugins_.size(); i++){
    if (plugins_[i].plugin == _plugin)
      return plugins_[i].keys[_keyIndex];
  }

65
  emit log(LOGERR,tr("ERROR: could not get KeyBinding"));
Dirk Wilden's avatar
Dirk Wilden committed
66 67 68
  return KeyBinding();
}

Dirk Wilden's avatar
Dirk Wilden committed
69 70 71 72 73 74 75 76 77
QString CoreWidget::getRPCName(QObject* _plugin ){
  if (_plugin == 0)
    return "";

  for (uint i=0; i < plugins_.size(); i++){
    if (plugins_[i].plugin == _plugin)
      return plugins_[i].rpcName;
  }

78
  emit log(LOGERR,tr("ERROR: could not get rpcname"));
Dirk Wilden's avatar
Dirk Wilden committed
79 80 81
  return "";
}

Dirk Wilden's avatar
Dirk Wilden committed
82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97
/// passes keyPressEvents to either the Core or a Plugin depending on who has registered the key
void CoreWidget::keyPressEvent(QKeyEvent* _e)
{
  std::pair< int,Qt::KeyboardModifiers > key = std::make_pair(_e->key(), _e->modifiers() );

  //iterate over all assigned keys
  KeyRange range = keys_.equal_range(key);

  KeyMap::iterator it;
  for (it=range.first; it != range.second; ++it){

    QObject* plugin = (*it).second.first;
    KeyBinding binding = getKeyBinding( plugin, (*it).second.second );

    //check if its a core Key
    if (plugin == 0){
Dirk Wilden's avatar
Dirk Wilden committed
98 99 100 101 102 103 104 105

      //the key belongs to a slot
      if (binding.slot){
        bool ok;
        emit call("core." + binding.description, ok);
        return;
      }

106 107 108 109
      // =================================================================================
      // Map event to the cores key and modifier.
      // Call the core key handler with the mapped event.
      // =================================================================================
Matthias Möller's avatar
Matthias Möller committed
110 111
      QKeyEvent mappedEvent (_e->type(),binding.key, binding.modifiers,
                             _e->text(), _e->isAutoRepeat(), _e->count() );
Dirk Wilden's avatar
Dirk Wilden committed
112

Matthias Möller's avatar
Matthias Möller committed
113
      coreKeyPressEvent(&mappedEvent);
Dirk Wilden's avatar
Dirk Wilden committed
114 115 116 117 118 119 120 121 122

      //if the key is multiUse also check other assigned keys
      if (binding.multiUse)
        continue;
      else
        return;
    }

    //it's a plugin key
Dirk Wilden's avatar
Dirk Wilden committed
123 124 125 126 127 128 129 130 131

    //the key belongs to a slot
    if (binding.slot){
      bool ok;
      emit call(getRPCName(plugin) +"."+ binding.description, ok);
      return;
    }

    //the key was specified through keyInterface
Dirk Wilden's avatar
Dirk Wilden committed
132 133 134
    KeyInterface* keyPlugin = qobject_cast< KeyInterface * >(plugin);

    if (keyPlugin){
135 136 137 138 139

      // =================================================================================
      // Map event to the plugins key and modifier.
      // Call it with the mapped event.
      // =================================================================================
Matthias Möller's avatar
Matthias Möller committed
140 141
      QKeyEvent mappedEvent(_e->type(),binding.key, binding.modifiers,
                             _e->text(), _e->isAutoRepeat(), _e->count() );
142

Matthias Möller's avatar
Matthias Möller committed
143
      keyPlugin->slotKeyEvent(&mappedEvent);
Dirk Wilden's avatar
Dirk Wilden committed
144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170
    }

    //if its not a multiUse key we are ready
    if (!binding.multiUse)
      return;
  }
}

//-----------------------------------------------------------------------------

/// passes keyReleaseEvents to either the Core or a Plugin depending on who has registered the key
void CoreWidget::keyReleaseEvent(QKeyEvent* _e) {

  if (_e->isAutoRepeat()) return; //consider only "real" release events

  std::pair< int,Qt::KeyboardModifiers > key = std::make_pair(_e->key(), _e->modifiers() );

  //iterate over all assigned keys
  KeyRange range = keys_.equal_range(key);

  KeyMap::iterator it;
  for (it=range.first; it != range.second; ++it){

    QObject* plugin = (*it).second.first;
    KeyBinding binding = getKeyBinding( plugin, (*it).second.second );

    if (plugin == 0){
171 172 173 174 175

      // =================================================================================
      // Map event to the cores key and modifier.
      // Call the core key handler with the mapped event.
      // =================================================================================
Matthias Möller's avatar
Matthias Möller committed
176 177 178
      QKeyEvent mappedEvent (_e->type(),binding.key, binding.modifiers,
                             _e->text(), _e->isAutoRepeat(), _e->count() );
      coreKeyReleaseEvent(&mappedEvent);
Dirk Wilden's avatar
Dirk Wilden committed
179 180 181 182 183 184 185 186 187 188 189 190

      //if the key is multiUse also check other assigned keys
      if (binding.multiUse)
        continue;
      else
        return;
    }

    //it's a plugin key
    KeyInterface* keyPlugin = qobject_cast< KeyInterface * >(plugin);

    if (keyPlugin){
191 192 193 194 195 196

      // =================================================================================
      // Map event to the plugins key and modifier.
      // Call the plugin with the mapped event.
      // =================================================================================

Matthias Möller's avatar
Matthias Möller committed
197 198
      QKeyEvent mappedEvent (_e->type(),binding.key, binding.modifiers,
                             _e->text(), _e->isAutoRepeat(), _e->count() );
199

Matthias Möller's avatar
Matthias Möller committed
200
      keyPlugin->slotKeyReleaseEvent(&mappedEvent);
Dirk Wilden's avatar
Dirk Wilden committed
201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216
    }

    //if its not a multiUse key we are ready
    if (!binding.multiUse)
      return;
  }
}

//-----------------------------------------------------------------------------

/// Register a key to the core or a plugin
void CoreWidget::slotRegisterKey(int _key, Qt::KeyboardModifiers _modifiers, QString _description, bool _multiUse){

  //first check if the key is already registered by the coreWidget
  bool found = false;
  bool multi = false;
217
  QString name;
Dirk Wilden's avatar
Dirk Wilden committed
218 219 220 221
  for (uint i=0; i < coreKeys_.size(); i++)
    if (coreKeys_[i].key == _key && coreKeys_[i].modifiers == _modifiers){
      found = true;
      multi = coreKeys_[i].multiUse;
222
      name = "Core";
Dirk Wilden's avatar
Dirk Wilden committed
223 224 225 226 227 228 229 230 231 232 233
      break;
    }

  //then check if the key is already registered by a different plugin
  if (!found)
    for (uint i=0; i < plugins_.size(); i++)
      for (int k=0; k < plugins_[i].keys.count(); k++)
        if (plugins_[i].keys[k].key == _key
        && plugins_[i].keys[k].modifiers == _modifiers){
          found = true;
          multi = plugins_[i].keys[k].multiUse;
234
          name = plugins_[i].name;
Dirk Wilden's avatar
Dirk Wilden committed
235 236 237
          break;
        }

238
  if (found && !multi)
Jan Möbius's avatar
Jan Möbius committed
239
    emit log(LOGERR, tr("Key already registered by '%1'").arg( name ) );
Dirk Wilden's avatar
Dirk Wilden committed
240 241 242 243 244 245 246 247

  //check if its a key for the core
  if (sender() == this){
    KeyBinding kb;
    kb.key = _key;
    kb.modifiers = _modifiers;
    kb.description = _description;
    kb.multiUse = multi || _multiUse;
Dirk Wilden's avatar
Dirk Wilden committed
248
    kb.slot = false;
Dirk Wilden's avatar
Dirk Wilden committed
249 250

    if (multi && !_multiUse)
Jan Möbius's avatar
Jan Möbius committed
251
      emit log(LOGERR, tr("Key already registered by '%1'. Forced registration as multiUse key.").arg( name ));
Dirk Wilden's avatar
Dirk Wilden committed
252 253 254

    coreKeys_.push_back( kb );

255 256
    keys_.insert( std::make_pair( std::make_pair(_key, _modifiers) , std::make_pair ((QObject*)0, int(coreKeys_.size()-1 ) ) )) ;
    invKeys_.insert( std::make_pair( std::make_pair ((QObject*)0, int(coreKeys_.size()-1) ) , std::make_pair(_key, _modifiers) ) );
Dirk Wilden's avatar
Dirk Wilden committed
257 258 259 260 261 262 263 264 265 266 267
    return;
  }

  //find plugin
 PluginInfo* pluginInfo = 0;

  for (uint i=0; i < plugins_.size(); i++)
    if (plugins_[i].plugin == sender())
      pluginInfo = &plugins_[i];

  if (pluginInfo == 0){
268
    emit log(LOGERR, tr("Unable to register key. Plugin not found!"));
Dirk Wilden's avatar
Dirk Wilden committed
269 270 271 272 273 274 275 276
    return;
  }

  KeyBinding kb;
  kb.key = _key;
  kb.modifiers = _modifiers;
  kb.description = _description;
  kb.multiUse = multi || _multiUse;
Dirk Wilden's avatar
Dirk Wilden committed
277
  kb.slot = false;
Dirk Wilden's avatar
Dirk Wilden committed
278 279

  if (multi && !_multiUse)
Jan Möbius's avatar
Jan Möbius committed
280
    emit log(LOGERR, tr("Key already registered by '%1'. Forced registration as multiUse key.").arg( name ));
Dirk Wilden's avatar
Dirk Wilden committed
281 282 283 284 285 286 287

  pluginInfo->keys.append( kb );

  keys_.insert( std::make_pair( std::make_pair(_key, _modifiers) , std::make_pair(pluginInfo->plugin, pluginInfo->keys.size()-1) ) );
  invKeys_.insert( std::make_pair( std::make_pair(pluginInfo->plugin, pluginInfo->keys.size()-1) , std::make_pair(_key, _modifiers) ) );
}

Dirk Wilden's avatar
Dirk Wilden committed
288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306
///scripting slots will automatically registered to be assigned  to an invalid key(-1)
void CoreWidget::slotRegisterSlotKeyBindings(){

  //check the core slots
  for (int i=0; i < coreSlots_.count(); i++){

    //only consider functions without arguments
    if ( !coreSlots_.at(i).slotName.contains( "()" ) )
      continue;

    KeyBinding kb;
    kb.key = -1;
    kb.modifiers = 0;
    kb.description = coreSlots_.at(i).slotName;
    kb.multiUse = true;
    kb.slot = true;

    coreKeys_.push_back( kb );

307 308
    keys_.insert( std::make_pair( std::make_pair(-1, (QFlags<Qt::KeyboardModifier>)0) , std::make_pair ((QObject*)0, int(coreKeys_.size()-1) ) )) ;
    invKeys_.insert( std::make_pair( std::make_pair ((QObject*)0, int(coreKeys_.size()-1) ) , std::make_pair(-1, (QFlags<Qt::KeyboardModifier>)0) ) );
Dirk Wilden's avatar
Dirk Wilden committed
309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326
  }

  //check all plugins
  for (uint i=0; i < plugins_.size(); i++)

    for (int j=0; j < plugins_[i].rpcFunctions.count(); j++){

      //only consider functions without arguments
      if ( !plugins_[i].rpcFunctions[j].contains( "()" )
         || plugins_[i].rpcFunctions[j] == "version()")
        continue;

      KeyBinding kb;
      kb.key = -1;
      kb.modifiers = 0;
      kb.description = plugins_[i].rpcFunctions[j];
      kb.multiUse = true;
      kb.slot = true;
Jan Möbius's avatar
 
Jan Möbius committed
327

Dirk Wilden's avatar
Dirk Wilden committed
328
      plugins_[i].keys.append( kb );
Jan Möbius's avatar
 
Jan Möbius committed
329

330 331
      keys_.insert( std::make_pair( std::make_pair(-1, (QFlags<Qt::KeyboardModifier>)0) , std::make_pair(plugins_[i].plugin, plugins_[i].keys.size()-1) ) );
      invKeys_.insert( std::make_pair( std::make_pair(plugins_[i].plugin, plugins_[i].keys.size()-1) , std::make_pair(-1, (QFlags<Qt::KeyboardModifier>)0) ) );
Dirk Wilden's avatar
Dirk Wilden committed
332 333 334
    }
}

Dirk Wilden's avatar
Dirk Wilden committed
335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366
/// add a new keyMapping (keyBindingID is the id of the keyBinding in the pluginInfo of _plugin :)
void CoreWidget::slotAddKeyMapping(int _key, Qt::KeyboardModifiers _modifiers, QObject* _plugin, int _keyBindingID){

  std::pair< int,Qt::KeyboardModifiers > keyCombi = std::make_pair(_key, _modifiers );
  std::pair< int,Qt::KeyboardModifiers > oldCombi;
  std::pair< QObject*, int > oldTarget;

  bool replace = false;

  //and check if the key is already assigned without multiUse
  KeyMap::iterator it;
  for (it=keys_.begin(); it != keys_.end(); ++it){

    int key = (*it).first.first;
    Qt::KeyboardModifiers modifiers = (*it).first.second;
    QObject* plugin = (*it).second.first;
    int bindingID = (*it).second.second;
    KeyBinding binding = getKeyBinding(plugin, bindingID);

    //check if its the keyBinding we want to map/replace
    if (plugin == _plugin && bindingID == _keyBindingID){
      replace = true;
      oldCombi = (*it).first;
      oldTarget = (*it).second;
      continue;
    }

    //check if the mapping is conflicting with other mappings
    if (_key == key && _modifiers == modifiers ){

      if (!binding.multiUse){
        if (plugin == 0)
367
          emit log(LOGERR, tr("Could not add key mapping. Key already assigned to the core."));
Dirk Wilden's avatar
Dirk Wilden committed
368 369
        else{
          BaseInterface* basePlugin = qobject_cast< BaseInterface * >(plugin);
370

Dirk Wilden's avatar
Dirk Wilden committed
371
          if (basePlugin)
Jan Möbius's avatar
Jan Möbius committed
372
            emit log(LOGERR, tr("Could not add key mapping. Key already assigned to %1").arg( basePlugin->name() ) );
Dirk Wilden's avatar
Dirk Wilden committed
373
          else
374
            emit log(LOGERR, tr("Could not add key mapping. Key already assigned to an unknown plugin."));
Dirk Wilden's avatar
Dirk Wilden committed
375 376 377 378 379 380 381 382 383 384 385
        }
        return;
      }
    }
  }

  KeyBinding keyBinding = getKeyBinding(_plugin, _keyBindingID);

  //check if new binding doesn't allow multiUse but other assignments for the key exist
  if (!keyBinding.multiUse)
    if ( (replace && keys_.count(keyCombi) > 1)  || (!replace && keys_.count(keyCombi) > 0) ){
386
      emit log(LOGERR, tr("Could not add (single usage) key mapping. Key already assigned."));
Dirk Wilden's avatar
Dirk Wilden committed
387 388 389 390 391 392 393 394
      return;
    }

  if (replace){
    keys_.erase(oldCombi);
    invKeys_.erase(oldTarget);
  }

395 396 397 398
  //now we can add the mapping
  keys_.insert   ( std::make_pair( keyCombi , std::make_pair(_plugin, _keyBindingID) ));
  invKeys_.insert( std::make_pair( std::make_pair(_plugin, _keyBindingID),  keyCombi ));

Dirk Wilden's avatar
Dirk Wilden committed
399 400
}

401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506
///Load key assignments from a given INI file
void CoreWidget::loadKeyBindings(INIFile& _ini){

  QVector< int > keys;
  QVector< int > modifiers;
  QStringList pluginNames;
  QVector< int > bindingIDs;

  //first load everything from INI file
  if ( !_ini.section_exists("KeyBindings") )
     return;

  int keyCount;
  if (_ini.get_entry(keyCount,"KeyBindings","KeyCount") ){

    int key;
    int mod;
    QString name;
    int binding;

    for (int i=0; i < keyCount; i++){

      if (!_ini.get_entry(key,     "KeyBindings","Key" + QString::number(i) ) ) continue;
      if (!_ini.get_entry(mod,     "KeyBindings","KeyModifiers" + QString::number(i) ) )  continue;
      if (!_ini.get_entry(name,    "KeyBindings","KeyTarget" + QString::number(i) ) )  continue;
      if (!_ini.get_entry(binding, "KeyBindings","KeyBinding" + QString::number(i) ) ) continue;

      keys.push_back( key );
      modifiers.push_back( mod );
      pluginNames.push_back( name );
      bindingIDs.push_back( binding );
    }
  }

  //add the keyMapping
  for (int i=0; i < keys.count(); i++){

    //first we need the plugin
    QObject* plugin = 0;

    if (pluginNames[i] != "Core" ){
      //search for the plugin
      for (uint i=0; i < plugins_.size(); i++)
        if (plugins_[i].rpcName == pluginNames[i] ){
          plugin = plugins_[i].plugin;
          break;
        }

      if (plugin == 0)
        continue; //because plugin was not found
    }

    slotAddKeyMapping( keys[i], (Qt::KeyboardModifiers) modifiers[i], plugin, bindingIDs[i] );
  }

}

///Store current key assignments to a given INI file
void CoreWidget::saveKeyBindings(INIFile& _ini){

  QVector< int > keys;
  QVector< int > modifiers;
  QStringList pluginNames;
  QVector< int > bindingIDs;

  //first get all keys with custom assignments
  KeyMap::iterator it;
  for (it=keys_.begin(); it != keys_.end(); ++it){

    int key = (*it).first.first;
    Qt::KeyboardModifiers mod = (*it).first.second;
    QObject* plugin = (*it).second.first;
    int bindingID = (*it).second.second;
    KeyBinding binding = getKeyBinding(plugin, bindingID);

    //check if current key assignment and original assignment differ
    if (key != binding.key || mod != binding.modifiers){

      //get the pluginName
      QString name;

      if (plugin == 0)
        name = "Core";
      else
        name = getRPCName(plugin);

      //store key assignment
      keys.push_back( key );
      modifiers.push_back( mod );
      pluginNames.push_back( name );
      bindingIDs.push_back( bindingID );
    }
  }

  //finally store everything to INI file
  _ini.add_entry("KeyBindings","KeyCount", keys.count());

  for (int i=0; i < keys.count(); i++){

    _ini.add_entry("KeyBindings","Key" + QString::number(i)         , keys[i] );
    _ini.add_entry("KeyBindings","KeyModifiers" + QString::number(i), modifiers[i] );
    _ini.add_entry("KeyBindings","KeyTarget" + QString::number(i)   , pluginNames[i] );
    _ini.add_entry("KeyBindings","KeyBinding" + QString::number(i)  , bindingIDs[i] );
  }
}

507
/// if a keyPressEvent belongs to the core this functions is called
Jan Möbius's avatar
Jan Möbius committed
508
void CoreWidget::registerCoreKeys() {
509 510

  //register keys for coreWidget
Jan Möbius's avatar
Jan Möbius committed
511 512
  connect(this , SIGNAL( registerKey(int, Qt::KeyboardModifiers, QString, bool) ),
          this , SLOT(slotRegisterKey(int, Qt::KeyboardModifiers, QString, bool)) );
513

Jan Möbius's avatar
Jan Möbius committed
514
  emit registerKey(Qt::Key_Print  , Qt::NoModifier, "Create Snapshot");
515 516 517
  emit registerKey(Qt::Key_Escape , Qt::NoModifier, "Switch to last action mode ( Move,Picking,Light or Info Mode)");
  emit registerKey(Qt::Key_Space  , Qt::NoModifier, "Toggle between multiview and single view");

518 519
  emit registerKey(Qt::Key_S      , Qt::ControlModifier, "Save Object");
  emit registerKey(Qt::Key_O      , Qt::ControlModifier, "Open Object");
Jan Möbius's avatar
Jan Möbius committed
520 521 522
  emit registerKey(Qt::Key_L      , Qt::ControlModifier, "Show/Hide Logger");
  emit registerKey(Qt::Key_T      , Qt::ControlModifier, "Show/Hide Toolbox");
  emit registerKey(Qt::Key_F      , Qt::ControlModifier, "Toggle Fullscreen");
523
  emit registerKey(Qt::Key_B      , Qt::ControlModifier, "Show/Hide StatusBar");
524
  emit registerKey(Qt::Key_N      , Qt::ControlModifier, "Show/Hide ToolBar");
525
  emit registerKey(Qt::Key_M      , Qt::ControlModifier, "Show/Hide MenuBar");
526

527

528 529 530
  if ( OpenFlipper::Options::isLinux() ) {
    emit registerKey(Qt::Key_Meta , Qt::MetaModifier, "Use Navigation mode while key is pressed");
    emit registerKey(Qt::Key_Meta , Qt::NoModifier, "Use Navigation mode while key is pressed");
Matthias Möller's avatar
Matthias Möller committed
531 532 533 534
    emit registerKey(Qt::Key_Super_L , Qt::NoModifier, "Use Navigation mode while key is pressed");
    emit registerKey(Qt::Key_Super_L , Qt::MetaModifier, "Use Navigation mode while key is pressed");
    emit registerKey(Qt::Key_Super_R , Qt::NoModifier, "Use Navigation mode while key is pressed");
    emit registerKey(Qt::Key_Super_R , Qt::MetaModifier, "Use Navigation mode while key is pressed");
535
  } else {
536 537
    emit registerKey(Qt::Key_Alt  , Qt::AltModifier, "Use Navigation mode while key is pressed");
    emit registerKey(Qt::Key_Alt  , Qt::NoModifier, "Use Navigation mode while key is pressed");
538 539
  }

Dirk Wilden's avatar
Dirk Wilden committed
540 541
  emit registerKey(Qt::Key_Shift  , Qt::ShiftModifier, "Apply context menu action to all Viewers", true);
  emit registerKey(Qt::Key_Shift  , Qt::NoModifier, "Apply context menu action to all Viewers", true);
542 543
  
  
544 545 546 547
  emit registerKey(Qt::Key_A      , Qt::NoModifier, "First Person view strafe left");
  emit registerKey(Qt::Key_D      , Qt::NoModifier, "First Person view strafe right");
  emit registerKey(Qt::Key_W      , Qt::NoModifier, "First Person view move forward");
  emit registerKey(Qt::Key_S      , Qt::NoModifier, "First Person view move back");
548
  
549 550
}

Dirk Wilden's avatar
Dirk Wilden committed
551 552
/// if a keyPressEvent belongs to the core this functions is called
void CoreWidget::coreKeyPressEvent  (QKeyEvent* _e){
Jan Möbius's avatar
Jan Möbius committed
553
  //emit log(LOGERR,"Key Press");
Matthias Möller's avatar
Matthias Möller committed
554 555
  if ( (( _e->key() == Qt::Key_Meta ) || (_e->key() == Qt::Key_Super_L) || (_e->key() == Qt::Key_Super_R))
      && OpenFlipper::Options::isLinux() ) {
Jan Möbius's avatar
 
Jan Möbius committed
556

Matthias Möller's avatar
Matthias Möller committed
557 558 559 560 561
    if ( lastActionMode() == actionMode()) {
      if (actionMode() == Viewer::PickingMode)
        setActionMode( Viewer::ExamineMode );
      else
        setActionMode( Viewer::PickingMode );
562
    }
Matthias Möller's avatar
Matthias Möller committed
563 564
    else
      setActionMode(lastActionMode());
565 566 567
  }

  if ( ( _e->key() == Qt::Key_Alt ) && ! OpenFlipper::Options::isLinux() ) {
Matthias Möller's avatar
Matthias Möller committed
568 569 570 571 572 573
    //emit log(LOGERR,"Switch to examine mode");
    if ( lastActionMode() == actionMode()) {
      if (actionMode() == Viewer::PickingMode)
        setActionMode( Viewer::ExamineMode );
      else
        setActionMode( Viewer::PickingMode );
574
    }
Matthias Möller's avatar
Matthias Möller committed
575 576
    else
      setActionMode(lastActionMode());
577 578 579
  }


Jan Möbius's avatar
Jan Möbius committed
580
  if (_e->modifiers() & Qt::ControlModifier ) {
Jan Möbius's avatar
Dennis:  
Jan Möbius committed
581
    switch (_e->key()) {
582 583 584 585
      case Qt::Key_B :
          toggleStatusBar();
        return;

Jan Möbius's avatar
Dennis:  
Jan Möbius committed
586 587 588
      case Qt::Key_F :
          toggleFullscreen();
        return;
Dirk Wilden's avatar
Dirk Wilden committed
589

Jan Möbius's avatar
Dennis:  
Jan Möbius committed
590 591 592
      case Qt::Key_L :
          toggleLogger();
        return;
Dirk Wilden's avatar
Dirk Wilden committed
593

Jan Möbius's avatar
Dennis:  
Jan Möbius committed
594 595 596
      case Qt::Key_T :
          toggleToolbox();
        return;
Dirk Wilden's avatar
Dirk Wilden committed
597

598
      case Qt::Key_M :
599
        toggleMenuBar();
600 601
        return;

602
      case Qt::Key_N:
603
          toggleToolBar();
604 605
        return;

Jan Möbius's avatar
Dennis:  
Jan Möbius committed
606 607
      case Qt::Key_O :
        loadMenu();
608
        return;
Dirk Wilden's avatar
Dirk Wilden committed
609

Jan Möbius's avatar
Dennis:  
Jan Möbius committed
610 611 612 613 614
      case Qt::Key_S :
        saveMenu();
      default:
        return;
    }
615

Dirk Wilden's avatar
Dirk Wilden committed
616 617
  }

Jan Möbius's avatar
Jan Möbius committed
618
  switch (_e->key()) {
619
    
Jan Möbius's avatar
Jan Möbius committed
620
    case Qt::Key_Escape:
621
        setActionMode( lastActionMode() );
Jan Möbius's avatar
Jan Möbius committed
622
      break;
Dirk Wilden's avatar
Dirk Wilden committed
623

Jan Möbius's avatar
Jan Möbius committed
624 625 626 627
    case Qt::Key_Print:
      std::cerr << "Todo : On Print Screen, create a snapshot for all viewers" << std::endl;
      break;

628
    case Qt::Key_Space:
629
      nextViewerLayout();
Dirk Wilden's avatar
Dirk Wilden committed
630
      break;
631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647
      
    case Qt::Key_A:
      strafeLeft();
      break;
      
    case Qt::Key_D:
      strafeRight();
      break;
      
    case Qt::Key_W:
      moveForward();
      break;      

    case Qt::Key_S:
      moveBack();
      break;      
      
Dirk Wilden's avatar
Dirk Wilden committed
648 649
    case Qt::Key_Shift :
      shiftPressed_ = true;
650 651
      break;

Jan Möbius's avatar
Jan Möbius committed
652
    default:
Dirk Wilden's avatar
Dirk Wilden committed
653
      shiftPressed_ = false;
Jan Möbius's avatar
Jan Möbius committed
654
      return;
Dirk Wilden's avatar
Dirk Wilden committed
655 656 657 658
  }
}

/// if a keyReleaseEvent belongs to the core this functions is called
Dirk Wilden's avatar
Dirk Wilden committed
659
void CoreWidget::coreKeyReleaseEvent(QKeyEvent* _e){
Dirk Wilden's avatar
Dirk Wilden committed
660

Matthias Möller's avatar
Matthias Möller committed
661 662
  if ( (( _e->key() == Qt::Key_Meta ) || (_e->key() == Qt::Key_Super_L) || (_e->key() == Qt::Key_Super_R))
      && OpenFlipper::Options::isLinux() ) {
663 664 665
      setActionMode( lastActionMode() );
  }

Jan Möbius's avatar
Jan Möbius committed
666
  //emit log(LOGERR,"Key release");
Jan Möbius's avatar
 
Jan Möbius committed
667 668

  if ( ( _e->key() == Qt::Key_Alt ) && !OpenFlipper::Options::isLinux() ) {
669 670 671 672
      setActionMode( lastActionMode() );
  }


Dirk Wilden's avatar
Dirk Wilden committed
673 674 675 676 677 678 679
  switch (_e->key()) {
    case Qt::Key_Shift :
      shiftPressed_ = false;
      break;
    default:
      return;
  }
Dirk Wilden's avatar
Dirk Wilden committed
680
}