Show Posts

This section allows you to view all posts made by this member. Note that you can only see posts made in areas you currently have access to.


Messages - zainey

Pages: 1 2 3 ... 5
1
Wiimote Finger Tracking / Re: Tongue Tracking
« on: July 25, 2012, 09:33:36 PM »
Hi,

The 'curves' settings in FreeTrack may help improve the lack of response reported around the centre position.

The curves menu feature can be used to amplify the apparent motion of the IR blob and thus make up for some of the limitations in the field of view or the actual range of IR dot motion.

Its not something I ordinarily tinker with, so I hope it helps with your application.

Thanks.

2
Wiimote Finger Tracking / Re: Tongue Tracking
« on: July 25, 2012, 02:58:20 AM »
Hi,

To amplify the 'gain' of the wiimote, you may consider placing a telescopic type lens in front of the wiimote camera.

A telescopic lens - like a rifle scope - would expand the effects of small lateral movements of a tongue, say to the viewing area of the wiimote. You may have to reduce the apparent 'blob' size as seen by the wiimote, as it seems to 'go blank' when viewing large 'blobs' up close.

Use the Freetrack software, in single LED point mode, to help in visualising what the wiimote sees, and to make adjustments for the perceived sensitivity of the wiimote IR camera as well.

You may also need to experiment with different narrow field of view lenses to see which kind works best. Even a compact CCTV type lens may do the trick.

Alignment is fairly straighforward. Line up the external IR LED with the bare wiimote to the centre coordinate (512, 384). Once the IR LED and wiimote are inline, then place the telescopic lens in the light path and move the lens around so the IR dot is re-aligned to the centre. Then fix the lens in place to use properly.

Hopefully that puts you on the right track. p

Thanks.


3
Hi,

For us non-musicians, a few diagrams/pictures or links may be helpful to see what you are doing.

There may be a simpler way to make your project work other than using the whiteboard method ....

thanks. 

4
Wiimote Finger Tracking / Re: Infra red tracking project
« on: April 19, 2012, 06:51:55 AM »
Hi,

I did a liittle more thinking about this.

If you want to detect the 'shot' on the target, then a wii remote positioned on the gun, with only two IR emitters located downrange at the target is all that is really required.

You would then have to calibrate the lateral distance of the IR emitters in respect of the target centre itself. This is just basic mathematics.

If you want to get really complicated - A four IR emitter system with realtime Wii Whiteboard type perspective  calibration would be necessary - for the 'pro' version.

This also assumes the IR emitters are bright enough to be detected by the wiimote. Possibly a lens could be put over the IR emitters so the IR light is directed like a torch uprange. Or a scope could possible be mounted on the end of the wiiremote for the same result.

Thanks.


5
Wiimote Finger Tracking / Re: Infra red tracking project
« on: April 09, 2012, 08:44:12 PM »
Hi,

This gun tracking project will not be a simple exercise.

If you want some idea of the complexity involved, look at this project.

Its an explanation of six degree of freedom optical tracking using off the shelf components, some Wii Remotes and GlovePie.

This is where I would start such a project :)

 http://www.mtbs3d.com/phpBB/viewtopic.php?f=6&t=4251


Thanks.

6
Project Ideas / Turn your DIY Wii Project into a saleable product
« on: March 10, 2012, 06:00:49 AM »
Hi,

I saw this article about making a large DIY sensor bar, the 'Megabar', into a commercial product through Kickstarter.

Maybe you have an idea that people will want to buy.

See article here :

http://spectrum.ieee.org/geek-life/hands-on/turning-a-diy-project-into-a-product/1


or PDF version here:

http://ieeexplore.ieee.org/stamp/stamp.jsp?arnumber=6156857



Thanks.




7
Hi,

I like your project.

Its been a while since anyone has moved forward with the Wii Cam Headtracking. I thought the world has given up on the idea since the novelty has worn off a bit

It gets interesting with wireless being used to transfer the i2c data from the standalone camera.

Keep going, as I would like to see some progress happening in this area. Great post.

By the way, Johnny Chung Lee - the Wii whiteboard guy - was interviewed recently and the video is available for online viewing at ABC Big Ideas.

See here:    http://www.abc.net.au/tv/bigideas/stories/2012/02/27/3438839.htm


Thanks.
 

8
Accessories / Re: The IR Great Rear Projection System for Wii Remote IWB
« on: January 25, 2012, 09:06:30 PM »
Hi,

This rear projection system with rear mounted sensor looks impressive.

I wonder if four calibration leds could be mounted on the back of the screen at the frame corners, so when the system is switched on it would automatically calibrate the screen, and then switch off the leds for normal use.

Anyhow, seems like a good idea to me.


Thanks.

9
Wiimote Desktop VR/Head Tracking / Re: Wiimote radial distortion
« on: January 19, 2012, 08:24:15 PM »
Hi,

I cannot help you with radial distortions as that is a second order effect.

The Wii Remote camera seems to be quite linear as it works accurately in whiteboard applications based on linear perspective projections.

Look at this article on Wii Camera optical parameters that I worked on.

http://www.glovepie.org/forum/viewtopic.php?f=6&t=650&p=1890&hilit=camera#p1890

Unless you are good with advanced linear algebra, then this might be sufficient.


Thanks.

10
Wiimote Smoothboard / Re: WII Smatboard - Mouse Right-Click
« on: November 15, 2011, 08:58:28 PM »
Hi,

The use of a light pen (IR) with wireless mouse functionality is something that others have been wanting for a while.

The only instance to my knowledge of a whiteboard wireless pen mouse is the VMarker .

There have been a number of attempts to achieve similar outcomes by using off the shelf components, but there have been deficiencies in functions, packaging, ergonomics or weight.

A really viable solution is still out there in my view.

The key problems I see is in keeping the number of buttons to a minimum for ease of use, making the battery life sufficient with low weight, and fitting in the wireless radio while keeping the pen fairly nimble.

From my experiments, if the wireless circuit board from a Wii Nunchuk was made narrower, then it would be much easier to package a wireless mouse function into a whiteboard light pen. But unless someone remakes the circuit board from a wireless nunchuk into a narrower format, then its not going to happen.

