Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 6957b603 authored by Jeff Brown's avatar Jeff Brown Committed by Android (Google) Code Review
Browse files

Merge "Add Dvorak keyboard layout."

parents 62d52f9f 4a3862f6
Loading
Loading
Loading
Loading
+9 −0
Original line number Diff line number Diff line
@@ -120,6 +120,10 @@ public:
    bool getEvents(int32_t deviceId, const char16_t* chars, size_t numChars,
            Vector<KeyEvent>& outEvents) const;

    /* Maps a scan code and usage code to a key code, in case this key map overrides
     * the mapping in some way. */
    status_t mapKey(int32_t scanCode, int32_t usageCode, int32_t* outKeyCode) const;

#if HAVE_ANDROID_OS
    /* Reads a key map from a parcel. */
    static sp<KeyCharacterMap> readFromParcel(Parcel* parcel);
@@ -198,6 +202,8 @@ private:

    private:
        status_t parseType();
        status_t parseMap();
        status_t parseMapKey();
        status_t parseKey();
        status_t parseKeyProperty();
        status_t parseModifier(const String8& token, int32_t* outMetaState);
@@ -209,6 +215,9 @@ private:
    KeyedVector<int32_t, Key*> mKeys;
    int mType;

    KeyedVector<int32_t, int32_t> mKeysByScanCode;
    KeyedVector<int32_t, int32_t> mKeysByUsageCode;

    KeyCharacterMap();
    KeyCharacterMap(const KeyCharacterMap& other);

+99 −1
Original line number Diff line number Diff line
@@ -90,7 +90,8 @@ KeyCharacterMap::KeyCharacterMap() :
}

KeyCharacterMap::KeyCharacterMap(const KeyCharacterMap& other) :
    RefBase(), mType(other.mType) {
    RefBase(), mType(other.mType), mKeysByScanCode(other.mKeysByScanCode),
    mKeysByUsageCode(other.mKeysByUsageCode) {
    for (size_t i = 0; i < other.mKeys.size(); i++) {
        mKeys.add(other.mKeys.keyAt(i), new Key(*other.mKeys.valueAt(i)));
    }
@@ -180,6 +181,16 @@ sp<KeyCharacterMap> KeyCharacterMap::combine(const sp<KeyCharacterMap>& base,
            map->mKeys.add(keyCode, new Key(*key));
        }
    }

    for (size_t i = 0; i < overlay->mKeysByScanCode.size(); i++) {
        map->mKeysByScanCode.replaceValueFor(overlay->mKeysByScanCode.keyAt(i),
                overlay->mKeysByScanCode.valueAt(i));
    }

    for (size_t i = 0; i < overlay->mKeysByUsageCode.size(); i++) {
        map->mKeysByUsageCode.replaceValueFor(overlay->mKeysByUsageCode.keyAt(i),
                overlay->mKeysByUsageCode.valueAt(i));
    }
    return map;
}

@@ -315,6 +326,37 @@ bool KeyCharacterMap::getEvents(int32_t deviceId, const char16_t* chars, size_t
    return true;
}

status_t KeyCharacterMap::mapKey(int32_t scanCode, int32_t usageCode, int32_t* outKeyCode) const {
    if (usageCode) {
        ssize_t index = mKeysByUsageCode.indexOfKey(usageCode);
        if (index >= 0) {
#if DEBUG_MAPPING
    ALOGD("mapKey: scanCode=%d, usageCode=0x%08x ~ Result keyCode=%d.",
            scanCode, usageCode, *outKeyCode);
#endif
            *outKeyCode = mKeysByUsageCode.valueAt(index);
            return OK;
        }
    }
    if (scanCode) {
        ssize_t index = mKeysByScanCode.indexOfKey(scanCode);
        if (index >= 0) {
#if DEBUG_MAPPING
    ALOGD("mapKey: scanCode=%d, usageCode=0x%08x ~ Result keyCode=%d.",
            scanCode, usageCode, *outKeyCode);
#endif
            *outKeyCode = mKeysByScanCode.valueAt(index);
            return OK;
        }
    }

#if DEBUG_MAPPING
        ALOGD("mapKey: scanCode=%d, usageCode=0x%08x ~ Failed.", scanCode, usageCode);
#endif
    *outKeyCode = AKEYCODE_UNKNOWN;
    return NAME_NOT_FOUND;
}

