PyPatchMatch 1.0.1__tar.gz → 2.0.0b1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. pypatchmatch-2.0.0b1/CMakeLists.txt +63 -0
  2. pypatchmatch-2.0.0b1/PKG-INFO +118 -0
  3. pypatchmatch-2.0.0b1/README.md +96 -0
  4. pypatchmatch-2.0.0b1/examples/images/forest_pruned.bmp +0 -0
  5. pypatchmatch-2.0.0b1/patchmatch/__init__.py +19 -0
  6. pypatchmatch-2.0.0b1/patchmatch/_lib.py +124 -0
  7. pypatchmatch-2.0.0b1/patchmatch/_version.py +24 -0
  8. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/inpaint.cpp +8 -3
  9. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/masked_image.cpp +0 -1
  10. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/nnf.cpp +7 -6
  11. pypatchmatch-2.0.0b1/patchmatch/patch_match.py +183 -0
  12. pypatchmatch-2.0.0b1/patchmatch/py.typed +0 -0
  13. pypatchmatch-2.0.0b1/pyproject.toml +105 -0
  14. pypatchmatch-2.0.0b1/scripts/build_opencv.py +120 -0
  15. pypatchmatch-2.0.0b1/tests/test_e2e.py +128 -0
  16. pypatchmatch-2.0.0b1/tests/test_patch_match.py +317 -0
  17. PyPatchMatch-1.0.1/PKG-INFO +0 -103
  18. PyPatchMatch-1.0.1/PyPatchMatch.egg-info/PKG-INFO +0 -103
  19. PyPatchMatch-1.0.1/PyPatchMatch.egg-info/SOURCES.txt +0 -20
  20. PyPatchMatch-1.0.1/PyPatchMatch.egg-info/dependency_links.txt +0 -1
  21. PyPatchMatch-1.0.1/PyPatchMatch.egg-info/requires.txt +0 -28
  22. PyPatchMatch-1.0.1/PyPatchMatch.egg-info/top_level.txt +0 -1
  23. PyPatchMatch-1.0.1/README.md +0 -67
  24. PyPatchMatch-1.0.1/patchmatch/Makefile +0 -60
  25. PyPatchMatch-1.0.1/patchmatch/__init__.py +0 -3
  26. PyPatchMatch-1.0.1/patchmatch/patch_match.py +0 -381
  27. PyPatchMatch-1.0.1/patchmatch/travis.sh +0 -9
  28. PyPatchMatch-1.0.1/pyproject.toml +0 -71
  29. PyPatchMatch-1.0.1/setup.cfg +0 -4
  30. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/LICENSE +0 -0
  31. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/inpaint.h +0 -0
  32. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/masked_image.h +0 -0
  33. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/nnf.h +0 -0
  34. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/pyinterface.cpp +0 -0
  35. {PyPatchMatch-1.0.1 → pypatchmatch-2.0.0b1}/patchmatch/csrc/pyinterface.h +0 -0