Thanks.

11
Wiimote Finger Tracking / Wiimote Touchpad in the works
« on: November 05, 2011, 04:52:08 AM »
Hi,

Nintendo are up to something with a new wiimote expansion with touchpad capability.

See here -  http://www.newscientist.com/blogs/onepercent/2011/11/nintendo-patent-turns-wii-remo.html

It also refers to the Nintendo Patent Application - 20110261012

Go to  http://patft.uspto.gov/ and "Quick search" this number "20110261012" under "AppFT: Applications"

Or just see it here -

http://appft.uspto.gov/netacgi/nph-Parser?Sect1=PTO2&Sect2=HITOFF&p=1&u=%2Fnetahtml%2FPTO%2Fsearch-bool.html&r=1&f=G&l=50&co1=AND&d=PG01&s1=20110261012&OS=20110261012&RS=20110261012


Thank.

12
Hi,

There are variations in Wii Remote circuit boards, but that may be due to different factories or cost cutting with subsequent revisions.

However, the genuine camera in the Wii Remote comes from Pixart and it comes with 8 pins and a metal square casing.

Any other camera is not genuine and has been designed that way to either circumvent patent laws or overcome manufacturing limitations or trade secrets.

I would change suppliers to get the real deal.


Other information I have found useful is

1. Chris the Carpenter

http://letsmakerobots.com/node/25513

http://letsmakerobots.com/node/28789

2. Stephen Hobley

http://www.stephenhobley.com/blog/2009/02/22/pixart-sensor-and-arduino/

http://www.stephenhobley.com/blog/2009/03/01/pixartwiimote-sensor-library-for-arduino/

http://www.stephenhobley.com/blog/2011/03/29/strange-wiimote-camera/


3. and others on the net.


Thanks

13
IR Pens / Re: Dual IR LED IWB Wii Mouse Pen
« on: September 09, 2011, 05:36:36 AM »
// DUAL LED MOUSE PEN INDICATION AND CONTROL

