class PhotoStrip(ScrollView): def on_press(self, filename): pass def on_release(self, filename): pass def __init__(self, *args, **kwargs): super(PhotoStrip, self).__init__(size_hint=(1,1), pos_hint={'center_x': 0.5, 'center_y': 0.5}, do_scroll_x=False, *args, **kwargs) self.register_event_type('on_press') self.register_event_type('on_release') self.strip = AsyncImage(source='photos-strip.png', allow_stretch=True, size_hint_y=1.8) self.add_widget(self.strip) self.image0 = image_button() self.image0.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image0) self.image1 = image_button() self.image1.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image1) self.image2 = image_button() self.image2.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image2) self.image3 = image_button() self.image3.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image3) self.strip.bind(size=self.update_buttons,pos=self.update_buttons) def set_path(self, path): print path path = filesystem.normpath(path) print path self.scroll_y = 1 if 'effect_y' in dir(self): # Kivy 1.6.0 doesn't have effect_y self.effect_y.value = self.effect_y.min # This is to work around a bug with the ScrollView (https://github.com/kivy/kivy/issues/2038) self.image0.source = filesystem.join(path, '0.jpg') self.image1.source = filesystem.join(path, '1.jpg') self.image2.source = filesystem.join(path, '2.jpg') self.image3.source = filesystem.join(path, 'blank') def press_btn(self, btn): self.dispatch('on_press', btn.source) def release_btn(self, btn): self.dispatch('on_release', btn.source) def update_buttons(self, instance, value): spacing = 20 padding = 25 offset = padding for img in [self.image0, self.image1, self.image2, self.image3]: img.size = (instance.norm_image_size[0]/60)*43, (instance.norm_image_size[1]-((spacing*3)+(padding*2)))/4 img.center_x = instance.center_x img.center_y = instance.top-((img.height/2)+offset) offset += img.height+spacing
class MapWidget(MDDialog2): @property def projection(self): # return ccrs.PlateCarree() # return ccrs.EckertI() # return ccrs.EquidistantConic() # return ccrs.LambertConformal(central_longitude=0)#,central_latitude=0) # return ccrs.LambertConformal(central_longitude=0)#,central_latitude=0) return ccrs.AlbersEqualArea() @property def figsize(self): # fig = plt.figure() # dpi=fig.dpi // 2 dpi=40 width,height=Window.size return (width//dpi, height//dpi) # bbox = fig.get_window_extent().transformed(fig.dpi_scale_trans.inverted()) # width, height = bbox.width*fig.dpi, bbox.height*fig.dpi # return (width,height) @property def color_land(self): return rgb(*darksienna3,a=0) #darksienna3) @property def color_water(self): return rgb(*russiangreen) @property def color_label(self): return rgb(*COLOR_ICON) @property def color_marker(self): return rgb(*COLOR_ICON) @property def color_line(self): return rgb(*rufusred) # COLOR_ICON) @property def color_line_dark(self): return rgb(*COLOR_ICON) def __init__(self): self.last_lat = None self.last_long = None self.points = [] self.opened=False self.label=None self.intro_label=None # self.fig = fig = plt.figure(figsize=(20,10)) plt.rcParams["figure.figsize"] = self.figsize self.ax = ax = plt.axes( projection=self.projection, ) # ax.set_extent([-170, 165, -55, 75]) # ax.background_patch.set_facecolor(rgb(*COLOR_CARD)[:3]) # ax.outline_patch.set_facecolor(rgb(*COLOR_CARD)[:3]) # self.ax.stock_img() # self.ax.coastlines(color=rgb(*COLOR_CARD)) ax.add_feature(cartopy.feature.OCEAN, zorder=0, color=self.color_water,edgecolor=self.color_water) ax.add_feature(cartopy.feature.LAND, zorder=0, color=self.color_land, edgecolor=self.color_land) ax.outline_patch.set_visible(False) ax.background_patch.set_visible(False) # ax.set_global() # ax.gridlines() self.layout=MDBoxLayout() self.layout.orientation='vertical' self.layout.cols=1 self.layout.size_hint=(None,None) self.layout.size=(Window.size[0],Window.size[1]) # ('666sp','666sp') self.layout.md_bg_color=rgb(*eerieblack) #rgb(*COLOR_BG,a=1) # self.layout.adaptive_height=True # self.layout.height=self.layout.minimum_height self.layout.spacing='0sp' self.layout.padding='0sp' self.img=None self.label_layout=MDGridLayout() self.label_layout.orientation='vertical' self.label_layout.cols=1 self.label_layout.row_default_height='25sp' self.label_layout.row_force_default='25sp' self.label_layout.rows=10 self.label_layout.pos_hint={'y':1} self.label_layout.size_hint=(None,None) self.label_layout.width=Window.size[0] self.label_layout.height='300sp' # self.label_layout.size=(Window.size[0],'400sp') # self.label_layout.size=Window.size # ('666sp','666sp') # self.layout.add_widget(self.label_layout) # do dialog's intro super().__init__( type='custom', text='', content_cls=self.layout, buttons=[ MDFlatButton( text="disconnect", text_color=rgb(*COLOR_TEXT), md_bg_color = rgb(*eerieblack), #(0,0,0,1), theme_text_color='Custom', on_release=self.dismiss, font_name=FONT_PATH ) ], color_bg = rgb(*eerieblack), #(0,0,0,1), overlay_color=(0,0,0,0), background_color=(0,0,0,0) ) self.ids.text.text_color=rgb(*COLOR_TEXT) self.ids.text.font_name=FONT_PATH self.size=Window.size #('666sp','666sp') # self. # self.adaptive_height=True def draw(self): from matplotlib import transforms from PIL import Image as pImage from PIL import ImageOps # tr = transforms.Affine2D().rotate_deg(90) # buf = io.BytesIO() # plt.ion() from comrad.constants import PATH_MAPS odir=PATH_MAPS if not os.path.exists(odir): os.makedirs(odir) ofn=os.path.join(odir,f't_{len(self.points)}.png') # plt.gca().invert_yaxis() plt.savefig(ofn, format='png',transparent=True,pad_inches=0.1,bbox_inches = 'tight') # flip? # im = pImage.open(ofn) # im = im.rotate(90) # im.save(ofn) if not self.img: self.img= AsyncImage(source=ofn) self.img.background_color=(0,0,0,0) self.img.overlay_color=(0,0,0,0) # self.img.texture.flip_horizontal() self.img.pos_hint={'center_x':0.48,'center_y':0.5} # self.img.size=Window.size # self.img.texture = img self.img.add_widget(self.label_layout,1) self.layout.add_widget(self.img,1) else: self.img.source=ofn # self.img.size_hint=(1,1) # self.img.width=Window.size[0] # self.img.allow_stretch=True def makelabel(self,txt): label=MDLabel(text=txt) label.color=self.color_label #rgb(*color) #self.color_label label.font_name=FONT_PATH label.font_size='20sp' # label.size_hint=(1,1) label.width=Window.size[0] label.height='25sp' label.valign='top' return label def add_point(self,lat,long,desc): logger.info(f'adding point? {desc} {lat}, {long}') # plt.text( # long+3, # lat-12, # desc, # horizontalalignment='left', # transform=self.projection # ) import random from comrad.constants import ALL_COLORS color = random.choice(ALL_COLORS) self.points+=[(lat,long,desc)] # # point plt.plot( long, lat, '.', markersize=25, linewidth=10, color=self.color_marker,#rgb(*color), transform=ccrs.Geodetic(), ) # line if self.last_lat and self.last_long: # if self.ax.lines: self.ax.lines.pop(0) for line in self.ax.lines: line.set_color(self.color_line_dark) plt.plot( [self.last_long, long], [self.last_lat, lat], color=self.color_line,#rgb(*color), #self.color_line, linewidth=4, marker='', transform=ccrs.Geodetic(), ) desc = '\n'.join('--> '+desc for lat,long,desc in self.points[-1:]) #if self.label: # self.img.remove_widget(self.label) self.label=label=self.makelabel(desc) # label.height='400sp' # label.pos_hint = {'center_y':0.1+(0.1 * len(self.points))} # label.pos = (0.5,0) self.label_layout.add_widget(label) self.last_lat,self.last_long = lat,long self.ax.set_global() # wait and show def open(self,maxwait=666,pulse=0.1): self.ax.lines=[] self.draw() if not self.intro_label: self.intro_label = self.makelabel('Comrad @Tor: Routing you through the global maze of the deep web ...') self.label_layout.add_widget(self.intro_label) super().open() self.opened=True # await asyncio.sleep(pulse) # waited=0 # while not self.ok_to_continue: # await asyncio.sleep(pulse) # waited+=pulse # if waited>maxwait: break # # logger.info(f'waiting for {waited} seconds... {self.ok_to_continue} {self.response}') # return self.response def dismiss(self): super().dismiss() self.intro_label=None if hasattr(self.layout,'img'): self.layout.remove_widget(self.img) if self.layout: self.remove_widget(self.layout)
class PhotoStrip(ScrollView): def on_press(self, filename): pass def on_release(self, filename): pass def __init__(self, *args, **kwargs): super(PhotoStrip, self).__init__(size_hint=(1, 1), pos_hint={ 'center_x': 0.5, 'center_y': 0.5 }, do_scroll_x=False, *args, **kwargs) self.register_event_type('on_press') self.register_event_type('on_release') self.strip = AsyncImage(source='photos-strip.png', allow_stretch=True, size_hint_y=1.8) self.add_widget(self.strip) self.image0 = image_button() self.image0.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image0) self.image1 = image_button() self.image1.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image1) self.image2 = image_button() self.image2.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image2) self.image3 = image_button() self.image3.bind(on_press=self.press_btn, on_release=self.release_btn) self.strip.add_widget(self.image3) self.strip.bind(size=self.update_buttons, pos=self.update_buttons) def set_path(self, path): print path path = filesystem.normpath(path) print path self.scroll_y = 1 if 'effect_y' in dir(self): # Kivy 1.6.0 doesn't have effect_y self.effect_y.value = self.effect_y.min # This is to work around a bug with the ScrollView (https://github.com/kivy/kivy/issues/2038) self.image0.source = filesystem.join(path, '0.jpg') self.image1.source = filesystem.join(path, '1.jpg') self.image2.source = filesystem.join(path, '2.jpg') self.image3.source = filesystem.join(path, 'blank') def press_btn(self, btn): self.dispatch('on_press', btn.source) def release_btn(self, btn): self.dispatch('on_release', btn.source) def update_buttons(self, instance, value): spacing = 20 padding = 25 offset = padding for img in [self.image0, self.image1, self.image2, self.image3]: img.size = (instance.norm_image_size[0] / 60) * 43, (instance.norm_image_size[1] - ((spacing * 3) + (padding * 2))) / 4 img.center_x = instance.center_x img.center_y = instance.top - ((img.height / 2) + offset) offset += img.height + spacing