Java, JavaFX, Groovy, Grails …
Archive for December, 2009
JavaFX Bubble Breaker
Dec 18th
Originally posted by me on ericonjavafx.com
package bubblebreaker;
import javafx.stage.Stage;
import javafx.scene.text.Text;
import javafx.scene.text.Font;
import java.util.Random;
import javafx.animation.KeyFrame;
import javafx.animation.Timeline;
import javafx.scene.CustomNode;
import javafx.scene.effect.Glow;
import javafx.scene.Group;
import javafx.scene.paint.Color;
import javafx.scene.paint.RadialGradient;
import javafx.scene.paint.Stop;
import javafx.scene.Scene;
import javafx.scene.shape.Circle;
import javafx.scene.text.TextAlignment;
import javafx.scene.effect.InnerShadow;
import javafx.scene.effect.DropShadow;
import javafx.ext.swing.SwingButton;
var shift = 10; // from from scene.x and scene.y
var score_count: Number = 0;
var group: Group = new Group;
var slots = [];
var checkedGroup = Group {
};
var totalScore = 0;
function initGroup() {
group = new Group;
slots = [];
totalScore = 0;
for (i in [1..10]) {
for (j in [1..10]) {
insert "true" into slots;
insert Ball2 {
radius: 25;
vx: i * 50 + shift;
vy: j * 50 + (shift * 5);
slot: sizeof slots;
id: "{sizeof slots}";
} into group.content;
}
}
insert "true" into slots;//this is required for the 100 slot
}
initGroup();
function fallStep() {
var aball ;
//1. iterate through the entire set of balls
for (node in group.content) {
aball = (node as Ball2);
//2. if a ball is marked for deletion then remove from the group and mark the slot as empty(false)
if (aball.flaggedfordeletion) {
slots[aball.slot] = "false";
totalScore = totalScore + Integer.parseInt(aball.score);
delete aball from group.content;
}
//3. if the slot below a ball is empty and not ending with a 1
if (slots[aball.slot + 1] == "false") {
var aa = aball.slot + 1;
if (aa == 11 or aa == 21 or aa == 31 or aa == 41 or aa == 51 or aa == 61 or aa == 71 or aa == 81 or aa == 91) {
//do nothing
} else {
//4. mark the slot at taken(true) and move the ball into it....also mark the previous slot as empty(false);
slots[aball.slot + 1] = "true";
slots[aball.slot] = "false";
aball.slot = aball.slot + 1;
aball.vy = aball.vy + 50;
aball.id = "{aball.slot}";
}
}
}
}
function shiftRightStep() {
for (i in [100..20 step -10]) {
if (slots[i] == "false") {
for (j in [(i - 10)..1 step -1]) {
var aa =
group.lookup("{j}") as Ball2;
if (aa != null) {
slots[j + 10] = "true";
aa.slot = aa.slot + 10;
aa.vx = aa.vx + 50;
aa.id = "{aa.slot}";
slots[j] = "false";
}
}
}
}
}
function findNeighbors(aball: Ball2): Void {
var val ;
//1.calculate all neighbors
var r_nball = group.lookup("{aball.slot + 10}") as Ball2;
var d_nball = group.lookup("{aball.slot + 1}") as Ball2;
var l_nball = group.lookup("{aball.slot - 10}") as Ball2;
var u_nball = group.lookup("{aball.slot - 1}") as Ball2;
//2. make a recursive call to check left,right,up and down
if (aball.slot <= 90 and not r_nball.checked) {
r_nball.checked = true;
val = check(aball, r_nball);
if (val) {
aball.checked = true;
findNeighbors(r_nball);
}
}
if (aball.slot mod 10 != 0 and not d_nball.checked) {
d_nball.checked = true;
val = check(aball, d_nball);
if (val) {
findNeighbors(d_nball);
}
}
if (aball.slot > 10 and not l_nball.checked) {
l_nball.checked = true;
val = check(aball, l_nball);
if (val) {
findNeighbors(l_nball);
}
}
if (aball.slot mod 10 != 1 and not u_nball.checked) {
u_nball.checked = true;
val = check(aball, u_nball);
if (val) {
findNeighbors(u_nball);
}
}
}
function check(aball: Ball2, u_nball: Ball2): Boolean {
var return_value: Boolean = false;
if (checkColor(aball, u_nball)) {
aball.effect = Glow {
level: .4
input: InnerShadow {
choke: 0.05
radius: 25
color: Color.BLACK
}
}
u_nball.effect = Glow {
level: .4
input: InnerShadow {
choke: 0.05
radius: 25
color: Color.BLACK
}
}
u_nball.initialSelect = true;
return_value = true;
}
return return_value;
}
function checkColor(aball: Ball2, nball: Ball2): Boolean {
var returnvalue: Boolean = false;
if (aball.colorval == nball.colorval) {
returnvalue = true;
}
return returnvalue;
}
function displayScore() {
for (node in group.content) {
var tball = (node as Ball2);
if (tball.effect != null) {
tball.score = "{score_count.intValue()}";
}
}
}
Timeline {
repeatCount: Timeline.INDEFINITE
keyFrames: KeyFrame {
time: 30ms
action: function () {
var aball ;
for (node in group.content) {
aball = (node as Ball2);
if (aball.flaggedfordeletion == true) {
for (i in [0..9]) {
fallStep();
}
for (i in [0..9]) {
shiftRightStep();
}
}
}
}
}
}.play();
class Ball2 extends CustomNode {
var radius: Number;
var vx: Number;
var vy: Number;
var slot: Integer;
var initialSelect: Boolean;
var flaggedfordeletion: Boolean;
var checked: Boolean;
var colorval ;
var score: String;
def acolor = [Color.ORANGE, Color.BLACK, Color.DODGERBLUE, Color.PURPLE];
var random: Random = Random {
};
override function create() {
colorval = random.nextInt(4);
Group {content: [
Circle {
translateX: bind vx
translateY: bind vy
radius: radius - 1
effect: DropShadow {
offsetX: 10
offsetY: 10
color: Color.BLACK
radius: 24
}
fill: RadialGradient {
radius: radius * .9;
focusX: radius * 0.2
focusY: radius * -8
proportional: false
stops: [
Stop {
offset: 0
color: Color.WHITE
}
Stop {
offset: 1
color: acolor[colorval];
}
]
}
onMousePressed: function (event) {
score_count = 0;
//1. for every event check to see if the a group has already been identified and this is the second click to initiate deletion
if (initialSelect) {
var flagged = [];//this is to check to see if only one ball is select FIX ME
for (node in group.content) {
var aball = (node as Ball2);
if (aball.initialSelect == true) {
insert aball into flagged;
}
}
if (sizeof flagged > 1) {//this is to check to see if only one ball is select FIX ME
for (flag in flagged) {
var f = (flag as Ball2);
f.flaggedfordeletion = true;
}
}
} else { //2. if we have a group identified but the user doesn't want to delete that group ( by selecting another groups ball) then
// remove the intialSelects and effects from the first group
for (node in group.content) {
var aball = (node as Ball2);
if (aball.initialSelect == true) {
aball.initialSelect = false;
aball.effect = null;
aball.score = "";
}
}
}
if (initialSelect == false) {
initialSelect = true;
findNeighbors(this);
for (node in group.content) {
var tball = (node as Ball2);
if (tball.effect != null) {
score_count = score_count + 1;
}
if (tball.checked == true) {
tball.checked = false;
}
}
if (score_count > 9) {
score_count = score_count * 9
}
if (score_count == 8 ) {
score_count = score_count * 7
}
if (score_count == 7) {
score_count = score_count * 6
}
if (score_count == 6) {
score_count = score_count * 5
}
if (score_count == 5) {
score_count = score_count * 5
}
if (score_count == 4) {
score_count = score_count * 3
}
if (score_count == 3) {
score_count = score_count * 2
}
displayScore();
}
}
}
Text {
font: Font {size: 12
}
x: bind vx - 5,
y: bind vy
textAlignment: TextAlignment.LEFT
content: bind "{score}";
}
]
}
}
}
var button = Group {
translateY: 610
translateX: 245
content: [
SwingButton {
text: "New Game"
action: function () {
initGroup()
}
}
]
}
var x = Stage {
title: "Bubble Breaker"
width: 600
height: 700
scene: Scene {
fill: Color.GREY;
content: bind [
button,
Text {
x: 220
y: 50
fill: Color.ORANGE
effect: Glow {
level: .8
input: InnerShadow {
choke: 0.05
radius: 2
color: Color.BLACK
}
}
font: Font {size: 30
}
content: "Score {totalScore}"
}
group
]
}
}Find the code on GitHub here
JavaFX Magic 8 Ball
Dec 18th
Originally posted by me on ericonjavafx.com
package magicanswers;
import javafx.lang.FX;
import javafx.scene.Group;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.media.Media;
import javafx.scene.media.MediaPlayer;
import javafx.scene.paint.Color;
import javafx.scene.paint.LinearGradient;
import javafx.scene.paint.Stop;
import javafx.scene.Scene;
import javafx.scene.shape.Rectangle;
import javafx.stage.Stage;
import magicanswers.Oracle;
var oracle = Oracle { }
var mediaUrl:String = "http://ericonjavafx.com/Magic8Ball/Opium.wav";
if(FX.getArgument("mediaURL") != null) {
mediaUrl = FX.getArgument("mediaURL").toString();
}
var music:MediaPlayer = MediaPlayer {
volume:.4;
media: Media {
source: mediaUrl
}
autoPlay: true
repeatCount:MediaPlayer.REPEAT_FOREVER
}
music.paused;
var stop_music:ImageView = ImageView {
opacity: 1.0
visible: true
x: 0
y: 675
fitWidth:100
preserveRatio: true
blocksMouse:true
image: Image {
url: "{__DIR__}Sound.png"
},
onMousePressed: function(e) {
if(music.paused){
music.play();
}else {
music.pause();
}
}
};
var scene:Scene;
Stage {
title: "Magic Eight Ball"
scene:
scene = Scene {
height: 700
width: 900
fill:null;
content: [
Group{
content:[ ImageView {
opacity: 1.0
visible: true
image: Image {
url: "{__DIR__}Background.png"
},
fitWidth:bind scene.width;
fitHeight:bind scene.height;
},oracle,
stop_music
]
}
]
}
};
package magicanswers;
import java.util.Random;
import javafx.animation.*;
import javafx.scene.*;
import javafx.scene.effect.DropShadow;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.paint.Color;
import javafx.scene.text.Font;
import javafx.scene.text.Text;
import javafx.scene.text.TextAlignment;
public class MessageObject extends CustomNode {
def rnd : Random = new Random();
public var content:String;
var image:Image = Image {
url: "{__DIR__}Triangle.png"
}
var imageView=ImageView {
image: bind image
visible: true
cache:true}
public override function create(): Node {
return Group {
content: [
imageView,
Text{
translateX: bind imageView.translateX + 31
translateY: bind imageView.translateY + 85
content:content;
font: Font {
size: 15
}
wrappingWidth: 100
textAlignment: TextAlignment.LEFT
fill:Color.LIGHTBLUE;
},
]
cache:true;
}
}
public var fade = Timeline {
def sx1 =.9; def sx2 = .5;
def sy1 =.9; def sy2 = .5;
def tx1 = 437; def tx2 = 437 ;
def ty1 = 300; def ty2 = 300;
def ro1 = this.rotate; def ro2 = rnd.nextDouble() * 400;
keyFrames: [
at(0s) {
this.opacity => .1 tween Interpolator.LINEAR;
this.scaleX => sx2 tween Interpolator.LINEAR;
this.scaleY => sy2 tween Interpolator.LINEAR;
this.translateX => tx2 tween Interpolator.LINEAR;
this.translateY => ty2 tween Interpolator.LINEAR;
this.rotate => ro2 tween Interpolator.LINEAR;
},
at(2s) {
this.opacity =>.5 tween Interpolator.LINEAR;
},
at(4s) {
this.opacity => 1.0 tween Interpolator.LINEAR;
this.scaleX => sx1 tween Interpolator.LINEAR;
this.scaleY => sy1 tween Interpolator.LINEAR;
this.translateX => tx1 tween Interpolator.LINEAR;
this.translateY => ty1 tween Interpolator.LINEAR;
this.rotate => ro1 tween Interpolator.LINEAR;
},
at(8s) {
this.opacity => .1 tween Interpolator.LINEAR;
},
KeyFrame {
time: 8s
action: function() {
delete this from (this.parent as Group).content;
}
}
]
}
};
package magicanswers;
import java.util.Random;
import javafx.animation.Interpolator;
import javafx.animation.KeyFrame;
import javafx.animation.Timeline;
import javafx.animation.transition.AnimationPath;
import javafx.animation.transition.PathTransition;
import javafx.scene.CustomNode;
import javafx.scene.effect.light.DistantLight;
import javafx.scene.effect.Lighting;
import javafx.scene.effect.Reflection;
import javafx.scene.Group;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.Node;
import javafx.scene.shape.ClosePath;
import javafx.scene.shape.HLineTo;
import javafx.scene.shape.MoveTo;
import javafx.scene.shape.Path;
public class Oracle extends CustomNode {
def rnd : Random = new Random();
//it appears that 9 words is the limit
var pool_of_answers = ["Who Knows","Absolutely","Maybe", "Yes", "No","Unclear at this time","Without a doubt"];
var answer_to_question = "";
var word:MessageObject;
var node:Node;
var flag_changeover:Boolean = false;
def path = [
MoveTo {
x: 500,
y:600 },
HLineTo{
x:525 },
HLineTo{
x:475}
ClosePath{ } ];
def animation = PathTransition
{
node: this;
path: AnimationPath.createFromPath(Path{
elements: path});
interpolate: true;
duration: .3s
repeatCount: 4
}
var image:Image = Image {
url: "{__DIR__}8ball.png"
preserveRatio: true
backgroundLoading: true
}
var image2:Image = Image {
url: "{__DIR__}8ball_view.png"
preserveRatio: true
backgroundLoading: true
}
public var changeover = Timeline {
keyFrames: [
at(0s) {
this.opacity => .9 tween Interpolator.LINEAR;
},
at(2s) {
this.opacity => 0 tween Interpolator.LINEAR;
},
at(4s) {
this.opacity => 1.0 tween Interpolator.LINEAR;
},
KeyFrame {
time: 2.0s
action: function() {
image=image2;
flag_changeover = true;
}
}
KeyFrame {
time:4.2s
action: function() {
generateMessage();
}
}
]
}
public override function create(): Node {
node = Group {
cache:true;
content: [
ImageView {
x: 250
y: 190
image: bind image
visible: true
cache:true
}
] // content
effect: Reflection {
topOffset:0.1;
fraction: 0.85
topOpacity:.3
bottomOpacity:0.1
input:Lighting {
light: DistantLight {
azimuth: -135
}
surfaceScale: 9
}
}
onMousePressed: function (event) {
if(not flag_changeover){
changeover.playFromStart();
}
else if(not animation.running and not word.fade.running ){
generateMessage();
}
}
}
}
function generateMessage(){
animation.playFromStart();
answer_to_question = pool_of_answers[
rnd.nextInt(sizeof pool_of_answers)];
word = MessageObject {
content: bind answer_to_question
};
insert word into (this.parent as Group).content;
word.fade.play();
}
}Get this code at GitHub.

