Add Account.uses_screenreader. Added evadventure mini-map

This commit is contained in:
Griatch 2022-07-24 23:09:53 +02:00
parent 306d6b44aa
commit c95c8213a0
5 changed files with 69 additions and 32 deletions

View file

@ -178,6 +178,8 @@ Up requirements to Django 4.0+, Twisted 22+, Python 3.9 or 3.10
move being done ('teleport', 'disembark', 'give' etc). (volund)
- Made RPSystem contrib msg calls pass `pose` or `say` as msg-`type` for use in
e.g. webclient pane filtering where desired. (volund)
- Added `Account.uses_screenreader(session=None)` as a quick shortcut for
finding if a user uses a screenreader (and adjust display accordingly).
## Evennia 0.9.5

View file

@ -12,32 +12,32 @@ instead for most things).
"""
import re
import time
from random import getrandbits
from django.conf import settings
from django.contrib.auth import authenticate, password_validation
from django.core.exceptions import ImproperlyConfigured, ValidationError
from django.utils import timezone
from django.utils.module_loading import import_string
from evennia.typeclasses.models import TypeclassBase
from django.utils.translation import gettext as _
from evennia.accounts.manager import AccountManager
from evennia.accounts.models import AccountDB
from evennia.objects.models import ObjectDB
from evennia.commands.cmdsethandler import CmdSetHandler
from evennia.comms.models import ChannelDB
from evennia.objects.models import ObjectDB
from evennia.scripts.scripthandler import ScriptHandler
from evennia.server.models import ServerConfig
from evennia.server.throttle import Throttle
from evennia.utils import class_from_module, create, logger
from evennia.utils.utils import lazy_property, to_str, make_iter, is_iter, variable_from_module
from evennia.server.signals import (
SIGNAL_ACCOUNT_POST_CREATE,
SIGNAL_OBJECT_POST_PUPPET,
SIGNAL_OBJECT_POST_UNPUPPET,
)
from evennia.typeclasses.attributes import NickHandler, ModelAttributeBackend
from evennia.scripts.scripthandler import ScriptHandler
from evennia.commands.cmdsethandler import CmdSetHandler
from evennia.server.throttle import Throttle
from evennia.typeclasses.attributes import ModelAttributeBackend, NickHandler
from evennia.typeclasses.models import TypeclassBase
from evennia.utils import class_from_module, create, logger
from evennia.utils.optionhandler import OptionHandler
from django.utils.translation import gettext as _
from random import getrandbits
from evennia.utils.utils import is_iter, lazy_property, make_iter, to_str, variable_from_module
__all__ = ("DefaultAccount", "DefaultGuest")
@ -237,6 +237,22 @@ class DefaultAccount(AccountDB, metaclass=TypeclassBase):
return objs
def uses_screenreader(self, session=None):
"""
Shortcut to determine if a session uses a screenreader. If no session given,
will return true if any of the sessions use a screenreader.
Args:
session (Session, optional): The session to check for screen reader.
"""
if session:
return bool(session.protocol_flags.get("SCREENREADER", False))
else:
return any(
session.protocol_flags.get("SCREENREADER") for session in self.sessions.all()
)
def get_display_name(self, looker, **kwargs):
"""
This is used by channels and other OOC communications methods to give a

View file

