Coverage for /home/pi/Software/model-railway-signalling/model_railway_signals/editor/objects/objects_textboxes.py: 100%

61 statements  

« prev     ^ index     » next       coverage.py v7.2.7, created at 2024-04-10 15:08 +0100

1#------------------------------------------------------------------------------------ 

2# This module contains all the functions for managing Text box objects 

3#------------------------------------------------------------------------------------ 

4# 

5# External API functions intended for use by other editor modules:  

6# create_textbox() - Create a default line object on the schematic 

7# delete_textbox(object_id) - Hard Delete an object when deleted from the schematic 

8# paste_textbox(object) - Paste a copy of an object to create a new one (returns new object_id) 

9# delete_textbox_object(object_id) - Soft delete the drawing object (prior to recreating) 

10# redraw_textbox_object(object_id) - Redraw the object on the canvas following an update 

11# default_textbox_object - The dictionary of default values for the object 

12# 

13# Makes the following external API calls to other editor modules: 

14# objects_common.set_bbox - to create/update the boundary box for the schematic object 

15# objects_common.find_initial_canvas_position - to find the next 'free' canvas position 

16#  

17# Accesses the following external editor objects directly: 

18# objects_common.schematic_objects - the master dictionary of Schematic Objects 

19# objects_common.default_object - The common dictionary element for all objects 

20# objects_common.object_type - The Enumeration of supported objects 

21# objects_common.canvas - Reference to the Tkinter drawing canvas 

22# 

23#------------------------------------------------------------------------------------ 

24 

25import uuid 

26import copy 

27import tkinter as Tk 

28 

29from . import objects_common 

30 

31#------------------------------------------------------------------------------------ 

32# Default Text Box Objects (i.e. state at creation) 

33#------------------------------------------------------------------------------------ 

34 

35default_textbox_object = copy.deepcopy(objects_common.default_object) 

36default_textbox_object["item"] = objects_common.object_type.textbox 

37default_textbox_object["text"] = "Text" 

38default_textbox_object["colour"] = "black" 

39default_textbox_object["justify"] = 2 ## 1=Left, 2=Center, 3=right 

40default_textbox_object["background"] = "grey85" 

41default_textbox_object["font"] = "Courier" 

42default_textbox_object["fontsize"] = 10 

43default_textbox_object["fontstyle"] = "" 

44default_textbox_object["border"] = 0 

45 

46#------------------------------------------------------------------------------------ 

47# Function to to update a text box object following a configuration change 

48#------------------------------------------------------------------------------------ 

49 

50def update_textbox(object_id, new_object_configuration): 

51 # Delete the existing object, copy across the new config and redraw 

52 delete_textbox_object(object_id) 

53 objects_common.schematic_objects[object_id] = copy.deepcopy(new_object_configuration) 

54 redraw_textbox_object(object_id) 

55 return() 

56 

57#------------------------------------------------------------------------------------ 

58# Function to re-draw a text box object on the schematic. Called when the object 

59# is first created or after the object attributes have been updated. 

60#------------------------------------------------------------------------------------ 

61 

62def redraw_textbox_object(object_id): 

63 x1 = objects_common.schematic_objects[object_id]["posx"] 

64 y1 = objects_common.schematic_objects[object_id]["posy"] 

65 colour = objects_common.schematic_objects[object_id]["colour"] 

66 background = objects_common.schematic_objects[object_id]["background"] 

67 font = (objects_common.schematic_objects[object_id]["font"], 

68 objects_common.schematic_objects[object_id]["fontsize"], 

69 objects_common.schematic_objects[object_id]["fontstyle"]) 

70 text = objects_common.schematic_objects[object_id]["text"] 

71 width = objects_common.schematic_objects[object_id]["border"] 

72 # Create the textbox, justifying the text as required 

73 if objects_common.schematic_objects[object_id]["justify"] == 1: justify=Tk.LEFT 

74 elif objects_common.schematic_objects[object_id]["justify"] == 2: justify=Tk.CENTER 

75 elif objects_common.schematic_objects[object_id]["justify"] == 3: justify=Tk.RIGHT 

