This commit is contained in:
yumoqing 2020-02-26 17:24:58 +08:00
parent 541cd701dc
commit d1463f7f94
6 changed files with 305 additions and 321 deletions

View File

@ -28,6 +28,32 @@ from .utils import *
from .pagescontainer import PageContainer
from .widgetExt.messager import Messager
from .blocks import Blocks
from appPublic.rsa import RSA
class ServerInfo:
def __init__(self):
self.rsaEngine = RSA()
self.publickey = None
self.authCode = None
def getServerPK(self):
config = getConfig()
url = '%s%s' % (config.uihome, config.publickey_url)
hc = App.get_running_app().hc
d = hc.get(url)
self.publickey = self.rsaEngine. publickeyFromText(d)
def encode(self,uinfo):
if self.publickey is None:
self.getServerPK()
if uinfo['authmethod'] == 'password':
authinfo = '%s::%s::%s' % (uinfo['authmethod'], uinfo['userid'], uinfo['passwd'])
x = self.rsaEngine.encode(self.publickey, authinfo)
self.authCode = x
return x
return None
def signal_handler(signal, frame):
app = App.get_running_app()
@ -42,7 +68,7 @@ class BlocksApp(App):
def build(self):
config = getConfig()
self.config = config
self.userinfo = {}
self.serverinfo = ServerInfo()
self.title = 'Test Title'
self.blocks = Blocks()
self.workers = Workers(maxworkers=config.maxworkers or 80)
@ -55,6 +81,18 @@ class BlocksApp(App):
print('build() called......')
return x
def getAuthHeader(self):
if not hasattr(self,'serverinfo'):
print('app serverinfo not found')
return {}
serverinfo = self.serverinfo
if hasattr(serverinfo,'authCode'):
return {
'authorization':serverinfo.authCode
}
print('serverinfo authCode not found')
return {}
def on_start(self):
print('on_start() called ...')

View File

@ -210,6 +210,7 @@ class Form(BoxLayout):
self.inputwidth = Window.width / self.cols
self.inputheight = CSize(self.options.get('inputheight',3))
self.initflag = False
self.register_event_type('on_submit')
self.bind(size=self.on_size,
pos=self.on_size)
@ -224,7 +225,6 @@ class Form(BoxLayout):
print('box_width=%d,cols=%d' % (self.inputwidth, self.cols))
self.add_widget(self.toolbar)
self.add_widget(self.fsc)
self.register_event_type('on_submit')
self.fieldWidgets=[]
for f in self.options['fields']:
w = InputBox(self, **f)
@ -232,12 +232,11 @@ class Form(BoxLayout):
self.fsc.add_widget(w)
self.fieldWidgets.append(w)
blocks = App.get_running_app().blocks
wid = self.widget_ids['__submit']
# wid = getWidgetById(self,'__submit')
# print('ids=',self.widget_ids.keys())
# wid = self.widget_ids['__submit']
wid = blocks.getWidgetByIdPath(self,'__submit')
wid.bind(on_press=self.on_submit_button)
# wid = getWidgetById(self,'__clear')
wid = self.widget_ids['__clear']
wid = blocks.getWidgetByIdPath(self,'__clear')
# wid = self.widget_ids['__clear']
wid.bind(on_press=self.on_clear_button)
self.initflag = True
@ -248,12 +247,13 @@ class Form(BoxLayout):
d.update(v)
return d
def on_submit(self,o,v=None):
print(o,v)
def on_submit(self,v=None):
print('Form():on_submit fired ...',v)
return False
def on_submit_button(self,o,v=None):
d = self.getData()
self.dispatch('on_submit',self,d)
self.dispatch('on_submit',d)
def on_clear_button(self,o,v=None):
for fw in self.fieldWidgets:
@ -291,6 +291,6 @@ class StrSearchForm(BoxLayout):
}
self.dispatch('on_submit',d)
def on_submit(self,o,v=None):
def on_submit(self,v=None):
print('StrSearchForm():on_submit fired ..........')

View File

