Jump to content

Can I toggle controls with boolen operators?


henrygr
 Share

Recommended Posts

When you're using the Analogue Pins from J5, you can stay in the AIN_Notify() Function, no need to setup anything else.

No variable needed then.

Just add (pseudo-code!):

switch(pin) {
  case 4:
    if(value > 64) {
        // switch selected
    } else {
        // switch not selected
    }
    break;
  case 5:
    if(value > 64) {
        // switch selected
    } else {
        // switch not selected
    }
    break;
  case 6:
    if(value > 64) {
        // switch selected
    } else {
        // switch not selected
    }
    break;
}

Note that this works _only_ inside the AIN_Notify() Function.

If you choose for other Pins, there has to be another implementation.

The function will be called, whenever the state of the AIN-Pin changes.

Best,

Michael

Link to comment
Share on other sites

  • Replies 68
  • Created
  • Last Reply

Top Posters In This Topic

Thank You Michael,

This looks superb (not that I have an eye for code, but I'm getting the idea).

Two points that I need to clarify:

1. As I have one ainx connected and the core is running in unmuxed mode, would I be better of connecting the 3 gang switch to three spare pins on the multiplexer?

2. I assume (although in my trade assumption is the mother of all f**k ups- I'm a chef) that when you code

switch(pin)

the (pin) is in direct reference to the pin on the core/multiplexer, and is to be replaced by a value accordingly. So how do I find out the value of the specific pin?

Once Again Many Thanks,

Mark.

Link to comment
Share on other sites

1. As I have one ainx connected and the core is running in unmuxed mode, would I be better of connecting the 3 gang switch to three spare pins on the multiplexer?

That's right. Just connect it to the spare pins on the multiplexed AINX-module.

2. I assume (although in my trade assumption is the mother of all f**k ups- I'm a chef) that when you code

switch(pin)

the (pin) is in direct reference to the pin on the core/multiplexer, and is to be replaced by a value accordingly. So how do I find out the value of the specific pin?

That's right; from the function overview:

[tt]void AIN_NotifyChange(unsigned char pin, unsigned int pin_value)[/tt]

This function is called by MIOS when a pot has been moved

C_IN Pot number in <pin>

10bit value in <pin_value>

So, pin contains the current pin (which initiated the call of the notification) and pin_value contains the current value of that pin; ranging from 0 to 1023 (switch closed if pin_value > 512)

You get the 7bit value (0 - 127) by calling [tt]unsigned char MIOS_AIN_Pin7bitGet(unsigned char pin)[/tt], but to determine your switched state 10bit is fine :)

It just has to be greater than half the value, then you know for sure it's closed and vice versa.

Cheers,

Michael

Link to comment
Share on other sites

OOOOH

So near yet so far.....

Michael,

I decided to test the example you gave me by keeping it simple, and basically using the first two pots only. So, I want to tell the PIC to switch the function of pin one, based on the position of pin two. In this example I wanted to keep it really easy, so I chose a CC event change (Reverb depth to Chorus depth). So here is the code:

void Init(void) __wparam
{
  // initialize the AIN driver
  MIOS_AIN_NumberSet(2);  
  MIOS_AIN_Muxed();        
  MIOS_AIN_DeadbandSet(7); 
}

void AIN_NotifyChange(unsigned char pin, unsigned int pin_value) __wparam {


switch (pin) {
 case 0x01:
    if(pin_value > 512) {
          
  MIOS_MIDI_TxBufferPut(0xb0); 
  MIOS_MIDI_TxBufferPut(0x5b); 
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin));
    } else {
  MIOS_MIDI_TxBufferPut(0xb0); // first value from table
  MIOS_MIDI_TxBufferPut(0x5d); // second value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin));
    }
   
 }
}

All I've managed to do though is to get the second pot to change its own function on its own movement. ie Chourus Depth up to the value of 64 and Reverb from there on.

Now, I recken one of two things

1. You are raising your eyes to heaven in total disbelief that I actually find this to be a problem

2. You are on the floor rolling around laughing at my ignorance.

Both of these situations are totally understandable. But please, once more, wipe the tears from your eyes and help me.

Thanks once again.

Mark.

When I get this completed, I will write the WIKI how to (and why to most importantly) do this little job. After that I'll wash your car for a whole year.....

Link to comment
Share on other sites

Hi Mark,

although you could possibly wash my bike, I don't think that's needed ;D

some comments:

