feat: enroute groups
This commit is contained in:
@@ -66,3 +66,7 @@ func (c *Cache) PutMaterial(pn uint, v float64) {
|
|||||||
func (c *Cache) RaceTechLevel(ri int, t game.Tech, v float64) {
|
func (c *Cache) RaceTechLevel(ri int, t game.Tech, v float64) {
|
||||||
c.raceTechLevel(ri, t, v)
|
c.raceTechLevel(ri, t, v)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c *Cache) ListRouteEligibleGroupIds(pn uint) iter.Seq[int] {
|
||||||
|
return c.listRouteEligibleGroupIds(pn)
|
||||||
|
}
|
||||||
|
|||||||
@@ -2,10 +2,13 @@ package controller_test
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"slices"
|
||||||
|
"testing"
|
||||||
|
|
||||||
"github.com/google/uuid"
|
"github.com/google/uuid"
|
||||||
"github.com/iliadenisov/galaxy/internal/controller"
|
"github.com/iliadenisov/galaxy/internal/controller"
|
||||||
"github.com/iliadenisov/galaxy/internal/model/game"
|
"github.com/iliadenisov/galaxy/internal/model/game"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@@ -67,6 +70,14 @@ var (
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
|
// [ ] Delete this fake test
|
||||||
|
func TestSlicesDelete(t *testing.T) {
|
||||||
|
sl := []int{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}
|
||||||
|
assert.Len(t, sl, 10)
|
||||||
|
sl = slices.DeleteFunc(sl, func(v int) bool { return v%2 == 0 })
|
||||||
|
assert.Len(t, sl, 5)
|
||||||
|
}
|
||||||
|
|
||||||
func assertNoError(err error) {
|
func assertNoError(err error) {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(fmt.Sprintf("init assertion failed: %v", err))
|
panic(fmt.Sprintf("init assertion failed: %v", err))
|
||||||
|
|||||||
@@ -1,8 +1,6 @@
|
|||||||
package controller
|
package controller
|
||||||
|
|
||||||
import (
|
import (
|
||||||
// "github.com/iliadenisov/galaxy/internal/controller"
|
|
||||||
e "github.com/iliadenisov/galaxy/internal/error"
|
|
||||||
// "github.com/iliadenisov/galaxy/internal/game/battle"
|
// "github.com/iliadenisov/galaxy/internal/game/battle"
|
||||||
"github.com/iliadenisov/galaxy/internal/model/game"
|
"github.com/iliadenisov/galaxy/internal/model/game"
|
||||||
)
|
)
|
||||||
@@ -17,12 +15,8 @@ func MakeTurn(c *Controller, r Repo, g *game.Game) error {
|
|||||||
// 02. Враждующие корабли вступают в схватку.
|
// 02. Враждующие корабли вступают в схватку.
|
||||||
battles := ProduceBattles(c.Cache)
|
battles := ProduceBattles(c.Cache)
|
||||||
|
|
||||||
// Internal control: after battles there are can't be groups with no ships left
|
// 03. Товары загружаются на корабли, находящиеся в начале грузовых маршрутов, и корабли входят в гиперпространство.
|
||||||
for i := range g.ShipGroups {
|
c.Cache.EnrouteGroups()
|
||||||
if g.ShipGroups[i].Number == 0 {
|
|
||||||
return e.NewGameStateError("")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*** Last steps ***/
|
/*** Last steps ***/
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,11 @@
|
|||||||
package controller
|
package controller
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"cmp"
|
||||||
|
"iter"
|
||||||
|
"math"
|
||||||
|
"slices"
|
||||||
|
|
||||||
e "github.com/iliadenisov/galaxy/internal/error"
|
e "github.com/iliadenisov/galaxy/internal/error"
|
||||||
"github.com/iliadenisov/galaxy/internal/model/game"
|
"github.com/iliadenisov/galaxy/internal/model/game"
|
||||||
"github.com/iliadenisov/galaxy/internal/util"
|
"github.com/iliadenisov/galaxy/internal/util"
|
||||||
@@ -82,3 +87,104 @@ func (c *Cache) RemovePlanetRoute(rt game.RouteType, origin uint) {
|
|||||||
delete(c.g.Map.Planet[pi].Route, rt)
|
delete(c.g.Map.Planet[pi].Route, rt)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: NOT IN THIS FUNC: remove routes if planet became uninhabited
|
||||||
|
func (c *Cache) EnrouteGroups() {
|
||||||
|
for pi := range c.g.Map.Planet {
|
||||||
|
if len(c.g.Map.Planet[pi].Route) == 0 {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
groups := slices.Collect(c.listRouteEligibleGroupIds(c.g.Map.Planet[pi].Number))
|
||||||
|
if len(groups) == 0 {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
sortGroups := func(g []int) {
|
||||||
|
// sort groups by largest CargoCapacity
|
||||||
|
slices.SortFunc(g, func(l, r int) int {
|
||||||
|
return cmp.Or(cmp.Compare(c.ShipGroup(r).CargoCapacity(c.ShipGroupShipClass(r)),
|
||||||
|
c.ShipGroup(l).CargoCapacity(c.ShipGroupShipClass(l))),
|
||||||
|
cmp.Compare(l, r))
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
reorderGroups := func(g []int) []int {
|
||||||
|
g = slices.DeleteFunc(g, func(i int) bool { return c.ShipGroup(i).State() != game.StateInOrbit })
|
||||||
|
sortGroups(g)
|
||||||
|
return g
|
||||||
|
}
|
||||||
|
|
||||||
|
sortGroups(groups)
|
||||||
|
|
||||||
|
p := c.MustPlanet(c.g.Map.Planet[pi].Number)
|
||||||
|
|
||||||
|
// COL -> CAP -> MAT -> EMPTY
|
||||||
|
for _, rt := range []game.RouteType{game.RouteColonist, game.RouteCapital, game.RouteMaterial, game.RouteEmpty} {
|
||||||
|
dest, ok := c.g.Map.Planet[pi].Route[rt]
|
||||||
|
if !ok {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
var res *float64
|
||||||
|
var ct game.CargoType
|
||||||
|
switch rt {
|
||||||
|
case game.RouteColonist:
|
||||||
|
res = &p.Colonists
|
||||||
|
ct = game.CargoColonist
|
||||||
|
case game.RouteCapital:
|
||||||
|
res = &p.Capital
|
||||||
|
ct = game.CargoCapital
|
||||||
|
case game.RouteMaterial:
|
||||||
|
res = &p.Material
|
||||||
|
ct = game.CargoMaterial
|
||||||
|
default:
|
||||||
|
for _, sgi := range groups {
|
||||||
|
c.LaunchShips(c.ShipGroup(sgi), dest)
|
||||||
|
}
|
||||||
|
groups = reorderGroups(groups)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
for res != nil && *res > 0 && len(groups) > 0 {
|
||||||
|
sgi := groups[0]
|
||||||
|
sg := c.ShipGroup(sgi)
|
||||||
|
st := c.ShipGroupShipClass(sgi)
|
||||||
|
ships := sg.Number
|
||||||
|
sgCapacity := sg.CargoCapacity(st)
|
||||||
|
toLoad := *res
|
||||||
|
if toLoad > sgCapacity {
|
||||||
|
toLoad = sgCapacity
|
||||||
|
} else if maxShips := uint(math.Ceil(toLoad / (sgCapacity / float64(ships)))); maxShips < ships {
|
||||||
|
newGroupIdx := c.breakGroupUnsafe(c.RaceIndex(sg.OwnerID), sgi, maxShips)
|
||||||
|
sg = c.ShipGroup(newGroupIdx)
|
||||||
|
}
|
||||||
|
// decrease planet resource
|
||||||
|
*res = *res - toLoad
|
||||||
|
// load group
|
||||||
|
sg.Load += toLoad
|
||||||
|
sg.CargoType = &ct
|
||||||
|
c.LaunchShips(sg, dest)
|
||||||
|
groups = reorderGroups(groups)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Cache) listRouteEligibleGroupIds(pn uint) iter.Seq[int] {
|
||||||
|
return func(yield func(int) bool) {
|
||||||
|
p := c.MustPlanet(pn)
|
||||||
|
for i := range c.ShipGroupsIndex() {
|
||||||
|
sg := c.ShipGroup(i)
|
||||||
|
st := c.ShipGroupShipClass(i)
|
||||||
|
if sg.OwnerID != p.Owner || // Planet must be owned by ships owner
|
||||||
|
sg.FleetID != nil || // Ships must not be part of a Fleet
|
||||||
|
sg.State() != game.StateInOrbit || // Ships must be only In_Orbit state
|
||||||
|
st.CargoBlockMass() == 0 || // Ship Class must have Cargo bays
|
||||||
|
sg.Load != 0 || // Ships must not be loaded for enrouting
|
||||||
|
sg.Destination != p.Number {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if !yield(i) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package controller_test
|
package controller_test
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"slices"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
e "github.com/iliadenisov/galaxy/internal/error"
|
e "github.com/iliadenisov/galaxy/internal/error"
|
||||||
@@ -89,3 +90,173 @@ func TestRemoveRoute(t *testing.T) {
|
|||||||
g.RemoveRoute(Race_0.Name, "COL", 1),
|
g.RemoveRoute(Race_0.Name, "COL", 1),
|
||||||
e.GenericErrorText(e.ErrInputEntityNotOwned))
|
e.GenericErrorText(e.ErrInputEntityNotOwned))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestListRouteEligibleGroupIds(t *testing.T) {
|
||||||
|
c, g := newCache()
|
||||||
|
|
||||||
|
// 1: idx = 0 / Ready to load
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 10))
|
||||||
|
|
||||||
|
// 2: idx = 1 / Has no cargo bay
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Gunship, R0_Planet_0_num, 1))
|
||||||
|
|
||||||
|
// 3: idx = 2 / In_Space
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 7))
|
||||||
|
c.ShipGroup(2).StateInSpace = &game.InSpace{
|
||||||
|
Origin: 2,
|
||||||
|
Range: 31.337,
|
||||||
|
}
|
||||||
|
|
||||||
|
// 4: idx = 3 / loaded with COL
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 11))
|
||||||
|
c.ShipGroup(3).CargoType = game.CargoColonist.Ref()
|
||||||
|
c.ShipGroup(3).Load = 1.234
|
||||||
|
|
||||||
|
// Foreign group -> idx 1
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 10))
|
||||||
|
assert.NoError(t, g.GiveawayGroup(Race_0.Name, Race_1.Name, 5, 0))
|
||||||
|
|
||||||
|
// 5: idx = 4 / Part of the Fleet
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 10))
|
||||||
|
assert.NoError(t, g.JoinShipGroupToFleet(Race_0.Name, "Fleet", 5, 0))
|
||||||
|
|
||||||
|
planet_0_groups := slices.Collect(c.ListRouteEligibleGroupIds(0))
|
||||||
|
assert.Len(t, planet_0_groups, 1)
|
||||||
|
for _, i := range planet_0_groups {
|
||||||
|
sg := c.ShipGroup(i)
|
||||||
|
st := c.ShipGroupShipClass(i)
|
||||||
|
assert.Equal(t, Race_0_ID, sg.OwnerID)
|
||||||
|
assert.Greater(t, sg.CargoCapacity(st), 0.)
|
||||||
|
assert.Equal(t, game.StateInOrbit, sg.State())
|
||||||
|
assert.Equal(t, 0., sg.Load)
|
||||||
|
assert.Nil(t, sg.FleetID)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestEnrouteGroups_SplitGroup(t *testing.T) {
|
||||||
|
c, g := newCache()
|
||||||
|
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "COL", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "MAT", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "CAP", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "EMP", R0_Planet_2_num, R1_Planet_1_num))
|
||||||
|
|
||||||
|
c.MustPlanet(R0_Planet_0_num).Colonists = 65
|
||||||
|
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 5)) // 21.0 per Ship
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(0).CargoCapacity(c.ShipGroupShipClass(0)))
|
||||||
|
|
||||||
|
c.EnrouteGroups()
|
||||||
|
|
||||||
|
assert.Len(t, slices.Collect(c.RaceShipGroups(Race_0_idx)), 2)
|
||||||
|
assert.Equal(t, game.StateInOrbit, c.ShipGroup(0).State())
|
||||||
|
assert.Equal(t, uint(1), c.ShipGroup(0).Number)
|
||||||
|
assert.Equal(t, 0., c.ShipGroup(0).Load)
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(1).State())
|
||||||
|
assert.Equal(t, uint(4), c.ShipGroup(1).Number)
|
||||||
|
assert.Equal(t, 65., c.ShipGroup(1).Load)
|
||||||
|
assert.Equal(t, 0., c.MustPlanet(R0_Planet_0_num).Colonists)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestEnrouteGroups_GroupSorting(t *testing.T) {
|
||||||
|
c, g := newCache()
|
||||||
|
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "COL", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "MAT", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "CAP", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
// assert.NoError(t, g.SetRoute(Race_0.Name, "EMP", R0_Planet_2_num, R1_Planet_1_num))
|
||||||
|
|
||||||
|
c.MustPlanet(R0_Planet_0_num).Colonists = 100
|
||||||
|
|
||||||
|
// 0: idx = 1
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 4)) // 21.0 per Ship
|
||||||
|
assert.Equal(t, 84., c.ShipGroup(0).CargoCapacity(c.ShipGroupShipClass(0)))
|
||||||
|
|
||||||
|
// 1: idx = 2
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 5)) // 21.0 per Ship
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(1).CargoCapacity(c.ShipGroupShipClass(1)))
|
||||||
|
|
||||||
|
c.EnrouteGroups()
|
||||||
|
|
||||||
|
assert.Len(t, slices.Collect(c.RaceShipGroups(Race_0_idx)), 2)
|
||||||
|
assert.Equal(t, game.StateInOrbit, c.ShipGroup(0).State())
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(1).State())
|
||||||
|
|
||||||
|
assert.Equal(t, 100., c.ShipGroup(1).Load)
|
||||||
|
assert.Equal(t, 0., c.MustPlanet(R0_Planet_0_num).Colonists)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestEnrouteGroups_LaunchOrder(t *testing.T) {
|
||||||
|
c, g := newCache()
|
||||||
|
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "COL", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "CAP", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "MAT", R0_Planet_0_num, R0_Planet_2_num))
|
||||||
|
assert.NoError(t, g.SetRoute(Race_0.Name, "EMP", R0_Planet_0_num, R1_Planet_1_num))
|
||||||
|
|
||||||
|
c.MustPlanet(R0_Planet_0_num).Colonists = 150
|
||||||
|
c.MustPlanet(R0_Planet_0_num).Capital = 100
|
||||||
|
c.MustPlanet(R0_Planet_0_num).Material = 20
|
||||||
|
|
||||||
|
// 0: idx = 1 (105 COL) ->
|
||||||
|
// 3: idx = 4 ( 45 COL)
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 5))
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(0).CargoCapacity(c.ShipGroupShipClass(0)))
|
||||||
|
|
||||||
|
// 1: idx = 2 (In_Orbit) ->
|
||||||
|
// 4: idx = 5 (20 MAT)
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 5))
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(1).CargoCapacity(c.ShipGroupShipClass(1)))
|
||||||
|
|
||||||
|
// 2: idx = 3 (100 CAP)
|
||||||
|
assert.NoError(t, c.CreateShips(Race_0_idx, Race_0_Freighter, R0_Planet_0_num, 5))
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(2).CargoCapacity(c.ShipGroupShipClass(2)))
|
||||||
|
|
||||||
|
c.EnrouteGroups()
|
||||||
|
|
||||||
|
assert.Len(t, slices.Collect(c.RaceShipGroups(Race_0_idx)), 5)
|
||||||
|
|
||||||
|
// full load of COL
|
||||||
|
sgi := 0
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(sgi).State())
|
||||||
|
assert.Equal(t, R0_Planet_2_num, c.ShipGroup(sgi).Destination)
|
||||||
|
assert.Equal(t, 105., c.ShipGroup(sgi).Load)
|
||||||
|
assert.NotNil(t, c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, game.CargoColonist, *c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, uint(5), c.ShipGroup(sgi).Number)
|
||||||
|
|
||||||
|
// rest of COL
|
||||||
|
sgi = 3
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(sgi).State())
|
||||||
|
assert.Equal(t, R0_Planet_2_num, c.ShipGroup(sgi).Destination)
|
||||||
|
assert.Equal(t, 45., c.ShipGroup(sgi).Load)
|
||||||
|
assert.NotNil(t, c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, game.CargoColonist, *c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, uint(3), c.ShipGroup(sgi).Number)
|
||||||
|
|
||||||
|
// full load of CAP
|
||||||
|
sgi = 2
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(sgi).State())
|
||||||
|
assert.Equal(t, R0_Planet_2_num, c.ShipGroup(sgi).Destination)
|
||||||
|
assert.Equal(t, 100., c.ShipGroup(sgi).Load)
|
||||||
|
assert.NotNil(t, c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, game.CargoCapital, *c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, uint(5), c.ShipGroup(sgi).Number)
|
||||||
|
|
||||||
|
// partial load of MAT
|
||||||
|
sgi = 4
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(sgi).State())
|
||||||
|
assert.Equal(t, R0_Planet_2_num, c.ShipGroup(sgi).Destination)
|
||||||
|
assert.Equal(t, 20., c.ShipGroup(sgi).Load)
|
||||||
|
assert.NotNil(t, c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, game.CargoMaterial, *c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, uint(1), c.ShipGroup(sgi).Number)
|
||||||
|
|
||||||
|
// empty / on_planet
|
||||||
|
sgi = 1
|
||||||
|
assert.Equal(t, game.StateLaunched, c.ShipGroup(sgi).State())
|
||||||
|
assert.Equal(t, R1_Planet_1_num, c.ShipGroup(sgi).Destination)
|
||||||
|
assert.Equal(t, 0., c.ShipGroup(sgi).Load)
|
||||||
|
assert.Nil(t, c.ShipGroup(sgi).CargoType)
|
||||||
|
assert.Equal(t, uint(1), c.ShipGroup(sgi).Number)
|
||||||
|
}
|
||||||
|
|||||||
@@ -504,6 +504,10 @@ func (c *Cache) breakGroupSafe(ri int, groupIndex uint, newGroupShips uint) (int
|
|||||||
if c.ShipGroup(sgi).Number < newGroupShips {
|
if c.ShipGroup(sgi).Number < newGroupShips {
|
||||||
return -1, e.NewBreakGroupIllegalNumberError("group #%d ships: %d -> %d", c.ShipGroup(sgi).Index, c.ShipGroup(sgi).Number, newGroupShips)
|
return -1, e.NewBreakGroupIllegalNumberError("group #%d ships: %d -> %d", c.ShipGroup(sgi).Index, c.ShipGroup(sgi).Number, newGroupShips)
|
||||||
}
|
}
|
||||||
|
return c.breakGroupUnsafe(ri, sgi, newGroupShips), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Cache) breakGroupUnsafe(ri, sgi int, newGroupShips uint) int {
|
||||||
newGroup := *c.ShipGroup(sgi)
|
newGroup := *c.ShipGroup(sgi)
|
||||||
if c.ShipGroup(sgi).CargoType != nil {
|
if c.ShipGroup(sgi).CargoType != nil {
|
||||||
newGroup.Load = c.ShipGroup(sgi).Load / float64(c.ShipGroup(sgi).Number) * float64(newGroupShips)
|
newGroup.Load = c.ShipGroup(sgi).Load / float64(c.ShipGroup(sgi).Number) * float64(newGroupShips)
|
||||||
@@ -511,7 +515,7 @@ func (c *Cache) breakGroupSafe(ri int, groupIndex uint, newGroupShips uint) (int
|
|||||||
newGroup.Number = newGroupShips
|
newGroup.Number = newGroupShips
|
||||||
c.ShipGroupShipsNumber(sgi, c.ShipGroup(sgi).Number-newGroup.Number)
|
c.ShipGroupShipsNumber(sgi, c.ShipGroup(sgi).Number-newGroup.Number)
|
||||||
newGroup.FleetID = nil
|
newGroup.FleetID = nil
|
||||||
return c.appendShipGroup(ri, &newGroup), nil
|
return c.appendShipGroup(ri, &newGroup)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Internal funcs
|
// Internal funcs
|
||||||
|
|||||||
Reference in New Issue
Block a user