Jump to content

robinfawell

Programmer
  • Posts

    292
  • Joined

  • Last visited

Everything posted by robinfawell

  1. Thank you once again, Thorsten. I'm very grateful! I had moved a little on my own, but was unsure of some of the code I was writing. I have tested the revised program and can report that it is working to a large extent. However the transfer from SPI to SRIO has, I believe, reversed both the DIN and the DOUT bit order. This as you know causes scrambling of pins and notes and reverses the order of first and second key contacts. I need to make more detailed checks on this to determine all the changes. I know that there are routines that can reverse the bits in a word. I am also sure that the program could be altered so that the correct order of "make and break" is maintained. My pin adapter for the Fatar contacts to Dio Matrix board will need to be modified so that it will fit under the keys in the Fatar keybed. I could easily make a new one to accommodate the reversed SR connections. I will let you know how the project progresses. Regards Robin PS If limit the SRIO transfers to 12 rows,can I use a diode based matrix system with some or all the remaining rows of the 2 SRs for use with APP_DIN_NotifyToggle?
  2. Dear Thorsten I have tried the tutorial 029 code with my Fatar 88 note keyboard. There is activity on MIOS Studio but looking at the code I see that the system only uses one DIN SR. My current setup uses the newer DIO_Matrix. I use 2 DOUT SR and 2 DIN SR. I only use 12 of the 16 available DIN SR. The wiring of the Fatar KB uses 8 + 2 DIN for the LH of the KB and 8 + 4 DIN for the RH of the KB . Hence 12 DIN used. The unused 2 DIN on the LH is scanned through 16 additional diodes to provide switches for the KB pedals, 2 sets of rotary Thumbwheel switches, Transpose and other purposes. I am using J5 as outputs for LED and hope to use one Analog output for Midi Volume. It would be very helpful if you could give me an idea how to add the second DIN SR. I think I can work out how to scramble the Pin numbers and notes. Thanks Robin Edit. I am in the process of trying to incorporate the structure of the tutorial 29 into my own code. I have a few more lines of code to add before I can try the program out with MIOS Studio.
  3. Thanks Thorsten I will modify Tutorial 29 and try to introduce my variations. Robin
  4. Thanks Thorsten. Here is my app.c // $Id: app.c 1109 2010-10-11 23:14:49Z tk $ /* * Example for a "fastscan button matrix" * * ========================================================================== * * Copyright © 2010 Thorsten Klose(tk@midibox.org) * Licensed for personal non-commercial use only. * All other rights reserved. * * ========================================================================== */ ///////////////////////////////////////////////////////////////////////////// // Include files ///////////////////////////////////////////////////////////////////////////// #include <mios32.h> #include "app.h" #include <FreeRTOS.h> #include <task.h> #include <queue.h> ///////////////////////////////////////////////////////////////////////////// // for optional debugging messages ///////////////////////////////////////////////////////////////////////////// // level >= 1: print warnings (recommended default value) // level >= 2: print debug messages for Robin's Fatar Keyboard // level >= 3: print row/column messages in addition for initial testing of matrix scan for other usecases #define DEBUG_VERBOSE_LEVEL 2 #define DEBUG_MSG MIOS32_MIDI_SendDebugMessage ///////////////////////////////////////////////////////////////////////////// // Local definitions ///////////////////////////////////////////////////////////////////////////// #define PRIORITY_TASK_MATRIX_SCAN ( tskIDLE_PRIORITY + 2 ) // scan 12 rows #define MATRIX_NUM_ROWS 12 // sink drivers used? (no for Fatar keyboard) #define MATRIX_DOUT_HAS_SINK_DRIVERS 0 // maximum number of supported pins (rowsxcolumns) = (12*16) #define KEYBOARD_NUM_PINS (12*16) // used MIDI port and channel (DEFAULT, USB0, UART0 or UART1) #define KEYBOARD_MIDI_PORT UART0 //#define KEYBOARD_MIDI_CHN DEFAULT ///////////////////////////////////////////////////////////////////////////// // Prototypes ///////////////////////////////////////////////////////////////////////////// static void TASK_MatrixScan(void *pvParameters); static void Timer(void); ///////////////////////////////////////////////////////////////////////////// // Local Variables ///////////////////////////////////////////////////////////////////////////// static u16 din_value[MATRIX_NUM_ROWS]; static volatile u32 timestamp; static u32 kb_del_fast = 30;//used to set loudness resolution static u32 kb_del_slow = 1000;//used to set loudness resolution u8 toggle_state_pedal = 0;// using momentary action membrane switch, alternately selects soft or //sostenuto pedal. Latter is grand piano type sustain u8 toggle_state_port = 1;// using momentary action membrane switch, alternately USB0 or UART0 u8 toggle_state_swell = 1;// For Swell (Vol Control) Organ Presets u8 hex_switch_state [8]; u8 kb_midi_port = 16; s8 transpose = 0; u8 kb_midi_chan = 0; u8 prg = 0; ///////////////////////////////////////////////////////////////////////////// // This hook is called after startup to initialize the application ///////////////////////////////////////////////////////////////////////////// void APP_Init(void) { // initialize all LEDs //MIOS32_BOARD_LED_Init(0xffffffff); // initialize DIN arrays int row; for(row=0; row<MATRIX_NUM_ROWS; ++row) { din_value[row] = 0xff; // default state: buttons depressed } // initialize all pins of J5C, as outputs in Push-Pull Mode u8 pin; for(pin=8; pin<11; ++pin){ MIOS32_BOARD_J5_PinInit(pin, MIOS32_BOARD_PIN_MODE_OUTPUT_PP); MIOS32_BOARD_J5_PinSet(pin, 0);}// ensures initial state of LED's are off // initialize all pins of J5A and J5B, as inputs in Pull-Up Mode for(pin=0; pin<7; ++pin) MIOS32_BOARD_J5_PinInit(pin, MIOS32_BOARD_PIN_MODE_INPUT_PU); // initialize MIOS32 Timer #0, so that Timer() function is // called each 100 uS: MIOS32_TIMER_Init(0, 100, Timer, MIOS32_IRQ_PRIO_MID); // start matrix scan task xTaskCreate(TASK_MatrixScan, (signed portCHAR *)"MatrixScan", configMINIMAL_STACK_SIZE, NULL, PRIORITY_TASK_MATRIX_SCAN, NULL); } ///////////////////////////////////////////////////////////////////////////// // This timer function is called periodically each 100 uS ///////////////////////////////////////////////////////////////////////////// static void Timer(void) { ++timestamp; } ///////////////////////////////////////////////////////////////////////////// // This task is running endless in background ///////////////////////////////////////////////////////////////////////////// void APP_Background(void) { // endless loop: print status information on LCD while( 1 ) { MIOS32_BOARD_LED_Init(0xffffffff); // toggle the state of all LEDs (allows to measure the execution speed with a scope) //MIOS32_BOARD_LED_Set(0xffffffff, ~MIOS32_BOARD_LED_Get()); } } ///////////////////////////////////////////////////////////////////////////// // This hook is called when a MIDI package has been received ///////////////////////////////////////////////////////////////////////////// void APP_MIDI_NotifyPackage(mios32_midi_port_t port, mios32_midi_package_t midi_package) { } ///////////////////////////////////////////////////////////////////////////// // This hook is called before the shift register chain is scanned ///////////////////////////////////////////////////////////////////////////// void APP_SRIO_ServicePrepare(void) { } ///////////////////////////////////////////////////////////////////////////// // This hook is called after the shift register chain has been scanned ///////////////////////////////////////////////////////////////////////////// void APP_SRIO_ServiceFinish(void) { } ///////////////////////////////////////////////////////////////////////////// // This hook is called when a button has been toggled // pin_value is 1 when button released, and 0 when button pressed ///////////////////////////////////////////////////////////////////////////// void APP_DIN_NotifyToggle(u32 pin, u32 pin_value) { } ///////////////////////////////////////////////////////////////////////////// // This hook is called when an encoder has been moved // incrementer is positive when encoder has been turned clockwise, else // it is negative ///////////////////////////////////////////////////////////////////////////// void APP_ENC_NotifyChange(u32 encoder, s32 incrementer) { } ///////////////////////////////////////////////////////////////////////////// // This hook is called when a pot has been moved ///////////////////////////////////////////////////////////////////////////// void APP_AIN_NotifyChange(u32 pin, u32 pin_value) { } ///////////////////////////////////////////////////////////////////////////// // This task is called to scan the button matrix ///////////////////////////////////////////////////////////////////////////// // will be called on button pin changes (see TASK_MatrixScan) void BUTTON_NotifyToggle(u8 row, u8 column, u8 pin_value) { // determine pin number based on row/column // based on pin map for Fatar keyboard provided by Robin (see doc/ directory) // tested with utils/test_pinmap.pl static u32 switch_timestamp[KEYBOARD_NUM_PINS]; u8 second_switch =0; u8 send_note_on = 0; u8 send_note_off = 0; u32 delta = 0; u8 note_number = 0; int pin = 0; //u8 hex_val = 0; //left hand keys if((column >=0 && column <=7 ) && (row >= 0 && row <= 9) && (row % 2 == 0)){//even pin = 8 * row + 2 *(7 - column);} if((column >=0 && column <=7 ) && (row>= 0 && row <= 9) && (row % 2 == 1)){//odd pin = (8 * (row -1) + (2 * (7 - column)) + 1); } //non-key switches if((column >=0 && column <=7 ) && (row >= 10 && row <= 11)){ pin = 8* row + 7 - column; // USB/ Midi Switch choose USB for PC and UART0 for external Midi Piano Module if(pin == 95 && pin_value == 0){ toggle_state_port ^= 0x01; MIOS32_BOARD_J5_PinSet(8,!toggle_state_port); toggle_state_port == 1 ? (kb_midi_port = USB0) : (kb_midi_port = UART0); } // Hex Sw to determine midi channel u32 hex_switch_state_index = pin - 80; hex_switch_state[hex_switch_state_index] = (pin_value ==0) ? 1 :0; if(pin >=80 && pin <= 87){ //Midi Channel set by Hex Switch kb_midi_chan = ((hex_switch_state[0]) | ((hex_switch_state[1])<<1) | ((hex_switch_state[2])<<2) |((hex_switch_state[3] )<<3)); //Program Change, Hex Switch used to provide 16 presets for Midi Piano Module with only 16 presets. prg = ((hex_switch_state[4]) | ((hex_switch_state[5])<<1) | ((hex_switch_state[6])<<2) |((hex_switch_state[7] )<<3)); //second hex switch to provide program change only for DIN0 Midi Out if((toggle_state_port == 0)) MIOS32_MIDI_SendProgramChange(kb_midi_port, kb_midi_chan, prg); } // enable sustain pedal or sostenuto pedal Sw located on LH Panel if(pin == 90 && pin_value == 0) { toggle_state_pedal ^= 0x01; MIOS32_BOARD_J5_PinSet(10,toggle_state_pedal);} #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG("toggle_state_port=%d, prg=%d, kb_midi_chan=%d, kb_midi_port=%d\n", toggle_state_port, prg, kb_midi_chan, kb_midi_port); #endif //soft pedal located on foot pedals if(pin == 89) {// send soft pedal CC MIOS32_MIDI_SendCC (kb_midi_port, kb_midi_chan, 67, pin_value == 0 ? 127 : 0);} // sustain pedal located on foot pedals same switch as sostenuto below if(pin == 88 && toggle_state_pedal == 0) { // send soft pedal CC MIOS32_MIDI_SendCC (kb_midi_port, kb_midi_chan, 64, pin_value == 0 ? 127: 0) ;} //sostenuto pedal located on foot pedals if(pin == 89 && toggle_state_pedal == 1) { // send sostenuto pedal CC MIOS32_MIDI_SendCC (kb_midi_port, kb_midi_chan, 66, pin_value == 0 ? 127 : 0 ) ;} //Panic button, Midi All Notes Off No Sw yet if(pin == 91 && pin_value == 0) { MIOS32_MIDI_SendCC (kb_midi_port, kb_midi_chan, 123, 0);} //transpose buttons if(pin == 92 && pin_value == 0){//pin 92 is RH Transpose Button ie + Transpose (Higher Note) transpose = transpose +1;} if(pin == 93 && pin_value == 0){//pin 93 is LH Transpose Button ie + Transpose (Lower Note) transpose = transpose -1;} if(transpose > 12){ transpose = 12;} if(transpose < -12){transpose = -12;} // Presets Arrays char * preset[15] = {"Dark Grand", "Classic Grand", "Mellow Ivory", "Rock Piano", "Warm Elect Piano", "Studio Elec Piano", "B3 Organ", "Rock Organ", "Vibes ", "Bright Vibes ", "Strng Bass/Piano", "Elect Bass/Organ", "Synth Tines", "Piano Bell", "Str Bass/E Piano"}; // Show transpose and Preset on LCD MIOS32_LCD_Clear(); MIOS32_LCD_CursorSet(0,0); MIOS32_LCD_PrintFormattedString ("%s", preset[prg]); MIOS32_LCD_CursorSet(0,1); MIOS32_LCD_PrintFormattedString ("TRANSPOSE %d",transpose); //Swell (Volume) To enable Pot to control Midi Volume forFixed Volume Organ sounds if(pin == 94 && pin_value == 0){ toggle_state_swell ^= 0x01; MIOS32_BOARD_J5_PinSet(9,toggle_state_swell);} //alter pot #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG(" transpose=%d, pin=%d, column=%d\n", transpose, pin, column); #endif } //right hand keys if((column >=8 && column <=15 ) && (row >= 0 && row <= 11) && (row % 2 == 0)){//even pin = (8 * row + 2 * (15 - column ) + 96);} if((column >=8 && column <=15 ) && (row>= 0 && row <= 11) && (row % 2 == 1)){//odd pin = (8 * (row -1) + (2 * (15 - column ) ) + 1 +96); } // following check ensures that we never continue with an unexpected/invalid pin number. // e.g. this could address a memory location outside the last_timestamp[] array! // print a warning message in this case for analysis purposes if( pin < 0 || pin >= KEYBOARD_NUM_PINS ) { #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG("WARNING: row=0x%02x, column=0x%02x, pin_value=%d -> pin=%d NOT MAPPED!\n", row, column, pin_value, pin); #endif return; } if(((column >=0 && column <=7 ) && (row >= 0 && row <= 9)) || ((column >=8 && column <=15 ) && (row >= 0 && row <= 11))){ // first or second switch if a key? second_switch = (pin & 1); // 0 if first switch, 1 if second switch // the note number (starting from A-0 = 21) Note use of transpose variable if((column >=0 && column <=7 ) && (row >= 0 && row <= 9)){//LH keys note_number = transpose + 21 + (pin >> 1);} if((column >=8 && column <=15 ) && (row >= 0 && row <= 11)){//RH keys note_number = transpose + 13 + (pin >> 1);} if( note_number > 127 ) // just another check to ensure that no invalid note will be sent note_number = 127; // we have three transitions which are for interest: // a) first switch changes from 1->0 (pin_value == 0): // - store the current timestamp // b) second switch changes from 1->0 (pin_value == 0): // - calculate delta between current timestamp and timestamp captured during a) // - do this only if the captured timestamp is != 0 (see also c) // - calculate velocity depending on the delay // - send Note On event // c) first switch changes from 0->1 (pin_value == 1): // - send Note Off event (resp. Note On with velocity 0) // - clear captured timestamp (allows to check for valid delay on next transition) if( pin_value == 0 ) { if( second_switch == 0 ) { // first switch switch_timestamp[pin] = timestamp; } else { // second switch delta = timestamp - switch_timestamp[pin -1]; send_note_on = 1; } } else {//pin_value = 1 if( second_switch == 1 ) { // 2nd switch switch_timestamp[pin] = 0; send_note_off = 1; } } // now we know: // - if a note on or off event should be sent // - the measured delta (note on only) if( send_note_on ) { // determine velocity depending on delta int velocity = 127 - (((delta -kb_del_fast) * 127) / (kb_del_slow-kb_del_fast)); // saturate to ensure that range 1..127 won't be exceeded if( velocity < 1 ) velocity = 1; if( velocity > 127 ) velocity = 127; MIOS32_MIDI_SendNoteOn(kb_midi_port, kb_midi_chan, note_number, velocity); #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG("row=%d, column=%d, pin_value=%d -> pin=%d, timestamp=%u, delta=%d, velocity=%d,-> NOTE ON\n", row, column, pin_value, pin, timestamp, delta, velocity); #endif } else if( send_note_off ) { // send Note On with velocity 0 MIOS32_MIDI_SendNoteOn(kb_midi_port, kb_midi_chan, note_number, 0x00); #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG("row=%d, column=%d, pin_value=%d -> pin=%d, timestamp=%u -> NOTE OFF\n", row, column, pin_value, pin, timestamp); #endif } else { #if DEBUG_VERBOSE_LEVEL >= 2 DEBUG_MSG("row=%d, column=%d, pin_value=%d -> pin=%d, timestamp=%u -> IGNORE\n", row, column, pin_value, pin, timestamp); #endif } } } static void TASK_MatrixScan(void *pvParameters) { while( 1 ) { // wait for next timesplice (1 mS) //vTaskDelay(1 / portTICK_RATE_MS); MIOS32_SPI_TransferModeInit(MIOS32_SRIO_SPI, MIOS32_SPI_MODE_CLK1_PHASE1, MIOS32_SPI_PRESCALER_8); // loop: // - latch DIN/DOUT values // - shift selection pattern for *next* row to DOUT registers // - read DIN values of previously selected row // since we need to select the first row before the first DIN values are latched, we loop from -1 // to handle the initial state int row; for(row=-1; row<MATRIX_NUM_ROWS; ++row) { if( row >= 0 ) { // not required for initial scan // latch DIN values MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 0); // spi, rc_pin, pin_value MIOS32_DELAY_Wait_uS(1); MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 1); // spi, rc_pin, pin_value } // determine selection mask for next row (written into DOUT registers while reading DIN registers) u16 select_row_pattern = ~(1 << (row+1)); #if MATRIX_DOUT_HAS_SINK_DRIVERS select_row_pattern ^= 0xffff; // invert selection pattern if sink drivers are connected to DOUT pins #endif // read DIN, write DOUT u8 din0 = MIOS32_SPI_TransferByte(MIOS32_SRIO_SPI, (select_row_pattern >> 8) & 0xff); u8 din1 = MIOS32_SPI_TransferByte(MIOS32_SRIO_SPI, (select_row_pattern >> 0) & 0xff); // latch new DOUT value MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 0); // spi, rc_pin, pin_value MIOS32_DELAY_Wait_uS(1); MIOS32_SPI_RC_PinSet(MIOS32_SRIO_SPI, MIOS32_SRIO_SPI_RC_PIN, 1); // spi, rc_pin, pin_value if( row >= 0 ) { // combine read DIN bytes to 16bit value u16 din_pattern = (din1 << 8) | din0; // check if values have been changed via XOR combination with previously scanned value u16 changed = din_pattern ^ din_value[row]; if( changed ) { // store changed value din_value[row] = din_pattern; // notify changed value int column; for(column=0; column<16; ++column) { u16 mask = 1 << column; if( changed & mask ) BUTTON_NotifyToggle(row, column, (din_pattern & mask) ? 1 : 0); } } } } } } Please note that I have added 16 diodes to the scan matrix: 4 to provide 16 Midi channels, 4 to provide 16 program changes plus others to change midi out channel, provide soft and sustain pedal and transpose + and -. The debug messages need cleaning up. The LCD messages are placed in the body of the button_notify_toggle function. Most of the complicated code is yours from a few years back. Robin
  5. I have tried many different variations to Print to the LCD Display but no luck using APP_Background. I am not sure of the exact operation of this Function but believe that it is used when higher priority tasks are idle. It may be that this idle time does not occur in my program. I should confirm that I am able to display the Transpose status and the Program Change (Presets on my piano Midi Module) by placing the LCD commands in the body of Button_Modify_Toggle. However I would like to use a lower priority method if at all possible. In the near future I want to add Black Key Keyboard Delay to the program. The Timer is set to 100 us. "// initialize MIOS32 Timer #0, so that Timer() function is // called each 100 uS: MIOS32_TIMER_Init(0, 100, Timer, MIOS32_IRQ_PRIO_MID); " Could this low time period prevent APP_Background from working? Any help will be welcomed. Robin
  6. Note This message has been edited from the original. I have thought about the problem and realise that it s very likely that App_Background must be working otherwise the system would not work. I am going to conduct one or more experiments to determine what proportion of time the scanning program takes of the total time available. I suspect that this is a very high proportion. Robin
  7. Thanks Thorsten I will follow your suggestion and report back. Robin
  8. As mentioned previously during the last few weeks on the forum I am revising my digital piano program. This based on TK's example. After a few problems I have now added a few extra functions to my program, namely:- Transpose A simple method using two momentary action membrane switches has been used. (Transpose +) and (Transpose -). I have limited the transpose range to +- 12 semitones. Hex Thumbwheel Switches I have also added a rotary (thumbwheel) 16 position hex switch to select Midi Channel. ( Later on I will use the same type of switch to control an send Midi Program Changes to my hardware Piano Module.) LCD I would like to show the Transpose status eg "Transpose +2" on a small 2 line LCD display and perhaps the name of the piano module preset. eg " Grand Piano 1" This is a new area for me. My main concern is to preserve the speed of the fast scan and to avoid any interference by the LCD program additions. Please give me a few pointers. Robin
  9. Thanks again Pete I took up your suggestion to rebuild the system. I have a 2nd PC where I attempted to build the toolchain etc. I failed ! However in parallel I examined the environmental variables at each stage and actually found some errors in PC no 1. This is difficult to understand. I had used PC No 1 a few weeks ago to make a simple code change and then suddenly it failed to work. I am up and running now. Robin
  10. Pete When the program was developed by TK the"clcd" was valid, (Version 1104) The toolchain shows conflicts and the current attempts using MAKE yield:- Robin PS
  11. Thanks for the reply I have somehow manage to restore a makefile. I am back to my first problem. Here is the result when trying to compile I have looked at the LCD module in the toolchain and it shows an additional directory "universal" in the path. Robin
  12. I have decide to revise my digital piano to include the Dio-Matrix module and to make some minor changes to the program. The first problem was a makefile problem which related to a non existing LCD file. I decided to update the SVN repository. This caused another problem; the makefile has been deleted! I am using a modified Fast Scan Matrix in the examples in the MIOS Toolchain. I do not really understand this aspect of programming, although I have a small knowledge of MIOS C programming. Can anyone help with the missing makefile? Thanks Robin
  13. I notice in the Tutorial 011 AIN that the analog input is explicitly masked in MIOS32_config.h Is it necessary to do this if the Analog input is initialised in void APP_Init(void) by defining specific J5 pin(s) as an analog input? In other words are both tasks necessary? Regards Robin
  14. Thank you again Thorsten The timestamp method using the MIOS Timer is now working. It provides a better "time" resolution than before. I intend to use the MIOS STOPWATCH to measure the scan rate. We will then know the scan parameters more accurately. I'm guessing that that the system has 10X the resolution of the original 1mS scan rate. The fastest (loudest) figure from the original system was about 3 - 4 Ms. With the latest program the loudest key strike corresponds to a delta count of about 35. I should add that these figures are based on a SPI prescaler of 8. I have incorporated several soft synths into a trial version of Mixcraft. This means that I can select various piano or organ sounds with a finger press on my touch sensitive monitor. I am very pleased with the result. All that remains is to incorporate an organ volume pedal and I will be finished. Of course I still need to make a matching piano stool in beech wood! Best Wishes Robin
  15. My ideas to use MIOS STOPWATCH for delay measurement were faulty. There is a possibility that the method could work provide two problems can be overcome. Operation of MIOS STOPWATCH Can multiple Time measurements be made following a single Reset command. Can the Reset Function be programmed to occur at Regular time intervals on a continuous basis? A time period of 1 second would be ideal. However I think that it would be possible to use a lower period eg 50 - 60 mS.? I will appreciate any help with the two questions. Thanks Robin
  16. Thanks to Peter and TK. I will follow your suggestion and use AIN on J5. Best Regards Robin
  17. Thanks to Peter and TK. I will follow your suggestion and use AIN on J5. Best Regards Robin
  18. Thanks to Peter and TK. I will follow your suggestion and use AIN on J5. Best Regards Robin
  19. I have completed the digital piano project in terms of my original needs. I have just added 2 midi channels so that I can split the keyboard. This additional work is partially coded. However I want to play a Hammond Organ, DX7 and Prophet softsynth that I purchased a few years ago. I need to incorporate a organ type "swell" pedal into the system. This is just a volume control. I will use the foot pedal to control the generation of the appropriate Midi CC. The distance from the main board to the pedal is about 1 metre. My belief is that a digital solution would be better than an analog one. I have no familiarity with faders or encoders. Are there "smooth" rotary switches? Are these method worth considering? Or are there other alternatives? I have a foot controlled pedal from an old organ that uses a potentiometer. Thanks for your help. Robin
  20. I have managed to solve my LED problem without the need for any alteration to the "standard" MIOS32 board set up. I am using 2 rotary BCD switches to define the keyboard max and min delay parameters. These determine the max and min loudness. I will use 2 Thumbwheel rotary hex switches to select two midi channels. One of these will be used when all the notes on the keyboard are using a single Midi channel. The second will be used for a split keyboard. In the latter case both Midi channel rotary thumbwheel switches will be used. I'm currently only using 3 pins to provide 3 pedal Midi control signals. A few more pins will be needed for the split controls This will mean that I will need to use another row on the 16 X 16 matrix. This additional row will provide 16 more pins. I intend to limit the matrix to 13 rows. This will have nearly 20% impact on scan time and will require less memory. All this means that I still have 11 of the pins available on J5. (One is used as a DOUT for pedal status). I can use the rest of the pins as an analog inputs or for additional DOUT's. Here is the code I used to provide the keyboard parameters and the Midi Channel. // Hex Sw to determine variable kb_del_fast u32 hex_switch_state_index = pin - 84; u8 midi_chn_1; hex_switch_state[hex_switch_state_index] = (pin_value ==0) ? 1 :0; if(pin >=84 && pin <= 95) kb_del_fast = 25 + ((hex_switch_state[0]) | ((hex_switch_state[1])<<1) | ((hex_switch_state[2])<<2) |((hex_switch_state[3] )<<3)); kb_del_slow = 100*((hex_switch_state[11]) | ((hex_switch_state[10])<<1) | ((hex_switch_state[9])<<2) |((hex_switch_state[8] )<<3));// sw order reversed midi_chn_1= ((hex_switch_state[7]) | ((hex_switch_state[6])<<1) | ((hex_switch_state[5])<<2) |((hex_switch_state[4] )<<3));// #if DEBUG_VERBOSE_LEVEL >= 1 DEBUG_MSG("pin_value=0x%01x -> pin=%d, kb_del_fast=%d, kb_del_slow=%d,midi_chn_1=%d \n", pin_value, pin, kb_del_fast, kb_del_slow, midi_chn_1); #endif Both type of switches "chatter" a little. It does not matter because the values are stored. After a few alterations the correct values are determined. This is demonstrated by the use of MIOS STUDIO and the Debug code. This probably of interest to a few people. However it gives an example of the use of MIO32 and shows how arrays are used. Regards Robin
  21. MIOS STOPWATCH Operation and further thoughts 4th Edit I have removed all my ramblings about how to use the MIOS STOPWATCH. The were completely wrong. Here is a small section of code that shows how MIOS STOPWATCH can be used to measure the delay between two switches closing. This is needed to determine the velocity of the Note On Midi signal. The initialisation and declaration of some of the variables are not shown. // We have three transitions which are of interest: // a) first switch changes from 1->0 (pin_value == 0): // - Reset Stopwatch and set the Reset Flag = 1 // - do this only if the Reset Flag is 0 // b) second switch changes from 1->0 (pin_value == 0): // - measure delay using the MIOS32_STOPWATCH_ValueGet() function // - calculate velocity depending on the delay // - send Note On event // c) first switch changes from 0->1 (pin_value == 1): // - send Note Off event (resp. Note On with velocity 0) // - clear Reset Flag int key_ix = pin & 0xfffffffe; int delay = -1; u8 send_note_on = 0; u8 send_note_off = 0; if( pin_value == 0 ) { if(( second_switch == 0 ) && (SW_Reset_Flag[key_ix] == 0)){ // first switch MIOS32_STOPWATCH_Reset(); SW_Reset_Flag[key_ix] = 1; } else { // second switch delay = MIOS32_STOPWATCH_ValueGet(); send_note_on = 1; } } else { if( second_switch == 0 ) { // first switch (SW_Reset_Flag[key_ix] = 0); send_note_off = 1; } } This code is based on Thorsten's original example using timestamps. The changes above enable the resolution to be improved. I now am using 0.1mS rather than 1mS. If necessary the resolution could be even smaller. Thank you again Thorsten for suggesting the idea. Best Regards Robin
  22. Hi Thorsten This evening I inserted the "SPI Prescalar" statement where I think you meant, not where I place it initially! It seems to work with a pre-scalar value of 8 . I need to do further work over a longer period of time with the soft synth to be sure. I will report back later to confirm this. MIOS STUDIO gives the normal 4 timestamp values with each press of the key. Later Edit I've been looking at the Function used to determine the delay. This is derived from timestamp. // determine timestamp (we need it for delay measurements) mios32_sys_time_t t = MIOS32_SYS_TimeGet(); u32 timestamp = 1000*t.seconds + t.fraction_ms; Speeding up the system will not improve the minimum resolution ie 1mS. Is there some way to improve the minimum time resolution or are we forced to examine another method?? Robin
  23. Currently I am using one of the pins of Connector J5A as a DOUT to drive an LED to show the Status of a pedal on my digital piano. J5B and J5C are connected to hex switches and used to define two variables. It would be convenient if I could use J5A to connect an additional rotary hex switch to change midi channels. I am using the following connectors, J8/9, J5 (all), J17(usb), J15A This means that I need to find a spare pin. I've looked at various options. 1) The CAN interface. I am unlikely to use this. The pins are already used with the STM Primer and provide for 2 LED's in that mode. 2) I will not need both Midi In/Out. Currently I use neither. 3)There are other possibilities including J4,J3,J16,J19. Any guidance will be appreciated. Regards Robin
  24. Hello Thorsten I have inserted the SPI initiate function as follows static void TASK_MatrixScan(void *pvParameters) { MIOS32_SPI_TransferModeInit(MIOS32_SRIO_SPI, MIOS32_SPI_MODE_CLK1_PHASE1, MIOS32_SPI_PRESCALER_4); while( 1 ) { // wait for next timesplice (1 mS) vTaskDelay(1 / portTICK_RATE_MS); // determine timestamp (we need it for delay Please note that the prescalar value of 4 seems to work! It seems to be too good to be true! Is there a way to check that that the transfer rate is being increased? Robin
  25. About 1 week has elapsed since I asked 2 questions about the Fast Scan Example. Question 1 I have spent some time on Question 1 and seem to have solved the problem with some fairly simple code in the initialisation section. I can now define the two keyboard delay variables with either hex or BCD rotary switches. This means that the two variables will be determined by reading the two switches at switch-on. These are used to determine the loudness (velocity) sensitivity of each note. You will need to read TK's code to see the relevance. Question 2 I would like to explore how fast the system can run. The main benefit will be that the velocity resolution will be improved. It looks as if a practical Fast Keyboard Delay will be 3 or 4 mS and the Slow Delay somewhere about 30 mS. Bear in mind that the the delay measurement is accurate to 1 mS. This means that loud notes could have an error of 1 in 3 ie 33%. From the Functions reference the speed of the system is fixed by the following Function. s32 MIOS32_SPI_TransferModeInit ( u8 spi, mios32_spi_mode_t spi_mode, mios32_spi_prescaler_t spi_prescaler ) (Re-)initializes SPI peripheral transfer mode By default, all SPI peripherals are configured with MIOS32_SPI_MODE_CLK1_PHASE1 and MIOS32_SPI_PRESCALER_128 This seems to be defined in s32 MIOS32_SRIO_Init(u32 mode) { in the mios32/trunk/common/mios32_srio.c file. Is it the just a matter of altering the pre-scalar values or are there RTOS or other implications? Regards Robin
×
×
  • Create New...