1. if you're using a [tt]switch[/tt] case, there's no need for [tt]if then else[/tt]

2. pins are counted from 0, not from 1. So if you connect your switch to pin 1 and 2 you have to address them as 0 and 1

3. you're asking for [tt]MIOS_AIN_Pin7bitGet(pin)[/tt] both times but pin is an overgiven value (see the AIN_NotifyChange parameters)

4. instead of calling [tt]MIOS_AIN_Pin7bitGet[/tt], you could also invoke a tiny bitshifting calculation: [tt]pin_value >> 3[/tt]. That means division by 2 with every bit (here: [tt]pin_value / 2 / 2 / 2 [/tt]). I don't know though which one is faster. I'd assume the bitshift, but I really don't know.

void AIN_NotifyChange(unsigned char pin, unsigned int pin_value) __wparam {

switch (pin) {
 case 0:
    if(pin_value > 512) {
      MIOS_MIDI_TxBufferPut(0xb0); 
      MIOS_MIDI_TxBufferPut(0x5b); 
      MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin));
    }
    break;
 case 1:
    if(pin_value > 512) {
     MIOS_MIDI_TxBufferPut(0xb0);
     MIOS_MIDI_TxBufferPut(0x5d);
     MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin));
    }
    break;
 }

Keep it up!

(wasn't that difficult, was it?)

Cheers,

Michael

Edit: I just noticed, there might be a misunderstanding => right now, the code sends a message ONLY when the switch gets closed (>512). To implement an action if the switch is released you can add [tt] } else { ...[/tt]; but it's apparently that pins 1 to 2 are NOT pressed, if pin 0 is active, so you can implement your logic in the appropriate case section...

hopefully I haven't confused you now... ;)

Link to comment
Share on other sites

right, it's switch PIN.

it's the way I've posted above.

that's the syntax

switch(pin):

  case (pin==0): // the pin==0 is just to show you what happens here!

    // do something

    break; // end the case and break out the switch;

              // without break, all the rest would be processed

  case (1):

  case (2):

    // do something for pin 1 AND pin 2:

    break;

  default (whatever):

    // this is the standard definition if nothing matches

    // it's optional

    break;

}

That's all.

It's just another syntax for a complex if then else.

Maybe it will help you to look out for a good online C-Book, there are some...

I noticed one mentioned here in the forum by stryd_one, just a week ago...

Best,

Michael

Link to comment
Share on other sites

the code does this:

switch(pin) <--- takes a look at the var passed to it, which it's decided to call pin (meaningful variable names rock)

case(1) <--- if the variable (in this case pin) is 1 do whatever it is you need to do, if not move on to the next case statement

default <-- this is the catch-all - but only runs if the variable doesn't match any of the other case statements above the defautl

break <-- this jumps out of the switch, it's put in the case statement operations to stop going through the rest of the options in the switch once you've found the one you want.

Link to comment
Share on other sites

Nearly there.

Have written this to test my code. It is supposed to change the affect that pots one and two have dependant on the value of the switch at three.

When three is closed the other two send an 'effect 1' signal on their respective channels. When open, it is an 'effect 3' signal

const unsigned char pot_event_map[2][3] = {

  {0xb0, 0x5b, 0x5d},   {0xb1, 0x5b, 0x5d},    
  };



void AIN_NotifyChange(unsigned char pin, unsigned int pin_value) __wparam
{

   int knob;
{
   switch(pin){
         case 2:
         if(pin_value > 512){         
         knob=1; 
         
     }else{
         knob=2;

}    break;    
}
}   
 // send mapped CC value
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][0]); // first value from table
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][knob]); // second value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin)); // 7bit pot value
}

However, all that is returned is erroneous messages on all three switches!

Any ideas as to where I have erred.

Mark.

Link to comment
Share on other sites

fist of all, you don't need not '[tt]int[/tt]' for [tt]knob[/tt], take '[tt]unsigned char[/tt]', it uses just 1 byte instead of 2 or 4 bytes.

next, you still haven't got the right syntax: there's only one pin mentioned. you code will only be processed if the state of pin 2 changes:

[tt]AIN_Notify_Change(pin,pin_value)[/tt] is only been called if [tt]pin_value[/tt] of [tt]pin[/tt] changes.

Read your function line for line in a mathmatical manner and "calculate" about what happens, if it's called when [tt]pin_value[/tt] changes on [tt]pin 1[/tt]!

;)

Michael

Link to comment
Share on other sites

OK, (2.10am)

