1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

134

""" 

Manage figures for pyplot interface. 

""" 

 

import atexit 

import gc 

import sys 

 

 

class Gcf(object): 

""" 

Singleton to manage a set of integer-numbered figures. 

 

This class is never instantiated; it consists of two class 

attributes (a list and a dictionary), and a set of static 

methods that operate on those attributes, accessing them 

directly as class attributes. 

 

Attributes: 

 

*figs*: 

dictionary of the form {*num*: *manager*, ...} 

 

*_activeQue*: 

list of *managers*, with active one at the end 

 

""" 

_activeQue = [] 

figs = {} 

 

@classmethod 

def get_fig_manager(cls, num): 

""" 

If figure manager *num* exists, make it the active 

figure and return the manager; otherwise return *None*. 

""" 

manager = cls.figs.get(num, None) 

if manager is not None: 

cls.set_active(manager) 

return manager 

 

@classmethod 

def destroy(cls, num): 

""" 

Try to remove all traces of figure *num*. 

 

In the interactive backends, this is bound to the 

window "destroy" and "delete" events. 

""" 

if not cls.has_fignum(num): 

return 

manager = cls.figs[num] 

manager.canvas.mpl_disconnect(manager._cidgcf) 

cls._activeQue.remove(manager) 

del cls.figs[num] 

manager.destroy() 

gc.collect(1) 

 

@classmethod 

def destroy_fig(cls, fig): 

"*fig* is a Figure instance" 

num = next((manager.num for manager in cls.figs.values() 

if manager.canvas.figure == fig), None) 

if num is not None: 

cls.destroy(num) 

 

@classmethod 

def destroy_all(cls): 

# this is need to ensure that gc is available in corner cases 

# where modules are being torn down after install with easy_install 

import gc # noqa 

for manager in list(cls.figs.values()): 

manager.canvas.mpl_disconnect(manager._cidgcf) 

manager.destroy() 

 

cls._activeQue = [] 

cls.figs.clear() 

gc.collect(1) 

 

@classmethod 

def has_fignum(cls, num): 

""" 

Return *True* if figure *num* exists. 

""" 

return num in cls.figs 

 

@classmethod 

def get_all_fig_managers(cls): 

""" 

Return a list of figure managers. 

""" 

return list(cls.figs.values()) 

 

@classmethod 

def get_num_fig_managers(cls): 

""" 

Return the number of figures being managed. 

""" 

return len(cls.figs) 

 

@classmethod 

def get_active(cls): 

""" 

Return the manager of the active figure, or *None*. 

""" 

if len(cls._activeQue) == 0: 

return None 

else: 

return cls._activeQue[-1] 

 

@classmethod 

def set_active(cls, manager): 

""" 

Make the figure corresponding to *manager* the active one. 

""" 

oldQue = cls._activeQue[:] 

cls._activeQue = [] 

for m in oldQue: 

if m != manager: 

cls._activeQue.append(m) 

cls._activeQue.append(manager) 

cls.figs[manager.num] = manager 

 

@classmethod 

def draw_all(cls, force=False): 

""" 

Redraw all figures registered with the pyplot 

state machine. 

""" 

for f_mgr in cls.get_all_fig_managers(): 

if force or f_mgr.canvas.figure.stale: 

f_mgr.canvas.draw_idle() 

 

atexit.register(Gcf.destroy_all)