Keypad to display

Attached is a bit of code I’m having a problem getting to run. In actual fact its two bits of code put together. The first bit is scanning a keypad for the number entered and the second bit outputs that number to a seven segment display. (This is just part of a project I’m working on but I need to get it working before I go any further). Both bits of code work because I’ve used them before in previous programs. Albeit on a 28X1 picaxe. This time I’m using a 28X2. Pins B0 to B3 scan the rows on the keypad and pins B4 to B7 output to the display driver 4511B. Can anyone please tell me where I’m going wrong? The other couple of lines of code store the last number entered and reload it to the display on power up.

Code:
power on:
read 0 b1
pinsB = b1

let dirsB = %11111111

symbol row = b4
symbol key = b5

init:
pause 500

main:
key = 0
for row = 0 to 3
	high row
	gosub keyscan
	low row
	
	if key = 1 then gosub route1
	if key = 2 then gosub route2
	if key = 3 then gosub route3
	if key = 4 then gosub route4
	if key = 5 then gosub route5
	if key = 6 then gosub route6
	if key = 7 then gosub route7
	if key = 8 then gosub route8
	if key = 9 then gosub route9

	
next row
goto main

keyscan:

if pinC.1 = 1 then
	key = row * 3 + 1
	do loop while pinC.1 = 1
	elseif pinC.2 = 1 then
	key = row * 3 + 2
	do loop while pinC.2 = 1
	elseif pinC.3 = 1 then
	key = row * 3 + 3
	do loop while pinC.3 = 1
endif
return

route1: let b1 = 1 
	let pinsB=b1 
	goto saveLastRoute
	return
route2: let b1 = 2 
	let pinsB=b1 
	goto saveLastRoute
	return
route3: let b1 = 3 
	let pinsB=b1 
	goto saveLastRoute
	return
route4: let b1 = 4 
	let pinsB=b1 
	goto saveLastRoute
	return
route5: let b1 = 5 
	let pinsB=b1 
	goto saveLastRoute
	return
route6: let b1 = 6 
	let pinsB=b1 
	goto saveLastRoute
	return
route7: let b1 = 7 
	let pinsB=b1 
	goto saveLastRoute
	return
route8: let b1 = 8 
	let pinsB=b1 
	goto saveLastRoute
	return
route9: let b1 = 9 
	let pinsB=b1 
	goto saveLastRoute
	return


saveLastRoute:
	Write 0,b1
	return

goto main
 

eclectic

Moderator
What "problem"?

The first few lines need a bit of jiggling to pass a Syntax check

Code:
poweron: ; **************

let dirsB = %11111111 ; *****

read 0, b1
pinsB = b1
and then what happens?
e
 

hippy

Ex-Staff (retired)
Pins B0 to B3 scan the rows on the keypad and pins B4 to B7 output to the display driver 4511B.
Your 'route0:' through 'route3:' routines set 'pinsB' ( B.0 through B.3 ), which probably messes with the keypad scanning.

Also, shouldn't the 'If key = ...' checks be after the 'next row' ?
 
eclectic: thanks for your reply. Yes put a space where I shouldn’t and missed out a comer this is what happens when you clean up the code for posting. I’d run a syntax check and no errors would show up, this is what I couldn’t understand. I would have expected the keypad number entered to display on the seven segment display, or at least that is the intention.

hippy: thanks also for your reply. In my attempts to solve the problem I moved the gosub commands to different locations within the code, and on programming if I placed them in the position shown the display showed a 0 and if I moved them to after ‘next row’ the display still showed a 0 but still no input from the keypad, however I agree they probably are better after ‘next row’.
As for your first statement, this is where I start to struggle. How do I set the pins B4 through B7 to output to the display? (later in the project I need further output pins to drive a stepper motor so understanding this part is essential).
Take a look at the bit of code attached. I used this to check that the keypad was scanning correctly. There is a LED hooked up to pin B4, the gosub commands are in the original position and the LED would flash off every key number entered. So using pinB4 wasn’t interfering with the scan on this occasion.
What do I have to change to get it to work?

symbol row = b1

symbol key = b2
let w3 = 5000
init:

pause 500

main:

key = 0

for row = 0 to 3

high row

gosub keyscan

low row

if key = 1 then gosub displayKey
if key = 2 then gosub displayKey
if key = 3 then gosub displayKey
if key = 4 then gosub displayKey
if key = 5 then gosub displayKey
if key = 6 then gosub displayKey
if key = 7 then gosub displayKey
if key = 8 then gosub displayKey
if key = 9 then gosub displayKey
if key = 10 then gosub displayKey
if key = 11 then gosub displayKey
if key = 12 then gosub displayKey
next row
goto main

keyscan:

if pinC.1 = 1 then

key = row * 3 + 1

do loop while pinC.1 = 1

