{"id":2300,"date":"2025-03-11T09:40:34","date_gmt":"2025-03-11T13:40:34","guid":{"rendered":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/?p=2300"},"modified":"2025-03-11T09:40:34","modified_gmt":"2025-03-11T13:40:34","slug":"casting-shadows-and-inverse-stereographic-projections","status":"publish","type":"post","link":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/2025\/03\/11\/casting-shadows-and-inverse-stereographic-projections\/","title":{"rendered":"Casting Shadows and Inverse Stereographic Projections"},"content":{"rendered":"<table style=\"background-color: #e2f0ff\">\r\n<tbody>\r\n<tr>\r\n<td style=\"width: 120px;padding: 3px;vertical-align: middle\"><img decoding=\"async\" loading=\"lazy\" class=\"alignleft wp-image-405 size-full\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2023\/10\/EricPortrait.png\" alt=\"\" width=\"150\" height=\"150\" \/><\/td>\r\n<td style=\"vertical-align: middle;padding: 3px\"><strong>Guest Writer: <span style=\"font-weight: bold\"><a href=\"https:\/\/www.mathworks.com\/matlabcentral\/profile\/authors\/869244\" target=\"_blank\" rel=\"noopener\">Eric Ludlam<\/a><\/span><\/strong>\r\n\r\nJoining us again is Eric Ludlam, development manager of the MATLAB charting team. Discover more about Eric on our\u00a0<a href=\"https:\/\/blogs.mathworks.com\/graphics-and-apps\/contributors\/\" target=\"_blank\" rel=\"noopener\">contributors page<\/a>.<\/td>\r\n<\/tr>\r\n<\/tbody>\r\n<\/table>\r\n<a href=\"https:\/\/matlab.mathworks.com\/open\/github\/v1?repo=MATLAB-Graphics-and-App-Building\/matlab-gaab-blog-2025&amp;file=InverseStereographicProjection\/StereographicProjections.mlx\" target=\"_blank\" rel=\"noopener\"><img decoding=\"async\" loading=\"lazy\" class=\"alignnone wp-image-2010\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2024\/11\/PumpkinDesignerAndFocusMode.mlx-11-23-24_5.png\" alt=\"\" width=\"160\" height=\"24\" \/><\/a>\r\n<div class=\"rtcContent\">\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">In the previous blog article, we talked about how to simulate simple shadows in MATLAB. Given a light source and a shape, we were able to draw some convincing shadows on the floor of the axes. But what if you have a shadow, and you want to compute a shape that can cast it?<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">One way to do that is to use a <span style=\"font-style: italic\">stereographic projection<\/span> which lets you project vertices between a sphere and a flat surface. Map makers have been transforming features on the earth into flat maps for a long time. Mapping toolbox's new <a href=\"https:\/\/www.mathworks.com\/help\/map\/ref\/mapaxes.html\" target=\"_blank\" rel=\"noopener\"><span style=\"font-family: monospace\">mapaxes<\/span><\/a> (R2023a) lets you explore several kinds of projections. Here's an example of a stereographic projection using <span style=\"font-family: monospace\">mapaxes<\/span>.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><span style=\"color: #008013\">% If you don't have Mapping Toolbox, you can skip this example<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">prj=projcrs(53026,<span style=\"color: #a709f5\">'Authority'<\/span>,<span style=\"color: #a709f5\">'ESRI'<\/span>);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">prj.ProjectionParameters.LatitudeOfNaturalOrigin=90;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">newmap(prj)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">land=readgeotable(<span style=\"color: #a709f5\">\"landareas.shp\"<\/span>);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">land(land.Name == <span style=\"color: #a709f5\">\"Antarctica\"<\/span>,:) = [];<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">geoplot(land)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">geolimits([30 90],[-180 180])<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper outputs\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">title(<span style=\"color: #a709f5\">'Stereographic Projection'<\/span>)<\/div>\r\n<\/div>\r\n<div style=\"padding: 10px 0px 6px 17px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px;line-height: 17.234px\">\r\n<div class=\"inlineElement eoOutputWrapper disableDefaultGestureHandling embeddedOutputsFigure\" data-testid=\"output_0\">\r\n<div class=\"figureElement eoOutputContent\" role=\"article\">\r\n\r\n<img decoding=\"async\" class=\"figureImage figureContainingNode\" style=\"width: 560px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_1.png\" \/>\r\n<div class=\"outputLayer selectedOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer activeOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer scrollableOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer navigationFocusLayer doNotExport\" role=\"application\" aria-hidden=\"false\" aria-label=\"figure output \"><\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 10px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">In this projection, the north pole of the earth (the top part of the sphere) is being projected onto a plane (your screen). Mapping toolbox projections cover a wide range of interesting options. We can use similar techniques as Mapping toolbox to project our 2D pattern in the opposite direction, back onto a sphere.<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">So with that background, let's pick out a shape we want as our eventual shadow. A hex-grid will be a good shape to use, because it looks neat when projected onto a sphere. I have a helper function I'll call here which returns a <a href=\"https:\/\/www.mathworks.com\/help\/matlab\/ref\/polyshape.html\" target=\"_blank\" rel=\"noopener\">Polyshape<\/a> object.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">ps = hexgrid; <span style=\"color: #008013\">% see end of this live script<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">plot(ps)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper outputs\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">axis <span style=\"color: #a709f5\">equal<\/span><\/div>\r\n<\/div>\r\n<div style=\"padding: 10px 0px 6px 17px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px;line-height: 17.234px\">\r\n<div class=\"inlineElement eoOutputWrapper disableDefaultGestureHandling embeddedOutputsFigure\" data-testid=\"output_1\">\r\n<div class=\"figureElement eoOutputContent\" role=\"article\">\r\n\r\n<img decoding=\"async\" class=\"figureImage figureContainingNode\" style=\"width: 560px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_2.png\" \/>\r\n<div class=\"outputLayer selectedOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer activeOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer scrollableOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer navigationFocusLayer doNotExport\" role=\"application\" aria-hidden=\"false\" aria-label=\"figure output \"><\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">As shadows go, this will be pretty interesting. Next, we need to get our vertices out of the Polyshape object. We'll convert it into a <a href=\"https:\/\/www.mathworks.com\/help\/matlab\/ref\/polyshape.triangulation.html\" target=\"_blank\" rel=\"noopener\">triangulation<\/a>, as the triangulation tools have handy features, we can take advantage of.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">psTri = ps.triangulation();<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">pts = psTri.Points;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px 0px 4px 4px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">faces = psTri.ConnectivityList();<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 10px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">We now need to do a reverse projection onto a sphere using a north pole stereographic projection similar to what we saw in the Mapping toolbox example. This projection will use a large portion of the sphere based on size of the polyshape we made. We only need to project the points, as the connectivity will remain the same between the desired shadow, and our new shape. This optimization works because the shadow fits wholly on the sphere.<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">Starting with the shadow points in <span style=\"font-family: monospace\">pts<\/span>, we can project onto a unit sphere (radius==1) which we assign to <span style=\"font-family: monospace\">SpherePts<\/span>. In the following code, <span style=\"font-family: monospace\">X<\/span> and <span style=\"font-family: monospace\">Y<\/span> are column vectors. The result is a <span style=\"font-family: monospace\">Nx3<\/span> matrix whose columns are <span style=\"font-family: monospace\">X<\/span>, <span style=\"font-family: monospace\">Y<\/span>, and <span style=\"font-family: monospace\">Z<\/span> respectively that specify the projection of the shadow onto the 3D sphere.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">X=pts(:,1)\/2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">Y=pts(:,2)\/2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">H=X.^2+Y.^2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px 0px 4px 4px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">SpherePts = [ 2*X.\/(H+1), 2*Y.\/(H+1), (H-1).\/(H+1)+1 ];<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 10px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">Now that we have the points on the sphere, we'll use the new vertices and the original faces array to create a triangulation. The triangulation is nice because it will give us access to the <a href=\"https:\/\/www.mathworks.com\/help\/matlab\/ref\/triangulation.freeboundary.html\" target=\"_blank\" rel=\"noopener\"><span style=\"font-family: monospace\">freeBoundary<\/span><\/a> function, which enables us to draw the outer boundary of the shape without the internal triangulation.<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">The code below creates 2 patches, one to draw the blue part (the full stereographic projection of the shadow onto the sphere), and the second draws the \"edge\" of the shape. That edge adds some artistic definition where parts of the shape overlap each other in the below view.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">Tri = triangulation(faces, SpherePts);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">newplot<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">patch(<span style=\"color: #a709f5\">'Vertices'<\/span>,Tri.Points,<span style=\"color: #a709f5\">'Faces'<\/span>,Tri.ConnectivityList(),<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'FaceColor'<\/span>,lines(1),<span style=\"color: #a709f5\">'EdgeColor'<\/span>,<span style=\"color: #a709f5\">'none'<\/span>);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">patch(<span style=\"color: #a709f5\">'Vertices'<\/span>,Tri.Points,<span style=\"color: #a709f5\">'Faces'<\/span>,Tri.freeBoundary(),<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'FaceColor'<\/span>,<span style=\"color: #a709f5\">'none'<\/span>,<span style=\"color: #a709f5\">'EdgeColor'<\/span>,<span style=\"color: #a709f5\">'black'<\/span>);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">view(3)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">axis <span style=\"color: #a709f5\">equal padded<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper outputs\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">grid <span style=\"color: #a709f5\">on<\/span><\/div>\r\n<\/div>\r\n<div style=\"padding: 10px 0px 6px 17px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px;line-height: 17.234px\">\r\n<div class=\"inlineElement eoOutputWrapper disableDefaultGestureHandling embeddedOutputsFigure\" data-testid=\"output_2\">\r\n<div class=\"figureElement eoOutputContent\" role=\"article\">\r\n\r\n<img decoding=\"async\" class=\"figureImage figureContainingNode\" style=\"width: 560px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_3.png\" \/>\r\n<div class=\"outputLayer selectedOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer activeOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer scrollableOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer navigationFocusLayer doNotExport\" role=\"application\" aria-hidden=\"false\" aria-label=\"figure output \"><\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">Since we're talking about shadows, let's add a light just over the \"north pole\" of our sphere and we'll drop a marker where the light is to make it easier to reason on what you see. Setting the <a href=\"https:\/\/www.mathworks.com\/help\/matlab\/ref\/light.html#mw_e03ab250-71c4-4934-8614-a01de28a07f2\" target=\"_blank\" rel=\"noopener\">light object's 'Style' property to 'local'<\/a> makes the light emit in all directions. In the image below, this means it looks like the light is shining from inside the sphere, and not on the outside.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">Lpos=[0 0 2];<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">light(<span style=\"color: #a709f5\">'Position'<\/span>,Lpos,<span style=\"color: #a709f5\">'Style'<\/span>,<span style=\"color: #a709f5\">'local'<\/span>);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">Lm=line(Lpos(1),Lpos(2),Lpos(3),<span style=\"color: #a709f5\">'Color'<\/span>,<span style=\"color: #a709f5\">'red'<\/span>,<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'Marker'<\/span>,<span style=\"color: #a709f5\">'o'<\/span>,<span style=\"color: #a709f5\">'MarkerFaceColor'<\/span>,<span style=\"color: #a709f5\">'auto'<\/span>,<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'MarkerSize'<\/span>,10,<span style=\"color: #a709f5\">'LineWidth'<\/span>,1);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">lighting <span style=\"color: #a709f5\">gouraud<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper outputs\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">material([ .6 .9 .3 2 .5 ])<\/div>\r\n<\/div>\r\n<div style=\"padding: 10px 0px 6px 17px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px;line-height: 17.234px\">\r\n<div class=\"inlineElement eoOutputWrapper disableDefaultGestureHandling embeddedOutputsFigure\" data-testid=\"output_3\">\r\n<div class=\"figureElement eoOutputContent\" role=\"article\">\r\n\r\n<img decoding=\"async\" class=\"figureImage figureContainingNode\" style=\"width: 560px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_4.png\" \/>\r\n<div class=\"outputLayer selectedOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer activeOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer scrollableOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer navigationFocusLayer doNotExport\" role=\"application\" aria-hidden=\"false\" aria-label=\"figure output \"><\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">Lastly, we'll pull our code-snippet for drawing shadows from <a href=\"https:\/\/blogs.mathworks.com\/graphics-and-apps\/2025\/03\/03\/casting-shadows\/\">the previous article<\/a> and use it on our newly created shape.<\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">pts = Tri.Points;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">shadowPts = zeros(size(pts));<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">shadowPts(:,1:2) = Lpos(3).*(pts(:,1:2)-Lpos(1:2)).\/(Lpos(3)-pts(:,3))+Lpos(1:2);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">Ps = patch(<span style=\"color: #a709f5\">'Vertices'<\/span>,shadowPts,<span style=\"color: #a709f5\">'Faces'<\/span>, Tri.ConnectivityList,<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'FaceColor'<\/span>, [.6 .6 .6], <span style=\"color: #a709f5\">'FaceAlpha'<\/span>, .5, <span style=\"color: #a709f5\">'FaceLighting'<\/span>,<span style=\"color: #a709f5\">'none'<\/span>,<span style=\"color: #0e00ff\">...<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper outputs\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #a709f5\">'EdgeColor'<\/span>, <span style=\"color: #a709f5\">'none'<\/span>);<\/div>\r\n<\/div>\r\n<div style=\"padding: 10px 0px 6px 17px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px;line-height: 17.234px\">\r\n<div class=\"inlineElement eoOutputWrapper disableDefaultGestureHandling embeddedOutputsFigure\" data-testid=\"output_4\">\r\n<div class=\"figureElement eoOutputContent\" role=\"article\">\r\n\r\n<img decoding=\"async\" class=\"figureImage figureContainingNode\" style=\"width: 560px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_5.png\" \/>\r\n<div class=\"outputLayer selectedOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer activeOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer scrollableOutputDecorationLayer doNotExport\" aria-hidden=\"true\"><\/div>\r\n<div class=\"outputLayer navigationFocusLayer doNotExport\" role=\"application\" aria-hidden=\"false\" aria-label=\"figure output \"><\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">In the above image, we have the stereographic projection of our original polyshape, a light object to illuminate it, and we then re-cast the shadow back onto the floor of the axes, showing that our projection worked!<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">I took this shape and wrote some additional code to turn it into an STL file that you can 3D print. Thanks to MathWorker Eric Felton for 3D printing the shape pictured below for this blog article!<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\"><img decoding=\"async\" loading=\"lazy\" class=\"imageNode\" style=\"vertical-align: baseline;width: 415px;height: 415px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_6.png\" alt=\"PrintForPost1.jpg\" width=\"415\" height=\"415\" \/><\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">In the above image, a small flashlight was used to cast a shadow of the 3D printed shape into a countertop.<\/div>\r\n<div style=\"margin: 2px 10px 9px 4px;padding: 0px;line-height: 21px;min-height: 0px;font-family: Helvetica, Arial, sans-serif, Helvetica, Arial, sans-serif;font-style: normal;font-size: 14px;font-weight: 400;text-align: left\">You can download the <a href=\"https:\/\/github.com\/MATLAB-Graphics-and-App-Building\/shadows-for-matlab\" target=\"_blank\" rel=\"noopener\"><span style=\"text-decoration: underline\">Shadows for MATLAB<\/span><\/a> project from github or <a href=\"https:\/\/www.mathworks.com\/matlabcentral\/fileexchange\/180262-shadows-for-matlab\" target=\"_blank\" rel=\"noopener\">File Exchange<\/a> to get all the code for this blog in handy utility functions, plus a repository of <span style=\"font-family: monospace\">STL<\/span> files you can print for different stereographically projected shapes. This File Exchange project includes additional shadow casting features, such as a function that will let you create shadows on all the axes walls:<img decoding=\"async\" loading=\"lazy\" class=\"imageNode\" style=\"vertical-align: baseline;width: 533px;height: 400px\" src=\"http:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_7.gif\" alt=\"HexgridShadowAnimation.gif\" width=\"533\" height=\"400\" \/><\/div>\r\n<div style=\"background-color: #f5f5f5;margin: 10px 15px 10px 0\">\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 4px 4px 0px 0px;padding: 6px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><span style=\"color: #0e00ff\">function <\/span>ps=hexgrid<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><span style=\"color: #008013\">% Compute a hexgrid polyshape with evenly wide edge lines.<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0R=.5; row = 9; col = 8;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0theta=linspace(0,2,7);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0xhex=sinpi(theta)*R;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0yhex=cospi(theta)*R;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0D=cosd(30)*R;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0ps=polyshape.empty();<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0WIDTH=col*D*2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0HEIGHT=(row-1)*R*1.5;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">for <\/span>i=1:(col+1)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0j=i-1;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">for <\/span>k=1:row<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">if <\/span>i&lt;=col || ~mod(k,2)<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0m=k-1;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0xbuff = ((xhex+mod(k,2)*D)+D*2*j)'-WIDTH\/2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0ybuff = (yhex+1.5*R*m)'-HEIGHT\/2;<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0ps(end+1) = polybuffer([xbuff ybuff], <span style=\"color: #a709f5\">'lines'<\/span>, R\/4); <span style=\"color: #008013\">%#ok<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">end<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">end<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0<span style=\"color: #0e00ff\">end<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\">\u00a0\u00a0\u00a0\u00a0ps=union(ps);<\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px;padding: 0px 45px 0px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><span style=\"color: #0e00ff\">end<\/span><\/div>\r\n<\/div>\r\n<div class=\"inlineWrapper\">\r\n<div style=\"border-radius: 0px 0px 4px 4px;padding: 0px 45px 4px 13px;line-height: 18.004px;min-height: 0px;font-family: Menlo, Monaco, Consolas, 'Courier New', monospace, Menlo, Monaco, Consolas, 'Courier New', monospace;font-size: 14px\"><\/div>\r\n<\/div>\r\n<\/div>\r\n&nbsp;\r\n\r\n<\/div>\r\n<script type=\"text\/javascript\">\r\n{ let css = '.eoOutputWrapper { width: calc(90vw - 10px) !important; }';\r\nlet head = document.head || document.getElementsByTagName('head')[0];\r\nlet style = document.createElement('style');\r\nhead.appendChild(style);\r\nstyle.type = 'text\/css';\r\nif (style.styleSheet) {\r\n    style.styleSheet.cssText = css;\r\n} else {\r\n    style.appendChild(document.createTextNode(css));\r\n}\r\n\r\n\r\n}<\/script><a href=\"https:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx\"><button class=\"btn btn-sm btn_color_blue pull-right add_margin_10\">Download Live Script<\/button><\/a>","protected":false},"excerpt":{"rendered":"<div class=\"overview-image\"><img src=\"https:\/\/blogs.mathworks.com\/graphics-and-apps\/files\/2025\/03\/StereographicProjections.mlx-02-28-25_7.gif\" class=\"img-responsive attachment-post-thumbnail size-post-thumbnail wp-post-image\" alt=\"\" decoding=\"async\" loading=\"lazy\" \/><\/div><p>\r\n\r\n\r\n\r\nGuest Writer: Eric Ludlam\r\n\r\nJoining us again is Eric Ludlam, development manager of the MATLAB charting team. Discover more about Eric on our\u00a0contributors page.\r\n\r\n\r\n\r\n\r\n\r\nIn the previous... <a class=\"read-more\" href=\"https:\/\/blogs.mathworks.com\/graphics-and-apps\/2025\/03\/11\/casting-shadows-and-inverse-stereographic-projections\/\">read more >><\/a><\/p>","protected":false},"author":198,"featured_media":2294,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[11,2,1],"tags":[],"_links":{"self":[{"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/posts\/2300"}],"collection":[{"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/users\/198"}],"replies":[{"embeddable":true,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/comments?post=2300"}],"version-history":[{"count":2,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/posts\/2300\/revisions"}],"predecessor-version":[{"id":2309,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/posts\/2300\/revisions\/2309"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/media\/2294"}],"wp:attachment":[{"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/media?parent=2300"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/categories?post=2300"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blogs.mathworks.com\/graphics-and-apps\/wp-json\/wp\/v2\/tags?post=2300"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}