Применить градиент к объекту сферы с помощью JavaFX
Я работаю в JavaFX для класса, и я пытаюсь применить градиент к сфере, но (очевидно), я не могу понять, как это сделать. Я застрял, потому что я знаю, что сфера - это объект, и поэтому он должен иметь материал, но (что касается цветов), PhongMaterial принимает только один цвет, и поэтому он не будет принимать градиент, потому что градиент - это диапазон цветов. Итак, в основном я пытаюсь сделать следующее:
Sphere sphere = new Sphere(50);
RadialGradient rg = new RadialGradient(0, 0, 0, 0, 5, true, CycleMethod.REPEAT, /*arbitrary/irrelevant color Stop objects*/));
PhongMaterial pm = new PhongMaterial();
pm.setDiffuseMap(pm);
sphere.setMaterial(asdf);
Теперь, очевидно, этот код не работает, но я думаю, что это идея / поток того, что я пытаюсь сделать.
1 ответ
Вы правы в одном, PhongMaterial
занимает Color
как диффузный цвет, и это не позволяет Gradient
, Для этого следует принять Paint
, Но это не тот случай.
Поэтому мы должны искать разные альтернативы.
DiffuseMap
Если вы проверите PhongMaterial
Вы можете установить диффузную карту с изображением. Это означает, что вы можете использовать существующее изображение с некоторым градиентом и применить его к сфере.
Что-то вроде этого:
Sphere sphere = new Sphere(100);
PhongMaterial material = new PhongMaterial();
material.setDiffuseMap(new Image("http://westciv.com/images/wdblogs/radialgradients/simpleclorstops.png"));
sphere.setMaterial(material);
даст следующий результат:
Динамическая Диффузная Карта
Очевидно, что это имеет недостаток в зависимости от статического изображения. Что если вы хотите изменить это динамически?
Вы можете сделать это, если вы сгенерируете свой радиальный градиент, визуализируете его на вторичной сцене и сделаете его снимок. Этот снимок возвращает WritableImage
что вы можете использовать непосредственно в качестве диффузной карты.
Что-то вроде этого:
Scene aux = new Scene(new StackPane(), 100, 100,
new RadialGradient(0, 0, 0.5, 0.5, 1, true, CycleMethod.REPEAT,
new Stop(0, Color.GREEN), new Stop(0.4, Color.YELLOW),
new Stop(0.6, Color.BLUE), new Stop(0.7, Color.RED)));
WritableImage snapshot = aux.snapshot(null);
Sphere sphere = new Sphere(100);
PhongMaterial material = new PhongMaterial();
material.setDiffuseMap(snapshot);
sphere.setMaterial(material);
Теперь у вас будет:
Карта плотности
Есть еще один вариант использования математической функции для создания карты плотности, и цвета будут заданы отображением этой функции.
Для этого вы не можете использовать встроенный Sphere
, но вы должны либо создать свой собственный TriangleMesh
и поиграйте с текстурными координатами, или вы можете просто использовать FXyz, библиотеку JavaFX 3D с открытым исходным кодом с множеством различных примитивов и параметров текстуры.
Для этого случая вы можете получить библиотеку из Maven Central (org.fxyz3d:fxyz3d:0.3.0
), использовать SegmentedSphereMesh
управления, а затем выберите режим текстуры `Vertices3D:
SegmentedSphereMesh sphere = new SegmentedSphereMesh(100);
sphere.setTextureModeVertices3D(1530, p -> p.z);
Обратите внимание, что функция в этом случае просто основана на z
координаты, но, очевидно, вы можете изменить это при необходимости.
Проверьте библиотеку (есть сэмплер), чтобы изучить другие варианты.