elseif pinC.2 = 1 then

key = row * 3 + 2

do loop while pinC.2 = 1

elseif pinC.3 = 1 then

key = row * 3 + 3

do loop while pinC.3 = 1

endif

return

displayKey:

high 4
pause w3
low 4


goto main
 

hippy

Ex-Staff (retired)
As for your first statement, this is where I start to struggle. How do I set the pins B4 through B7 to output to the display? (later in the project I need further output pins to drive a stepper motor so understanding this part is essential).
You can use HIGH, LOW, TOGGLE, "LET pinB.4=" through "LET pinB.7=", and even "LET pinsB=" so long as you don't adversely interfere with the signals used for anything other than your display.

The problem seems to be not quite understanding how to drive the 4511 display. You need to set a binary bit pattern on pins B.4 through B.7 whereas you were setting pins across the whole B.0 to B.7 range.

To output a 1 : Let pinsB = %00010000 or Let pinsB = $10
To output a 2 : Let pinsB = %00100000 or Let pinsB = $20
To output a 3 : Let pinsB = %00110000 or Let pinsB = $30
etc
To output a 9 : Let pinsB = %10010000 or Let pinsB = $90
 
Hippy: Thanks again for you help. I’m going to have to get my head round what you’ve said and try it out. I’ll come back if I get stuck!
 
hippy: right - that's working fine and I've managed to save the last number entered as well. Now - if I set pins C4 to C7 as output pins will I be able to control a stepper motor through them? or will I have to address each pin separately again?
 
Hi! again
Going a stage further I’ve written the code for controlling the stepper motor, outputting on pins C.4 to C.7, however I only get a ‘buzzing’ on the motor and no stepping when I input a number on the keypad. The buzzing is not continuous and seems to equal the step count.
Let me explain what I’m trying to achieve.
There are a number of fixed radial positions that I want the motor to step to. These positions are fixed by a set number of steps from a zero position. They are represented by the symbols ‘stall1’ – stall9’. The number of steps from the zero position is held in a word variable ‘w6’ – ‘w14’. Numbers 1 - 9 on the keypad represent the positions ‘stall1’ – ‘stall9’. Entering a number on the keypad puts that number on a 7 segment display and loads the number of steps to that position, (‘w6’ – ‘w14’), into a variable ‘newpos’ w4. This is compared to a variable ‘current’ w3, which is 0 when the programme is first loaded, and calculates the number of steps required to step from the current position to the new position and puts them into a variable ‘steps’ w16. Depending on the new position being higher or lower than the current position the motor is stepped accordingly through the stepping sequence. The new position then becomes the current position ready for the next number input on the keypad. The current position is saved to memory to be available when next powered up.
Well - that’s the theory anyway, but I can’t get the motor to step through its routine. What am I doing wrong? I’m using a 28X2. Running the simulation in PE doesn’t show up any anomalies it all seems to run OK.

Motor control (keypad).jpg
Code:
Code:
poweron:
read 0,b1
pinsB = b1  	'lines 1 - 3 puts last number on shutdown onto display
read 10, word w3  	'loads current into w3 on start up
  	
let dirsB = %11111111   	'sets pinsB to outputs
let dirsC = %11110000  	'sets pinsC to outputs
symbol current = w3     	'lines 8 to 32 sets symbols against
symbol newpos = w4		'variables
symbol zeropos = w5
let zeropos = 0
symbol stall1 = w6
let stall1 = 450
symbol stall2 = w7
let stall2 = 500
symbol stall3 = w8
let stall3 = 550
symbol stall4 = w9
let stall4 = 600
symbol stall5 = w10
let stall5 = 650
symbol stall6 = w11
let stall6 = 700
symbol stall7 = w12
let stall7 = 1200
symbol stall8 = w13
let stall8 = 1800
symbol stall9 = w14
let stall9 = 2000
symbol steps = w16
symbol row = b4   
symbol key = b5

init: 		'lines 34 to 119 scans keypad
pause 500   	'sets newpos against number entered
			'and directs programme according to that number
main:
key = 0
for row = 0 to 3
	high row
	gosub keyscan
	low row
	
next row

	if key = 1 then
		let newpos = stall1
		gosub disp1
		gosub calcs	
	endif
	if key = 2 then
		let newpos = stall2
		gosub disp2
		gosub calcs
		
	endif
	if key = 3 then
		let newpos = stall3
		gosub disp3
		gosub calcs
		
	endif
	if key = 4 then
		let newpos = stall4
		gosub disp4
		gosub calcs
		
	endif
	if key = 5 then
		let newpos = stall5
		gosub disp5
		gosub calcs
		
	endif
	if key = 6 then
		let newpos = stall6
		gosub disp6
		gosub calcs
		
	endif
	if key = 7 then
		let newpos = stall7
		gosub disp7
		gosub calcs
		
	endif
	if key = 8 then
		let newpos = stall8
		gosub disp8
		gosub calcs
		
	endif
	if key = 9 then
		let newpos = stall9
		gosub disp9
		gosub calcs
		
	endif
	if key = 11 then
		let newpos = zeropos
		gosub disp0
		gosub calcs
		
	endif