if var.macrocount == 10


         // ISOLATE WIIMOTE to one read for case structure
         // may not be necessary
         if wiimote.dot1vis

              var.newvis1 = true

              var.dot1x =  wiimote.dot1x
              var.dot1y =  wiimote.dot1y

          else

              var.newvis1 = false

          end


          if wiimote.dot2vis

              var.newvis2 = true

              var.dot2x =  wiimote.dot2x
              var.dot2y =  wiimote.dot2y


          else

              var.newvis2 = false

          end

          // next frame comparison only
          // visible dots transition detection filter
          if ((delta(var.newvis1) == 0) AND  (delta(var.newvis2) == 0) )


               //to eliminate incompleted intermediate state transitions over more than one frame
               if var.buffercount >= 2

                    var.vis1 =  var.newvis1
                    var.vis2 =  var.newvis2

                    // START of LEFT PEN BUTTON mouse commands  ( SINGLE LED )

                    // LEFT MOUSE BUTTON DOUBLE CLICK
                    if (NOT var.rightpressmode) AND DoubleClicked( var.vis1 AND NOT var.vis2 AND NOT var.pointermode )

                            var.dotvx =  var.dot1x
                            var.dotvy =  var.dot1y

                            var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                            var.wout = var.rectout[3]
                            var.uout = var.rectout[1]/var.wout
                            var.vout = var.rectout[2]/var.wout

                            // no pointer smoothing on clicking
                            mouse.CursorPosX = var.uout
                            mouse.CursorPosY = var.vout

                            // no such function available - DoubleClick(Mouse.LeftButton)
                            Press(Mouse.LeftButton)
                            Release(Mouse.LeftButton)
                            Press(Mouse.LeftButton)
                            Release(Mouse.LeftButton)

                            var.lastmousecommand = 'Double Left click '

                            debug = '1. Last Command  =  ' + var.lastmousecommand


                    // POINTER MODE - TERMINATION
                    else if (NOT var.rightpressmode) AND (var.pointermode AND helddown( Not ( var.vis1 AND NOT var.vis2) , var.pointerextendtime ) )

                           var.pointermode = false

                           var.lastmousecommand = 'Pointer RELEASED'

                           debug = '2. Last Command  =  ' + var.lastmousecommand

                    // POINTER MODE - ACTIVATION
                    else if (NOT var.rightpressmode) AND (var.pointermode OR helddown(  var.vis1 AND NOT var.vis2 , var.pointerinitiatetime ) )

                           var.pointermode = true

                           // Mouse Pointer Only - No Mouse Command issued

                           // FOR POINTER MODE TIMEOUT WITH OVERLAPPING RIGHT PEN BUTTON INDICATION

                           if var.vis1 AND var.vis2

                                if  var.righthandpen  // Wii Camera view to left side of left pointing pen

                                   if  var.dot2x > var.dot1x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // right hand pen use pointer end sensing

                                else  // Wii Camera view to right side of right pointing pen

                                   if var.dot1x > var.dot2x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // left hand pen use pointer end sensing

                                end // pen pointer end sensing from different Wii Camera side view

                           else

                               var.dotvx =  var.dot1x
                               var.dotvy =  var.dot1y

                           end

                           // end pointer LED selection and timeout section

                           var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                           var.wout = var.rectout[3]
                           var.uoutLP = var.rectout[1]/var.wout
                           var.voutLP = var.rectout[2]/var.wout

                           //some smoothing optional
                           mouse.CursorPosX = smooth(var.uoutLP, 1)
                           mouse.CursorPosY = smooth(var.voutLP, 1)

                           var.lastmousecommand = 'Pointer PRESSED'

                           debug = '3. Last Command  =  ' + var.lastmousecommand


                    // LEFT MOUSE BUTTON SINGLE CLICK
                    // NOTE: Pointermode caught before this case - no pointer mode preconditioning required

                    else if (NOT var.rightpressmode) AND SingleClicked( var.vis1 AND NOT var.vis2)

                           var.dotvx =  var.dot1x
                           var.dotvy =  var.dot1y

                           var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                           var.wout = var.rectout[3]
                           var.uout = var.rectout[1]/var.wout
                           var.vout = var.rectout[2]/var.wout

                           // no pointer smoothing on clicking
                           mouse.CursorPosX = var.uout
                           mouse.CursorPosY = var.vout

                           // no such function available - SingleClick(Mouse.LeftButton)
                           Press(mouse.LeftButton)
                           Release(Mouse.LeftButton)

                           var.lastmousecommand = 'Single Left click'

                           debug = '4. Last Command  =  ' + var.lastmousecommand


                    // START of RIGHT PEN BUTTON mouse commands  ( DUAL LED )

                    // RIGHT MOUSE BUTTON DOUBLE CLICK - IS OPTIONAL AS IT IS NOT REALLY NEEDED

                    else if DoubleClicked( var.vis1 AND var.vis2 AND NOT var.rightpressmode )

                           if  var.righthandpen  // Wii Camera view to left side of left pointing pen

                                   if  var.dot2x > var.dot1x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // right hand pen use pointer end sensing

                           else  // Wii Camera view to right side of right pointing pen

                                    if var.dot1x > var.dot2x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // left hand pen use pointer end sensing

                           end // pen pointer end sensing from different Wii Camera side view


                           var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                           var.wout = var.rectout[3]
                           var.uout = var.rectout[1]/var.wout
                           var.vout = var.rectout[2]/var.wout

                           // no pointer smoothing on dounle clicking
                           mouse.CursorPosX = var.uout
                           mouse.CursorPosY = var.vout

                           // no such function available - DoubleClick(Mouse.RightButton)
                           Press(Mouse.RightButton)
                           Release(Mouse.RightButton)
                           Press(Mouse.RightButton)
                           Release(Mouse.RightButton)

                           var.lastmousecommand = 'Double Right click '

                           debug = '5. Last Command  =  ' + var.lastmousecommand

                    // LEFT MOUSE BUTTON PRESS - TERMINATION
                    else if var.rightpressmode AND helddown( Not ( var.vis1 AND var.vis2) , var.rightpressextendtime )

                           var.rightpressmode = false

                           Release(Mouse.LeftButton)

                           var.lastmousecommand = 'Context Button RELEASED'

                           debug = '6. Last Command  =  ' + var.lastmousecommand

                    // LEFT MOUSE BUTTON PRESS - ACTIVATION
                    // ( text and drag/drop modes )
                    else if var.rightpressmode OR helddown(  var.vis1 AND var.vis2 , var.rightpressinitiatetime )

                           if var.vis1 AND var.vis2

                                   if  var.righthandpen  // Wii Camera view to left side of left pointing pen

                                       if  var.dot2x > var.dot1x

                                           var.dotvx =  var.dot1x
                                           var.dotvy =  var.dot1y

                                       else  // led positions swap

                                           var.dotvx =  var.dot2x
                                           var.dotvy =  var.dot2y

                                       end // right hand pen use pointer end sensing

                                   else  // Wii Camera view to right side of right pointing pen

                                       if var.dot1x > var.dot2x

                                          var.dotvx =  var.dot1x
                                          var.dotvy =  var.dot1y

                                       else  // led positions swap

                                          var.dotvx =  var.dot2x
                                          var.dotvy =  var.dot2y

                                       end // left hand pen use pointer end sensing

                                   end // pen pointer end sensing from different Wii Camera side view

                           // ignore single LED detection during right pen button pressmode
                           end


                           var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                           var.wout = var.rectout[3]
                           var.uoutRP = var.rectout[1]/var.wout
                           var.voutRP = var.rectout[2]/var.wout

                           // no pointer smoothing on right pen press mode
                           mouse.CursorPosX = var.uoutRP
                           mouse.CursorPosY = var.voutRP

                           // localise mouse pointer first then issue mouse button press for text highlight or drag modes
                           if not var.rightpressmode

                              Press(Mouse.LeftButton)

                              wait 20ms

                           end if

                           var.rightpressmode = true

                           var.lastmousecommand = 'Context Button PRESSED'

                           debug = '7. Last Command  =  ' + var.lastmousecommand


                    // RIGHT MOUSE BUTTON SINGLE CLICK
                    // NOTE: Rightpress mode caught before this case - no press mode preconditioning required

                    else if SingleClicked( var.vis1 AND var.vis2 )


                           if  var.righthandpen  // Wii Camera view to left side of left pointing pen

                                   if  var.dot2x > var.dot1x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // right hand pen use pointer end sensing

                           else  // Wii Camera view to right side of right pointing pen

                                   if  var.dot1x > var.dot2x

                                       var.dotvx =  var.dot1x
                                       var.dotvy =  var.dot1y

                                   else  // led positions swap

                                       var.dotvx =  var.dot2x
                                       var.dotvy =  var.dot2y

                                   end // left hand pen use pointer end sensing

                           end // pen pointer end sensing from different Wii Camera side view


                           var.rectout = [(var.dotvx + 0.5), (767.5 - var.dotvy), 1] *  var.QuadToRect

                           var.wout = var.rectout[3]
                           var.uout = var.rectout[1]/var.wout
                           var.vout = var.rectout[2]/var.wout

                           // no pointer smoothing on single clicking
                           mouse.CursorPosX = var.uout
                           mouse.CursorPosY = var.vout

                           // no such function available - SingleClick(Mouse.RightButton)
                           Press(Mouse.RightButton)
                           Release(Mouse.RightButton)

                           var.lastmousecommand = 'Single Right click'

                           debug = '8. Last Command  =  ' + var.lastmousecommand


                    end // Left and Right Pen Button command case structure


               else
                    // frame buffer counting for finalising LED indication state

                    var.buffercount = var.buffercount + 1

               end  // LED indication is steady


        else
               // LED indication is transitioning
               var.buffercount = 0

        end // LED transition detection


 end // macro count = 10: this interactive whiteboard macro is normally running


 
