# This is a quick python program to get and save the first few frames
# of raw data from the Seek Thermal camera.
# copy & paste this code into a file xxxx.py
# run the code like this "python xxxx.py 42"
# 42 being the number of frames to capture.
import usb.core
import usb.util
import sys
import Image
y = int(sys.argv[1])
# find our Seek Thermal device 289d:0010
dev = usb.core.find(idVendor=0x289d, idProduct=0x0010)
# was it found?
if dev is None:
raise ValueError('Device not found')
# set the active configuration. With no arguments, the first
# configuration will be the active one
dev.set_configuration()
# get an endpoint instance
cfg = dev.get_active_configuration()
intf = cfg[(0,0)]
ep = usb.util.find_descriptor(
intf,
# match the first OUT endpoint
custom_match = \
lambda e: \
usb.util.endpoint_direction(e.bEndpointAddress) == \
usb.util.ENDPOINT_OUT)
assert ep is not None
#msg = '\x41\x41'
#print (msg)
# Deinit the device
msg= '\x00\x00'
assert dev.ctrl_transfer(0x41, 0x3C, 0, 0, msg) == len(msg)
assert dev.ctrl_transfer(0x41, 0x3C, 0, 0, msg) == len(msg)
assert dev.ctrl_transfer(0x41, 0x3C, 0, 0, msg) == len(msg)
# Setup device
#msg = x01
assert dev.ctrl_transfer(0x41, 0x54, 0, 0, 0x01)
#
msg = '\x00\x00'
assert dev.ctrl_transfer(0x41, 0x3C, 0, 0, msg) == len(msg)
ret1 = dev.ctrl_transfer(0xC1, 0x4E, 0, 0, 4)
ret2 = dev.ctrl_transfer(0xC1, 0x36, 0, 0, 12)
#print ret1
#print ret2
#
msg = '\x20\x00\x30\x00\x00\x00'
assert dev.ctrl_transfer(0x41, 0x56, 0, 0, msg) == len(msg)
ret3 = dev.ctrl_transfer(0xC1, 0x58, 0, 0, 0x40)
#print ret3
#
msg = '\x20\x00\x50\x00\x00\x00'
assert dev.ctrl_transfer(0x41, 0x56, 0, 0, msg) == len(msg)
ret4 = dev.ctrl_transfer(0xC1, 0x58, 0, 0, 0x40)
#print ret4
#
msg = '\x0C\x00\x70\x00\x00\x00'
assert dev.ctrl_transfer(0x41, 0x56, 0, 0, msg) == len(msg)
ret5 = dev.ctrl_transfer(0xC1, 0x58, 0, 0, 0x18)
#print ret5
#
msg = '\x06\x00\x08\x00\x00\x00'
assert dev.ctrl_transfer(0x41, 0x56, 0, 0, msg) == len(msg)
ret6 = dev.ctrl_transfer(0xC1, 0x58, 0, 0, 0x0C)
#print ret6
#
msg = '\x08\x00'
assert dev.ctrl_transfer(0x41, 0x3E, 0, 0, msg) == len(msg)
ret7 = dev.ctrl_transfer(0xC1, 0x3D, 0, 0, 2)
#print ret7
#
msg = '\x08\x00'
assert dev.ctrl_transfer(0x41, 0x3E, 0, 0, msg) == len(msg)
msg = '\x01\x00'
assert dev.ctrl_transfer(0x41, 0x3C, 0, 0, msg) == len(msg)
ret8 = dev.ctrl_transfer(0xC1, 0x3D, 0, 0, 2)
#print ret8
# Get and save the first 11 frames as 16bit .png files
# The file name is rawDataXX_YY.png where xx is the frame # and YY is the frame ID
# except for frame # 2 where the data in pixil 10 is not the frame # but part of the
# gradient
x = 0
while x < y:
msg = '\xC0\x7E\x00\x00'
assert dev.ctrl_transfer(0x41, 0x53, 0, 0, msg) == len(msg)
ret9 = dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
status = ret9[20]
img = Image.fromstring("I", (208,156), ret9, "raw", "I;16")
x = x + 1
img.save('rawData%d'%(x,)+'_%d'%(status,)+'.png')
# img.show()
print 'Done'
2) Use the following Python code to capture as many raw frames as you choose.Code: [Select]...
msg = '\xC0\x7E\x00\x00'
assert dev.ctrl_transfer(0x41, 0x53, 0, 0, msg) == len(msg)
ret9 = dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
ret9 += dev.read(0x81, 0x3F60, 1000)
status = ret9[20]
img = Image.fromstring("I", (208,156), ret9, "raw", "I;16")
...
Look at frames 1,3,4,5. they all look like cal frames except with the max data at different points. I think it is worth looking at them further, maybe they are factory cal data for that specific imager.
...ken...
Frame 9 ID 6 is the first "pre-calibration" frame, (since it occurs right before the ID 1 calibration frame (as to what is used for I'm clueless)
0x1: 001
0x6: 110
0x3: 011
Ok, there is no clear bit connections with similar histogram frames 0x1 and 0x6, so maybe this is some kind of frame id, but who knows I see min values or 0 for all these frames, but since they include the "patent pixels" and maybe some dead pixels, that is understandable. I will look at removing the zero values to see if that casts any light on the range of these frames.
I know they are 8bits it was more for visual inspection...
My approach will be to take one capture of painted aluminium plate at 0*C and also one at 100*C.
The alu plate will cover the entire view of sensor.
How on earth did Mu get approval on their POS ? Maybe they didn't ?
New Post on Seek's Facebook page:
Scott Maggio Why are you still accepting Apple orders if you a "few weeks away" from knowing if you will even be approved?
"There have been reports from users about thermal gradient problems with the images in the app. This means that the temperature can vary across a uniform surface, which results in color differences. Some variation is expected in the camera, but we are also working on an app update that will further minimize the effect. That updated version is in testing right now and we hope to have it posted by the end of the month."
00007298 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_getLibraryVersion>:
00007318 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_requestShutterOperation>:
00007360 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_CheckGainTable>:
0000737c <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ColorizeInit>:
000073a0 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ColorizeProcess>:
00007480 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ColorizeDeInit>:
00007488 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_applyThermographyLut>:
00007800 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_applyLUT>:
00007948 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_TemperatureInit>:
000079d4 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_Temperature>:
000079f4 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_TemperatureDeInit>:
000079fc <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ImageProcessInit>:
00007a14 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ImageProcessDeInit>:
00007a18 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ImageProcessProcess>:
00007abc <Java_com_tyriansystems_Seekware_SeekwareNativeLib_BclaheInit>:
00007ae4 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_BclaheProcess>:
00007b46 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_BclaheDeInit>:
00007b4a <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ThermographyInit>:
00007b5e <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ThermographyDeInit>:
00007b62 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_ThermographyCalculate>:
00007c4e <Java_com_tyriansystems_Seekware_SeekwareNativeLib_Golomb>:
00007d4c <Java_com_tyriansystems_Seekware_SeekwareNativeLib_RGBAToYUV420SemiPlanar>:
00007e26 <Java_com_tyriansystems_Seekware_SeekwareNativeLib_WriteBits>:
Decompiled, SEEK thermal app.
JAR files are fundamental archive files, built on the ZIP file format and have the .jar file extension.
my images names are of the form rawdataXX_YY.png where XX is the frame sequence # and YY is the Frame ID from Pixel 10.
-rw-rw-r-- 1 501 501 2593 2014-11-23 15:10 /opt/imagej2/Fiji.app/luts/iron256_by_eneuro.lut