@ -1,15 +1,24 @@
"""
EvAdventure rooms.
The base EvAdventure room has a modified display header that shows a little mini-map.
All EvAdventure rooms inherit from this room, and it is integral to combat as well as
the dungeon generation. But one can also mix with other non-EvAdventure rooms (you will
just not be able to fight in them).
"""
from copy import deepcopy
from evennia import AttributeProperty, DefaultCharacter, DefaultRoom, TagProperty
from evennia import DefaultCharacter, DefaultRoom
from evennia.utils.utils import inherits_from
CHAR_SYMBOL = "|w@|n"
CHAR_ALT_SYMBOL = "|w>|n"
ROOM_SYMBOL = "|bo|n"
LINK_COLOR = "|B"
_MAP_GRID = [
[" ", " ", " ", " ", " "],
[" ", " ", " ", " ", " "],
@ -18,9 +27,9 @@ _MAP_GRID = [
[" ", " ", " ", " ", " "],
]
_EXIT_GRID_SHIFT = {
"north": (0, 1, "|"),
"north": (0, 1, "||"),
"east": (1, 0, "-"),
"south": (0, -1, "|"),
"south": (0, -1, "||"),
"west": (-1, 0, "-"),
"northeast": (1, 1, "/"),
"southeast": (1, -1, "\\"),
@ -46,24 +55,28 @@ class EvAdventureRoom(DefaultRoom):
def get_display_header(self, looker, **kwargs):
"""
Display the current location as a mini-map.
"""
if not inherits_from(looker, DefaultCharacter):
# we don't need a map for npcs/mobs
# make sure to not show make a map for users of screenreaders.
# for optimization we also don't show it to npcs/mobs
if not inherits_from(looker, DefaultCharacter) or (
looker.account and looker.account.uses_screenreader()
):
return ""
# build a map
map_grid = deepcopy(_MAP_GRID)
dx0, dy0 = 2, 2
map_grid[dy0][dx0] = "|w@|n"
map_grid[dy0][dx0] = CHAR_SYMBOL
for exi in self.exits:
dx, dy, symbol = _EXIT_GRID_SHIFT.get(exi.key, (None, None, None))
if symbol is None:
# we have a non-cardinal direction to go to - mark us blue to indicate this
map_grid[dy0][dx0] = "|b>|n"
# we have a non-cardinal direction to go to - indicate this
map_grid[dy0][dx0] = CHAR_ALT_SYMBOL
continue
map_grid[dy0 + dy][dx0 + dx] = symbol
map_grid[dy0 + dy][dx0 + dx] = f"{LINK_COLOR}{symbol}|n"
if exi.destination != self:
map_grid[dy0 + dy + dy][dx0 + dx + dx] = "X"
map_grid[dy0 + dy + dy][dx0 + dx + dx] = ROOM_SYMBOL
# Note that on the grid, dy is really going *downwards* (origo is
# in the top left), so we need to reverse the order at the end to mirror it

View file

@ -4,10 +4,17 @@ Helpers for testing evadventure modules.
"""
from evennia.utils import create
from ..characters import EvAdventureCharacter
from ..objects import EvAdventureObject
from ..rooms import EvAdventureRoom
from .. import enums
from ..characters import EvAdventureCharacter
from ..objects import (
EvAdventureArmor,
EvAdventureHelmet,
EvAdventureObject,
EvAdventureShield,
EvAdventureWeapon,
)
from ..rooms import EvAdventureRoom
class EvAdventureMixin:
@ -23,27 +30,27 @@ class EvAdventureMixin:
EvAdventureCharacter, key="testchar", location=self.location
)
self.helmet = create.create_object(
EvAdventureObject,
EvAdventureHelmet,
key="helmet",
attributes=[("inventory_use_slot", enums.WieldLocation.HEAD), ("armor", 1)],
)
self.shield = create.create_object(
EvAdventureObject,
EvAdventureShield,
key="shield",
attributes=[("inventory_use_slot", enums.WieldLocation.SHIELD_HAND), ("armor", 1)],
)
self.armor = create.create_object(
EvAdventureObject,
EvAdventureArmor,
key="armor",
attributes=[("inventory_use_slot", enums.WieldLocation.BODY), ("armor", 11)],
)
self.weapon = create.create_object(
EvAdventureObject,
EvAdventureWeapon,
key="weapon",
attributes=[("inventory_use_slot", enums.WieldLocation.WEAPON_HAND)],
)
self.big_weapon = create.create_object(
EvAdventureObject,
EvAdventureWeapon,
key="big_weapon",
attributes=[("inventory_use_slot", enums.WieldLocation.TWO_HANDS)],
)

View file

@ -10,7 +10,6 @@ from evennia.utils.test_resources import BaseEvenniaTest
from evennia.utils.utils import inherits_from
from .. import dungeon
from ..rooms import EvAdventureDungeonRoom
from .mixins import EvAdventureMixin
@ -33,7 +32,7 @@ class TestDungeon(EvAdventureMixin, BaseEvenniaTest):
self.start_room = create_object(droomclass, key="bottom of well")
self.assertEqual(
self.start_room.scripts.get("evadventure_startroom_resetter")[0].interval, -1
self.start_room.scripts.get("evadventure_dungeon_startroom_resetter")[0].interval, -1
)
self.start_north = create_object(
dungeon.EvAdventureDungeonStartRoomExit,
@ -71,7 +70,7 @@ class TestDungeon(EvAdventureMixin, BaseEvenniaTest):
# first go north, this should generate a new room
new_room_north = self._move_character("north")
self.assertNotEqual(self.start_room, new_room_north)
self.assertTrue(inherits_from(new_room_north, EvAdventureDungeonRoom))
self.assertTrue(inherits_from(new_room_north, dungeon.EvAdventureDungeonRoom))
# check if Orchestrator was created
orchestrator = new_room_north.db.dungeon_orchestrator