@ -2,34 +2,15 @@ from kivy.app import App
from kivy.core.window import Window
from kivy.uix.popup import Popup
from appPublic.Singleton import SingletonDecorator
from appPublic.jsonConfig import getConfig
from appPublic.registerfunction import RegisterFunction
from appPublic.rsa import RSA
# from .form import Form
class ServerInfo:
def __init__(self):
self.rsaEngine = RSA()
config = getConfig()
url = '%s%s' % (config.uihome, config.publickey_url)
hc = App.get_running_app().hc
d = hc.get(url)
self.publickey = self.rsaEngine. publickeyFromText(d)
def encode(self,uinfo):
if uinfo['authmethod'] == 'password':
authinfo = '%s::%s::%s' % (uinfo['authmethod'], uinfo['userid'], uinfo['password'])
txt = self.serverinfo.encode(authinfo)
x = self.rsaEngine.encode(self.publickey, txt)
return x
return None
logformdesc = {
"widgettype":"Form",
"options":{
"cols":1,
"labelwidth":0.3,
"labelwidth":0.4,
"textsize":1,
"inputheight":3,
"inputheight":4,
"fields":[
{
"name":"userid",
@ -44,61 +25,43 @@ logformdesc = {
"uitype":"password"
}
]
},
"binds":[
{
"wid":"self",
"event":"on_submit",
"datawidegt":"self",
"actiontype":"registedfunction",
"rfname":"setupUserInfo"
}
]
}
}
@SingletonDecorator
class LoginForm(Popup):
def __init__(self):
super().__init__(size_hint=(0.8,0.8))
app = App.get_running_app()
print('here ..1............')
self.content = app.blocks.widgetBuild(logformdesc)
# self.content.bind(on_submit=setipUserInfo)
print('here ..2............',self.content)
self.title = 'login'
self.blockCalls = []
self.open_status = False
print('here ..3............')
self.initflag = False
self.bind(size=self.buildContent,
pos=self.buildContent)
def buildContent(self,o,size):
print('build Content. ....')
if self.initflag:
return
print('build Content ....... ....')
self.initflag = True
app = App.get_running_app()
self.content = app.blocks.widgetBuild(logformdesc)
self.content.bind(on_submit=self.on_submit)
self.content.bind(on_cancel=self.on_submit)
print('here ..4............')
self.open()
def close(self):
self.open_status = False
def on_submit(self,o,userinfo):
print('login(),on_submit fired ....')
self.dismiss()
print('userinfo=',userinfo)
app = App.get_running_app()
def on_submit(self,o,v):
self.dismiss()
if userinfo.get('passwd',False):
userinfo['authmethod'] = 'password'
authinfo = app.serverinfo.encode(userinfo)
login_url = '%s%s' % (app.config.uihome, app.config.login_url)
x = app.hc.get(login_url)
print('login return=', x, login_url, authinfo)
def on_cancel(self,o,v):
print('login() on_cancel fired .....')
self.dismiss()
def setupUserInfo(obj, userinfo):
app = App.get_running_app()
if not hasattr(app, 'serverinfo'):
app.serverinfo = ServerInfo()
if userinfo.get('password',False):
userinfo['authmethod'] = 'password'
authinfo = app.serverinfo.encode(userinfo)
headers = {
"authorization":authinfo
}
login_url = '%s%s' % (app.config.uihome, app.config.login_url)
app.hc.get(login_url,headers=headers)
rf = RegisterFunction()
rf.register('setupUserInfo',setupUserInfo)

View File

@ -51,7 +51,11 @@ class VResponsiveLayout(ScrollView):
def setCols(self,t=None):
self.box_width = self.org_box_width
self.cols = int(self.width / self.box_width)
if self.width < self.box_width:
self.cols = self.org_cols
else:
self.cols = int(self.width / self.box_width)
print('VResponsiveLayout()::setCols():self.cols=',self.cols, 'self.box_width=',self.box_width,'self.org_cols=',self.org_cols)
if isHandHold():
w,h = self.size
if w < h:

View File

