@@ -1830,60 +1830,91 @@ def pointwise_become_partial(
18301830 a : float ,
18311831 b : float ,
18321832 ) -> Self :
1833- """Given two bounds a and b, transforms the points of the self vmobject into the points of the vmobject
1834- passed as parameter with respect to the bounds. Points here stand for control points of the bezier curves (anchors and handles)
1833+ """Given a 2nd :class:`.VMobject` ``vmobject``, a lower bound ``a`` and
1834+ an upper bound ``b``, modify this :class:`.VMobject`'s points to
1835+ match the portion of the Bézier spline described by ``vmobject.points``
1836+ with the parameter ``t`` between ``a`` and ``b``.
18351837
18361838 Parameters
18371839 ----------
18381840 vmobject
1839- The vmobject that will serve as a model.
1841+ The :class:`.VMobject` that will serve as a model.
18401842 a
1841- upper- bound.
1843+ The lower bound for ``t`` .
18421844 b
1843- lower- bound
1845+ The upper bound for ``t``
18441846
18451847 Returns
18461848 -------
1847- :class:`VMobject`
1848- ``self``
1849+ :class:`.VMobject`
1850+ The :class:`.VMobject` itself, after the transformation.
1851+
1852+ Raises
1853+ ------
1854+ TypeError
1855+ If ``vmobject`` is not an instance of :class:`VMobject`.
18491856 """
1850- assert isinstance (vmobject , VMobject )
1857+ if not isinstance (vmobject , VMobject ):
1858+ raise TypeError (
1859+ f"Expected a VMobject, got value { vmobject } of type "
1860+ f"{ type (vmobject ).__name__ } ."
1861+ )
18511862 # Partial curve includes three portions:
1852- # - A middle section, which matches the curve exactly
1853- # - A start, which is some ending portion of an inner cubic
1854- # - An end, which is the starting portion of a later inner cubic
1863+ # - A middle section, which matches the curve exactly.
1864+ # - A start, which is some ending portion of an inner cubic.
1865+ # - An end, which is the starting portion of a later inner cubic.
18551866 if a <= 0 and b >= 1 :
18561867 self .set_points (vmobject .points )
18571868 return self
1858- bezier_quads = vmobject .get_cubic_bezier_tuples ()
1859- num_cubics = len (bezier_quads )
1869+ num_curves = vmobject .get_num_curves ()
1870+ if num_curves == 0 :
1871+ self .clear_points ()
1872+ return self
18601873
1861- # The following two lines will compute which bezier curves of the given mobject need to be processed.
1862- # The residue basically indicates de proportion of the selected bezier curve that have to be selected.
1863- # Ex : if lower_index is 3, and lower_residue is 0.4, then the algorithm will append to the points 0.4 of the third bezier curve
1864- lower_index , lower_residue = integer_interpolate (0 , num_cubics , a )
1865- upper_index , upper_residue = integer_interpolate (0 , num_cubics , b )
1874+ # The following two lines will compute which Bézier curves of the given Mobject must be processed.
1875+ # The residue indicates the proportion of the selected Bézier curve which must be selected.
1876+ #
1877+ # Example: if num_curves is 10, a is 0.34 and b is 0.78, then:
1878+ # - lower_index is 3 and lower_residue is 0.4, which means the algorithm will look at the 3rd Bézier
1879+ # and select its part which ranges from t=0.4 to t=1.
1880+ # - upper_index is 7 and upper_residue is 0.8, which means the algorithm will look at the 7th Bézier
1881+ # and select its part which ranges from t=0 to t=0.8.
1882+ lower_index , lower_residue = integer_interpolate (0 , num_curves , a )
1883+ upper_index , upper_residue = integer_interpolate (0 , num_curves , b )
18661884
1867- self .clear_points ()
1868- if num_cubics == 0 :
1869- return self
1885+ nppc = self .n_points_per_curve
1886+ # If both indices coincide, get a part of a single Bézier curve.
18701887 if lower_index == upper_index :
1871- self . append_points (
1872- partial_bezier_points (
1873- bezier_quads [ lower_index ],
1874- lower_residue ,
1875- upper_residue ,
1876- ) ,
1888+ # Look at the "lower_index"-th Bézier curve and select its part from
1889+ # t=lower_residue to t=upper_residue.
1890+ self . points = partial_bezier_points (
1891+ vmobject . points [ nppc * lower_index : nppc * ( lower_index + 1 )] ,
1892+ lower_residue ,
1893+ upper_residue ,
18771894 )
18781895 else :
1879- self .append_points (
1880- partial_bezier_points (bezier_quads [lower_index ], lower_residue , 1 ),
1896+ # Allocate space for (upper_index-lower_index+1) Bézier curves.
1897+ self .points = np .empty ((nppc * (upper_index - lower_index + 1 ), self .dim ))
1898+ # Look at the "lower_index"-th Bezier curve and select its part from
1899+ # t=lower_residue to t=1. This is the first curve in self.points.
1900+ self .points [:nppc ] = partial_bezier_points (
1901+ vmobject .points [nppc * lower_index : nppc * (lower_index + 1 )],
1902+ lower_residue ,
1903+ 1 ,
18811904 )
1882- for quad in bezier_quads [lower_index + 1 : upper_index ]:
1883- self .append_points (quad )
1884- self .append_points (
1885- partial_bezier_points (bezier_quads [upper_index ], 0 , upper_residue ),
1905+ # If there are more curves between the "lower_index"-th and the
1906+ # "upper_index"-th Béziers, add them all to self.points.
1907+ self .points [nppc :- nppc ] = vmobject .points [
1908+ nppc * (lower_index + 1 ) : nppc * upper_index
1909+ ]
1910+ # Look at the "upper_index"-th Bézier curve and select its part from
1911+ # t=0 to t=upper_residue. This is the last curve in self.points.
1912+ self .points [- nppc :] = partial_bezier_points (
1913+ vmobject .points [nppc * upper_index : nppc * (upper_index + 1 )],
1914+ 0 ,
1915+ upper_residue ,
18861916 )
1917+
18871918 return self
18881919
18891920 def get_subcurve (self , a : float , b : float ) -> Self :
0 commit comments