Skip to content

Commit e228b19

Browse files
committed
Spline: implement JmeCloneable and test
1 parent 75f0b73 commit e228b19

File tree

2 files changed

+162
-40
lines changed

2 files changed

+162
-40
lines changed

jme3-core/src/main/java/com/jme3/math/Spline.java

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@
3232
package com.jme3.math;
3333

3434
import com.jme3.export.*;
35+
import com.jme3.util.clone.Cloner;
36+
import com.jme3.util.clone.JmeCloneable;
3537
import java.io.IOException;
3638
import java.util.ArrayList;
3739
import java.util.Iterator;
@@ -41,7 +43,7 @@
4143
*
4244
* @author Nehon
4345
*/
44-
public class Spline implements Savable {
46+
public class Spline implements JmeCloneable, Savable {
4547

4648
public enum SplineType {
4749
Linear,
@@ -536,4 +538,41 @@ public void read(JmeImporter im) throws IOException {
536538
weights = in.readFloatArray("weights", null);
537539
basisFunctionDegree = in.readInt("basisFunctionDegree", 0);
538540
}
541+
542+
/**
543+
* Callback from {@link com.jme3.util.clone.Cloner} to convert this
544+
* shallow-cloned spline into a deep-cloned one, using the specified cloner
545+
* and original to resolve copied fields.
546+
*
547+
* @param cloner the cloner that's cloning this spline (not null)
548+
* @param original the object from which this spline was shallow-cloned
549+
* (not null, unaffected)
550+
*/
551+
@Override
552+
public void cloneFields(Cloner cloner, Object original) {
553+
this.controlPoints = cloner.clone(controlPoints);
554+
if (segmentsLength != null) {
555+
this.segmentsLength = new ArrayList<>(segmentsLength);
556+
}
557+
this.CRcontrolPoints = cloner.clone(CRcontrolPoints);
558+
if (knots != null) {
559+
this.knots = new ArrayList<>(knots);
560+
}
561+
this.weights = cloner.clone(weights);
562+
}
563+
564+
/**
565+
* Create a shallow clone for the JME cloner.
566+
*
567+
* @return a new object
568+
*/
569+
@Override
570+
public Spline jmeClone() {
571+
try {
572+
Spline clone = (Spline) clone();
573+
return clone;
574+
} catch (CloneNotSupportedException exception) {
575+
throw new RuntimeException(exception);
576+
}
577+
}
539578
}

jme3-core/src/test/java/com/jme3/math/SplineTest.java

Lines changed: 122 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
import com.jme3.asset.AssetManager;
3535
import com.jme3.asset.DesktopAssetManager;
3636
import com.jme3.export.binary.BinaryExporter;
37+
import com.jme3.util.clone.Cloner;
3738
import java.util.ArrayList;
3839
import java.util.List;
3940
import org.junit.Assert;
@@ -52,70 +53,76 @@ public class SplineTest {
5253
// *************************************************************************
5354
// tests
5455

56+
/**
57+
* Verifies that spline cloning works correctly.
58+
*/
59+
@Test
60+
public void cloneSplines() {
61+
// Clone a Bézier spline:
62+
{
63+
Spline test1 = createBezier();
64+
Spline copy1 = Cloner.deepClone(test1);
65+
assertSplineEquals(test1, copy1);
66+
}
67+
68+
// Clone a NURB spline:
69+
{
70+
Spline test2 = createNurb();
71+
Spline copy2 = Cloner.deepClone(test2);
72+
assertSplineEquals(test2, copy2);
73+
}
74+
75+
// Clone a Catmull-Rom spline:
76+
{
77+
Spline test3 = createCatmullRom();
78+
Spline copy3 = Cloner.deepClone(test3);
79+
assertSplineEquals(test3, copy3);
80+
}
81+
82+
// Clone a linear spline:
83+
{
84+
Spline test4 = createLinear();
85+
Spline copy4 = Cloner.deepClone(test4);
86+
assertSplineEquals(test4, copy4);
87+
}
88+
89+
// Clone a default spline:
90+
{
91+
Spline test5 = new Spline();
92+
Spline copy5 = Cloner.deepClone(test5);
93+
assertSplineEquals(test5, copy5);
94+
}
95+
}
96+
5597
/**
5698
* Verifies that spline serialization/deserialization works correctly.
5799
*/
58100
@Test
59101
public void saveAndLoadSplines() {
60102
// Serialize and deserialize a Bezier spline:
61103
{
62-
Vector3f[] controlPoints1 = {
63-
new Vector3f(0f, 1f, 0f), new Vector3f(1f, 2f, 1f),
64-
new Vector3f(1.5f, 1.5f, 1.5f), new Vector3f(2f, 0f, 1f)
65-
};
66-
67-
Spline test1 = new Spline(
68-
Spline.SplineType.Bezier, controlPoints1, 0.1f, true);
104+
Spline test1 = createBezier();
69105
Spline copy1 = BinaryExporter.saveAndLoad(assetManager, test1);
70106
assertSplineEquals(test1, copy1);
71107
}
72108

73109
// Serialize and deserialize a NURB spline:
74110
{
75-
List<Vector4f> controlPoints2 = new ArrayList<>(5);
76-
controlPoints2.add(new Vector4f(0f, 1f, 2f, 3f));
77-
controlPoints2.add(new Vector4f(3f, 1f, 4f, 0f));
78-
controlPoints2.add(new Vector4f(2f, 5f, 3f, 0f));
79-
controlPoints2.add(new Vector4f(3f, 2f, 3f, 1f));
80-
controlPoints2.add(new Vector4f(0.5f, 1f, 0.6f, 5f));
81-
List<Float> nurbKnots = new ArrayList<>(6);
82-
nurbKnots.add(0.2f);
83-
nurbKnots.add(0.3f);
84-
nurbKnots.add(0.4f);
85-
nurbKnots.add(0.43f);
86-
nurbKnots.add(0.51f);
87-
nurbKnots.add(0.52f);
88-
89-
Spline test2 = new Spline(controlPoints2, nurbKnots);
111+
Spline test2 = createNurb();
90112
Spline copy2 = BinaryExporter.saveAndLoad(assetManager, test2);
91113
assertSplineEquals(test2, copy2);
92114
}
93115

94116
// Serialize and deserialize a Catmull-Rom spline:
95117
{
96-
List<Vector3f> controlPoints3 = new ArrayList<>(6);
97-
controlPoints3.add(new Vector3f(0f, 1f, 2f));
98-
controlPoints3.add(new Vector3f(3f, -1f, 4f));
99-
controlPoints3.add(new Vector3f(2f, 5f, 3f));
100-
controlPoints3.add(new Vector3f(3f, -2f, 3f));
101-
controlPoints3.add(new Vector3f(0.5f, 1f, 0.6f));
102-
controlPoints3.add(new Vector3f(-0.5f, 4f, 0.2f));
103-
104-
Spline test3 = new Spline(
105-
Spline.SplineType.CatmullRom, controlPoints3, 0.01f, false);
118+
Spline test3 = createCatmullRom();
106119
Spline copy3 = BinaryExporter.saveAndLoad(assetManager, test3);
107120
assertSplineEquals(test3, copy3);
108121
}
109122

110123
// Serialize and deserialize a linear spline:
111124
{
112-
List<Vector3f> controlPoints4 = new ArrayList<>(3);
113-
controlPoints4.add(new Vector3f(3f, -1f, 4f));
114-
controlPoints4.add(new Vector3f(2f, 0f, 3f));
115-
controlPoints4.add(new Vector3f(3f, -2f, 3f));
116-
117-
Spline test4 = new Spline(
118-
Spline.SplineType.Linear, controlPoints4, 0f, true);
125+
Spline test4 = createLinear();
119126
Spline copy4 = BinaryExporter.saveAndLoad(assetManager, test4);
120127
assertSplineEquals(test4, copy4);
121128
}
@@ -172,4 +179,80 @@ private static void assertSplineEquals(Spline s1, Spline s2) {
172179
s1.getTotalLength(), s2.getTotalLength(), 0f);
173180
Assert.assertArrayEquals(s1.getWeights(), s2.getWeights(), 0f);
174181
}
182+
183+
/**
184+
* Generate a simple cyclic Bézier spline for testing.
185+
*
186+
* @return a new Spline
187+
*/
188+
private static Spline createBezier() {
189+
Vector3f[] controlPoints1 = {
190+
new Vector3f(0f, 1f, 0f), new Vector3f(1f, 2f, 1f),
191+
new Vector3f(1.5f, 1.5f, 1.5f), new Vector3f(2f, 0f, 1f)
192+
};
193+
194+
Spline result = new Spline(
195+
Spline.SplineType.Bezier, controlPoints1, 0.1f, true);
196+
return result;
197+
}
198+
199+
/**
200+
* Generate a simple acyclic Catmull-Rom spline for testing.
201+
*
202+
* @return a new Spline
203+
*/
204+
private static Spline createCatmullRom() {
205+
List<Vector3f> controlPoints3 = new ArrayList<>(6);
206+
controlPoints3.add(new Vector3f(0f, 1f, 2f));
207+
controlPoints3.add(new Vector3f(3f, -1f, 4f));
208+
controlPoints3.add(new Vector3f(2f, 5f, 3f));
209+
controlPoints3.add(new Vector3f(3f, -2f, 3f));
210+
controlPoints3.add(new Vector3f(0.5f, 1f, 0.6f));
211+
controlPoints3.add(new Vector3f(-0.5f, 4f, 0.2f));
212+
213+
Spline result = new Spline(
214+
Spline.SplineType.CatmullRom, controlPoints3, 0.01f, false);
215+
return result;
216+
}
217+
218+
/**
219+
* Generate a simple cyclic linear spline for testing.
220+
*
221+
* @return a new Spline
222+
*/
223+
private static Spline createLinear() {
224+
List<Vector3f> controlPoints4 = new ArrayList<>(3);
225+
controlPoints4.add(new Vector3f(3f, -1f, 4f));
226+
controlPoints4.add(new Vector3f(2f, 0f, 3f));
227+
controlPoints4.add(new Vector3f(3f, -2f, 3f));
228+
229+
Spline result = new Spline(
230+
Spline.SplineType.Linear, controlPoints4, 0f, true);
231+
return result;
232+
}
233+
234+
/**
235+
* Generate a simple NURB spline for testing.
236+
*
237+
* @return a new Spline
238+
*/
239+
private static Spline createNurb() {
240+
List<Vector4f> controlPoints2 = new ArrayList<>(5);
241+
controlPoints2.add(new Vector4f(0f, 1f, 2f, 3f));
242+
controlPoints2.add(new Vector4f(3f, 1f, 4f, 0f));
243+
controlPoints2.add(new Vector4f(2f, 5f, 3f, 0f));
244+
controlPoints2.add(new Vector4f(3f, 2f, 3f, 1f));
245+
controlPoints2.add(new Vector4f(0.5f, 1f, 0.6f, 5f));
246+
247+
List<Float> nurbKnots = new ArrayList<>(6);
248+
nurbKnots.add(0.2f);
249+
nurbKnots.add(0.3f);
250+
nurbKnots.add(0.4f);
251+
nurbKnots.add(0.43f);
252+
nurbKnots.add(0.51f);
253+
nurbKnots.add(0.52f);
254+
255+
Spline result = new Spline(controlPoints2, nurbKnots);
256+
return result;
257+
}
175258
}

0 commit comments

Comments
 (0)