@@ -0,0 +1,63 @@
1
+ cmake_minimum_required(VERSION 3.21)
2
+ project(patchmatch LANGUAGES CXX)
3
+
4
+ option(PATCHMATCH_BUILD_EXAMPLES "Build the C++ example (requires OpenCV imgcodecs)" OFF)
5
+ option(PATCHMATCH_WITH_HIGHGUI "Enable the debug visualization of Inpainting::run (requires OpenCV highgui)" OFF)
6
+ option(PATCHMATCH_FAST_MATH "Compile with fast-math optimizations" ON)
7
+
8
+ if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
9
+ set(CMAKE_BUILD_TYPE Release CACHE STRING "Build type" FORCE)
10
+ endif()
11
+
12
+ set(CMAKE_CXX_STANDARD 17)
13
+ set(CMAKE_CXX_STANDARD_REQUIRED ON)
14
+ set(CMAKE_CXX_EXTENSIONS OFF)
15
+ set(CMAKE_WINDOWS_EXPORT_ALL_SYMBOLS ON)
16
+
17
+ set(PATCHMATCH_OPENCV_COMPONENTS core)
18
+ if(PATCHMATCH_WITH_HIGHGUI)
19
+ list(APPEND PATCHMATCH_OPENCV_COMPONENTS imgproc highgui)
20
+ endif()
21
+ if(PATCHMATCH_BUILD_EXAMPLES)
22
+ list(APPEND PATCHMATCH_OPENCV_COMPONENTS imgcodecs)
23
+ endif()
24
+ find_package(OpenCV REQUIRED COMPONENTS ${PATCHMATCH_OPENCV_COMPONENTS})
25
+
26
+ add_library(patchmatch SHARED
27
+ patchmatch/csrc/inpaint.cpp
28
+ patchmatch/csrc/masked_image.cpp
29
+ patchmatch/csrc/nnf.cpp
30
+ patchmatch/csrc/pyinterface.cpp
31
+ )
32
+ target_include_directories(patchmatch PUBLIC patchmatch/csrc)
33
+ target_link_libraries(patchmatch PUBLIC opencv_core)
34
+
35
+ if(MSVC AND NOT OpenCV_SHARED)
36
+ # A static OpenCV (as built by scripts/build_opencv.py) uses the static MSVC runtime.
37
+ set_property(TARGET patchmatch PROPERTY
38
+ MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>")
39
+ endif()
40
+
41
+ if(PATCHMATCH_FAST_MATH)
42
+ if(MSVC)
43
+ target_compile_options(patchmatch PRIVATE /fp:fast)
44
+ else()
45
+ target_compile_options(patchmatch PRIVATE -ffast-math)
46
+ endif()
47
+ endif()
48
+
49
+ if(PATCHMATCH_WITH_HIGHGUI)
50
+ target_compile_definitions(patchmatch PRIVATE PATCHMATCH_WITH_HIGHGUI)
51
+ target_link_libraries(patchmatch PRIVATE opencv_imgproc opencv_highgui)
52
+ endif()
53
+
54
+ if(PATCHMATCH_BUILD_EXAMPLES)
55
+ add_executable(cpp_example examples/cpp_example.cpp)
56
+ target_link_libraries(cpp_example PRIVATE patchmatch opencv_imgcodecs)
57
+ endif()
58
+
59
+ # The Python package loads the library via ctypes from its own directory.
60
+ install(TARGETS patchmatch
61
+ LIBRARY DESTINATION patchmatch
62
+ RUNTIME DESTINATION patchmatch
63
+ )
@@ -0,0 +1,118 @@
1
+ Metadata-Version: 2.4
2
+ Name: PyPatchMatch
3
+ Version: 2.0.0b1
4
+ Summary: This library implements the PatchMatch based inpainting algorithm.
5
+ Author-Email: The InvokeAI Project <lincoln.stein@gmail.com>, Kyle Schouviller <kyle0654@hotmail.com>, Matthias Wild <mauwii@outlook.de>, Younesse ANDAM <younesse.andam@gmail.com>
6
+ License-Expression: MIT
7
+ License-File: LICENSE
8
+ Classifier: Programming Language :: C++
9
+ Classifier: Programming Language :: Python :: 3
10
+ Classifier: Programming Language :: Python :: 3.10
11
+ Classifier: Programming Language :: Python :: 3.11
12
+ Classifier: Programming Language :: Python :: 3.12
13
+ Classifier: Programming Language :: Python :: 3.13
14
+ Classifier: Programming Language :: Python :: 3.14
15
+ Classifier: Topic :: Multimedia :: Graphics
16
+ Classifier: Topic :: Scientific/Engineering :: Image Processing
17
+ Project-URL: Source Code, https://github.com/mauwii/PyPatchMatch
18
+ Requires-Python: >=3.10
19
+ Requires-Dist: numpy
20
+ Requires-Dist: pillow
21
+ Description-Content-Type: text/markdown
22
+
23
+ # PatchMatch based Inpainting
24
+
25
+ [![License: MIT](https://img.shields.io/badge/License-MIT-blueviolet.svg)](https://github.com/mauwii/PyPatchMatch/blob/main/LICENSE)
26
+ [![PyPI](https://img.shields.io/pypi/v/PyPatchMatch)](https://pypi.org/project/PyPatchMatch/)
27
+ [![Downloads](https://static.pepy.tech/badge/pypatchmatch)](https://pepy.tech/project/pypatchmatch)
28
+ [![Ruff](https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json)](https://github.com/astral-sh/ruff)
29
+
30
+ This library implements the PatchMatch based inpainting algorithm. It provides both C++
31
+ and Python interfaces. This implementation is heavily based on the implementation by
32
+ Younesse ANDAM: [younesse-cv/PatchMatch](https://github.com/younesse-cv/PatchMatch),
33
+ with some bug fixes, and updates.
34
+
35
+ ## Installation
36
+
37
+ ```sh
38
+ pip install PyPatchMatch
39
+ ```
40
+
41
+ Wheels for Linux, macOS and Windows ship the compiled library including the required
42
+ OpenCV runtime, so no compiler or OpenCV installation is needed. On other platforms pip
43
+ builds from the source distribution, which requires a C++17 compiler, CMake and the
44
+ OpenCV development files (e.g. `apt install libopencv-dev` or `brew install opencv`).
45
+
46
+ ## Usage
47
+
48
+ Python (see [examples/py_example.py](examples/py_example.py)):
49
+
50
+ ```python
51
+ import patchmatch
52
+
53
+ image = ... # HxWx3 uint8 numpy array or PIL image
54
+ mask = ... # HxW uint8 or bool numpy array or PIL image, non-zero marks the holes
55
+ result = patchmatch.inpaint(image, mask, patch_size=3)
56
+ ```
57
+
58
+ The mask must have the same height and width as the image. If `mask` is omitted, all
59
+ pure white pixels are treated as holes.
60
+ `patchmatch.patchmatch_available` tells whether the native library could be loaded.
61
+ The previous import path `from patchmatch import patch_match` keeps working.
62
+
63
+ C++ (see [examples/cpp_example.cpp](examples/cpp_example.cpp), build and run it with
64
+ [examples/cpp_example_run.sh](examples/cpp_example_run.sh)):
65
+
66
+ ```cpp
67
+ #include "inpaint.h"
68
+
69
+ int main() {
70
+ cv::Mat image = ...;
71
+ cv::Mat mask = ...;
72
+
73
+ auto metric = PatchSSDDistanceMetric(5);
74
+ cv::Mat result = Inpainting(image, mask, &metric).run();
75
+ }
76
+ ```
77
+
78
+ The library is built with CMake; `PATCHMATCH_BUILD_EXAMPLES` builds the example and
79
+ `PATCHMATCH_WITH_HIGHGUI` enables the debug visualization of `Inpainting::run`.
80
+
81
+ ## Development
82
+
83
+ The project is managed with [uv](https://docs.astral.sh/uv/):
84
+
85
+ ```sh
86
+ uv sync # create .venv, build the library, install dev deps
87
+ uv run pre-commit install # enable ruff and the other hooks on commit
88
+ uv run pytest # run the test suite
89
+ uv run pytest -m "not e2e" # only the fast unit tests
90
+ ```
91
+
92
+ Releases are published to PyPI by creating a GitHub release; the version is taken from
93
+ its tag (e.g. `v1.1.0`).
94
+
95
+ ## README and COPYRIGHT by Younesse ANDAM
96
+
97
+ @Author: Younesse ANDAM
98
+
99
+ @Contact: younesse.andam@gmail.com
100
+
101
+ Description:
102
+
103
+ This project is a personal implementation of an algorithm called PATCHMATCH
104
+ that restores missing areas in an image. The algorithm is presented in the following
105
+ paper PatchMatch A Randomized Correspondence Algorithm for Structural Image Editing by
106
+ C.Barnes, E.Shechtman, A.Finkelstein and Dan B.Goldman ACM Transactions on Graphics
107
+ (Proc. SIGGRAPH), vol.28, aug-2009
108
+
109
+ For more information please refer to
110
+ http://www.cs.princeton.edu/gfx/pubs/Barnes_2009_PAR/index.php
111
+
112
+ Copyright (c) 2010-2011
113
+
114
+ ## Requirements
115
+
116
+ To run the project you need to install Opencv library and link it to your project.
117
+ Opencv can be download it here
118
+ http://opencv.org/downloads.html
@@ -0,0 +1,96 @@
1
+ # PatchMatch based Inpainting
2
+
3
+ [![License: MIT](https://img.shields.io/badge/License-MIT-blueviolet.svg)](https://github.com/mauwii/PyPatchMatch/blob/main/LICENSE)
4
+ [![PyPI](https://img.shields.io/pypi/v/PyPatchMatch)](https://pypi.org/project/PyPatchMatch/)
5
+ [![Downloads](https://static.pepy.tech/badge/pypatchmatch)](https://pepy.tech/project/pypatchmatch)
6
+ [![Ruff](https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json)](https://github.com/astral-sh/ruff)
7
+
8
+ This library implements the PatchMatch based inpainting algorithm. It provides both C++
9
+ and Python interfaces. This implementation is heavily based on the implementation by
10
+ Younesse ANDAM: [younesse-cv/PatchMatch](https://github.com/younesse-cv/PatchMatch),
11
+ with some bug fixes, and updates.
12
+
13
+ ## Installation
14
+
15
+ ```sh
16
+ pip install PyPatchMatch
17
+ ```
18
+
19
+ Wheels for Linux, macOS and Windows ship the compiled library including the required
20
+ OpenCV runtime, so no compiler or OpenCV installation is needed. On other platforms pip
21
+ builds from the source distribution, which requires a C++17 compiler, CMake and the
22
+ OpenCV development files (e.g. `apt install libopencv-dev` or `brew install opencv`).
23
+
24
+ ## Usage
25
+
26
+ Python (see [examples/py_example.py](examples/py_example.py)):
27
+
28
+ ```python
29
+ import patchmatch
30
+
31
+ image = ... # HxWx3 uint8 numpy array or PIL image
32
+ mask = ... # HxW uint8 or bool numpy array or PIL image, non-zero marks the holes
33
+ result = patchmatch.inpaint(image, mask, patch_size=3)
34
+ ```
35
+
36
+ The mask must have the same height and width as the image. If `mask` is omitted, all
37
+ pure white pixels are treated as holes.
38
+ `patchmatch.patchmatch_available` tells whether the native library could be loaded.
39
+ The previous import path `from patchmatch import patch_match` keeps working.
40
+
41
+ C++ (see [examples/cpp_example.cpp](examples/cpp_example.cpp), build and run it with
42
+ [examples/cpp_example_run.sh](examples/cpp_example_run.sh)):
43
+
44
+ ```cpp
45
+ #include "inpaint.h"
46
+
47
+ int main() {
48
+ cv::Mat image = ...;
49
+ cv::Mat mask = ...;
50
+
51
+ auto metric = PatchSSDDistanceMetric(5);
52
+ cv::Mat result = Inpainting(image, mask, &metric).run();
53
+ }
54
+ ```
55
+
56
+ The library is built with CMake; `PATCHMATCH_BUILD_EXAMPLES` builds the example and
57
+ `PATCHMATCH_WITH_HIGHGUI` enables the debug visualization of `Inpainting::run`.
58
+
59
+ ## Development
60
+
61
+ The project is managed with [uv](https://docs.astral.sh/uv/):
62
+
63
+ ```sh
64
+ uv sync # create .venv, build the library, install dev deps
65
+ uv run pre-commit install # enable ruff and the other hooks on commit
66
+ uv run pytest # run the test suite
67
+ uv run pytest -m "not e2e" # only the fast unit tests
68
+ ```
69
+
70
+ Releases are published to PyPI by creating a GitHub release; the version is taken from
71
+ its tag (e.g. `v1.1.0`).
72
+
73
+ ## README and COPYRIGHT by Younesse ANDAM
74
+
75
+ @Author: Younesse ANDAM
76
+
77
+ @Contact: younesse.andam@gmail.com
78
+
79
+ Description:
80
+
81
+ This project is a personal implementation of an algorithm called PATCHMATCH
82
+ that restores missing areas in an image. The algorithm is presented in the following
83
+ paper PatchMatch A Randomized Correspondence Algorithm for Structural Image Editing by
84
+ C.Barnes, E.Shechtman, A.Finkelstein and Dan B.Goldman ACM Transactions on Graphics
85
+ (Proc. SIGGRAPH), vol.28, aug-2009
86
+
87
+ For more information please refer to
88
+ http://www.cs.princeton.edu/gfx/pubs/Barnes_2009_PAR/index.php
89
+
90
+ Copyright (c) 2010-2011
91
+
92
+ ## Requirements
93
+
94
+ To run the project you need to install Opencv library and link it to your project.
95
+ Opencv can be download it here
96
+ http://opencv.org/downloads.html
@@ -0,0 +1,19 @@
1
+ """PatchMatch based inpainting."""
2
+
3
+ from ._version import __version__
4
+ from .patch_match import (
5
+ inpaint,
6
+ inpaint_regularity,
7
+ patchmatch_available,
8
+ set_random_seed,
9
+ set_verbose,
10
+ )
11
+
12
+ __all__ = [
13
+ "__version__",
14
+ "inpaint",
15
+ "inpaint_regularity",
16
+ "patchmatch_available",
17
+ "set_random_seed",
18
+ "set_verbose",
19
+ ]
@@ -0,0 +1,124 @@
1
+ """ctypes bindings for the native patchmatch library."""
2
+
3
+ from __future__ import annotations
4
+
5
+ import ctypes
6
+ import sys
7
+ from pathlib import Path
8
+
9
+ import numpy as np
10
+
11
+ if sys.platform == "win32":
12
+ LIBRARY_NAME = "patchmatch.dll"
13
+ elif sys.platform == "darwin":
14
+ LIBRARY_NAME = "libpatchmatch.dylib"
15
+ else:
16
+ LIBRARY_NAME = "libpatchmatch.so"
17
+
18
+
19
+ class CShapeT(ctypes.Structure):
20
+ _fields_ = [
21
+ ("width", ctypes.c_int),
22
+ ("height", ctypes.c_int),
23
+ ("channels", ctypes.c_int),
24
+ ]
25
+
26
+
27
+ class CMatT(ctypes.Structure):
28
+ _fields_ = [
29
+ ("data_ptr", ctypes.c_void_p),
30
+ ("shape", CShapeT),
31
+ ("dtype", ctypes.c_int),
32
+ ]
33
+
34
+
35
+ # Order matches the PM_dtype_e enum in csrc/pyinterface.h.
36
+ _PYMAT_DTYPES = [
37
+ np.dtype(np.uint8),
38
+ np.dtype(np.int8),
39
+ np.dtype(np.uint16),
40
+ np.dtype(np.int16),
41
+ np.dtype(np.int32),
42
+ np.dtype(np.float32),
43
+ np.dtype(np.float64),
44
+ ]
45
+ _PYMAT_DTYPE_IDS = {dtype: i for i, dtype in enumerate(_PYMAT_DTYPES)}
46
+
47
+
48
+ def np_to_pymat(npmat: np.ndarray) -> CMatT:
49
+ """Wrap a contiguous HxWxC array without copying it."""
50
+ if npmat.ndim != 3:
51
+ raise ValueError(f"expected a 3-dimensional array, got {npmat.ndim} dims")
52
+ if not npmat.flags.c_contiguous:
53
+ raise ValueError("expected a C-contiguous array")
54
+ try:
55
+ dtype_id = _PYMAT_DTYPE_IDS[npmat.dtype]
56
+ except KeyError:
57
+ raise TypeError(f"unsupported dtype {npmat.dtype}") from None
58
+ height, width, channels = npmat.shape
59
+ return CMatT(
60
+ ctypes.c_void_p(npmat.ctypes.data),
61
+ CShapeT(width, height, channels),
62
+ dtype_id,
63
+ )
64
+
65
+
66
+ def pymat_to_np(pymat: CMatT) -> np.ndarray:
67
+ """Copy the data referenced by ``pymat`` into a new numpy array."""
68
+ dtype = _PYMAT_DTYPES[pymat.dtype]
69
+ shape = (pymat.shape.height, pymat.shape.width, pymat.shape.channels)
70
+ buffer = (ctypes.c_byte * (int(np.prod(shape)) * dtype.itemsize)).from_address(
71
+ pymat.data_ptr
72
+ )
73
+ return np.frombuffer(buffer, dtype=dtype).reshape(shape).copy()
74
+
75
+
76
+ def find_library() -> Path:
77
+ """Locate the shared library that is installed next to this package."""
78
+ package = sys.modules[__package__]
79
+ for directory in package.__path__:
80
+ candidate = Path(directory) / LIBRARY_NAME
81
+ if candidate.is_file():
82
+ return candidate
83
+ raise OSError(
84
+ f"{LIBRARY_NAME} not found in {list(package.__path__)}; "
85
+ "reinstall PyPatchMatch or build it from source with OpenCV available"
86
+ )
87
+
88
+
89
+ def load_library() -> ctypes.CDLL:
90
+ lib = ctypes.CDLL(str(find_library()))
91
+
92
+ lib.PM_set_random_seed.argtypes = [ctypes.c_uint]
93
+ lib.PM_set_random_seed.restype = None
94
+ lib.PM_set_verbose.argtypes = [ctypes.c_int]
95
+ lib.PM_set_verbose.restype = None
96
+ lib.PM_free_pymat.argtypes = [CMatT]
97
+ lib.PM_free_pymat.restype = None
98
+
99
+ lib.PM_inpaint.argtypes = [CMatT, CMatT, ctypes.c_int]
100
+ lib.PM_inpaint2.argtypes = [CMatT, CMatT, CMatT, ctypes.c_int]
101
+ lib.PM_inpaint_regularity.argtypes = [
102
+ CMatT,
103
+ CMatT,
104
+ CMatT,
105
+ ctypes.c_int,
106
+ ctypes.c_float,
107
+ ]
108
+ lib.PM_inpaint2_regularity.argtypes = [
109
+ CMatT,
110
+ CMatT,
111
+ CMatT,
112
+ CMatT,
113
+ ctypes.c_int,
114
+ ctypes.c_float,
115
+ ]
116
+ for func in (
117
+ lib.PM_inpaint,
118
+ lib.PM_inpaint2,
119
+ lib.PM_inpaint_regularity,
120
+ lib.PM_inpaint2_regularity,
121
+ ):
122
+ func.restype = CMatT
123
+
124
+ return lib
@@ -0,0 +1,24 @@
1
+ # file generated by vcs-versioning
2
+ # don't change, don't track in version control
3
+ from __future__ import annotations
4
+
5
+ __all__ = [
6
+ "__version__",
7
+ "__version_tuple__",
8
+ "version",
9
+ "version_tuple",
10
+ "__commit_id__",
11
+ "commit_id",
12
+ ]
13
+
14
+ version: str
15
+ __version__: str
16
+ __version_tuple__: tuple[int | str, ...]
17
+ version_tuple: tuple[int | str, ...]
18
+ commit_id: str | None
19
+ __commit_id__: str | None
20
+
21
+ __version__ = version = '2.0.0b1'
22
+ __version_tuple__ = version_tuple = (2, 0, 0, 'b1')
23
+
24
+ __commit_id__ = commit_id = 'g987b0e524'
@@ -1,8 +1,9 @@
1
1
  #include <algorithm>
2
2
  #include <iostream>
3
- #include <opencv2/imgcodecs.hpp>
3
+ #ifdef PATCHMATCH_WITH_HIGHGUI
4
4
  #include <opencv2/imgproc.hpp>
5
5
  #include <opencv2/highgui.hpp>
6
+ #endif
6
7
 
7
8
  #include "inpaint.h"
8
9
 
@@ -48,13 +49,13 @@ namespace
48
49
  */
49
50
 
50
51
  Inpainting::Inpainting(cv::Mat image, cv::Mat mask, const PatchDistanceMetric *metric)
51
- : m_initial(image, mask), m_distance_metric(metric), m_pyramid(), m_source2target(), m_target2source()
52
+ : m_initial(image, mask), m_pyramid(), m_source2target(), m_target2source(), m_distance_metric(metric)
52
53
  {
53
54
  _initialize_pyramid();
54
55
  }
55
56
 
56
57
  Inpainting::Inpainting(cv::Mat image, cv::Mat mask, cv::Mat global_mask, const PatchDistanceMetric *metric)
57
- : m_initial(image, mask, global_mask), m_distance_metric(metric), m_pyramid(), m_source2target(), m_target2source()
58
+ : m_initial(image, mask, global_mask), m_pyramid(), m_source2target(), m_target2source(), m_distance_metric(metric)
58
59
  {
59
60
  _initialize_pyramid();
60
61
  }
@@ -104,6 +105,7 @@ cv::Mat Inpainting::run(bool verbose, bool verbose_visualize, unsigned int rando
104
105
  if (verbose)
105
106
  std::cerr << "Initialization done." << std::endl;
106
107
 
108
+ #ifdef PATCHMATCH_WITH_HIGHGUI
107
109
  if (verbose_visualize)
108
110
  {
109
111
  auto visualize_size = m_initial.size();
@@ -115,6 +117,9 @@ cv::Mat Inpainting::run(bool verbose, bool verbose_visualize, unsigned int rando
115
117
  cv::imshow("Target", target_visualize);
116
118
  cv::waitKey(0);
117
119
  }
120
+ #else
121
+ (void)verbose_visualize;
122
+ #endif
118
123
 
119
124
  target = _expectation_maximization(source, target, level, verbose);
120
125
  }
@@ -150,7 +150,6 @@ void MaskedImage::compute_image_gradients()
150
150
 
151
151
  for (int i = 1; i < size.height - 1; ++i)
152
152
  {
153
- const auto *ptr = m_image.ptr<unsigned char>(i, 0);
154
153
  const auto *ptry1 = m_image.ptr<unsigned char>(i + 1, 0);
155
154
  const auto *ptry2 = m_image.ptr<unsigned char>(i - 1, 0);
156
155
  const auto *ptrx1 = m_image.ptr<unsigned char>(i, 0) + 3;
@@ -287,16 +287,17 @@ int RegularityGuidedPatchDistanceMetricV2::operator()(const MaskedImage &source,
287
287
  if (target_y < 0 || target_y >= target.size().height || target_x < 0 || target_x >= target.size().width)
288
288
  return PatchDistanceMetric::kDistanceScale;
289
289
 
290
- int source_scale = m_ijmap.size().height / source.size().height;
291
- int target_scale = m_ijmap.size().height / target.size().height;
292
-
293
- // fprintf(stderr, "RegularityGuidedPatchDistanceMetricV2 %d %d %d %d\n", source_y * source_scale, m_ijmap.size().height, source_x * source_scale, m_ijmap.size().width);
290
+ // Map pyramid-level coordinates to the full-resolution ijmap. Height and width are
291
+ // scaled independently and clamped, since the pyramid sizes are rounded per axis.
292
+ const int map_h = m_ijmap.size().height, map_w = m_ijmap.size().width;
293
+ auto map_y = [&](const MaskedImage &img, int y) { return std::min(y * map_h / img.size().height, map_h - 1); };
294
+ auto map_x = [&](const MaskedImage &img, int x) { return std::min(x * map_w / img.size().width, map_w - 1); };
294
295
 
295
296
  double score1 = PatchDistanceMetric::kDistanceScale;
296
297
  if (!source.is_globally_masked(source_y, source_x) && !target.is_globally_masked(target_y, target_x))
297
298
  {
298
- auto source_ij = m_ijmap.ptr<float>(source_y * source_scale, source_x * source_scale);
299
- auto target_ij = m_ijmap.ptr<float>(target_y * target_scale, target_x * target_scale);
299
+ auto source_ij = m_ijmap.ptr<float>(map_y(source, source_y), map_x(source, source_x));
300
+ auto target_ij = m_ijmap.ptr<float>(map_y(target, target_y), map_x(target, target_x));
300
301
 
301
302
  float di = fabs(source_ij[0] - target_ij[0]);
302
303
  if (di > 0.5)