| #!/usr/bin/env python |
| """max-osc-python.py : demonstration of a service node communicating parameters and data with Max via OSC messaging. |
| |
| Copyright (c) 2014-2017, Garth Zeglin. All rights reserved. Provided under the |
| terms of the BSD 3-clause license. |
| |
| This uses txosc and Twisted to send and receive OSC messages. |
| """ |
| |
| |
| # references: |
| # https://docs.scipy.org/doc/numpy/ |
| # https://bitbucket.org/arjan/txosc/wiki/Home |
| # https://twistedmatrix.com/trac/wiki/Documentation |
| |
| # standard Python modules |
| from __future__ importprint_function |
| importtime, argparse, random |
| |
| # NumPy system for numeric and matrix computation |
| importnumpyasnp |
| |
| # Twisted networking framework |
| importtwisted.internet.reactor |
| importtwisted.internet.task |
| importtwisted.internet.protocol |
| |
| # TxOSC OpenSoundControl library |
| importtxosc.osc |
| importtxosc.dispatch |
| importtxosc.async |
| |
| fromPILimportImage, ImageFilter, ImageChops |
| importnumpyasnp |
| importcv2 |
| importmatplotlib.pyplotasplt |
| |
| importtime |
| importos.path |
| |
| |
| ############ |
| |
| #----- Parameters ------ |
| N_image1=5 |
| N_image2=np.arange(0, N_image1, 1) # [0,1,2] num of images |
| N_image3=np.arange(0, N_image1-1, 1) # [0,1] num of diff |
| plot=1# 1: plot on, 0: plot off |
| #----------------------- |
| |
| |
| |
| #---------------------------------------------- |
| ifos.path.exists("./output2.txt"): |
| print ("output2.txt exists") |
| ifnotos.path.exists("./output2.txt"): |
| print("\n-----------------------------------") |
| print("image loading....") |
| img_pixels= [] |
| foriinN_image2: |
| str= ("%d"%i) |
| print("alos_"+str+".jpg") |
| img=Image.open("alos_"+str+".jpg") |
| |
| grey_img=img.convert('L') |
| width, height=grey_img.size |
| print ("width, height =", width, height) |
| img_pixels.append(np.array([[grey_img.getpixel((j,m)) forjinrange(width)] forminrange(height)])) |
| #plt.imshow(img_pixels[i]) |
| #plt.show() |
| |
| foriinN_image2: |
| print("---img", i) |
| print(img_pixels[i]) |
| |
| |
| |
| |
| #---------------------------------------------- |
| |
| print("\n-----------------------------------") |
| print("image subtracting....") |
| sub= [] |
| foriinN_image3: |
| sub.append(img_pixels[i+1] -img_pixels[i]) |
| |
| foriinN_image3: |
| print("---sub", i) |
| print(sub[i]) |
| |
| |
| |
| |
| #---------------------------------------------- |
| |
| print("\n-----------------------------------") |
| print("Finding out significantly changes....") |
| sub_data2= [] |
| sum= [] |
| ave= [] |
| N_pixels=height*width |
| print ("N_pixels =", N_pixels) |
| print ("width, height =", width, height) |
| foriinN_image3: |
| sub_data1= [] # initialize |
| print ("subbbbb", i) |
| sum.append(np.sum(sub[i])) |
| ave.append(np.average(sub[i])) |
| foryinrange(0,height): |
| forxinrange(0,width): |
| #print (sub[i][y][x]) |
| sub_data1.append(sub[i][y][x]) |
| #print(sub_data1) |
| sub_data2.append(sub_data1) |
| |
| |
| |
| |
| sigma= [] |
| foriinN_image3: |
| sigma2=0# initialize |
| forninrange(0,N_pixels): |
| sigma2+=np.power(sub_data2[i][n]-ave[i], 2) |
| sigma.append(np.power(sigma2/N_pixels, 0.5)) |
| |
| foriinN_image3: |
| print ("---sub", i) |
| print ("sum =", sum[i]) |
| print ("ave =", ave[i]) |
| print ("sigma = %.5e"%sigma[i]) |
| #print (sub_data2[i]) |
| |
| |
| |
| # brighter (red) |
| x_b2, y_b2, sub_b2= [], [], [] |
| sound_b2, count_b2= [], [] |
| max_x_b2, max_y_b2= [], [] |
| foriinN_image3: |
| x_b1= [] #initialize |
| y_b1= [] #initialize |
| sub_b1= [] #initialize |
| sound_b1=0#initialize |
| count_b1=0#initialize |
| maxim=0 |
| max_x_b1=0 |
| max_y_b1=0 |
| foryinrange(0,height): |
| forxinrange(0,width): |
| if (sub[i][y][x] >=ave[i] +3*sigma[i]): |
| ifsub[i][y][x] >=maxim: |
| maxim=sub[i][y][x] |
| max_x_b1=x |
| max_y_b1=y |
| x_b1.append(x) |
| y_b1.append(y) |
| sub_b1.append(sub[i][y][x]) |
| sound_b1+=sub[i][y][x] |
| count_b1+=1 |
| x_b2.append(x_b1) |
| y_b2.append(y_b1) |
| sub_b2.append(sub_b1) |
| sound_b2.append(sound_b1) |
| count_b2.append(count_b1) |
| max_x_b2.append(max_x_b1) |
| max_y_b2.append(max_y_b1) |
| |
| |
| #print (max(sub_b2)) |
| |
| # darker (blue) |
| x_d2, y_d2, sub_d2= [], [], [] |
| sound_d2, count_d2= [], [] |
| max_x_d2, max_y_d2= [], [] |
| foriinN_image3: |
| x_d1= [] #initialize |
| y_d1= [] #initialize |
| sub_d1= [] #initialize |
| sound_d1=0#initialize |
| count_d1=0#initialize |
| maxim=0 |
| foryinrange(0,height): |
| forxinrange(0,width): |
| if (sub[i][y][x] <=ave[i] -3*sigma[i]): |
| if-sub[i][y][x] >=maxim: |
| maxim=-sub[i][y][x] |
| max_x_d1=x |
| max_y_d1=y |
| x_d1.append(x) |
| y_d1.append(y) |
| sub_d1.append(sub[i][y][x]) |
| sound_d1+=-sub[i][y][x] |
| count_d1+=1 |
| x_d2.append(x_d1) |
| y_d2.append(y_d1) |
| sub_d2.append(sub_d1) |
| sound_d2.append(sound_d1) |
| count_d2.append(count_d1) |
| max_x_d2.append(max_x_d1) |
| max_y_d2.append(max_y_d1) |
| |
| |
| #---------------------------------------------- |
| |
| f1=open('output.txt', 'w') |
| |
| |
| # bright |
| print("\n-----------------------------------") |
| print("Converting to sounds (1)....") |
| delta_sound_b=max(sound_b2)-min(sound_b2)+1e-10# prevent dividing by 0 |
| print(delta_sound_b) |
| delta_count_b=max(count_b2)-min(count_b2)+1e-10 |
| delta_max_x_b=max(max_x_b2)-min(max_x_b2)+1e-10 |
| delta_max_y_b=max(max_y_b2)-min(max_y_b2)+1e-10 |
| |
| Norm_sound_b, Norm_count_b= [], [] |
| max_x_b, max_y_b= [], [] |
| foriinN_image3: |
| Norm_sound_b.append((sound_b2[i] -min(sound_b2))/delta_sound_b) |
| Norm_count_b.append((count_b2[i] -min(count_b2))/delta_count_b) |
| max_x_b.append((max_x_b2[i] -min(max_x_b2))/delta_max_x_b) |
| max_y_b.append((max_y_b2[i] -min(max_y_b2))/delta_max_y_b) |
| foriinN_image3: |
| print ("---sub", i) |
| print ("sound", sound_b2[i]) |
| print ("count", count_b2[i]) |
| print ("Normalized sound = %.2f"%Norm_sound_b[i]) |
| print ("Normalized count = %.2f"%Norm_count_b[i]) |
| |
| |
| |
| # dark |
| print("\n-----------------------------------") |
| print("Converting to sounds (2)....") |
| delta_sound_d=max(sound_d2)-min(sound_d2)+1e-10 |
| delta_count_d=max(count_d2)-min(count_d2)+1e-10 |
| delta_max_x_d=max(max_x_d2)-min(max_x_d2)+1e-10 |
| delta_max_y_d=max(max_y_d2)-min(max_y_d2)+1e-10 |
| |
| Norm_sound_d, Norm_count_d= [], [] |
| max_x_d, max_y_d= [], [] |
| foriinN_image3: |
| Norm_sound_d.append((sound_d2[i] -min(sound_d2))/delta_sound_d) |
| Norm_count_d.append((count_d2[i] -min(count_d2))/delta_count_d) |
| max_x_d.append((max_x_d2[i] -min(max_x_d2))/delta_max_x_d) |
| max_y_d.append((max_y_d2[i] -min(max_y_d2))/delta_max_y_d) |
| |
| list= [] |
| foriinN_image3: |
| print ("---sub", i) |
| print ("sound", sound_d2[i]) |
| print ("count", count_d2[i]) |
| print ("Normalized sound = %.2f"%Norm_sound_d[i]) |
| print ("Normalized count = %.2f"%Norm_count_d[i]) |
| NSB= ("%.3f"%Norm_sound_b[i]) |
| NCB= ("%.3f"%Norm_count_b[i]) |
| NSD= ("%.3f"%Norm_sound_d[i]) |
| NCD= ("%.3f"%Norm_count_d[i]) |
| #print(NSB, NCB, NSD, NCD) |
| str='%.3f %.3f %.3f %.3f %.3f %.3f %.3f %.3f\n'% (abs(Norm_sound_b[i]), abs(Norm_count_b[i]), abs(Norm_sound_d[i]), abs(Norm_count_d[i]), max_x_b[i], max_y_b[i], max_x_d[i], max_y_d[i]) |
| f1.write(str) |
| |
| f1.close() |
| |
| #----- Plotting ------- |
| ifplot==1: |
| foriinN_image3: |
| plt.imshow(sub[i]) |
| #plt.imshow(img_pixels[i]) |
| |
| CB=plt.colorbar() |
| CB.formatter.set_scientific(True) |
| CB.formatter.set_powerlimits((0,0)) |
| CB.update_ticks() |
| #CB.ax.ticklabel_format(style='sci', scilimits=(0,0)) |
| CB.set_label('color bar') |
| |
| plt.title("Difference") |
| #plt.xlabel("RA. [pixel]") |
| #plt.ylabel("DEC. [pixel]") |
| plt.plot(x_d2[i], y_d2[i], 'bo', markersize=3) |
| plt.plot(x_b2[i], y_b2[i], 'ro', markersize=3) |
| #plt.xlim([-0.5,width-0.5]) |
| plt.show() |
| #----------------------- |
| |
| # print("x_b2, y_b2") |
| # print(x_b2, y_b2) |
| # print("x_d2, y_d2") |
| # print(x_d2, y_d2) |
| ############# |
| |
| |
| #----- Plotting ------- |
| |
| |
| |
| |
| arr=np.loadtxt("output.txt", delimiter=" ", dtype="float") |
| arrT=np.array(arr.T) |
| print(arr.T) |
| np.savetxt('output2.txt', arr.T, fmt='%.3f') |
| |
| |
| |
| |
| |
| base_time=time.time() |
| |
| # The associated Max patcher assumes that the Python node sends and receives using the following UDP port numbers: |
| PYTHON_NODE_RECV_PORT=12001 |
| PYTHON_NODE_SEND_PORT=12000 |
| |
| ################################################################ |
| classOscServer(object): |
| """The OscServer class holds all the application state: communication ports, |
| message callback assignments, and dynamic parameters.""" |
| |
| def__init__(self, recv_port=PYTHON_NODE_RECV_PORT, send_port=PYTHON_NODE_SEND_PORT, verbose=False): |
| |
| self.verbose=verbose |
| self.recv_portnum=recv_port |
| self.send_portnum=send_port |
| self._reactor=None |
| self._ping_count=0 |
| |
| # set default generator parameters |
| self._reset_parameters() |
| return |
| |
| def_reset_parameters(self): |
| self._xfreq=1 |
| self._yfreq=1 |
| self._xphase=0.0 |
| self._yphase=0.0 |
| |
| deflisten( self, reactor ): |
| """The listen method is called to establish the UDP ports to receive and send OSC messages.""" |
| self._reactor=reactor |
| self.receiver=txosc.dispatch.Receiver() |
| self._server_protocol=txosc.async.DatagramServerProtocol(self.receiver) |
| self._server_port=reactor.listenUDP(self.recv_portnum, self._server_protocol, maxPacketSize=60000) |
| ifself.verbose: print( "Listening on osc.udp://localhost:%s", self.recv_portnum ) |
| |
| self._client_protocol=txosc.async.DatagramClientProtocol() |
| self._client_port=reactor.listenUDP(0, self._client_protocol, maxPacketSize=60000) |
| ifself.verbose: print( "Ready to send using %s"%self._client_port) |
| |
| # Set up the OSC message handling system. As a convention for |
| # legibility, the message callback methods have msg_ prepended to the |
| # message, but this is not required. |
| |
| # Assign methods to receive messages intended for debugging the system. |
| self.receiver.addCallback( "/reset", self.msg_reset ) |
| self.receiver.addCallback( "/quit", self.msg_quit ) |
| self.receiver.addCallback( "/ping", self.msg_ping ) |
| |
| # Assign methods to receive parameter control messages. |
| self.receiver.addCallback( "/xfreq", self.msg_xfreq) |
| self.receiver.addCallback( "/yfreq", self.msg_yfreq) |
| |
| # Assign methods to receive other event functions. |
| self.receiver.addCallback( "/nextframe", self.msg_nextframe) |
| |
| # Assign a default function to receive any other OSC message. |
| self.receiver.fallback=self.msg_fallback |
| |
| return |
| |
| #### Message handlers. ############################################ |
| |
| |
| # Define a default handler for any unmatched message address. |
| defmsg_fallback(self, message, address): |
| print("Received OSC message with unhandled address '%s' from %s: %s"% (message.address, address, message.getValues())) |
| return |
| |
| defmsg_reset( self, message, address): |
| ifself.verbose: print("Receive reset request.") |
| self._reset_parameters() |
| return |
| |
| defmsg_quit( self, message, address): |
| ifself.verbose: print( "Received quit request, shutting down." ) |
| self._reactor.stop() |
| |
| defmsg_ping( self, message, address): |
| ifself.verbose: print("Received ping request.") |
| |
| # reply to the IP address from which the message was received |
| send_host=address[0] |
| |
| self._ping_count+=1 |
| self._client_protocol.send( txosc.osc.Message("/pong", self._ping_count), (send_host, self.send_portnum)) |
| return |
| |
| defmsg_xfreq( self, message, address): |
| self._xfreq=message.getValues()[0] |
| ifself.verbose: print("xfreq now %s"%self._xfreq) |
| return |
| |
| defmsg_yfreq( self, message, address): |
| self._yfreq=message.getValues()[0] |
| ifself.verbose: print("yfreq now %s"%self._yfreq) |
| return |
| |
| defmsg_nextframe( self, message, address): |
| #----parameters---- |
| N_variance=8 |
| music_length=10#sec |
| freq=1#sec |
| #------------------ |
| |
| ifself.verbose: print("Generating next frame.") |
| |
| |
| # create a two-channel trajectory signal as a 2xN array |
| cols=N_variance |
| rows=1# output each row in order |
| trajectory=np.ndarray((rows, cols), dtype=np.float32) |
| |
| # create index array for calculating functions |
| #tt = np.linspace(0.0, 1.0, cols, dtype=np.float32) |
| |
| data_x=np.loadtxt("output2.txt", comments="#", delimiter=' ') |
| |
| # compute two sets of trajectory samples |
| |
| #print(data_x) |
| #for i in range (0,len(data_x[:,0])): |
| |
| if (time.time()-base_time) <music_length: |
| print("num of diff", N_image1-1) |
| foriinrange (0,N_image1-1): |
| print("\n---", i, "---") |
| raw= [] |
| forninrange (0,N_variance): |
| raw.append(data_x[n,i]) |
| #print (data_x[n,i]) |
| print("raw",raw) |
| trajectory[0,:] =raw |
| |
| |
| # Reformat the trajectory for sending as an OSC message. The txosc Message |
| # class doesn't recognize numpy values, so the pixel values are |
| # converted to an ordinary Python list of numbers. The transpose is |
| # used to re-order the values so each plane is sent in succession. |
| samples= [float(value) forvalueintrajectory.flat] |
| msg=txosc.osc.Message("/trajectory", cols, rows, *samples) |
| |
| # send the trajectory back to the source of the request |
| send_host=address[0] |
| self._client_protocol.send( msg, (send_host, self.send_portnum)) |
| time.sleep(freq) |
| |
| |
| print ("time passed", time.time()-base_time) |
| |
| |
| |
| return |
| """ |
| while True: |
| for i in range (0,N_image1-1): |
| raw = [] |
| for n in range (0,N_variance): |
| raw.append(data_x[n,i]) |
| print (data_x[n,i]) |
| #print("raw",raw) |
| trajectory[0,:] = raw |
| |
| |
| print("Hello") |
| |
| # Reformat the trajectory for sending as an OSC message. The txosc Message |
| # class doesn't recognize numpy values, so the pixel values are |
| # converted to an ordinary Python list of numbers. The transpose is |
| # used to re-order the values so each plane is sent in succession. |
| samples = [float(value) for value in trajectory.flat] |
| msg = txosc.osc.Message("/trajectory", cols, rows, *samples) |
| |
| # send the trajectory back to the source of the request |
| send_host = address[0] |
| self._client_protocol.send( msg, (send_host, self.send_portnum)) |
| print("pushexit") |
| comand = str(input()) |
| if comand == "exit": |
| break |
| return |
| """ |
| |
| ################################################################ |
| |
| # Script entry point. |
| if__name__=="__main__": |
| parser=argparse.ArgumentParser( description="""Demonstration of a UDP OSC node which can communicate with Max.""") |
| parser.add_argument( '--verbose', action='store_true', help='Emit debugging output.') |
| args=parser.parse_args() |
| |
| # Set up the txosc UDP port listening for requests. |
| osc_server=OscServer( verbose=args.verbose ) |
| osc_server.listen( twisted.internet.reactor ) |
| |
| # Start the Twisted event loop. |
| twisted.internet.reactor.run() |
| |
| ifargs.verbose: print("Event loop exited.") |