forked from eden-emu/eden
		
	gl_texture_cache: WIP texture rescale
This commit is contained in:
		
							parent
							
								
									ba18047e8d
								
							
						
					
					
						commit
						10e5065a5c
					
				
					 2 changed files with 69 additions and 3 deletions
				
			
		|  | @ -698,7 +698,10 @@ void Image::UploadMemory(const ImageBufferMap& map, | ||||||
| void Image::DownloadMemory(ImageBufferMap& map, | void Image::DownloadMemory(ImageBufferMap& map, | ||||||
|                            std::span<const VideoCommon::BufferImageCopy> copies) { |                            std::span<const VideoCommon::BufferImageCopy> copies) { | ||||||
|     glMemoryBarrier(GL_PIXEL_BUFFER_BARRIER_BIT); // TODO: Move this to its own API
 |     glMemoryBarrier(GL_PIXEL_BUFFER_BARRIER_BIT); // TODO: Move this to its own API
 | ||||||
| 
 |     const bool is_rescaled = True(flags & ImageFlagBits::Rescaled); | ||||||
|  |     if (is_rescaled) { | ||||||
|  |         ScaleDown(); | ||||||
|  |     } | ||||||
|     glBindBuffer(GL_PIXEL_PACK_BUFFER, map.buffer); |     glBindBuffer(GL_PIXEL_PACK_BUFFER, map.buffer); | ||||||
|     glPixelStorei(GL_PACK_ALIGNMENT, 1); |     glPixelStorei(GL_PACK_ALIGNMENT, 1); | ||||||
| 
 | 
 | ||||||
|  | @ -716,6 +719,9 @@ void Image::DownloadMemory(ImageBufferMap& map, | ||||||
|         } |         } | ||||||
|         CopyImageToBuffer(copy, map.offset); |         CopyImageToBuffer(copy, map.offset); | ||||||
|     } |     } | ||||||
|  |     if (is_rescaled) { | ||||||
|  |         ScaleUp(); | ||||||
|  |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| GLuint Image::StorageHandle() noexcept { | GLuint Image::StorageHandle() noexcept { | ||||||
|  | @ -849,12 +855,70 @@ void Image::CopyImageToBuffer(const VideoCommon::BufferImageCopy& copy, size_t b | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | void Image::Scale() { | ||||||
|  |     // TODO: Pass scaling factor?
 | ||||||
|  |     if (gl_format == 0 || gl_type == 0) { | ||||||
|  |         // compressed textures
 | ||||||
|  |         return; | ||||||
|  |     } | ||||||
|  |     if (info.type == ImageType::Linear) { | ||||||
|  |         UNIMPLEMENTED(); | ||||||
|  |         return; | ||||||
|  |     } | ||||||
|  |     GLint prev_draw_fbo; | ||||||
|  |     GLint prev_read_fbo; | ||||||
|  |     glGetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING, &prev_draw_fbo); | ||||||
|  |     glGetIntegerv(GL_READ_FRAMEBUFFER_BINDING, &prev_read_fbo); | ||||||
|  |     const GLenum attachment = [this] { | ||||||
|  |         switch (GetFormatType(info.format)) { | ||||||
|  |         case SurfaceType::ColorTexture: | ||||||
|  |             return GL_COLOR_ATTACHMENT0; | ||||||
|  |         case SurfaceType::Depth: | ||||||
|  |             return GL_DEPTH_ATTACHMENT; | ||||||
|  |         case SurfaceType::DepthStencil: | ||||||
|  |             return GL_DEPTH_STENCIL_ATTACHMENT; | ||||||
|  |         default: | ||||||
|  |             UNREACHABLE(); | ||||||
|  |             return GL_COLOR_ATTACHMENT0; | ||||||
|  |         } | ||||||
|  |     }(); | ||||||
|  |     const GLenum mask = [this] { | ||||||
|  |         switch (GetFormatType(info.format)) { | ||||||
|  |         case SurfaceType::ColorTexture: | ||||||
|  |             return GL_COLOR_BUFFER_BIT; | ||||||
|  |         case SurfaceType::Depth: | ||||||
|  |             return GL_DEPTH_BUFFER_BIT; | ||||||
|  |         case SurfaceType::DepthStencil: | ||||||
|  |             return GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT; | ||||||
|  |         default: | ||||||
|  |             UNREACHABLE(); | ||||||
|  |             return GL_COLOR_BUFFER_BIT; | ||||||
|  |         } | ||||||
|  |     }(); | ||||||
|  |     const GLenum filter = (mask & GL_COLOR_BUFFER_BIT) != 0 ? GL_LINEAR : GL_NEAREST; | ||||||
|  |     GLuint fbo_handle; | ||||||
|  |     glGenFramebuffers(1, &fbo_handle); | ||||||
|  |     glBindFramebuffer(GL_DRAW_FRAMEBUFFER, fbo_handle); | ||||||
|  |     glBindFramebuffer(GL_READ_FRAMEBUFFER, fbo_handle); | ||||||
|  |     glNamedFramebufferTexture(fbo_handle, attachment, texture.handle, 0); | ||||||
|  | 
 | ||||||
|  |     const size_t scaled_width = info.size.width; | ||||||
|  |     const size_t scaled_height = info.size.height * 2; | ||||||
|  |     glBlitNamedFramebuffer(fbo_handle, fbo_handle, 0, 0, info.size.width, info.size.height, 0, 0, | ||||||
|  |                            scaled_width, scaled_height, mask, filter); | ||||||
|  |     // TODO: resize texture?
 | ||||||
|  |     glCopyTextureSubImage3D(texture.handle, 0, 0, 0, 0, 0, 0, scaled_width, scaled_height / 2); | ||||||
|  |     // Restore previous framebuffers
 | ||||||
|  |     glBindFramebuffer(GL_DRAW_FRAMEBUFFER, prev_draw_fbo); | ||||||
|  |     glBindFramebuffer(GL_READ_FRAMEBUFFER, prev_read_fbo); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| bool Image::ScaleUp() { | bool Image::ScaleUp() { | ||||||
|     if (True(flags & ImageFlagBits::Rescaled)) { |     if (True(flags & ImageFlagBits::Rescaled)) { | ||||||
|         return false; |         return false; | ||||||
|     } |     } | ||||||
|     flags |= ImageFlagBits::Rescaled; |     flags |= ImageFlagBits::Rescaled; | ||||||
|     UNIMPLEMENTED(); |     Scale(); | ||||||
|     return true; |     return true; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | @ -863,7 +927,7 @@ bool Image::ScaleDown() { | ||||||
|         return false; |         return false; | ||||||
|     } |     } | ||||||
|     flags &= ~ImageFlagBits::Rescaled; |     flags &= ~ImageFlagBits::Rescaled; | ||||||
|     UNIMPLEMENTED(); |     Scale(); | ||||||
|     return true; |     return true; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -198,6 +198,8 @@ private: | ||||||
| 
 | 
 | ||||||
|     void CopyImageToBuffer(const VideoCommon::BufferImageCopy& copy, size_t buffer_offset); |     void CopyImageToBuffer(const VideoCommon::BufferImageCopy& copy, size_t buffer_offset); | ||||||
| 
 | 
 | ||||||
|  |     void Scale(); | ||||||
|  | 
 | ||||||
|     OGLTexture texture; |     OGLTexture texture; | ||||||
|     OGLTextureView store_view; |     OGLTextureView store_view; | ||||||
|     GLenum gl_internal_format = GL_NONE; |     GLenum gl_internal_format = GL_NONE; | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 ameerj
						ameerj