Changeset - 0aad247a1168
[Not reviewed]
default
0 2 0
Drew Perttula - 8 years ago 2017-05-22 04:46:41
drewp@bigasterisk.com
refactor and fix captureDevice
Ignore-this: 6698fdc1670318d0e8eb9e3e5aa9d5cf
2 files changed with 59 insertions and 49 deletions:
0 comments (0 inline, 0 general)
bin/captureDevice
Show inline comments
 
#!bin/python
 
from __future__ import division
 
from rdflib import URIRef, Literal
 
from rdflib import URIRef
 
from twisted.internet import reactor
 
from twisted.internet.defer import inlineCallbacks, Deferred
 

	
 
import logging
 
import optparse
 
import os
 
import time
 
import traceback
 
import treq
 
import cyclone.web, cyclone.websocket, cyclone.httpclient
 
from greplin import scales
 

	
 
from run_local import log
 
from lib.cycloneerr import PrettyErrorHandler
 
@@ -23,26 +22,21 @@ from light9.paint.capture import writeCa
 
from light9.greplin_cyclone import StatsForCyclone
 
from light9.effect.settings import DeviceSettings
 
from light9.effect.sequencer import sendToCollector
 

	
 
stats = scales.collection('/webServer', scales.PmfStat('setAttr'))
 

	
 
class Attrs(PrettyErrorHandler, cyclone.web.RequestHandler):
 
    def put(self):
 
        with stats.setAttr.time():
 
            client, clientSession, settings, sendTime = parseJsonMessage(self.request.body)
 
            self.set_status(202)
 

	
 

	
 
class Camera(object):
 
    def __init__(self, imageUrl):
 
        self.imageUrl = imageUrl
 
    
 
    def takePic(self, uri, writePath):
 
        log.info('takePic %s', uri)
 
        return treq.get(self.imageUrl).addCallbacks(lambda r: self._done(writePath, r), log.error)
 
        return treq.get(self.imageUrl).addCallbacks(lambda r: self._done(writePath, r),
 
                                                    log.error)
 
        
 
    @inlineCallbacks
 
    def _done(self, writePath, response):
 
        jpg = yield response.content()
 
        try:
 
            os.makedirs(os.path.dirname(writePath))
 
@@ -50,71 +44,87 @@ class Camera(object):
 
            pass
 
        with open(writePath, 'w') as out:
 
            out.write(jpg)
 
        log.info('wrote %s', writePath)
 

	
 

	
 

	
 
settleTime = .5
 

	
 
camera = Camera('http://dash:8200/picamserve/pic?res=480&resize=480&rotation=180&iso=800&redgain=1.6&bluegain=2&shutter=60000')
 
class Capture(object):
 
    settleTime = .5
 
    def __init__(self, graph):
 
        self.graph = graph
 
        
 
        def steps(a, b, n):
 
            return [round(a + (b - a) * i / n, 5) for i in range(n)]
 

	
 