// MOUSE BUTTON MAPPING TO LED INDICATION AND PEN ROCKER SWITCH POSITION
//
//Mouse Command -------------------- TIP LED ----- TAIL LED ------ PEN MOUSE EQUIVALENT -------- PEN ROCKER SWITCH POSITION --------
//
//CURSOR POINTER                           X             -              LEFT BUTTON PRESS                  BACKWARD ROCKER PRESS ( ->| )
//
//Left Mouse Button Press                  X             X             RIGHT BUTTON PRESS                 FORWARD ROCKER PRESS  ( |<- )
//
//Left Mouse Button Click                   X             -              LEFT BUTTON CLICK                    BACKWARD ROCKER CLICK  ( -> )
//
//Left Mouse Button Double Click        X             -              LEFT BUTTON DOUBLE CLICK        BACKWARD ROCKER DBL CLICK  ( ->> )
//
//Right Mouse Button Press (Ommitted)   -             -              -                             -
//
//Right Mouse Button Click                  X             X              RIGHT BUTTON CLICK                 FORWARD ROCKER CLICK ( <- )
//
//Right Mouse Button Double Click        X             X             RIGHT BUTTON DOUBLE CLICK     FORWARD ROCKER DBL CLICK ( <<- )
//
//
//---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
//


//
// END OF GLOVEPIE DUAL LED ROCKER SWITCH PEN INTERACTIVE WII REMOTE WHITEBOARD VERSION TWO PROGRAM SCRIPT
//




14
IR Pens / Re: Dual IR LED IWB Wii Mouse Pen
« on: September 09, 2011, 05:25:30 AM »
// HOMOGRAPHY MODULE
// GENERAL NOTE: Glovepie works with row vectors and matrix post-multiplication convention
// [row vectors] = Transpose[column vectors]
// Column vector format: [A][C][D] transpose[vector] <=> Glovepie Row vector format: [vector].transpose[D].transpose[C].transpose[A]


if var.macrocount == 5
// Do homography matrix calculation once

// solving unit square to quadrilateral homography matrix with 4 corresponding point pairs
// row vector format Hs->q = [a d g, b e h, c  f  1 ]

// determining parameters g and h

// coefficients of simultaneous linear equations in g and h

var.xk1 = var.x1 - var.x2

var.xk2 = var.x3 - var.x2

var.xk3 = var.x0 - var.x1 + var.x2 - var.x3


var.yk1 = var.y1 - var.y2

var.yk2 = var.y3 - var.y2

var.yk3 = var.y0 - var.y1 + var.y2 - var.y3

// solving the simultaneous linear equations for g and h using cramers rule

var.g = ( var.xk3 *  var.yk2 -  var.yk3 * var.xk2 ) / (  var.xk1 * var.yk2 -  var.yk1 * var.xk2 )

var.h = ( var.xk1 *  var.yk3 -  var.yk1 * var.xk3 ) / (  var.xk1 * var.yk2 -  var.yk1 * var.xk2 )


// solving remaining linear equations for parameters a to f, given g and h

var.a = var.x1 - var.x0 + var.g * var.x1

var.b = var.x3 - var.x0 + var.h * var.x3

var.c = var.x0

var.d = var.y1 - var.y0 + var.g * var.y1

var.e = var.y3 - var.y0 + var.h * var.y3

var.f = var.y0

//Unit Square to Quadrilateral Homography
// row vector format Hs->q = [a d g, b e h, c  f  1 ]

var.UnitSquareToQuad = [ var.a , var.d , var.g ; var.b , var.e , var.h ; var.c , var.f , 1 ]

// Solving quad to unit square homography by inverting unit square to quadrilateral homography matrix
// CALCULATE ADJOINT MATRIX only and ignore determinant calculation

  var.ADJ =  [0,0,0;0,0,0;0,0,0]


  var.ADJ[1,1] =   var.e - var.f * var.h

  var.ADJ[1,2] =   var.f * var.g - var.d

  var.ADJ[1,3] =   var.d * var.h - var.e * var.g

  var.ADJ[2,1] =   var.c * var.h - var.b

  var.ADJ[2,2] =   var.a - var.c * var.g

  var.ADJ[2,3] =   var.b * var.g - var.a * var.h

  var.ADJ[3,1] =   var.b * var.f - var.c * var.e

  var.ADJ[3,2] =   var.c * var.d - var.a * var.f

  var.ADJ[3,3] =   var.a * var.e - var.b * var.d


// HOMOGRAPHY
// Quadrilateral to Rectangular homography matrix via Unit Square transformation
// row vector format
// Hq->r = [Hs->q]^-1 . [Ss->r] . [Ts->r]


// Calculate unit square to rectangular scaling matrix
// row vector format
// Ss->r = [Sx 0 0, 0 Sy 0, 0  0  1 ]

var.Scale = [1,0,0;0,1,0;0,0,1]

var.Scale[1,1] = Screen.Width * ( 1 - 2* var.screenXmarginratio )

var.Scale[2,2] = Screen.Height * ( 1 - 2 * var.screenYmarginratio )

//okay
//debug = var.Scale

// Calculate origin translation for scaled rectangular matrix
// row vector format
// Ts->r = [1 0 0, 0 1 0, Xs->r  Ys->r  1 ]

var.Translate = [1,0,0;0,1,0;0,0,1]

// translation for new x0,y0 = 0,0

var.Translate[3,1] = Screen.Width * var.screenXmarginratio
var.Translate[3,2] = Screen.Height * var.screenYmarginratio

// Calculate net unit square scaling and translation to rectangle matrix
var.ScaleTranslate = var.Scale * var.Translate

//okay
//debug = var.ScaleTranslate

var.QuadToRect = var.ADJ * var.ScaleTranslate

//okay
//debug = var.QuadToRect


var.macrocount = 6
wait 1s

  end  // end macrocount 5 : homography calculation complete


// RECTANGLE TO QUADRILATERAL MAPPING FOR CORNER POINTS

// Calculate Rectangular to Quadrilateral homography matrix via Unit Square transformation
// row vector format
// Hr->q = [Tr->s].[Sr->s].[Hs->q].


if   var.macrocount == 6

// Calculate origin translation matrix for rectangle to unit square
// row vector format
// Tr->s = Inverse[Ts->r] = [1 0 0, 0 1 0, -(Xs->r) -(Ys->r)  1 ]

var.InverseTranslate = [1,0,0;0,1,0;0,0,1]

// translation for new x0,y0 = 0,0