Just got home from work.

stryd_one:

Erroneous- not the correct result, but consistant in its return. Lots of data I didn't even bother quantifying. Funny enough, earlier on I  forgot the whole 'switch' command in the script and gave 'knob' a static value at the very beginning of the main.c page and got the same result. Then I moved the 'int knob=2;' to within the wpram calling pot movement and it worked like a dream! Food for thought? (Remember- I'm a chef, not a programmer- this was my own way of debugging)

An 'if/else' in a switch statement is plausible. You are not allowed to use expressions or ranges.

audiocommander:

fist of all, you don't need not 'int' for knob, take 'unsigned char', it uses just 1 byte instead of 2 or 4 bytes.

Correct. At the time of posting I figured it was most probably a problem with how I called the variable. I think that is where the problrm lies. Is the unsigned part of it necessary? All values are positive.

As regards the rest of your note, I think I explained above that it worked perfectly when when I gave 'knob' a value- yes, the function line works. My problem is making sure the variable is passed on in its true integer form.

Time for bed.

Will test it all in the morning.

I LIKE this C code thing............

Mark.

Link to comment
Share on other sites

stryd,

switch statements don't use "else" in them, but you can have an if statement within the one of the cases of the switch.

ie.

switch (x) {

      case 1:

                If (y>0) {

                      do whatever here;

                }

                break;

    default:

                catch all here       

}

switch statements are great when you have lots of options, but they can be confusing at first. If you find yourself getting lost in the logic I suggest you use if/then/else/elseif, and build the switch (or not bother) once you've got the logic right.

Link to comment
Share on other sites

switch statements don't use "else" in them, but you can have an if statement within the one of the cases of the switch.

Heheheh thanks for the explanation David :) I actually knew that stuff, but I somehow missed the 'if' and though he was using 'else' instead of default: ... That's what I get for taking rushed breaks from work to read the forum  ;D

Link to comment
Share on other sites

yeah, but the main logic problem is still there and I think it's because switch and if-then-else has been mixed wrongly:

AIN_NotifyChange is called if the value on the pin changes!

example: change of pin 0 from OFF (0) to ON (1023):

[tt]AIN_NotifyChange(0, 1023) { ... }[/tt]

example: change of pin 2 from ON (1023) to OFF (0):

[tt]AIN_NotifyChange(2, 0) { ... }[/tt]

Now please, before posting another question think about that!

If you got only

[tt]switch(pin) {

case 2:

...

break;

}[/tt]

what about case 0 and 1? The code inside the switch-statement will never ever be executed when pin 0 and 1 change, and remember, it's a three-state switch, so if you switch from 0 to 1 the state of pin 2 does not change (it remains OFF).

And the worst thing is: if you test it with pin 0 and pin 1, your variable "knob" is undeterminded but used to send values, because it's only the switch-statement which isn't executed, but the SendMIDI-commands are indeed processed! No wonder, there's coming garbage...

Please, do proceed as I stated above:

- Read again the switch-syntax, you got it twice, from David and me.

- Then take yourself a quiet minute, get a pen and a paper, set in real numbers for your variables and test it six times, for each pin (0 and 1 and 2) and each value (0 and 1023) and calculate what happens at each step! It will be quite obvious to you.

;) Michael

Edit: and one more hint:

go get yourself a code-editor that supports line indentation. It is obvious your [tt]} else {[/tt] is meant to be an [tt]else[/tt] for the [tt]case[/tt]. If you'd have a correct line indentation, these kind of errors would not happen!

Link to comment
Share on other sites

hey stryd,

sorry man - not trying to teach you to suck eggs, I got all excited about actually being able to give advice rather than being on the other end ;)

Henry,

audiocommander makes some really good points.

When I first started coding I found a trick that helps you get your head around the logic: - before you do any code, write out the steps you need to go through as comments, that way you can work out the logic without adding the confusion of unfamilar code, and it means you've got well commented code (trust me, comments in code are the bomb, esp when in 6 months time you need to make a change to the code and you've forgotten everything to do with that code). Back in university you weren't meant to touch code until you've done you're nasty spiderman (nassi sniderman) or flow chart diagrams.

and yes, get yourself a copy of a decent text editor - I can't get my head round untabbed code, first thing I do when I get some is tab it out, then start work...

Link to comment
Share on other sites

hey stryd,

sorry man - not trying to teach you to suck eggs, I got all excited about actually being able to give advice rather than being on the other end ;)

