FIx: Fixed Coverage Screenshots And htmlRepot.
This commit is contained in:
@@ -0,0 +1,515 @@
|
||||
|
||||
|
||||
|
||||
<!DOCTYPE html>
|
||||
<html id="htmlId">
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
|
||||
<title>Coverage Report > FireParticleSystem</title>
|
||||
<style type="text/css">
|
||||
@import "../../css/coverage.css";
|
||||
@import "../../css/idea.min.css";
|
||||
</style>
|
||||
<script type="text/javascript" src="../../js/highlight.min.js"></script>
|
||||
<script type="text/javascript" src="../../js/highlightjs-line-numbers.min.js"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div class="content">
|
||||
<div class="breadCrumbs">
|
||||
Current scope: <a href="../../index.html">all classes</a>
|
||||
<span class="separator">|</span>
|
||||
<a href="../index.html">it.polimi.ingsw.gc14.View.GUI</a>
|
||||
</div>
|
||||
|
||||
<h1>Coverage Summary for Class: FireParticleSystem (it.polimi.ingsw.gc14.View.GUI)</h1>
|
||||
|
||||
<table class="coverageStats">
|
||||
|
||||
<tr>
|
||||
<th class="name">Class</th>
|
||||
<th class="coverageStat
|
||||
">
|
||||
Method, %
|
||||
</th>
|
||||
<th class="coverageStat
|
||||
">
|
||||
Branch, %
|
||||
</th>
|
||||
<th class="coverageStat
|
||||
">
|
||||
Line, %
|
||||
</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name">FireParticleSystem</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/5)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/29)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/49)
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name">FireParticleSystem$1</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/2)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/2)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/4)
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name">FireParticleSystem$Particle</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/7)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/40)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/69)
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td class="name"><strong>Total</strong></td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/14)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/71)
|
||||
</span>
|
||||
</td>
|
||||
<td class="coverageStat">
|
||||
<span class="percent">
|
||||
0%
|
||||
</span>
|
||||
<span class="absValue">
|
||||
(0/122)
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
<br/>
|
||||
<br/>
|
||||
|
||||
|
||||
<pre>
|
||||
<code class="sourceCode" id="sourceCode"> package it.polimi.ingsw.gc14.View.GUI;
|
||||
|
||||
import javafx.animation.AnimationTimer;
|
||||
import javafx.scene.Scene;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.scene.paint.Color;
|
||||
import javafx.scene.shape.Circle;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* Ambient fire-particle effect rendered on a transparent overlay pane.
|
||||
*
|
||||
* <p>Three particle types float from the screen corners toward the center:
|
||||
* <ul>
|
||||
* <li><b>embers</b> (type 0) — slow, glowing orange circles with a soft halo.</li>
|
||||
* <li><b>sparks</b> (type 1) — fast, short-lived bright particles.</li>
|
||||
* <li><b>dust</b> (type 2) — large, translucent brown drifting circles.</li>
|
||||
* </ul>
|
||||
*
|
||||
* <p>Call {@link #start()} after adding {@link #getPane()} to the scene graph
|
||||
*/
|
||||
public class FireParticleSystem {
|
||||
|
||||
/** Maximum number of live particles at any given time. */
|
||||
private static final int MAX_PARTICLES = 30;
|
||||
/** Minimum nanoseconds between particle spawn batches. */
|
||||
private static final long SPAWN_INTERVAL_NS = 100_000_000L;
|
||||
/** Minimum nanoseconds between rendered frames (30 fps cap). */
|
||||
private static final long FRAME_INTERVAL_NS = 1_000_000_000L / 30;
|
||||
/** Physics update steps applied per rendered frame (multiplies effective speed). */
|
||||
private static final int STEPS_PER_FRAME = 3;
|
||||
|
||||
/** Mouse-transparent overlay pane that hosts all particle nodes. */
|
||||
private final Pane pane;
|
||||
/** The scene whose dimensions are used to position and fade particles. */
|
||||
private final Scene scene;
|
||||
/** Currently live particles. */
|
||||
<b class="nc"> private final List<Particle> particles = new ArrayList<>();</b>
|
||||
/** Shared random source for particle initialization and physics noise. */
|
||||
<b class="nc"> private final Random rnd = new Random();</b>
|
||||
/** Timestamp (ns) of the last particle spawn batch. */
|
||||
<b class="nc"> private long lastSpawn = 0;</b>
|
||||
/** Timestamp (ns) of the last rendered frame. */
|
||||
<b class="nc"> private long lastFrame = 0;</b>
|
||||
/** {@code true} after the first tick pre-populates the particle pool. */
|
||||
<b class="nc"> private boolean warmedUp = false;</b>
|
||||
|
||||
/**
|
||||
* Creates the particle system bound to the given scene.
|
||||
* The internal overlay pane is transparent and mouse-transparent.
|
||||
*
|
||||
* @param scene the scene whose dimensions are used for particle positioning and fading.
|
||||
*/
|
||||
<b class="nc"> public FireParticleSystem(Scene scene) {</b>
|
||||
<b class="nc"> this.scene = scene;</b>
|
||||
<b class="nc"> pane = new Pane();</b>
|
||||
<b class="nc"> pane.setMouseTransparent(true);</b>
|
||||
<b class="nc"> pane.setPickOnBounds(false);</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the transparent overlay pane that holds all particle nodes.
|
||||
*
|
||||
* @return the mouse-transparent {@link Pane} overlay.
|
||||
*/
|
||||
<b class="nc"> public Pane getPane() { return pane; }</b>
|
||||
|
||||
/** Starts the animation timer. */
|
||||
public void start() {
|
||||
<b class="nc"> AnimationTimer timer = new AnimationTimer() {</b>
|
||||
@Override
|
||||
public void handle(long now) {
|
||||
<b class="nc"> if (now - lastFrame < FRAME_INTERVAL_NS) return;</b>
|
||||
<b class="nc"> lastFrame = now;</b>
|
||||
<b class="nc"> tick(now);</b>
|
||||
}
|
||||
};
|
||||
<b class="nc"> timer.start();</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Advances the simulation by one frame: pre-warms on first call, spawns new particles,
|
||||
* steps existing ones, removes dead ones, and updates their visual state.
|
||||
*
|
||||
* @param now the current timestamp in nanoseconds from the animation timer.
|
||||
*/
|
||||
private void tick(long now) {
|
||||
<b class="nc"> double w = scene.getWidth();</b>
|
||||
<b class="nc"> double h = scene.getHeight();</b>
|
||||
<b class="nc"> if (w == 0 || h == 0) return;</b>
|
||||
|
||||
<b class="nc"> if (!warmedUp) {</b>
|
||||
<b class="nc"> warmedUp = true;</b>
|
||||
<b class="nc"> for (int i = 0; i < MAX_PARTICLES; i++) {</b>
|
||||
<b class="nc"> Particle p = spawnParticle(w, h);</b>
|
||||
<b class="nc"> int advance = rnd.nextInt(800) + 100;</b>
|
||||
<b class="nc"> for (int f = 0; f < advance; f++) p.update();</b>
|
||||
<b class="nc"> if (!p.isDead(w, h)) {</b>
|
||||
<b class="nc"> p.addTo(pane);</b>
|
||||
<b class="nc"> p.updateVisual(w, h);</b>
|
||||
<b class="nc"> particles.add(p);</b>
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
<b class="nc"> if (now - lastSpawn > SPAWN_INTERVAL_NS && particles.size() < MAX_PARTICLES) {</b>
|
||||
<b class="nc"> lastSpawn = now;</b>
|
||||
<b class="nc"> int count = rnd.nextInt(2) + 1;</b>
|
||||
<b class="nc"> for (int i = 0; i < count && particles.size() < MAX_PARTICLES; i++) {</b>
|
||||
<b class="nc"> Particle p = spawnParticle(w, h);</b>
|
||||
<b class="nc"> p.addTo(pane);</b>
|
||||
<b class="nc"> particles.add(p);</b>
|
||||
}
|
||||
}
|
||||
|
||||
<b class="nc"> Iterator<Particle> it = particles.iterator();</b>
|
||||
<b class="nc"> while (it.hasNext()) {</b>
|
||||
<b class="nc"> Particle p = it.next();</b>
|
||||
<b class="nc"> for (int s = 0; s < STEPS_PER_FRAME; s++) p.update();</b>
|
||||
<b class="nc"> if (p.isDead(w, h)) {</b>
|
||||
<b class="nc"> p.removeFrom(pane);</b>
|
||||
<b class="nc"> it.remove();</b>
|
||||
} else {
|
||||
<b class="nc"> p.updateVisual(w, h);</b>
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new particle starting near one of the four screen corners.
|
||||
*
|
||||
* @param w scene width in pixels.
|
||||
* @param h scene height in pixels.
|
||||
* @return the newly constructed {@link Particle}.
|
||||
*/
|
||||
private Particle spawnParticle(double w, double h) {
|
||||
<b class="nc"> int corner = rnd.nextInt(4);</b>
|
||||
<b class="nc"> double margin = 0.12;</b>
|
||||
double x, y;
|
||||
<b class="nc"> switch (corner) {</b>
|
||||
<b class="nc"> case 0 -> { x = rnd.nextDouble() * w * margin; y = h - rnd.nextDouble() * h * margin; }</b>
|
||||
<b class="nc"> case 1 -> { x = w - rnd.nextDouble() * w * margin; y = h - rnd.nextDouble() * h * margin; }</b>
|
||||
<b class="nc"> case 2 -> { x = rnd.nextDouble() * w * margin; y = rnd.nextDouble() * h * margin; }</b>
|
||||
<b class="nc"> default -> { x = w - rnd.nextDouble() * w * margin; y = rnd.nextDouble() * h * margin; }</b>
|
||||
}
|
||||
<b class="nc"> return new Particle(x, y, w, h, corner, rnd);</b>
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* A single fire particle with position, velocity, wobble, and JavaFX visual nodes.
|
||||
* Particles are typed: 0 = ember, 1 = spark, 2 = dust.
|
||||
*/
|
||||
private static class Particle {
|
||||
|
||||
/** Current X position in scene pixels. */
|
||||
double x;
|
||||
/** Current Y position in scene pixels. */
|
||||
double y;
|
||||
/** Horizontal velocity component. */
|
||||
double vx;
|
||||
/** Vertical velocity component. */
|
||||
double vy;
|
||||
/** Remaining life fraction (1.0 = full, 0.0 = dead); only decrements for sparks. */
|
||||
double life;
|
||||
/** Visual radius of the particle's core circle. */
|
||||
final double size;
|
||||
/** Current phase of the sinusoidal wobble. */
|
||||
double wobblePhase;
|
||||
/** Angular speed of the wobble oscillation. */
|
||||
final double wobbleSpeed;
|
||||
/** Amplitude factor of the wobble displacement. */
|
||||
final double wobbleAmp;
|
||||
/** Particle type: 0 = ember, 1 = spark, 2 = dust. */
|
||||
final int type;
|
||||
/** Shared random source used during physics updates. */
|
||||
final Random rnd;
|
||||
|
||||
/** Primary visible circle node. */
|
||||
final Circle core;
|
||||
/** Soft glow halo circle behind {@link #core}; non-null only for embers (type 0). */
|
||||
final Circle glow;
|
||||
|
||||
/**
|
||||
* Initializes the particle at position ({@code x}, {@code y}) with velocity
|
||||
* aimed roughly from the given {@code corner} toward the scene center.
|
||||
*
|
||||
* @param x spawn X coordinate.
|
||||
* @param y spawn Y coordinate.
|
||||
* @param w scene width (used to compute target direction).
|
||||
* @param h scene height (used to compute target direction).
|
||||
* @param corner spawn corner index: 0 = bottom-left, 1 = bottom-right, 2 = top-left, 3 = top-right.
|
||||
* @param rnd shared random source.
|
||||
*/
|
||||
<b class="nc"> Particle(double x, double y, double w, double h, int corner, Random rnd) {</b>
|
||||
<b class="nc"> this.x = x;</b>
|
||||
<b class="nc"> this.y = y;</b>
|
||||
<b class="nc"> this.life = 1.0;</b>
|
||||
<b class="nc"> this.rnd = rnd;</b>
|
||||
<b class="nc"> this.type = weightedType(rnd);</b>
|
||||
|
||||
<b class="nc"> double targetX = (corner == 0 || corner == 2) ? w * 0.75 : w * 0.25;</b>
|
||||
<b class="nc"> double targetY = (corner == 0 || corner == 1) ? h * 0.25 : h * 0.75;</b>
|
||||
<b class="nc"> double baseAngle = Math.atan2(targetY - y, targetX - x);</b>
|
||||
<b class="nc"> double angle = baseAngle + (rnd.nextDouble() - 0.5) * (Math.PI / 3.5);</b>
|
||||
|
||||
double speed;
|
||||
<b class="nc"> if (type == 0) {</b>
|
||||
<b class="nc"> speed = 0.5 + rnd.nextDouble() * 0.7;</b>
|
||||
<b class="nc"> size = rnd.nextDouble() * 3 + 2;</b>
|
||||
<b class="nc"> glow = new Circle(size * 2.2);</b>
|
||||
<b class="nc"> core = new Circle(size / 2);</b>
|
||||
<b class="nc"> } else if (type == 1) {</b>
|
||||
<b class="nc"> speed = 1.5 + rnd.nextDouble() * 2.0;</b>
|
||||
<b class="nc"> size = rnd.nextDouble() * 1.5 + 0.5;</b>
|
||||
<b class="nc"> glow = null;</b>
|
||||
<b class="nc"> core = new Circle(size / 2);</b>
|
||||
} else {
|
||||
<b class="nc"> speed = 0.2 + rnd.nextDouble() * 0.35;</b>
|
||||
<b class="nc"> size = rnd.nextDouble() * 8 + 5;</b>
|
||||
<b class="nc"> glow = null;</b>
|
||||
<b class="nc"> core = new Circle(size);</b>
|
||||
<b class="nc"> core.setFill(Color.color(0.55, 0.38, 0.22));</b>
|
||||
}
|
||||
|
||||
<b class="nc"> vx = Math.cos(angle) * speed;</b>
|
||||
<b class="nc"> vy = Math.sin(angle) * speed;</b>
|
||||
<b class="nc"> wobblePhase = rnd.nextDouble() * Math.PI * 2;</b>
|
||||
<b class="nc"> wobbleSpeed = 0.025 + rnd.nextDouble() * 0.04;</b>
|
||||
<b class="nc"> wobbleAmp = 0.1 + rnd.nextDouble() * 0.4;</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a particle type weighted toward embers (55% ember, 23% spark, 22% dust).
|
||||
*
|
||||
* @param rnd the random source.
|
||||
* @return particle type: 0, 1, or 2.
|
||||
*/
|
||||
private static int weightedType(Random rnd) {
|
||||
<b class="nc"> double r = rnd.nextDouble();</b>
|
||||
<b class="nc"> if (r < 0.55) return 0;</b>
|
||||
<b class="nc"> if (r < 0.78) return 1;</b>
|
||||
<b class="nc"> return 2;</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds this particle's visual nodes to {@code pane} (glow first so core renders on top).
|
||||
*
|
||||
* @param pane the overlay pane to add nodes to.
|
||||
*/
|
||||
void addTo(Pane pane) {
|
||||
<b class="nc"> if (glow != null) pane.getChildren().add(glow);</b>
|
||||
<b class="nc"> pane.getChildren().add(core);</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes this particle's visual nodes from {@code pane}.
|
||||
*
|
||||
* @param pane the overlay pane to remove nodes from.
|
||||
*/
|
||||
void removeFrom(Pane pane) {
|
||||
<b class="nc"> pane.getChildren().remove(core);</b>
|
||||
<b class="nc"> if (glow != null) pane.getChildren().remove(glow);</b>
|
||||
}
|
||||
|
||||
/** Advances this particle by one physics step: applies wobble, moves, and decrements spark life. */
|
||||
void update() {
|
||||
<b class="nc"> wobblePhase += wobbleSpeed;</b>
|
||||
<b class="nc"> vx += Math.sin(wobblePhase) * wobbleAmp * 0.05;</b>
|
||||
<b class="nc"> vy += Math.cos(wobblePhase) * wobbleAmp * 0.02;</b>
|
||||
<b class="nc"> x += vx;</b>
|
||||
<b class="nc"> y += vy;</b>
|
||||
<b class="nc"> if (type == 1) life -= 0.008 + rnd.nextDouble() * 0.006;</b>
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns {@code true} when this particle has left the scene bounds or, for sparks, its life reached zero.
|
||||
*
|
||||
* @param w scene width.
|
||||
* @param h scene height.
|
||||
* @return {@code true} if the particle should be removed.
|
||||
*/
|
||||
boolean isDead(double w, double h) {
|
||||
<b class="nc"> double pad = size * 4;</b>
|
||||
<b class="nc"> return x < -pad || x > w + pad || y < -pad || y > h + pad</b>
|
||||
|| (type == 1 && life <= 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates color, opacity, and translate position of this particle's visual nodes
|
||||
* based on distance from scene edges and remaining life.
|
||||
*
|
||||
* @param w scene width.
|
||||
* @param h scene height.
|
||||
*/
|
||||
void updateVisual(double w, double h) {
|
||||
<b class="nc"> double edge = Math.min(w, h) * 0.05;</b>
|
||||
<b class="nc"> double fadeX = Math.min(x / edge, Math.min((w - x) / edge, 1.0));</b>
|
||||
<b class="nc"> double fadeY = Math.min(y / edge, Math.min((h - y) / edge, 1.0));</b>
|
||||
<b class="nc"> double posAlpha = Math.max(0, Math.min(fadeX, fadeY));</b>
|
||||
<b class="nc"> double lifeAlpha = (type == 1) ? Math.min(life * 2.0, 1.0) : 1.0;</b>
|
||||
<b class="nc"> double alpha = posAlpha * lifeAlpha;</b>
|
||||
|
||||
<b class="nc"> core.setTranslateX(x);</b>
|
||||
<b class="nc"> core.setTranslateY(y);</b>
|
||||
|
||||
<b class="nc"> if (type == 0) {</b>
|
||||
<b class="nc"> double dist = Math.sqrt((x - w/2) * (x - w/2) + (y - h/2) * (y - h/2));</b>
|
||||
<b class="nc"> double hotness = Math.max(0, 1.0 - dist / (Math.sqrt(w * w + h * h) * 0.4));</b>
|
||||
<b class="nc"> double g = 0.3 + hotness * 0.5;</b>
|
||||
<b class="nc"> core.setFill(Color.color(1.0, g, 0.0));</b>
|
||||
<b class="nc"> core.setOpacity(alpha * 0.88);</b>
|
||||
<b class="nc"> glow.setTranslateX(x);</b>
|
||||
<b class="nc"> glow.setTranslateY(y);</b>
|
||||
<b class="nc"> glow.setFill(Color.color(1.0, g * 0.35, 0.0));</b>
|
||||
<b class="nc"> glow.setOpacity(alpha * 0.10);</b>
|
||||
<b class="nc"> } else if (type == 1) {</b>
|
||||
<b class="nc"> double brightness = Math.min(life * 2.5, 1.0);</b>
|
||||
<b class="nc"> core.setFill(Color.color(1.0, brightness * 0.85 + 0.15, brightness * 0.15));</b>
|
||||
<b class="nc"> core.setOpacity(alpha);</b>
|
||||
} else {
|
||||
<b class="nc"> core.setOpacity(alpha * 0.20);</b>
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</code>
|
||||
</pre>
|
||||
</div>
|
||||
|
||||
<script type="text/javascript">
|
||||
(function() {
|
||||
var msie = false, msie9 = false;
|
||||
/*@cc_on
|
||||
msie = true;
|
||||
@if (@_jscript_version >= 9)
|
||||
msie9 = true;
|
||||
@end
|
||||
@*/
|
||||
|
||||
if (!msie || msie && msie9) {
|
||||
hljs.highlightAll()
|
||||
hljs.initLineNumbersOnLoad();
|
||||
}
|
||||
})();
|
||||
</script>
|
||||
|
||||
<div class="footer">
|
||||
|
||||
<div style="float:right;">generated on 2026-06-19 22:53</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
Reference in New Issue
Block a user