package model import ( "fmt" "gorm.io/gorm" "strconv" "strings" "time" ) type Device struct { gorm.Model Type string `json:"type"` // 设备类型 Vendor string `json:"vendor"` // 厂商 SN string `json:"device_sn"` // 编码 Lng float64 `json:"lng"` Lat float64 `json:"lat"` Battery float64 `json:"battery"` High float64 `json:"high"` GpsType string `json:"gps_type"` LocateState string `json:"locate_state"` Mac string `json:"mac"` Ip string `json:"ip"` IsOutBound int `json:"isOutBound" gorm:"default:1"` // 0 没出界 1 有出界 BoundId uint `json:"bound_id"` // 所处的电子围栏 } func (obj *Device) FindAll() []Device { list := []Device{} err := DB.Table("devices").Find(&list).Error if err != nil { return nil } return list } func (obj *Device) FindByBoundID(bound_id uint) ([]Device, int64) { list := []Device{} var total int64 err := DB.Table("devices").Where("bound_id = ?", bound_id).Find(&list).Error err = DB.Table("devices").Where("bound_id = ?", bound_id).Count(&total).Error if err != nil { return nil, 0 } return list, total } func (obj *Device) Update() (err error) { if isExistDevice(obj.SN) { var err error // 坐标为0时不更新位置 dev := Device{Battery: obj.Battery} dev.UpdatedAt = time.Now() if obj.Lat == 0 { err = DB.Table("devices").Where("sn = ?", obj.SN).Select("battery").Updates(dev).Error } else { dev.High = obj.High dev.Lat = obj.Lat dev.Lng = obj.Lng err = DB.Table("devices").Where("sn = ?", obj.SN).Select("lng", "lat", "battery", "high").Updates(dev).Error } if err != nil { fmt.Println("修改数据出错") return err } } else { err := DB.Table("devices").Create(&obj).Error if err != nil { return err } // fmt.Println("新增安全帽数据") } hasZone, zoneId := CheckInBound(obj) if hasZone { if zoneId > 0 { DB.Table("devices").Where("sn=?", obj.SN).Update(Device{BoundId: zoneId, IsOutBound: 0}) } else { DB.Table("devices").Where("sn=?", obj.SN).Update(Device{IsOutBound: 1}) } } return nil } func isExistDevice(sn string) bool { var count int64 DB.Table("devices").Where("sn = ?", sn).Count(&count) return count > 0 } func CheckInBound(dv *Device) (bool, uint) { obj := DrawZone{} zones := obj.FindAll() if zones == nil { return false, 0 } pointToCheck := Point{Lng: dv.Lng, Lat: dv.Lat} for i := 0; i < len(zones); i++ { zone := zones[i] arr := strings.Split(zone.Dots, "&") pointArr := []Point{} for i := 0; i < len(arr); i++ { str := arr[i] subArr := strings.Split(str, ",") f1, _ := strconv.ParseFloat(subArr[0], 64) f2, _ := strconv.ParseFloat(subArr[1], 64) newPoint := Point{Lng: f1, Lat: f2} pointArr = append(pointArr, newPoint) } if IsPointInPolygon(pointToCheck, pointArr) { return true, zone.ID } } return true, 0 }