planetsfactory 0.0.2

Planet factory — classify, build and catalogue planets for any star system: Solar System, TRAPPIST-1, Kepler-90, Proxima Centauri, or fully custom worlds.
Documentation
use crate::config::parameters::*;
use std::f64::consts::PI;

pub struct RoguePlanet {
    pub name: String,
    pub mass: f64,
    pub radius: f64,
    pub age: f64,
    pub albedo: f64,
    pub iron_core_fraction: f64,
    pub velocity: f64,
}

impl RoguePlanet {
    pub fn new(name: &str, mass: f64, radius: f64, age: f64) -> Self {
        Self {
            name: name.to_string(),
            mass,
            radius,
            age,
            albedo: 0.1,
            iron_core_fraction: 0.30,
            velocity: 30.0e3,
        }
    }

    pub fn with_details(
        name: &str,
        mass: f64,
        radius: f64,
        age: f64,
        albedo: f64,
        iron_core_fraction: f64,
        velocity: f64,
    ) -> Self {
        Self {
            name: name.to_string(),
            mass,
            radius,
            age,
            albedo,
            iron_core_fraction,
            velocity,
        }
    }

    pub fn mass_earth(&self) -> f64 {
        self.mass / EARTH_MASS
    }

    pub fn radius_earth(&self) -> f64 {
        self.radius / EARTH_RADIUS
    }

    pub fn surface_gravity(&self) -> f64 {
        surface_gravity(self.mass, self.radius)
    }

    pub fn escape_velocity(&self) -> f64 {
        escape_velocity(self.mass, self.radius)
    }

    pub fn mean_density(&self) -> f64 {
        mean_density(self.mass, self.radius)
    }

    pub fn surface_temperature(&self) -> f64 {
        let internal_heat = self.radiogenic_heating();
        let area = 4.0 * PI * self.radius * self.radius;
        (internal_heat / (SIGMA_SB * area)).powf(0.25)
    }

    pub fn radiogenic_heating(&self) -> f64 {
        let rock_mass = self.mass * (1.0 - self.iron_core_fraction);
        let h0 = 5e-12;
        let tau = 1.25e9 * YEAR;
        rock_mass * h0 * (-self.age / tau).exp()
    }

    pub fn core_radius(&self) -> f64 {
        self.radius * self.iron_core_fraction.cbrt()
    }

    pub fn atmosphere_retained(&self) -> bool {
        let v_esc = self.escape_velocity();
        let t_surf = self.surface_temperature();
        let v_thermal = (3.0 * K_B * t_surf / (28.0 * 1.66e-27)).sqrt();
        v_esc > 6.0 * v_thermal
    }

    pub fn kinetic_energy(&self) -> f64 {
        0.5 * self.mass * self.velocity * self.velocity
    }

    pub fn capture_velocity(host_mass: f64, encounter_distance: f64) -> f64 {
        (2.0 * G * host_mass / encounter_distance).sqrt()
    }

    pub fn galactic_crossing_time(disk_height: f64) -> f64 {
        let v_z = 10.0e3;
        2.0 * disk_height / v_z
    }

    pub fn to_cartesian_free(&self) -> ([f64; 3], [f64; 3]) {
        ([0.0, 0.0, 0.0], [self.velocity, 0.0, 0.0])
    }
}