var.InverseTranslate[3,1] = 0 - ( Screen.Width * var.screenXmarginratio )
var.InverseTranslate[3,2] = 0 - ( Screen.Height * var.screenYmarginratio )



// Calculate scaling matrix for rectangle to unit square
// row vector format
// Sr->s = Inverse[Ss->r] = [ 1/Sx 0 0, 0 1/Sy 0, 0  0  1 ]

var.InverseScale = [1,0,0;0,1,0;0,0,1]

var.InverseScale[1,1] = (1 / ( Screen.Width * ( 1 - 2* var.screenXmarginratio ) )  )

var.InverseScale[2,2] = (1 / ( Screen.Height * ( 1 - 2 * var.screenYmarginratio ) ) )

// Calculate net rectangle to unit square translation and scaling matrix
var.TranslateScale = var.InverseTranslate * var.InverseScale

//debug = var.TranslateScale

var.RectToQuad = var.TranslateScale * var.UnitSquareToQuad

// BACK PLOTTING SCREEN RECTANGLE TO WII CAMERA IMAGE QUADRILATERAL FOR CHECKING SCREEN CORNER POINT VISIBILITY TO WIIMOTE
// TOP-LEFT QUAD CORNER
var.testextent1 = [0 , 0 ,1] *  var.RectToQuad

// TOP-RIGHT QUAD CORNER
var.testextent2 = [Screen.Width , 0 ,1] *  var.RectToQuad
//var.testextent2 = [1280 , 0 ,1] *  var.RectToQuad

// BOTTOM-RIGHT QUAD CORNER
var.testextent3 = [Screen.Width , Screen.Height ,1] *  var.RectToQuad
//var.testextent3 = [1280 , 960 ,1] *  var.RectToQuad

// BOTTOM-LEFT QUAD CORNER
var.testextent4 = [0 , Screen.Height ,1] *  var.RectToQuad
//var.testextent4 = [0 , 960 ,1] *  var.RectToQuad

//NOTE: WII CAMERA VIEW OF CORNER POINTS ARE SHOWN AT ITS NATIVE 4:3 ASPECT RATIO, REGARDLESS OF WIDESCREEN DISPLAY ASPECT RATIO
//NORMALISED TO SCREEN HEIGHT, ASSUMES SQUARE PIXELS AND LANDSCAPE MODE
//Corner Point 1 - Top Left
var.wte1 = var.testextent1[3]
var.ute1 = var.testextent1[1]/var.wte1
var.vte1 = var.testextent1[2]/var.wte1

// debug =  var.ute1 + '   ' + var.vte1

//Cursor31.PosX = var.ute1/1024 * Screen.Width
Cursor31.PosX = var.ute1/1024 * Screen.Height * 4 / 3  + Screen.Width/2 - 2/3 * Screen.Height
Cursor31.PosY = var.vte1/768 * Screen.Height

Cursor31.Caption = "( 0 , 0 )"
Cursor31.roll = 45
Cursor31.Visible = true

//Corner Point 2 - Top Right
var.wte2 = var.testextent2[3]
var.ute2 = var.testextent2[1]/var.wte2
var.vte2 = var.testextent2[2]/var.wte2

//debug =  var.ute2 + '   ' + var.vte2

//Cursor32.PosX = var.ute2/1024 * Screen.Width
Cursor32.PosX = var.ute2/1024 * Screen.Height * 4/3  + Screen.Width/2 - 2/3 * Screen.Height
Cursor32.PosY = var.vte2/768 * Screen.Height

Cursor32.Caption = "( 1 , 0 )"
Cursor32.roll = 45
Cursor32.Visible = true

//Corner Point 3 - Bottom Right
var.wte3 = var.testextent3[3]
var.ute3 = var.testextent3[1]/var.wte3
var.vte3 = var.testextent3[2]/var.wte3

//debug =  var.ute3 + '   ' + var.vte3

//Cursor33.PosX = var.ute3/1024 * Screen.Width
Cursor33.PosX = var.ute3/1024 * Screen.Height * 4/3 + Screen.Width/2 - 2/3 * Screen.Height
Cursor33.PosY = var.vte3/768 * Screen.Height

Cursor33.Caption = "( 1 , 1 )"
Cursor33.roll = 45
Cursor33.Visible = true

//Corner Point 4 - Bottom Left
var.wte4 = var.testextent4[3]
var.ute4 = var.testextent4[1]/var.wte4
var.vte4 = var.testextent4[2]/var.wte4

//debug =  var.ute3 + '   ' + var.vte3

//Cursor34.PosX = var.ute4/1024 * Screen.Width
Cursor34.PosX = var.ute4/1024 * Screen.Height * 4/3 + Screen.Width/2 - 2/3 * Screen.Height
Cursor34.PosY = var.vte4/768 * Screen.Height

Cursor34.Caption = "( 0 , 1 )"
Cursor34.roll = 45
Cursor34.Visible = true


var.diagonalangle = atan( Screen.Height/Screen.Width)

Cursor41.Roll = var.diagonalangle - 90
Cursor42.Roll = 90 - var.diagonalangle
Cursor43.Roll = 90 + var.diagonalangle
Cursor44.Roll = 0 - 90 - var.diagonalangle


var.macrocount = 7
wait 1s

end if  // end macrocount 6


//CHECKING SCREEN CORNER POINT VISIBILITY IN WIIMOTE CAMERA - FOR SINGLE POINTER LED ONLY !!!
if var.macrocount == 7

// testing screen top left corner point visibility

if (var.ute1 < 0) or (var.ute1 > 1024) or (var.vte1 < 0) or (var.vte1 > 768)

    Cursor41.PermanentCursor = -2
    Cursor41.PosX = Screen.Width*0.1
    Cursor41.Posy = Screen.Height*0.1
    Cursor41.Caption = ""

    Cursor41.Visible = true

    var.visibleflag = 0
    wait 0.5s

end if


// testing screen top right corner point visibility

