예제 #1
0
func init() {
	load_requests = make(chan loadRequest, 10)
	pipe := make(chan loadRequest, 10)
	// We want to be able to handle any number of incoming load requests, so
	// we have one go-routine collect them all and send them along pipe any
	// time someone is ready to receive one.
	go func() {
		defer base.StackCatcher()
		var rs []loadRequest
		var send chan loadRequest
		var hold loadRequest
		for {
			select {
			case r := <-load_requests:
				rs = append(rs, r)
			case send <- hold:
				rs = rs[1:]
			}
			if len(rs) > 0 {
				send = pipe
				hold = rs[0]
			} else {
				// If send is nil then it will effectively be excluded from the select
				// statement above.  This is good since we won't have anything to send
				// until we get more requests.
				rs = nil
				send = nil
			}
		}
	}()
	for i := 0; i < 4; i++ {
		go loadTextureRoutine(pipe)
	}
}
예제 #2
0
파일: game.go 프로젝트: runningwild/magnus
func (gw *GameWindow) Draw(region gui.Region, style gui.StyleStack) {
	defer base.StackCatcher()
	defer func() {
		// gl.Translated(gl.Double(gw.region.X), gl.Double(gw.region.Y), 0)
		gl.Disable(gl.TEXTURE_2D)
		gl.Color4ub(255, 255, 255, 255)
		gl.LineWidth(3)
		gl.Begin(gl.LINES)
		bx, by := gl.Int(region.X), gl.Int(region.Y)
		bdx, bdy := gl.Int(region.Dx), gl.Int(region.Dy)
		gl.Vertex2i(bx, by)
		gl.Vertex2i(bx, by+bdy)
		gl.Vertex2i(bx, by+bdy)
		gl.Vertex2i(bx+bdx, by+bdy)
		gl.Vertex2i(bx+bdx, by+bdy)
		gl.Vertex2i(bx+bdx, by)
		gl.Vertex2i(bx+bdx, by)
		gl.Vertex2i(bx, by)
		gl.End()
		gl.LineWidth(1)
	}()

	gw.Engine.Pause()
	game := gw.Engine.GetState().(*Game)
	game.RenderLocal(region, gw.Local)
	gw.Engine.Unpause()
}
예제 #3
0
파일: main.go 프로젝트: runningwild/magnus
func main() {
	defer base.StackCatcher()
	fmt.Printf("sys.Startup()...")
	sys.Startup()
	fmt.Printf("successful.\n")
	fmt.Printf("gl.Init()...")
	err := gl.Init()
	fmt.Printf("successful.\n")
	if err != nil {
		base.Error().Fatalf("%v", err)
	}

	fmt.Printf("render.Init()...")
	render.Init()
	fmt.Printf("successful.\n")
	render.Queue(func() {
		fmt.Printf("sys.CreateWindow()...")
		sys.CreateWindow(10, 10, wdx, wdy)
		fmt.Printf("successful.\n")
		sys.EnableVSync(true)
	})
	base.InitShaders()
	runtime.GOMAXPROCS(10)
	fmt.Printf("sys.Think()...")
	sys.Think()
	fmt.Printf("successful.\n")

	base.LoadAllDictionaries()

	if Version() != "standard" {
		engine, local := debugHookup(Version())
		mainLoop(engine, local, "standard")
	} else {
		standardHookup()
	}
}
예제 #4
0
파일: game.go 프로젝트: runningwild/magnus
func (g *Game) Think() {
	g.GameThinks++
	if g.Setup != nil {
		return
	}
	defer base.StackCatcher()

	// cache wall data
	if g.temp.AllWalls == nil || g.temp.AllWallsDirty {
		g.temp.AllWalls = make(map[Gid][]linear.Seg2)
		g.temp.WallCache = make(map[Gid]*wallCache)
		g.temp.VisibleWallCache = make(map[Gid]*wallCache)
		for gid := range g.Levels {
			var allWalls []linear.Seg2
			base.DoOrdered(g.Levels[gid].Room.Walls, func(a, b string) bool { return a < b }, func(_ string, walls linear.Poly) {
				for i := range walls {
					allWalls = append(allWalls, walls.Seg(i))
				}
			})
			// g.DoForEnts(func(entGid Gid, ent Ent) {
			// 	if ent.Level() == gid {
			// 		for _, walls := range ent.Walls() {
			// 			for i := range walls {
			// 				allWalls = append(allWalls, walls.Seg(i))
			// 			}
			// 		}
			// 	}
			// })
			g.temp.AllWalls[gid] = allWalls
			g.temp.WallCache[gid] = &wallCache{}
			g.temp.WallCache[gid].SetWalls(g.Levels[gid].Room.Dx, g.Levels[gid].Room.Dy, allWalls, 100)
			g.temp.VisibleWallCache[gid] = &wallCache{}
			g.temp.VisibleWallCache[gid].SetWalls(g.Levels[gid].Room.Dx, g.Levels[gid].Room.Dy, allWalls, stats.LosPlayerHorizon)
			base.Log().Printf("WallCache: %v", g.temp.WallCache)
		}
		g.Moba.losCache.SetWallCache(g.temp.VisibleWallCache[GidInvadersStart])
	}

	// cache ent data
	for _, ent := range g.temp.AllEnts {
		if ent.Dead() {
			if _, ok := ent.(*PlayerEnt); ok {
				var id int64
				_, err := fmt.Sscanf(string(ent.Id()), "Engine:%d", &id)
				if err != nil {
					base.Error().Printf("Unable to parse player id '%v'", ent.Id())
				} else {
					if engineData, ok := g.Engines[id]; ok {
						if !ok {
							base.Error().Printf("Unable to find engine %d for player %v", id, ent.Id())
						} else {
							engineData.CountdownFrames = 60 * 10
						}
					}
				}
			}
			ent.OnDeath(g)
			g.RemoveEnt(ent.Id())
		}
	}

	// Death countdown
	for engineId, engineData := range g.Engines {
		if engineData.CountdownFrames > 0 {
			engineData.CountdownFrames--
			if engineData.CountdownFrames == 0 {
				// TODO: It's a bit janky to do it like this, right?
				g.AddPlayers([]int64{engineId}, engineData.Side)
			}
		}
	}

	if g.temp.AllEnts == nil || g.temp.AllEntsDirty {
		g.temp.AllEnts = g.temp.AllEnts[0:0]
		g.DoForEnts(func(gid Gid, ent Ent) {
			g.temp.AllEnts = append(g.temp.AllEnts, ent)
		})
		g.temp.AllEntsDirty = false
	}

	for _, proc := range g.Processes {
		proc.Think(g)
	}
	algorithm.Choose(&g.Processes, func(proc Process) bool { return proc.Phase() != PhaseComplete })

	// Advance players, check for collisions, add segments
	for _, ent := range g.temp.AllEnts {
		ent.Think(g)
		pos := ent.Pos()
		eps := 1.0e-3
		pos.X = clamp(pos.X, eps, float64(g.Levels[ent.Level()].Room.Dx)-eps)
		pos.Y = clamp(pos.Y, eps, float64(g.Levels[ent.Level()].Room.Dy)-eps)
		ent.SetPos(pos)
	}

	for i := 0; i < len(g.temp.AllEnts); i++ {
		for j := i + 1; j < len(g.temp.AllEnts); j++ {
			outerEnt := g.temp.AllEnts[i]
			innerEnt := g.temp.AllEnts[j]
			distSq := outerEnt.Pos().Sub(innerEnt.Pos()).Mag2()
			colDist := outerEnt.Stats().Size() + innerEnt.Stats().Size()
			if distSq > colDist*colDist {
				continue
			}
			if distSq < 0.0001 {
				continue
			}
			if distSq <= 0.25 {
				distSq = 0.25
			}
			dist := math.Sqrt(distSq)
			force := 50.0 * (colDist - dist)
			outerEnt.ApplyForce(outerEnt.Pos().Sub(innerEnt.Pos()).Scale(force / dist))
			innerEnt.ApplyForce(innerEnt.Pos().Sub(outerEnt.Pos()).Scale(force / dist))
		}
	}

	switch {
	case g.Moba != nil:
		g.ThinkMoba()
	case g.Standard != nil:
		panic("Thinkgs aren't implemented, like thinking on mana sources")
		// Do standard thinking
	default:
		panic("Game mode not set")
	}
}