0

uncanny eyes with Teensy 3.1
Moderators: adafruit_support_bill, adafruit

Please be positive and constructive with your questions and comments.

Re: uncanny eyes with Teensy 3.1

by imwoody36 on Mon Apr 15, 2019 8:37 am

I feel validated that im not the only one with problems

imwoody36
 
Posts: 19
Joined: Wed Apr 26, 2017 2:20 pm

Re: uncanny eyes with Teensy 3.1

by imwoody36 on Mon Apr 15, 2019 9:32 am

okay,
I installed the new arduino gui 1.8.9
and the teensy installer without any add ons (for 1.8.9 arduino beta)
and I verified the two librarys ...gfx and 1351 as instructed.


still get the invalid conversion spi error shown below

Arduino: 1.8.9 (Windows 10), TD: 1.46-beta10, Board: "Teensy 3.2 / 3.1, Serial, 72 MHz, Faster, US English"

C:\Program Files (x86)\Arduino\arduino-builder -dump-prefs -logger=machine -hardware C:\Program Files (x86)\Arduino\hardware -hardware C:\Users\Steve Woodruff\AppData\Local\Arduino15\packages -tools C:\Program Files (x86)\Arduino\tools-builder -tools C:\Program Files (x86)\Arduino\hardware\tools\avr -tools C:\Users\Steve Woodruff\AppData\Local\Arduino15\packages -built-in-libraries C:\Program Files (x86)\Arduino\libraries -libraries C:\Users\Steve Woodruff\Documents\Arduino\libraries -fqbn=teensy:avr:teensy31:usb=serial,speed=72,opt=o2std,keys=en-us -ide-version=10809 -build-path C:\Users\STEVEW~1\AppData\Local\Temp\arduino_build_869234 -warnings=none -build-cache C:\Users\STEVEW~1\AppData\Local\Temp\arduino_cache_690023 -verbose C:\Users\Steve Woodruff\Documents\Arduino\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino
C:\Program Files (x86)\Arduino\arduino-builder -compile -logger=machine -hardware C:\Program Files (x86)\Arduino\hardware -hardware C:\Users\Steve Woodruff\AppData\Local\Arduino15\packages -tools C:\Program Files (x86)\Arduino\tools-builder -tools C:\Program Files (x86)\Arduino\hardware\tools\avr -tools C:\Users\Steve Woodruff\AppData\Local\Arduino15\packages -built-in-libraries C:\Program Files (x86)\Arduino\libraries -libraries C:\Users\Steve Woodruff\Documents\Arduino\libraries -fqbn=teensy:avr:teensy31:usb=serial,speed=72,opt=o2std,keys=en-us -ide-version=10809 -build-path C:\Users\STEVEW~1\AppData\Local\Temp\arduino_build_869234 -warnings=none -build-cache C:\Users\STEVEW~1\AppData\Local\Temp\arduino_cache_690023 -verbose C:\Users\Steve Woodruff\Documents\Arduino\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino
Using board 'teensy31' from platform in folder: C:\Program Files (x86)\Arduino\hardware\teensy\avr
Using core 'teensy3' from platform in folder: C:\Program Files (x86)\Arduino\hardware\teensy\avr
Detecting libraries used...
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI\\SPI.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library\\Adafruit_GFX.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library\\Adafruit_SPITFT.cpp" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library\\glcdfont.c" -o nul
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library\\Adafruit_SSD1351.cpp" -o nul
Generating function prototypes...
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -E -CC -x c++ -w -g -Wall -ffunction-sections -fdata-sections -nostdlib -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\preproc\\ctags_target_for_gcc_minus_e.cpp"
"C:\\Program Files (x86)\\Arduino\\tools-builder\\ctags\\5.8-arduino11/ctags" -u --language-force=c++ -f - --c++-kinds=svpf --fields=KSTtzns --line-directives "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\preproc\\ctags_target_for_gcc_minus_e.cpp"
Compiling sketch...
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/precompile_helper" "C:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr/cores/teensy3" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234" "C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -x c++-header -O2 -g -Wall -ffunction-sections -fdata-sections -nostdlib -MMD -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr/cores/teensy3" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234/pch/Arduino.h" -o "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234/pch/Arduino.h.gch"
Using previously compiled file: C:\Users\STEVEW~1\AppData\Local\Temp\arduino_build_869234\pch\Arduino.h.gch

"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-g++" -c -O2 -g -Wall -ffunction-sections -fdata-sections -nostdlib -MMD -fno-exceptions -felide-constructors -std=gnu++14 -Wno-error=narrowing -fno-rtti -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -D__MK20DX256__ -DTEENSYDUINO=146 -DARDUINO=10809 -DF_CPU=72000000 -DUSB_SERIAL -DLAYOUT_US_ENGLISH "-IC:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234/pch" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3" "-IC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\libraries\\SPI" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_GFX_Library" "-IC:\\Users\\Steve Woodruff\\Documents\\Arduino\\libraries\\Adafruit_SSD1351_library" "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp" -o "C:\\Users\\STEVEW~1\\AppData\\Local\\Temp\\arduino_build_869234\\sketch\\uncannyEyes.ino.cpp.o"
uncannyEyes: In function 'void setup()':
uncannyEyes:132: error: invalid conversion from 'SPIClass*' to 'int8_t {aka signed char}' [-fpermissive]
eye[e].display = new displayType(&TFT_SPI, eyeInfo[e].select, DISPLAY_DC, -1);

^

In file included from C:\Users\STEVEW~1\AppData\Local\Temp\arduino_build_869234\sketch\config.h:80:0,

from C:\Users\Steve Woodruff\Documents\Arduino\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino:32:

C:\Users\Steve Woodruff\Documents\Arduino\libraries\Adafruit_SSD1351_library/Adafruit_SSD1351.h:90:5: note: initializing argument 1 of 'Adafruit_SSD1351::Adafruit_SSD1351(int8_t, int8_t, int8_t, int8_t, int8_t)'