if (var.ute2 < 0) or (var.ute2 > 1024) or (var.vte2 < 0) or (var.vte2 > 768)

    Cursor42.PermanentCursor = -2
    Cursor42.PosX = Screen.Width*0.9
    Cursor42.Posy = Screen.Height*0.1
    Cursor42.Caption = ""

    Cursor42.Visible = true

    var.visibleflag = 0
    wait 0.5s

end if

// testing screen bottom right corner point visibility

if (var.ute3 < 0) or (var.ute3 > 1024) or (var.vte3 < 0) or (var.vte3 > 768)

    Cursor43.PermanentCursor = -2
    Cursor43.PosX = Screen.Width*0.9
    Cursor43.Posy = Screen.Height*0.9
    Cursor43.Caption = ""

    Cursor43.Visible = true

    var.visibleflag = 0
    wait 0.5s

end if

// testing screen bottom left corner point visibility

if (var.ute4 < 0) or (var.ute4 > 1024) or (var.vte4 < 0) or (var.vte4 > 768)

    Cursor44.PermanentCursor = -2
    Cursor44.PosX = Screen.Width*0.1
    Cursor44.Posy = Screen.Height*0.9
    Cursor44.Caption = ""

    Cursor44.Visible = true

    var.visibleflag = 0
    wait 0.5s

end if


var.macrocount = 8
wait 1s

end if // end macrocount 7 : Screen quadrilateral visibilty for wii remote camera


if var.macrocount == 8

if var.visibleflag == 1

    Cursor14.PermanentCursor = -2
    Cursor14.PosX =  Screen.Width/2 - 200
    Cursor14.Caption = "Whiteboard 4 Point Calibration Complete - All corner points of screen are visible to the Wiimote"
    Cursor14.Visible = true

    //Calculate tracking utilisation

    var.diagonal1 = [(var.ute3 - var.ute1),(var.vte3 - var.vte1)]

    var.diagonal2 = [(var.ute4 - var.ute2),(var.vte4 - var.vte2)]

    var.WiiCamQuadPixelArea = 0.5 * | (var. diagonal1 x var. diagonal2) |

    var.WiiCamSensorPixelArea = 1024 * 768

    var.trackutilisation = Int(var.WiiCamQuadPixelArea / var.WiiCamSensorPixelArea * 100 )

    var.batterylevel =  Int(wiimote.Battery/1.92)

    debug = 'Tracking utilisation = ' + var.trackutilisation + ' %     '   +  'Battery Level = ' +  var.batterylevel + ' %     '  +  'Maximum Pen Click Time Interval = ' +  var.pointerinitiatetime + '    (This can be adjusted dynamically with Windows Control Panel open)  '

    wait 10s

    var.macrocount = 9


else

    Cursor14.PermanentCursor = 12
    Cursor14.PosX =  Screen.Width/2 - 400
    Cursor14.Caption = " WARNING  -  The indicated Far Corner Point of screen is out of Camera view.  Please adjust the Wii Remote position and recalibrate."
    Cursor14.Visible = true

    debug = 'Tracking utilisation is NOT APPLICABLE   '   +  'Battery Level = ' +  var.batterylevel + ' %'

    wait 10s

end if //  all corner points visible to IR camera ... proceed to whiteboard


wait 1s

end if // end macrocount 8


if var.macrocount == 9

debug = 'Tracking utilisation = ' + var.trackutilisation + ' %     '   +  'Battery Level = ' +  var.batterylevel + ' %     '  +  'Maximum Pen Click Time Interval = ' +  var.pointerinitiatetime + '    (This can be adjusted dynamically with Windows Control Panel open)  '

Cursor14.PosX =  Screen.Width/2 - 100
Cursor14.Caption = "Double-Click Pen on Screen to minimise GlovePie to tray"

        if DoubleClicked(wiimote.dot1vis)

           Cursor14.Caption = "Minimising GlovePie .... please wait "

           MinimizePie

           // Screen calibration points
           Cursor10.Visible = false
           Cursor11.Visible = false
           Cursor12.Visible = false
           Cursor13.Visible = false
           Cursor14.Visible = false


           //Wiimote corner point extents
           Cursor30.Visible = false
           Cursor31.Visible = false
           Cursor32.Visible = false
           Cursor33.Visible = false
           Cursor34.Visible = false

           // Corner direction pointers
           Cursor40.Visible = false
           Cursor41.Visible = false
           Cursor42.Visible = false
           Cursor43.Visible = false
           Cursor44.Visible = false

           wait 1s

           var.macrocount = 10

           wait 1s

         end if // minimise glovepie

end if // end macrocount 9

15
IR Pens / Re: Dual IR LED IWB Wii Mouse Pen
« on: September 09, 2011, 05:23:04 AM »
//

// GLOVEPIE INTERACTIVE WHITEBOARD SOFTWARE
// FOR DUAL IR LED ROCKER SWITCH MOUSE PEN (or equivalent) with WII REMOTE SENSOR

// Version 2.0 - Released for Publication
// Friday 9 September 2011
// By M.A.V. Brisbane, Australia

// DUAL IR LED ROCKER SWITCH MOUSE PEN details originally published at:
//   http://www.wiimoteproject.com/ir-pens/dual-ir-led-iwb-wii-mouse-pen/

// PROGRAMMED IN GLOVEPIE VERSION 0.43 WITH 32-bit WINDOWS XP3 ON X86 INTEL PC

// Particular thanks to Carl Kenner (GlovePIE) and Nintendo (Wii Remote)
//   and thanks to the Many Others for your technical contributions and inspirations

// MATHEMATICS OF PERSPECTIVE PROJECTION based on:

// SOURCE 1:
// http://www1.cs.columbia.edu/~belhumeur/courses/compPhoto/heckbert-proj.pdf
// Citation:
// "Fundamentals of Texture Mapping and Image Warping"
// Paul Heckbert
// pp 17-21, Masterís thesis, UCB/CSD 89/516, CS Division, U.C. Berkeley, June 1989.

// SOURCE 2:
// http://www.decew.net/OSS/References/Quadrilateral%20mapping.pdf
// Citation:
// "A Planar Perspective Image Matching using Point Correspondences and Rectangle-to-Quadrilateral Mapping,"
// Dong-Keun Kim, Byung-Tae Jang, Chi-Jung Hwang,
// ssiai, pp.0087, Fifth IEEE Southwest Symposium on Image Analysis and Interpretation, 2002

