mirror of
				https://github.com/RGBCube/serenity
				synced 2025-10-31 06:02:44 +00:00 
			
		
		
		
	LibGfx/JPEGXL: Support images with the have_crop option in FrameHeader
				
					
				
			This commit only allows us to read these values. The decoder will still output the image as if no cropping was requested.
This commit is contained in:
		
							parent
							
								
									a9620d8784
								
							
						
					
					
						commit
						70e4d3a9b6
					
				
					 1 changed files with 29 additions and 8 deletions
				
			
		|  | @ -681,6 +681,10 @@ struct FrameHeader { | |||
| 
 | ||||
|     u8 lf_level {}; | ||||
|     bool have_crop { false }; | ||||
|     i32 x0 {}; | ||||
|     i32 y0 {}; | ||||
|     u32 width {}; | ||||
|     u32 height {}; | ||||
| 
 | ||||
|     BlendingInfo blending_info {}; | ||||
|     FixedArray<BlendingInfo> ec_blending_info {}; | ||||
|  | @ -701,7 +705,9 @@ static int operator&(FrameHeader::Flags first, FrameHeader::Flags second) | |||
|     return static_cast<int>(first) & static_cast<int>(second); | ||||
| } | ||||
| 
 | ||||
| static ErrorOr<FrameHeader> read_frame_header(LittleEndianInputBitStream& stream, ImageMetadata const& metadata) | ||||
| static ErrorOr<FrameHeader> read_frame_header(LittleEndianInputBitStream& stream, | ||||
|     SizeHeader size_header, | ||||
|     ImageMetadata const& metadata) | ||||
| { | ||||
|     FrameHeader frame_header; | ||||
|     bool const all_default = TRY(stream.read_bit()); | ||||
|  | @ -744,15 +750,29 @@ static ErrorOr<FrameHeader> read_frame_header(LittleEndianInputBitStream& stream | |||
|         if (frame_header.frame_type != FrameHeader::FrameType::kLFFrame) | ||||
|             frame_header.have_crop = TRY(stream.read_bit()); | ||||
| 
 | ||||
|         if (frame_header.have_crop) | ||||
|             TODO(); | ||||
|         if (frame_header.have_crop) { | ||||
|             auto const read_crop_dimension = [&]() -> ErrorOr<u32> { | ||||
|                 return U32(TRY(stream.read_bits(8)), 256 + TRY(stream.read_bits(11)), 2304 + TRY(stream.read_bits(14)), 18688 + TRY(stream.read_bits(30))); | ||||
|             }; | ||||
| 
 | ||||
|             if (frame_header.frame_type != FrameHeader::FrameType::kReferenceOnly) { | ||||
|                 frame_header.x0 = unpack_signed(TRY(read_crop_dimension())); | ||||
|                 frame_header.y0 = unpack_signed(TRY(read_crop_dimension())); | ||||
|             } | ||||
| 
 | ||||
|             frame_header.width = TRY(read_crop_dimension()); | ||||
|             frame_header.height = TRY(read_crop_dimension()); | ||||
|         } | ||||
| 
 | ||||
|         bool const normal_frame = frame_header.frame_type == FrameHeader::FrameType::kRegularFrame | ||||
|             || frame_header.frame_type == FrameHeader::FrameType::kSkipProgressive; | ||||
| 
 | ||||
|         // FIXME: also consider "cropped" image of the dimension of the frame
 | ||||
|         VERIFY(!frame_header.have_crop); | ||||
|         bool const full_frame = !frame_header.have_crop; | ||||
|         // Let full_frame be true if and only if have_crop is false or if the frame area given
 | ||||
|         // by width and height and offsets x0 and y0 completely covers the image area.
 | ||||
|         bool const cover_image_area = frame_header.x0 <= 0 && frame_header.y0 <= 0 | ||||
|             && (frame_header.width + frame_header.x0 >= size_header.width) | ||||
|             && (frame_header.height + frame_header.y0 == size_header.height); | ||||
|         bool const full_frame = !frame_header.have_crop || cover_image_area; | ||||
| 
 | ||||
|         if (normal_frame) { | ||||
|             frame_header.blending_info = TRY(read_blending_info(stream, metadata, full_frame)); | ||||
|  | @ -2304,13 +2324,14 @@ static ErrorOr<Frame> read_frame(LittleEndianInputBitStream& stream, | |||
| 
 | ||||
|     Frame frame; | ||||
| 
 | ||||
|     frame.frame_header = TRY(read_frame_header(stream, metadata)); | ||||
|     frame.frame_header = TRY(read_frame_header(stream, size_header, metadata)); | ||||
| 
 | ||||
|     if (!frame.frame_header.have_crop) { | ||||
|         frame.width = size_header.width; | ||||
|         frame.height = size_header.height; | ||||
|     } else { | ||||
|         TODO(); | ||||
|         frame.width = frame.frame_header.width; | ||||
|         frame.height = frame.frame_header.height; | ||||
|     } | ||||
| 
 | ||||
|     if (frame.frame_header.upsampling > 1) { | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Lucas CHOLLET
						Lucas CHOLLET