76 text_box = objects_common.canvas.create_text(x1,y1,fill=colour,text=text,tags=str(object_id),justify=justify,font=font) 

77 # find the boundary box and create the rectangle for the background 

78 bbox = objects_common.canvas.bbox(text_box) 

79 rectangle = objects_common.canvas.create_rectangle(bbox[0]-3, bbox[1]-3, bbox[2]+3, bbox[3]+2, 

80 width=width, tags=str(object_id), fill=background, outline=colour) 

81 # Raise the text item to be in front of the rectangle item 

82 objects_common.canvas.tag_raise(text_box, rectangle) 

83 # Store the reference for the the Tkinter drawing objects 

84 objects_common.schematic_objects[object_id]["tags"] = str(object_id) 

85 # Create/update the selection rectangle for the Text box 

86 objects_common.set_bbox (object_id, objects_common.canvas.bbox(str(object_id))) 

87 return() 

88 

89#------------------------------------------------------------------------------------ 

90# Function to Create a new default Text Box (and draw it on the canvas) 

91#------------------------------------------------------------------------------------ 

92 

93def create_textbox(): 

94 # Generate a new object from the default configuration with a new UUID 

95 # Note that we don't need to assign the 'itemID' as textboxes are just 

96 # for annotating the schematic (not used in layout configuration/automation) 

97 object_id = str(uuid.uuid4()) 

98 objects_common.schematic_objects[object_id] = copy.deepcopy(default_textbox_object) 

99 # Find the initial canvas position 

100 x, y = objects_common.find_initial_canvas_position() 

101 # Add the specific elements for this particular instance of the object 

102 objects_common.schematic_objects[object_id]["posx"] = x 

103 objects_common.schematic_objects[object_id]["posy"] = y 

104 # Draw the text box on the canvas 

105 redraw_textbox_object(object_id) 

106 return(object_id) 

107 

108#------------------------------------------------------------------------------------ 

109# Function to paste a copy of an existing text box - returns the new Object ID 

110#------------------------------------------------------------------------------------ 

111 

112def paste_textbox(object_to_paste, deltax:int, deltay:int): 

113 # Create a new UUID for the pasted object 

114 new_object_id = str(uuid.uuid4()) 

115 objects_common.schematic_objects[new_object_id] = copy.deepcopy(object_to_paste) 

116 # Set the position for the "pasted" object (offset from the original position) 

117 objects_common.schematic_objects[new_object_id]["posx"] += deltax 

118 objects_common.schematic_objects[new_object_id]["posy"] += deltay 

119 # Set the Boundary box for the new object to None so it gets created on re-draw 

120 objects_common.schematic_objects[new_object_id]["bbox"] = None 

121 # Draw the new object 

122 redraw_textbox_object(new_object_id) 

123 return(new_object_id) 

124 

125#------------------------------------------------------------------------------------ 

126# Function to "soft delete" the object from the canvas - Primarily used to 

127# delete the textbox in its current configuration prior to re-creating in its 

128# new configuration - also called as part of a hard delete (below). 

129#------------------------------------------------------------------------------------ 

130 

131def delete_textbox_object(object_id): 

132 # Delete the tkinter drawing objects associated with the object 

133 objects_common.canvas.delete(objects_common.schematic_objects[object_id]["tags"]) 

134 return() 

135 

136#------------------------------------------------------------------------------------ 

137# Function to 'hard delete' a text box object (drawing objects and the main 

138# dictionary entry). Function called when object is deleted from the schematic. 

139#------------------------------------------------------------------------------------ 

140 

141def delete_textbox(object_id): 

142 # Soft delete the associated library objects from the canvas 

143 delete_textbox_object(object_id) 

144 # "Hard Delete" the selected object - deleting the boundary box rectangle and deleting 

145 # the object from the dictionary of schematic objects 

146 objects_common.canvas.delete(objects_common.schematic_objects[object_id]["bbox"]) 

147 del objects_common.schematic_objects[object_id] 

148 return() 

149 

150####################################################################################