//NOTE: For consistency with convention, the co-ordinate origin for the Wii IR CAMERA Image and CURSOR Screen, is the TOP LEFT CORNER.
//The X-axis points rightward and the Y-axis is inverted and points downward
//This requires a corrective Y-axis transformation for the wiimote IR Image points:  wiimote.dot1y -> 768 - wiimote.dot1y

// DONE LIST
// DONE - TEST CALIBRATION TARGETS
// DONE - TEST VIEW OF SCREEN CORNERS BY WII REMOTE CAMERA
// DONE - TEST TRACKING AREA UTILISATION
// DONE - TEST BATTERY LEVEL
// DONE - TEST REAL DUAL LED TWO BUTTON MOUSE PEN
// DONE - TEST INTEGRATION OF RIGHT BUTTON and LEFT BUTTON MOUSE COMMANDS USING SINGLE AND DUAL LED INDICATION
// DONE - TEST DRAG & DROP + CUT & PASTE
// DONE - TEST MINIMISING THE GLOVEPIE SET-UP SCREEN TO THE TRAY WITH PEN DOUBLE CLICK
// DONE - MAP OUT THE CONFIGURATION OF THE PEN MOUSE BUTTONS AND ROCKER SWITCH POSITIONS CORRESPONDING TO THE ACTUAL MOUSE OUTPUT COMMANDS
// DONE - TEST DYNAMIC MOUSE CLICK SPEED ADJUSTMENT FROM WINDOWS CONTROL PANEL

// FUTURE LIST
// Future - TEST LEFT HANDED OR RIGHT HANDED PEN SELECTION OPTION USING THE INITIAL CALIBRATION AND SET UP SCREEN

// **** LIMITATIONS ****
// Is is essential that both PEN IR LEDS can be detected by the WII REMOTE CAMERA when in use with the WHITEBOARD or other SCREEN
// The software is set up for RIGHT HANDED PEN USE and for the Wii Remote Camera to be seeing the left side of the pen
// The screen must have sufficient diffuse reflectivity so the TIP LED IR LIGHT is readily reflected and can be detected by the Wii Remote Camera
//  - otherwise use a piece of matte single sided tape loosely stuck to the pen tip to act as a tip led reflection surface - it works well
// Be mindful of the pen button mapping with respect to the mouse button actions - including the timeout delay for the pressed button modes
// The software assumes the Wii Remote Camera and Screen are aligned with no significant horizontal roll angle difference
// The pen mouse click speed (Double Click speed) can be manually adjusted by the slider control in the Mouse section of Windows Control Panel


if starting

// LEFT MOUSE BUTTON COMMANDS
 var.pointermode = false

// RIGHT MOUSE BUTTON COMMANDS
 var.rightpressmode = false

// RIGHT HANDED OR LEFT HANDED PEN OPTION
// for left side view of pen - using pen with right hand and pen pointing left on screen
 var.righthandpen = true

// ALTERNATIVELY - for right side view of pen - using pen with left hand - pointing right on screen
// CHANGE: var.righthandpen from '=true' to '=false'

 var.lastmousecommand = '  none    '

// FRAME BUFFERING VARIABLES FOR LED SWITCHING INDICATION
 var.newvis1 = false

 var.newvis2 = false

 var.vis1 = false

 var.vis2 = false

 var.buffercount = 0


// inside screen margin fraction for point calibration
var.screenXmarginratio = 0.1
var.screenYmarginratio = 0.1

var.macrocount = 0

Cam.BgColour = 0xFFFFFF

// Screen calibration points
Cursor10.Visible = false
Cursor11.Visible = false
Cursor12.Visible = false
Cursor13.Visible = false
Cursor14.Visible = false


//Wiimote corner point extents
Cursor30.Visible = false
Cursor31.Visible = false
Cursor32.Visible = false
Cursor33.Visible = false
Cursor34.Visible = false

// Corner direction pointers
Cursor40.Visible = false
Cursor41.Visible = false
Cursor42.Visible = false
Cursor43.Visible = false
Cursor44.Visible = false


Cursor10.Caption = "Click on Centre"
Cursor11.Caption = "Click on Centre"
Cursor12.Caption = "Click on Centre"
Cursor13.Caption = "Click on Centre"


Cursor10.PermanentCursor = 2
Cursor11.PermanentCursor = 2
Cursor12.PermanentCursor = 2
Cursor13.PermanentCursor = 2


Cursor30.PermanentCursor = 2
Cursor31.PermanentCursor = 2
Cursor32.PermanentCursor = 2
Cursor33.PermanentCursor = 2
Cursor34.PermanentCursor = 2

Cursor41.PermanentCursor = -2
Cursor42.PermanentCursor = -2
Cursor43.PermanentCursor = -2
Cursor44.PermanentCursor = -2

var.visibleflag = 1

     // Set WII IR CAMERA FOR MAXIMUM SENSITIVITY
     // Start of Wiimote IR CAMERA Sensistivy Programming block

     // step 1
     // Enable IR Camera (Send 0x04 to Output Report 0x13)
     WiimoteSend(1, 0x13, 0x04)

     wait 100ms

     // step 2
     //Enable IR Camera 2 (Send 0x04 to Output Report 0x1a)
     WiimoteSend(1, 0x1a, 0x04)

     wait 100ms

     // step 3
     //Write 0x08 to register 0x4b00030
     WiimotePoke(1,0x04b00030, 0x08)

     wait 100ms

    // step 4
    //Write Sensitivity Block 1 to registers at 0x4b00000
     WiimotePoke(1,0x04b00000, 0x02)
     wait 100ms
     WiimotePoke(1,0x04b00001, 0x00)
     wait 100ms
     WiimotePoke(1,0x04b00002, 0x00)
     wait 100ms
     WiimotePoke(1,0x04b00003, 0x00)
     wait 100ms
     WiimotePoke(1,0x04b00004, 0x00)
     wait 100ms
     WiimotePoke(1,0x04b00005, 0x00)
     wait 100ms
     WiimotePoke(1,0x04b00006, 0xFF)
     wait 100ms
     WiimotePoke(1,0x04b00007, 0x00)
     wait 100ms
     // maximimu sensitivity setting - 0xc0
     WiimotePoke(1,0x04b00008, 0xc0)

     wait 100ms

     //step 5
     //Write Sensitivity Block 2
     WiimotePoke(1,0x04b0001a, 0x40)

     wait 100ms
     WiimotePoke(1,0x04b0001b, 0x00)

     wait 100ms
    //step 6
    // Write Mode Number to register 0xb00033
    WiimotePoke(1,0x04b00033, 0x01)

    wait 100ms

    //step 7
    // Write 0x08 to register 0x4b00030 (again)
    WiimotePoke(1,0x04b00030, 0x08)

    wait 100ms
    // END of Wiimote IR CAMERA Sensistivy Programming block


