"""DuckieDai Momentum for TI-84 Plus CE Python."""


def duckiedai_intro(program_name, wait=True):
    """Show the reusable DuckieDai program opening."""
    title = program_name[:16]
    empty = 16 - len(title)
    left = empty // 2
    right = empty - left

    print("+----------------------+")
    print("|   " + " " * left + title + " " * right + "   |")
    print("|                      |")
    print("|       __             |")
    print("|   ___(o )>  quack!   |")
    print("|   \\ <_. )           |")
    print("|    `---'             |")
    print("|     by DuckieDai     |")
    print("+----------------------+")
    print("Loading...")

    if wait:
        input("Press enter to start ")
        print("\n" * 6)


def number(prompt):
    """Allow positive, negative, or zero values."""
    while True:
        try:
            value = float(input(prompt))

            if value > -1e100 and value < 1e100:
                return value

        except ValueError:
            pass

        print("Enter a valid number.")


def positive_number(prompt):
    """Require a value greater than zero."""
    while True:
        try:
            value = float(input(prompt))

            if value > 0 and value < 1e100:
                return value

        except ValueError:
            pass

        print("Enter a number above 0.")


def show_answer(name, value, unit):
    input("Press enter for answer ")
    print("\n" * 6)
    print("ANSWER")
    print(name + " = " + str(value))
    print(unit)


def basic_momentum():
    print("BASIC MOMENTUM")
    print()
    print("p = m*v")
    print()
    print("1. Solve momentum")
    print("2. Solve mass")
    print("3. Solve velocity")
    print()

    choice = input("Choose 1-3: ")
    print()

    # -------------------------
    # Momentum
    # -------------------------

    if choice == "1":

        mass = positive_number("Mass (kg): ")
        velocity = number("Velocity (m/s): ")

        momentum = mass * velocity

        print()
        print("Using:")
        print("p = m*v")

        show_answer(
            "p",
            momentum,
            "kg*m/s"
        )

    # -------------------------
    # Mass
    # -------------------------

    elif choice == "2":

        momentum = number("Momentum: ")
        velocity = number("Velocity (m/s): ")

        if velocity == 0:
            print()
            print("Cannot divide by")
            print("zero velocity.")

        else:
            mass = momentum / velocity

            print()
            print("Using:")
            print("p = m*v")
            print()
            print("Rearranged:")
            print("m = p/v")

            show_answer(
                "m",
                mass,
                "kg"
            )

    # -------------------------
    # Velocity
    # -------------------------

    elif choice == "3":

        momentum = number("Momentum: ")
        mass = positive_number("Mass (kg): ")

        velocity = momentum / mass

        print()
        print("Using:")
        print("p = m*v")
        print()
        print("Rearranged:")
        print("v = p/m")

        show_answer(
            "v",
            velocity,
            "m/s"
        )

    else:
        print("Invalid choice.")


def collision_solver():
    print("2-OBJECT COLLISION")
    print()
    print("Momentum before")
    print("= momentum after")
    print()
    print("m1*v1i + m2*v2i")
    print("=")
    print("m1*v1f + m2*v2f")
    print()
    print("Direction matters!")
    print("+ right / - left")
    input("Press enter for menu ")
    print("\n" * 6)
    print()
    print("Which is unknown?")
    print()
    print("1. Object 1 final v")
    print("2. Object 2 final v")
    print()

    choice = input("Choose 1 or 2: ")
    print()

    m1 = positive_number("Mass 1 (kg): ")
    m2 = positive_number("Mass 2 (kg): ")

    v1i = number("Initial v1: ")
    v2i = number("Initial v2: ")

    print()

    # ===================================
    # Solve v1 final
    # ===================================

    if choice == "1":

        v2f = number("Final v2: ")

        initial_p = (
            m1 * v1i +
            m2 * v2i
        )

        v1f = (
            initial_p -
            m2 * v2f
        ) / m1

        print()
        print("Using conservation:")
        print("Pi = Pf")
        print()
        print("m1*v1i + m2*v2i")
        print("= m1*v1f + m2*v2f")
        print()
        print("Rearranged:")
        print("v1f =")
        print("(Pi-m2*v2f)/m1")

        show_answer(
            "v1 final",
            v1f,
            "m/s"
        )

    # ===================================
    # Solve v2 final
    # ===================================

    elif choice == "2":

        v1f = number("Final v1: ")

        initial_p = (
            m1 * v1i +
            m2 * v2i
        )

        v2f = (
            initial_p -
            m1 * v1f
        ) / m2

        print()
        print("Using conservation:")
        print("Pi = Pf")
        print()
        print("m1*v1i + m2*v2i")
        print("= m1*v1f + m2*v2f")
        print()
        print("Rearranged:")
        print("v2f =")
        print("(Pi-m1*v1f)/m2")

        show_answer(
            "v2 final",
            v2f,
            "m/s"
        )

    else:
        print("Invalid choice.")


def stick_together():
    print("STICK TOGETHER")
    print("COLLISION")
    print()
    print("Objects share one")
    print("final velocity.")
    print()
    print("+ right / - left")
    print()

    m1 = positive_number("Mass 1 (kg): ")
    v1 = number("Velocity 1: ")

    m2 = positive_number("Mass 2 (kg): ")
    v2 = number("Velocity 2: ")

    final_v = (
        m1 * v1 +
        m2 * v2
    ) / (m1 + m2)

    print()
    print("Using:")
    print("m1*v1 + m2*v2")
    print("=")
    print("(m1+m2)*vf")
    print()
    print("Rearranged:")
    print("vf =")
    print("(m1*v1+m2*v2)")
    print("/(m1+m2)")

    show_answer(
        "Final velocity",
        final_v,
        "m/s"
    )


def main():
    duckiedai_intro("MOMENTUM")

    print("MOMENTUM TOOLKIT")
    print()
    print("1. Basic momentum")
    print("2. Collision solver")
    print("3. Stick together")
    print()

    choice = input("Choose 1-3: ")

    print()

    if choice == "1":
        basic_momentum()

    elif choice == "2":
        collision_solver()

    elif choice == "3":
        stick_together()

    else:
        print("Invalid choice.")

    print()
    print("DuckieDai says: done!")


# TI-Python imports the selected AppVar rather than
# setting __name__ to main.
main()
