rvlt Posted January 3, 2013 Report Share Posted January 3, 2013 The calibration feature for the wheels sounds great! Will an AINSer be supported for this as well? I don't trust the onboard a-d conversion of the LPC17 so much.. Actually the wheel calibration is one of the main reasons I want to upgrade my existing controller keyboard to a MB KB version. I had to change the pots of my pitch- and modwheels because they were worn out. I put in pots with the same values, but since every pot has a (slightly) different curve, they don't send the full range of CCs anymore and the mod wheels is jittering now quite heavy. There is no way of calibrating this, so... MB KB to the rescue! :smile: Quote Link to comment Share on other sites More sharing options...
TK. Posted January 3, 2013 Author Report Share Posted January 3, 2013 Yes, I could support the AINSER as well. But the remaining analog inputs won't be fully configurable, because such a function would conflict with the MBNG features where I did it better (than before ;). I also would like to evaluate, if the MBKB could be merged with MBNG - this would be the most simple way to maintain the project, and it would give us the highest flexibility. We would have the drawback that the minimum latency increases from ca. 130 uS to ca. 2 mS for a Fatar 61 Keyboard in worst case (to 1 mS if the optimized scan is used). The latency would be higher, since MBNG requires more headroom for all the other functions which are running in parallel. Would such a high latency be acceptable? Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
Duggle Posted January 3, 2013 Report Share Posted January 3, 2013 Its always hard to accept higher latencies mentally, though in practice it often makes less difference that you think (esp. when its <5ms total). I am and will be using the KB through the SEQ which I assume adds 2ms to live notes forwarded through to synths (then latency of the actual synth added to this..) Am I correct in understanding that using optimized scan on a NG based KB may add only 800 or 900us to the total latency? Quote Link to comment Share on other sites More sharing options...
TK. Posted January 3, 2013 Author Report Share Posted January 3, 2013 Am I correct in understanding that using optimized scan on a NG based KB may add only 800 or 900us to the total latency? yes The increased latency will mainly affect the accuracy of the velocity values. Currently the measured delay ranges from 50...1000, with a 10 times slower scan we would only measure delays between 5..100 anymore. It depends on the outcome with your "velocity curve" implementation if a difference can really be notified. Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
rvlt Posted January 3, 2013 Report Share Posted January 3, 2013 Hard to tell in theory. Do we have any numbers of other (commercial) midi keyboards to compare with? For me an added latency of max. 1ms still sounds fast, at least for normal (non-percussive) keyboard operation. I'm thinking of a real world example: Say you want to build a midi keyboard with a few pots, encoders etc., so you add a LPC17 with MBKB software for super low latency. Then you add another LPC17 (with MBNG) for the rest of the controllers. If you want to use only a single USB port (for convenience) to connect your computer, you would have to merge (e.g. via Midi I/O #4) the MBKB midi data with the MBNG controller data in the MBNG, right? Would this process also add latency, maybe even more than 1ms? So from this point of view a merge between MBKB and MBNG would be much more convenient, and performance-wise on the same level. But this is all (my) theory, maybe it's best to try it out: If we'd have a beta version of an KB-enhanced MBNG, we could compare these two and see if it "feels" different. (BTW I'm just waiting for my DIO_Matrix module to arrive from Smash_TV, than I'll try MBKB asap..) Cheers Lars Quote Link to comment Share on other sites More sharing options...
Duggle Posted January 3, 2013 Report Share Posted January 3, 2013 The velocity values would be a lot more "granular" i.e would encompass the range 1 to 127 but certain values would never appear on the output because it would map 5..100 onto 127..1. With nonlinear scaling it would invariably reduce the total number of values that appear on the output. Would it ever be noticed? (imho) no, does it bother me (mentally) that the velocity output would be granular, yes :hmm: . Personally (subject to change, of course!) I might entertain the idea of developing on a small STM32 "minicore" (minimal MB Core32) that does nothing more than scan the keyboard(s) apply velocity scaling, then forward midi events to a uart (maybe at higher baud, for direct connect with an NG?). Quote Link to comment Share on other sites More sharing options...
rvlt Posted January 13, 2013 Report Share Posted January 13, 2013 Hey, I've managed to install MB_KB today. I spent half a day to measure the matrix layout / connections of my old miditech keyboard, just find out that .... ... the two cables with DIL16 headers coming from the miditech match exactly the two DIL16 sockets on the DIO Matrix. So it is a 1:1 connection, I didn't have to resolder a single cable!!! That was really PLUG'N'PLAY!! Could have saved my about 5 hours if I just tried to connect them and see what happens, but anyway... :rolleyes: So far everything's working great. Ready to try MB_NG+KB ... :smile: Cheers Lars Quote Link to comment Share on other sites More sharing options...
Duggle Posted January 13, 2013 Report Share Posted January 13, 2013 I suppose the keyboard has a Fatar 61 note keybed? Quote Link to comment Share on other sites More sharing options...
rvlt Posted January 14, 2013 Report Share Posted January 14, 2013 "Meifa CO., Ltd. © Copyright Keyboard-R" is printed on the backpanel. Maybe it's a Fatar clone or something.. Quote Link to comment Share on other sites More sharing options...
TK. Posted January 14, 2013 Author Report Share Posted January 14, 2013 Could have saved my about 5 hours if I just tried to connect them and see what happens, but anyway... :rolleyes: :thumbsup: So far everything's working great. Ready to try MB_NG+KB ... :smile: We can give it a trial run this weekend. :) Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
NorthernLightX Posted January 15, 2013 Report Share Posted January 15, 2013 I spent half a day to measure the matrix layout / connections of my old miditech keyboard, just find out that .... ... the two cables with DIL16 headers coming from the miditech match exactly the two DIL16 sockets on the DIO Matrix. So it is a 1:1 connection, I didn't have to resolder a single cable!!! Would that be the same Miditech / Midiplus keybed that I aquired some time ago? That would be sweet, would save me from measuring that shiz as well :w00t: Quote Link to comment Share on other sites More sharing options...
rvlt Posted January 15, 2013 Report Share Posted January 15, 2013 If there are two cables with DIL16 headers coming from your keybed, I'd say yes. Just order a DIO_Matrix module and give it a go.. ;) Quote Link to comment Share on other sites More sharing options...
nlate Posted January 19, 2013 Report Share Posted January 19, 2013 (edited) Dear Thorsten I successfully installed the precompiled MIDIBOX_kb_V1_007 .hex file on my LPC17xx system. Everything worked as expected: Terminal commands etc. Keyboard setup for Fatar DF88 Keyb. Minor issue: set kb 1 note_offset 24 (C-0) should be 21 (a-1) optimize option works perfect: 180 (6*30) us for a all 88 keys in steady state !!! 360 (12*30) us if all Dins (lower & upper half) change at once (very rarely)! some ideas and findings: delay_fastest should be made separate for white and black keys, because the lever of the black keys is shorter than the lever of the white keys. With the Fatar TP9-88 I could generate shortest delay of 40 ticks on black keys, with the white ones I never came under 57 ticks. delay_slowest can be made fixed, since it determines the latency of the sent MIDI cmd, eg. delay_slowest = delay_fastest + 127 * 8 => 31,7 ms latency. kc->break_inverted seems not to be initialized in KEYBOARD_Init(). In fct: void KEYBOARD_SRIO_ServicePrepare(void) which is called every 30 us:// optional scan optimization for break/make: if break not active, we don't need to scan make if( kc->scan_velocity && !kc->break_inverted && kc->scan_optimized ) {... // can ber replaced by :if( kc->scan_optimized ) { ... If the remaining conditions are checked in KEYBOARD_Init() and the related Set_..() functions Before I intended to modify the code, I build the project from the Reposity with Rev 1633 and loaded it into the platform. Everything went as expected until I pressed one of the two rightmost keys (B-6 & C-7): The System crashed with "!! HARD FAULT !! at PC = 0x000064d8" Since I haven´t any debugger I decided to go the hard way and did some version comparisons... I went back to Rev 1632 which was the the revision of your Build V1.007 and everything works without crashes. I checked the differencies to Rev 1633 and found out that app_lcd for universal lcd was changed, but this should not have any influence on the code. But then I realized that the terminal.c code was updated for all apps except for the Keyboard. So after modifying terminal.c the crashes were gone. I´m not 100% sure if I made the changes at the right places in terminal.c, so it would be fine if you can review the attached terminal.c and update the repository Thanks very much and best regards Jo terminal.zip Edited January 19, 2013 by nlate Quote Link to comment Share on other sites More sharing options...
TK. Posted January 20, 2013 Author Report Share Posted January 20, 2013 Hi Jo,thanks for the feedback!I will check your findings & proposals this evening.To the changes in terminal.c: they can't be the reason for such a crash, the root cause must be somewhere else - e.g. a stack overflow or something similar. I will try to reproduce this.Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
nlate Posted January 20, 2013 Report Share Posted January 20, 2013 Dear Thorsten Thanks in advance for your investigations. In the meantime I made some measurements with my USB logic analyzer. They may be helpful for the MBKB project documentation. I attached them as screenshots, the titles are hopefully self-explainining. MBKB_1RowScan.jpg Detail, how the Dout registers are controlled for one row. MBKB_ScanNonOptimizedOnly.jpg Timing for non optimized row scan without key press MBKB_ScanOptimizedOnly.jpg Same as above but with optimized row scan MBKB_ScanNonOptimizedC-0pressed.jpg Timing for 1 Key press C-0 non optimized scan MBKB_ScanOptimizedC-0pressed.jpg Same as above but with optimized scan MBKB_ScanOptimizedC-0_D-3pressed.jpg 2 keys pressed on Left and Right half of the 88 key Fatar keyboard with optimized row scan. MBKB_ScanOptimizedLhRhChordPressed.jpg 6-key Cord press with optimized row scan I also added the timing files in the zip archive the can be viewed in with the Analyzer SW available at http://www.pctestinstruments.com/downloads.htm running in Demo mode Best regards Jo MBKBtimings.zip Quote Link to comment Share on other sites More sharing options...
TK. Posted January 20, 2013 Author Report Share Posted January 20, 2013 Thanks for the sanity check, very useful! :smile:The scan rate is lower than specified at the MBKB page since I had to decrease the SPI rate after it turned out, that a too fast SPI overloads the application too much so that USB transfer were delayed by several mS - I aligned the latency values at the MBKB page now. To your proposals: delay_fastest should be made separate for white and black keys, because the lever of the black keys is shorter than the lever of the white keys.With the Fatar TP9-88 I could generate shortest delay of 40 ticks on black keys, with the white ones I never came under 57 ticks It's possible to specify a separate delay_fastest_black_keys now. It's taken on black keys when the specified value is > 0Currently the value is not stored in EEPROM, because I would like to wait for more potential parameters before changing the storage structure.The changes are available in the repository. delay_slowest can be made fixed, since it determines the latency of the sent MIDI cmd,eg. delay_slowest = delay_fastest + 127 * 8 => 31,7 ms latency I guess that with "made fixed" you mean, that the same value can be taken for black and white keys? kc->break_inverted seems not to be initialized in KEYBOARD_Init(). done (but this was uncritical, since the runtime environment will initialize all variables with 0 anyhow In fct: void KEYBOARD_SRIO_ServicePrepare(void) which is called every 30 us:// optional scan optimization for break/make: if break not active, we don't need to scan makeif( kc->scan_velocity && !kc->break_inverted && kc->scan_optimized ) {...// can ber replaced by :if( kc->scan_optimized ) { ...If the remaining conditions are checked in KEYBOARD_Init() and the related Set_..() functions I will keep this conditional check as it is - at a single place.Otherwise I would have to do similar checks at multiple places, which leads to more error prone code. In addition, it could be that in future kc->break_inverted could be considered for the optimized scan (which is only a testing issue - very hard if I don't own such an exotic keyboard...) The System crashed with "!! HARD FAULT !! at PC = 0x000064d8" I'm not able to reproduce this (neither with the latest revision, nor with r1633) Are you using the MIOS32 toolchain? (ensures that you are using the same compiler + newlib version) The PC indicates, that an unintended write operation into the FreeRTOS variable range happened.But I haven't found a place where this could happen. Anyhow, I added a check for an "invalid" read operation (kc->prev_row != 0xff) - which won't solve the problem, but is just more clean.And I added a check for the key number boundary (key >= KEYBOARD_NUM_PINS) for the case that I overlooked something during the key number calculation. Could you please check if the firmware still crashes with these changes when the upper notes are played? Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
nlate Posted January 20, 2013 Report Share Posted January 20, 2013 (edited) Dear Thorsten I updated my MIOS32 folder to the current Rev. 1663, built the project as always with the MIOS32 Toolchain under WinXP, installed the firmware with MIOS Studio and started the KB V1.008:The aforementioned crashes didn´t occur anymore over the whole keyrange!!! Thank You very much! I agree with all points you mentioned! Your question about delay_slowest:Yes, I mean the same value for both black and white keys. Fixed means imho that it depends only on the Users preferences, how much latency he would accept for NoteOn generation (about 31,7 ms in my example). Imho it´s not dependent on the actual keybed. Thanks again and regards Jo Edited January 20, 2013 by nlate Quote Link to comment Share on other sites More sharing options...
TK. Posted January 20, 2013 Author Report Share Posted January 20, 2013 Hi Jo, great that the crash issue is solved! :) The delay_slowest value not only affects the latency, but also the (linear) velocity calculation. With higher values the velocity will get "stronger" earlier. This dependency could change once a non-linear velocity curve is available. Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
TK. Posted January 27, 2013 Author Report Share Posted January 27, 2013 The keyboard driver is now integrated into MIDIbox NG V1.014: I'm looking forward to your feedback! :) Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
Polykobol Posted March 12, 2013 Report Share Posted March 12, 2013 I have a cool idea to use this Midibox KB... 8-) Quote Link to comment Share on other sites More sharing options...
nlate Posted March 15, 2013 Report Share Posted March 15, 2013 Dear Thorsten, Dear MIDIBOXers During the recent weeks I extended the midibox_kb project for detecting also release velocity if the keybed is able to detect it like the FATAR DF xx types. Additionally EEPROM preset system is also extended to cope with the additional parameters. Initially I also revised the parameter documentation on http://ucapps.de/midibox_kb.html and I propose some minor additions/corrections for the FATAR DF type keybeds: e.g: - set kb <1|2> note_offset <0-127>: 21 for 88 keys (a-1); 28 for 76 keys (E-0); 36 for 61 keys & 49 keys (C-1); 48 for 25 keys (C-2) - set kb <1|2> din_key_offset <0-127>: 32 for 61 keys and 76 keys; 40 for 88 keys ; The below proposed code changes/additions don´t generate noticable performance losses during my testing with a FATAR DF TP9/88 keybed. But I´m not completely sure if the changes behaves as expected with other separate Break/Make contact keybeds. So feel free to use inspect the code in your MIDI_KB project. Mios32\modules\keyboard\keyboard.h: typedef struct { ..... u8 scan_release_velocity:1; ..... ..... u16 delay_fastest_release; u16 delay_fastest_release_black_keys; ...... u16 delay_slowest_release; ...... } keyboard_config_t; Mios32\modules\keyboard\keyboard.c: // removal of: static u8 key_note_on_sent[KEYBOARD_NUM][KEYBOARD_NUM_PINS / 8]; static u8 key_note_off_sent[KEYBOARD_NUM][KEYBOARD_NUM_PINS / 8]; // not used anymore (s. below) s32 KEYBOARD_Init(u32 mode) { init of the additional structure members (s. above) } void KEYBOARD_SRIO_ServicePrepare(void) { // modified increment timestamp for velocity delay measurements // but skip 0, which is used as reset of *ts_make and *ts_break values if ( !(++timestamp)) ++timestamp; ... } void KEYBOARD_SRIO_ServiceFinish(void) { .... // use of timestamp ptrs instead of values u16 *ts_ptr = (u16 *)&din_activated_timestamp[kb][prev_row * MATRIX_NUM_ROWS]; ... *ts_ptr == 0 // as additional condition to get updated in the for(..) loops ... // additional for(..) loop to handle release timestamps ... } static void KEYBOARD_NotifyToggle(u8 kb, u8 row, u8 column, u8 depressed) { // modified debounce processing // check for *ts_break_ptr and *ts_make_ptr instead of *note_on_sent and *note_off_sent // all access to the content of timestamp pointers is secured by MIOS32_IRQ_Disable(); .... MIOS32_IRQ_Enable(); ... // black key handling modified depending on kc->note_offset because this // offset determs the key to normalized note and not to the evtl. transposed MIDI note. // not every keybed starts with ´C´! ... // branch depending on pressed or released key // additional released key processing } // additional help fct.: static int KEYBOARD_GetVelocity(s16 delay, u16 delay_slowest, u16 delay_fastest) { } // modified help fct. with additional parameter u8 depressed static s32 KEYBOARD_MIDI_SendNote(u8 kb, u8 note_number, u8 velocity, u8 depressed) { } // additional release velocity dependent parameters in: s32 KEYBOARD_TerminalHelp(void *_output_function) { } // and s32 KEYBOARD_TerminalParseLine(char *input, void *_output_function) { } // and s32 KEYBOARD_TerminalPrintConfig(int kb, void *_output_function) { } In MIOS32\apps\controllers\midibox_kb_v1\src\presets.h: // additional offset definitions at the end of: .. #define PRESETS_ADDR_KB1_DELAY_FASTEST_BLACK_KEYS (0xd1 + 0*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xd1 #define PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE (0xd2 + 0*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xd2 #define PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE_BLACK_KEYS (0xd3 + 0*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xd3 #define PRESETS_ADDR_KB1_DELAY_SLOWEST_RELEASE (0xd4 + 0*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xd4 ... // and ... #define PRESETS_ADDR_KB2_DELAY_FASTEST_BLACK_KEYS (0xd1 + 1*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xf1 #define PRESETS_ADDR_KB2_DELAY_FASTEST_RELEASE (0xd2 + 1*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xf2 #define PRESETS_ADDR_KB2_DELAY_FASTEST_RELEASE_BLACK_KEYS (0xd3 + 1*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xf3 #define PRESETS_ADDR_KB2_DELAY_SLOWEST_RELEASE (0xd4 + 1*PRESETS_OFFSET_BETWEEN_KB_RECORDS) // 0xf4 In Mios32\apps\controllers\midibox_kb_v1\src\presets.c: // modified fcts: s32 PRESETS_Init(u32 mode) { ... // added bit at the end! kc->scan_release_velocity = (misc & (1 << 4)) ? 1 : 0; ... // added parameters at the end! kc->delay_fastest_black_keys = PRESETS_Read16(PRESETS_ADDR_KB1_DELAY_FASTEST_BLACK_KEYS + offset); kc->delay_fastest_release = PRESETS_Read16(PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE + offset); kc->delay_fastest_release_black_keys = PRESETS_Read16(PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE_BLACK_KEYS + offset); kc->delay_slowest_release = PRESETS_Read16(PRESETS_ADDR_KB1_DELAY_SLOWEST_RELEASE + offset); ... } s32 PRESETS_StoreAll(void) { ... //added bitfield at the end! u16 misc = ... (kc->scan_release_velocity << 4); status |= PRESETS_Write16(PRESETS_ADDR_KB1_MISC + offset, misc); ... //added parameters at the end! status |= PRESETS_Write16(PRESETS_ADDR_KB1_DELAY_FASTEST_BLACK_KEYS + offset, kc->delay_fastest_black_keys); status |= PRESETS_Write16(PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE + offset, kc->delay_fastest_release); status |= PRESETS_Write16(PRESETS_ADDR_KB1_DELAY_FASTEST_RELEASE_BLACK_KEYS + offset, kc->delay_fastest_release_black_keys); status |= PRESETS_Write16(PRESETS_ADDR_KB1_DELAY_SLOWEST_RELEASE + offset, kc->delay_slowest_release); ... } Have fun :rolleyes: Regards, Jo Midibox_kb_relVelocity.zip Quote Link to comment Share on other sites More sharing options...
Duggle Posted March 15, 2013 Report Share Posted March 15, 2013 That's really cool. I'm not sure whether my Synths (Virus B and C) can do anything with release velocity, perhaps Native Instruments VSTi do? I have a MBKB with a dual Fatar 66 keybeds. Anyhow, well done. Quote Link to comment Share on other sites More sharing options...
TK. Posted March 17, 2013 Author Report Share Posted March 17, 2013 Thanks a lot for your contribution! :smile: I tested the new option with my cannibalized Korg Microkontrol keyboard, it's working fine! So, I took over your code almost 1:1, and only changed back the default delay values to the "less elaborated" ones to get a good starting point for all keyboard types. I also updated the documentation based on your input: http://www.ucapps.de/midibox_kb.html And I released a new version: MIDIbox KB V1.009 ~~~~~~~~~~~~~~~~~ o support for the "single_usb" option, which can be enabled with the bootloader update application V1.012 ("set usb_single 1") Use this option if you are working with a Windows PC which can't handle the 4 USB ports correctly (e.g. stucking MIDI, Filebrowser operations are failing, etc.) o support for Note Off velocity (implemented by Jo aka. Nlate). This feature has to be enabled with the release_velocity parameter. In addition, some suitable delay values have to be specified, such as: set kb 1 release_velocity on set kb 1 delay_fastest_release 100 set kb 1 delay_fastest_release_black_keys 80 set kb 1 delay_slowest_release 1000 One thing puzzles me a bit: why are you writing "0xff == prev_row" instead of "prev_row == 0xff"? Both expressions should be equal, but the original expression is better to read (from my point of view) Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
nlate Posted March 18, 2013 Report Share Posted March 18, 2013 (edited) Dear Thorsten, Thanks for adding the release velocity to the repository, and for updating the documenation. One thing puzzles me a bit: why are you writing "0xff == prev_row" instead of "prev_row == 0xff"? Both expressions should be equal, but the original expression is better to read (from my point of view) This is a result of experience with hard to find bugs in production quality code. suppose the coder intents to write: if( variable_x == CONST_A){ expression(); } but makes a typo of: if( variable_x = CONST_A){ expression(); } both variants are valid c code, and rarly generate wrong results, if the variable_x has the value CONST_A most of the time! if you write: if( CONST_A == varable_x){ expression(); } with the same typo: if( CONST_A = variable_x){ expression(); } you will get a compiler error, and your typo is easily detected by the compiler! Just my two cents for writing robust code. Cheers, Jo Edited March 18, 2013 by nlate Quote Link to comment Share on other sites More sharing options...
TK. Posted March 18, 2013 Author Report Share Posted March 18, 2013 Interesting! gcc outputs a warning if I would write variable_x = CONST_A /Users/TK/svn/mios32/trunk/modules/keyboard/keyboard.c:307:5: warning: suggest parentheses around assignment used as truth value But since parentheses are sometimes used in such expressions as well, the programming error wouldn't be recognized (no warning). Seems that I should change my habits as well ;) Best Regards, Thorsten. Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.