Ejemplo n.º 1
0
void
CKeyState::fakeToggle(KeyModifierMask modifier)
{
	const KeyButtons& buttons = m_maskToKeys[getIndexForModifier(modifier)];
	if (buttons.empty() || !isToggle(modifier)) {
		return;
	}
	KeyButton button = buttons[0];

	// get the sequence of keys to simulate key toggle
	Keystrokes keys;
	Keystroke keystroke;
	keystroke.m_key    = button;
	keystroke.m_press  = true;
	keystroke.m_repeat = false;
	keys.push_back(keystroke);
	keystroke.m_press  = false;
	keys.push_back(keystroke);

	// generate key events
	fakeKeyEvents(keys, 1);

	// note the toggle
	m_keys[button] ^= kToggled;
	m_mask         ^= modifier;
}
Ejemplo n.º 2
0
bool Button::state() const
{
	if ( isToggle() )
		return m_button->isChecked(); //was: state()
	else
		return m_button->isDown();
}
Ejemplo n.º 3
0
void
CKeyState::updateKeyState(KeyButton serverID, KeyButton localID,
				bool press, bool fake)
{
	// ignore bogus keys
	if (serverID == 0 || localID == 0) {
		return;
	}

	// update key state.  state doesn't change when auto-repeating.
	if (press) {
		m_serverKeyMap[serverID] = localID;
		m_keys[localID]         |= kDown;
	}
	else {
		m_serverKeyMap[serverID] = 0;
		m_keys[localID]         &= ~kDown;
	}

	// update modifier state
	KeyModifierMask mask = m_keyToMask[localID];
	if (mask != 0) {
		if (isToggle(mask)) {
			// never report half-duplex keys as down
			if (isHalfDuplex(mask)) {
				m_keys[localID] &= ~kDown;
				// half-duplex keys on the primary screen don't send the
				// usual press/release pairs but instead send the press
				// when toggling on and the release when toggleing off.
				// since we normally toggle our shadow state on the press
				// we need to treat the release as a press on the primary
				// screen.  we know we're on the primary screen if fake is
				// false.  secondary screens always get press/release pairs.
				if (!fake) {
					press = true;
				}
			}

			// toggle on the press
			if (press) {
				m_keys[localID] ^= kToggled;
				m_mask          ^= mask;
			}
		}
		else {
			if (press) {
				m_mask |= mask;
			}
			else if (!isModifierActive(mask)) {
				m_mask &= ~mask;
			}
		}
		LOG((CLOG_DEBUG2 "new mask: 0x%04x", m_mask));
	}
}
Ejemplo n.º 4
0
void
CKeyState::setToggled(KeyModifierMask modifier)
{
	if (isToggle(modifier)) {
		const KeyButtons& buttons = m_maskToKeys[getIndexForModifier(modifier)];
		for (KeyButtons::const_iterator j = buttons.begin();
									j != buttons.end(); ++j) {
			m_keys[(*j) & kButtonMask] |= kToggled;
		}
	}
}
Ejemplo n.º 5
0
void Button::setState( bool state )
{
	if ( this->state() == state )
		return;
	
	if ( isToggle() )
		m_button->setOn(state);
	else
		m_button->setDown(state);
	
	slotStateChanged();
}
Ejemplo n.º 6
0
bool
CKeyState::isModifierActive(KeyModifierMask mask) const
{
	const KeyButtons& buttons = m_maskToKeys[getIndexForModifier(mask)];
	KeyButtons::const_iterator j = buttons.begin();
	if (j != buttons.end()) {
		if (isToggle(mask)) {
			// modifier is a toggle
			if ((m_keys[*j] & kToggled) != 0) {
				return true;
			}
		}
		else {
			// modifier is not a toggle
			for (; j != buttons.end(); ++j) {
				if ((m_keys[*j] & kDown) != 0) {
					return true;
				}
			}
		}
	}
	return false;
}
Ejemplo n.º 7
0
bool
CKeyState::mapModifier(Keystrokes& keys, Keystrokes& undo,
				KeyModifierMask mask, bool desireActive, bool force) const
{
	// look up modifier
	const KeyButtons& buttons = m_maskToKeys[getIndexForModifier(mask)];
	if (buttons.empty()) {
		return false;
	}

	// ignore if already in desired state
	if (!force && isModifierActive(mask) == desireActive) {
		return true;
	}

	// initialize keystroke
	Keystroke keystroke;
	keystroke.m_repeat = false;

	// handle toggles
	if (isToggle(mask)) {
		keystroke.m_key   = buttons[0];
		keystroke.m_press = true;
		keys.push_back(keystroke);
		keystroke.m_press = false;
		keys.push_back(keystroke);
		keystroke.m_press = false;
		undo.push_back(keystroke);
		keystroke.m_press = true;
		undo.push_back(keystroke);
	}

	else if (desireActive) {
		// press
		keystroke.m_key   = buttons[0];
		keystroke.m_press = true;
		keys.push_back(keystroke);
		keystroke.m_press = false;
		undo.push_back(keystroke);
	}

	else {
		// releasing a modifier is quite different from pressing one.
		// when we release a modifier we have to release every keycode that
		// is assigned to the modifier since the modifier is active if any
		// one of them is down.  when we press a modifier we just have to
		// press one of those keycodes.
		for (KeyButtons::const_iterator j = buttons.begin();
								j != buttons.end(); ++j) {
			if (isKeyDown(*j)) {
				keystroke.m_key   = *j;
				keystroke.m_press = false;
				keys.push_back(keystroke);
				keystroke.m_press = true;
				undo.push_back(keystroke);
			}
		}
	}

	return true;
}