378 lines
8.6 KiB
Go
378 lines
8.6 KiB
Go
package entertainment
|
|
|
|
import (
|
|
"crypto/rand"
|
|
"fmt"
|
|
"go_dreamfactory/lego/core"
|
|
"go_dreamfactory/pb"
|
|
"math/big"
|
|
)
|
|
|
|
const (
|
|
Width = 7
|
|
Height = 7
|
|
Total = Width * Height
|
|
)
|
|
|
|
// type Girde struct {
|
|
// X int32 // x
|
|
// Y int32
|
|
// ID int32
|
|
// Itype int32
|
|
// }
|
|
|
|
type Girde struct {
|
|
oid int32 // 唯一ID
|
|
color int32 // 颜色
|
|
cid int32 // 配置表id
|
|
score int32 // 分数
|
|
special int32 // 消除特效
|
|
}
|
|
|
|
//地图数据
|
|
type MapData struct {
|
|
//Data map[int32]*pb.GirdeData // 地图数据
|
|
|
|
Plat []*pb.GirdeData // 地图
|
|
|
|
oid int32 // 唯一id
|
|
}
|
|
|
|
func (this *MapData) Init(service core.IService, module core.IModule, comp core.IModuleComp, options core.IModuleOptions) (err error) {
|
|
// this.Data = make(map[int32]*pb.GirdeData, Width*Height)
|
|
this.Plat = make([]*pb.GirdeData, Width*Height)
|
|
return
|
|
}
|
|
|
|
// 1~6随机一个数
|
|
func GetRandType() int32 {
|
|
n, _ := rand.Int(rand.Reader, big.NewInt(6))
|
|
return int32(n.Int64() + 1)
|
|
}
|
|
|
|
func (this *MapData) CreateGride(index int32) *pb.GirdeData {
|
|
t := GetRandType()
|
|
fmt.Printf("create=====index: %d, color:%d \n", index, t)
|
|
this.oid++
|
|
return &pb.GirdeData{
|
|
Oid: this.oid,
|
|
Color: t,
|
|
Cid: GetRandType(),
|
|
Score: 1,
|
|
Special: 1,
|
|
}
|
|
}
|
|
|
|
// 初始化地图数据
|
|
func (this *MapData) InitMap() {
|
|
this.oid = 1000 // 方便观察 从1000开始
|
|
this.Plat = make([]*pb.GirdeData, Width*Height)
|
|
for i := 0; i < Width*Height; i++ {
|
|
|
|
this.Plat[i] = this.CreateGride(int32(i)) //(int32(i/Width), int32(i%Height))
|
|
}
|
|
|
|
//this.Debugf()
|
|
}
|
|
|
|
// 交换2个元素(参数 oid )
|
|
func (this *MapData) SwapGirde(oldId, newId int32) bool {
|
|
var (
|
|
bSwap bool // 能否交换
|
|
)
|
|
// x = int32(i/Width), y = int32(i%Height)
|
|
if (oldId%Height != Total-1 && oldId+1 == newId) ||
|
|
(oldId%Height > 0 && oldId-1 == newId) ||
|
|
(oldId+Width < Total && oldId+Width == newId) ||
|
|
(oldId-Width > 0 && oldId-Width == newId) {
|
|
bSwap = true
|
|
tmp := new(pb.GirdeData)
|
|
*tmp = *this.Plat[newId]
|
|
this.Plat[newId] = this.Plat[oldId]
|
|
this.Plat[oldId] = tmp
|
|
}
|
|
|
|
this.Debugf()
|
|
return bSwap
|
|
}
|
|
|
|
func (this *MapData) SetMap() {
|
|
sz2 := []int32{
|
|
5, 1, 2, 5, 1, 5, 2,
|
|
3, 1, 5, 4, 2, 4, 4,
|
|
4, 4, 2, 1, 6, 4, 1,
|
|
6, 3, 1, 4, 3, 6, 3,
|
|
6, 3, 3, 1, 1, 6, 1,
|
|
5, 6, 5, 5, 1, 3, 1,
|
|
6, 5, 5, 1, 2, 1, 4,
|
|
}
|
|
var pos int
|
|
for index := Width - 1; index >= 0; index-- {
|
|
for j := 0; j < Height; j++ {
|
|
this.Plat[index+j*Height].Color = sz2[pos]
|
|
pos++
|
|
//fmt.Printf(" x:%d y:%d c:%d ", this.Plat[index+j*7].X, this.Plat[index+j*7].Y, this.Plat[index+j*7].Color)
|
|
//fmt.Printf("%d ", this.Plat[index+j*7].Color)
|
|
}
|
|
//fmt.Printf("\n")
|
|
}
|
|
this.Debugf()
|
|
}
|
|
func (this *MapData) Debugf() {
|
|
fmt.Printf("================\n")
|
|
for index := Width - 1; index >= 0; index-- {
|
|
|
|
for j := 0; j < Height; j++ {
|
|
fmt.Printf("%d:%d ", this.Plat[index+j*Height].Oid, this.Plat[index+j*Height].Color)
|
|
}
|
|
fmt.Printf("\n")
|
|
}
|
|
|
|
}
|
|
|
|
// 检查5消
|
|
func (this *MapData) Check5X() (bEliminate bool, score int32) {
|
|
for k, v := range this.Plat {
|
|
if v.Color == 0 {
|
|
continue
|
|
}
|
|
x := int32(k % Height) // x
|
|
if x+4 < Height {
|
|
k1 := this.Plat[k].Color
|
|
k2 := this.Plat[k+1].Color
|
|
k3 := this.Plat[k+2].Color
|
|
k4 := this.Plat[k+3].Color
|
|
k5 := this.Plat[k+4].Color
|
|
if k5 == 0 || k2 == 0 || k3 == 0 || k4 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k3 == k4 && k5 == k1 && k2 == k3 {
|
|
score += this.Plat[k].Score
|
|
score += this.Plat[k+1].Score
|
|
score += this.Plat[k+2].Score
|
|
score += this.Plat[k+3].Score
|
|
score += this.Plat[k+4].Score
|
|
this.Plat[k] = &pb.GirdeData{}
|
|
this.Plat[k+1] = &pb.GirdeData{}
|
|
this.Plat[k+2] = &pb.GirdeData{}
|
|
this.Plat[k+3] = &pb.GirdeData{}
|
|
this.Plat[k+4] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
|
|
}
|
|
}
|
|
if k+4*Width < Total {
|
|
k1 := this.Plat[k].Color
|
|
k2 := this.Plat[k+Width].Color
|
|
k3 := this.Plat[k+2*Width].Color
|
|
k4 := this.Plat[k+3*Width].Color
|
|
k5 := this.Plat[k+4*Width].Color
|
|
if k5 == 0 || k2 == 0 || k3 == 0 || k4 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k3 == k4 && k5 == k1 && k2 == k3 {
|
|
score += this.Plat[k].Score
|
|
score += this.Plat[k+Width].Score
|
|
score += this.Plat[k+2*Width].Score
|
|
score += this.Plat[k+3*Width].Score
|
|
score += this.Plat[k+4*Width].Score
|
|
this.Plat[k] = &pb.GirdeData{}
|
|
this.Plat[k+Width] = &pb.GirdeData{}
|
|
this.Plat[k+2*Width] = &pb.GirdeData{}
|
|
this.Plat[k+3*Width] = &pb.GirdeData{}
|
|
this.Plat[k+4*Width] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
}
|
|
}
|
|
}
|
|
|
|
return
|
|
}
|
|
|
|
func (this *MapData) Check4X() (bEliminate bool, score int32) {
|
|
for k, v := range this.Plat {
|
|
if v.Color == 0 {
|
|
continue
|
|
}
|
|
x := int32(k % Height) // x
|
|
|
|
if x+3 < Height {
|
|
k1 := this.Plat[x].Color
|
|
k2 := this.Plat[x+1].Color
|
|
k3 := this.Plat[x+2].Color
|
|
k4 := this.Plat[x+3].Color
|
|
if k2 == 0 || k3 == 0 || k4 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k3 == k4 && k2 == k3 {
|
|
score += this.Plat[x].Score
|
|
score += this.Plat[x+1].Score
|
|
score += this.Plat[x+2].Score
|
|
score += this.Plat[x+3].Score
|
|
this.Plat[x] = &pb.GirdeData{}
|
|
this.Plat[x+1] = &pb.GirdeData{}
|
|
this.Plat[x+2] = &pb.GirdeData{}
|
|
this.Plat[x+3] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
}
|
|
}
|
|
if k+3*Width < Total {
|
|
k1 := this.Plat[k].Color
|
|
k2 := this.Plat[k+Width].Color
|
|
k3 := this.Plat[k+2*Width].Color
|
|
k4 := this.Plat[k+3*Width].Color
|
|
if k2 == 0 || k3 == 0 || k4 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k3 == k4 && k2 == k3 {
|
|
score += this.Plat[k].Score
|
|
score += this.Plat[k+Width].Score
|
|
score += this.Plat[k+2*Width].Score
|
|
score += this.Plat[k+3*Width].Score
|
|
|
|
this.Plat[k] = &pb.GirdeData{}
|
|
this.Plat[k+Width] = &pb.GirdeData{}
|
|
this.Plat[k+2*Width] = &pb.GirdeData{}
|
|
this.Plat[k+3*Width] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
}
|
|
}
|
|
}
|
|
return
|
|
}
|
|
|
|
func (this *MapData) Check3X() (bEliminate bool, score int32) {
|
|
for k, v := range this.Plat {
|
|
if v.Color == 0 {
|
|
continue
|
|
}
|
|
x := int32(k % Height) // x
|
|
|
|
if x+2 < Height {
|
|
k1 := this.Plat[k].Color
|
|
k2 := this.Plat[k+1].Color
|
|
k3 := this.Plat[k+2].Color
|
|
if k2 == 0 || k3 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k2 == k3 {
|
|
score += this.Plat[k].Score
|
|
score += this.Plat[k+1].Score
|
|
score += this.Plat[k+2].Score
|
|
this.Plat[k] = &pb.GirdeData{}
|
|
this.Plat[k+1] = &pb.GirdeData{}
|
|
this.Plat[k+2] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
}
|
|
}
|
|
|
|
if k+2*Width < Total {
|
|
k1 := this.Plat[k].Color
|
|
k2 := this.Plat[k+Width].Color
|
|
k3 := this.Plat[k+2*Width].Color
|
|
if k2 == 0 || k3 == 0 {
|
|
continue
|
|
}
|
|
if k1 == k2 && k2 == k3 {
|
|
score += this.Plat[k].Score
|
|
score += this.Plat[k+Width].Score
|
|
score += this.Plat[k+2*Width].Score
|
|
|
|
this.Plat[k] = &pb.GirdeData{}
|
|
this.Plat[k+Width] = &pb.GirdeData{}
|
|
this.Plat[k+2*Width] = &pb.GirdeData{}
|
|
bEliminate = true
|
|
}
|
|
}
|
|
}
|
|
return
|
|
}
|
|
|
|
// 校验地图可消除的 判断各组上面2个和右边两个是否三个相等
|
|
func (this *MapData) CheckMap() (score int32, szMap []*pb.MapData) {
|
|
for {
|
|
var curScore int32
|
|
if bRet, s := this.Check5X(); !bRet {
|
|
fmt.Printf("=====检测消除5x===========\n")
|
|
curScore += s
|
|
}
|
|
if bRet, s := this.Check4X(); !bRet {
|
|
fmt.Printf("=====检测消除4x===========\n")
|
|
curScore += s
|
|
}
|
|
if bRet, s := this.Check3X(); !bRet {
|
|
fmt.Printf("=====检测消除3x===========\n")
|
|
curScore += s
|
|
}
|
|
score += curScore // 总分
|
|
if curScore == 0 {
|
|
break
|
|
}
|
|
//szMap = append(szMap, this.DropGirde()...)
|
|
this.DropGirde()
|
|
|
|
szMap = append(szMap, &pb.MapData{
|
|
Data: this.Plat,
|
|
CurSocre: curScore,
|
|
})
|
|
}
|
|
|
|
//this.Debugf()
|
|
return
|
|
}
|
|
|
|
// 下落 生成新的格子 (返回掉落所获得的分数)
|
|
func (this *MapData) DropGirde() {
|
|
|
|
for i := 0; i < Width; i++ {
|
|
for j := 0; j < Height; j++ {
|
|
index := i*Width + j
|
|
if this.Plat[index].Color == 0 { // 说明这列有空
|
|
var add int
|
|
for m := j + 1; m < Height; m++ {
|
|
k1 := i*Width + m
|
|
if this.Plat[k1].Color != 0 {
|
|
this.Plat[index] = this.Plat[k1]
|
|
index++
|
|
add++
|
|
}
|
|
// if this.Plat[k1].Color != 0 {
|
|
// tmp := new(pb.GirdeData)
|
|
// *tmp = *this.Plat[k1]
|
|
// sz = append(sz, tmp)
|
|
// }
|
|
}
|
|
for m := j + add; m < Height; m++ {
|
|
k1 := i*Width + m
|
|
this.Plat[k1] = this.CreateGride(int32(k1))
|
|
}
|
|
break
|
|
}
|
|
}
|
|
}
|
|
|
|
this.Debugf()
|
|
return
|
|
}
|
|
func (this *MapData) AiSwapGirde() bool {
|
|
var (
|
|
bSwap bool // 能否交换
|
|
)
|
|
for pos := 0; pos < Total; pos++ {
|
|
y := pos % Height
|
|
if y < Height-1 {
|
|
if this.SwapGirde(int32(pos), int32(pos+1)) {
|
|
bSwap = true
|
|
break
|
|
}
|
|
}
|
|
if pos/Width+1 < Width {
|
|
if this.SwapGirde(int32(pos), int32(pos+1)) {
|
|
bSwap = true
|
|
break
|
|
}
|
|
}
|
|
}
|
|
return bSwap
|
|
}
|