#🤖│community_dev

1 messages · Page 17 of 1

craggy wave
#

There is a market for quality keyboards though

#

(that's actually how I found out about this keyboard)

#

Though the fundamentally broken assumption was that the source would be available

#

Because all these nerds customize the crap out of everything

wide nymph
#

You can get quality keyboards with QMK on it and play around with it. Or Input cub's hm TLL, I forgot the abbreviation or Keyboardio's what's the name again.

#

If we would be making a regular keyboard, we would of used one of the above as well.

#

But we're not and the above also can't fulfil the requirement for it.

#

and for what we've made, the most important part is the analog value part.

#

That's what people really want to play with.

craggy wave
#

Right, but why not cater to people who know what they're doing enough to see the value of the keyboard?

#

Bugs get found and fixed and it improves the base product for all the users

wide nymph
#

So, when we started, we gave raw access to the analog values of the keyboard. But you needed to go pretty low-level to understand it. Then we created the Analog SDK, now you can go much higher-level, more accessible. The next step is to further simplify and build useful tools on top of that.

#

So you can actually create value

#

Then firmware such as QMK, TLL and that of keyboardio can also connect with the Analog SDK

#

and enjoy the same type of valuable creations

#

Without touching each other's firmware nor limiting it to a single firmware

#

Because firmware is one hell of a messy work.

craggy wave
#

eh

#

I'm not so sure about that

#

The only messiness I've run into is crappy microprocessor design

#

Like atmega is so inconsistent

#

They pretend it's one base design but it's all these diverging things under the same label

wide nymph
#

There'll always be something, just a matter of what you can accept. But if your realistic and look a the % of the world population that can actually do firmware work. Versus people that can build something in python or javascript or any other language for that matter

#

You'd rather not create all the value in a single keyboard firmware

craggy wave
#

More like the percentage of people that can write decent code that does anything

#

People don't even care about understanding what they're doing

#

They just mash keys until they end up sweeping the most obvious problems under the rug

wide nymph
#

In all cases, this is the direction we're taking.

  1. Focus on value for the end-user
  2. Make analog input keyboard industry standard

Our firmware is our unique solution and isn't here to become the new standard nor the best firmware that exists nor compete with other open source projects. It's here to simple work exactly how we want it to work in the most efficient and effective way.

craggy wave
#

Oh, the analog thing

#

Yeah, I didn't really care much about it

#

I was slightly interested, but also curious about the switch actuation

wide nymph
#

Well, in this case, your ideal keyboard is a quality keyboard running QMK or another open-source firmware. Perhaps further down the road , they'll also have analog input hardware and make compatibility in their firmware.

craggy wave
#

Nah

wide nymph
#

We'd be actively encouraging and making it available for them to do so however.

craggy wave
#

QMK code sucks

#

So I'm not interested

wide nymph
#

But we won't do the firmware work for it. We don't want to do firmware work for others.

craggy wave
#

But also microcontrollers are slow

#

If I build something, it won't even have firmware

#

Just components

wide nymph
#

Alright, sounds like a DIY project then 😄

craggy wave
#

I still think not having the source open results in a lack of interest from the technically competent who would otherwise contribute

#

Same problem with the chronos 1.4

#

But in that case NDA is the limiting factor

wide nymph
#

That is true, and I don't deny that. We are just not at the point at which this is, for us, the best move forward.

Further down the road however, having more things established and our company/team grown, this might be a different story.

chilly oar
#

I love the keyboard but I think it lag behind on the software side. Because it is analog you can theoretical do some cool stuff with it that others don't, like per key actuation points. But there are still basic features missing, like macros.
And yes the most people don't care about all the fearures which products offers or don't use them quite often. But because the Wooting keyboards are in the premium class people buy them for a reason and I think if the keyboard would have more special features, more people would buy these because of that. For myself, I bought it because of the possibilities it has. But unfortunately I'm not experience enough to write my own windows driver to create a virtual device that reads the analog input from the keyboard and do all the stuff I want.

knotty night
#

What do you mean by macros? AutoFire and the like? It's a ton of work for a small OEM such as wooting to implement stuff like that, and there are plenty of 3rd-party apps out there that will do that kind of stuff

chilly oar
#

Like for moba, you press a single key but it fires multiple keystrokes.

knotty night
#

It's a pretty big project to make a GUI that supports those kinds of things

chilly oar
#

I know...

knotty night
#

Too many OEMs as it is with software that is incompatible with other devices - eg with the wooting s/w you would probably never be able to make a binding for Shift on wooting + click on mouse

chilly oar
#

It would be possible but of course very complex.

knotty night
#

So I just see it as a ton of work for something which is never going to satisfy all cases

chilly oar
#

It would be possible to add another interface for a mouse in the firmware for thinks like mouse clicks and so on.

#

But the normal way would be a virtual device for this kind of stuff.

knotty night
#

I don't see it as Wooting's responsibility to write software to mutate mouse input

#

Yeah but the problem is blocking the native functionality of the mouse in that instance

chilly oar
#

This can be something that "others" do by just using the anolog API but as I say at the moment I'm not capable of.

#

You don't have to block the normal mouse...

knotty night
#

If you wanted to make Shift+Click do something other than click you would

#

shift+click spams 1... you may well want to block the click

chilly oar
#

Yes, this would be even more complicated...

knotty night
#

Plus stuff like joystick. It's never gonna happen that you would be able to merge input from another device onto the wooting XI or DI controller

#

Or rather highly unlikely

#

If the wooting itself handles that in hardware, probably impossible

#

Plus the alternative is not for you to write code yourself to do it via the API - it's to use a 3rd-party app that's written

#

Such as UCR, Joystick Gremlin, Input Mapper, Joy2Key, etc, etc

chilly oar
#

So do UCR support macros?

knotty night
#

The new UCR does not currently support sending key combos (eg ALT+F1)

#

The old AHK version does

#

Well, the new version could, but we would need to write a custom plugin

#

in terms of things like rapid fire etc, I think there are some plugins for the old version, don't think we have them for the new one yet, but it would be simple to write

#

I think Joystick Gremlin has some nice macro stuff IIRC

chilly oar
#

But all the programs only emulate virtual joysticks right, not keyborads or mouses?

knotty night
#

UCR can control keyboard and mouse

#

it uses the Interception device driver for that

#

Can send as a physical keyboard or mouse - indistinguishable from the real thing as it is coming from the driver

chilly oar
#

And you can block the original control?

knotty night
#

Yes, it is blocked before the OS sees it

#

ultra-deep block, even blocks CTRL-ALT-DEL

chilly oar
#

And your driver hook up the USB driver right?

knotty night
#

eh?

chilly oar
#

You change the control flow how windows handles the USB Bus driver

knotty night
#

Interception is a filter driver, attaches to all keyboards and mice

chilly oar
#

I axpect you need driver signing for this.

knotty night
#

It's signed

chilly oar
#

So you pay for it?

knotty night
#

No, interception is not mine

#

I can get stuff signed tho if I need

#

Nefarius has a signing cert that he uses for ViGEm

#

If needs be, could probs raise the cash for my own - I raised the cash for the vJoy signing cert back in the day

#

We are thinking of trying to write our own version of Interception tho, there are limitations with it that the author wants $$$ to remove

#

He initially said he wanted $2,200 for a commercial license, then moved the goalposts on us

#

Then said he wanted $400/month via Patreon

#

For something he admitted he had already written...

chilly oar
#

A lot of money...

knotty night
#

We woulda paid the one-off cost quite happily

#

coulda crowdfunded that no problem

chilly oar
#

I expect you don't earn money from your UCR tool.

knotty night
#

But to ask people to pay him a salary for 6 months while he added functionality we didn't want, while holding out on the functionality we did want (Which he already had), we said FU

#

I will never ever charge for it

#

No interest in making it my living, it's a hobby

#

Besides, too much burden of expectation if you charge for something

#

Besides, it's already been financially beneficial - UCR was instrumental in allowing me to change career from IT to Automated Test

quiet root
#

anyone know how to decode the profile codes?

proud pumice
#

Decode?

quiet root
#

as in know what keys are assigned to what analog input etc

#

i mean the wootility somehow does it

proud pumice
#

It's a GUID. I think they have a database where they look up the assignments

quiet root
#

but wouldnt that mean to pmuch have a list of all possible combos?

proud pumice
#

It's a random generated ID so I don't think you can decode it

quiet root
#

oh ya it is so its online database based

little monolith
#

how can it be randomly generated

quiet root
#

it communicated with a server

#

and send the profile there

#

and then loads it from there aswell

little monolith
#

are you sure?

#

always thought of it as of string encoded raw profile data

quiet root
#

same but i checked with message analyzer

little monolith
#

interesting

quiet root
#

a raw encode would prob be better because it would work offline and save on cost

little monolith
#

yeah, that's how i would implement it

glacial horizon
#

It could also be misused though

#

Its probably for safety measures

little monolith
#

how tho

quiet root
#

well if i spoof the server that saves em and gives em back i can misuse it aswell

grizzled wolf
#

Wait what? Profiles requiring an internet connection?

quiet root
#

as far as i can tell yes

#

sharing the same profile multiple times gives a new code

grizzled wolf
#

That should be pretty easy to test.

quiet root
#

wouldnt know why else ud get different codes for exactly the same profile

#

and how it would know what settings to apply

#

sad that the electron code is all obfuscated

#

üöus i think they dont like me poking around in it anyway

grizzled wolf
#

You can poke around in the wootility to see what it does.

quiet root
#

oh we can? nice

#

so i guess weekend will be spend figuring out how it works

#

and prob writing my own

grizzled wolf
#

It's an Electron app which you can take appart

#

I'd be surprised if it needed to be online, that would be really stupid.

quiet root
#

k will test this real quick i guess

#

cant share without internet

#

and cant import

#

it checks the clipboard for a valid profile string

#

and only then it shows the import profile button

#

it checks using the internet

#

same for sharing

#

so ya the wootility requires internet

#

at least for profile sharing/importing

proud oasis
#

did anyone get the twooting working with the sdk yet?

proud pumice
#

nope

#

implemented a wrapper in c# but the is_connected function returns false everytime

proud oasis
#

so.. is_connected can be ignored?

strong siren
#

The source on GitHub doesn't search for the twooting PID

quiet root
#

^

proud pumice
#

yeah, guessed so

quiet root
#

just build a custom sdk dll with the twooting pid

#

that should work for now

strong siren
#

Does it work actually?

#

I might make an Aurora build with that change for gottz

quiet root
#

dont even need to build aurora they prob ship with the sdk dll

#

just replace dll with the custom one

strong siren
#

Yeah true

proud oasis
#

ah. struct hid_device_info* hid_info = hid_enumerate(WOOTING_ONE_VID, WOOTING_ONE_PID);

strong siren
#

Those are defined above

proud oasis
#

ye. obv changing the defines

strong siren
#

Tell me if you get it working with Aurora, I'm curious :D

proud oasis
#

hm. currently struggling to find the vid and pid

#

too many usb devices connected

#

vid is 03EB and pid is FF02

#

wooting one is 03EB:FF01

#

so it's just a increment 😄

#

it works

#

well.. with the node example it does

#

aurora does not want to start

#

niiiice it works

#

@strong siren

proud pumice
#

thanks gottz

proud oasis
#

np

#

tell me if you also need the analog sdk modified

proud pumice
#

so no need to download the c++ libraries..

#

nope, only RGB

glacial horizon
#

Ia aurora compatible with wooting two yet?

proud oasis
#

if you replace the wooting-rgb-sdk.dll with mine, then yes

strong siren
#

I'll see if I can add a layout for it

glacial horizon
#

Oh damn nice

#

Will try

strong siren
#

@proud oasis does it might up the numpad if you choose a kb with one?

proud oasis
#

lemme check

strong siren
glacial horizon
#

So the numpad defaults to red, huh?

#

Like in the video

proud oasis
#

nope does not do anything with the numpad

#

so the wrapper needs a bit of tweaking i assume

#

but it changes lighting if i press a numpad button

#

so it's listening to them.

#

different api i know.

strong siren
#

That might be as sdk problem

proud oasis
#

lemme dig through the code

strong siren
#

Maybe the size of data sent to the keyboard is getting capped because the one doesn't have nunpad

#

I don't think there are any limitations to that in Aurora

proud oasis
#

derp. i should stop hopping between channels

#
// Converts the array index to a memory location in the RGB buffers
static uint8_t get_safe_led_idex(uint8_t row, uint8_t column) {
    const uint8_t rgb_led_index[WOOTING_RGB_ROWS][WOOTING_RGB_COLS] = {
        { 0, NOLED, 11, 12, 23, 24, 36, 47, 85, 84, 49, 48, 59, 61, 73, 81, 80, 113, 114, 115, 116 },
        { 2, 1, 14, 13, 26, 25, 35, 38, 37, 87, 86, 95, 51, 63, 75, 72, 74, 96, 97, 98, 99 },
        { 3, 4, 15, 16, 27, 28, 39, 42, 40, 88, 89, 52, 53, 71, 76, 83, 77, 102, 103, 104, 100 },
        { 5, 6, 17, 18, 29, 30, 41, 46, 44, 90, 93, 54, 57, 65, NOLED, NOLED, NOLED, 105, 106, 107, NOLED },
        { 9, 8, 19, 20, 31, 34, 32, 45, 43, 91, 92, 55, NOLED, 66, NOLED, 78, NOLED, 108, 109, 110, 101 },
        { 10, 22, 21, NOLED, NOLED, NOLED, 33, NOLED, NOLED, NOLED, 94, 58, 67, 68, 70, 79, 82, NOLED, 111, 112, NOLED }
    };

    if (row < WOOTING_RGB_ROWS && column < WOOTING_RGB_COLS) {
        return rgb_led_index[row][column];
    } else {
        return NOLED;
    }
}
#

lookin good. the numpad is in

strong siren
#

Yeah discuss here

proud oasis
#

by default

#

lemme try using the node examples a bit more

proud pumice
#

dll works great

quiet root
proud oasis
#

what was the issue?

#

or just changed pid?

quiet root
#

implemented pmuch a fix so the dll works with both

#

just wanted to share precompiled dlls for analog and rgb

#

including source

#

also PRd it to the repos on GH

proud oasis
proud pumice
#

am i blind or is there no way to set the brightness of the leds with the rgb library?

proud oasis
#

0 0 0 = black

#

127 0 0 = dark red

#

so.. there goes your brightness

#
#define WOOTING_RGB_ROWS 6
#define WOOTING_RGB_COLS 21

interestingly this was already in

#

yet wooting_rgb_array_set_full does not change the numpad

quiet root
#

@proud pumice the libs are pretty minimalistic

proud oasis
#

ye. if you want proper brightness controls convert hsl to rgb instead

quiet root
#

might work on the sdks or smth over the weekend cause i actually dont want to reverse the wootility. id wish it would be opensource

proud oasis
#

me too

proud pumice
#

ah okay. thanks

proud oasis
#

you can extract the electron app but then you end up with a release build. so.. pretty unreadable javascript

#

me too was related to the wootility

quiet root
#

ya its obfuscated to shit

proud oasis
#

well not really obfuscated. just minified and optimized

proud pumice
#

setting the brightness works well but seems pretty inconvenient

quiet root
#

thats pmuch obfuscated

proud pumice
#

but better than nothing. 😄

quiet root
#

in js obfusctaed is almost the same as minfying and optimizing

#

looks the same and reads the same

#

i dont really see a difference to actual obfuscated code

proud oasis
#

variable names got replaced with the alphabet (ordered by frequence)

#

stuff like that is just part of the compile toolchain of webpack

quiet root
#

and part of obfuscation

proud oasis
#

so.. they didn't do that on purpose. it's just part of the design of the toolchain

quiet root
#

just saying that the toolchain pmuch obfuscates by default

proud oasis
#

well it reduces file size

quiet root
#

just make it use random 6 character names instead of single letters

proud oasis
#

so.. less server bandwidth for shipping updates

#

i kinda see this from an enterprise point of view

quiet root
#

i see this from an "the wootility doesnt really benefit from 20kb saved" point of view

#

cant imagine it saving that much space

proud oasis
#

it has been proven that gzip pretty much gives the same benefit as minification

#

so.. it actually does not matter to minify as long as stuff is gzipped

#

but people don't know.

#

also if you call .toString on functions they will return the actual code. wich means: it's also stored in ram

quiet root
#

one day we get a cpp based wootility

proud oasis
#

so minification can reduce ram usage

#

compiling stuff down so it shows up as "native code" is also possible. but that requires some v8 tweaking in electron.

#

stack tracing that is impossible though

#

i don't get it

#

in wooting-usb.h there is #define RGB_RAW_BUFFER_SIZE 96 and it creates four rgb buffers that get initialized with that size. we have 6 rows and 21 cols.. should be sufficient right?

#

oh it isn't..

#

the colors_buffer is too small

#

or is it? i have no clue

#

@strong siren the problem is not aurora. it's clearly the sdk

#

(that the numpad does not get colors)

#

tampered a bit with the raw usb packages. it seems like the firmware restricts it

quiet root
#

@proud oasis u did see the magic table at the top of wooting-rgb-sdk.c right?

proud oasis
#

ye

#

it includes the numpad

#

here pretty so you can clearly see the numpad

quiet root
#

shit u right

#

maybe remove the checks

proud oasis
#

oooh where is that from

quiet root
#

or well update them to new numbers

#

just update all checks with led index

#

or well the result of get_safe_led_index

proud oasis
#

ooh i see now

quiet root
#

thats why it wont work

proud oasis
#

probably wee need a fifth buffer for this

quiet root
#

yep we do

proud oasis
#

will try to add it

quiet root
#

dont forget to add a new check for out of bounds tho just in case

proud oasis
#

ye

strong siren
proud oasis
#

good find

strong siren
#

wrong channel i guess :S

quiet root
#

dont forget to pr it if it works gott

proud oasis
#

ye this looks nice

#

also the APP button should be FN

#

but apart from that it's great

quiet root
#

same

strong siren
#

ah i forgot that

quiet root
#

hyped for the weekend helping out jeroen with some development work on the sdks

proud oasis
#

apart from that, all other layouts like DE ISO etc. can also be applied

#

standard layout

quiet root
#

well imma go to sleep so i got enough power for the weekend infront of me

proud oasis
#

okidoki

#

have a good sleep! hopefully i'll have pinged you when you wake up

quiet root
#

would be cool

#

hf

#

almost forgot

#

dont forget to only send the numpad buffer for w2

#

w1 prob wont like it

proud oasis
#

ye. already writing TODO comments for that

quiet root
#

well then see ya

proud oasis
#

night

proud pumice
#

just wondering. screen mode and pause keys are in the wrong order, aren't they?

proud oasis
#

ye. compared to usual DE ISO it's swapped

#

ships with these keys swapped

proud oasis
#

the wooting ships with them swapped

proud pumice
#

oh. i see. thanks

#

but what's the icon on it?

proud oasis
#

you can change brightness of the rgb with it

#

it gets brighter if you fn pause

#

and darker if you fn print

proud pumice
#

doesn't work for me

proud oasis
#

it's moderate steps

#

hold down fn print for a while

proud pumice
#

nope, no effect

proud oasis
#

works for me

proud pumice
#

fixed it by disconnecting the keyboard

#

but the keycap is wrong

proud oasis
#

we should certainly address that to the wooting guys

#

i guess it can be fixed with a firmware update

proud pumice
#

yeah, think so. they fixed the multimedia shortcuts aswell

proud oasis
#

ye they even work without the wootility

#

ooooh interesting

#

the fifth buffer seems to be the right one

#

it's already in the RGB_PARTS enum

#

HOLY SHIT! IT WORKS!!

proud pumice
#

what are you working on?

proud oasis
#

rgb sdk

proud pumice
#

oh, the numpad thingy?

proud oasis
#

ye

#

just fixed it as you can see

proud pumice
#

very nice

#

good job!

proud oasis
#

now i need to make sure wooting ones don't get the fifth rgb buffer

#

i assume this sdk does not work with multiple wootings anyways right?

proud pumice
#

don't think so

proud oasis
#

anyone with a wooting one here and able to test the dll?

#

works with the twooting just fine

proud pumice
#

thanks

proud pumice
#

my keyboard is buggy again. "save to keyboard" just kills it and i don't know why

proud oasis
#

@quiet root i guess i'm done

boreal nest
#

Is here a good place to report a (possible) API-related firmware bug in the Two? wooting_rgb_direct_set_key has incorrect handling for key codes >= 96 (numpad, A1/2/3, etc). The API call itself works fine, however the keyboard modifies the wrong key. Numlock and numpad / modify F10; numpad *, -, +, enter, 7, 8, and 9 modify F9; numpad 4, 5, 6, 1, 2, 3, 0, dot, and A1 do nothing; and A2, A3, and FullsizeMode modify the equals key. Using the buffered version via wooting_rgb_array_change_single (and related) work as expected, it's only the direct calls that have the issue. Not sure if it's my end or the keyboard, though.

wide nymph
#

Here is good

boreal nest
#

Thanks

quiet root
#

@proud oasis maybe check what emonas said out

slate bridge
#

@proud oasis It works for me.

#

nvm. I don't have a Wooting One, but I can confirm it works on the Wooting Two over here.

proud oasis
#

@boreal nest were you using my current implementation? i did fix a bug that didn't drop rgb calls to the numpad section on wooting ones

boreal nest
#

Fortunately (or unfortunately), the direct calls have no such protection. They just verify the row/col are valid against an internal table (that has the numpad) and passes the key code

#

The API call goes through fine, and the table appears valid

#

But yes I am using your current version. Setting keys >=96 works fine if you using the wooting_rgb_array_change_single (and similar) buffered calls works fine, it's just the wooting_rgb_direct_set_key and wooting_rgb_direct_reset_key calls that don't appear to handle them

proud oasis
#

will fix. hold on

#

agreed @boreal nest they don't call get_safe_led_idex(row, column);

boreal nest
#

The buffered ones do not, yeah. But the direct ones do

#

wooting_usb_send_feature(WOOTING_SINGLE_COLOR_COMMAND, get_safe_led_index(row, column), red, green, blue) is effectively all wooting_rgb_direct_set_key does (ignoring special handling of ANSI vs ISO left shift/return and sanity checks)

#

So wooting_usb_send_feature(WOOTING_SINGLE_COLOR_COMMAND, 96, 255, 255, 255) is the call for changing numlock to white, however it's actually changing F10

proud oasis
#

wait

#

you are calling the usb api directly?

#

so.. how do you expect sdk protection then 😄

boreal nest
#

No, I'm using wooting_rgb_direct_set_key

#

But calling the usb api directly with safe values produces the same result

#

For testing where the issue is I was cutting out middlemen to try to narrow it down

proud oasis
#

you on ansi?

boreal nest
#

Yeah

proud oasis
#

so i assume i'd just need to make get_safe_led_idex return NOLED on >= 96 if it's a wooting one?

#

wait.. i'm confused

boreal nest
#

Yes, that would be good for them. But I'm on a Two :P

proud oasis
#

you have a wooting one or a two

#

ok

#

so two ansi

boreal nest
#

Yep. As far as I can tell the call is completely valid

proud oasis
#

hm. sorry i got to go

boreal nest
#

No worries

proud oasis
#

maybe @quiet root can figure this out in my absence

#

going to go to a article 13 demo now

#

has prio

boreal nest
#

Definitely

#

Good luck

quiet root
#

will figure that out once the miss is done shopping

#

shouldnt take too long

boreal nest
#

Take your time

knotty night
quiet root
#

no gui?

#

dont have a wooting one and dont wanna try tricking it into thinking i got one

boreal nest
#

I have a Wooting Two, though lol

quiet root
#

ohh

proud oasis
#

he has a wooting two with ansi layout

knotty night
#

ie column 1, row 2, is Q on QWERTY, and A on AZERTY?

quiet root
#

prob as iso thing

#

the scan index is completely different from the array of safe keys

proud oasis
#

america.. fuck yeah..

knotty night
#

Yeah, it's not true scan code

#

I am just looking now into maybe building some helper functions or something

#

I have some handy code surrounding this

quiet root
#

i looped through all numbers from 0 to 116 and it got wonky in the end

proud oasis
#

96 is numlock btw

quiet root
#

it doesnt set numlock tho

#

it sets f10

proud oasis
#

and according to @boreal nest it will trigger a differnent key's rgb

quiet root
#

for me at least

knotty night
#

Are you ISO or ANSI?

quiet root
#

im iso

proud oasis
#

iso

#

for me it's fine

quiet root
#

when i tried setting 96 it also set f10

knotty night
#

So what, maybe the matrix is ANSI?

#

or rather that doc

proud oasis
#

maybe i just failed to reproduce the issue yet

boreal nest
#

96/97 set f10, 98-104 sets f9, 105-113 does nothing, and 114-116 sets equals on my end

#

0-95 work as expected (skipping NO_LED slots)

knotty night
#

Having a look at how it reports to the keyboard driver now

#

it seems to send perfectly normal scancodes

#

A1-3 and Mode send nothing

proud oasis
#

just sounds to me as if it addresses the second led controller and not the third one

#

(the twooting has three if i'm not mistaken)

#

going to play with it here now.. i'm not on my pc but i have my twooting with me

knotty night
#

Does anyone have an ANSI keyboard? even a non-wooting

#

Can you tell me what your scancode for \ | is ?

proud oasis
#

it's the #' key

#

they lack the <>| key

#

191

#

and they don't have 226

knotty night
#

that's dec?

proud oasis
#

ye

knotty night
#

the one to the right of Left shift?

proud oasis
#

0xBF and 0xE2

#

0xE2 is to the right of left shift

#

they don't have that on ansi

#

it's a non existent key

knotty night
#

Sorry, my bad

proud oasis
#

and 0xBF is on a different place for them

knotty night
#

the one above enter

proud oasis
#

they have it below the backspace key and above return

knotty night
#

I was talking about where it is on mine 😛

proud oasis
#

iso has it on the lower left of return

knotty night
#

Lower left of return on UK ISO is # ~

proud oasis
#

ye. that's the key

#

on ansi it's just above return

#

on the upper right

#

directly next to the delete key

knotty night
#

I am wondering about \ |, which on UK ISO is right of LShift, on US ANSI is above enter

proud oasis
#

that's not existing

#

they don't have that key at all

knotty night
#

Wondering if SC is consistent across ANSI/ISO

proud oasis
#

0xE2

#

it's a pain to use the german layout on ansi btw cause then you cannot type < > and |

knotty night
#

That does not seem to match anything

proud oasis
#

well that's the scan code

#

isn't that what you wanted?

knotty night
#

yeah, thanks, it just confuses me a bit

#

E2 is a very high scancode and not on any list I can find

#

Mind you, what I am getting for that key doesn't match up for any table I can find 😛

proud oasis
#

try 0x3c

quiet root
#

i actually have a new problem

#

just compiled a fresh copy of the rgb sdk

#

now i cant dllimport in c# anymore

#

noice

proud oasis
#

sounds weird

quiet root
#

it acts as if i got some name mangling going on

proud oasis
#

btw you have push perm on my fork

quiet root
#

because it claims wooting_rgb_reset isnt a valid entry point

proud oasis
#

would just add up into the pull request

knotty night
#

Is there an API endpoint to detect ANSI or ISO?

#

I don't see anything

proud oasis
#

would be interesting to know if the serial number could give some insight in regards to that

#

if so, it could be read from it

knotty night
#

I don't see how this whole API is feasible without it

#

unless you load an ANSI or an ISO dll or something

proud oasis
#

it does some stuff i don't get though

knotty night
#

That looks like it is responding to keys?

proud oasis
#
#define LED_LEFT_SHIFT_ANSI 9
#define LED_LEFT_SHIFT_ISO 7
#define LED_ENTER_ANSI 65
#define LED_ENTER_ISO 62
knotty night
#

I don't see that it would be feasible, given the current API, to accurately work out the coordinates of the keys that vary

#

Yeah, but you would have to wait for one of those keys to be pressed surely to get a clue as to what kind of keyboard it was

boreal nest
#

<_< >_> there's a private API call for getting the device configuration, which has the keyboard layout. Nothing on the public side, though. Doubt something like the S/N would contain that since it's configurable

knotty night
#

OK, sounds like a goer then

boreal nest
#

... I got way too curious and went digging. Can't help myself sometimes

knotty night
#

So we need a layer of abstraction that applies different scancode <-> row/column or something

#

Even when the new analog API appears, you are always going to need to be able to convert

boreal nest
#

Wouldn't that be handled in the firmware? The key codes < 96 function fine. Key codes >= 96 work fine on the Two when not using the direct set/reset calls

knotty night
#

Are you talking about the wooting "scan" codes?

#

I mean true scan code

boreal nest
#

Ahh

knotty night
#

It's very difficult to interop with the wooting with no easy way to translate from between SC and wooting-specific codes

#

It also allows you a way to get a proper localized name for the key

#

you can use WinAPI to get layout-specific name for that key

#

ScanCode input has a code 1..255 plus an "extended" bit

proud oasis
#

browsers get the same data right?

knotty night
#

convention generally is to pack that down to one number 1..512 with >255 signifying extended flag set

#

(If you want a single number unique ID for each key that is)

#

So IMHO, the analog API should be written with ScanCode as the UID for each key, and no mention of localized key names for a given code

#

that's decided at run-time

#

@proud oasis Heavily depends on mechanism used within browser I spose, but It's probably possible

proud oasis
#

@knotty night browsers are strainge

#

i clear on key down

#

the codes seem to match

#

' appears with the name "backslash" to me

#

and < > | as "IntlBackslash"

knotty night
#

I am getting no joy with the analog SDK 😦

#

DLLs seem to be loading, but no data

proud oasis
#

i didn't dig into the analog sdk yet. i assume it has the same issue as the rgb sdk had before we touched it

knotty night
#

wooting_kb_connected returning false

#

for rgb and analog

proud oasis
#

ye cause the wooting one and the wooting two have different product id's in usb

knotty night
#

via the C# wrapper anyway

proud oasis
#

look at this

#

this is what i had to do to get rgb working for the twooting

knotty night
#

This looks like it should be common to both?

#

ah no

#

completely separate repos

proud oasis
#

rgb and analog are separate ye.

knotty night
#

could I get a built copy of your dll tho?

proud oasis
#

lemme took a quick look at the analog sdk

knotty night
#

wanna see if my code is happy with it

proud oasis
knotty night
#

ta

proud oasis
#

i'm even using it in aurora right now

knotty night
#

what is that, x86 or x64?

proud oasis
#

64

#

if you need 32, i could just remote into my pc and build it

knotty night
#

it verks!

proud oasis
#

neatzo

knotty night
#

arise my pretty!

#

OK, so they didn't update the SDK for release then, great

proud oasis
#

luckily it's open source

#

oh and i really appreciate the work they put into the wootility right now

knotty night
#

I don't really do unmanaged 😦

proud oasis
#

before i learned how to use assembler in c, i wrote 8086 machine code into memory and flagged it executable. this.. in my opinion is unmanaged code

knotty night
#

Well it's not that deep, but it's still outside my comfort zone

proud oasis
#

what if i tell you that i love javascript

knotty night
#

JS is a cool language

quiet root
#

so is the keycode thing fixed already?

knotty night
#

it's staggering what you can do with it these days

proud oasis
#

ye.. some node.. some ffi.. voila.. c libraries in js

#

and creating native c++ modules for nodejs is easy too

knotty night
#

Well it seems that the analog SDK is not compatible with the W2, so I am kind of roadblocked

proud oasis
#

i think @quiet root touched it

knotty night
#

no point messing with scancodes if I can't read keys 😛

proud oasis
#

maybe he has a dll

#

ye. there is the twooting fix

quiet root
#

do have a 64bit dll

knotty night
#

would rather x86 if you have it

quiet root
#

sec

knotty night
#

but i'll take either in a pinch

quiet root
knotty night
#

cheers man

proud oasis
#

hm. looking through the code.. it should work just fine

quiet root
#

what?

proud oasis
#

the numpad

knotty night
#

Result! thank you

quiet root
#

when i just press through it fucks up at 96

#

exactly what was described by Emonas

#

the dll is not different from ur source except that it exports the wooting_usb functions aswell so i can use wooting_usb_send_feature

#

which is whats broken

knotty night
#

Yeah, similar for me, seemed to be at 98 or something?

quiet root
#

96 which should be numpad changes f10

#

and so on

proud oasis
#

can you drop a wooting_usb_send_feature line here?

quiet root
#

wooting_usb_send_feature(30, 96, 255, 255, 255)

knotty night
#

oh yeah, 96 stays lit

#

but it lights up 97

#

then 98, nothing

proud oasis
#

96 should be numlock btw

#

so ye

quiet root
#

it basically tells the keyboard to light up a single key and keycode 96 which is the same as if u call set key direct with the row and column for numlock

proud oasis
#

it's a firmware issue

quiet root
#

does it work with the normal wooting_rgb functions?

#

as in setting just the numlock with row and column?

proud oasis
#

yep

#

i tried the nodejs examples and extended them for the numpad

quiet root
#

it works?

proud oasis
#

and aurora works fine too

#

yep it works

quiet root
#

can u check with c#?

proud oasis
#

lemme install visual studio here

quiet root
knotty night
#

Are you trying to address rgb via "scan" code?

#

or via row/column?

proud oasis
knotty night
#

one value - code surely?

quiet root
#

@knotty night well both are pmuch the same the direct key set gets the 96 from the magic table by row and column

#

so its pmuch the same as passing 96 directly

knotty night
#

well the analog test in the C# wrapper manages to set the colour of NumLock

#

row 1, col 17 for me

boreal nest
#

wooting_rgb_array_change_single(1, 17, 0, 0, 0); wooting_rgb_array_update_keyboard(); works fine for changing numlock (96)
wooting_rgb_direct_set_key(1, 17, 0, 0, 0); however does not, and instead changes 0,11 (48, which is F10)

proud oasis
#

fact i don't like about microsofts visual studio installer: the bandwidth is never maxed out

#

just fyi in case anyone want to try aurora with twooting support.

proud oasis
#

this is col / row

#

but ye. i'm going to use the codes instead of the x/y

#

just fyi

#

mklink wooting-rgb-sdk64.dll c:\safe\twooting\wooting-rgb-sdk\windows\x64\Release\wooting-rgb-sdk64.dll

#

this way i can just compile and re run the tester

proud oasis
#

just fyi


    const uint8_t rgb_led_index[WOOTING_RGB_ROWS][WOOTING_RGB_COLS] = {
        {  0, NOLED, 11,    12,    23,    24, 36,    47,    85,    84, 49, 48,    59, 61,    73,    81,    80,   113, 114, 115,   116 },
        {  2,     1, 14,    13,    26,    25, 35,    38,    37,    87, 86, 95,    51, 63,    75,    72,    74,    96,  97,  98,    99 },
        {  3,     4, 15,    16,    27,    28, 39,    42,    40,    88, 89, 52,    53, 71,    76,    83,    77,   102, 103, 104,   100 },
        {  5,     6, 17,    18,    29,    30, 41,    46,    44,    90, 93, 54,    57, 65, NOLED, NOLED, NOLED,   105, 106, 107, NOLED },
        {  9,     8, 19,    20,    31,    34, 32,    45,    43,    91, 92, 55, NOLED, 66, NOLED,    78, NOLED,   108, 109, 110,   101 },
        { 10,    22, 21, NOLED, NOLED, NOLED, 33, NOLED, NOLED, NOLED, 94, 58,    67, 68,    70,    79,    82, NOLED, 111, 112, NOLED }
    };
#

to me it makes sense now that the iso has left shift on 9 and the ansi on 7. (pcb wiring to the led controller)

#

as well as the return button difference

knotty night
#

@proud oasis You got an x86 build of that rgb sdk?

proud oasis
#

i can just build it. hold on

knotty night
#

cheers

proud oasis
#

also exporting the native usb funcs

#
typedef enum RGB_PARTS {
    PART0,
    PART1,
    PART2,
    PART3,
    PART4
} RGB_PARTS;

WOOTINGRGBSDK_API void wooting_usb_set_disconnected_cb(void_cb cb);
WOOTINGRGBSDK_API void wooting_usb_disconnect(bool trigger_cb);
WOOTINGRGBSDK_API bool wooting_usb_find_keyboard();
WOOTINGRGBSDK_API bool wooting_usb_send_buffer(RGB_PARTS part_number, uint8_t rgb_buffer[]);
WOOTINGRGBSDK_API bool wooting_usb_send_feature(uint8_t commandId, uint8_t parameter0, uint8_t parameter1, uint8_t parameter2, uint8_t parameter3);

WOOTINGRGBSDK_API bool wooting_rgb_kbd_connected(void);
WOOTINGRGBSDK_API void wooting_rgb_set_disconnected_cb(void_cb cb);
WOOTINGRGBSDK_API bool wooting_rgb_reset(void);
WOOTINGRGBSDK_API bool wooting_rgb_direct_set_key(uint8_t row, uint8_t column, uint8_t red, uint8_t green, uint8_t blue);
WOOTINGRGBSDK_API bool wooting_rgb_direct_reset_key(uint8_t row, uint8_t column);
WOOTINGRGBSDK_API bool wooting_rgb_array_update_keyboard(void);
WOOTINGRGBSDK_API void wooting_rgb_array_auto_update(bool auto_update);
WOOTINGRGBSDK_API bool wooting_rgb_array_set_single(uint8_t row, uint8_t column, uint8_t red, uint8_t green, uint8_t blue);
WOOTINGRGBSDK_API bool wooting_rgb_array_set_full(const uint8_t *colors_buffer);
knotty night
#

I seemed to need to add , CallingConvention = CallingConvention.Cdecl to my imports which I didn't before

#

but it's all good, that's what I normally have to do

proud oasis
#

how comes you do 32 bit?

#

just wondering

knotty night
#

works with x86 or x64

proud oasis
grizzled wolf
#

It lit up like a Christmas tree, isn't that what it's supposed to be doing?

proud oasis
#

na

#
using System;
using System.Runtime.InteropServices;
using System.Threading;

namespace ConsoleApp1
{
    class Program
    {
        [DllImport("wooting-rgb-sdk64.dll", CharSet = CharSet.Unicode)]
        public static extern bool wooting_usb_send_feature(byte commandId, byte parameter0, byte parameter1,
            int parameter2, int parameter3);

        [DllImport("wooting-rgb-sdk64.dll", CharSet = CharSet.Unicode)]
        public static extern void wooting_usb_disconnect(bool triggerCb);

        static void Main(string[] args)
        {
            byte x = 0;

            while (x <= 116)
            {
                Console.Clear();
                Console.WriteLine("Setting " + x + " to white");
                wooting_usb_send_feature(30, x, 255, 255, 255);
                Thread.Sleep(100);
                wooting_usb_send_feature(30, x, 0, 0, 0);
                x++;  
            }

            wooting_usb_send_feature(32, 0, 0, 0, 0);
            wooting_usb_disconnect(false);
        }
    }
}

thanks to @quiet root for writing this test code

#

it essentially just iterates through all the id's

#

that's passing into this:

bool wooting_usb_send_feature(uint8_t commandId, uint8_t parameter0, uint8_t parameter1, uint8_t parameter2, uint8_t parameter3) {
    if (!wooting_usb_find_keyboard()) {
        return false;
    }

    uint8_t report_buffer[WOOTING_COMMAND_SIZE];

    report_buffer[0] = 0; // HID report index (unused)
    report_buffer[1] = 0xD0; // Magic word
    report_buffer[2] = 0xDA; // Magic word
    report_buffer[3] = commandId;
    report_buffer[4] = parameter3;
    report_buffer[5] = parameter2;
    report_buffer[6] = parameter1;
    report_buffer[7] = parameter0;

    if (hid_send_feature_report(keyboard_handle, report_buffer, WOOTING_COMMAND_SIZE) == WOOTING_COMMAND_SIZE) {
        return true;
    }
    else {
        wooting_usb_disconnect(true);
        return false;
    }
}
#

hmmmm

#

idea

#

ugly though

proud oasis
#
bool wooting_usb_send_feature(uint8_t commandId, uint8_t parameter0, uint8_t parameter1, uint8_t parameter2, uint8_t parameter3) {
    if (!wooting_usb_find_keyboard()) {
        return false;
    }

    uint8_t report_buffer[WOOTING_COMMAND_SIZE +3];
    bool done;

    report_buffer[0] = 0; // HID report index (unused)
    report_buffer[1] = 0xD0; // Magic word
    report_buffer[2] = 0xDA; // Magic word

    if (commandId == WOOTING_SINGLE_COLOR_COMMAND && parameter0 >= 96) {
        report_buffer[3] = WOOTING_RAW_COLORS_REPORT;
        report_buffer[4] = 2; // Slave nr
        report_buffer[5] = parameter0 - 96; // Reg start address
        report_buffer[6] = parameter1;
        report_buffer[7] = parameter2;
        report_buffer[8] = parameter3;
        uint16_t crc = getCrc16ccitt(((uint8_t*)&report_buffer) +4, 5);
        report_buffer[9] = (uint8_t)crc;
        report_buffer[10] = crc >> 8;
        printf("%u is part of the numpad section\n", parameter0);
        printf("cmd: %u\n", report_buffer[3]);
        printf("slave number: %u\n", report_buffer[4]);
        printf("register offset: %u\n", report_buffer[5]);
        printf("red: %u\n", report_buffer[6]);
        printf("green: %u\n", report_buffer[7]);
        printf("blue: %u\n", report_buffer[8]);
        printf("crc: %u\n", report_buffer[9] + (report_buffer[10] << 8));
        done = hid_send_feature_report(keyboard_handle, report_buffer, WOOTING_COMMAND_SIZE +3) == WOOTING_COMMAND_SIZE +3;
    }
    else {
        report_buffer[3] = commandId;
        report_buffer[4] = parameter3;
        report_buffer[5] = parameter2;
        report_buffer[6] = parameter1;
        report_buffer[7] = parameter0;
        done = hid_send_feature_report(keyboard_handle, report_buffer, WOOTING_COMMAND_SIZE) == WOOTING_COMMAND_SIZE;
    }


    if (done) {
        return true;
    }
    else {
        wooting_usb_disconnect(true);
        return false;
    }
}

this should work but does not

#

idea @knotty night?

#

ooooooh i see why

#

the buffers are actually much more complex than i thought. derp.

#

12 reds in a row. then nothingness to fill up to 16. then 12 greens in a row.. and so on

#

i should probably stop trying to break my keyboard

knotty night
#

I have the basics down of a wooting wrapper for AutoHotkey

#

C# wrapper with CLR interface for AHK

#
Wooting := new WootingWrapper()

keyWatcher := Wooting.Instance.SubscribeKey(GetKeySC("1"), Func("AxisChanged"))
return

AxisChanged(value){
    ToolTip % value
}

1::
    return
#

Subscribe to 1 key analog value, and block it

#

Have not got all keys added to the SC->Row/Col lookup table yet

proud oasis
#

@boreal nest @quiet root @knotty night @proud pumice i'm sorry to say that.. but i cannot abuse the buffers to work with less than 12 buttons at once.. so i guess it's better to just use the buffers for now.
this issue has to be fixed in firmware unless it is a different usb api command

wooting_usb_send_feature(WOOTING_SINGLE_COLOR_COMMAND, 96, 255, 255, 255);
to
wooting_usb_send_feature(WOOTING_SINGLE_COLOR_COMMAND, 116, 255, 255, 255);
does not work properly.

wooting_usb_send_feature(WOOTING_SINGLE_RESET_COMMAND, 0, 0, 0, 96);
to
wooting_usb_send_feature(WOOTING_SINGLE_RESET_COMMAND, 0, 0, 0, 116);
don't work either

proud pumice
#

no worries. thanks for your efforts, you did a great job there 😃

proud oasis
knotty night
#

I have the basics of the AHK wrapper down.
Full control over keys - get events for update of analog values from keys, turn on/off blocking of the digital key, application-specific blocking of the digital key

#
#include Lib\WootingWrapper.AHK

Wooting := new WootingWrapper()

last := A_TickCount
keyWatcher := Wooting.SubscribeKey("A"    ; Subscribe to the A key - use the AHK key name
        , Func("AxisChanged")             ; Call the Function "AxisChanged" when it changes
        , "ahk_class Notepad")            ; Key Blocking is only active in Notepad
    .SetBlock(1)                        ; Turn Key Blocking on

return

; Toggle disabling of key, even if in Notepad
F12::
    keyWatcher.ToggleBlock()            ; Toggle blocking
    return

; Called and passed analog value when key changes state
AxisChanged(value){
    static threshold := 100
    static oldVal := 0
    static lastEvent := "NONE"
    if (oldVal == 0 && value){
        ; Press
        lastEvent := "INITIAL PRESS"
    }
    if (oldval < threshold && value >= threshold){
        ; Press past 50 %
        lastEvent := "PRESS PAST THRESH"
    } else if (oldval >= threshold && value < threshold){
        ; Release past 50 %
        lastEvent := "RELEASE PAST THRESH"
    }
    if (oldVal && value == 0){
        ; Full release
        lastEvent := "FULL RELEASE"
    }
    ToolTip % "Axis Changed. Old Value: " oldVal ", New Value: " value ", Last Event: " lastEvent
    
    oldVal := value
}

^Esc::
    ExitApp
#

Demo for the A key
AxisChanged function fired when analog value changes
A key blocked while in Notepad
Turn on/off blocking with F12

boreal nest
#

Yeah, I was thinking it was a firmware issue but I wanted to rule other things out first. The buffers are probably a better choice when driving a lot of keys, but I ran into another oddity. Open Wootility -> change Escape to, for example, 184,64,0 (a sort of bronze) -> use wooting_rgb_direct_set_key to change key 0,0 (Escape) to 184,64,0. It changes to a brighter yellow color, inconsistent with the color the Wootility sets. wooting_rgb_array_change_single exhibits the same inconsistent behavor, but it's easier to demo with a single key

faint vapor
#

@boreal nest remember that if you have some RGB FX active that you only get a brightness of 0 - 30% kappa

boreal nest
#

The API disables (or well, pauses) any running FX that's set. I didn't have one enabled, anyway. Lemme get a comparison pic for it, one sec

#

... if I can get this camera to not wash out the colors

#

Surrounding keys are set to 192,67,0 via the Wootility while that S is set to 192,67,0 via wooting_rgb_direct_set_key

proud oasis
#

i noticed that in aurora too. the led's loose dynamic as brighter they get. we should either do some wizzardry to the wootility code to figure this out or just wait

#

rgb values are pretty much not linear

boreal nest
#

It must be something about how the firmware handles these commands as the USB calls the Wootility uses to change the values works fine

#

I've dug through the Wootility already out of curiousity of how it all functions. Implementing the USB calls it uses, I tested changing LEDs and they work the same as from the Wootility with no special handling. Going to use some pseudo-code this time... profileColorMap = getCurrentProfileColorMap(); profileColorMap[0..2] = [ 192, 67, 0 ] /* set Escape explicitly */ setProfileColorMap(profileColorMap); and the LEDs were the proper colors. Putting that color map through wooting_rgb_array_* calls yields the inconsistent colors

#

Specifically using the non-permanent calls the profile editor uses to preview it on the keyboard (so the normal wooting_rgb_reset() call undoes any changes made)

#

Not really sure I want to elaborate, since they must not be public for a reason (though the ability to read the current color map would be useful for the public one in my opinion.. have something to fill the wooting_rgb_array_* buffers with) but yeah.. the inconsistency seems limited to the calls the public API uses

quiet root
#

imo the sdk should be able todo the same as the wootility

proud oasis
#

would be useful to also read A1, A2, A3 and the digital profile presence

#

like.. what mode the keyboard is currently on

#

reading the original color map could also be useful for tools like aurora. this way the original color scheme could be used as base layer and then any modifications you do based on scripting would apply on top

#

last night i also came up with an idea that would allow us to have some kind of rgb / analog proxy so multiple applications could use the sdk

#

essentially checking a mutex to see if a sdk daemon is running and if it's not, the sdk will perform direct usb communication

#

so people don't necessarily need to install the daemon

boreal nest
#

To a point I agree the API should be able to do the same as the Wootility. Things like updating the firmware or what appears to be a way to change the serial number, on the other hand, should definitely stay far, far away from any public API

quiet root
#

ya

#

i meant more like the profile and rgb

proud oasis
#

reading colors, reading profiles, applying profiles

#

well.. applying could stay in the wootility since it does a good job for that i think

boreal nest
#

I'd be slightly weary of having the proper profile saving calls public as well. Don't need someone going overboard and wiping the saved profiles from the keyboard by accident

proud oasis
#

hm. reading could also result in games banning analog usage

#

i kinda flex my thoughts there a bit.. don't take that for granted

#

as of right now, games and stuff that implements the sdk needs to update the sdk when a new peripheral from wooting arrives

#

that's bad i think

#

razer for example just uses a centralized daemon that does the usb stuff and the api just connects to that instead

#

would also result in less usb api calls since stuff could be grouped

boreal nest
#

Not much that can be done about that. Suppose you could read what the name of the HID device rather than PID/VID but I'd expect that to be far less reliable

#

Since the Two, at least, reports a name of "Wooting WootingTwo"

proud oasis
#

hm. weird name

boreal nest
#

Eh, vendor name followed by product name

#

You'd still need to update for new devices that way, come to think of it. Nevermind heh

proud oasis
#

if the usb api would be separated into a daemon it could also easily be patches for issues

#

while the sdk itself cannot

#

there are always devs out there who don't update stuff

#

when extracting the usb stuff into a separate daemon the question arises how to do the ipc

boreal nest
#

Right now my main concern is that the public API uses an RGB call that specifically pauses a lot of background tasks running on the keyboard (RGB FX, honoring the Wootility's RGB-related calls, etc) which I'd imagine is to cut down on processor load while it's being driven manually. I don't know what sort of side effects heat/load-wise there would be to driving the LEDs via the Wootility's API since they don't pause the RGB FX

#

But as it is right now, the Wootility's calls are more accurate when it comes to colors... so it would be the obvious target for devs to use

proud oasis
#

even though it's just single key and not using the buffers

quiet root
#

and if u close it they are still paused

proud oasis
#

let it run until the end

#

it resets

boreal nest
#

Sending COLOR_INIT_COMMAND does the pausing. You must follow with RESET_ALL_COMMAND to unpause

proud oasis
#

but ye. as soon as the application using the sdk will crash, it will not recover back to the unmodified state

#

unless you do teh reset

#

color_init_command? i don't send that

boreal nest
#

And the firmware straight-up crashes if you try to use direct_* or array_* calls before calling init

#

wooting_usb_find_keyboard automatically calls it as part of the initial discovery

#

wooting_usb_send_feature(WOOTING_COLOR_INIT_COMMAND, 0, 0, 0, 0);

proud oasis
#

i also had a weird crash yesterday that rendered the xinput useless. it just didn't do anything until i rebooted. even after replugging usb

#
        static void Main(string[] args) {

            if (!wooting_usb_find_keyboard()) {
                Console.WriteLine("no wooting keyboard detected.");
                Console.ReadKey();
                return;
            }

            byte x = 0;

            while (x <= 116) {
                Console.Clear();
                Console.WriteLine("switching key id " + x);
                wooting_usb_send_feature(30, x, 255, 255, 255);
                Thread.Sleep(100);
                wooting_usb_send_feature(30, x, 255, 0, 255);
                if (x > 0) wooting_usb_send_feature(31, 0, 0, 0, x -1);
                x++;  
            }

            wooting_usb_send_feature(32, 0, 0, 0, 0);
            wooting_usb_disconnect(false);
        }
#

this is the console app

#

no color init command

boreal nest
#

Yeah it's done as part of wooting_usb_find_keyboard

quiet root
#

why a sleep tho why not read key

boreal nest
#

// Once the keyboard is found send an init command and abuse two reads to make a 50 ms delay to make sure the keyboard is ready

proud oasis
#

cause it iterates from 0 to 116

boreal nest
#

At that point

proud oasis
#

so.. readkey would be pain

quiet root
#

cant look at kbd and screen at the same time tho

#

with just 100ms sleep

boreal nest
#

There's no call for reading back a single key. There's a pair of calls for grabbing the entire map of all keys at once

proud oasis
#

oh true. it does the color init in the find keyboard code

#

this also explains why the rgb sdk and the analog sdk are separate

boreal nest
#

Yeah, and that call pauses the FX and some other things

#

You could fix that fairly easily

proud oasis
#

ye

quiet root
#

gott did u se the difference between the array setting and the direct setting of key colors?

#

one sends a completely different usb command than the other

proud oasis
#

did you see my attempt to fake single key through WOOTING_RAW_COLORS_REPORT?

quiet root
#

no

boreal nest
#

Move them to a wooting_rgb_init function and note down both HID devices (analog is highest interface ID, leds are highest-4)

proud oasis
#

i failed epicly when i realized how the buffers are actually structured

#

0x00 - 0x0d is red, 0x10 - 0x1d is green, 0x20 - 0x2d is blue

#

so.. the buffer has to contain at least 0x2f bytes

#

i wonder what e and f do

#

i doubt it's checksums

#

since it's 16 bit it could be flags or something

boreal nest
#

I wonder why that pwm map has 48 entries when the only code that uses it explicitly only uses the lower 24

quiet root
#

maybe for future shit

proud oasis
#

well i just explained why it has 48

#

simply said, look at it

#
    const uint8_t pwm_mem_map[48] =
    {
        0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x8, 0x9, 0xa, 0xb, 0xc, 0xd,
        0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d,
        0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d,
        0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d
    };
boreal nest
#

uint8_t buffer_index = pwm_mem_map[led_index % 24]; though

proud oasis
#

0x00 to 0x2F is rgb of 12 keys.

boreal nest
#

That's the only line that uses the pwm map, and it specifically limits to the lower 24

proud oasis
#

why 24 you ask?

#

there:

#
    switch (part_number) {
    case PART0: {
        report_buffer[4] = 0; // Slave nr
        report_buffer[5] = 0; // Reg start address
        break;
    }
    case PART1: {
        report_buffer[4] = 0; // Slave nr
        report_buffer[5] = RGB_RAW_BUFFER_SIZE; // Reg start address
        break;
    }
    case PART2: {
        report_buffer[4] = 1; // Slave nr
        report_buffer[5] = 0; // Reg start address
        break;
    }
    case PART3: {
        report_buffer[4] = 1; // Slave nr
        report_buffer[5] = RGB_RAW_BUFFER_SIZE; // Reg start address
        break;
    }
    case PART4: {
        if (is_wooting_one) {
            return true;
        }
        report_buffer[4] = 2; // Slave nr
        report_buffer[5] = 0; // Reg start address
        break;
    }
#

the reg start address

#

the packages could be twice as big

#

yes, the pwm_mem_map only is used 50% but you could use the whole map if you just change the outgoing buffer

#

you could also just change 12 keys instead of 24

#

or 36

#

in one usb hid call

boreal nest
#

True

proud oasis
#
    uint8_t buffer_index = pwm_mem_map[led_index % 24];
    buffer_pointer[buffer_index] = red;
    buffer_pointer[buffer_index + 0x10] = green;
    buffer_pointer[buffer_index + 0x20] = blue;
boreal nest
#

A single call cannot go above 124 bytes as I recall, though

proud oasis
#

this is the first time i touch usb so.. no clue. thanks for that intel

boreal nest
#

WOOTING_REPORT_SIZE is 129. wooting_usb_send_buffer has the first byte 0, next 2 are magic, fourth byte is command, 123 bytes of data, then 2 checksum bytes at the very end

#

Not sure if that's a USB limitation or a Wooting-imposed limitation though

proud oasis
#

i shall create a test for that

#

the report size is just the buffer size

boreal nest
#

Keep having to tab to the github for function/variable names. I ported the API over to NodeJS straight (so there's no .dll or anything involved) and expanded it, so the naming conventions are a little different. const { Keyboard } = require('./wooting.js'); let kb = Keyboard.get(); kb.enableLeds(); kb.directSetKey(Keyboard.LEDs.Escape, 255, 255, 255); etc. Was very careful to make sure it was identical to it

proud oasis
#

😮

#

how do you connect to usb with it?

boreal nest
#

Weary on sharing 'cause uhm... there's also Keyboard.getCurrentRgbProfile(), Keyboard.loadRgbProfile(index)...

#

Using node-hid

#

NodeJS bindings on top of the same hid library the C API uses

proud oasis
#

lul what a coincidence

#

anyways.. i g2g now.. will be back soon and do some testing with the rgb buffer. maybe i find something fun and the whole twootings colors could be set in two usb calls

#

well.. two for the one, three for the two

#

would also be interesting if i could just change 12 keys with one call. this would mean i could improve the rgb_buffer0_changed = true; stuff etc.

#

partitioning

#

less data = more speed

boreal nest
#

Given how the colors report call is laid out, it might unfortunately not be possible with it

quiet root
#

is this turning into speedwhoring

boreal nest
#

First 2 bytes are flags for which of the 5 buffers are given from the looks of it

#

Or well, less so flags and more like.. addressing math? There's 5 total parts, 96 bytes each, for 480 total bytes. That's enough space to fit 160 RGB triplets in. Granted there's dead space in the buffers that are never written to. 120 bytes in total for the Two and 96 for the One. Every 6 keys there's a spacer of 6 bytes. Removing that from the total and there's just enough space for the full key map in 5 calls for the Two and 4 for the One. I don't think you can squeeze less calls out of it with any tricks

#

Not a single clue what the dead zones are for other than maybe memory alignment

proud oasis
#

well

#

the hid command also specifies the command length

#

so i assume the firmware can see the size of that buffer that is being transferred

#

so.. the experiment that i'm going to write now will alter the package size to see if it works

boreal nest
#

I might have an idea of what those odd unused bytes might be in the buffers. Brightness.

proud oasis
#

oh

#

i just noticed something interesting

#

do you have separate color schemes for A1 - A3 and mode?

#

this is interesting

boreal nest
#

Ah, the moment when not being on Windows and Wine being annoying makes an appearance lol

#

System.EntryPointNotFoundException: wooting_usb_find_keyboard welp

proud oasis
#

interesting

#

well

#
            byte x = 0;

            while (x <= 116) {
                Console.Clear();
                Console.WriteLine("switching key id " + x);
                wooting_usb_send_feature(30, x, 255, 255, 255);
                Thread.Sleep(100);
                wooting_usb_send_feature(30, x, 255, 0, 255);
                if (x > 0) wooting_usb_send_feature(31, 0, 0, 0, x -1);
                x++;  
            }

            wooting_usb_send_feature(32, 0, 0, 0, 0);
            wooting_usb_disconnect(false);
#

simply run something similar to that and change the modes

#

i'll capture a video of it now

boreal nest
#

In theory it shouldn't let you change modes. At least from testing I've done before - the RGB init call blocks the keyboard from making any changes of its own, even capslock/numlock/fnlock don't change for me

proud oasis
#

oh snap..

#

cert expired.. i suck.. brb

boreal nest
#

Ahhh I see. Even though the keyboard isn't allowed to modify the LEDs, it still honors the mode switching, which changes the active profile. Reset call sets the key to what that key is in the active profile. Neat

proud oasis
#

yep

#

would be fun if the firmware would just flag keys that were changed through single

#

so then the w00ting effects and profile color schemes would shine through as "background" layer

#

but judging from trial and error i'd say single and buffered is pretty much direct led controller access

#

except for reset

boreal nest
#

Would make sense

proud oasis
#

finally could upload it..

#

phone -> syncthing -> homeserver
laptop -> samba -> websocket port forwarding proxy i made -> homeserver

#

ssl cert expired -> websocket proxy didn't work anymore, thus no samba

boreal nest
#

That's ... one hell of a chain

proud oasis
#

ye but it even works behind the chinese firewall

#

since it's valid websocket traffic

#

made that with some alcohol during a day

#

ssh port forwarding would ofc do too

boreal nest
#

Can verify the unknown bytes of the buffer appear to do nothing at all

#

Even though it seems perfectly set up for controlling individual key brightness with it

proud oasis
#

i assume the led controllers have 16 channels and just 12 of them are wired out.

#

multiplexing has to be done somewhere somehow.. unless we reverse engineer the wooting hardware we could never know for sure xD

boreal nest
#

Yeah, not keen on going quite that far lol

proud oasis
#

i would. i just assume the wooting team would be open about this if we just ask politely though

#

especially in regards to the issues we just figured out

boreal nest
#

All this started by my crazy idea of having CPU/GPU load/temps show on the F row and number row lol Long since had that done, but curiosity peaked and now picking apart how to do it better

proud oasis
#

well.. feel free to port Aurora to linux

boreal nest
#
const leds = {
  map: [],
  mode: LED_MODES.DIRECT,
  init() {
    let { DIRECT, ARRAY, NAUGHTY } = LED_MODES;
    kb.loadCurrentRgbProfile();
    switch (leds.mode) {
      case DIRECT: return kb.enableLeds();
      case ARRAY: if (!kb.enableLeds()) { return false; } return kb.setColormap(kb.profile.colorMap);
      case NAUGHTY: return leds.copyMap(kb.profile.colorMap);
      default: return false;
    }
  },
  copyMap(colorMap) {
    let { map } = leds;
    if (leds.mode != LED_MODES.NAUGHTY) { return false; }
    for (let i = 0, l = colorMap.length; i < l; i++) { map[i] = colorMap[i]; }
    return true;
  },
  setKey(key, r, g, b) {
    let { DIRECT, ARRAY, NAUGHTY } = LED_MODES;
    switch (leds.mode) {
      case DIRECT: return kb.directSetKey(key, r, g, b);
      case ARRAY: return kb.changeSingleKey(key, r, g, b);
      case NAUGHTY:
        { let { map } = leds; map[key*3] = r; map[key*3+1] = g; map[key*3+2] = b; }
        return true;
      default: return false;
    }
  },
  resetKey(key) {
    let { DIRECT, ARRAY, NAUGHTY } = LED_MODES, { colorMap } = kb.profile;
    switch (leds.mode) {
      case DIRECT: return kb.directResetKey(key);
      case ARRAY: return kb.changeSingleKey(key, colorMap[key*3], colorMap[key*3+1], colorMap[key*3+2]);
      case NAUGHTY:
        { let { map } = leds; for (let i = 0; i < 3; i++) { map[key*3+i] = colorMap[key*3+i]; } }
        return true;
      default: return false;
    }
  },
  updateKeys() {
    let { DIRECT, ARRAY, NAUGHTY } = LED_MODES;
    switch (leds.mode) {
      case DIRECT: return true;
      case ARRAY: return kb.updateKeyboard();
      case NAUGHTY: return kb.setProfileColormap(leds.map);
      default: return false;
    }
  }
};```
This is going to be long, isn't it
#

... yep

#

Makes experimenting easier

karmic storm
#

Hello I am scripting my keyboard with node.js and in basic example I have this code

#
const ffi = require("ffi")
// Define the functions from the DLL
const wootingAnalog = ffi.Library('./libs/wooting-analog-sdk.dll', {
  "wooting_kbd_connected": [ 'bool', [] ],
  "wooting_read_analog": [ 'uint8', ['uint8', 'uint8'] ]
});
const keyboardConnected = wootingAnalog.wooting_kbd_connected()
    if(!keyboardConnected) {
      console.log('Keyboard not connected')
};
// Every millisecond, read the W-key with index 2:2
  setInterval(() => {
    const row = 2
    const column = 2
    const analogValue = wootingAnalog.wooting_read_analog(row, column)
    console.log(`Analog value: ${analogValue}`)
  }, 1)
#

Its good ?

gusty blaze
#

up !

#

and what is ffi ?

quiet root
#

a simple way to integrate dlls into node

gusty blaze
#

ok !

#

thxu

#

i mad what is wrtie on your site but..., tyhat doesnt work

glacial sable
#

i do have the same Problem as @gusty blaze :/

faint vapor
#

Hey guys, I just started trying to use the RGB SDK with node, but the wooting_rgb_kbd_connected function always returns false even though my keyboard is connected waitwut

#

I used the example script btw

faint vapor
hybrid lake
#

Hey guys, I've moved countries last weekend (back to asia) so haven't been able to jump onto everything immediately. I'll get on the PR's today or tomorrow. I also saw the Dinput feedback, thanks @knotty night

#

Please let me know if there's something important I missed

boreal nest
#

@hybrid lake
I don't know how important, but with the Wooting Two...

  1. The Elevator binding in DInput doesn't appear to work and Trigger is missing entirely under Linux
  2. Escape doesn't appear to work when bound to anything in DInput nor XInput under Linux (using xboxdrv for XInput support)
  3. Fn+Mode uses Scroll Lock instead of the Two's Mode key
  4. the USB SINGLE_COLOR_COMMAND and SINGLE_RESET_COMMAND commands don't work correctly for keys >= 96 (numpad, A1/2/3, Mode). 96-97 modify 48 (F10), 98-104 modify 49 (F9), 105-113 do nothing, and 114-116 modify 95 (Underscore)
  5. don't know if this is an issue or if SINGLE_COLOR_COMMAND and RAW_COLORS_REPORT simply handle RGB differently, but there's some inconsistency between RGB values set to keys/shown on the Wootility and the same values sent over the API. For example, setting a key to 184,64,0 via the Wootility results in an orange, while setting the same value over the API results in more of a yellow

Sorry for so many, but I've been playing around with things a lot the past few days

chilly oar
boreal nest
#

I'm a Linux user, so "under Windows" is a problem. OS shouldn't matter, though. For me, there's axis 0-8, with Elevator presumably being 7. Binding the same key to Throttle, Elevator, and Accelerator, axis 6 and 8 span 0-255 as expected, but axis 7 remains 0

chilly oar
#

Year I remember there was a problem with a value under linux...

boreal nest
#

Oh, I didn't expect it to be a Linux-specific thing. Lemme edit to specify

chilly oar
#

When I tested it, please give me a few minutes...

boreal nest
#

Take your time

chilly oar
#

Yes, Elevator an Trigger are not working under linux for me with W1. The problem is that linux don't understand it. Can't tell for shure because I have to do much more tests.

#

Did you have problems with the Trigger to?

boreal nest
#

Yeah, I hadn't tested Trigger. There's not even an axis for it registered it seems

chilly oar
#

Yes, one is missing and one value are not registered correct.

boreal nest
#

Yeah. Very strange

chilly oar
#

I'm kinda onto it because I tested a lot of the HID stuff with the Wooting lately for my self, because I want to learn the HID USB stuff. I'm not finished right now. When I'm finished I want to provide a few improvement to them.

boreal nest
#

I wish you luck with that

chilly oar
#

🤔

quiet root
#

@boreal nest could u try setting a key to pure red with the wootility and sdk and see if theres a difference

boreal nest
#

Sure

#

No difference with pure red. At least not to the eye

quiet root
#

ok and could u also try putting in hex values instead of decimal so 0xYY

#

maybe we understand the commands wrong

#

cant really imagine there only being a problem with mixing colors

boreal nest
#

It's still writing as 24bit RGB either way

quiet root
#

code does weird shit sometimes

boreal nest
#

I don't think it's the command specifically, as the direct set ones also exhibit the behavor

#

There might be some post-processing that isn't applied to the SDK calls that's the difference. I'm not really sure

quiet root
#

but wouldnt it do it on any color then as in even pure red would be less red

boreal nest
#

Depends on what the post-processing does

quiet root
#

thats some weird pp if it only affects rgb values where 2 values are greater than 0

#

like if its smth that changes the rgb values it would always do it

boreal nest
#

I think it's more about the individual values. 127,127,127 triggers it as well (the SDK's version of it is brighter)

#

So it could be adjusting pwm values differently between the SDK and the calls the Wootility makes

#

Another example: 127,127,0 via the SDK looks closer to 255,220,0 based on me trying to eyeball it

#

So it definitely seems like there's some post-processing going on firmware-side with the Wootility calls that don't happen via the SDK. But what it's doing exactly I'm not sure

quiet root
#

cause it seems like a luminance thing

#

i compared both rgbs u send and the most obvious difference was that one was half as bright in HSL

boreal nest
#

Similar, but the SDK is more orange

grizzled wolf
#

Just got my wooting and I haven't been in the loop about any software development going on. Have there been any cool ideas or features using the analog input for typing/programming that you've heard of?

karmic storm
#

@gusty blaze Ta eu ta réponse

quiet root
#

@grizzled wolf i cant think of any good use for analog in typing/programming tbh

grizzled wolf
#

How good is the wooting (two) at detecting key press velocity? Is the sample rate of position detection sufficient?

#

Imagine backspacing a character/word/line depending on how hard you press backspace

gusty blaze
#

j'ai vu @karmic storm

knotty night
#

@hybrid lake There are some other issues with DI too, although I am not 100% sure on what is "right and what is "wrong". From what I understand, DI basically only supports 8 usages - X, Y, Z, Rx, Ry, Rz, SL0, SL1.
However, there seem to be some other usages which are aliases of these - eg I think "Wheel" is an alias for X.
From what I understand - "Elevator" is not one of these axes, and this is borne out by the fact that I cannot bind it in any of the games that I have tried

#

Also, some of the axes in Wootility only have one binding (eg "Throttle"), whereas most have high/low (eg X, Y etc).

#

In DI, AFAIK axes are not flagged as being a "normal / centering" or "pedal / trigger" type axis - you could, in theory, use any axis for either a normal or a pedal style axis

#

So IMHO what needs to be done is all axes in Wootility should have two bindings for them, but all of them should support only one key being bound to either high or low

#

In that instance, that one key should use all the axis (Like the throttle axis does now)

#

Or, as mentioned before, once you bind a 2nd key to that axis, it should split the axis between the two keys

#

Interestingly, "Elevator" does show up in DIView

#

So not quite sure what is going on there.

#

It doesn't show up in joy.cpl tho

chilly oar
#

@knotty night As far as I found informations on this Dinput supports 8 axis and 2 sliders (Throttle and Rudder, but the last is supported by the hardware but not allocable in the wootility). Because the other three (Elevator, Accelerator, Trigger) are not supported by the Dinput interface you can't see them under "joy.cpl" and DIView.

knotty night
#

AFAIK it's 8 axes including the 2 sliders

#

The throttle / wheel axes appear to be aliases

chilly oar
#

Its different but transparent for the applications.

knotty night
#

right

chilly oar
#

Yes, they are aliases

#

And yes, to split up the two sliders would be a good think, like one for 0.5 to 1.0 and the other from 0.5 to 0. Because it can be calibrated on the Dinput interface there are no downfalls I think.

#

But not all applications seems to use the Dinput interface.

knotty night
#

Well, it's not technically hard to have it so that no matter if one key or two keys are bound to an axis, the full range is used

#

(Maths-wise anyway)

chilly oar
#

You are familar with using the Dinput interface or?

knotty night
#

I use SharpDX

#

so not directly, but SharpDX is a very thin wrapper

chilly oar
#

But it uses the DirectX API so I guess it uses Dinput.

knotty night
#

SharpDX wraps DI, XI and RI

#

RawInput

chilly oar
#

You programm rely on the values from the same values that you can see in "joy.cpl" right?

knotty night
#

But it doesn't shield you from the underlying API too much

chilly oar
#

So if you calibrate the controller under "joy.cpl" did it effect your values too or not?

knotty night
#

Yeah, in SharpDX, DI uses the native ushort values, and XI uses the native short values

chilly oar
#

?

knotty night
#

DirectInput reports axis values as short (0..65535)

chilly oar
#

Did a controller calibration changes the value you see?

knotty night
#

XInput reports axis values as ushort -32768...32767

#

In DI, when you read an axis, you get the post calibration values

#

(Black values in DIView)

chilly oar
#

I'm confussed because a Xbox 360 Controller only have possitive values.

knotty night
#

on what are you basing this?

#

HTML5?

chilly oar
#

No the HID Report Descriptor from the Xbox 360 controller form my W1.

#

You can see the picture of it in the helpdesk section

knotty night
#

The Xinput API reports values in the range -32768..32767 for normal axes, 0..255 for triggers

#

I dunno what it uses at the HID level

#

Oh my god, have you SEEN the HID usage tables - the amount of crazy stuff that is in the spec??

#

Like they have a whole "Sports" usage page, with a specially defined usage for golf clubs

chilly oar
#

Ok, you are right. I caputured the data. Its from -32768 to 0 to 32767.

knotty night
#

Annoyingly, it's not possible to perfectly convert between DI and XI ranges

chilly oar
#

Yes, there are a lot special stuff, and nearly noone uses this.

knotty night
#

DI considers mid-point to be 32767

#

On DI, the upper side of the scale is bigger, but on XI the lower side of the scale is bigger

#

So if you just shift scale up / down to convert DI/XI, your mid-point will be off by 1

chilly oar
#

Just shifted, but I saw the RAW data, and its seems to be signed, because on the deppest press for down I got x8000 and for up x7fff.

knotty night
#

Also, when working with stick axes, if using signed integers, bear in mind that you cannot invert a signed integer with * -1 !!

#

-32768 * -1 == -32768!!

#

if using a short

#

Amazed at how many coders don't realize that - have caught out numerous people with that in job interviews 😛

chilly oar
#

I forgot this things long time ago, was like *-1 and plus or minus 1 or something like that.

#

Give me a few minutes...

knotty night
#

There's no one "right" answer

chilly oar
#

There is one

quiet root
#

that only doesnt work for -32768 tho

chilly oar
#

-2 = ^(2 - 1)

quiet root
#

since the result would be 32768 which overflows to -32768

#

highest positive number is 32767

chilly oar
#

No Multiplication, bitwise xor

#

the negative values can be one more than the possitive ones

quiet root
#

thats inverting the bits tho

chilly oar
#

-32768 to 32767

#

That is what I mean

#

a value xor with themselves is inverting

#

no

#

that is bullshit

#

no xor at all 😃

#

a value xor with itself is everytime 0

quiet root
knotty night
#
        public static short Invert(short value)
        {
            if (value == 0) return 0;
            if (value == short.MaxValue)
            {
                return short.MinValue;
            }

            if (value == short.MinValue)
            {
                return short.MaxValue;
            }

            return (short) (value * -1);
        }
#

This is what I use

#

Has funcs for Deadzone, Sensitivity curves, Invert

#

And circular DZ

quiet root
#

now ur invert misses 1 value tho

knotty night
#

Yes, as I said, no perfect solution

#

You just have to pick a compromise

#

My thinking is to make sure max deflection is always possible

#

and lose fidelity at 1 unit from the extremes

#

where it is likely to be less of an issue

#

it's one in 65k units, so it's hardly the end of the world, especially if it is not a significant (eg max value or center) point

#

-32766 being unreachable is hardly a big deal

chilly oar
#

You can do a negation by multiplictaion with "-1" OR by a subtraction with 1 and a bitwise invertation afterwards. Nearly everytime when you use the first method your complier uses in reality the other method because it is much faster.

knotty night
#

oops, -32767 rather

#

If you use +1 or -1 you will break mid-point

#

which for me is a bigger deal if you invert an axis and it does not sit at exactly 0

chilly oar
#

Because of the midpoint you can just use -32767 to 32767

knotty night
#

With modern hall sensor sticks, they are that precise that it is noticeable if you have no deadzone

quiet root
#
  public static short Invert(short number) {
    return number == short.MinValue ? short.MaxValue : number * -1;
  }
#

done

#

now u miss 0 numbers

knotty night
#

Then max deflection is unreachable, which seems uncool

#

@quiet root then -32768 is unreachable

quiet root
#

yes but its accurate inversion

#

because inverting 32767 should return -32767

knotty night
#

I would rather one non-maximum value be unreachable

#

one value has to be unreachable

#

for me, that should not be a max/min value and should not be the mid-point