bool KeyCharacterMap::getKey(int32_t keyCode, const Key** outKey) const {
    ssize_t index = mKeys.indexOfKey(keyCode);
    if (index >= 0) {
@@ -616,6 +658,10 @@ status_t KeyCharacterMap::Parser::parse() {
                    mTokenizer->skipDelimiters(WHITESPACE);
                    status_t status = parseType();
                    if (status) return status;
                } else if (keywordToken == "map") {
                    mTokenizer->skipDelimiters(WHITESPACE);
                    status_t status = parseMap();
                    if (status) return status;
                } else if (keywordToken == "key") {
                    mTokenizer->skipDelimiters(WHITESPACE);
                    status_t status = parseKey();
@@ -710,6 +756,58 @@ status_t KeyCharacterMap::Parser::parseType() {
    return NO_ERROR;
}

status_t KeyCharacterMap::Parser::parseMap() {
    String8 keywordToken = mTokenizer->nextToken(WHITESPACE);
    if (keywordToken == "key") {
        mTokenizer->skipDelimiters(WHITESPACE);
        return parseMapKey();
    }
    ALOGE("%s: Expected keyword after 'map', got '%s'.", mTokenizer->getLocation().string(),
            keywordToken.string());
    return BAD_VALUE;
}

status_t KeyCharacterMap::Parser::parseMapKey() {
    String8 codeToken = mTokenizer->nextToken(WHITESPACE);
    bool mapUsage = false;
    if (codeToken == "usage") {
        mapUsage = true;
        mTokenizer->skipDelimiters(WHITESPACE);
        codeToken = mTokenizer->nextToken(WHITESPACE);
    }

    char* end;
    int32_t code = int32_t(strtol(codeToken.string(), &end, 0));
    if (*end) {
        ALOGE("%s: Expected key %s number, got '%s'.", mTokenizer->getLocation().string(),
                mapUsage ? "usage" : "scan code", codeToken.string());
        return BAD_VALUE;
    }
    KeyedVector<int32_t, int32_t>& map =
            mapUsage ? mMap->mKeysByUsageCode : mMap->mKeysByScanCode;
    if (map.indexOfKey(code) >= 0) {
        ALOGE("%s: Duplicate entry for key %s '%s'.", mTokenizer->getLocation().string(),
                mapUsage ? "usage" : "scan code", codeToken.string());
        return BAD_VALUE;
    }

    mTokenizer->skipDelimiters(WHITESPACE);
    String8 keyCodeToken = mTokenizer->nextToken(WHITESPACE);
    int32_t keyCode = getKeyCodeByLabel(keyCodeToken.string());
    if (!keyCode) {
        ALOGE("%s: Expected key code label, got '%s'.", mTokenizer->getLocation().string(),
                keyCodeToken.string());
        return BAD_VALUE;
    }

#if DEBUG_PARSER
    ALOGD("Parsed map key %s: code=%d, keyCode=%d.",
            mapUsage ? "usage" : "scan code", code, keyCode);
#endif
    map.add(code, keyCode);
    return NO_ERROR;
}

status_t KeyCharacterMap::Parser::parseKey() {
    String8 keyCodeToken = mTokenizer->nextToken(WHITESPACE);
    int32_t keyCode = getKeyCodeByLabel(keyCodeToken.string());
+19 −9
Original line number Diff line number Diff line
@@ -199,17 +199,26 @@ status_t KeyLayoutMap::Parser::parse() {
}

status_t KeyLayoutMap::Parser::parseKey() {
    String8 scanCodeToken = mTokenizer->nextToken(WHITESPACE);
    String8 codeToken = mTokenizer->nextToken(WHITESPACE);
    bool mapUsage = false;
    if (codeToken == "usage") {
        mapUsage = true;
        mTokenizer->skipDelimiters(WHITESPACE);
        codeToken = mTokenizer->nextToken(WHITESPACE);
    }

    char* end;
    int32_t scanCode = int32_t(strtol(scanCodeToken.string(), &end, 0));
    int32_t code = int32_t(strtol(codeToken.string(), &end, 0));
    if (*end) {
        ALOGE("%s: Expected key scan code number, got '%s'.", mTokenizer->getLocation().string(),
                scanCodeToken.string());
        ALOGE("%s: Expected key %s number, got '%s'.", mTokenizer->getLocation().string(),
                mapUsage ? "usage" : "scan code", codeToken.string());
        return BAD_VALUE;
    }
    if (mMap->mKeysByScanCode.indexOfKey(scanCode) >= 0) {
        ALOGE("%s: Duplicate entry for key scan code '%s'.", mTokenizer->getLocation().string(),
                scanCodeToken.string());
    KeyedVector<int32_t, Key>& map =
            mapUsage ? mMap->mKeysByUsageCode : mMap->mKeysByScanCode;
    if (map.indexOfKey(code) >= 0) {
        ALOGE("%s: Duplicate entry for key %s '%s'.", mTokenizer->getLocation().string(),
                mapUsage ? "usage" : "scan code", codeToken.string());
        return BAD_VALUE;
    }

@@ -243,12 +252,13 @@ status_t KeyLayoutMap::Parser::parseKey() {
    }

#if DEBUG_PARSER
    ALOGD("Parsed key: scanCode=%d, keyCode=%d, flags=0x%08x.", scanCode, keyCode, flags);
    ALOGD("Parsed key %s: code=%d, keyCode=%d, flags=0x%08x.",
            mapUsage ? "usage" : "scan code", code, keyCode, flags);
#endif
    Key key;
    key.keyCode = keyCode;
    key.flags = flags;
    mMap->mKeysByScanCode.add(scanCode, key);
    map.add(code, key);
    return NO_ERROR;
}

+35 −7
Original line number Diff line number Diff line
@@ -19,10 +19,38 @@

type OVERLAY

# Test
key A {
    label:                              'X'
    base:                               'x'
    shift, capslock:                    'X'
    ctrl, alt, meta:                    none
}
map key 12 LEFT_BRACKET
map key 13 RIGHT_BRACKET
map key 16 APOSTROPHE
map key 17 COMMA
map key 18 PERIOD
map key 19 P
map key 20 Y
map key 21 F
map key 22 G
map key 23 C
map key 24 R
map key 25 L
map key 26 SLASH
map key 27 EQUALS
map key 30 A
map key 31 O
map key 32 E
map key 33 U
map key 34 I
map key 35 D
map key 36 H
map key 37 T
map key 38 N
map key 39 S
map key 40 MINUS
map key 44 SEMICOLON
map key 45 Q
map key 46 J
map key 47 K
map key 48 X
map key 49 B
map key 50 M
map key 51 W
map key 52 V
map key 53 Z
+17 −9
Original line number Diff line number Diff line
@@ -443,13 +443,24 @@ status_t EventHub::mapKey(int32_t deviceId, int32_t scanCode, int32_t usageCode,
    AutoMutex _l(mLock);
    Device* device = getDeviceLocked(deviceId);

    if (device && device->keyMap.haveKeyLayout()) {
        status_t err = device->keyMap.keyLayoutMap->mapKey(
                scanCode, usageCode, outKeycode, outFlags);
        if (err == NO_ERROR) {
    if (device) {
        // Check the key character map first.
        sp<KeyCharacterMap> kcm = device->getKeyCharacterMap();
        if (kcm != NULL) {
            if (!kcm->mapKey(scanCode, usageCode, outKeycode)) {
                *outFlags = 0;
                return NO_ERROR;
            }
        }

        // Check the key layout next.
        if (device->keyMap.haveKeyLayout()) {
            if (!device->keyMap.keyLayoutMap->mapKey(
                    scanCode, usageCode, outKeycode, outFlags)) {
                return NO_ERROR;
            }
        }
    }

    *outKeycode = 0;
    *outFlags = 0;
@@ -531,10 +542,7 @@ sp<KeyCharacterMap> EventHub::getKeyCharacterMap(int32_t deviceId) const {
    AutoMutex _l(mLock);
    Device* device = getDeviceLocked(deviceId);
    if (device) {
        if (device->combinedKeyMap != NULL) {
            return device->combinedKeyMap;
        }
        return device->keyMap.keyCharacterMap;
        return device->getKeyCharacterMap();
    }
    return NULL;
}
Loading