goto main

keyscan:

if pinC.0 = 1 then
	key = row * 3 + 1
	do loop while pinC.0 = 1
	elseif pinC.1 = 1 then
	key = row * 3 + 2
	do loop while pinC.1 = 1
	elseif pinC.2 = 1 then
	key = row * 3 + 3
	do loop while pinC.2 = 1
endif
return

calcs:	if newpos = current then	'lines 121 to 135 calculates
		goto main   			'the number of motor steps required
endif 						'and direction to move from current
		if newpos < current then	'to new position
		let steps = current - newpos
		
		gosub rotateA
endif
		if newpos > current then
		let steps = newpos - current
		
		gosub rotateB
endif

return
disp1:  let b1 = $10    	'lines 136 to 175 outputs 
	let pinsB = $10   	'keypad input number to 
	goto saveLastRoute	'7 segment display
	return
disp2: let b1 = $20
	let pinsB = $20 
	goto saveLastRoute
	return
disp3:  let b1 = $30
	let pinsB = $30 
	goto saveLastRoute
	return
disp4: let b1 = $40 
	let pinsB = $40 
	goto saveLastRoute
	return
disp5: let b1 = $50 
	let pinsB = $50
	goto saveLastRoute
	return
disp6: let b1 = $60 
	let pinsB = $60
	goto saveLastRoute
	return
disp7: let b1 = $70 
	let pinsB = $70 
	goto saveLastRoute
	return
disp8: let b1 = $80
	let pinsB = $80 
	goto saveLastRoute
	return
disp9: let b1 = $90 
	let pinsB = $90
	goto saveLastRoute
	return
disp0: let b1 = $00
	let pinsB = $00
	goto saveLastRoute
	return

saveLastRoute:    	'line 177 to 179 saves
	Write 0,b1  	'last keypad entry to
	return		'memory

rotateA:    				'line 181 to 192 sets
	for w15 = 0 to steps    	'for - next loops for 		     
      let b2 = b2 - 1   		'motor steps     
      gosub step1 				
	next w15     	
	return	
rotateB:
	for w15 = 0 to steps    	    
      let b2 = b2 + 1     
      gosub step1 				
	next w15     	
	return

step1:				'line 194 to 198 motor
					'step sequence (full step)
	let b2 = b2 & %00000011 	
	lookup b2,(%10100000,%10010000,%01010000,%01100000),b3 
	let pinsC = b3  		
	return
	let newpos = current  	'makes new position current position
write 10,word current 	'saves current position to memory
return
goto main
 

hippy

Ex-Staff (retired)
Going a stage further I&#8217;ve written the code for controlling the stepper motor, outputting on pins C.4 to C.7, however I only get a &#8216;buzzing&#8217; on the motor and no stepping when I input a number on the keypad. The buzzing is not continuous and seems to equal the step count.
Take a step back, put aside how it will eventually work, and develop a separate program which simply steps the motor forward. Extend that to stepping then stopping. And then to stepping backwards if required.

Once you have the motor control program working you can then integrate that into your key handling code.
 

bfgstew

Senior Member
Double check the data sheet for correct wiring of the enable pins................Have a read of this.


PS on your keypad, add a 330 ohm resistor to each output from the keypad, I had mine the same as this and it fried the inputs if inadvertandly press more than 1 key, since I have added them I have had no more bother.
 
Hi!
Thanks to both of you for your help, as for the wiring I'm sure I've got it right I've used this drive sequence before but this is the first time on a 28X2. Thanks also for the advice on fitting resistors I'll do that. Good link I'll take a look at that.
 
Taking the advice &#8216;hippyy&#8217; gave I concentrated on the stepping sequence and alongside other tweaks&#8217; I changed my bit of code for &#8216;westaus55's code to do half stepping and after sorting out my 1&#8217;s and 0&#8217;s, the whole code worked as planned. However when I ran the programme the motor ran full step not half step as expected, is this due to the default clock frequency being 8MHz on the 28X2? What would I have to do to get back to half step without setting the frequency to 4MHz?
 
Yes it is! This is the bit of code I'm referring to.

Code:
step1:					'line 208/213 motor
						'step sequence 
		b2 = b2 & %00000111
			lookup b2,(%00100000,%01100000,%01000000,%01010000,%00010000,%10010000,%10000000,%10100000),b3
			pinsC = b3  		
	return
If you want to see the full programme code I'll up load it for you.
 
Top