@@ -95,13 +95,14 @@ GuideColoursteps <- ggproto(
95
95
96
96
extract_key = function (scale , aesthetic , even.steps , ... ) {
97
97
98
- breaks <- scale $ get_breaks()
98
+ orig_breaks <- scale $ get_breaks()
99
+ is_missing <- which(is.na(orig_breaks ))
99
100
100
- if (! (even.steps || ! is.numeric(breaks ))) {
101
+ if (! (even.steps || ! is.numeric(orig_breaks ))) {
101
102
return (Guide $ extract_key(scale , aesthetic ))
102
103
}
103
104
104
- parsed <- parse_binned_breaks(scale , breaks )
105
+ parsed <- parse_binned_breaks(scale , orig_breaks )
105
106
if (is.null(parsed )) {
106
107
return (parsed )
107
108
}
@@ -114,7 +115,13 @@ GuideColoursteps <- ggproto(
114
115
} else {
115
116
key $ .value <- breaks
116
117
}
117
- key $ .label <- scale $ get_labels(breaks )
118
+
119
+ orig_labels <- NULL
120
+ if (length(is_missing ) > 0 ) {
121
+ is_missing <- is_missing [1 ]
122
+ orig_labels <- scale $ get_labels(orig_breaks )[match(breaks , orig_breaks )]
123
+ }
124
+ key $ .label <- orig_labels %|| % scale $ get_labels(breaks )
118
125
119
126
if (breaks [1 ] %in% limits ) {
120
127
key $ .value <- key $ .value - 1L
@@ -123,6 +130,20 @@ GuideColoursteps <- ggproto(
123
130
if (breaks [length(breaks )] %in% limits ) {
124
131
key [[1 ]][nrow(key )] <- NA
125
132
}
133
+
134
+ if (length(is_missing ) > 0 ) {
135
+ missing <- data_frame0(
136
+ !! aesthetic : = scale $ map(orig_breaks [is_missing ]),
137
+ .value = orig_breaks [is_missing ],
138
+ .label = scale $ get_labels(orig_breaks )[is_missing ]
139
+ )
140
+ if (is_missing == 1 ) {
141
+ key <- vec_c(missing , key )
142
+ } else {
143
+ key <- vec_c(key , missing )
144
+ }
145
+ }
146
+
126
147
# To avoid having to recalculate these variables in other methods, we
127
148
# attach the parsed values as attributes. It might not be very elegant,
128
149
# but it works.
@@ -170,21 +191,34 @@ GuideColoursteps <- ggproto(
170
191
show.limits <- FALSE
171
192
}
172
193
194
+ key <- params $ key
173
195
if (show.limits ) {
174
- key <- params $ key
196
+ # Separate NA-breaks from proper breaks
197
+ missing <- vec_slice(key , is.na(key $ .value ))
198
+ key <- vec_slice(key , ! is.na(key $ .value ))
199
+
200
+ # Add extra top and bottom rows for limits
175
201
limits <- attr(key , " parsed" )$ limits %|| % scale $ get_limits()
176
202
key <- key [c(NA , seq_len(nrow(key )), NA ), , drop = FALSE ]
177
203
n <- nrow(key )
178
204
key $ .value [c(1 , n )] <- range(params $ decor $ min , params $ decor $ max )
179
205
key $ .label [c(1 , n )] <- scale $ get_labels(limits )
206
+
207
+ # Remove duplicates when e.g. outer breaks are included in limits
180
208
if (key $ .value [1 ] == key $ .value [2 ]) {
181
209
key <- vec_slice(key , - 1 )
182
210
n <- n - 1
183
211
}
184
212
if (key $ .value [n - 1 ] == key $ .value [n ]) {
185
213
key <- vec_slice(key , - n )
186
214
}
187
- params $ key <- key
215
+
216
+ # Reintroduce NA-breaks
217
+ if (is.na(params $ key $ .value [1 ])) {
218
+ key <- vec_c(missing , key )
219
+ } else {
220
+ key <- vec_c(key , missing )
221
+ }
188
222
}
189
223
190
224
params $ title <- scale $ make_title(
@@ -195,11 +229,15 @@ GuideColoursteps <- ggproto(
195
229
if (params $ reverse ) {
196
230
limits <- rev(limits )
197
231
}
198
- params $ key $ .value <- rescale(params $ key $ .value , from = limits )
199
- params $ decor $ min <- rescale(params $ decor $ min , from = limits )
200
- params $ decor $ max <- rescale(params $ decor $ max , from = limits )
201
- params $ key <-
202
- vec_slice(params $ key , ! is.na(oob_censor_any(params $ key $ .value )))
232
+ key $ .value <- rescale(key $ .value , from = limits )
233
+ params $ decor $ min <- rescale(params $ decor $ min , from = limits )
234
+ params $ decor $ max <- rescale(params $ decor $ max , from = limits )
235
+
236
+ keep <- ! is.na(oob_censor_any(key $ .value ))
237
+ if (! is.na(scale $ na.value %|| % NA )) {
238
+ keep <- keep | is.na(key $ .value ) & ! is.na(key [[params $ aesthetic ]])
239
+ }
240
+ params $ key <- vec_slice(key , keep )
203
241
params
204
242
},
205
243
0 commit comments