@@ -98,8 +98,8 @@ def __init__(
9898 x = 0 ,
9999 y = 0 ,
100100 text = "" ,
101- max_glyphs = None , # This input parameter is ignored, only present for compatibility
102- # with label.py
101+ max_glyphs = None , # This input parameter is ignored, only present for compatibility
102+ # with label.py
103103 color = 0xFFFFFF ,
104104 background_color = None ,
105105 line_spacing = 1.25 ,
@@ -114,117 +114,199 @@ def __init__(
114114 ** kwargs
115115 ):
116116
117- if text == "" :
118- raise RuntimeError (
119- "Please provide text string, or use label.py for mutable text"
120- )
117+ # instance the Group
118+ # this Group will contain just one TileGrid with one contained bitmap
119+ super ().__init__ (
120+ max_size = 1 , x = x , y = y , ** kwargs
121+ ) # this will include any arguments, including scale
121122
122123 self ._font = font
123124
124- # Scale will be passed to Group using kwargs.
125- if "scale" in kwargs .keys ():
126- self ._scale = kwargs ["scale" ]
127- else :
128- self ._scale = 1
125+ # Create the two-color palette
126+ self .palette = displayio .Palette (2 )
127+ self .color = color
128+ self .background_color = background_color
129+
130+ self ._anchor_point = anchor_point
131+ self ._anchored_position = anchored_position
132+
133+ self ._scale = 1 # initialize to the default scale of 1
134+
135+ # call the text updater with all the arguments.
136+ self ._reset_text (font = font ,
137+ x = x ,
138+ y = y ,
139+ text = text ,
140+ # color=color,
141+ # background_color=background_color,
142+ line_spacing = line_spacing ,
143+ background_tight = background_tight ,
144+ padding_top = padding_top ,
145+ padding_bottom = padding_bottom ,
146+ padding_left = padding_left ,
147+ padding_right = padding_right ,
148+ anchor_point = anchor_point ,
149+ anchored_position = anchored_position ,
150+ save_text = save_text ,
151+ ** kwargs ,
152+ )
129153
130- self ._line_spacing = line_spacing
131- self ._save_text = save_text
154+
155+ def _reset_text (
156+ self ,
157+ font = None ,
158+ x = None ,
159+ y = None ,
160+ text = None ,
161+ line_spacing = None ,
162+ background_tight = None ,
163+ padding_top = None ,
164+ padding_bottom = None ,
165+ padding_left = None ,
166+ padding_right = None ,
167+ anchor_point = None ,
168+ anchored_position = None ,
169+ save_text = None ,
170+ ** kwargs
171+ ):
172+
173+ # store the instance variables
174+
175+ print ('_reset_text Text string to print: {}' .format (text ))
176+
177+ # Store all the instance variables
178+ if font is not None :
179+ self ._font = font
180+ if x is not None :
181+ self .x = x
182+ if y is not None :
183+ self .y = y
184+ # if color is not None:
185+ # self.color = color
186+ # if background_color is not None:
187+ # self.background_color = background_color
188+ if line_spacing is not None :
189+ self ._line_spacing = line_spacing
190+ if background_tight is not None :
191+ self ._background_tight = background_tight
192+ if padding_top is not None :
193+ self ._padding_top = max (0 , padding_top )
194+ if padding_bottom is not None :
195+ self ._padding_bottom = max (0 , padding_bottom )
196+ if padding_left is not None :
197+ self ._padding_left = max (0 , padding_left )
198+ if padding_right is not None :
199+ self ._padding_right = max (0 , padding_right )
200+ if anchor_point is not None :
201+ self .anchor_point = anchor_point
202+ if anchored_position is not None :
203+ self ._anchored_position = anchored_position
204+ if save_text is not None :
205+ self ._save_text = save_text
206+
207+ # if text is not provided as a parameter (text is None), use the previous value.
208+ if (text is None ) and self ._save_text :
209+ text = self ._text
132210
133211 if self ._save_text : # text string will be saved
134212 self ._text = text
135213 else :
136214 self ._text = None # save a None value since text string is not saved
137215
138- # limit padding to >= 0
139- padding_top = max (0 , padding_top )
140- padding_bottom = max (0 , padding_bottom )
141- padding_left = max (0 , padding_left )
142- padding_right = max (0 , padding_right )
143-
144- # Calculate the text bounding box
145-
146- # Calculate tight box to provide bounding box dimensions to match label for
147- # anchor_position calculations
148- (
149- tight_box_x ,
150- tight_box_y ,
151- tight_x_offset ,
152- tight_y_offset ,
153- ) = self ._text_bounding_box (
154- text , font , self ._line_spacing , background_tight = True ,
155- )
156-
157- if background_tight :
158- box_x = tight_box_x
159- box_y = tight_box_y
160- y_offset = tight_y_offset
161- x_offset = tight_x_offset
162-
163- else :
164- (box_x , box_y , x_offset , y_offset ) = self ._text_bounding_box (
165- text , font , self ._line_spacing , background_tight = background_tight ,
166- )
167- # Calculate the background size including padding
168- box_x = box_x + padding_left + padding_right
169- box_y = box_y + padding_top + padding_bottom
216+ # Scale will be passed to Group using kwargs.
217+ if "scale" in kwargs .keys ():
218+ self ._scale = kwargs ["scale" ]
170219
171- # Create the two-color palette
172- self .palette = displayio .Palette (2 )
173220
174- self . background_color = background_color
175- self . color = color
221+ # Check for empty string
222+ if ( text == "" ) or ( text is None ): # If empty string, just create a zero-sized bounding box and that's it.
176223
177- # Create the bitmap and TileGrid
178- self .bitmap = displayio .Bitmap (box_x , box_y , len (self .palette ))
179-
180- # Place the text into the Bitmap
181- self ._place_text (
182- self .bitmap ,
183- text ,
184- font ,
185- self ._line_spacing ,
186- padding_left - x_offset ,
187- padding_top + y_offset ,
188- )
189-
190- label_position_yoffset = int ( # To calibrate with label.py positioning
191- (font .get_glyph (ord ("M" )).height ) / 2
192- )
193-
194- self .tilegrid = displayio .TileGrid (
195- self .bitmap ,
196- pixel_shader = self .palette ,
197- width = 1 ,
198- height = 1 ,
199- tile_width = box_x ,
200- tile_height = box_y ,
201- default_tile = 0 ,
202- x = - padding_left + x_offset ,
203- y = label_position_yoffset - y_offset - padding_top ,
204- )
224+ self ._bounding_box = (
225+ 0 ,
226+ 0 ,
227+ 0 , # zero width with text == ""
228+ 0 , # zero height with text == ""
229+ )
230+ # Clear out any items in the self Group, in case this is an update to the bitmap_label
231+ for item in self :
232+ self .pop (0 )
233+
234+ else : # The text string is not empty, so create the Bitmap and TileGrid and append to the self Group
235+
236+
237+ # Calculate the text bounding box
238+
239+ # Calculate tight box to provide bounding box dimensions to match label for
240+ # anchor_position calculations
241+ (
242+ tight_box_x ,
243+ tight_box_y ,
244+ tight_x_offset ,
245+ tight_y_offset ,
246+ ) = self ._text_bounding_box (
247+ text , self ._font , self ._line_spacing , background_tight = True ,
248+ ) # calculate the box size for a tight background
249+
250+ if self ._background_tight :
251+ box_x = tight_box_x
252+ box_y = tight_box_y
253+ y_offset = tight_y_offset
254+ x_offset = tight_x_offset
255+
256+ else : # calculate the box size for a loose background
257+ (box_x , box_y , x_offset , y_offset ) = self ._text_bounding_box (
258+ text , self ._font , self ._line_spacing , background_tight = self ._background_tight ,
259+ )
260+ # Calculate the background size including padding
261+ box_x = box_x + self ._padding_left + self ._padding_right
262+ box_y = box_y + self ._padding_top + self ._padding_bottom
263+
264+ # Create the bitmap and TileGrid
265+ self .bitmap = displayio .Bitmap (box_x , box_y , len (self .palette ))
266+
267+ # Place the text into the Bitmap
268+ self ._place_text (
269+ self .bitmap ,
270+ text ,
271+ self ._font ,
272+ self ._line_spacing ,
273+ self ._padding_left - x_offset ,
274+ self ._padding_top + y_offset ,
275+ )
205276
206- # instance the Group
207- # this Group will contain just one TileGrid with one contained bitmap
208- super ().__init__ (
209- max_size = 1 , x = x , y = y , ** kwargs
210- ) # this will include any arguments, including scale
211- self .append (self .tilegrid ) # add the bitmap's tilegrid to the group
277+ label_position_yoffset = int ( # To calibrate with label.py positioning
278+ (self ._font .get_glyph (ord ("M" )).height ) / 2
279+ )
212280
213- # Update bounding_box values. Note: To be consistent with label.py,
214- # this is the bounding box for the text only, not including the background.
281+ self .tilegrid = displayio .TileGrid (
282+ self .bitmap ,
283+ pixel_shader = self .palette ,
284+ width = 1 ,
285+ height = 1 ,
286+ tile_width = box_x ,
287+ tile_height = box_y ,
288+ default_tile = 0 ,
289+ x = - self ._padding_left + x_offset ,
290+ y = label_position_yoffset - y_offset - self ._padding_top ,
291+ )
215292
216- self ._bounding_box = (
217- self .tilegrid .x ,
218- self .tilegrid .y ,
219- tight_box_x ,
220- tight_box_y ,
221- )
293+ # Clear out any items in the self Group, in case this is an update to the bitmap_label
294+ for item in self :
295+ self .pop (0 )
296+ self .append (self .tilegrid ) # add the bitmap's tilegrid to the group
297+
298+ # Update bounding_box values. Note: To be consistent with label.py,
299+ # this is the bounding box for the text only, not including the background.
300+ self ._bounding_box = (
301+ self .tilegrid .x ,
302+ self .tilegrid .y ,
303+ tight_box_x ,
304+ tight_box_y ,
305+ )
222306
223- self ._anchored_position = anchored_position
224- self .anchor_point = anchor_point
225307 self .anchored_position = (
226308 self ._anchored_position
227- ) # sets anchored_position with setter after bitmap is created
309+ ) # set the anchored_position with setter after bitmap is created, sets the x,y positions of the label
228310
229311 @staticmethod
230312 def _line_spacing_ypixels (font , line_spacing ):
@@ -240,7 +322,7 @@ def _text_bounding_box(self, text, font, line_spacing, background_tight=False):
240322 # descender, will depend upon font used
241323
242324 try :
243- self . _font .load_glyphs (text + glyphs )
325+ font .load_glyphs (text + glyphs )
244326 except AttributeError :
245327 # ignore if font does not have load_glyphs
246328 pass
@@ -434,9 +516,8 @@ def line_spacing(self):
434516
435517 @line_spacing .setter
436518 def line_spacing (self , new_line_spacing ):
437- raise RuntimeError (
438- "line_spacing is immutable for bitmap_label.py; use label.py for mutable line_spacing"
439- )
519+ self ._reset_text (line_spacing = new_line_spacing )
520+
440521
441522 @property
442523 def color (self ):
@@ -473,11 +554,10 @@ def text(self):
473554 """Text to displayed."""
474555 return self ._text
475556
476- @text .setter
557+ @text .setter # Cannot set color or background color with text setter, use separate setter
477558 def text (self , new_text ):
478- raise RuntimeError (
479- "text is immutable for bitmap_label.py; use label.py library for mutable text"
480- )
559+ self ._reset_text (text = new_text )
560+ print ('updated text: {}' .format (new_text ))
481561
482562 @property
483563 def font (self ):
@@ -486,9 +566,7 @@ def font(self):
486566
487567 @font .setter
488568 def font (self , new_font ):
489- raise RuntimeError (
490- "font is immutable for bitmap_label.py; use label.py library for mutable font"
491- )
569+ self ._reset_text (font = new_font )
492570
493571 @property
494572 def anchor_point (self ):
0 commit comments