local transforms = asset.require("scene/solarsystem/sun/transforms")
local earth_transforms = asset.require("scene/solarsystem/planets/earth/transforms")

local equatorialRotationMatrix = {
  -0.05487554,  0.4941095, -0.8676661,
  -0.8734371 , -0.4448296, -0.1980764,
  -0.483835  ,  0.7469823,  0.4559838
}

local eclipticRotationMatrix = {
  -0.05487554,  0.4941095, -0.8676661,
  -0.9938214 , -0.1109906, -0.0003515167,
  -0.09647644,  0.8622859,  0.4971472
}

local speck = asset.syncedResource({
  Name = "Grids Speck Files",
  Type = "HttpSynchronization",
  Identifier = "digitaluniverse_grids_speck",
  Version = 2
})

local radio = {
  Identifier = "RadioSphere",
  Parent = earth_transforms.EarthBarycenter.Identifier,
  Transform = {
    Scale = {
      Type = "TimeDependentScale",
      -- First TV signals strong enough to leave the ionosphere
      ReferenceDate = "1936 AUG 01 12:00:00",
      Speed = 299792458 -- c
    }, 
    Rotation = {
      Type = "StaticRotation",
      Rotation = equatorialRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableSphericalGrid",
    Enabled = false,
    Opacity = 1.0,
    Color = { 0.3, 0.84, 1.0 },
    LineWidth = 2.0
  },
  GUI = {
    Name = "Radio Sphere",
    Path = "/Other/Grids"
  }
}

local oort = {
  Identifier = "OortSphere",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Scale = {
      Type = "StaticScale",
      Scale = 7.47989845E15
    }, 
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableSphericalGrid",
    Enabled = false,
    Opacity = 0.8,
    Color = { 0.8, 0.4, 0.4 },
    LineWidth = 2.0
  },
  GUI = {
    Name = "Oort Sphere",
    Path = "/Other/Grids"
  }
}

local ecliptic = {
  Identifier = "EclipticSphere",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Scale = {
      Type = "StaticScale",
      Scale = 9.46377307652E17
    }, 
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableSphericalGrid",
    Enabled = false,
    Opacity = 1.0,
    Color = { 0.74, 0.26, 0.26 },
    LineWidth = 2.0
  },
  GUI = {
    Name = "Ecliptic Sphere",
    Path = "/Other/Grids"
  }
}

local eclipticLabels = {
  Identifier = "EclipticSphereLabels",
  Parent = transforms.SolarSystemBarycenter.Name,
  Renderable = {
    Type = "RenderableBillboardsCloud",
    Enabled = false,
    Color = { 1.0, 1.0, 1.0 },
    Opacity = 0.65,
    LabelFile = speck .. "eclip.label",
    Unit = "pc",
    DrawLabels = true,
    TextColor = { 0.5, 0.5, 0.5 },
    TextSize = 14.75,
    TextMinMaxSize = { 1, 50 },
    TransformationMatrix = {
      -0.05487554,  0.4941095, -0.8676661,    0.0,
      -0.9938214 , -0.1109906, -0.0003515167, 0.0,
      -0.09647644,  0.8622859,  0.4971472,    0.0,
      0.0,          0.0,        0.0,          1.0
    }
  },
  GUI = {
    Name = "Ecliptic Sphere Labels",
    Path = "/Other/Grids"
  }
}

local equatorial = {
  Identifier = "EquatorialSphere",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Scale = {
      Type = "StaticScale",
      Scale = 4.28601E17;
    }, 
    Rotation = {
      Type = "StaticRotation",
      Rotation = equatorialRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableSphericalGrid",
    Enabled = false,
    Opacity = 0.8,
    Color = { 0.69, 0.68, 0.29 },
    LineWidth = 2.0
  },
  GUI = {
    Name = "Equatorial Sphere",
    Path = "/Other/Grids"
  }
}

local equatorialLabels = {
  Identifier = "EquatorialSphereLabels",
  Parent = transforms.SolarSystemBarycenter.Name,
  Renderable = {
    Type = "RenderableBillboardsCloud",
    Enabled = false,
    Color = { 1.0, 1.0, 1.0 },
    Opacity = 0.65,
    LabelFile = speck .. "radec.label",
    Unit = "pc",
    DrawLabels = true,
    TextColor = { 0.5, 0.5, 0.5 },
    TextSize = 14.5,
    TextMinMaxSize = { 2, 70 },
    TransformationMatrix = {
      -0.05487554,  0.4941095, -0.8676661, 0.0,
      -0.8734371 , -0.4448296, -0.1980764, 0.0,
      -0.483835  ,  0.7469823,  0.4559838, 0.0,
        0.0       ,  0.0      ,  0.0      , 1.0
    }
  },
  GUI = {
    Name = "Equatorial Sphere Labels",
    Path = "/Other/Grids"
  }
}

local galactic = {
  Identifier = "GalacticSphere",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Scale = {
      Type = "StaticScale",
      Scale = 9.46377307652E18;
    }
  },
  Renderable = {
    Type = "RenderableSphericalGrid",
    Enabled = false,
    LineWidth = 2.0,
    Opacity = 1.0,
    Color = { 0.0, 0.6, 0.6 }
  },
  GUI = {
    Name = "Galactic Sphere",
    Path = "/Other/Grids"
  }
}

