@@ -145,8 +145,17 @@ impl<T: Data> Widget<T> for Image {
145
145
) -> Size {
146
146
bc. debug_check ( "Image" ) ;
147
147
148
- if bc. is_width_bounded ( ) {
149
- bc. max ( )
148
+ // If either the width or height is constrained calculate a value so that the image fits
149
+ // in the size exactly. If it is unconstrained by both width and height take the size of
150
+ // the image.
151
+ let max = bc. max ( ) ;
152
+ let image_size = self . image_data . size ( ) ;
153
+ if bc. is_width_bounded ( ) && !bc. is_height_bounded ( ) {
154
+ let ratio = max. width / image_size. width ;
155
+ Size :: new ( max. width , ratio * image_size. height )
156
+ } else if bc. is_height_bounded ( ) && !bc. is_width_bounded ( ) {
157
+ let ratio = max. height / image_size. height ;
158
+ Size :: new ( ratio * image_size. width , max. height )
150
159
} else {
151
160
bc. constrain ( self . image_data . size ( ) )
152
161
}
@@ -317,4 +326,60 @@ mod tests {
317
326
} ,
318
327
) ;
319
328
}
329
+
330
+ #[ test]
331
+ fn width_bound_layout ( ) {
332
+ use crate :: {
333
+ tests:: harness:: Harness ,
334
+ widget:: { Container , Scroll } ,
335
+ WidgetExt , WidgetId ,
336
+ } ;
337
+ use float_cmp:: approx_eq;
338
+
339
+ let id_1 = WidgetId :: next ( ) ;
340
+ let image_data = ImageBuf :: from_raw (
341
+ vec ! [ 255 , 255 , 255 , 0 , 0 , 0 , 0 , 0 , 0 , 255 , 255 , 255 ] ,
342
+ ImageFormat :: Rgb ,
343
+ 2 ,
344
+ 2 ,
345
+ ) ;
346
+
347
+ let image_widget =
348
+ Scroll :: new ( Container :: new ( Image :: new ( image_data) ) . with_id ( id_1) ) . vertical ( ) ;
349
+
350
+ Harness :: create_simple ( true , image_widget, |harness| {
351
+ harness. send_initial_events ( ) ;
352
+ harness. just_layout ( ) ;
353
+ let state = harness. get_state ( id_1) ;
354
+ assert ! ( approx_eq!( f64 , state. layout_rect( ) . x1, 400.0 ) ) ;
355
+ } )
356
+ }
357
+
358
+ #[ test]
359
+ fn height_bound_layout ( ) {
360
+ use crate :: {
361
+ tests:: harness:: Harness ,
362
+ widget:: { Container , Scroll } ,
363
+ WidgetExt , WidgetId ,
364
+ } ;
365
+ use float_cmp:: approx_eq;
366
+
367
+ let id_1 = WidgetId :: next ( ) ;
368
+ let image_data = ImageBuf :: from_raw (
369
+ vec ! [ 255 , 255 , 255 , 0 , 0 , 0 , 0 , 0 , 0 , 255 , 255 , 255 ] ,
370
+ ImageFormat :: Rgb ,
371
+ 2 ,
372
+ 2 ,
373
+ ) ;
374
+
375
+ let image_widget =
376
+ Scroll :: new ( Container :: new ( Image :: new ( image_data) ) . with_id ( id_1) ) . horizontal ( ) ;
377
+
378
+ Harness :: create_simple ( true , image_widget, |harness| {
379
+ harness. send_initial_events ( ) ;
380
+ harness. just_layout ( ) ;
381
+ let state = harness. get_state ( id_1) ;
382
+ assert ! ( approx_eq!( f64 , state. layout_rect( ) . x1, 400.0 ) ) ;
383
+ } )
384
+ }
320
385
}
0 commit comments