oldschool-toontown/toontown/minigame/DistributedTargetGame.py
Little Cat 1801d2b9fb
all: replace pandac.PandaModules imports.
UD/AI + Client boots up.
2022-12-16 20:40:57 -04:00

1550 lines
63 KiB
Python

from panda3d.core import *
from toontown.toonbase.ToonBaseGlobal import *
from direct.interval.IntervalGlobal import *
from .DistributedMinigame import *
from direct.distributed.ClockDelta import *
from direct.fsm import ClassicFSM, State
from direct.fsm import State
from direct.task import Task
from . import ArrowKeys
from . import TargetGameGlobals
from toontown.toonbase import ToontownGlobals
from toontown.toonbase import TTLocalizer
import math
from math import *
import random
import random
from . import RubberBand
from . import FogOverlay
def circleX(angle, radius, centerX, centerY):
x = radius * cos(angle) + centerX
return x
def circleY(angle, radius, centerX, centerY):
y = radius * sin(angle) + centerY
return y
def getCirclePoints(segCount, centerX, centerY, radius, wideX = 1.0, wideY = 1.0):
returnShape = []
for seg in range(0, segCount):
coordX = wideX * circleX(pi * 2.0 * float(float(seg) / float(segCount)), radius, centerX, centerY)
coordY = wideY * circleY(pi * 2.0 * float(float(seg) / float(segCount)), radius, centerX, centerY)
returnShape.append((coordX, coordY, 1))
coordX = wideX * circleX(pi * 2.0 * float(0 / segCount), radius, centerX, centerY)
coordY = wideY * circleY(pi * 2.0 * float(0 / segCount), radius, centerX, centerY)
returnShape.append((coordX, coordY, 1))
return returnShape
def getRingPoints(segCount, centerX, centerY, radius, thickness = 2.0, wideX = 1.0, wideY = 1.0):
returnShape = []
for seg in range(0, segCount):
coordX = wideX * circleX(pi * 2.0 * float(float(seg) / float(segCount)), radius - thickness, centerX, centerY)
coordY = wideY * circleY(pi * 2.0 * float(float(seg) / float(segCount)), radius - thickness, centerX, centerY)
returnShape.append((coordX, coordY, 1))
coordX = wideX * circleX(pi * 2.0 * float(float(seg) / float(segCount)), radius, centerX, centerY)
coordY = wideY * circleY(pi * 2.0 * float(float(seg) / float(segCount)), radius, centerX, centerY)
returnShape.append((coordX, coordY, 1))
return returnShape
def addRing(attachNode, color, vertexCount, radius, layer = 0, thickness = 1.0):
targetGN = GeomNode('target Circle')
zFloat = 0.025
targetCircleShape = getRingPoints(5 + int(vertexCount), 0.0, 0.0, radius, thickness)
gFormat = GeomVertexFormat.getV3cp()
targetCircleVertexData = GeomVertexData('holds my vertices', gFormat, Geom.UHDynamic)
targetCircleVertexWriter = GeomVertexWriter(targetCircleVertexData, 'vertex')
targetCircleColorWriter = GeomVertexWriter(targetCircleVertexData, 'color')
for vertex in targetCircleShape:
targetCircleVertexWriter.addData3f(0.0 + vertex[0], 0.0 + vertex[1], zFloat)
targetCircleColorWriter.addData4f(1.0, 1.0, 1.0, 1.0)
targetTris = GeomTristrips(Geom.UHStatic)
sizeTarget = len(targetCircleShape)
for countVertex in range(0, sizeTarget):
targetTris.addVertex(countVertex)
targetTris.addVertex(0)
targetTris.addVertex(1)
targetTris.closePrimitive()
targetGeom = Geom(targetCircleVertexData)
targetGeom.addPrimitive(targetTris)
attachNode.addGeom(targetGeom)
return targetGeom
def addCircle(attachNode, color, vertexCount, radius, layer = 0):
targetGN = GeomNode('target Circle')
zFloat = 0.025
targetCircleShape = getCirclePoints(5 + int(vertexCount), 0.0, 0.0, radius)
gFormat = GeomVertexFormat.getV3cp()
targetCircleVertexData = GeomVertexData('holds my vertices', gFormat, Geom.UHDynamic)
targetCircleVertexWriter = GeomVertexWriter(targetCircleVertexData, 'vertex')
targetCircleColorWriter = GeomVertexWriter(targetCircleVertexData, 'color')
targetCircleVertexWriter.addData3f(0.0, 0.0, zFloat)
targetCircleColorWriter.addData4f(1.0, 1.0, 1.0, 1.0)
for vertex in targetCircleShape:
targetCircleVertexWriter.addData3f(0.0 + vertex[0], 0.0 + vertex[1], zFloat)
targetCircleColorWriter.addData4f(1.0, 1.0, 1.0, 1.0)
targetTris = GeomTrifans(Geom.UHStatic)
sizeTarget = len(targetCircleShape)
targetTris.addVertex(0)
for countVertex in range(1, sizeTarget + 1):
targetTris.addVertex(countVertex)
targetTris.addVertex(1)
targetTris.closePrimitive()
targetGeom = Geom(targetCircleVertexData)
targetGeom.addPrimitive(targetTris)
attachNode.addGeom(targetGeom)
return targetGeom
def checkPlace(placeX, placeY, fillSize, placeList):
goodPlacement = 1
for place in placeList:
distance = math.sqrt((place[0] - placeX) * (place[0] - placeX) + (place[1] - placeY) * (place[1] - placeY))
distance = distance - (fillSize + place[2])
if distance <= 0.0:
goodPlacement = 0
break
return goodPlacement
class DistributedTargetGame(DistributedMinigame):
UPDATE_ENVIRON_TASK = 'TargetGameUpdateEnvironTask'
UPDATE_LOCALTOON_TASK = 'TargetGameUpdateLocalToonTask'
UPDATE_SHADOWS_TASK = 'TargetGameUpdateShadowsTask'
COLLISION_DETECTION_TASK = 'TargetGameCollisionDetectionTask'
END_GAME_WAIT_TASK = 'TargetGameCollisionDetectionTask'
UPDATE_POWERBAR_TASK = 'TargetGameUpdatePowerBarTask'
GAME_DONE_TASK = 'gameDoneTask'
UPDATE_COUNTDOWN_TASK = 'countdown task'
FLY2FALL_CAM_TASK = 'fly2FallCameraTask'
PRELAUNCH_CAM_TASK = 'prelaunchCameraTask'
SCORE_CAM_TASK = 'scoreCameraTask'
TOONSTRETCHTASK = 'tooncamtask'
UPDATE_LOCAL_TOON_PRIORITY = 0
UPDATE_POWER_BAR_PRIORITY = 1
UPDATE_RUBBER_BAND_PRIORITY = 2
COLLISION_DETECTION_PRIORITY = 5
UPDATE_SHADOWS_PRIORITY = 47
UMBRELLA_TEXTURE_LIST = ['phase_4/maps/mg_slingshot_umbrella_blue.jpg',
'phase_4/maps/mg_slingshot_umbrella_purple.jpg',
'phase_4/maps/mg_slingshot_umbrella_red.jpg',
'phase_4/maps/mg_slingshot_umbrella_yellow.jpg']
RT_UNKNOWN = 0
RT_SUCCESS = 1
RT_GROUPSUCCESS = 2
RT_FAILURE = 3
def __init__(self, cr):
DistributedMinigame.__init__(self, cr)
self.gameFSM = ClassicFSM.ClassicFSM('DistributedTargetGame', [State.State('off', self.enterOff, self.exitOff, ['prelaunch']),
State.State('prelaunch', self.enterPrelaunch, self.exitPrelaunch, ['launch']),
State.State('launch', self.enterLaunch, self.exitLaunch, ['fly']),
State.State('fly', self.enterFly, self.exitFly, ['fall', 'bouncing', 'score']),
State.State('fall', self.enterFall, self.exitFall, ['bouncing', 'score']),
State.State('bouncing', self.enterBouncing, self.exitBouncing, ['score']),
State.State('score', self.enterScore, self.exitScore, ['cleanup', 'prelaunch']),
State.State('cleanup', self.enterCleanup, self.exitCleanup, [])], 'off', 'cleanup')
self.addChildGameFSM(self.gameFSM)
self.targets = None
self.round = 1
self.signalLaunch = 0
self.stretchX = 0
self.stretchY = 0
self.targetsPlaced = []
self.pattern = None
self.maxDist = 50
self.targetMarker = None
self.umbrellaColorSelect = [1,
1,
1,
1]
self.localTrack = None
self.hitInfo = None
return
def getTitle(self):
return TTLocalizer.TargetGameTitle
def getInstructions(self):
p = self.avIdList.index(self.localAvId)
if self.isSinglePlayer():
text = TTLocalizer.TargetGameInstructionsSinglePlayer
else:
text = TTLocalizer.TargetGameInstructionsMultiPlayer
return text
def getMaxDuration(self):
return 60
def defineConstants(self):
self.CAMERA_Y = -25
self.TOON_Y = 0
self.FAR_PLANE_DIST = 370
tScreenCenterToEdge = 1.0
self.TOONXZ_SPEED = TargetGameGlobals.MAX_TOONXZ / tScreenCenterToEdge
self.WATER_DEPTH = 75.0
self.ENVIRON_LENGTH = TargetGameGlobals.ENVIRON_LENGTH
self.ENVIRON_WIDTH = TargetGameGlobals.ENVIRON_WIDTH
self.ENVIRON_START_OFFSET = 20.0
self.TOON_INITIAL_SPACING = 14.0
waterZOffset = 28.0
self.SEA_FLOOR_Z = -self.WATER_DEPTH / 2.0 + waterZOffset
self.FOGDISTGROUND = 600
self.FOGDISTCLOUD = 200
farPlaneDist = self.CAMERA_Y + self.FAR_PLANE_DIST - self.TOON_Y
self.ringGroupArrivalPeriod = 3.0
self.AMB_COLOR = Vec4(0.75, 0.8, 1.0, 1.0)
self.CLOUD_COLOR = Vec4(1.0, 1.0, 1.0, 1.0)
self.SHADOW_Z_OFFSET = 0.1
self.Y_VIS_MAX = self.FAR_PLANE_DIST
self.Y_VIS_MIN = self.CAMERA_Y
targetRadius = TargetGameGlobals.TARGET_RADIUS * 1.025
self.GAME_END_DELAY = 1.0
self.TOON_LOD = 1000
self.speedLaunch = 60
self.speedStall = 30
self.speedForward = 0
self.airResistance = 0.1
self.umbrellaResistance = 0.11
self.distance = 0
self.zVel = 0
self.lastPressed = None
self.lastPressTime = None
self.driftX = 0
self.driftY = 0
self.launchLaterial = 0
self.laterial = 0
self.gravity = 12.5
self.inList = []
self.placeShift = 10
self.startPower = 10
self.canPressRight = 1
self.canPressLeft = 1
self.jumpCount = 0
self.trampZ = 3.6
self.trampBounceCount = 0
self.cameraState = 'Low'
self.updateTick = 0
self.hitInfo = None
return
def load(self):
self.notify.debug('load')
DistributedMinigame.load(self)
self.defineConstants()
self.help = DirectLabel(parent=aspect2d, relief=None, pos=(-0.0, 0, -0.8), text=TTLocalizer.TargetGameCountdown, text_scale=0.08, text_fg=(1, 1, 1, 1))
self.help.hide()
self.fogOver = FogOverlay.FogOverlay(Point3(self.CLOUD_COLOR[0], self.CLOUD_COLOR[1], self.CLOUD_COLOR[2]))
self.scoreboard = DirectFrame(parent=aspect2d, relief=None, geom=DGG.getDefaultDialogGeom(), geom_color=ToontownGlobals.GlobalDialogColor, geom_scale=(1.75, 1, 0.75), pos=(0, 0, 0.587))
self.roundLabel = DirectLabel(parent=self.scoreboard, relief=None, pos=(0, 0, 0.28), text=TTLocalizer.TargetGameBoard % self.round, text_scale=0.08)
av1Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(-0.8, 0, 0.14), text_align=TextNode.ALeft, text=' ', text_scale=0.08)
av2Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(-0.8, 0, 0.02), text_align=TextNode.ALeft, text=' ', text_scale=0.08)
av3Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(-0.8, 0, -0.1), text_align=TextNode.ALeft, text=' ', text_scale=0.08)
av4Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(-0.8, 0, -0.22), text_align=TextNode.ALeft, text=' ', text_scale=0.08)
score1Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(0.8, 0, 0.14), text_align=TextNode.ARight, text=' ', text_scale=0.08)
score2Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(0.8, 0, 0.02), text_align=TextNode.ARight, text=' ', text_scale=0.08)
score3Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(0.8, 0, -0.1), text_align=TextNode.ARight, text=' ', text_scale=0.08)
score4Label = DirectLabel(parent=self.scoreboard, relief=None, pos=(0.8, 0, -0.22), text_align=TextNode.ARight, text=' ', text_scale=0.08)
self.avLabels = [av1Label,
av2Label,
av3Label,
av4Label]
self.scoreLabels = [score1Label,
score2Label,
score3Label,
score4Label]
self.scoreboard.hide()
self.music = base.loader.loadMusic('phase_4/audio/bgm/MG_Diving.ogg')
self.sndAmbience = None
self.skyListLow = []
self.skyListMid = []
loadBase = 'phase_4/models/minigames/'
self.modelName = 'slingshot_game_desert4.bam'
self.trampoline = loader.loadModel('phase_4/models/minigames/slingshot_game_tramp.bam')
self.trampoline.setBin('ground', 100)
self.trampoline.find('**/tramp_shadow').hide()
self.cacti = loader.loadModel('phase_4/models/minigames/slingshot_game_cacti.bam')
self.cactusA = self.cacti.find('**/cactus_a')
self.cactusB = self.cacti.find('**/cactus_b')
self.findGround = '**/sand_layer1'
self.findSky = '**/blue_sky_layer1'
self.findCloudExtra = '**/cloud_layer1'
self.findCloud = '**/cloud_layer_alpha'
self.findLeftMount = '**/mountain_set_b'
self.findRightMount = '**/mountain_c'
self.findBack = '**/backdrop_layer1'
self.environModel = loader.loadModel(loadBase + self.modelName)
self.skyGN = GeomNode('sky Geometry')
self.skyNode1 = self.environModel.attachNewNode(self.skyGN)
leftMountModel = self.environModel.find(self.findLeftMount)
rightMountModel = self.environModel.find(self.findRightMount)
wrongCloud = self.environModel.find(self.findCloudExtra)
wrongCloud.hide()
backModel = self.environModel.find(self.findBack)
backModel.hide()
leftMountModel.hide()
rightMountModel.hide()
groundModel = self.environModel.find(self.findGround)
groundModel.setBin('ground', 0)
groundModel.setZ(-0.05)
skyModel = self.environModel.find(self.findSky)
skyModel2 = self.environModel.find(self.findCloud)
skyModel3 = self.environModel.attachNewNode('skyLow')
skyModel2.copyTo(skyModel3)
skyModel.setZ(76.0)
skyModel.setColorScale(1.0, 1.0, 1.0, 1.0)
skyModel.setBin('ground', 2)
skyModel2.setZ(63.0)
skyModel2.setDepthWrite(0)
skyModel2.setTransparency(1)
skyModel2.setColorScale(1.0, 1.0, 1.0, 1.0)
skyModel2.setTwoSided(True)
skyModel2.setBin('fixed', 3)
skyModel2.setR(180)
skyModel3.setZ(50.0)
skyModel3.setDepthWrite(0)
skyModel3.setTransparency(1)
skyModel3.setColorScale(1.0, 1.0, 1.0, 1.0)
skyModel3.setTwoSided(True)
skyModel3.setBin('fixed', 4)
self.skyListLow.append(skyModel3)
self.lowSky = skyModel3
self.environModel.setPos(0, -5.0, 0)
self.environModel.flattenMedium()
self.environModel.setScale(15.0, 15.0, 2.0)
self.dropShadowModel = loader.loadModel('phase_3/models/props/drop_shadow')
self.dropShadowModel.setColor(0, 0, 0, 0.5)
self.dropShadowModel.flattenMedium()
self.toonDropShadows = []
self.__textGen = TextNode('targetGame')
self.__textGen.setFont(ToontownGlobals.getSignFont())
self.__textGen.setAlign(TextNode.ACenter)
self.powerBar = DirectWaitBar(guiId='launch power bar', pos=(0.0, 0, -0.65), relief=DGG.SUNKEN, frameSize=(-2.0,
2.0,
-0.2,
0.2), borderWidth=(0.02, 0.02), scale=0.25, range=100, sortOrder=50, frameColor=(0.5, 0.5, 0.5, 0.5), barColor=(1.0, 0.0, 0.0, 1.0), text='0%', text_scale=0.26, text_fg=(1, 1, 1, 1), text_align=TextNode.ACenter, text_pos=(0, -0.05))
self.power = self.startPower
self.powerBar['value'] = self.power
self.powerBar.hide()
self.rubberBands = []
self.umbrella = loader.loadModel('phase_4/models/minigames/slingshot_game_umbrellas.bam')
pick = random.randint(0, 3)
self.umbrellaColorSelect[pick] = 0
tex = loader.loadTexture(DistributedTargetGame.UMBRELLA_TEXTURE_LIST[pick])
tex.setMinfilter(Texture.FTLinearMipmapLinear)
tex.setMagfilter(Texture.FTLinear)
self.umbrella.setTexture(tex, 1)
open = self.umbrella.find('**/open_umbrella')
open.hide()
open.setPos(0.1, 0.2, -0.1)
open.setHpr(-90.0, 0.0, 15.0)
closed = self.umbrella.find('**/closed_umbrella')
closed.show()
hands = localAvatar.getRightHands()
ce = CompassEffect.make(NodePath(), CompassEffect.PRot)
closed.node().setEffect(ce)
closed.setHpr(0.0, 100.0, 35.0)
for hand in hands:
self.umbrella.instanceTo(hand)
self.remoteUmbrellas = {}
self.addSound('wind1', 'target_cloud.ogg', 'phase_4/audio/sfx/')
self.addSound('trampoline', 'target_trampoline_2.ogg', 'phase_4/audio/sfx/')
self.addSound('launch', 'target_launch.ogg', 'phase_4/audio/sfx/')
self.addSound('miss', 'target_Lose.ogg', 'phase_4/audio/sfx/')
self.addSound('score', 'target_happydance.ogg', 'phase_4/audio/sfx/')
self.addSound('impact', 'target_impact_grunt1.ogg', 'phase_4/audio/sfx/')
self.addSound('umbrella', 'target_chute.ogg', 'phase_4/audio/sfx/')
self.addSound('bounce', 'target_impact_only.ogg', 'phase_4/audio/sfx/')
self.flySound = loader.loadSfx('phase_4/audio/sfx/target_wind_fly_loop.ogg')
self.flySound.setVolume(0.0)
self.flySound.setPlayRate(1.0)
self.flySound.setLoop(True)
self.flySound.play()
self.rubberSound = loader.loadSfx('phase_4/audio/sfx/target_stretching_aim_loop.ogg')
self.rubberSound.setVolume(0.0)
self.rubberSound.setPlayRate(1.0)
self.rubberSound.setLoop(True)
self.rubberSound.play()
self.flutterSound = loader.loadSfx('phase_4/audio/sfx/target_wind_float_clothloop.ogg')
self.flutterSound.setVolume(1.0)
self.flutterSound.setPlayRate(1.0)
self.flutterSound.setLoop(True)
return
def addSound(self, name, soundName, path = None):
if not hasattr(self, 'soundTable'):
self.soundTable = {}
if path:
self.soundPath = path
soundSource = '%s%s' % (self.soundPath, soundName)
self.soundTable[name] = loader.loadSfx(soundSource)
def playSound(self, name, volume = 1.0):
if hasattr(self, 'soundTable'):
self.soundTable[name].setVolume(volume)
self.soundTable[name].play()
def addSkys(self, instance):
low = instance.find('**/skyLow')
mid = instance.find(self.findCloud)
self.skyListLow.append(low)
self.skyListMid.append(mid)
def setTargetSeed(self, targetSeed, extra = None):
if not self.hasLocalToon:
return
random.seed(targetSeed)
self.pattern = TargetGameGlobals.difficultyPatterns[self.getSafezoneId()]
print('seed %s' % targetSeed)
self.setupTargets()
def setupTargets(self):
fieldWidth = self.ENVIRON_WIDTH * 3
fieldLength = self.ENVIRON_LENGTH * 3.7
self.targetSubParts = [2,
2,
2,
1]
self.targetList = self.pattern[0]
self.targetValue = self.pattern[1]
self.targetSize = self.pattern[2]
self.targetColors = self.pattern[3]
self.targetSubParts = self.pattern[4]
highestValue = 0
for value in self.targetValue:
if value > highestValue:
highestValue = value
placeList = []
self.jumpColor = TargetGameGlobals.colorBlack
self.placeValue = highestValue * 0.5
self.jumpSize = self.pattern[5]
self.jumpNum = self.pattern[6]
self.accept('enterJump', self.jumpIn)
self.accept('exitJump', self.jumpOut)
self.targets = render.attachNewNode('targetGameTargets')
for typeIndex in range(len(self.targetList)):
for targetIndex in range(self.targetList[typeIndex]):
goodPlacement = 0
while not goodPlacement:
placeX = random.random() * (fieldWidth * 0.6) - fieldWidth * 0.6 * 0.5
placeY = (random.random() * 0.6 + (0.0 + 0.4 * (self.placeValue * 1.0 / (highestValue * 1.0)))) * fieldLength
fillSize = self.targetSize[typeIndex]
goodPlacement = checkPlace(placeX, placeY, fillSize, placeList)
placeList.append((placeX, placeY, fillSize))
subIndex = self.targetSubParts[typeIndex]
first = 1
while subIndex:
combinedIndex = typeIndex + subIndex - 1
targetGN = GeomNode('target Circle')
targetNodePathGeom = self.targets.attachNewNode(targetGN)
targetNodePathGeom.setPos(placeX, placeY, 0)
points = self.targetSize[combinedIndex] / 2 + 20
order = len(self.targetList) - combinedIndex + 10
if first:
first = 0
geo = addCircle(targetGN, self.targetColors[combinedIndex], points, self.targetSize[combinedIndex], order)
else:
thickness = abs(self.targetSize[combinedIndex] - self.targetSize[combinedIndex + 1]) - 0.0
geo = addRing(targetGN, self.targetColors[combinedIndex], points, self.targetSize[combinedIndex], order, thickness)
targetNodePathGeom.setBin('ground', combinedIndex * 2 + 1)
targetNodePathGeom.setColorScale(self.targetColors[combinedIndex]['Red'], self.targetColors[combinedIndex]['Green'], self.targetColors[combinedIndex]['Blue'], self.targetColors[combinedIndex]['Alpha'])
targetNodePathGeom.setDepthWrite(False)
targetNodePathGeom.setDepthTest(False)
targetNodePathGeom.setTransparency(TransparencyAttrib.MAlpha)
self.targetsPlaced.append((placeX,
placeY,
combinedIndex,
geo))
subIndex -= 1
for jump in range(self.jumpNum):
normJumpSize = 6.8
goodPlacement = 0
while not goodPlacement:
placeX = random.random() * (fieldWidth * 0.6) - fieldWidth * 0.6 * 0.5
placeY = (random.random() * 0.6 + (0.0 + 0.4 * (self.placeValue * 1.0 / (highestValue * 1.0)))) * fieldLength
fillSize = self.jumpSize
goodPlacement = checkPlace(placeX, placeY, fillSize, placeList)
placeList.append((placeX, placeY, fillSize))
target = CollisionSphere(0, 0, 0, self.jumpSize)
target.setTangible(0)
targetNode = CollisionNode('Jump')
targetNode.addSolid(target)
targetGN = GeomNode('target jump Circle')
targetNodePathGeom = self.targets.attachNewNode(targetGN)
trampI = self.trampoline.copyTo(self.targets)
trampI.setPos(placeX, placeY, 0.05)
latScale = self.jumpSize / normJumpSize
trampI.setScale(latScale, latScale, 1.0)
targetNodePath = self.targets.attachNewNode(targetNode)
targetNodePath.setPos(placeX, placeY, 0.0)
targetNodePathGeom.setPos(placeX, placeY, 0.05)
points = self.jumpSize / 2 + 20
order = 0
addCircle(targetGN, self.jumpColor, points, self.jumpSize + 0.5, order)
targetNodePathGeom.setColorScale(self.jumpColor['Red'], self.jumpColor['Green'], self.jumpColor['Blue'], 0.25)
targetNodePathGeom.setBin('ground', 20)
targetNodePathGeom.setDepthWrite(True)
targetNodePathGeom.setTransparency(TransparencyAttrib.MAlpha)
cactusCount = 30
for cactus in range(cactusCount):
placeX = random.random() * (fieldWidth * 0.75) - fieldWidth * 0.75 * 0.5
placeY = 5.0 + random.random() * (fieldLength - 5.0)
targetGN = GeomNode('cactus')
cactus = random.choice([self.cactusA, self.cactusB])
targetNodePathGeom = self.targets.attachNewNode(targetGN)
targetNodePathGeom = self.targets.attachNewNode(targetGN)
cactusI = cactus.copyTo(self.targets)
cactusI.setPos(placeX, placeY, 0)
cactusI.setHpr(random.random() * 360, 0, 0)
cactusI.setScale(0.5 + random.random())
def unload(self):
self.notify.debug('unload')
DistributedMinigame.unload(self)
del self.__textGen
del self.toonDropShadows
self.dropShadowModel.removeNode()
del self.dropShadowModel
self.environModel.removeNode()
del self.environModel
self.fogOver.delete()
self.umbrella.removeNode()
del self.umbrella
for umbrella in self.remoteUmbrellas:
self.remoteUmbrellas[umbrella].removeNode()
self.remoteUmbrellas.clear()
del self.remoteUmbrellas
self.flySound.stop()
del self.flySound
self.rubberSound.stop()
del self.rubberSound
self.flutterSound.stop()
del self.flutterSound
del self.music
del self.sndAmbience
self.removeChildGameFSM(self.gameFSM)
del self.gameFSM
if self.targets:
self.targets.removeNode()
del self.targets
self.scoreboard.destroy()
del self.scoreboard
self.powerBar.destroy()
del self.powerBar
self.help.destroy()
del self.help
if self.localTrack:
self.localTrack.finish()
del self.localTrack
def onstage(self):
self.notify.debug('onstage')
DistributedMinigame.onstage(self)
self.arrowKeys = ArrowKeys.ArrowKeys()
toon = base.localAvatar
toon.reparentTo(render)
toon.setAnimState('SitStart', 1.0)
toon.useLOD(self.TOON_LOD)
self.__placeToon(self.localAvId)
self.localStartPos = toon.getPos()
localBand = RubberBand.RubberBand(toon, Point3(0, -1.75, 0), taskPriority=self.UPDATE_RUBBER_BAND_PRIORITY)
tP = self.getToonPlace(self.localAvId)
pos = Point3(tP[0], tP[1] + 10, tP[2])
localBand.setPos(pos)
self.rubberBands.append(localBand)
toon.dropShadow.hide()
toonPos = base.localAvatar.getPos()
camera.reparentTo(render)
toonPos = self.getAvatar(self.localAvId).getPos()
camera.setPosHpr(toonPos[0], toonPos[1] - 18, toonPos[2] + 10, 0, -15, 0)
base.camLens.setFov(80)
base.camLens.setFar(self.FOGDISTGROUND)
base.setBackgroundColor(self.AMB_COLOR)
self.__fog = Fog('ringGameFog')
if base.wantFog:
self.__fog.setColor(self.AMB_COLOR)
self.__fog.setLinearRange(0.1, self.FOGDISTGROUND)
render.setFog(self.__fog)
self.environNode = render.attachNewNode('environNode')
self.environBlocks = []
maxI = 4
self.maxDist = (maxI - 1) * self.ENVIRON_LENGTH
for i in range(-1, maxI + 1):
instance = self.environModel.copyTo(self.environNode)
y = self.ENVIRON_LENGTH * i
instance.setY(y)
self.addSkys(instance)
self.environBlocks.append(instance)
jRange = 3
for j in range(0, jRange):
instance = self.environModel.copyTo(self.environNode)
x = self.ENVIRON_WIDTH * (j + 1)
instance.setY(y)
instance.setX(-x)
height = random.random() * 5.0 + 5.0
heading = random.random() * 15.0 - 7.5
self.addSkys(instance)
self.environBlocks.append(instance)
if j == jRange - 2:
mount = instance.find(self.findLeftMount)
mount.setScale(1.0, 1.1, height)
mount.setBin('ground', 1)
mount.show()
sand = mount.find('**/sand_b')
sand.hide()
mount.setPos(mount.getX() + 8.5, 0, 0.0)
if i >= maxI - 1:
mount.setHpr(310, 0, 0)
mount.setScale(1.0, 1.5, height * 1.2)
mount.setPos(mount.getX() - 2.0, 0, 0.0)
if i == maxI:
mount.hide()
if i == -1:
mount.setHpr(50, 0, 0)
mount.setScale(1.0, 1.5, height * 1.2)
mount.setPos(mount.getX() + 5.0, 3.0, 0.0)
if j == jRange - 1:
sand = instance.find(self.findGround)
sand.hide()
for j in range(0, jRange):
instance = self.environModel.copyTo(self.environNode)
x = self.ENVIRON_WIDTH * (j + 1)
instance.setY(y)
instance.setX(x)
height = random.random() * 5.0 + 5.0
heading = random.random() * 15.0 - 7.5
self.addSkys(instance)
self.environBlocks.append(instance)
if j == jRange - 2:
mount = instance.find(self.findRightMount)
mount.setScale(1.0, 1.1, height)
mount.setBin('ground', 1)
mount.show()
sand = mount.find('**/sand_c')
sand.hide()
mount.setPos(mount.getX() - 8.5, 0, 0.0)
if i >= maxI - 1:
mount.setHpr(50, 0, 0)
mount.setScale(1.0, 1.5, height * 1.2)
mount.setPos(mount.getX() + 2.0, 0, 0.0)
if i == maxI:
mount.hide()
if i == -1:
mount.setHpr(310, 0, 0)
mount.setScale(1.0, 1.5, height * 1.2)
mount.setPos(mount.getX() - 5.0, 3.0, 0.0)
if j == jRange - 1:
sand = instance.find(self.findGround)
sand.hide()
self.__addToonDropShadow(self.getAvatar(self.localAvId))
self.__spawnUpdateEnvironTask()
self.__spawnUpdateShadowsTask()
self.__spawnUpdateLocalToonTask()
if self.music:
base.playMusic(self.music, looping=1, volume=0.8)
if None != self.sndAmbience:
base.playSfx(self.sndAmbience, looping=1, volume=0.8)
return
def reset(self):
toon = base.localAvatar
toon.setAnimState('SitStart', 1.0)
toon.useLOD(self.TOON_LOD)
self.__placeToon(self.localAvId)
toon.dropShadow.hide()
self.__spawnUpdateLocalToonTask()
toonPos = base.localAvatar.getPos()
camera.setPosHpr(toonPos[0], toonPos[1] - 26, toonPos[2] + 10, 0, -15, 0)
base.camLens.setFov(80)
self.resetNums()
def resetNums(self):
self.stretchX = 0
self.stretchY = 0
self.driftX = 0
self.driftY = 0
self.driftY = 0
self.jumpCount = 0
self.trampBounceCount = 0
self.cameraState = 'Low'
def offstage(self):
self.notify.debug('offstage')
DistributedMinigame.offstage(self)
if self.music:
self.music.stop()
if None != self.sndAmbience:
self.sndAmbience.stop()
self.__killUpdateLocalToonTask()
self.__killUpdateShadowsTask()
self.__killUpdateEnvironTask()
self.__killCountDownTask()
del self.soundTable
self.__removeAllToonDropShadows()
render.clearFog()
base.camLens.setFar(ToontownGlobals.DefaultCameraFar)
base.camLens.setFov(ToontownGlobals.DefaultCameraFov)
camera.setHpr(0, 90, 0)
base.setBackgroundColor(ToontownGlobals.DefaultBackgroundColor)
self.arrowKeys.destroy()
del self.arrowKeys
for block in self.environBlocks:
del block
self.environNode.removeNode()
del self.environNode
for avId in self.avIdList:
av = self.getAvatar(avId)
if av:
av.dropShadow.show()
av.resetLOD()
for band in self.rubberBands:
band.delete()
rubberBands = []
self.targetsPlaced = []
return
def handleDisabledAvatar(self, avId):
self.notify.debug('handleDisabledAvatar')
self.notify.debug('avatar ' + str(avId) + ' disabled')
self.__removeToonDropShadow(self.remoteToons[avId])
DistributedMinigame.handleDisabledAvatar(self, avId)
def __genText(self, text):
self.__textGen.setText(text)
return self.__textGen.generate()
def __placeToon(self, avId):
toon = self.getAvatar(avId)
i = self.avIdList.index(avId)
numToons = float(self.numPlayers)
x = i * self.TOON_INITIAL_SPACING
x -= self.TOON_INITIAL_SPACING * (numToons - 1) / 2.0
pos = self.getToonPlace(avId)
toon.setPosHpr(pos[0], pos[1], pos[2], 0, 0, 0)
def getToonPlace(self, avId):
toon = self.getAvatar(avId)
i = self.avIdList.index(avId)
numToons = float(self.numPlayers)
x = i * self.TOON_INITIAL_SPACING
x -= self.TOON_INITIAL_SPACING * (numToons - 1) / 2.0
pos = Point3(x + self.placeShift, self.TOON_Y, 1.0)
return pos
def setGameReady(self):
if not self.hasLocalToon:
return
self.notify.debug('setGameReady')
if DistributedMinigame.setGameReady(self):
return
if not self.isSinglePlayer():
base.localAvatar.collisionsOff()
cSphere = CollisionSphere(0.0, 0.0, 0.0, TargetGameGlobals.CollisionRadius)
cSphereNode = CollisionNode('RingGameSphere-%s' % self.localAvId)
cSphereNode.addSolid(cSphere)
cSphereNode.setFromCollideMask(TargetGameGlobals.CollideMask)
cSphereNode.setIntoCollideMask(BitMask32.allOff())
self.cSphereNodePath = base.localAvatar.attachNewNode(cSphereNode)
self.pusher = CollisionHandlerPusher()
self.pusher.addCollider(self.cSphereNodePath, base.localAvatar)
self.pusher.setHorizontal(0)
self.cTrav = CollisionTraverser('DistributedRingGame')
self.cTrav.addCollider(self.cSphereNodePath, self.pusher)
self.remoteToonCollNPs = {}
for avId in self.remoteAvIdList:
toon = self.getAvatar(avId)
if toon:
cSphere = CollisionSphere(0.0, 0.0, 0.0, TargetGameGlobals.CollisionRadius)
cSphereNode = CollisionNode('RingGameSphere-%s' % avId)
cSphereNode.addSolid(cSphere)
cSphereNode.setCollideMask(TargetGameGlobals.CollideMask)
cSphereNP = toon.attachNewNode(cSphereNode)
self.remoteToonCollNPs[avId] = cSphereNP
for avId in self.remoteAvIdList:
toon = self.getAvatar(avId)
if toon:
toon.reparentTo(render)
self.__placeToon(avId)
toon.setAnimState('SitStart', 1.0)
toon.useLOD(self.TOON_LOD)
toon.dropShadow.hide()
self.__addToonDropShadow(toon)
band = RubberBand.RubberBand(toon, Point3(0, -1.75, 0), taskPriority=self.UPDATE_RUBBER_BAND_PRIORITY)
tP = self.getToonPlace(avId)
pos = Point3(tP[0], tP[1] + 10, tP[2])
band.setPos(pos)
self.rubberBands.append(band)
umbrella = self.umbrella.copyTo(render)
self.remoteUmbrellas[avId] = umbrella
test = 0
kill = 16
while test == 0 and kill > 0:
kill -= 1
pick = random.randint(0, 3)
if self.umbrellaColorSelect[pick]:
self.umbrellaColorSelect[pick] = 0
test = 1
tex = loader.loadTexture(DistributedTargetGame.UMBRELLA_TEXTURE_LIST[pick])
tex.setMinfilter(Texture.FTLinearMipmapLinear)
tex.setMagfilter(Texture.FTLinear)
umbrella.setTexture(tex, 1)
open = umbrella.find('**/open_umbrella')
open.hide()
open.setPos(0.1, 0.2, -0.1)
open.setHpr(-90.0, 180.0, 0.0)
open.setScale(1.5)
closed = umbrella.find('**/closed_umbrella')
closed.show()
hand = toon.getRightHands()[0]
ce = CompassEffect.make(NodePath(), CompassEffect.PRot)
closed.node().setEffect(ce)
closed.setHpr(0.0, 90.0, 35.0)
umbrella.reparentTo(hand)
toon.startSmooth()
self.remoteToons = {}
for avId in self.remoteAvIdList:
toon = self.getAvatar(avId)
self.remoteToons[avId] = toon
labelIndex = 0
for avId in self.avIdList:
av = self.getAvatar(avId)
self.avLabels[labelIndex]['text'] = av.getName()
labelIndex += 1
def setGameStart(self, timestamp):
if not self.hasLocalToon:
return
self.notify.debug('setGameStart')
DistributedMinigame.setGameStart(self, timestamp)
self.gameFSM.request('prelaunch')
def enterOff(self):
self.notify.debug('enterOff')
def exitOff(self):
pass
def enterPrelaunch(self):
self.defineConstants()
self.resetNums()
self.gameFSM.request('launch')
self.powerBar.show()
self.powerBar['value'] = self.startPower
camera.reparentTo(render)
self.__placeToon(self.localAvId)
toonPos = self.getAvatar(self.localAvId).getPos()
newPos = Point3(toonPos[0], toonPos[1] - 25, toonPos[2] + 7)
newHpr = Point3(0, -15, 0)
self.cameraWork = camera.posHprInterval(2.5, newPos, newHpr, blendType='easeInOut')
self.cameraWork.start()
base.camLens.setFov(80)
self.stretchY = self.startPower
self.power = self.startPower
self.scoreboard.hide()
open = self.umbrella.find('**/open_umbrella')
open.hide()
closed = self.umbrella.find('**/closed_umbrella')
closed.show()
self.umbrella.setScale(1.0)
if self.targetMarker:
self.targetMarker.removeNode()
def exitPrelaunch(self):
pass
def enterLaunch(self):
self.__spawnUpdatePowerBarTask()
self.__spawnCountDownTask()
self.help.show()
self.help['text'] = TTLocalizer.TargetGameCountHelp
def exitLaunch(self):
self.cameraWork.finish()
self.__killUpdatePowerBarTask()
self.speedLaunch = self.power
self.powerBar.hide()
self.playSound('launch')
def enterFly(self):
self.notify.debug('enterFly')
self.__spawnCollisionDetectionTask()
self.__placeToon(self.localAvId)
self.speedForward = self.speedLaunch
self.laterial = -self.launchLaterial * 7
self.zVel = self.speedForward * 0.5
toon = base.localAvatar
toon.b_setAnimState('swim', 1.0)
toon.stopBobSwimTask()
toon.dropShadow.hide()
camera.reparentTo(base.localAvatar)
camera.setPosHpr(0, self.CAMERA_Y + self.TOON_Y + 12, 5, 0, -15, 0)
base.camLens.setFov(80)
self.help.show()
self.help['text'] = TTLocalizer.TargetGameFlyHelp
self.rubberSound.setVolume(0.0)
self.rubberSound.setPlayRate(1.0)
self.rubberSound.stop()
def exitFly(self):
taskMgr.remove(self.END_GAME_WAIT_TASK)
self.__killCollisionDetectionTask()
self.help.hide()
def enterFall(self):
self.notify.debug('enterLaunch')
toon = base.localAvatar
toon.b_setAnimState('jumpAirborne', 1.0)
toon.dropShadow.hide()
self.speedForward = self.speedForward * 0.5
self.gravity = 4
newHpr = Point3(0, -68, 0)
newPos = Point3(0, self.CAMERA_Y + self.TOON_Y + 15, 15)
camera.posHprInterval(2.5, newPos, newHpr, blendType='easeInOut', name=self.FLY2FALL_CAM_TASK).start()
open = self.umbrella.find('**/open_umbrella')
open.show()
closed = self.umbrella.find('**/closed_umbrella')
closed.hide()
self.umbrella.setHpr(0, 180.0, -25.0)
self.umbrella.setScale(1.5)
self.help.show()
self.help['text'] = TTLocalizer.TargetGameFallHelp
self.playSound('umbrella')
self.flutterSound.play()
def exitFall(self):
self.flutterSound.stop()
def enterBouncing(self):
self.notify.debug('enterLaunch')
self.gravity = 12.5
open = self.umbrella.find('**/open_umbrella')
open.hide()
closed = self.umbrella.find('**/closed_umbrella')
closed.hide()
self.umbrella.setHpr(0, 0, 0)
self.umbrella.setScale(1.0)
toon = base.localAvatar
toon.b_setAnimState('neutral', 1.0)
toon.dropShadow.hide()
self.help.show()
self.help['text'] = TTLocalizer.TargetGameBounceHelp
def exitBouncing(self):
pass
def enterScore(self):
def count(value, list):
count = 0
for item in list:
if value == item:
count += 1
return count
self.notify.debug('enterScore')
self.__killUpdateLocalToonTask()
self.__spawnGameDoneTask()
self.scoreboard.show()
score = 1
self.sendUpdate('setScore', [base.localAvatar.getX(), base.localAvatar.getY()])
topValue = 0
hitTarget = None
for target in self.targetsPlaced:
radius = self.targetSize[target[2]]
value = self.targetValue[target[2]]
posX = target[0]
posY = target[1]
dx = posX - base.localAvatar.getX()
dy = posY - base.localAvatar.getY()
distance = math.sqrt(dx * dx + dy * dy)
if distance < radius and topValue < value:
topValue = value
hitTarget = target
hitX = posX
hitY = posY
if hitTarget:
targetGN = GeomNode('target Circle')
targetNodePathGeom = self.targets.attachNewNode(targetGN)
targetNodePathGeom.setPos(hitX, hitY, 0)
addRing(targetGN, TargetGameGlobals.colorBlack, 100, self.targetSize[hitTarget[2]] + 0.5, 0)
targetNodePathGeom.setColorScale(TargetGameGlobals.colorWhite['Red'], TargetGameGlobals.colorWhite['Green'], TargetGameGlobals.colorWhite['Blue'], TargetGameGlobals.colorWhite['Alpha'])
targetNodePathGeom.setBin('ground', hitTarget[2] * 2 + 100)
targetNodePathGeom.setDepthWrite(False)
targetNodePathGeom.setDepthTest(False)
targetNodePathGeom.setTransparency(TransparencyAttrib.MAlpha)
self.targetMarker = targetNodePathGeom
score = topValue
self.localTrack = Sequence()
if self.hitInfo == 'OnButt':
self.localTrack.append(ActorInterval(base.localAvatar, 'slip-forward', startFrame=25, endFrame=55))
self.hitInfo = 'GettingUp'
else:
self.localTrack.append(ActorInterval(base.localAvatar, 'slip-forward', startFrame=50, endFrame=55))
self.localTrack.append(Wait(0.5))
if score <= 1:
self.localTrack.append(Parallel(Func(base.localAvatar.b_setAnimState, 'Sad', 1.0), Func(self.playSound, 'miss')))
else:
self.localTrack.append(Parallel(Func(base.localAvatar.b_setAnimState, 'victory', 1.0), Func(self.playSound, 'score')))
newHpr = Point3(180, 10, 0)
newPos = Point3(0, -(self.CAMERA_Y + self.TOON_Y + 12), 1)
camera.posHprInterval(5.0, newPos, newHpr, blendType='easeInOut', name=self.SCORE_CAM_TASK).start()
self.help.hide()
self.localTrack.start()
return
def exitScore(self):
pass
def enterCleanup(self):
self.notify.debug('enterCleanup')
if not self.isSinglePlayer():
for np in list(self.remoteToonCollNPs.values()):
np.removeNode()
del self.remoteToonCollNPs
self.cSphereNodePath.removeNode()
del self.cSphereNodePath
del self.pusher
del self.cTrav
base.localAvatar.collisionsOn()
def exitCleanup(self):
pass
def signalDone(self):
self.sendUpdate('setPlayerDone', [])
def __spawnUpdatePowerBarTask(self):
taskMgr.remove(self.UPDATE_POWERBAR_TASK)
taskMgr.add(self.__updatePowerBarTask, self.UPDATE_POWERBAR_TASK, priority=self.UPDATE_POWER_BAR_PRIORITY)
self.rubberSound.play()
self.bandVolume = 0.0
def __killUpdatePowerBarTask(self):
taskMgr.remove(self.UPDATE_POWERBAR_TASK)
taskMgr.remove(self.TOONSTRETCHTASK)
def __spawnCountDownTask(self):
self.countDown = 10
self.signalLaunch = 0
taskMgr.remove(self.UPDATE_COUNTDOWN_TASK)
self.doCountDown()
def __killCountDownTask(self):
taskMgr.remove(self.UPDATE_COUNTDOWN_TASK)
def __spawnGameDoneTask(self):
taskMgr.remove(self.GAME_DONE_TASK)
taskMgr.doMethodLater(5.0, self.__gameDone, self.GAME_DONE_TASK)
def __killUpdateGameDoneTask(self):
taskMgr.remove(self.GAME_DONE_TASK)
def __spawnUpdateLocalToonTask(self):
self.__initPosBroadcast()
taskMgr.remove(self.UPDATE_LOCALTOON_TASK)
taskMgr.add(self.__updateLocalToonTask, self.UPDATE_LOCALTOON_TASK, priority=self.UPDATE_LOCAL_TOON_PRIORITY)
def __killUpdateLocalToonTask(self):
taskMgr.remove(self.UPDATE_LOCALTOON_TASK)
def doCountDown(self, task = None):
if self.countDown < 0:
self.signalLaunch = 1
else:
self.powerBar['text'] = TTLocalizer.TargetGameCountdown % self.countDown
self.countDown -= 1
taskMgr.doMethodLater(1.0, self.doCountDown, self.UPDATE_COUNTDOWN_TASK)
def __initPosBroadcast(self):
self.__posBroadcastPeriod = 0.2
self.__timeSinceLastPosBroadcast = 0.0
self.__lastPosBroadcast = self.getAvatar(self.localAvId).getPos()
self.__storeStop = 0
lt = self.getAvatar(self.localAvId)
lt.d_clearSmoothing()
lt.sendCurrentPosition()
def __posBroadcast(self, dt):
self.__timeSinceLastPosBroadcast += dt
if self.__timeSinceLastPosBroadcast > self.__posBroadcastPeriod:
self.__timeSinceLastPosBroadcast -= self.__posBroadcastPeriod
self.getAvatar(self.localAvId).cnode.broadcastPosHprFull()
def __spawnUpdateEnvironTask(self):
taskMgr.remove(self.UPDATE_ENVIRON_TASK)
taskMgr.add(self.__updateEnvironTask, self.UPDATE_ENVIRON_TASK)
def __killUpdateEnvironTask(self):
taskMgr.remove(self.UPDATE_ENVIRON_TASK)
def __updateEnvironTask(self, task):
return
dt = globalClock.getDt()
self.speedForward = self.speedForward - self.speedForward * self.airResistance * dt
t = globalClock.getFrameTime() - self.__timeBase
self.distance = self.distance + dt * self.speedForward
distance = self.distance
distance %= self.ENVIRON_LENGTH
self.environNode.setY(-distance)
return Task.cont
def __updatePowerBarTask(self, task):
powerUp = 0
timeDiff = None
if not self.arrowKeys.rightPressed():
self.canPressRight = 1
elif self.arrowKeys.rightPressed() and self.canPressRight:
powerUp = 1
self.canPressRight = 0
if not self.arrowKeys.leftPressed():
self.canPressLeft = 1
elif self.arrowKeys.leftPressed() and self.canPressLeft:
powerUp = 1
self.canPressLeft = 0
if self.lastPressTime:
timeDiff = globalClock.getFrameTime() - self.lastPressTime
if powerUp and not self.lastPressTime:
self.lastPressTime = globalClock.getFrameTime()
self.ticker = 0.0
elif powerUp:
splitTime = abs(timeDiff)
if splitTime < 0.15:
splitTime = 0.15
self.power += 0.6 / abs(timeDiff) + 5.0
self.lastPressTime = globalClock.getFrameTime()
self.powerBar['value'] = self.power
if self.signalLaunch:
self.lastPressTime = 1
self.ticker = 1
timeDiff = 100000
if self.lastPressTime:
self.ticker += globalClock.getDt()
if self.ticker >= 0.1:
self.ticker = 0.0
powerDiv = 0.05
self.power -= 1.0 + 0.2 * (self.power * powerDiv * (self.power * powerDiv))
if timeDiff is not None and timeDiff > 0.5:
self.power = self.powerBar['value']
self.signalLaunch = 0
if self.power > 120:
self.power = 120
if self.power < 40:
self.power = 40
self.gameFSM.request('fly')
self.stretchY = 0.9 * self.stretchY + 0.1 * self.power
self.stretchX = 0.9 * self.stretchX + 0.1 * self.launchLaterial
base.localAvatar.setY(self.localStartPos[1] - self.stretchY * 0.12)
base.localAvatar.setX(self.localStartPos[0] + self.stretchX)
dt = globalClock.getDt()
self.__posBroadcast(dt)
stretchDiff = abs(self.stretchY - self.power) * 0.2
self.bandVolume += stretchDiff
self.bandVolume -= globalClock.getDt()
self.rubberSound.setVolume(self.bandVolume)
self.rubberSound.setPlayRate(1.0 + self.stretchY / 120.0)
return task.cont
def __updateLocalToonTask(self, task):
stateName = None
if self.gameFSM.getCurrentState():
stateName = self.gameFSM.getCurrentState().getName()
toonPos = self.getAvatar(self.localAvId).getPos()
dt = globalClock.getDt()
if stateName == 'fall':
self.speedForward = self.speedForward - self.speedForward * self.umbrellaResistance * dt
self.laterial = self.laterial - self.laterial * self.umbrellaResistance * dt
if toonPos[2] > 350.0:
diff = toonPos[2] - 350.0
self.speedForward += -diff * dt * 0.05
else:
self.speedForward = self.speedForward - self.speedForward * self.airResistance * dt
self.laterial = self.laterial - self.laterial * self.airResistance * dt
t = globalClock.getFrameTime() - self.__timeBase
self.distance = self.distance + dt * self.speedForward
if self.distance > self.maxDist:
self.distance = self.maxDist
if stateName in ['fall', 'bouncing']:
if self.distance < 15.0:
self.distance = 15.0
pos = [toonPos[0], self.distance, toonPos[2]]
if stateName in ['fly', 'fall']:
pos[0] += dt * self.laterial
liftMult = 0
if stateName == 'fly':
if self.arrowKeys.upPressed():
pass
if self.arrowKeys.downPressed():
self.gameFSM.request('fall')
elif stateName == 'fall':
if self.driftX > self.TOONXZ_SPEED:
self.driftX = self.TOONXZ_SPEED
if self.driftX < -self.TOONXZ_SPEED:
self.driftX = -self.TOONXZ_SPEED
if self.driftY > self.TOONXZ_SPEED:
self.driftY = self.TOONXZ_SPEED
if self.driftY < -self.TOONXZ_SPEED:
self.driftY = -self.TOONXZ_SPEED
if self.arrowKeys.rightPressed():
self.driftX += self.TOONXZ_SPEED * dt
if self.arrowKeys.leftPressed():
self.driftX -= self.TOONXZ_SPEED * dt
if self.arrowKeys.upPressed():
self.driftY += self.TOONXZ_SPEED * dt
if self.arrowKeys.downPressed():
self.driftY -= self.TOONXZ_SPEED * dt
pos[0] += self.driftX * dt
pos[1] += self.driftY * dt
self.distance = pos[1]
liftMult = 1
elif stateName == 'bouncing':
pos[0] += self.driftX * dt
pos[1] += self.driftY * dt
self.distance = pos[1]
else:
xVel = 0.0
if self.arrowKeys.leftPressed():
xVel -= self.TOONXZ_SPEED
if self.arrowKeys.rightPressed():
xVel += self.TOONXZ_SPEED
self.launchLaterial += xVel * dt
if self.launchLaterial < -TargetGameGlobals.MAX_LAT:
self.launchLaterial = -TargetGameGlobals.MAX_LAT
if self.launchLaterial > TargetGameGlobals.MAX_LAT:
self.launchLaterial = TargetGameGlobals.MAX_LAT
pos[0] = self.getToonPlace(self.localAvId)[0] - self.launchLaterial
lift = (self.speedForward - self.speedStall) / self.speedStall * liftMult
onScreenDebug.removeAllWithPrefix(self.getDisplayPrefix())
onScreenDebug.add('%s Vel' % self.getDisplayPrefix(), self.zVel)
onScreenDebug.add('%s Lift' % self.getDisplayPrefix(), lift)
onScreenDebug.add('%s Gravity' % self.getDisplayPrefix(), self.gravity)
onScreenDebug.add('%s Pos' % self.getDisplayPrefix(), pos[2])
onScreenDebug.add('%s Drifty' % self.getDisplayPrefix(), self.driftY)
if lift < 0:
lift = 0
upforce = lift * 10.0 - self.gravity
self.zVel += (lift - self.gravity) * dt
pos[2] += self.zVel * dt
if pos[2] < self.trampZ:
if self.jumpCount:
self.playSound('trampoline')
rebound = 0.75
if self.trampBounceCount >= 1:
rebound = 0.5
self.gameFSM.request('bouncing')
pos[2] = self.trampZ
if self.zVel != 0:
signZ = self.zVel / abs(self.zVel)
else:
signZ = 1
self.zVel = -(self.zVel * rebound - signZ * 1.0)
self.trampBounceCount += 1
if abs(self.zVel) < 1.0:
self.zVel = 0
toon = base.localAvatar
if stateName in ['fly', 'fall', 'bouncing']:
toon.b_setAnimState('neutral', 1.0)
toon.dropShadow.hide()
self.gameFSM.request('score')
elif pos[2] < 0.1:
toon = base.localAvatar
if stateName == 'fall' or stateName == 'fly':
self.gameFSM.request('bouncing')
if stateName == 'fly':
ivolume = math.sqrt(abs(self.zVel) / 40.0)
self.hitInfo = 'OnButt'
self.localTrack = ActorInterval(toon, 'slip-forward', startFrame=12, endFrame=24)
self.localTrack.start()
self.playSound('impact', ivolume)
self.playSound('bounce', ivolume)
elif stateName == 'fall' or stateName == 'bouncing':
ivolume = math.sqrt(abs(self.zVel) / 40.0)
if ivolume > 0.4:
if self.hitInfo == 'OnButt':
self.localTrack = ActorInterval(toon, 'slip-forward', startFrame=13, endFrame=24)
self.localTrack.start()
else:
self.localTrack = ActorInterval(toon, 'jump-land', startFrame=6, endFrame=21)
self.localTrack.start()
self.playSound('bounce', ivolume)
pos[2] = 0.1
rebound = 0.5
self.speedForward = self.speedForward * rebound
self.driftX = self.driftX * rebound
self.driftY = self.driftY * rebound
toon = base.localAvatar
if self.zVel != 0:
signZ = self.zVel / abs(self.zVel)
else:
signZ = 1
self.zVel = -(self.zVel * rebound - signZ * 1.0)
if abs(self.zVel) < 1.0:
self.zVel = 0
if stateName == 'fly' or stateName == 'bouncing':
self.gameFSM.request('score')
if pos[0] > TargetGameGlobals.MAX_FIELD_SPAN:
pos[0] = TargetGameGlobals.MAX_FIELD_SPAN
self.laterial = 0
if pos[0] < -TargetGameGlobals.MAX_FIELD_SPAN:
pos[0] = -TargetGameGlobals.MAX_FIELD_SPAN
self.laterial = 0
self.getAvatar(self.localAvId).setPos(pos[0], pos[1], pos[2])
if hasattr(self, 'cTrav'):
self.cTrav.traverse(render)
if stateName in ['fly', 'fall', 'bouncing']:
self.__posBroadcast(dt)
visZ = camera.getZ(render)
lowHeight = 100
lowRange = 20
opacityLow = 1
baseOpLow = 0.6
baseTransLow = 1.0 - baseOpLow
if visZ < lowHeight - lowRange or visZ > lowHeight + lowRange:
transLow = 1.0
else:
dif = abs(visZ - lowHeight)
transLow = dif / lowRange
for item in self.skyListLow:
item.setColorScale(1.0, 1.0, 1.0, transLow * baseOpLow)
midHeight = 126
midRange = 20
opacityMid = 1
baseOpMid = 1.0
baseTransMid = 1.0 - baseOpMid
if visZ < midHeight - midRange or visZ > midHeight + midRange:
transMid = 1.0
else:
dif = abs(visZ - midHeight)
transMid = dif / midRange
for item in self.skyListMid:
item.setColorScale(1.0, 1.0, 1.0, transMid * baseOpMid)
minTrans = min(1.0, transMid, transLow)
fogVis = 1.0 - minTrans
fogColor = self.AMB_COLOR * minTrans + self.CLOUD_COLOR * fogVis
fogRange = minTrans * self.FOGDISTGROUND + fogVis * self.FOGDISTCLOUD
newCamState = 'Low'
if visZ > midHeight:
newCamState = 'High'
if self.cameraState != newCamState:
self.cameraState = newCamState
self.cloudRendering('High')
elif visZ > lowHeight:
newCamState = 'Mid'
if self.cameraState != newCamState:
if self.cameraState == 'Low':
self.playSound('wind1')
self.cameraState = newCamState
self.cloudRendering('Mid')
else:
newCamState = 'Low'
if self.cameraState != newCamState:
self.cameraState = newCamState
self.cloudRendering('Low')
overlayOp = 0.5
self.fogOver.setOpacity(fogVis * overlayOp)
vol = (self.speedForward + abs(self.zVel)) / 120.0
self.flySound.setVolume(vol)
self.flySound.setPlayRate(1.0 + abs(self.zVel) * 0.005)
if self.updateTick % 5 == 0:
for avId in self.remoteAvIdList:
toon = self.getAvatar(avId)
if toon:
state = toon.animFSM.getCurrentState().getName()
umbrella = self.remoteUmbrellas.get(avId)
if umbrella:
if state == 'Sit':
open = umbrella.find('**/open_umbrella')
open.hide()
closed = umbrella.find('**/closed_umbrella')
closed.show()
elif state == 'swim':
open = umbrella.find('**/open_umbrella')
open.hide()
closed = umbrella.find('**/closed_umbrella')
closed.show()
elif state == 'jumpAirborne':
open = umbrella.find('**/open_umbrella')
open.show()
closed = umbrella.find('**/closed_umbrella')
closed.hide()
elif state == 'neutral':
open = umbrella.find('**/open_umbrella')
open.hide()
closed = umbrella.find('**/closed_umbrella')
closed.hide()
else:
open = umbrella.find('**/open_umbrella')
open.hide()
closed = umbrella.find('**/closed_umbrella')
closed.hide()
self.updateTick += 1
return Task.cont
def cloudRendering(self, layer):
if layer == 'Low':
for item in self.skyListMid:
item.setBin('fixed', 3)
for item in self.skyListLow:
item.setBin('fixed', 4)
elif layer == 'Mid':
for item in self.skyListMid:
item.setBin('fixed', 3)
for item in self.skyListLow:
item.setBin('fixed', 3)
elif layer == 'High':
for item in self.skyListMid:
item.setBin('fixed', 4)
for item in self.skyListLow:
item.setBin('fixed', 3)
def __addDropShadow_INTERNAL(self, object, scale_x, scale_y, scale_z, list):
shadow = self.dropShadowModel.copyTo(render)
shadow.setPos(0, self.CAMERA_Y, -100)
shadow.setBin('shadow', 100)
shadow.setDepthWrite(False)
shadow.setDepthTest(True)
shadow.setScale(scale_x, scale_y, scale_z)
list.append([shadow, object])
def __removeDropShadow_INTERNAL(self, object, list):
for i in range(len(list)):
entry = list[i]
if entry[1] == object:
entry[0].removeNode()
list.pop(i)
return
self.notify.warning('parent object ' + str(object) + ' not found in drop shadow list!')
def __addToonDropShadow(self, object):
self.__addDropShadow_INTERNAL(object, 0.5, 0.5, 0.5, self.toonDropShadows)
def __removeToonDropShadow(self, object):
self.__removeDropShadow_INTERNAL(object, self.toonDropShadows)
def __removeAllToonDropShadows(self):
for entry in self.toonDropShadows:
entry[0].removeNode()
self.toonDropShadows = []
def __spawnUpdateShadowsTask(self):
taskMgr.remove(self.UPDATE_SHADOWS_TASK)
taskMgr.add(self.__updateShadowsTask, self.UPDATE_SHADOWS_TASK, priority=self.UPDATE_SHADOWS_PRIORITY)
def __killUpdateShadowsTask(self):
taskMgr.remove(self.UPDATE_SHADOWS_TASK)
def __updateShadowsTask(self, task):
list = self.toonDropShadows
for entry in list:
object = entry[1]
y = object.getY(render)
x = object.getX(render)
if self.jumpCount and object == base.localAvatar:
z = self.trampZ + self.SHADOW_Z_OFFSET
else:
z = 0.0 + self.SHADOW_Z_OFFSET
shadow = entry[0]
shadow.setPos(x, y, z)
return Task.cont
def __spawnCollisionDetectionTask(self):
self.__ringGroupsPassed = 0
taskMgr.remove(self.COLLISION_DETECTION_TASK)
taskMgr.add(self.__collisionDetectionTask, self.COLLISION_DETECTION_TASK, priority=self.COLLISION_DETECTION_PRIORITY)
def __killCollisionDetectionTask(self):
taskMgr.remove(self.COLLISION_DETECTION_TASK)
def __collisionDetectionTask(self, task):
return Task.cont
def __endGameDolater(self, task):
self.gameOver()
return Task.done
def setTimeBase(self, timestamp):
if not self.hasLocalToon:
return
self.__timeBase = globalClockDelta.networkToLocalTime(timestamp)
def setColorIndices(self, a, b, c, d):
if not self.hasLocalToon:
return
self.colorIndices = [a,
b,
c,
d]
def getDisplayPrefix(self):
return 'TargetGame'
def __gameDone(self, task = None):
self.signalDone()
return task.done
def setGameDone(self, extra = None):
self.gameOver()
def setRoundDone(self):
if not self.hasLocalToon:
return
self.round += 1
self.roundLabel['text'] = TTLocalizer.TargetGameBoard % self.round
self.reset()
self.gameFSM.request('prelaunch')
def setSingleScore(self, score, avId):
if not self.hasLocalToon:
return
for existIndex in range(len(self.avIdList)):
if self.avIdList[existIndex] == avId:
self.scoreLabels[existIndex]['text'] = '%s' % score
def jumpIn(self, colEntry):
self.jumpCount += 1
def jumpOut(self, colEntry):
self.jumpCount -= 1
if self.jumpCount < 0:
self.jumpCount = 0