Wireless SNES controllers

Topics regarding the Uzebox hardware/AVCore/BaseBoard (i.e: PCB, resistors, connectors, part list, schematics, hardware issues, etc.) should go here.
User avatar
PitfallJones
Posts: 39
Joined: Mon Aug 16, 2010 12:01 am

Wireless SNES controllers

Post by PitfallJones »

Do you think these will work with the UZEBOX?
retrobit.jpg
retrobit.jpg (15.17 KiB) Viewed 16828 times
http://www.amazon.com/SuperRetro-Wirele ... B0083LSCZ8
User avatar
uze6666
Site Admin
Posts: 4801
Joined: Tue Aug 12, 2008 9:13 pm
Location: Montreal, Canada
Contact:

Re: Wireless SNES controllers

Post by uze6666 »

Good question, I saw similar ones on aliexpress some time ago and wondered the same thing. They should, specially with the last kernel tweak to support the asciipad.
User avatar
PitfallJones
Posts: 39
Joined: Mon Aug 16, 2010 12:01 am

Re: Wireless SNES controllers

Post by PitfallJones »

Well I got them - and they are really good !
They work on my SNES fine but they don't work on the UZE.
It sort of almost works - it seems to think the B button is start and ignores all the others so some sort of info is getting across ....
On well - no time to debug now - back to finishing my game...
- PJ

P.S.
There's a review of them here: (not by me)
http://playingwithsuperpower.com/retrob ... er-review/
User avatar
uze6666
Site Admin
Posts: 4801
Joined: Tue Aug 12, 2008 9:13 pm
Location: Montreal, Canada
Contact:

Re: Wireless SNES controllers

Post by uze6666 »

I'll order one then and see if I can fix the kernel to support it as well...
User avatar
PitfallJones
Posts: 39
Joined: Mon Aug 16, 2010 12:01 am

Re: Wireless SNES controllers

Post by PitfallJones »

Great Stuff - thanks for that Uze - I've been having a lot of fun playing my snes with them - had all my old carts out yesterday :-)
User avatar
PitfallJones
Posts: 39
Joined: Mon Aug 16, 2010 12:01 am

Re: Wireless SNES controllers

Post by PitfallJones »

Hi Uze,

Did you ever have any luck with that wireless controller?

PJ
User avatar
uze6666
Site Admin
Posts: 4801
Joined: Tue Aug 12, 2008 9:13 pm
Location: Montreal, Canada
Contact:

Re: Wireless SNES controllers

Post by uze6666 »

Ah no, I forgot to order one.I must admit its fairly low priority right now, the Ethernet stuff is king! :)
User avatar
uze6666
Site Admin
Posts: 4801
Joined: Tue Aug 12, 2008 9:13 pm
Location: Montreal, Canada
Contact:

Re: Wireless SNES controllers

Post by uze6666 »

Finally got my wireless pad. It's much better than I anticipated. It works fine with my SNES, I could do all those Street Fighter 2 moves flawlessly! :) Now I looked at the timing used by the kernel and it's about 10x faster than the signaling made by a SNES (according to some spec), so I guess the problem lies there. Using the same timing in the current polling approach would waste a lot of cycles and reduce the precious cycles the games have during vsync. The only way I could see would be to use some interrupt based approach but I don't think it's worth spending much time on this.
User avatar
nicksen782
Posts: 714
Joined: Wed Feb 01, 2012 8:23 pm
Location: Detroit, United States
Contact:

Re: Wireless SNES controllers

Post by nicksen782 »

I tried these:
http://www.8bitdo.com/retro-receiver-snes/
http://www.8bitdo.com/snes30/

The controller looks fantastic! However, it is erratic/wrong buttons on Uzebox. I managed to get it working with the Controller Tester .uze but only once and I had to put/take the receiver a couple of times (also, tight fit.)

I've read that the kernel reads the controller too often. I really like this controller. I looked at the ASM for reading the controller but I did not follow it well. I expected to see something resembling operating a shift register but I only saw reads. (uzeboxVideoEngineCore.s: ReadJoypad). Where is the reading of the joypad triggered?

So, I tried this figuring that it would slow the polling...

Code: Select all

KERNEL_OPTIONS += -DCONTROLLERS_VSYNC_READ=0

Code: Select all

static void getGamepad(void){
	// Bring in the game struct.
	struct game_ * game = &gamestruct;

	// Input
	// game->btnHeld     = ReadJoypad(padNum);
	DetectControllers();  // Probably not needed.
	ReadControllers();
	game->btnHeld     = joypad1_status_lo;
	game->btnPressed  = game->btnHeld & (game->btnHeld^game->btnPrev);
	game->btnReleased = game->btnPrev & (game->btnHeld^game->btnPrev);	// Not used right now. Might be good for later!
	game->btnPrev     = game->btnHeld;
}

