def share_code(ev): src = editor.getValue() if len(src) > 2048: d = dialog.InfoDialog("Copy url", f"code length is {len(src)}, must be < 2048", style={"zIndex": 10}, ok=True) else: href = window.location.href.rsplit("?", 1)[0] query = doc.query query["code"] = src url = f"{href}{query}" url = url.replace("(", "%28").replace(")", "%29") d = dialog.Dialog("Copy url") area = html.TEXTAREA(rows=0, cols=0) d.panel <= area area.value = url # copy to clipboard area.focus() area.select() doc.execCommand("copy") d.remove() d = dialog.Dialog("Copy url") d.panel <= html.DIV("url copied in the clipboard<br>Send it to share the code") buttons = html.DIV() ok = html.BUTTON("Ok") buttons <= html.DIV(ok, style={"text-align": "center"}) d.panel <= html.BR() + buttons @bind(ok, "click") def click(evt): d.remove()
def deleteSheetRequest(event): sheet = event.target["id"].split('`')[1] box = dialog.Dialog("Confirm Deletion", ok_cancel=("Delete", "Cancel")) box.panel <= html.P( "Are you sure you want to delete sheet \"" \ + sheet + "\"? (The file will remain on disk, " \ + "but will be inaccessible)" ) def delete(clickEvent): box.close() ajaxPostJSON( "/user/", {"method": "delete", "sheetName": sheet}, lambda r : sheetReplyGeneric(r, { "noErrorTitle": "Deleted", "noErrorBody": "Sheet \"{0[0]}\" has been deleted.\n" \ + "A backup copy will remain in the server's recycle bin, " \ + "just in case.", "errorTitle": "Deletion Error" }, [ "sheetName" ]) ) box.ok_button.bind("click", delete)
def classEdit() -> dialog.Dialog: d = dialog.Dialog("Class(es)", ok_cancel = True, default_css = False) def toggleLevels(event): if event.target.checked: del d.select("#levelList")[0].attrs["readonly"] else: d.select("#levelList")[0].attrs["readonly"] = '' d.panel <= html.P("Enter one or more classes and corresponding hit dice, separating multiple entries by a comma (,).") d.panel <= html.LABEL("Class List:", For = "classList") d.panel <= html.INPUT(id = "classList") d.panel <= html.P("For the hit dice, write each entry as the number of sides of the associated die (ex. \"6\" for a d6).") d.panel <= html.LABEL("Dice List:", For = "diceList") d.panel <= html.INPUT(id = "diceList") d.panel <= html.P("If you need to edit class levels, enter them here like the dice.") d.panel <= html.LABEL("Edit Level(s)?", For = "levelsCheck") levelsCheck = html.INPUT(id = "levelsCheck", type = "checkbox") levelsCheck.bind("change", toggleLevels) d.panel <= levelsCheck d.panel <= html.BR() d.panel <= html.LABEL("Level List:", For = "levelList") d.panel <= html.INPUT(id = "levelList", readonly = '') return d
def featureEdit(feature: str) -> dialog.Dialog: d = dialog.Dialog(feature, ok_cancel=True, default_css=False) def toggleNumeric(event): if event.target.checked: del d.select("#value")[0].attrs["readonly"] del d.select("#abilityModCheck")[0].attrs["disabled"] else: d.select("#value")[0].attrs["readonly"] = '' d.select("#abilityModCheck")[0].attrs["disabled"] = '' d.select("#abilityModCheck")[0].checked = False d.select("#abilityModCheck")[0].dispatchEvent( window.Event.new("change")) def toggleAbility(event): for a in abilities: if event.target.checked: del d.select('#' + a + "RB")[0].attrs["disabled"] else: d.select('#' + a + "RB")[0].attrs["disabled"] = '' if True not in [ r.checked for r in d.select("input[name=\"ability\"]") ]: d.select("#strengthRB")[0].checked = True d.panel <= html.LABEL("Feature Name:", For="name") d.panel <= html.INPUT(id="name", Class="dialogName") d.panel <= html.BR() d.panel <= html.LABEL("Feature Description:", For="desc") d.panel <= html.INPUT(id="description") d.panel <= html.BR() d.panel <= html.LABEL("Is Numeric?", For="numericCheck") numericCheck = html.INPUT(id="numericCheck", type="checkbox") numericCheck.bind("change", toggleNumeric) d.panel <= numericCheck d.panel <= html.LABEL("Modifies Ability Score?", For="abilityModCheck") abilityModCheck = html.INPUT(id="abilityModCheck", type="checkbox", disabled='') abilityModCheck.bind("change", toggleAbility) d.panel <= abilityModCheck d.panel <= html.BR() d.panel <= html.LABEL("Feature Value:", For="value") d.panel <= html.INPUT(id="value", Type="number", readonly='') d.panel <= html.BR() for a in abilities: d.panel <= html.INPUT(id=a + "RB", name="ability", value=a[:3], type="radio", disabled='') d.panel <= html.LABEL(a.capitalize(), For=a + "RB") d.panel <= html.BR() return d
def listEntryDelete(item : str, itemType : str) -> dialog.Dialog: d = dialog.Dialog("Confirm Deletion", ok_cancel = ("Yes", "No"), default_css = False) d.panel <= html.B( "Are you sure you want to delete the \"" + item + "\" " + itemType + "?" ) return d
def levelSet() -> dialog.Dialog: d = dialog.Dialog("Set Character Level", ok_cancel = True, default_css = False) d.panel <= html.LABEL("Enter your new Character Level (1 -> 20):", For = "newCharLevel") d.panel <= html.INPUT(id = "newCharLevel", type = "number", min = 1, max = 20) d.panel <= html.BR() d.panel <= html.B( "Please note that changing your level will set your experience to the minimum required to match." ) return d
def spellTableSetMaxLevel(className : str, currentMaxLevel : int) -> dialog.Dialog: d = dialog.Dialog( "Maximum " + className + " Spell Level", ok_cancel = True, default_css = False ) d.panel <= html.P("Enter a new maximum spell level (1 to 9 inclusive):") d.panel <= html.INPUT( id = "newMaxSpellLevel", type = "number", min = 1, max = 9, value = currentMaxLevel ) return d
def spellTableCreate() -> dialog.Dialog: d = dialog.Dialog("Create Spell Table", ok_cancel = True, default_css = False) d.panel <= html.P("Select an ability to be the source of magical power:") for a in ("intelligence", "wisdom", "charisma"): d.panel <= html.INPUT( id = a + "`spellTableAbilityRadio", name = "ability", value = a, type = "radio" ) d.panel <= html.LABEL(a.capitalize(), For = a + "`spellTableAbilityRadio") d.panel <= html.BR() d.panel <= html.P("Select a class that does not yet have a spell table:") return d
def skillEdit(skill: str) -> dialog.Dialog: d = dialog.Dialog(skill, ok_cancel=True, default_css=False) d.panel <= html.LABEL("Skill Name:", For="name") d.panel <= html.INPUT(id="name", Class="dialogName") d.panel <= html.BR() for a in abilities: d.panel <= html.INPUT( id=a + "RB", name="ability", value=a[:3], type="radio") d.panel <= html.LABEL(a.capitalize(), For=a + "RB") d.panel <= html.BR() return d
def cursor_success(evt): infos['nb_modules'] += 1 cursor = evt.target.result if cursor: record = cursor.value timestamp = datetime.fromtimestamp(record.timestamp / 1000) source_ts = datetime.fromtimestamp(record.source_ts / 1000) table <= TR( TD(record.name) + TD(bool(record.is_package)) + TD(len(record.content), align="right") + TD(timestamp.strftime('%Y-%m-%d %H:%M')) + TD(source_ts.strftime('%Y-%m-%d %H:%M'))) infos['size'] += len(record.content) getattr(cursor, "continue")() else: panel = dialog.Dialog('indexedDB cache', top=0, left=0).panel panel <= H1("Brython indexedDB cache") size = '{:,d}'.format(infos['size']) panel <= H3(f"{infos['nb_modules']} modules, size {size} bytes") panel <= table
def experienceAdjust(method) -> dialog.Dialog: if method == "Edit": titleString = "Set Experience" labelString = "New Total Experience:" elif method == "Add": titleString = "Add Experience" labelString = "Amount of Experience to add:" d = dialog.Dialog(titleString, ok_cancel = True, default_css = False) d.panel <= html.LABEL(labelString, For = "xpAmount") d.panel <= html.INPUT(id = "xpAmount", type = "number", min = 0) if method == "Edit": d.panel <= html.BR() d.panel <= html.B( "Please note that changing your experience will set your character level to match." ) return d
def wheightEdit(heightData, weightData) -> dialog.Dialog: d = dialog.Dialog("Edit Weight/Height", ok_cancel=True, default_css=False) def setMeasure(event): for r in d.select("input[name=\"measure\"]"): if r.checked: measure = r.value break if measure == "height": dataDict = heightData else: dataDict = weightData d.select("#measure")[0].value = dataDict["measure"] d.select("#unit")[0].value = dataDict["unit"] heightRadio = html.INPUT(id="editHeight", type="radio", name="measure", value="height") heightRadio.bind("change", setMeasure) d.panel <= heightRadio d.panel <= html.LABEL("Height", For="editHeight") weightRadio = html.INPUT(id="editWeight", type="radio", name="measure", value="weight") weightRadio.bind("change", setMeasure) d.panel <= weightRadio d.panel <= html.LABEL("Weight", For="editWeight") d.panel <= html.BR() d.panel <= html.LABEL("Measure:", For="measure") d.panel <= html.INPUT(id="measure", type="number", min=0, step=0.01) d.panel <= html.BR() d.panel <= html.LABEL("Unit:", For="unit") d.panel <= html.INPUT(id="unit") return d
def spellEdit(spell : str) -> dialog.Dialog: def toggleDamage(event): for i in d.select(".damage"): if event.target.checked: del i.attrs["readonly"] else: i.attrs["readonly"] = '' d = dialog.Dialog(spell, ok_cancel = True, default_css = False) d.panel <= html.LABEL("Spell Name:", For = "name") d.panel <= html.INPUT(id = "name", Class = "dialogName") d.panel <= html.BR() d.panel <= html.LABEL("Spell Description:", For = "description") d.panel <= html.INPUT(id = "description") d.panel <= html.BR() d.panel <= html.LABEL("Spell Level:", For = "level") d.panel <= html.INPUT(id = "level", type = "number", min = 0, max = 9, value = 0) d.panel <= html.LABEL("Spell School:", For = "school") spellSchool = html.SELECT(id = "school", name = "school") for school in ( "abjuration", "conjuration", "divination", "enchantment", "evocation", "illusion", "necromancy", "transmutation" ): spellSchool <= html.OPTION(school.capitalize(), value = school) d.panel <= spellSchool d.panel <= html.BR() d.panel <= html.LABEL("Spell Range (Measure, Unit):", For = "rangeMeasure") d.panel <= html.INPUT(id = "rangeMeasure", type = "number", min = 0, value = 0) rangeUnit = html.SELECT(id = "rangeUnit", name = "rangeUnit") for unit in ("feet", "touch", "self"): rangeUnit <= html.OPTION(unit.capitalize(), value = unit) d.panel <= rangeUnit d.panel <= html.BR() d.panel <= html.P( "For touch and non-AoE self ranges, leave the Measure field at 0." ) d.panel <= html.BR() d.panel <= html.LABEL("Spell Casting Time (Measure, Unit):", For = "castingMeasure") d.panel <= html.INPUT(id = "castingMeasure", type = "number", min = 1, value = 1) castingUnit = html.SELECT(id = "castingUnit", name = "castingUnit") for unit in ("bonus Action", "action", "minutes", "hours"): castingUnit <= html.OPTION(unit.capitalize(), value = unit) d.panel <= castingUnit d.panel <= html.BR() d.panel <= html.LABEL("Spell Duration (Measure, Unit):", For = "durationMeasure") d.panel <= html.INPUT(id = "durationMeasure", type = "number", min = 0, value = 0) durationUnit = html.SELECT(id = "durationUnit", name = "durationUnit") for unit in ( "days", "hours", "minutes", "rounds", "days, Concentration", "hours, Concentration", "minutes, Concentration", "rounds, Concentration", "instantaneous", "until Dispelled", "special" ): durationUnit <= html.OPTION(unit.capitalize(), value = unit) d.panel <= durationUnit d.panel <= html.BR() d.panel <= html.P( "For instantaneous, until dispelled, or special durations, leave the Measure field at 0." ) d.panel <= html.BR() d.panel <= html.LABEL("Does Damage?", For = "damageCheckbox") damageCheckbox = html.INPUT(id = "damageCheckbox", type = "checkbox") damageCheckbox.bind("change", toggleDamage) d.panel <= damageCheckbox d.panel <= html.BR() d.panel <= html.LABEL("Damage Dice Count:", For = "damageCount") d.panel <= html.INPUT( id = "damageCount", Class = "damage", type = "number", min = 1, value = 1, readonly = '' ) d.panel <= html.LABEL("Damage Dice Value:", For = "damageDie") d.panel <= html.INPUT( id = "damageDie", Class = "damage", type = "number", min = 4, value = 4, readonly = '' ) d.panel <= html.BR() d.panel <= html.LABEL("Damage Type:", For = "damageType") d.panel <= html.INPUT(id = "damageType", Class = "damage", readonly = '') return d
def itemEdit(item : str) -> dialog.Dialog: d = dialog.Dialog(item, ok_cancel = True, default_css = False) def toggleWeapon(event): for i in d.select(".weapon"): if i.type == "radio" or i.type == "checkbox": if event.target.checked: del i.attrs["disabled"] else: i.attrs["disabled"] = '' elif i.type == "number": if event.target.checked: del i.attrs["readonly"] else: i.attrs["readonly"] = '' d.panel <= html.LABEL("Item Name:", For = "name") d.panel <= html.INPUT(id = "name", Class = "dialogName") d.panel <= html.BR() d.panel <= html.LABEL("Item Description:", For = "desc") d.panel <= html.INPUT(id = "description") d.panel <= html.BR() d.panel <= html.LABEL("Item Count:", For = "count") d.panel <= html.INPUT(id = "count", type = "number", min = 0) d.panel <= html.LABEL("Item Weight:", For = "weight") d.panel <= html.INPUT(id = "weight", type = "number", min = 0, step = 0.01) d.panel <= html.BR() d.panel <= html.P("Value") d.panel <= html.LABEL("Gold:", For = "gold") d.panel <= html.INPUT(id = "gold", type = "number", min = 0) d.panel <= html.LABEL("Silver:", For = "silver") d.panel <= html.INPUT(id = "silver", type = "number", min = 0, max = 10) d.panel <= html.LABEL("Copper:", For = "copper") d.panel <= html.INPUT(id = "copper", type = "number", min = 0, max = 10) d.panel <= html.BR() weaponTitleTag = html.P("Weapon") weaponCheck = html.INPUT(id = "weaponCheck", type = "checkbox") weaponCheck.bind("change", toggleWeapon) weaponTitleTag <= weaponCheck weaponTitleTag <= html.LABEL("Is Weapon?", For = "weaponCheck") d.panel <= weaponTitleTag d.panel <= html.P("Kind") d.panel <= html.INPUT( id = "weaponTypeSM", Class = "weapon", type = "radio", name = "kind", value = "simpleMelee", disabled = '' ) d.panel <= html.LABEL("Simple Melee", For = "weaponTypeSM") d.panel <= html.INPUT( id = "weaponTypeSR", Class = "weapon", type = "radio", name = "kind", value = "simpleRanged", disabled = '' ) d.panel <= html.LABEL("Simple Ranged", For = "weaponTypeSR") d.panel <= html.INPUT( id = "weaponTypeMM", Class = "weapon", type = "radio", name = "kind", value = "martialMelee", disabled = '' ) d.panel <= html.LABEL("Martial Melee", For = "weaponTypeMM") d.panel <= html.INPUT( id = "weaponTypeMR", Class = "weapon", type = "radio", name = "kind", value = "martialRanged", disabled = '' ) d.panel <= html.LABEL("Martial Ranged", For = "weaponTypeMR") d.panel <= html.BR() d.panel <= html.P("Damage Type") d.panel <= html.INPUT( id = "damageTypeB", Class = "weapon", type = "radio", name = "type", value = "bludgeoning", disabled = '' ) d.panel <= html.LABEL("Bludgeoning", For = "damageTypeB") d.panel <= html.INPUT( id = "damageTypeP", Class = "weapon", type = "radio", name = "type", value = "piercing", disabled = '' ) d.panel <= html.LABEL("Piercing", For = "damageTypeP") d.panel <= html.INPUT( id = "damageTypeS", Class = "weapon", type = "radio", name = "type", value = "slashing", disabled = '' ) d.panel <= html.LABEL("Slashing", For = "damageTypeS") d.panel <= html.BR() d.panel <= html.INPUT( id = "isProficient", Class = "weapon", type = "checkbox", disabled = '' ) d.panel <= html.LABEL("Proficient?", For = "isProficient") d.panel <= html.INPUT( id = "bonusFromSTR", Class = "weapon", type = "radio", name = "ability", value = "str", disabled = '' ) d.panel <= html.LABEL("Strength (Melee*)", For = "bonusFromSTR") d.panel <= html.INPUT( id = "bonusFromDEX", Class = "weapon", type = "radio", name = "ability", value = "dex", disabled = '' ) d.panel <= html.LABEL("Dexterity (Ranged*)", For = "bonusFromDEX") d.panel <= html.BR() d.panel <= html.P("* Finesse weapons can derive from either ability per player choice") d.panel <= html.P("Damage Values") d.panel <= html.LABEL("Damage Dice Count:", For = "dmgCount") d.panel <= html.INPUT( id = "dmgCount", Class = "weapon", type = "number", min = 0, readonly = '' ) d.panel <= html.LABEL("Damage Dice Value:", For = "dmgDie") d.panel <= html.INPUT( id = "dmgDie", Class = "weapon", type = "number", min = 0, readonly = '' ) d.panel <= html.BR() d.panel <= html.LABEL("Damage Bonus:", For = "dmgBonus") d.panel <= html.INPUT( id = "dmgBonus", Class = "weapon", type = "number", min = 0, readonly = '' ) return d