<snip>

When I first started coding I found a trick that helps you get your head around the logic: - before you do any code, write out the steps you need to go through as comments, that way you can work out the logic without adding the confusion of unfamilar code, and it means you've got well commented code

Hahaha nah it's alll good, I need all the advice I can get when it comes to C :)

That's a really good tip, I like that a lot! I do something similar, but usually overwrite the pseudocode, it never occurred to me to leave it in place and make it into comments

Nazi Spiderman LMAO I never heard that one

Link to comment
Share on other sites

  • 3 weeks later...

I'm back all.

Many thanks for your sympathies.

Had time to reflect on things. Have a look at this.

const unsigned char pot_event_map[27][5] = {
  // Pot 0..7 
   {0xb0, 0xb0, 0x13, 0x1c, 0x4f},   {0xb0, 0xb1, 0x12, 0x1b, 0x17},   {0xb0, 0xb1, 0x11, 0x1a, 0x16},   {0xb0, 0xb1, 0x10, 0x19, 0x15},
   {0xb0, 0xb1, 0x0f, 0x18, 0x14},   {0xb0, 0xb3, 0x0e, 0x17, 0x07},   {0xb0, 0xb2, 0x0d, 0x16, 0x07},   {0xb0, 0xb1, 0x0c, 0x15, 0x07},
  // Pot 8..15 
   {0xb0, 0xb0, 0x54, 0x53, 0x56},   {0xb0, 0xb0, 0x45, 0x5e, 0x59},   {0xb0, 0xb0, 0x4c, 0x5d, 0x57},   {0xb0, 0xb0, 0x42, 0x43, 0x55},
   {0xb0, 0xb0, 0x48, 0x03, 0x44},   {0xb0, 0xb0, 0x47, 0x5b, 0x08},   {0xb0, 0xb0, 0x46, 0x5c, 0x0a},   {0xb0, 0xb0, 0x14, 0x1d, 0x4e},
  // Pot 16..23 
   {0xb0, 0xb0, 0x01, 0x01, 0x01},   {0xb0, 0xb0, 0x0b, 0x0b, 0x0b},   {0xb0, 0xb0, 0x02, 0x02, 0x02},   {0xb0, 0xb0, 0x1e, 0x1e, 0x1e},
   {0xb0, 0xb0, 0x1f, 0x1f, 0x1f},   {0xb0, 0xb0, 0x49, 0x51, 0x4c},   {0xb0, 0xb0, 0x4a, 0x52, 0x07},   {0xb0, 0xb0, 0x4b, 0x09, 0x58},
  // the switch- pots 24, 25 and 26 with harmless info
   {0xbf, 0xbf, 0x77, 0x77, 0x77},   {0xbf, 0xbf, 0x77, 0x77, 0x77},   {0xbf, 0xbf, 0x77, 0x77, 0x77},
  };
Super. Tested all the code by sending one set of variables at a time and they all do what they are suppesed to (except one, but I think it is a programming bug in B4) Now, back to the switch/case funtion
void AIN_NotifyChange(unsigned char pin, unsigned int pin_value) __wparam {



switch (pin) {
 case 24:
    if(pin_value > 512) {
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][0]); // first value from table
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][2]); // third value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin)); // 7bit pot value
    }
    break;
 case 25:
    if(pin_value > 512) {
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][0]); // first value from table
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][3]); // fourth value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin)); // 7bit pot value
    }
    break;
 case 26:
    if(pin_value > 512) {
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][1]); // second value from table
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][4]); // fifth value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin)); // 7bit pot value
    }
    break;

	default:{
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][0]); // first value from table
  MIOS_MIDI_TxBufferPut(pot_event_map[pin][2]); // third value from table
  MIOS_MIDI_TxBufferPut(MIOS_AIN_Pin7bitGet(pin)); // 7bit pot value
    }
 }
}

All I get is the default. If I remove the default from the code I get nothing except the harmless channel 16 messages from the switch itself (pins 24, 25 and 26)

Any ideas?

Aaaargh!

:) :) :) :)

Link to comment
Share on other sites

hello henrygr :)

As I still assume you still don't have no DIN-Board and instead soldered your switch directly to the core, it is very unlikely you'll ever get a notification for pins 24 to 26 (=pins 25 to 27 from the DIN-board, if you count from 1).

You should instead receive notifications for pins 0,1 and 2 (if I remember right)

best ;)

Michael

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
 Share


×
×
  • Create New...