@ -42,7 +42,7 @@ class ThreadCall(Thread,EventDispatcher):
pass
def checkStop(self,timestamp):
x = self.join(timeout=0.0001)
x = self.join(timeout=0.001)
if self.is_alive():
self.timing = Clock.schedule_once(self.checkStop,0)
return
@ -79,12 +79,28 @@ class Workers(Thread):
with self.lock:
self.tasks.insert(0,[callee,callback,errback,kwargs])
hostsessions = {}
class HttpClient:
def __init__(self):
self.s = requests.Session()
self.workers = App.get_running_app().workers
def url2domain(self,url):
parts = url.split('/')[:3]
pre = '/'.join(parts)
return pre
def webcall(self,url,method="GET",params={},files={},headers={}):
app = App.get_running_app()
domain = self.url2domain(url)
sessionid = hostsessions.get(domain,None)
print('hostsessions=', hostsessions, 'sessionid=',sessionid, 'domain=',domain)
if sessionid:
headers.update({'session':sessionid})
elif app.getAuthHeader():
headers.update(app.getAuthHeader())
print('headers=',headers)
if method in ['GET']:
req = requests.Request(method,url,
params=params,headers=headers)
@ -94,6 +110,11 @@ class HttpClient:
prepped = self.s.prepare_request(req)
resp = self.s.send(prepped)
if resp.status_code == 200:
h = resp.headers.get('Set-Cookie',None)
if h:
print('*************set-Cookie=',h,'domain=',domain)
sessionid = h.split(';')[0]
hostsessions[domain] = sessionid
try:
data = resp.json()
if type(data) != type({}):
@ -128,7 +149,7 @@ class HttpClient:
except Exception as e:
if errback is not None:
errback(e)
return None
kwargs = {
"url":url,
"method":method,

View File

@ -1,5 +1,6 @@
import os
import sys
import time
from kivy.utils import platform
from traceback import print_exc
from kivy.core.window import Window
@ -15,6 +16,7 @@ from kivy.app import App
from kivy.clock import Clock
from kivy.properties import ObjectProperty, StringProperty, BooleanProperty, \
NumericProperty, DictProperty, OptionProperty
from pythonosc import dispatcher, osc_server
from .utils import *
from .baseWidget import PressableImage
@ -26,79 +28,26 @@ desktopOSs=[
othersplatforms=['ios','android']
class VPlayer(FloatLayout):
class BaseVPlayer(FloatLayout):
fullscreen = BooleanProperty(False)
exit = BooleanProperty(False)
stoped_play = BooleanProperty(False)
paused_play = BooleanProperty(False)
def __init__(self,vfile=None,
playlist=None,
loop=False,
openfile_img=None,
exit_img = None,
pause_img = None,
play_img = None,
mute_img = None,
track_img = None,
next_img = None,
replay_img = None,
can_openfile=False,
can_cut=False,
can_replay=False,
can_changevolume=True
):
def __init__(self,vfile=None):
super().__init__()
Window.allow_screensaver = False
print(self,vfile)
self._video = Video(allow_stretch=True,pos_hint={'x': 0, 'y': 0},size_hint=(1,1))
self.add_widget(self._video)
self.loop = loop
self.openfile_img = openfile_img
self.can_openfile = can_openfile
self.can_replay = can_replay
self.can_cut = can_cut
self.can_changevolume = can_changevolume
if self.openfile_img:
self.can_openfile = True
self.exit_img = exit_img
self.play_img = play_img
self.pause_img = pause_img
self.mute_img = mute_img
self.track_img = track_img
self.next_img = next_img
self.replay_img = replay_img
self.ffplayer = None
self.menubar = None
self._popup = None
self.menu_status = False
self.manualMode = False
self.update_task = None
self.old_path = os.getcwd()
self.pb = None
if vfile:
if type(vfile) == type([]):
self.playlist = vfile
else:
self.playlist = [vfile]
self.curplay = 0
self.play()
if type(vfile) == type([]):
self.playlist = vfile
else:
self.playlist = []
self.curplay = -1
self.playlist = [vfile]
self.curplay = 0
self.play()
self._video.bind(eos=self.video_end)
self._video.bind(state=self.on_state)
self._video.bind(loaded=self.createProgressbar)
self._video.bind(on_touch_down=self.show_hide_menu)
self.register_event_type('on_playend')
def __del__(self):
print('********** delete VPlayer instance ********')
if self._video is None:
return
if self.update_task:
self.update_task.cancel()
self.update_task = None
self._video.state = 'pause'
Window.allow_screensaver = True
del self._video
@ -117,75 +66,10 @@ class VPlayer(FloatLayout):
def video_end(self,t,v):
self.curplay += 1
if not self.loop and self.curplay >= len(self.playlist):
self.dispatch('on_playend')
return
self.curplay = self.curplay % len(self.playlist)
self._video.source = self.playlist[self.curplay]
self._video.state = 'play'
def totime(self,dur):
h = dur / 3600
m = dur % 3600 / 60
s = dur % 60
return '%02d:%02d:%02d' % (h,m,s)
def createProgressbar(self,obj,v):
if hasattr(self._video._video, '_ffplayer'):
self.ffplayer = self._video._video._ffplayer
if self.pb is None:
self.pb = BoxLayout(orientation='horizontal',
size_hint = (0.99,None),height=CSize(1.4))
self.curposition = Label(text='0',width=CSize(4),
size_hint_x=None)
self.curposition.align='right'
self.maxposition = Label(text=self.totime(self._video.duration),
width=CSize(4),size_hint_x=None)
self.maxposition.align = 'left'
self.slider = Slider(min=0,
max=self._video.duration,
value=0,
orientation='horizontal',
step=0.01)
self.slider.bind(on_touch_down=self.enterManualMode)
self.slider.bind(on_touch_up=self.endManualMode)
self.manual_mode=False
self.pb.add_widget(self.curposition)
self.pb.add_widget(self.slider)
self.pb.add_widget(self.maxposition)
self.update_task = Clock.schedule_interval(self.update_slider,1)
self.buildMenu()
def enterManualMode(self,obj,touch):
if not self.slider.collide_point(*touch.pos):
return
self.manualMode = True
def endManualMode(self,obj,touch):
if not self.manualMode:
return
if self._video.duration < 0.0001:
return
self._video.seek(self.slider.value/self._video.duration)
self.manualMode = False
def update_slider(self,t):
self.curposition.text = self.totime(self._video.position)
if not self.manualMode:
self.slider.value = self._video.position
self.slider.max = self._video.duration
self.maxposition.text = self.totime(self._video.duration)
def beforeDestroy(self):
try:
del self
except Exception as e:
print_exc()
return True
def on_state(self,o,v):
if self._video.state == 'play':
Window.allow_screensaver = False
@ -212,7 +96,6 @@ class VPlayer(FloatLayout):
if value:
Window.fullscreen = True
print('Window size=',Window.size)
self._fullscreen_state = state = {
'parent': self.parent,
'pos': self.pos,
@ -221,7 +104,6 @@ class VPlayer(FloatLayout):
'size_hint': self.size_hint,
'window_children': window.children[:]}
print('vplayer fullscreen,platform=',platform,desktopOSs)
if platform in desktopOSs:
Window.maximize()
# remove all window children
@ -251,10 +133,182 @@ class VPlayer(FloatLayout):
self.size = state['size']
if state['parent'] is not window:
state['parent'].add_widget(self)
print('vplayer fullscreen,platform=',platform,desktopOSs)
if platform in desktopOSs:
Window.restore()
def endplay(self,btn):
self._video.seek(1.0,precise=True)
def replay(self,btn):
self._video.seek(0.0,precise=True)
def audioswitch(self,btn):
if self.ffplayer is not None:
self.ffplayer.request_channel('audio')
def setVolume(self,obj,v):
self._video.volume = v
def setPosition(self,obj,v):
self._video.seek(v)
def mute(self,btn):
if self._video.volume > 0.001:
self.old_volume = self._video.volume
self._video.volume = 0.0
else:
self._video.volume = self.old_volume
def stop(self):
try:
self._video.state = 'stop'
except:
print_exc()
def pause(self,t=None):
if self._video.state == 'play':
self._video.state = 'pause'
else:
self._video.state = 'play'
class OSCVPlayer(BaseVPlayer):
def __init__(self,ip,port,vfile=None):
self.ip = ip
self.port = port
self.dispatcher = dispatcher.Dispatcher()
self.server = osc_server.ThreadingOSCUDPServer( (self.ip, self.port), self.dispatcher)
BaseVPlayer.__init__(self,vfile=vfile)
self.map('/mute',self.mute)
self.map('/pause',self.pause)
self.map('/atrack',self.audioswitch)
self.map('/endplay',self.endplay)
self.map('/replay',self.replay)
self.map('/setvalume',self.setVolume)
self.map('/setposition',self.setPosition)
self.map('/next',self.next)
self.server.serve_forever()
self.fullscreen = True
label = Label(text='%s %d' % (self.ip,self.port), font_size=CSize(2))
label.size = self.width - label.width, 0
self.add_widget(label)
def next(self,obj):
self.source = self.vfile + '?t=%f' % time.time()
def map(self,p,f):
self.dispatcher.map(p,f,None)
class VPlayer(BaseVPlayer):
def __init__(self,vfile=None,
playlist=None,
loop=False
):
super().__init__(vfile=vfile)
self.loop = loop
self.menubar = None
self._popup = None
self.menu_status = False
self.manualMode = False
self.update_task = None
self.pb = None
if vfile:
if type(vfile) == type([]):
self.playlist = vfile
else:
self.playlist = [vfile]
self.curplay = 0
self.play()
else:
self.playlist = []
self.curplay = -1
self._video.bind(on_touch_down=self.show_hide_menu)
self.register_event_type('on_playend')
def __del__(self):
print('********** delete VPlayer instance ********')
if self._video is None:
return
if self.update_task:
self.update_task.cancel()
self.update_task = None
self._video.state = 'pause'
Window.allow_screensaver = True
del self._video
self._video = None
def video_end(self,t,v):
self.curplay += 1
if not self.loop and self.curplay >= len(self.playlist):
self.dispatch('on_playend')
return
self.curplay = self.curplay % len(self.playlist)
self._video.source = self.playlist[self.curplay]
self._video.state = 'play'
def totime(self,dur):
h = dur / 3600
m = dur % 3600 / 60
s = dur % 60
return '%02d:%02d:%02d' % (h,m,s)
def createProgressBar(self):
if hasattr(self._video._video, '_ffplayer'):
self.ffplayer = self._video._video._ffplayer
if self.pb is None:
self.pb = BoxLayout(orientation='horizontal',
size_hint = (0.99,None),height=CSize(1.4))
self.curposition = Label(text='0',width=CSize(4),
size_hint_x=None)
self.curposition.align='right'
self.maxposition = Label(text=self.totime(self._video.duration),
width=CSize(4),size_hint_x=None)
self.maxposition.align = 'left'
self.slider = Slider(min=0,
max=self._video.duration,
value=0,
orientation='horizontal',
step=0.01)
self.slider.bind(on_touch_down=self.enterManualMode)
self.slider.bind(on_touch_up=self.endManualMode)
self.manual_mode=False
self.pb.add_widget(self.curposition)
self.pb.add_widget(self.slider)
self.pb.add_widget(self.maxposition)
self.menubar.add_widget(self.pb)
self.update_task = Clock.schedule_interval(self.update_slider,1)
def enterManualMode(self,obj,touch):
if not self.slider.collide_point(*touch.pos):
return
self.manualMode = True
def endManualMode(self,obj,touch):
if not self.manualMode:
return
if self._video.duration < 0.0001:
return
self._video.seek(self.slider.value/self._video.duration)
self.manualMode = False
def update_slider(self,t):
self.curposition.text = self.totime(self._video.position)
if not self.manualMode:
self.slider.value = self._video.position
self.slider.max = self._video.duration
self.maxposition.text = self.totime(self._video.duration)
def beforeDestroy(self):
try:
del self
except Exception as e:
print_exc()
return True
def show_hide_menu(self,obj,touch):
if not self.collide_point(*touch.pos):
print('not inside the player')
@ -265,14 +319,15 @@ class VPlayer(FloatLayout):
print('doube_tap')
return
if self.menubar:
if not self.menubar:
self.buildMenu()
return
if self.menu_status:
self.remove_widget(self.menubar)
self.menu_status = not self.menu_status
if self.menu_status:
self.add_widget(self.menubar)
else:
self.remove_widget(self.menubar)
return
else:
self.add_widget(self.menubar)
self.menu_status = not self.menu_status
def buildMenu(self):
self.menubar = BoxLayout(orientation='horizontal',
@ -291,10 +346,6 @@ class VPlayer(FloatLayout):
)
self.btn_mute.bind(on_press=self.mute)
self.menubar.add_widget(self.btn_mute)
if self.can_openfile:
btn_open = Button(text='open')
btn_open.bind(on_press=self.openfile)
self.menubar.add_widget(btn_open)
btn_cut = PressableImage(source=blockImage('next.jpg'),
size_hint=(None,None),
size=CSize(3,3)
@ -326,123 +377,30 @@ class VPlayer(FloatLayout):
step=0.07)
slider.bind(on_touch_up=self.setVolume)
self.menubar.add_widget(slider)
self.menubar.add_widget(self.pb)
self.menubar.pos = CSize(0,0)
self.createProgressBar()
self.add_widget(self.menubar)
self.menu_status = True
def endplay(self,btn):
self._video.seek(1.0,precise=True)
def replay(self,btn):
self._video.seek(0.0,precise=True)
def hideMenu(self):
self._popup.dismiss()
self.remove_widget(self.menubar)
self.menubar = None
def audioswitch(self,btn):
if self.ffplayer is not None:
self.ffplayer.request_channel('audio')
def setVolume(self,obj,touh):
self._video.volume = obj.value
def setVolume(self,obj,v=None):
BaseVPlayer.setVolume(self,obj,obj.value)
def mute(self,btn):
if self._video.volume > 0.001:
self.old_volume = self._video.volume
self._video.volume = 0.0
if self.menubar:
BaseVPlayer.mute(self,btn)
if self.menubar:
if self._video.volume < 0.001:
btn.source = blockImage('volume.jpg')
else:
self._video.volume = self.old_volume
if self.menubar:
else:
btn.source = blockImage('mute.jpg')
def stop(self):
try:
self._video.state = 'stop'
except:
print_exc()
def on_disabled(self,o,v):
if self.disabled:
self.stop()
del self._video
def pause(self,t=None):
if self._video.state == 'play':
self._video.state = 'pause'
if self.menubar:
BaseVPlayer.pause(self,t)
if self.menubar:
if self._video.state == 'pause':
self.btn_pause.source = blockImage('play.jpg')
else:
self._video.state = 'play'
if self.menubar:
else:
self.btn_pause.source = blockImage('pause.jpg')
def openfile(self,t):
if self._popup is None:
def vfilter(path,filename):
vexts = ['.avi',
'.mpg',
'.mpe',
'.mpeg',
'.mlv',
'.dat',
'.mp4',
'.flv',
'.mov',
'.rm',
'.mkv',
'.rmvb',
'.asf',
'.3gp'
]
for ext in vexts:
if filename.endswith(ext):
return True
return False
c = BoxLayout(orientation='vertical')
self.file_chooser = FileChooserListView()
self.file_chooser.filters = [vfilter]
self.file_chooser.multiselect = True
self.file_chooser.path = self.old_path
self.file_chooser.bind(on_submit=self.loadFilepath)
c.add_widget(self.file_chooser)
b = BoxLayout(size_hint_y=None,height=35)
c.add_widget(b)
cancel = Button(text='Cancel')
cancel.bind(on_press=self.cancelopen)
load = Button(text='load')
load.bind(on_press=self.playfile)
b.add_widget(load)
b.add_widget(cancel)
self._popup = Popup(title='Open file',content=c,size_hint=(0.9,0.9))
self._popup.open()
def cancelopen(self,obj):
self.hideMenu()
def loadFilepath(self,obj,fpaths,evt):
print('fp=',fpaths,type(fpaths),'evt=',evt)
self.hideMenu()
self.playlist = fpaths
self.curplay = 0
self._video.source = self.playlist[self.curplay]
self._video.state = 'play'
def playfile(self,obj):
print('obj')
self.hideMenu()
self.playlist = []
for f in self.file_chooser.selection:
fp = os.path.join(self.file_chooser.path,f)
self.playlist.append(fp)
self.curplay = 0
self._video.source = self.playlist[self.curplay]
self._video.state = 'play'
if __name__ == '__main__':
class MyApp(App):
def build(self):