end if  // starting


// DYNAMICALLY ADJUSTIBLE MOUSE CLICK SPEED TIMING
// CHANGE THE MOUSE CLICK SPEED IN THE WINDOWS CONTROL PANEL WHILST THIS PROGRAM IS RUNNING
// Open the VARIABLES Menu in GlovePIE or view the debug box status display to view the current mouse speed setting

// Pen mouse clicking time is set relative to the system mouse clicking time
// so as to lock-in the synchronisation of switching commands in the case structure

// POINTER BUTTON PRESSING NEEDS A NEGATIVE TIME DELAY TO BLOCK INCIDENTAL SINGLE CLICK FIRING IN THE CASE STRUCTURE - DO NOT MAKE POSITIVE
var.pointerinitiatetime = Mouse.DoubleClickTime - 20ms

var.pointerextendtime = Mouse.DoubleClickTime + 750ms


// CONTEXT BUTTON PRESSING NEEDS A NEGATIVE TIME DELAY TO BLOCK INCIDENTAL SINGLE CLICK FIRING IN THE CASE STRUCTURE - DO NOT MAKE POSITIVE
var.rightpressinitiatetime = Mouse.DoubleClickTime - 20ms

var.rightpressextendtime = Mouse.DoubleClickTime + 750ms


// WIIMOTE CAMERA CALIBRATION POINTS Module
// CALIBRATION - FOUR CORNER POINTS - LESS MARGIN

// TOP LEFT SCREEN POINT
if  var.macrocount == 0

Cursor10.Visible = true


var.px0 = Screen.Width  * var.screenXmarginratio
var.py0 = Screen.Height * var.screenYmarginratio


Cursor10.PosX =  var.px0
Cursor10.PosY =  var.py0

         if wiimote.dot1vis == true

               //WIIMOTE POINT 1 CAPTURE

                var.x0 = wiimote.dot1x + 0.5
                var.y0 = 767.5 - wiimote.dot1y

                Cursor10.PermanentCursor = 12
                Cursor10.Caption = "DONE"
                wait 1s
                var.macrocount = 1

                //debug =  var.x0 +  '   '  +  var.y0
                //wait 10s

                wait 0.5s

         end if

end if // point 1 calibrationr


// TOP RIGHT SCREEN POINT
if  var.macrocount == 1

Cursor11.Visible = true

var.px1 = Screen.Width  * (1 - var.screenXmarginratio )
var.py1 = Screen.Height * var.screenYmarginratio

Cursor11.PosX =  var.px1
Cursor11.PosY =  var.py1

        if wiimote.dot1vis == true

            //WIIMOTE POINT 2 CAPTURE

             var.x1 = wiimote.dot1x + 0.5
             var.y1 = 767.5 - wiimote.dot1y

             Cursor11.PermanentCursor = 12
             Cursor11.Caption = "DONE"
             wait 1s
             var.macrocount = 2

             //debug =  var.x1 +  '   '  +  var.y1
             //wait 10s

             wait 0.5s

         end if


end if  // point 2 calibration

// BOTTOM RIGHT SCREEN POINT
if  var.macrocount == 2

Cursor12.Visible = true

var.px2 = Screen.Width  * (1 - var.screenXmarginratio )
var.py2 = Screen.Height * (1 - var.screenYmarginratio )


Cursor12.PosX =  var.px2
Cursor12.PosY =  var.py2

        if wiimote.dot1vis == true

              //WIIMOTE POINT 3 CAPTURE

              var.x2 = wiimote.dot1x + 0.5
              var.y2 = 767.5 - wiimote.dot1y

              Cursor12.PermanentCursor = 12
              Cursor12.Caption = "DONE"
              wait 1s
              var.macrocount = 3

              //debug =  var.x2 +  '   '  +  var.y2
              //wait 10s

              wait 0.5s

          end if

  end if // point 3 calibration


// BOTTOM LEFT SCREEN POINT
if  var.macrocount == 3

Cursor13.Visible = true

var.px3 = Screen.Width  *  var.screenXmarginratio
var.py3 = Screen.Height * (1 - var.screenYmarginratio )


Cursor13.PosX =  var.px3
Cursor13.PosY =  var.py3
  
          if wiimote.dot1vis == true

                //WIIMOTE POINT 4 CAPTURE

                var.x3 = wiimote.dot1x + 0.5
                var.y3 = 767.5 - wiimote.dot1y

                Cursor13.PermanentCursor = 12
                Cursor13.Caption = "DONE"
                wait 1s
                var.macrocount = 4

                //debug =  var.x3 +  '   '  +  var.y3
                //wait 10s

                wait 0.5s

            end if

end if // point 4 calibration

// Terminate Calibration Screen
if  var.macrocount == 4

     var.px4 = Screen.Width/2 - 350
     var.py4 = Screen.height/2 - 200

     Cursor14.PosX =  var.px4
     Cursor14.PosY =  var.py4

     wait 1s
     var.macrocount = 5

     // Screen calibration points
     Cursor10.Visible = false
     Cursor11.Visible = false
     Cursor12.Visible = false
     Cursor13.Visible = false
     Cursor14.Visible = false

     wait 1s

end if // end macrocount 4 : four point calibration complete

//END OF WIIMOTE CAMERA CALIBRATION POINTS Module


Pages: 1 2 3 ... 5