local galacticLabels = {
  Identifier = "GalacticSphereLabels",
  Parent = transforms.SolarSystemBarycenter.Name,
  Renderable = {
    Type = "RenderableBillboardsCloud",
    Enabled = false,
    Color = { 1.0, 1.0, 1.0 },
    Opacity = 0.65,
    LabelFile = speck .. "galac.label",
    Unit = "pc",
    DrawLabels = true,
    TextColor = { 0.5, 0.5, 0.5 },
    TextSize = 15.8,
    TextMinMaxSize = { 1, 100 }
  },
  GUI = {
    Name = "Galactic Sphere Labels",
    Path = "/Other/Grids"
  }
}

local plane1ld = {
  Identifier = "1ldGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "1ld.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "1ld.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 10.3,
    TextMinMaxSize = { 0, 30 },
    Unit = "Km"
  },
  GUI = {
    Name = "1ld Grid",
    Path = "/Other/Grids"
  }
}

local plane1lm = {
  Identifier = "1lmGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "1lm.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "1lm.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 11.8,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "1lm Grid",
    Path = "/Other/Grids"
  }
}

local plane1ly = {
  Identifier = "1lyGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "1ly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "1ly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 13.0,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "1ly Grid",
    Path = "/Other/Grids"
  }
}

local plane10ly = {
  Identifier = "10lyGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "10ly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "10ly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 14.17,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "10ly Grid",
    Path = "/Other/Grids"
  }
}

local plane100ly = {
  Identifier = "100lyGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "100ly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "100ly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 15.0,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "100ly Grid",
    Path = "/Other/Grids"
  }
}

local plane1kly = {
  Identifier = "1klyGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "1kly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "1kly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 16.0,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "1kly Grid",
    Path = "/Other/Grids"
  }
}

local plane10kly = {
  Identifier = "10klyGrid",
  Parent = transforms.SolarSystemBarycenter.Name,
  Transform = {
    Rotation = {
      Type = "StaticRotation",
      Rotation = eclipticRotationMatrix
    }
  },
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "10kly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "10kly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 17.25,
    TextMinMaxSize = { 0, 30 },
    Unit = "pc"
  },
  GUI = {
    Name = "10kly Grid",
    Path = "/Other/Grids"
  }
}

local plane100kly = {
  Identifier = "100klyGrid",
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "100kly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "100kly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 18.6,
    TextMinMaxSize = { 0, 30 },
    Unit = "Mpc"
  },
  GUI = {
    Name = "100kly Grid",
    Path = "/Other/Grids"
  }
}

local plane1Mly = {
  Identifier = "1MlyGrid",
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "1Mly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "1Mly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 19.6,
    TextMinMaxSize = { 0, 30 },
    Unit = "Mpc"
  },
  GUI = {
    Name = "1Mly Grid",
    Path = "/Other/Grids"
  }
}

local plane10Mly = {
  Identifier = "10MlyGrid",
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "10Mly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "10Mly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 20.6,
    TextMinMaxSize = { 0, 30 },
    Unit = "Mpc"
  },
  GUI = {
    Name = "10Mly Grid",
    Path = "/Other/Grids"
  }
}

local plane100Mly = {
  Identifier = "100MlyGrid",
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "100Mly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "100Mly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 21.6,
    TextMinMaxSize = { 0, 30 },
    Unit = "Mpc"
  },
  GUI = {
    Name = "100Mly Grid",
    Path = "/Other/Grids"
  }
}

local plane20Gly = {
  Identifier = "20GlyGrid",
  Renderable = {
    Type = "RenderableDUMeshes",
    Enabled = false,
    Opacity = 0.4,
    File = speck .. "20Gly.speck",
    MeshColor = {{ 0.1, 0.5, 0.6 }},
    LabelFile = speck .. "20Gly.label",
    TextColor = { 0.0, 0.2, 0.5 },
    TextSize = 23.6,
    TextMinMaxSize = { 0, 30 },
    Unit = "Mpc"
  },
  GUI = {
    Name = "20Gly Grid",
    Path = "/Other/Grids"
  }
}

local nodes = {
  radio, oort, ecliptic, eclipticLabels, equatorial, equatorialLabels,
  galactic, galacticLabels, plane1ld, plane1lm, plane1ly, plane10ly,
  plane100ly, plane1kly, plane10kly, plane100kly, plane1Mly, plane10Mly, plane100Mly,
  plane20Gly
}

asset.onInitialize(function()
  for i, node in ipairs(nodes) do
    openspace.addSceneGraphNode(node)
  end
end)
  
asset.onDeinitialize(function()
  for i = #nodes, 1, -1 do
    local node = nodes[i]
    openspace.removeSceneGraphNode(node)
  end
end)

for i, node in ipairs(nodes) do
  asset.export(node)
end



asset.meta = {
  Name = "Grids",
  Version = "2.1",
  Description = [[Various grids for showing size reference. Included: 10,000 light year
    grid, 10 light year grid, 20 billion light year grid, 10 million light year grid,
    100 light year grid, 100 million light year grid, Ecliptic Coordinate Sphere
    (500-light-year radius), Galactic Coordinate Sphere (1000-light-year radius),
    Galaxy Coordinate Grid, Celestial Coordinates / Radio Sphere (dynamic radius), 1
    billion light year grid, Celestial Coordinate Sphere (1000000-light-year radius),
    1,000 light year grid, 1 million light year grid, 1 light year grid]],
  Author = "Brian Abbott (AMNH)",
  URL = "https://www.amnh.org/research/hayden-planetarium/digital-universe",
  License = "AMNH Digital Universe"
}
