mirror of
https://github.com/Sneed-Group/Poodletooth-iLand
synced 2024-12-24 12:12:36 -06:00
321 lines
9.5 KiB
Python
321 lines
9.5 KiB
Python
|
from pandac.PandaModules import *
|
||
|
from NametagConstants import *
|
||
|
from Nametag3d import *
|
||
|
from Nametag2d import *
|
||
|
|
||
|
class NametagGroup:
|
||
|
CCNormal = CCNormal
|
||
|
CCNoChat = CCNoChat
|
||
|
CCNonPlayer = CCNonPlayer
|
||
|
CCSuit = CCSuit
|
||
|
CCToonBuilding = CCToonBuilding
|
||
|
CCSuitBuilding = CCSuitBuilding
|
||
|
CCHouseBuilding = CCHouseBuilding
|
||
|
CCSpeedChat = CCSpeedChat
|
||
|
CCFreeChat = CCFreeChat
|
||
|
|
||
|
CHAT_TIMEOUT_MAX = 12.0
|
||
|
CHAT_TIMEOUT_MIN = 4.0
|
||
|
CHAT_TIMEOUT_PROP = 0.5
|
||
|
|
||
|
def __init__(self):
|
||
|
self.nametag2d = Nametag2d()
|
||
|
self.nametag3d = Nametag3d()
|
||
|
self.icon = PandaNode('icon')
|
||
|
|
||
|
self.chatTimeoutTask = None
|
||
|
|
||
|
self.font = None
|
||
|
self.speechFont = None
|
||
|
self.name = ''
|
||
|
self.displayName = ''
|
||
|
self.wordWrap = None
|
||
|
self.qtColor = VBase4(1,1,1,1)
|
||
|
self.colorCode = CCNormal
|
||
|
self.avatar = None
|
||
|
self.active = True
|
||
|
|
||
|
self.chatPages = []
|
||
|
self.chatPage = 0
|
||
|
self.chatFlags = 0
|
||
|
|
||
|
self.objectCode = None
|
||
|
|
||
|
self.manager = None
|
||
|
|
||
|
self.nametags = []
|
||
|
self.addNametag(self.nametag2d)
|
||
|
self.addNametag(self.nametag3d)
|
||
|
|
||
|
self.visible3d = True # Is a 3D nametag visible, or do we need a 2D popup?
|
||
|
|
||
|
self.tickTask = taskMgr.add(self.__tickTask, self.getUniqueId(), sort=45)
|
||
|
|
||
|
self.stompTask = None
|
||
|
self.stompText = None
|
||
|
self.stompFlags = 0
|
||
|
|
||
|
def destroy(self):
|
||
|
taskMgr.remove(self.tickTask)
|
||
|
if self.manager is not None:
|
||
|
self.unmanage(self.manager)
|
||
|
for nametag in list(self.nametags):
|
||
|
self.removeNametag(nametag)
|
||
|
if self.stompTask:
|
||
|
self.stompTask.remove()
|
||
|
|
||
|
def getNametag2d(self):
|
||
|
return self.nametag2d
|
||
|
|
||
|
def getNametag3d(self):
|
||
|
return self.nametag3d
|
||
|
|
||
|
def getNameIcon(self):
|
||
|
return self.icon
|
||
|
|
||
|
def getNumChatPages(self):
|
||
|
if not self.chatFlags & (CFSpeech|CFThought):
|
||
|
return 0
|
||
|
|
||
|
return len(self.chatPages)
|
||
|
|
||
|
def setPageNumber(self, page):
|
||
|
self.chatPage = page
|
||
|
self.updateTags()
|
||
|
|
||
|
def getChatStomp(self):
|
||
|
return bool(self.stompTask)
|
||
|
|
||
|
def getChat(self):
|
||
|
if self.chatPage >= len(self.chatPages):
|
||
|
return ''
|
||
|
else:
|
||
|
return self.chatPages[self.chatPage]
|
||
|
|
||
|
def getStompText(self):
|
||
|
return self.stompText
|
||
|
|
||
|
def getStompDelay(self):
|
||
|
return 0.2
|
||
|
|
||
|
def getUniqueId(self):
|
||
|
return 'Nametag-%d' % id(self)
|
||
|
|
||
|
def hasButton(self):
|
||
|
return bool(self.getButtons())
|
||
|
|
||
|
def getButtons(self):
|
||
|
if self.getNumChatPages() < 2:
|
||
|
# Either only one page or no pages displayed. This means no button,
|
||
|
# unless the game code specifically requests one.
|
||
|
if self.chatFlags & CFQuitButton:
|
||
|
return NametagGlobals.quitButtons
|
||
|
elif self.chatFlags & CFPageButton:
|
||
|
return NametagGlobals.pageButtons
|
||
|
else:
|
||
|
return None
|
||
|
elif self.chatPage == self.getNumChatPages()-1:
|
||
|
# Last page of a multiple-page chat. This calls for a quit button,
|
||
|
# unless the game says otherwise.
|
||
|
if not self.chatFlags & CFNoQuitButton:
|
||
|
return NametagGlobals.quitButtons
|
||
|
else:
|
||
|
return None
|
||
|
else:
|
||
|
# Non-last page of a multiple-page chat. This calls for a page
|
||
|
# button, but only if the game requests it:
|
||
|
if self.chatFlags & CFPageButton:
|
||
|
return NametagGlobals.pageButtons
|
||
|
else:
|
||
|
return None
|
||
|
|
||
|
def setActive(self, active):
|
||
|
self.active = active
|
||
|
|
||
|
def isActive(self):
|
||
|
return self.active
|
||
|
|
||
|
def setAvatar(self, avatar):
|
||
|
self.avatar = avatar
|
||
|
|
||
|
def setFont(self, font):
|
||
|
self.font = font
|
||
|
self.updateTags()
|
||
|
|
||
|
def setSpeechFont(self, font):
|
||
|
self.speechFont = font
|
||
|
self.updateTags()
|
||
|
|
||
|
def setWordwrap(self, wrap):
|
||
|
self.wordWrap = wrap
|
||
|
self.updateTags()
|
||
|
|
||
|
def setColorCode(self, cc):
|
||
|
self.colorCode = cc
|
||
|
self.updateTags()
|
||
|
|
||
|
def setName(self, name):
|
||
|
self.name = name
|
||
|
self.updateTags()
|
||
|
|
||
|
def setDisplayName(self, name):
|
||
|
self.displayName = name
|
||
|
self.updateTags()
|
||
|
|
||
|
def setQtColor(self, color):
|
||
|
self.qtColor = color
|
||
|
self.updateTags()
|
||
|
|
||
|
def setChat(self, chatString, chatFlags):
|
||
|
if not self.chatFlags&CFSpeech:
|
||
|
# We aren't already displaying some chat. Therefore, we don't have
|
||
|
# to stomp.
|
||
|
self._setChat(chatString, chatFlags)
|
||
|
else:
|
||
|
# Stomp!
|
||
|
self.clearChat()
|
||
|
self.stompText = chatString
|
||
|
self.stompFlags = chatFlags
|
||
|
self.stompTask = taskMgr.doMethodLater(self.getStompDelay(), self.__updateStomp,
|
||
|
'ChatStomp-' + self.getUniqueId())
|
||
|
|
||
|
def _setChat(self, chatString, chatFlags):
|
||
|
if chatString:
|
||
|
self.chatPages = chatString.split('\x07')
|
||
|
self.chatFlags = chatFlags
|
||
|
else:
|
||
|
self.chatPages = []
|
||
|
self.chatFlags = 0
|
||
|
self.setPageNumber(0) # Calls updateTags() for us.
|
||
|
|
||
|
self._stopChatTimeout()
|
||
|
if chatFlags&CFTimeout:
|
||
|
self._startChatTimeout()
|
||
|
|
||
|
def __updateStomp(self, task):
|
||
|
self._setChat(self.stompText, self.stompFlags)
|
||
|
self.stompTask = None
|
||
|
|
||
|
def setContents(self, contents):
|
||
|
# This function is a little unique, it's meant to override contents on
|
||
|
# EXISTING nametags only:
|
||
|
for tag in self.nametags:
|
||
|
tag.setContents(contents)
|
||
|
|
||
|
def setObjectCode(self, objectCode):
|
||
|
self.objectCode = objectCode
|
||
|
|
||
|
def getObjectCode(self):
|
||
|
return self.objectCode
|
||
|
|
||
|
def _startChatTimeout(self):
|
||
|
length = len(self.getChat())
|
||
|
timeout = min(max(length*self.CHAT_TIMEOUT_PROP, self.CHAT_TIMEOUT_MIN), self.CHAT_TIMEOUT_MAX)
|
||
|
self.chatTimeoutTask = taskMgr.doMethodLater(timeout, self.__doChatTimeout,
|
||
|
'ChatTimeout-' + self.getUniqueId())
|
||
|
|
||
|
def __doChatTimeout(self, task):
|
||
|
self._setChat('', 0)
|
||
|
return task.done
|
||
|
|
||
|
def _stopChatTimeout(self):
|
||
|
if self.chatTimeoutTask:
|
||
|
taskMgr.remove(self.chatTimeoutTask)
|
||
|
|
||
|
def clearShadow(self):
|
||
|
pass
|
||
|
|
||
|
def clearChat(self):
|
||
|
self._setChat('', 0)
|
||
|
if self.stompTask:
|
||
|
self.stompTask.remove()
|
||
|
|
||
|
def updateNametag(self, tag):
|
||
|
tag.font = self.font
|
||
|
tag.speechFont = self.speechFont
|
||
|
tag.name = self.name
|
||
|
tag.wordWrap = self.wordWrap or DEFAULT_WORDWRAPS[self.colorCode]
|
||
|
tag.displayName = self.displayName or self.name
|
||
|
tag.qtColor = self.qtColor
|
||
|
tag.colorCode = self.colorCode
|
||
|
tag.chatString = self.getChat()
|
||
|
tag.buttons = self.getButtons()
|
||
|
tag.chatFlags = self.chatFlags
|
||
|
tag.avatar = self.avatar
|
||
|
tag.icon = self.icon
|
||
|
|
||
|
tag.update()
|
||
|
|
||
|
def __testVisible3D(self):
|
||
|
# We must determine if a 3D nametag is visible or not, since this
|
||
|
# affects the visibility state of 2D nametags.
|
||
|
|
||
|
# Next, we iterate over all of our nametags until we find a visible
|
||
|
# one:
|
||
|
for nametag in self.nametags:
|
||
|
if not isinstance(nametag, Nametag3d):
|
||
|
continue # It's not in the 3D system, disqualified.
|
||
|
|
||
|
if nametag.isOnScreen():
|
||
|
return True
|
||
|
|
||
|
# If we got here, none of the tags were a match...
|
||
|
return False
|
||
|
|
||
|
|
||
|
def __tickTask(self, task):
|
||
|
for nametag in self.nametags:
|
||
|
nametag.tick()
|
||
|
if (NametagGlobals.masterNametagsActive and self.active) or self.hasButton():
|
||
|
nametag.setClickRegionEvent(self.getUniqueId())
|
||
|
else:
|
||
|
nametag.setClickRegionEvent(None)
|
||
|
|
||
|
if NametagGlobals.onscreenChatForced and self.chatFlags & CFSpeech:
|
||
|
# Because we're *forcing* chat onscreen, we skip the visible3d test
|
||
|
# and go ahead and display it anyway.
|
||
|
visible3d = False
|
||
|
elif not NametagGlobals.masterArrowsOn and not self.chatFlags:
|
||
|
# We're forcing margins offscreen; therefore, we should pretend
|
||
|
# that the 3D nametag is always visible.
|
||
|
visible3d = True
|
||
|
else:
|
||
|
visible3d = self.__testVisible3D()
|
||
|
|
||
|
if visible3d ^ self.visible3d:
|
||
|
self.visible3d = visible3d
|
||
|
for nametag in self.nametags:
|
||
|
if isinstance(nametag, MarginPopup):
|
||
|
nametag.setVisible(not visible3d)
|
||
|
|
||
|
return task.cont
|
||
|
|
||
|
def updateTags(self):
|
||
|
for nametag in self.nametags:
|
||
|
self.updateNametag(nametag)
|
||
|
|
||
|
def addNametag(self, nametag):
|
||
|
self.nametags.append(nametag)
|
||
|
self.updateNametag(nametag)
|
||
|
if self.manager is not None and isinstance(nametag, MarginPopup):
|
||
|
nametag.manage(manager)
|
||
|
|
||
|
def removeNametag(self, nametag):
|
||
|
self.nametags.remove(nametag)
|
||
|
if self.manager is not None and isinstance(nametag, MarginPopup):
|
||
|
nametag.unmanage(manager)
|
||
|
nametag.destroy()
|
||
|
|
||
|
def manage(self, manager):
|
||
|
self.manager = manager
|
||
|
for tag in self.nametags:
|
||
|
if isinstance(tag, MarginPopup):
|
||
|
tag.manage(manager)
|
||
|
|
||
|
def unmanage(self, manager):
|
||
|
self.manager = None
|
||
|
for tag in self.nametags:
|
||
|
if isinstance(tag, MarginPopup):
|
||
|
tag.unmanage(manager)
|
||
|
tag.destroy()
|