Digital Pinball Machine

Infrared remote control power button emulator

 

The purpose of this project is to be able to switch a TV on when connected to the mains supply without the use of the remote control. Specifically designed for my pinball project, this could have uses elsewhere.

 

As you probably know, most TVs don’t automatically turn on when mains power is restored. You wouldn't want it to either especially in the event of a power cut, you would want the device to stay off when the power returns. This is also the case with some monitors. This creates a problem for the pinball machine — each time it’s powered up, you have to grab multiple remotes, power up each monitor before launching windows.

In the case of windows 7, starting it up before all the monitors were online has caused a scenario where the screen layout became drastically messed up and ended up staying like that.

I don’t think this is an issue in Windows 10 anymore, but I have not put that to the test, resetting up the screens is not something I would want to waste my time doing.

 
How is this problem best solved?

The solution I came up with was to make devices that re-create the power on signals that the infrared remote controls output.

Summary, I've used PIC microcontrollers with a sounder and IR LED attached. Once the whole pinball machine is powered up, the IR emulator knows how long to wait for the LCD screen to initialise. After that time has ellapsed, it will fire the IR on signal.

Once all screens are on, I just tap the PC's power button.

Before I go any further, there is likely much easier ways to do this in 2025. I made these devices around 2015 with spare parts that I had.


 
For initially finding out how to copy the codes, an oscilloscope with an old IR receiver (from a very old CRT TV) was used
The first remote control is from the main playfield, a sharp 40" TV. The oscilloscope image is a capture of the data when the infra red remote power button is pressed. All the timings are included.
The second remote control is for the backglass display, a 32" Hanspree TV. The oscilloscope image is a capture of the data when the infra red remote power button is pressed. All the timings are included.

In the PIC code further down, I have taken all these timings and just got the PIC to create every on / off exactly as per the oscilloscope screen output. Ideally, I would create calls for each on/off timing, but this is just a dirty routine to quickly emulate the code(s).

Most infra red remote controllers (if not all) modulate the IR LED around 38Khz. when the LED is lit (presumably to avoid false triggers). We can achieve this with the PIC micro, so avoiding additional electronics to do that part.

This is the code to operate the Sharp TV playfield power on. Only the core code is shown here. The crystal used is the internal 4 Mhz on a 16F88. This is pretty dirty code and could be optimised with a few routines.

 

 

; Whats happening?
; 2 routines make this work.  ledON and uSdelay.
; Take a look at the scope image for the Share 40" TV power button.
; The first thing in the timing is to switch the IR LED on for 980uS
; Each time the ledON routine runs, it takes 28.1uS to complete, so we loop the by setting the W register 
; to the number of loops required.  In this case, we can get close by looping 35 times.
; 
; Once that has happened, the LED needs to stay off for 780uS
; That is the first bit sent to the LED.
; The 4 lines of code below do exactly this.

		MOVLW	d'35'		; LET W=35; Do ledOn for 980us, 35 x28.1µS = 984uS in the ledON routine
		CALL	ledON		; GoSub ledON; Do routine for the delay specified above
		MOVLW	d'78'		; off for 780µS;  This is a delay routine where 78 = 780µS. LED is off here
		CALL	uSdelay		;

; the ledON is a bit more complex than just swiching on.  When it is on, its infact flashing off and on at 38Khz.
; The routine is near the end of the code that achieves this.

; the code continues for the remaining data to be sent to the IR led.  
; This rebuilds the same power button code seen in the image above
;---------------------------------------------------------
		MOVLW	d'67'		; on for 1880(66=1881)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	
;block of 3
		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	
		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	
		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	

		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'164'		; off for 1640µS - 1ST BIG OFF TIME
		CALL	uSdelay	

		MOVLW	d'67'		; on for 1880(66=1881)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	

		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'164'		; off for 1640µS - 2ND BIG OFF TIME
		CALL	uSdelay

		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	

		MOVLW	d'67'		; on for 1880(66=1881)   big on time
		CALL	ledON
		MOVLW	d'78'		; off for 780µS
		CALL	uSdelay	

		MOVLW	d'35'		; on for 984 (nearest to 980)
		CALL	ledON
; Data sending is complete


;==========================================================================================
; LEDON ROUTINE
; LED on routine that turns the led on/off at 38 Khz for X uS before return
ledON		;MOVLW	d'25'		; This is where the code starts when ledON is called
		MOVWF	delayCounter	; That value set in W is copied into delayCounter

irONloop	bsf	PORTA, 2			; Switch on pin2 on PORT A (The IR LED)
		MOVLW	d'3'		; W = 3 (tuned  timing routine)
		MOVWF	delayValue	; delayValue = W
innerloop7	DECFSZ	delayValue,F	; delayValue = delayValue- 1, if delayValue=0,skip the next instruction
		GOTO	innerloop7

		bcf	PORTA, 2		; Switch off pin2 on PORT A (The IR LED)
		MOVLW	d'4'		; W = 4
		MOVWF	delayValue	; delayValue = W
innerloop8	DECFSZ	delayValue,F
		GOTO	innerloop8	; This is a precisely tuned delay routine that has become a pain in the Ass


		DECFSZ	delayCounter,F
		GOTO	irONloop	
		return

;****************************************************************
;uSdelay - a value of 10 = 100uS at 4Mhz			
;****************************************************************
uSdelay					; Precision delay routine starts here (as per the description above)
		MOVWF	delayCounter	;LET delayCounter = W
outerloop
		MOVLW	0x2		;Innerloop to loop twice
		MOVWF	delayValue	;LET delayValuer = W (which has the value 2)	
innerloop99
		DECFSZ	delayValue,F	;delayValue = delayValue - 1, if delayValue = 0, skip the next instruction
		GOTO	innerloop99	;
		DECFSZ	delayCounter,F	;delayCounter = delayCounter - 1, if delayCounter=0,skip the next instruction
		GOTO	outerloop
		RETURN

;***********************************************

 
The final code goes a step further than this and has a delay timer at the start. This beeps a sounder for the time required to wait until the TV/Monitor is ready for a power on signal.

I've supplied the assembly code and hex file for both Sharp TV and Hanspree TV so they can be flashed into a 16F88.

 

I developed the code using Labcenter Proteus that I purchased I think back in the early 00's.

If you have this software, you can just load my work straight into it here.

circuit below
 
 

 

← Back to Projects