def launch(graph):
 

	
 
    def steps(a, b, n):
 
        return [round(a + (b - a) * i / n, 5) for i in range(n)]
 

	
 
    startTime = time.time()
 
    toGather = []
 
        startTime = time.time()
 
        self.captureId = 'cap%s' % (int(startTime) - 1495170000)
 
        self.toGather = []
 

	
 
    row = 0
 
    for ry in steps(0.85, .92, 6):
 
        xSteps = steps(.24, .45, 12)
 
        if row % 2:
 
            xSteps.reverse()
 
        row += 1
 
        for rx in xSteps:
 
            toGather.append(DeviceSettings(graph, [
 
                (L9['device/moving1'], L9['rx'], rx),
 
                (L9['device/moving1'], L9['ry'], ry),
 
            ]))
 
        row = 0
 
        for ry in steps(0.85, .92, 6):
 
            xSteps = steps(.24, .45, 12)
 
            if row % 2:
 
                xSteps.reverse()
 
            row += 1
 
            for rx in xSteps:
 
                self.toGather.append(DeviceSettings(graph, [
 
                    (L9['device/moving1'], L9['rx'], rx),
 
                    (L9['device/moving1'], L9['ry'], ry),
 
                ]))
 

	
 
    numPics = [0]
 
    settingsCache = set()
 
        self.numPics = 0
 
        self.settingsCache = set()
 
        self.step().addErrback(log.error)
 
        
 
    @inlineCallbacks
 
    def step():
 
        if not toGather:
 
    def step(self):
 
        if not self.toGather:
 
            reactor.stop()
 
            return
 
        settings = toGather.pop()
 
        settings = self.toGather.pop()
 
        
 
        log.info('move to %r', settings)
 
        yield sendToCollector(client='captureDevice', session='main', settings=settings)
 
        
 
        d = Deferred()
 
        reactor.callLater(settleTime, d.callback, None)
 
        reactor.callLater(self.settleTime, d.callback, None)
 
        yield d
 
        dev = settings.devices()[0]
 

	
 
        devTail = dev.rsplit('/')[-1]
 
        captureId = 'cap%s' % (int(startTime) - 1495170000)
 
        picId = 'pic%s' % numPics[0]
 
        path = '/'.join(['capture', devTail, captureId, picId])
 
        ctx = URIRef('/'.join([showconfig.showUri(), 'capture', devTail, captureId, 'index']))
 
        uri = URIRef('/'.join([showconfig.showUri(), 'capture', devTail, captureId, picId]))
 
        
 
        picId = 'pic%s' % self.numPics
 
        path = '/'.join(['capture', devTail, self.captureId, picId])
 
        ctx = URIRef('/'.join([showconfig.showUri(), 'capture', devTail, self.captureId,
 
                               'index']))
 
        uri = URIRef('/'.join([showconfig.showUri(), 'capture', devTail, self.captureId,
 
                               picId]))
 
                     
 
        relOutPath = path + '.jpg'
 
        
 
        yield camera.takePic(uri, os.path.join(showconfig.root(), relOutPath))
 
        numPics[0] += 1
 
        self.numPics += 1
 

	
 
        writeCaptureDescription(graph, ctx, uri, dev, relOutPath, settingsCache, settings)
 
        writeCaptureDescription(self.graph, ctx, uri, dev, relOutPath,
 
                                self.settingsCache, settings)
 
        
 
        reactor.callLater(0, self.step)
 

	
 
        
 
        reactor.callLater(0, step)
 
    step().addErrback(log.error)
 
    
 

	
 
camera = Camera('http://dash:8200/picamserve/pic?res=480&resize=480&rotation=180&iso=800&redgain=1.6&bluegain=2&shutter=60000')
 

	
 
class Attrs(PrettyErrorHandler, cyclone.web.RequestHandler):
 
    def put(self):
 
        with stats.setAttr.time():
 
            client, clientSession, settings, sendTime = parseJsonMessage(self.request.body)
 
            self.set_status(202)
 

	
 
def launch(graph):
 

	
 
    cap = Capture(graph)
 
    reactor.listenTCP(networking.captureDevice.port,
 
                      cyclone.web.Application(handlers=[
 
                          (r'/()', cyclone.web.StaticFileHandler,
 
                           {"path" : "light9/web", "default_filename" : "captureDevice.html"}),
 
                          (r'/stats', StatsForCyclone),
 
                      ]),
light9/paint/capture.py
Show inline comments
 
import os
 
from rdflib import URIRef
 
from light9 import showconfig
 
from light9.rdfdb.patch import Patch
 
from light9.namespaces import L9
 
from light9.paint.solve import loadNumPy
 
from light9.paint.solve import loadNumpy
 

	
 
def writeCaptureDescription(graph, ctx, uri, dev, relOutPath, settingsSubgraphCache, settings):
 
    graph.patch(Patch(addQuads=settings.statements(
 
        uri, ctx=ctx,
 
        settingRoot=URIRef('/'.join([showconfig.showUri(), 'capture', dev.rsplit('/')[1]])),
 
        settingsSubgraphCache=settingsSubgraphCache)))
 
@@ -21,13 +21,13 @@ class CaptureLoader(object):
 
        
 
    def loadImage(self, pic, thumb=(100, 100)):
 
        ip = self.graph.value(pic, L9['imagePath'])
 
        if not ip.startswith(showconfig.show()):
 
            raise ValueError(repr(ip))
 
        diskPath = os.path.join(showconfig.root(), ip[len(self.show):])
 
        return loadNumPy(diskPath, thumb)
 
        return loadNumpy(diskPath, thumb)
 
        
 
    def devices(self):
 
        """devices for which we have any captured data"""
 

	
 
    def capturedSettings(self, device):
 
        """list of (pic, settings) we know for this device"""
0 comments (0 inline, 0 general)