Rekonstruktion aus unterschiedlichen Bildansichten
Ein 3D-Objekt kann auf der Grundlage unterschiedlicher 2D-Ansichten rekonstruiert werden. ImageDisplacements kann verwendet werden, um die Parallaxe zwischen zwei aufeinanderfolgenden Ansichten zu bestimmen. Je größer die Parallaxenverschiebung, umso näher erscheint das Objekt hinter dem entsprechenden Pixel. Mit dieser Information zur Tiefe können Sie die Gitternetzkanten eines Objekts, das durch ImageMesh und TriangulateMesh erzeugt wurde, ausfüllen. Das Ergebnis wird durch Anwendung von Texture-Mapping auf das 3D-Gitternetzobjekt veranschaulicht.
Erstellen Sie eine Maske des mittleren Bilds.
mask = Erosion[Binarize[imgs[[2]], 0], 1];
Bestimmen Sie die Parallaxe im linken und rechten Bild in Bezug auf das mittlere Bild.
parallaxL = First@ImageDisplacements[imgs[[{2, 1}]]];
parallaxR = First@ImageDisplacements[imgs[[{2, 3}]]];
Kombinieren Sie diese Verschiebungen zu einer Gesamtparallaxe.
parallax = parallaxL - parallaxR;
Im gegebenen Setting ist die -Komponente der Parallaxe annähernd proportional zur Tiefe der entsprechenden Pixelquelle.
depth = Blur@
Opening[ImageMultiply[ImageAdjust@Image[parallax[[All, All, 1]]],
mask], DiskMatrix[4]]
Erstellen Sie eine Tiefenfunktion.
depthFunction = ListInterpolation[Transpose@Reverse@ImageData[depth]];
Erstellen Sie ein Gitternetz des Objekts mit Netzverfeinerung abhängig von der Salienz des Objekts.
resolution = ImageAdjust@ImageSaliencyFilter[imgs[[2]]];
resolutionFunction =
ListInterpolation[Transpose@Reverse@ImageData@resolution];
\[CapitalOmega] = TriangulateMesh[
ImageMesh[Erosion[mask, DiskMatrix[2]]],
MeshRefinementFunction ->
Function[{vertices, area},
area > 32 + 512 (1 - resolutionFunction @@ Mean[vertices])^6]
]
Füllen Sie das Gitternetz mit der Tiefenfunktion auf.
Graphics3D[
GraphicsComplex[
Apply[{##, depthFunction[##]} &,
MeshCoordinates[\[CapitalOmega]], {1}],
{EdgeForm[], MeshCells[\[CapitalOmega], 2]}
],
PlotRange -> Append[Thread[{0, ImageDimensions[mask]}], {0, 1}],
BoxRatios -> {1, 1, 2/3},
ViewPoint -> Top
]
Extrahieren Sie die Beschaffenheit des Objekts aus dem mittleren Bild.
texture = SetAlphaChannel[imgs[[2]], mask]
Übertragen Sie die Oberflächenbeschaffenheit auf das 3D-Objekt.
Graphics3D[
{Texture[texture],
GraphicsComplex[
Apply[{##, depthFunction[##]} &,
MeshCoordinates[\[CapitalOmega]], {1}],
{EdgeForm[], MeshCells[\[CapitalOmega], 2]},
VertexTextureCoordinates ->
Map[#/ImageDimensions[texture] &, MeshCoordinates[\[CapitalOmega]]]
]
},
PlotRange -> Append[Thread[{0, ImageDimensions[mask]}], {0, 1}],
BoxRatios -> {1, 1, 2/3},
Lighting -> {{"Ambient", White}},
ViewPoint -> Top,
Boxed -> False
]