mirror of
https://github.com/opencv/opencv.git
synced 2026-07-29 15:23:05 +04:00
2ec6a6bb65
Added OnnxRuntime GPU wrapper #28588 ### Pull Request Readiness Checklist See details at https://github.com/opencv/opencv/wiki/How_to_contribute#making-a-good-pull-request - [x] I agree to contribute to the project under Apache 2 License. - [x] To the best of my knowledge, the proposed patch is not based on a code under GPL or another license that is incompatible with OpenCV - [x] The PR is proposed to the proper branch - [x] There is a reference to the original bug report and related work - [x] There is accuracy test, performance test and test data in opencv_extra repository, if applicable Patch to opencv_extra has the same branch name. - [x] The feature is well documented and sample code can be built with the project CMake
177 lines
5.2 KiB
Python
177 lines
5.2 KiB
Python
"""
|
|
This file is part of OpenCV project.
|
|
It is subject to the license terms in the LICENSE file found in the top-level directory
|
|
of this distribution and at http://opencv.org/license.html.
|
|
|
|
Copyright (C) 2025, Bigvision LLC.
|
|
|
|
|
|
This sample demonstrates super-resolution using the SeeMoreDetails model.
|
|
The model upscales images by 4x while enhancing details and reducing noise.
|
|
Supports image inputs only.
|
|
|
|
SeeMoreDetails Repo: https://github.com/eduardzamfir/seemoredetails
|
|
"""
|
|
|
|
import cv2 as cv
|
|
import argparse
|
|
import numpy as np
|
|
import os
|
|
from common import *
|
|
|
|
def get_args_parser(func_args):
|
|
backends = ("default", "openvino", "opencv", "vkcom", "cuda")
|
|
targets = (
|
|
"cpu",
|
|
"opencl",
|
|
"opencl_fp16",
|
|
"ncs2_vpu",
|
|
"hddl_vpu",
|
|
"vulkan",
|
|
"cuda",
|
|
"cuda_fp16",
|
|
)
|
|
|
|
parser = argparse.ArgumentParser(add_help=False)
|
|
parser.add_argument(
|
|
"--zoo",
|
|
default=os.path.join(os.path.dirname(os.path.abspath(__file__)), "models.yml"),
|
|
help="An optional path to file with preprocessing parameters.",
|
|
)
|
|
parser.add_argument(
|
|
"--input", help="Path to input image file.", default="chicky_512.png", required=False
|
|
)
|
|
parser.add_argument(
|
|
"--backend",
|
|
default="default",
|
|
type=str,
|
|
choices=backends,
|
|
help="Choose one of computation backends: "
|
|
"default: automatically (by default), "
|
|
"openvino: Intel's Deep Learning Inference Engine (https://software.intel.com/openvino-toolkit), "
|
|
"opencv: OpenCV implementation, "
|
|
"vkcom: VKCOM, "
|
|
"cuda: CUDA, "
|
|
"webnn: WebNN",
|
|
)
|
|
parser.add_argument(
|
|
"--target",
|
|
default="cpu",
|
|
type=str,
|
|
choices=targets,
|
|
help="Choose one of target computation devices: "
|
|
"cpu: CPU target (by default), "
|
|
"opencl: OpenCL, "
|
|
"opencl_fp16: OpenCL fp16 (half-float precision), "
|
|
"ncs2_vpu: NCS2 VPU, "
|
|
"hddl_vpu: HDDL VPU, "
|
|
"vulkan: Vulkan, "
|
|
"cuda: CUDA, "
|
|
"cuda_fp16: CUDA fp16 (half-float preprocess)",
|
|
)
|
|
|
|
args, _ = parser.parse_known_args()
|
|
|
|
model_name = "seemoredetails"
|
|
add_preproc_args(args.zoo, parser, "super_resolution", model_name)
|
|
|
|
parser = argparse.ArgumentParser(
|
|
parents=[parser],
|
|
description="""
|
|
To run:
|
|
Default image:
|
|
python super_resolution.py
|
|
Image processing:
|
|
python super_resolution.py --input=path/to/your/input/image.jpg
|
|
|
|
The model performs 4x super-resolution on input images.
|
|
""",
|
|
formatter_class=argparse.RawTextHelpFormatter,
|
|
)
|
|
return parser.parse_args(func_args)
|
|
|
|
def load_model(args):
|
|
"""Load the super-resolution model"""
|
|
try:
|
|
model_path = findModel(args.model, args.sha1)
|
|
net = cv.dnn.readNetFromONNX(model_path)
|
|
net.setPreferableBackend(get_backend_id(args.backend))
|
|
net.setPreferableTarget(get_target_id(args.target))
|
|
return net
|
|
except Exception as e:
|
|
print(f"Error loading model: {e}")
|
|
return None
|
|
|
|
def postprocess_output(output, args, original_shape=None):
|
|
"""Postprocess model output to displayable image"""
|
|
output = np.squeeze(output, axis=0)
|
|
output = np.clip(output, 0, 1)
|
|
output = np.transpose(output, (1, 2, 0))
|
|
output = (output * 255).astype(np.uint8)
|
|
|
|
output = cv.cvtColor(output, cv.COLOR_RGB2BGR)
|
|
|
|
if original_shape is not None:
|
|
target_height, target_width = original_shape
|
|
upscaled_height, upscaled_width = target_height * 4, target_width * 4
|
|
output = cv.resize(output, (upscaled_width, upscaled_height))
|
|
|
|
return output
|
|
|
|
def apply_super_resolution(net, image, args):
|
|
"""Apply super-resolution to a single image"""
|
|
original_shape = image.shape[:2]
|
|
|
|
blob = cv.dnn.blobFromImage(
|
|
image,
|
|
scalefactor=args.scale,
|
|
size=(args.width, args.height),
|
|
mean=args.mean,
|
|
swapRB=args.rgb,
|
|
crop=False,
|
|
)
|
|
|
|
net.setInput(blob)
|
|
t0 = cv.getTickCount()
|
|
output = net.forward()
|
|
t = (cv.getTickCount() - t0) / cv.getTickFrequency()
|
|
|
|
result = postprocess_output(output, args, original_shape)
|
|
|
|
label = "Inference time: %.2f ms" % (t * 1000.0)
|
|
cv.putText(result, label, (10, 30), cv.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
|
|
|
|
return result
|
|
|
|
def main(func_args=None):
|
|
args = get_args_parser(func_args)
|
|
|
|
net = load_model(args)
|
|
if net is None:
|
|
print("Failed to load model.")
|
|
return -1
|
|
|
|
input_path = cv.samples.findFile(args.input)
|
|
image = cv.imread(input_path)
|
|
if image is None:
|
|
print(f"Cannot load image: {input_path}")
|
|
return -1
|
|
|
|
print(f"Processing image: {input_path}")
|
|
result = apply_super_resolution(net, image, args)
|
|
|
|
cv.namedWindow("Input", cv.WINDOW_NORMAL)
|
|
cv.namedWindow("Super-Resolution Result", cv.WINDOW_NORMAL)
|
|
cv.imshow("Input", image)
|
|
cv.imshow("Super-Resolution Result", result)
|
|
print("Press 'q' to quit...")
|
|
while True:
|
|
key = cv.waitKey(0) & 0xFF
|
|
if key == ord("q"):
|
|
break
|
|
cv.destroyAllWindows()
|
|
return 0
|
|
|
|
if __name__ == "__main__":
|
|
main()
|