Code: Select all

// Keep in sync.
		while (!GetVsyncFlag()) {} ClearVsyncFlag();
		// Read the gamepad.
		getGamepad();
So... I'm reading the gamepad once per vsync. I'm guessing this is too quick? Since I'm handling the reading of the gamepad manually (right??) could I artificially slow the polling down by only reading the controller every, say, 5 vsyncs? Or is the problem the actual clocking of the bits from the controller? I could have a counter (I already actually do this for timing) that when used with an if statement could check for the value to be >=5, read the controller, then reset the counter.

Perhaps something like this:

Code: Select all

static void getGamepad(void){
	// Bring in the game struct.
	struct game_ * game = &gamestruct;

	if(game->gamepadPollCounter >=5){
		ReadControllers();
		game->gamepadPollCounter=0;
	}
	else{ game->gamepadPollCounter++; }
	
	// Input
	// game->btnHeld     = ReadJoypad(padNum);
	
	DetectControllers();
	
	game->btnHeld     = joypad1_status_lo;
	game->btnPressed  = game->btnHeld & (game->btnHeld^game->btnPrev);
	game->btnReleased = game->btnPrev & (game->btnHeld^game->btnPrev);	// Not used right now. Might be good for later!
	game->btnPrev     = game->btnHeld;
}
User avatar
D3thAdd3r
Posts: 3221
Joined: Wed Apr 29, 2009 10:00 am
Location: Minneapolis, United States

Re: Wireless SNES controllers

Post by D3thAdd3r »

Hey Nicksen, I have not tried this for these particular controllers but based on some other ones that had issue, I do not think it is the issue with polling every frame as most SNES games did so. The bit clocking and/or latching itself is maybe 10x too fast, but works with most controllers(since they are just a shift register and not a more complex wireless system..that they did cheap no doubt).

My guess is that something along these lines would work(from uzeboxCore.c):

Code: Select all

void ReadButtons(){
	unsigned int p1ButtonsLo=0,p2ButtonsLo=0;
	unsigned char i;

	//latch controllers
	JOYPAD_OUT_PORT|=_BV(JOYPAD_LATCH_PIN);
	#if SNES_MOUSE == 1
		if(snesMouseEnabled){
			WaitUs(1);
		}else{
			Wait200ns();
			Wait200ns();
		}	
	#else
		for(unsigned char j=0;j<8;j++){//might need some tinkering..
			Wait200ns();
			Wait200ns();
		}
	#endif
	JOYPAD_OUT_PORT&=~(_BV(JOYPAD_LATCH_PIN));


	//read button states
	for(i=0;i<16;i++){

		p1ButtonsLo>>=1;
		p2ButtonsLo>>=1;

		#if SNES_MOUSE == 1
			if(snesMouseEnabled){
				WaitUs(5);
			}else{
				Wait200ns();
				Wait200ns();
			}	
		#else
			for(unsigned char j=0;j<8;j++){//might need some tinkering..
				Wait200ns();
				Wait200ns();
			}
		#endif
			
		//pulse clock pin		
		JOYPAD_OUT_PORT&=~(_BV(JOYPAD_CLOCK_PIN));
		
		if((JOYPAD_IN_PORT&(1<<JOYPAD_DATA1_PIN))==0) p1ButtonsLo|=(1<<15);
		if((JOYPAD_IN_PORT&(1<<JOYPAD_DATA2_PIN))==0) p2ButtonsLo|=(1<<15);
		
		JOYPAD_OUT_PORT|=_BV(JOYPAD_CLOCK_PIN);
		
		#if SNES_MOUSE == 1
			if(snesMouseEnabled){
				WaitUs(5);
			}else{
				Wait200ns();
				Wait200ns();
			}	
		#else
			for(unsigned char j=0;j<8;j++){//might need some tinkering..
				Wait200ns();
				Wait200ns();
			}
		#endif

	}

	#if JOYSTICK==TYPE_SNES
		joypad1_status_lo=p1ButtonsLo;
		joypad2_status_lo=p2ButtonsLo;
	#else
		joypad1_status_lo=p1ButtonsLo&0xff;
		joypad2_status_lo=p2ButtonsLo&0xff;	
	#endif

	if(joypad1_status_lo==(BTN_START+BTN_SELECT+BTN_Y+BTN_B) || joypad2_status_lo==(BTN_START+BTN_SELECT+BTN_Y+BTN_B)){
		SoftReset();
	}

}
Naturally even if this or some more extreme(slower) form works, there is the downside of how many cycles it eats. This could probably be a good thing to have a compile flag for, then anyone could try and see if there is enough cycles to support it or not for any particular game. Probably some games would crash as they couldn't spare it, especially mode 3 ones. I bet you could make them work using less delay than this, basically backing it off until they show problems then bumping it back up and calling that the timing limit.
Post Reply