Adafruit_SSD1351(int8_t cs_pin, int8_t dc_pin, int8_t mosi_pin,

^

Using library SPI at version 1.0 in folder: C:\Program Files (x86)\Arduino\hardware\teensy\avr\libraries\SPI
Using library Adafruit_GFX_Library at version 1.4.9 in folder: C:\Users\Steve Woodruff\Documents\Arduino\libraries\Adafruit_GFX_Library
Using library Adafruit_SSD1351_library at version 1.2.0 in folder: C:\Users\Steve Woodruff\Documents\Arduino\libraries\Adafruit_SSD1351_library
invalid conversion from 'SPIClass*' to 'int8_t {aka signed char}' [-fpermissive]

imwoody36
 
Posts: 19
Joined: Wed Apr 26, 2017 2:20 pm

Re: uncanny eyes with Teensy 3.1

by pburgess on Tue Apr 16, 2019 1:04 am

I don’t have a fix yet, but just letting you know I’ve been able to reproduce it now. Oddly the issue manifests on Windows but not on Mac. I’ll probably have a workaround tomorrow, will let you know here when that happens.

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by pburgess on Tue Apr 16, 2019 2:11 pm

Required a small change in the uncannyEyes.ino sketch, the latest can be retrieved from Github:
https://github.com/adafruit/Uncanny_Eyes

I’m a bit baffled as to why the problem only appeared on Windows, but it does appear to be fixed now. Thanks for your patience.

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by imwoody36 on Tue Apr 16, 2019 4:43 pm

it compiled and loaded for me!,
no display yet , but it was 2 minutes ago and I expect i will find a wiring error soon.

thanks for your efforts

imwoody36
 
Posts: 19
Joined: Wed Apr 26, 2017 2:20 pm

Re: uncanny eyes with Teensy 3.1

by imwoody36 on Thu Apr 18, 2019 3:08 pm

Is there a way to mirror an eye?
I have experimented with right and left,
and I have rotated with the config file line 48
and I have helped my cross eyed and Derpy eyes by making them Symmetrical

imwoody36
 
Posts: 19
Joined: Wed Apr 26, 2017 2:20 pm

Re: uncanny eyes with Teensy 3.1

by pburgess on Thu Apr 18, 2019 4:55 pm

One of the displays is mirrored, this starts around line 226 in the sketch. In order to avoid 'derpy eyes,' line 609 then flips the pupil X coordinate when drawing that eye.

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by frostfyre on Tue Apr 23, 2019 6:33 pm

I am also having an issue with verifying the code since it gives me this error message:

Code: Select all | TOGGLE FULL SIZE









C:\Users\Celti\Desktop\UncannyEyes\uncannyEyes\uncannyEyes.ino:57:0: warning: "IRIS_MAX" redefined

 #define IRIS_MAX      720 // Clip upper "

 ^

In file included from C:\Users\Celti\Desktop\UncannyEyes\uncannyEyes\uncannyEyes.ino:22:0:

sketch\graphics/noScleraEye.h:2:0: note: this is the location of the previous definition

 #define IRIS_MAX 550

 ^

C:\Users\Celti\Desktop\UncannyEyes\uncannyEyes\uncannyEyes.ino:611:17: warning: extra tokens at end of #ifdef directive

 #ifdef IRIS_PIN && (IRIS_PIN >= 0) // Interactive iris  ***

                 ^

C:\Users\Celti\Desktop\UncannyEyes\uncannyEyes\uncannyEyes.ino: In function 'void setup()':

uncannyEyes:232:16: error: 'ST7735_MADCTL' was not declared in this scope

   SPI.transfer(ST7735_MADCTL);

                ^

exit status 1
'ST7735_MADCTL' was not declared in this scope


Not sure what it means, or if I have to change it to something else more specific.

frostfyre
 
Posts: 4
Joined: Tue Apr 23, 2019 6:29 pm

Re: uncanny eyes with Teensy 3.1

by pburgess on Tue Apr 23, 2019 7:34 pm

@frostfire — looks like you’re using an older version or someone else’s version of the uncannyEyes source. Please fetch the current code here:
https://github.com/adafruit/Uncanny_Eyes

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by frostfyre on Tue Apr 23, 2019 7:48 pm

pburgess wrote:@frostfire — looks like you’re using an older version or someone else’s version of the uncannyEyes source. Please fetch the current code here:
https://github.com/adafruit/Uncanny_Eyes


Just did. It's now giving me this after verifying:

Code: Select all | TOGGLE FULL SIZE
Arduino: 1.8.9 (Windows 10), Board: "Teensy 3.2 / 3.1, Serial, 72 MHz, Faster, US English"

C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino: In function 'void setup()':

uncannyEyes:138:53: error: 'TFT_SPI' was not declared in this scope

     eye[e].display     = new displayType(128, 128, &TFT_SPI,

                                                     ^

C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino: In function 'void drawEye(uint8_t, uint16_t, uint8_t, uint8_t, uint8_t, uint8_t)':

uncannyEyes:365:28: error: 'IRIS_MAP_HEIGHT' was not declared in this scope

   uint32_t irisScale     = IRIS_MAP_HEIGHT * 65536 / irisThreshold;

                            ^

uncannyEyes:370:3: error: 'TFT_SPI' was not declared in this scope

   TFT_SPI.beginTransaction(settings);

   ^

uncannyEyes:376:57: error: 'SCREEN_HEIGHT' was not declared in this scope

   eye[e].display->spiWrite(0); eye[e].display->spiWrite(SCREEN_HEIGHT - 1);

                                                         ^

uncannyEyes:378:57: error: 'SCREEN_WIDTH' was not declared in this scope

   eye[e].display->spiWrite(0); eye[e].display->spiWrite(SCREEN_WIDTH  - 1);

                                                         ^

uncannyEyes:386:28: error: 'SCLERA_HEIGHT' was not declared in this scope

   irisY       = scleraY - (SCLERA_HEIGHT - IRIS_HEIGHT) / 2;

                            ^

uncannyEyes:386:44: error: 'IRIS_HEIGHT' was not declared in this scope

   irisY       = scleraY - (SCLERA_HEIGHT - IRIS_HEIGHT) / 2;

                                            ^

uncannyEyes:392:30: error: 'SCLERA_WIDTH' was not declared in this scope

     irisX   = scleraXsave - (SCLERA_WIDTH - IRIS_WIDTH) / 2;

                              ^

uncannyEyes:392:45: error: 'IRIS_WIDTH' was not declared in this scope

     irisX   = scleraXsave - (SCLERA_WIDTH - IRIS_WIDTH) / 2;

                                             ^

uncannyEyes:394:11: error: 'lower' was not declared in this scope

       if((lower[screenY][screenX] <= lT) ||

           ^

uncannyEyes:395:11: error: 'upper' was not declared in this scope

          (upper[screenY][screenX] <= uT)) {             // Covered by eyelid

           ^

uncannyEyes:399:13: error: 'sclera' was not declared in this scope

         p = sclera[scleraY][scleraX];

             ^

uncannyEyes:401:13: error: 'polar' was not declared in this scope

         p = polar[irisY][irisX];                        // Polar angle/dist

             ^

uncannyEyes:405:16: error: 'IRIS_MAP_WIDTH' was not declared in this scope

           a = (IRIS_MAP_WIDTH * (p >> 7)) / 512;        // Angle (X)

                ^

uncannyEyes:406:15: error: 'iris' was not declared in this scope

           p = iris[d][a];                               // Pixel = iris

               ^

uncannyEyes:408:15: error: 'sclera' was not declared in this scope

           p = sclera[scleraY][scleraX];                 // Pixel = sclera

               ^

C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino: In function 'void frame(uint16_t)':

uncannyEyes:609:32: error: 'SCLERA_WIDTH' was not declared in this scope

   eyeX = map(eyeX, 0, 1023, 0, SCLERA_WIDTH  - 128);

                                ^

uncannyEyes:610:32: error: 'SCLERA_HEIGHT' was not declared in this scope

   eyeY = map(eyeY, 0, 1023, 0, SCLERA_HEIGHT - 128);

                                ^

uncannyEyes:631:6: error: 'sampleY' was not declared in this scope

   if(sampleY < 0) n = 0;

      ^

uncannyEyes:632:24: error: 'upper' was not declared in this scope

   else            n = (upper[sampleY][sampleX] +

                        ^

uncannyEyes:633:39: error: 'SCREEN_WIDTH' was not declared in this scope

                        upper[sampleY][SCREEN_WIDTH - 1 - sampleX]) / 2;

                                       ^

exit status 1
'TFT_SPI' was not declared in this scope

frostfyre
 
Posts: 4
Joined: Tue Apr 23, 2019 6:29 pm

Re: uncanny eyes with Teensy 3.1

by pburgess on Tue Apr 23, 2019 8:28 pm

Make sure you're using the latest version of the Adafruit_GFX and display-specific libraries.

Also, if you’ve installed any of those using the Teensyduino installer, you’ll need to remove those versions and install them through the Arduino Library Manager instead. There’s been some feature drift over time and they’re no longer cross-compatible.

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by frostfyre on Tue Apr 23, 2019 9:05 pm

pburgess wrote:Make sure you're using the latest version of the Adafruit_GFX and display-specific libraries.

Also, if you’ve installed any of those using the Teensyduino installer, you’ll need to remove those versions and install them through the Arduino Library Manager instead. There’s been some feature drift over time and they’re no longer cross-compatible.


Everything's current and not using the Teensyduino libraries. So far, the same error messages occur with the TFT_SPI not declared and other jargon included:

Code: Select all | TOGGLE FULL SIZE
Arduino: 1.8.9 (Windows 10), Board: "Teensy 3.2 / 3.1, Serial, 72 MHz, Faster, US English"

In file included from C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino:37:0:

sketch\graphics/noScleraEye.h:2:0: warning: "IRIS_MAX" redefined

 #define IRIS_MAX 550

 ^

In file included from C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino:36:0:

sketch\config.h:116:0: note: this is the location of the previous definition

   #define IRIS_MAX      720 // Iris size (0-1023) in darkest light

 ^

C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino: In function 'void setup()':

uncannyEyes:138:43: error: 'TFT_SPI' was not declared in this scope

     eye[e].display     = new displayType(&TFT_SPI, eyeInfo[e].select,

                                           ^

uncannyEyes:243:7: error: 'TFT_SPI' was not declared in this scope

       TFT_SPI.transfer(ST77XX_MADCTL); // Current TFT lib

       ^

C:\Users\Celti\Desktop\Uncanny_Eyes-master\uncannyEyes\uncannyEyes.ino: In function 'void drawEye(uint8_t, uint16_t, uint8_t, uint8_t, uint8_t, uint8_t)':

uncannyEyes:373:3: error: 'TFT_SPI' was not declared in this scope

   TFT_SPI.beginTransaction(settings);

   ^

exit status 1
'TFT_SPI' was not declared in this scope



here's the current code loaded from github a few hours ago and in Adriuno:
Code: Select all | TOGGLE FULL SIZE
//--------------------------------------------------------------------------
// Uncanny eyes for Adafruit 1.5" OLED (product #1431) or 1.44" TFT LCD
// (#2088).  Works on PJRC Teensy 3.x and on Adafruit M0 and M4 boards
// (Feather, Metro, etc.).  This code uses features specific to these
// boards and WILL NOT work on normal Arduino or other boards!
//
// SEE FILE "config.h" FOR MOST CONFIGURATION (graphics, pins, display type,
// etc).  Probably won't need to edit THIS file unless you're doing some
// extremely custom modifications.
//
// Adafruit invests time and resources providing this open source code,
// please support Adafruit and open-source hardware by purchasing products
// from Adafruit!
//
// Written by Phil Burgess / Paint Your Dragon for Adafruit Industries.
// MIT license.  SPI FIFO insight from Paul Stoffregen's ILI9341_t3 library.
// Inspired by David Boccabella's (Marcwolf) hybrid servo/OLED eye concept.
//--------------------------------------------------------------------------

#include <SPI.h>
#include <Adafruit_ST7735.h>
#include <Adafruit_GFX.h>
#ifdef ARDUINO_ARCH_SAMD
  #include <Adafruit_ZeroDMA.h>
  #include <Adafruit_NeoMatrix_ZeroDMA.h>
#include <gamma.h>


 

#endif

typedef struct {        // Struct is defined before including config.h --
  int8_t  select;       // pin numbers for each eye's screen select line
  int8_t  wink;         // and wink button (or -1 if none) specified there,
  uint8_t rotation;     // also display rotation.
} eyeInfo_t;

#include "config.h"     // ****** CONFIGURATION IS DONE IN HERE ******


#if defined(_ADAFRUIT_ST7735H_) || defined(_ADAFRUIT_ST77XXH_)
  typedef Adafruit_ST7735  displayType; // Using TFT display(s)
#else
  typedef Adafruit_SSD1351 displayType; // Using OLED display(s)
#endif

// A simple state machine is used to control eye blinks/winks:
#define NOBLINK 0       // Not currently engaged in a blink
#define ENBLINK 1       // Eyelid is currently closing
#define DEBLINK 2       // Eyelid is currently opening
typedef struct {
  uint8_t  state;       // NOBLINK/ENBLINK/DEBLINK
  uint32_t duration;    // Duration of blink state (micros)
  uint32_t startTime;   // Time (micros) of last state change
} eyeBlink;

#define NUM_EYES (sizeof eyeInfo / sizeof eyeInfo[0]) // config.h pin list

struct {                // One-per-eye structure
  displayType *display; // -> OLED/TFT object
  eyeBlink     blink;   // Current blink/wink state
} eye[NUM_EYES];

#ifdef ARDUINO_ARCH_SAMD
  // SAMD boards use DMA (Teensy uses SPI FIFO instead):
  // Two single-line 128-pixel buffers (16bpp) are used for DMA.
  // Though you'd think fewer larger transfers would improve speed,
  // multi-line buffering made no appreciable difference.
  uint16_t          dmaBuf[2][128];
  uint8_t           dmaIdx = 0; // Active DMA buffer # (alternate fill/send)
  Adafruit_ZeroDMA  dma;
  DmacDescriptor   *descriptor;

  // DMA transfer-in-progress indicator and callback
  static volatile bool dma_busy = false;
  static void dma_callback(Adafruit_ZeroDMA *dma) { dma_busy = false; }
#endif

uint32_t startTime;  // For FPS indicator

#if defined(SYNCPIN) && (SYNCPIN >= 0)
#include <Wire.h>
// If two boards are synchronized over I2C, this struct is passed from one
// to other. No device-independent packing & unpacking is performed...both
// boards are expected to be the same architecture & endianism.
struct {
  uint16_t iScale;  // These are basically the same arguments as
  uint8_t  scleraX; // drawEye() expects, explained in that function.
  uint8_t  scleraY;
  uint8_t  uT;
  uint8_t  lT;
} syncStruct = { 512,
  (SCLERA_WIDTH-SCREEN_WIDTH)/2, (SCLERA_HEIGHT-SCREEN_HEIGHT)/2, 0, 0 };

void wireCallback(int n) {
  if(n == sizeof syncStruct) {
    // Read 'n' bytes from I2C into syncStruct
    uint8_t *ptr = (uint8_t *)&syncStruct;
    for(uint8_t i=0; i < sizeof syncStruct; i++) {
      ptr[i] = Wire.read();
    }
  }
}

bool receiver = false;
#endif // SYNCPIN

// INITIALIZATION -- runs once at startup ----------------------------------

void setup(void) {
  uint8_t e; // Eye index, 0 to NUM_EYES-1

#if defined(SYNCPIN) && (SYNCPIN >= 0) // If using I2C sync...
  pinMode(SYNCPIN, INPUT_PULLUP);      // Check for jumper to ground
  if(!digitalRead(SYNCPIN)) {          // If there...
    receiver = true;                   // Set this one up as receiver
    Wire.begin(SYNCADDR);
    Wire.onReceive(wireCallback);
  } else {
    Wire.begin();                      // Else set up as sender
  }
#endif

  Serial.begin(115200);
  //while (!Serial);
  Serial.println("Init");
  randomSeed(analogRead(A3)); // Seed random() from floating analog input

#ifdef DISPLAY_BACKLIGHT
  // Enable backlight pin, initially off
  Serial.println("Backlight off");
  pinMode(DISPLAY_BACKLIGHT, OUTPUT);
  digitalWrite(DISPLAY_BACKLIGHT, LOW);
#endif

  // Initialize eye objects based on eyeInfo list in config.h:
  for(e=0; e<NUM_EYES; e++) {
    Serial.print("Create display #"); Serial.println(e);
#if defined(_ADAFRUIT_ST7735H_) || defined(_ADAFRUIT_ST77XXH_) // TFT
    eye[e].display     = new displayType(&TFT_SPI, eyeInfo[e].select,
                           DISPLAY_DC, -1);
#else // OLED
    eye[e].display     = new displayType(128, 128, &TFT_SPI,
                           eyeInfo[e].select, DISPLAY_DC, -1);
#endif
    eye[e].blink.state = NOBLINK;
    // If project involves only ONE eye and NO other SPI devices, its
    // select line can be permanently tied to GND and corresponding pin
    // in config.h set to -1.  Best to use it though.
    if(eyeInfo[e].select >= 0) {
      pinMode(eyeInfo[e].select, OUTPUT);
      digitalWrite(eyeInfo[e].select, HIGH); // Deselect them all
    }
    // Also set up an individual eye-wink pin if defined:
    if(eyeInfo[e].wink >= 0) pinMode(eyeInfo[e].wink, INPUT_PULLUP);
  }
#if defined(BLINK_PIN) && (BLINK_PIN >= 0)
  pinMode(BLINK_PIN, INPUT_PULLUP); // Ditto for all-eyes blink pin
#endif

#if defined(DISPLAY_RESET) && (DISPLAY_RESET >= 0)
  // Because both displays share a common reset pin, -1 is passed to
  // the display constructor above to prevent the begin() function from
  // resetting both displays after one is initialized.  Instead, handle
  // the reset manually here to take care of both displays just once:
  Serial.println("Reset displays");
  pinMode(DISPLAY_RESET, OUTPUT);
  digitalWrite(DISPLAY_RESET, LOW);  delay(1);
  digitalWrite(DISPLAY_RESET, HIGH); delay(50);
  // Alternately, all display reset pin(s) could be connected to the
  // microcontroller reset, in which case DISPLAY_RESET should be set
  // to -1 or left undefined in config.h.
#endif

  // After all-displays reset, now call init/begin func for each display:
  for(e=0; e<NUM_EYES; e++) {
#if defined(_ADAFRUIT_ST7735H_) || defined(_ADAFRUIT_ST77XXH_) // TFT
    eye[e].display->initR(INITR_144GREENTAB);
    Serial.print("Init ST77xx display #"); Serial.println(e);
#else // OLED
    eye[e].display->begin();
#endif
    Serial.println("Rotate");
    eye[e].display->setRotation(eyeInfo[e].rotation);
  }
  Serial.println("done");

#if defined(LOGO_TOP_WIDTH) || defined(COLOR_LOGO_WIDTH)
  Serial.println("Display logo");
  // I noticed lots of folks getting right/left eyes flipped, or
  // installing upside-down, etc.  Logo split across screens may help:
  for(e=0; e<NUM_EYES; e++) { // Another pass, after all screen inits
    eye[e].display->fillScreen(0);
    #ifdef LOGO_TOP_WIDTH
      // Monochrome Adafruit logo is 2 mono bitmaps:
      eye[e].display->drawBitmap(NUM_EYES*64 - e*128 - 20,
        0, logo_top, LOGO_TOP_WIDTH, LOGO_TOP_HEIGHT, 0xFFFF);
      eye[e].display->drawBitmap(NUM_EYES*64 - e*128 - LOGO_BOTTOM_WIDTH/2,
        LOGO_TOP_HEIGHT, logo_bottom, LOGO_BOTTOM_WIDTH, LOGO_BOTTOM_HEIGHT,
        0xFFFF);
    #else
      // Color sponsor logo is one RGB bitmap:
      eye[e].display->fillScreen(color_logo[0]);
      eye[0].display->drawRGBBitmap(
        (eye[e].display->width()  - COLOR_LOGO_WIDTH ) / 2,
        (eye[e].display->height() - COLOR_LOGO_HEIGHT) / 2,
        color_logo, COLOR_LOGO_WIDTH, COLOR_LOGO_HEIGHT);
    #endif
    // After logo is drawn
  }
  #ifdef DISPLAY_BACKLIGHT
    int i;
    Serial.println("Fade in backlight");
    for(i=0; i<BACKLIGHT_MAX; i++) { // Fade logo in
      analogWrite(DISPLAY_BACKLIGHT, i);
      delay(2);
    }
    delay(1400); // Pause for screen layout/orientation
    Serial.println("Fade out backlight");
    for(; i>=0; i--) {
      analogWrite(DISPLAY_BACKLIGHT, i);
      delay(2);
    }
    for(e=0; e<NUM_EYES; e++) { // Clear display(s)
      eye[e].display->fillScreen(0);
    }
    delay(100);
  #else
    delay(2000); // Pause for screen layout/orientation
  #endif // DISPLAY_BACKLIGHT
#endif // LOGO_TOP_WIDTH

  // One of the displays is configured to mirror on the X axis.  Simplifies
  // eyelid handling in the drawEye() function -- no need for distinct
  // L-to-R or R-to-L inner loops.  Just the X coordinate of the iris is
  // then reversed when drawing this eye, so they move the same.  Magic!
#if defined(SYNCPIN) && (SYNCPIN >= 0)
  if(receiver) {
#endif
#if defined(_ADAFRUIT_ST7735H_) || defined(_ADAFRUIT_ST77XXH_) // TFT
    const uint8_t mirrorTFT[]  = { 0x88, 0x28, 0x48, 0xE8 }; // Mirror+rotate
    digitalWrite(eyeInfo[0].select, LOW);
    digitalWrite(DISPLAY_DC, LOW);
    #ifdef ST77XX_MADCTL
      TFT_SPI.transfer(ST77XX_MADCTL); // Current TFT lib
    #else
      TFT_SPI.transfer(ST7735_MADCTL); // Older TFT lib
    #endif
    digitalWrite(DISPLAY_DC, HIGH);
    TFT_SPI.transfer(mirrorTFT[eyeInfo[0].rotation & 3]);
    digitalWrite(eyeInfo[0].select , HIGH);
  #else // OLED
    const uint8_t rotateOLED[] = { 0x74, 0x77, 0x66, 0x65 },
                  mirrorOLED[] = { 0x76, 0x67, 0x64, 0x75 }; // Mirror+rotate
    // If OLED, loop through ALL eyes and set up remap register
    // from either mirrorOLED[] (first eye) or rotateOLED[] (others).
    // The OLED library doesn't normally use the remap reg (TFT does).
    for(e=0; e<NUM_EYES; e++) {
      eye[e].display->writeCommand(SSD1351_CMD_SETREMAP);
      eye[e].display->spiWrite(e ?
        rotateOLED[eyeInfo[e].rotation & 3] :
        mirrorOLED[eyeInfo[e].rotation & 3]);
    }
#endif
#if defined(SYNCPIN) && (SYNCPIN >= 0)
  } // Don't mirror receiver screen
#endif

#ifdef ARDUINO_ARCH_SAMD
  // Set up SPI DMA on SAMD boards:
  int                dmac_id;
  volatile uint32_t *data_reg;
  if(&TFT_PERIPH == &sercom0) {
    dmac_id  = SERCOM0_DMAC_ID_TX;
    data_reg = &SERCOM0->SPI.DATA.reg;
#if defined SERCOM1
  } else if(&TFT_PERIPH == &sercom1) {
    dmac_id  = SERCOM1_DMAC_ID_TX;
    data_reg = &SERCOM1->SPI.DATA.reg;
#endif
#if defined SERCOM2
  } else if(&TFT_PERIPH == &sercom2) {
    dmac_id  = SERCOM2_DMAC_ID_TX;
    data_reg = &SERCOM2->SPI.DATA.reg;
#endif
#if defined SERCOM3
  } else if(&TFT_PERIPH == &sercom3) {
    dmac_id  = SERCOM3_DMAC_ID_TX;
    data_reg = &SERCOM3->SPI.DATA.reg;
#endif
#if defined SERCOM4
  } else if(&TFT_PERIPH == &sercom4) {
    dmac_id  = SERCOM4_DMAC_ID_TX;
    data_reg = &SERCOM4->SPI.DATA.reg;
#endif
#if defined SERCOM5
  } else if(&TFT_PERIPH == &sercom5) {
    dmac_id  = SERCOM5_DMAC_ID_TX;
    data_reg = &SERCOM5->SPI.DATA.reg;
#endif
  }

  Serial.println("DMA init");
  dma.allocate();
  dma.setTrigger(dmac_id);
  dma.setAction(DMA_TRIGGER_ACTON_BEAT);
  descriptor = dma.addDescriptor(
    NULL,               // move data
    (void *)data_reg,   // to here
    sizeof dmaBuf[0],   // this many...
    DMA_BEAT_SIZE_BYTE, // bytes/hword/words
    true,               // increment source addr?
    false);             // increment dest addr?
  dma.setCallback(dma_callback);

#endif // End SAMD-specific SPI DMA init

#ifdef DISPLAY_BACKLIGHT
  Serial.println("Backlight on!");
  analogWrite(DISPLAY_BACKLIGHT, BACKLIGHT_MAX);
#endif

  startTime = millis(); // For frame-rate calculation
}


// EYE-RENDERING FUNCTION --------------------------------------------------

SPISettings settings(SPI_FREQ, MSBFIRST, SPI_MODE0);

void drawEye( // Renders one eye.  Inputs must be pre-clipped & valid.
  uint8_t  e,       // Eye array index; 0 or 1 for left/right
  uint16_t iScale,  // Scale factor for iris (0-1023)
  uint8_t  scleraX, // First pixel X offset into sclera image
  uint8_t  scleraY, // First pixel Y offset into sclera image
  uint8_t  uT,      // Upper eyelid threshold value
  uint8_t  lT) {    // Lower eyelid threshold value

  uint8_t  screenX, screenY, scleraXsave;
  int16_t  irisX, irisY;
  uint16_t p, a;
  uint32_t d;

#if defined(SYNCPIN) && (SYNCPIN >= 0)
  if(receiver) {
    // Overwrite arguments with values in syncStruct.  Disable interrupts
    // briefly so new data can't overwrite the struct in mid-parse.
    noInterrupts();
    iScale  = syncStruct.iScale;
    // Screen is mirrored, this 'de-mirrors' the eye X direction
    scleraX = SCLERA_WIDTH - 1 - SCREEN_WIDTH - syncStruct.scleraX;
    scleraY = syncStruct.scleraY;
    uT      = syncStruct.uT;
    lT      = syncStruct.lT;
    interrupts();
  } else {
    // Stuff arguments into syncStruct and send to receiver
    syncStruct.iScale  = iScale;
    syncStruct.scleraX = scleraX;
    syncStruct.scleraY = scleraY;
    syncStruct.uT      = uT;
    syncStruct.lT      = lT;
    Wire.beginTransmission(SYNCADDR);
    Wire.write((char *)&syncStruct, sizeof syncStruct);
    Wire.endTransmission();
  }
#endif

  uint8_t  irisThreshold = (128 * (1023 - iScale) + 512) / 1024;
  uint32_t irisScale     = IRIS_MAP_HEIGHT * 65536 / irisThreshold;

  // Set up raw pixel dump to entire screen.  Although such writes can wrap
  // around automatically from end of rect back to beginning, the region is
  // reset on each frame here in case of an SPI glitch.
  TFT_SPI.beginTransaction(settings);
  digitalWrite(eyeInfo[e].select, LOW);                        // Chip select
#if defined(_ADAFRUIT_ST7735) || defined(_ADAFRUIT_ST77XXH_) // TFT
  eye[e].display->setAddrWindow(0, 0, 128, 128);
#else // OLED
  eye[e].display->writeCommand(SSD1351_CMD_SETROW);    // Y range
  eye[e].display->spiWrite(0); eye[e].display->spiWrite(SCREEN_HEIGHT - 1);
  eye[e].display->writeCommand(SSD1351_CMD_SETCOLUMN); // X range
  eye[e].display->spiWrite(0); eye[e].display->spiWrite(SCREEN_WIDTH  - 1);
  eye[e].display->writeCommand(SSD1351_CMD_WRITERAM);  // Begin write
#endif
  digitalWrite(eyeInfo[e].select, LOW);                // Re-chip-select
  digitalWrite(DISPLAY_DC, HIGH);                      // Data mode
  // Now just issue raw 16-bit values for every pixel...

  scleraXsave = scleraX; // Save initial X value to reset on each line
  irisY       = scleraY - (SCLERA_HEIGHT - IRIS_HEIGHT) / 2;
  for(screenY=0; screenY<SCREEN_HEIGHT; screenY++, scleraY++, irisY++) {
#ifdef ARDUINO_ARCH_SAMD
    uint16_t *ptr = &dmaBuf[dmaIdx][0];
#endif
    scleraX = scleraXsave;
    irisX   = scleraXsave - (SCLERA_WIDTH - IRIS_WIDTH) / 2;
    for(screenX=0; screenX<SCREEN_WIDTH; screenX++, scleraX++, irisX++) {
      if((lower[screenY][screenX] <= lT) ||
         (upper[screenY][screenX] <= uT)) {             // Covered by eyelid
        p = 0;
      } else if((irisY < 0) || (irisY >= IRIS_HEIGHT) ||
                (irisX < 0) || (irisX >= IRIS_WIDTH)) { // In sclera
        p = sclera[scleraY][scleraX];
      } else {                                          // Maybe iris...
        p = polar[irisY][irisX];                        // Polar angle/dist
        d = p & 0x7F;                                   // Distance from edge (0-127)
        if(d < irisThreshold) {                         // Within scaled iris area
          d = d * irisScale / 65536;                    // d scaled to iris image height
          a = (IRIS_MAP_WIDTH * (p >> 7)) / 512;        // Angle (X)
          p = iris[d][a];                               // Pixel = iris
        } else {                                        // Not in iris
          p = sclera[scleraY][scleraX];                 // Pixel = sclera
        }
      }
#ifdef ARDUINO_ARCH_SAMD
      *ptr++ = __builtin_bswap16(p); // DMA: store in scanline buffer
#else
      // SPI FIFO technique from Paul Stoffregen's ILI9341_t3 library:
      while(KINETISK_SPI0.SR & 0xC000); // Wait for space in FIFO
      KINETISK_SPI0.PUSHR = p | SPI_PUSHR_CTAS(1) | SPI_PUSHR_CONT;
#endif
    } // end column
#ifdef ARDUINO_ARCH_SAMD
    while(dma_busy); // Wait for prior DMA xfer to finish
    descriptor->SRCADDR.reg = (uint32_t)&dmaBuf[dmaIdx] + sizeof dmaBuf[0];
    dma_busy = true;
    dmaIdx   = 1 - dmaIdx;
    dma.startJob();
#endif
  } // end scanline

#ifdef ARDUINO_ARCH_SAMD
  while(dma_busy);  // Wait for last scanline to transmit
#else
  KINETISK_SPI0.SR |= SPI_SR_TCF;         // Clear transfer flag
  while((KINETISK_SPI0.SR & 0xF000) ||    // Wait for SPI FIFO to drain
       !(KINETISK_SPI0.SR & SPI_SR_TCF)); // Wait for last bit out
#endif

  digitalWrite(eyeInfo[e].select, HIGH);          // Deselect
  TFT_SPI.endTransaction();
}

// EYE ANIMATION -----------------------------------------------------------

const uint8_t ease[] = { // Ease in/out curve for eye movements 3*t^2-2*t^3
    0,  0,  0,  0,  0,  0,  0,  1,  1,  1,  1,  1,  2,  2,  2,  3,   // T
    3,  3,  4,  4,  4,  5,  5,  6,  6,  7,  7,  8,  9,  9, 10, 10,   // h
   11, 12, 12, 13, 14, 15, 15, 16, 17, 18, 18, 19, 20, 21, 22, 23,   // x
   24, 25, 26, 27, 27, 28, 29, 30, 31, 33, 34, 35, 36, 37, 38, 39,   // 2
   40, 41, 42, 44, 45, 46, 47, 48, 50, 51, 52, 53, 54, 56, 57, 58,   // A
   60, 61, 62, 63, 65, 66, 67, 69, 70, 72, 73, 74, 76, 77, 78, 80,   // l
   81, 83, 84, 85, 87, 88, 90, 91, 93, 94, 96, 97, 98,100,101,103,   // e
  104,106,107,109,110,112,113,115,116,118,119,121,122,124,125,127,   // c
  128,130,131,133,134,136,137,139,140,142,143,145,146,148,149,151,   // J
  152,154,155,157,158,159,161,162,164,165,167,168,170,171,172,174,   // a
  175,177,178,179,181,182,183,185,186,188,189,190,192,193,194,195,   // c
  197,198,199,201,202,203,204,205,207,208,209,210,211,213,214,215,   // o
  216,217,218,219,220,221,222,224,225,226,227,228,228,229,230,231,   // b
  232,233,234,235,236,237,237,238,239,240,240,241,242,243,243,244,   // s
  245,245,246,246,247,248,248,249,249,250,250,251,251,251,252,252,   // o
  252,253,253,253,254,254,254,254,254,255,255,255,255,255,255,255 }; // n

#ifdef AUTOBLINK
uint32_t timeOfLastBlink = 0L, timeToNextBlink = 0L;
#endif

void frame( // Process motion for a single frame of left or right eye
  uint16_t        iScale) {     // Iris scale (0-1023) passed in
  static uint32_t frames   = 0; // Used in frame rate calculation
  static uint8_t  eyeIndex = 0; // eye[] array counter
  int16_t         eyeX, eyeY;
  uint32_t        t = micros(); // Time at start of function

  if(!(++frames & 255)) { // Every 256 frames...
    uint32_t elapsed = (millis() - startTime) / 1000;
    if(elapsed) Serial.println(frames / elapsed); // Print FPS
  }

  if(++eyeIndex >= NUM_EYES) eyeIndex = 0; // Cycle through eyes, 1 per call

  // X/Y movement

#if defined(JOYSTICK_X_PIN) && (JOYSTICK_X_PIN >= 0) && \
    defined(JOYSTICK_Y_PIN) && (JOYSTICK_Y_PIN >= 0)

  // Read X/Y from joystick, constrain to circle
  int16_t dx, dy;
  int32_t d;
  eyeX = analogRead(JOYSTICK_X_PIN); // Raw (unclipped) X/Y reading
  eyeY = analogRead(JOYSTICK_Y_PIN);
#ifdef JOYSTICK_X_FLIP
  eyeX = 1023 - eyeX;
#endif
#ifdef JOYSTICK_Y_FLIP
  eyeY = 1023 - eyeY;
#endif
  dx = (eyeX * 2) - 1023; // A/D exact center is at 511.5.  Scale coords
  dy = (eyeY * 2) - 1023; // X2 so range is -1023 to +1023 w/center at 0.
  if((d = (dx * dx + dy * dy)) > (1023 * 1023)) { // Outside circle
    d    = (int32_t)sqrt((float)d);               // Distance from center
    eyeX = ((dx * 1023 / d) + 1023) / 2;          // Clip to circle edge,
    eyeY = ((dy * 1023 / d) + 1023) / 2;          // scale back to 0-1023
  }

#else // Autonomous X/Y eye motion
      // Periodically initiates motion to a new random point, random speed,
      // holds there for random period until next motion.

  static boolean  eyeInMotion      = false;
  static int16_t  eyeOldX=512, eyeOldY=512, eyeNewX=512, eyeNewY=512;
  static uint32_t eyeMoveStartTime = 0L;
  static int32_t  eyeMoveDuration  = 0L;

  int32_t dt = t - eyeMoveStartTime;      // uS elapsed since last eye event
  if(eyeInMotion) {                       // Currently moving?
    if(dt >= eyeMoveDuration) {           // Time up?  Destination reached.
      eyeInMotion      = false;           // Stop moving
      eyeMoveDuration  = random(3000000); // 0-3 sec stop
      eyeMoveStartTime = t;               // Save initial time of stop
      eyeX = eyeOldX = eyeNewX;           // Save position
      eyeY = eyeOldY = eyeNewY;
    } else { // Move time's not yet fully elapsed -- interpolate position
      int16_t e = ease[255 * dt / eyeMoveDuration] + 1;   // Ease curve
      eyeX = eyeOldX + (((eyeNewX - eyeOldX) * e) / 256); // Interp X
      eyeY = eyeOldY + (((eyeNewY - eyeOldY) * e) / 256); // and Y
    }
  } else {                                // Eye stopped
    eyeX = eyeOldX;
    eyeY = eyeOldY;
    if(dt > eyeMoveDuration) {            // Time up?  Begin new move.
      int16_t  dx, dy;
      uint32_t d;
      do {                                // Pick new dest in circle
        eyeNewX = random(1024);
        eyeNewY = random(1024);
        dx      = (eyeNewX * 2) - 1023;
        dy      = (eyeNewY * 2) - 1023;
      } while((d = (dx * dx + dy * dy)) > (1023 * 1023)); // Keep trying
      eyeMoveDuration  = random(72000, 144000); // ~1/14 - ~1/7 sec
      eyeMoveStartTime = t;               // Save initial time of move
      eyeInMotion      = true;            // Start move on next frame
    }
  }

#endif // JOYSTICK_X_PIN etc.

  // Blinking

#ifdef AUTOBLINK
  // Similar to the autonomous eye movement above -- blink start times
  // and durations are random (within ranges).
  if((t - timeOfLastBlink) >= timeToNextBlink) { // Start new blink?
    timeOfLastBlink = t;
    uint32_t blinkDuration = random(36000, 72000); // ~1/28 - ~1/14 sec
    // Set up durations for both eyes (if not already winking)
    for(uint8_t e=0; e<NUM_EYES; e++) {
      if(eye[e].blink.state == NOBLINK) {
        eye[e].blink.state     = ENBLINK;
        eye[e].blink.startTime = t;
        eye[e].blink.duration  = blinkDuration;
      }
    }
    timeToNextBlink = blinkDuration * 3 + random(4000000);
  }
#endif

  if(eye[eyeIndex].blink.state) { // Eye currently blinking?
    // Check if current blink state time has elapsed
    if((t - eye[eyeIndex].blink.startTime) >= eye[eyeIndex].blink.duration) {
      // Yes -- increment blink state, unless...
      if((eye[eyeIndex].blink.state == ENBLINK) && ( // Enblinking and...
#if defined(BLINK_PIN) && (BLINK_PIN >= 0)
        (digitalRead(BLINK_PIN) == LOW) ||           // blink or wink held...
#endif
        ((eyeInfo[eyeIndex].wink >= 0) &&
         digitalRead(eyeInfo[eyeIndex].wink) == LOW) )) {
        // Don't advance state yet -- eye is held closed instead
      } else { // No buttons, or other state...
        if(++eye[eyeIndex].blink.state > DEBLINK) { // Deblinking finished?
          eye[eyeIndex].blink.state = NOBLINK;      // No longer blinking
        } else { // Advancing from ENBLINK to DEBLINK mode
          eye[eyeIndex].blink.duration *= 2; // DEBLINK is 1/2 ENBLINK speed
          eye[eyeIndex].blink.startTime = t;
        }
      }
    }
  } else { // Not currently blinking...check buttons!
#if defined(BLINK_PIN) && (BLINK_PIN >= 0)
    if(digitalRead(BLINK_PIN) == LOW) {
      // Manually-initiated blinks have random durations like auto-blink
      uint32_t blinkDuration = random(36000, 72000);
      for(uint8_t e=0; e<NUM_EYES; e++) {
        if(eye[e].blink.state == NOBLINK) {
          eye[e].blink.state     = ENBLINK;
          eye[e].blink.startTime = t;
          eye[e].blink.duration  = blinkDuration;
        }
      }
    } else
#endif
    if((eyeInfo[eyeIndex].wink >= 0) &&
       (digitalRead(eyeInfo[eyeIndex].wink) == LOW)) { // Wink!
      eye[eyeIndex].blink.state     = ENBLINK;
      eye[eyeIndex].blink.startTime = t;
      eye[eyeIndex].blink.duration  = random(45000, 90000);
    }
  }

  // Process motion, blinking and iris scale into renderable values

  // Scale eye X/Y positions (0-1023) to pixel units used by drawEye()
  eyeX = map(eyeX, 0, 1023, 0, SCLERA_WIDTH  - 128);
  eyeY = map(eyeY, 0, 1023, 0, SCLERA_HEIGHT - 128);
  if(eyeIndex == 1) eyeX = (SCLERA_WIDTH - 128) - eyeX; // Mirrored display

  // Horizontal position is offset so that eyes are very slightly crossed
  // to appear fixated (converged) at a conversational distance.  Number
  // here was extracted from my posterior and not mathematically based.
  // I suppose one could get all clever with a range sensor, but for now...
  if(NUM_EYES > 1) eyeX += 4;
  if(eyeX > (SCLERA_WIDTH - 128)) eyeX = (SCLERA_WIDTH - 128);

  // Eyelids are rendered using a brightness threshold image.  This same
  // map can be used to simplify another problem: making the upper eyelid
  // track the pupil (eyes tend to open only as much as needed -- e.g. look
  // down and the upper eyelid drops).  Just sample a point in the upper
  // lid map slightly above the pupil to determine the rendering threshold.
  static uint8_t uThreshold = 128;
  uint8_t        lThreshold, n;
#ifdef TRACKING
  int16_t sampleX = SCLERA_WIDTH  / 2 - (eyeX / 2), // Reduce X influence
          sampleY = SCLERA_HEIGHT / 2 - (eyeY + IRIS_HEIGHT / 4);
  // Eyelid is slightly asymmetrical, so two readings are taken, averaged
  if(sampleY < 0) n = 0;
  else            n = (upper[sampleY][sampleX] +
                       upper[sampleY][SCREEN_WIDTH - 1 - sampleX]) / 2;
  uThreshold = (uThreshold * 3 + n) / 4; // Filter/soften motion
  // Lower eyelid doesn't track the same way, but seems to be pulled upward
  // by tension from the upper lid.
  lThreshold = 254 - uThreshold;
#else // No tracking -- eyelids full open unless blink modifies them
  uThreshold = lThreshold = 0;
#endif

  // The upper/lower thresholds are then scaled relative to the current
  // blink position so that blinks work together with pupil tracking.
  if(eye[eyeIndex].blink.state) { // Eye currently blinking?
    uint32_t s = (t - eye[eyeIndex].blink.startTime);
    if(s >= eye[eyeIndex].blink.duration) s = 255;   // At or past blink end
    else s = 255 * s / eye[eyeIndex].blink.duration; // Mid-blink
    s          = (eye[eyeIndex].blink.state == DEBLINK) ? 1 + s : 256 - s;
    n          = (uThreshold * s + 254 * (257 - s)) / 256;
    lThreshold = (lThreshold * s + 254 * (257 - s)) / 256;
  } else {
    n          = uThreshold;
  }

  // Pass all the derived values to the eye-rendering function:
  drawEye(eyeIndex, iScale, eyeX, eyeY, n, lThreshold);
}

// AUTONOMOUS IRIS SCALING (if no photocell or dial) -----------------------

#if !defined(LIGHT_PIN) || (LIGHT_PIN < 0)

// Autonomous iris motion uses a fractal behavior to similate both the major
// reaction of the eye plus the continuous smaller adjustments that occur.

uint16_t oldIris = (IRIS_MIN + IRIS_MAX) / 2, newIris;

void split( // Subdivides motion path into two sub-paths w/randimization
  int16_t  startValue, // Iris scale value (IRIS_MIN to IRIS_MAX) at start
  int16_t  endValue,   // Iris scale value at end
  uint32_t startTime,  // micros() at start
  int32_t  duration,   // Start-to-end time, in microseconds
  int16_t  range) {    // Allowable scale value variance when subdividing

  if(range >= 8) {     // Limit subdvision count, because recursion
    range    /= 2;     // Split range & time in half for subdivision,
    duration /= 2;     // then pick random center point within range:
    int16_t  midValue = (startValue + endValue - range) / 2 + random(range);
    uint32_t midTime  = startTime + duration;
    split(startValue, midValue, startTime, duration, range); // First half
    split(midValue  , endValue, midTime  , duration, range); // Second half
  } else {             // No more subdivisons, do iris motion...
    int32_t dt;        // Time (micros) since start of motion
    int16_t v;         // Interim value
    while((dt = (micros() - startTime)) < duration) {
      v = startValue + (((endValue - startValue) * dt) / duration);
      if(v < IRIS_MIN)      v = IRIS_MIN; // Clip just in case
      else if(v > IRIS_MAX) v = IRIS_MAX;
      frame(v);        // Draw frame w/interim iris scale value
    }
  }
}

#endif // !LIGHT_PIN

// MAIN LOOP -- runs continuously after setup() ----------------------------

void loop() {

#if defined(LIGHT_PIN) && (LIGHT_PIN >= 0) // Interactive iris

  int16_t v = analogRead(LIGHT_PIN);       // Raw dial/photocell reading
#ifdef LIGHT_PIN_FLIP
  v = 1023 - v;                            // Reverse reading from sensor
#endif
  if(v < LIGHT_MIN)      v = LIGHT_MIN;  // Clamp light sensor range
  else if(v > LIGHT_MAX) v = LIGHT_MAX;
  v -= LIGHT_MIN;  // 0 to (LIGHT_MAX - LIGHT_MIN)
#ifdef LIGHT_CURVE  // Apply gamma curve to sensor input?
  v = (int16_t)(pow((double)v / (double)(LIGHT_MAX - LIGHT_MIN),
    LIGHT_CURVE) * (double)(LIGHT_MAX - LIGHT_MIN));
#endif
  // And scale to iris range (IRIS_MAX is size at LIGHT_MIN)
  v = map(v, 0, (LIGHT_MAX - LIGHT_MIN), IRIS_MAX, IRIS_MIN);
#ifdef IRIS_SMOOTH // Filter input (gradual motion)
  static int16_t irisValue = (IRIS_MIN + IRIS_MAX) / 2;
  irisValue = ((irisValue * 15) + v) / 16;
  frame(irisValue);
#else // Unfiltered (immediate motion)
  frame(v);
#endif // IRIS_SMOOTH

#else  // Autonomous iris scaling -- invoke recursive function

  newIris = random(IRIS_MIN, IRIS_MAX);
  split(oldIris, newIris, micros(), 10000000L, IRIS_MAX - IRIS_MIN);
  oldIris = newIris;

#endif // LIGHT_PIN
}


Either I am missing something or it really doesn't like it and choking atm. It seems like it's just the TFT_SPI and not sure which library (if any) is causing it. Everything is up to date and nothing has changed on my end.

frostfyre
 
Posts: 4
Joined: Tue Apr 23, 2019 6:29 pm

Re: uncanny eyes with Teensy 3.1

by pburgess on Tue Apr 23, 2019 10:56 pm

In your config.h file, are you #including more than one of the eye .h files?

Try compiling the plain unmodified original uncannyEyes.ino sketch, see if any difference. The code you pasted has some changes from the original.

pburgess
 
Posts: 4020
Joined: Sun Oct 26, 2008 2:29 am

Re: uncanny eyes with Teensy 3.1

by frostfyre on Tue Apr 23, 2019 11:05 pm

pburgess wrote:In your config.h file, are you #including more than one of the eye .h files?

Try compiling the plain unmodified original uncannyEyes.ino sketch, see if any difference. The code you pasted has some changes from the original.


Nope, just the one "graphics/noScleraEye.h" file in the config.h.
For measure, I redownloaded and added the code again, and it is still giving me the same error regarding the "TFT_SPI was not declared in this scope".

EDIT: I managed to get it to compile and load, but no eyes on the screens. So far, it's just a blank, white display.

EDITEDIT: Got em!

frostfyre
 
Posts: 4
Joined: Tue Apr 23, 2019 6:29 pm

Please be positive and constructive with your questions and comments.