示例#1
0
        static int obj_desc_inscrip(Object o_ptr, ref string buf, int max, int end)
        {
            string[] u = { "", "", "", "" };
            int      n = 0;

            Object.obj_pseudo_t feel        = o_ptr.pseudo();
            Bitflag             flags_known = new Bitflag(Object_Flag.SIZE);
            Bitflag             f2          = new Bitflag(Object_Flag.SIZE);

            o_ptr.object_flags_known(ref flags_known);

            /* Get inscription */
            if (o_ptr.note != null && o_ptr.note.value != null)
            {
                u[n++] = o_ptr.note.ToString();
            }

            /* Use special inscription, if any */
            if (!o_ptr.is_known() && feel != 0)
            {
                /* cannot tell excellent vs strange vs splendid until wield */
                if (!o_ptr.was_worn() && o_ptr.ego != null)
                {
                    u[n++] = "ego";
                }
                else
                {
                    u[n++] = Misc.inscrip_text[(int)feel];             //I know that feel bro.
                }
            }
            else if (((o_ptr.ident & Object.IDENT_EMPTY) != 0) && !o_ptr.is_known())
            {
                u[n++] = "empty";
            }
            else if (!o_ptr.is_known() && o_ptr.was_worn())
            {
                if (o_ptr.wield_slot() == Misc.INVEN_WIELD || o_ptr.wield_slot() == Misc.INVEN_BOW)
                {
                    u[n++] = "wielded";
                }
                else
                {
                    u[n++] = "worn";
                }
            }
            else if (!o_ptr.is_known() && o_ptr.was_fired())
            {
                u[n++] = "fired";
            }
            else if (!o_ptr.flavor_is_aware() && o_ptr.flavor_was_tried())
            {
                u[n++] = "tried";
            }

            /* Note curses */
            Object_Flag.create_mask(f2, false, Object_Flag.object_flag_type.CURSE);
            if (flags_known.is_inter(f2))
            {
                u[n++] = "cursed";
            }

            /* Note squelch */
            if (Squelch.item_ok(o_ptr))
            {
                u[n++] = "squelch";
            }

            if (n != 0)
            {
                int i;
                for (i = 0; i < n; i++)
                {
                    if (i == 0)
                    {
                        buf = buf + " {";
                    }
                    buf = buf + u[i];
                    if (i < n - 1)
                    {
                        buf += ", ";
                    }
                }

                buf += "}";
            }

            return(end);
        }
示例#2
0
        /**
         * Describes item `o_ptr` into buffer `buf` of size `max`.
         *
         * ODESC_PREFIX prepends a 'the', 'a' or number
         * ODESC_BASE results in a base description.
         * ODESC_COMBAT will add to-hit, to-dam and AC info.
         * ODESC_EXTRA will add pval/charge/inscription/squelch info.
         * ODESC_PLURAL will pluralise regardless of the number in the stack.
         * ODESC_STORE turns off squelch markers, for in-store display.
         * ODESC_SPOIL treats the object as fully identified.
         *
         * Setting 'prefix' to true prepends a 'the', 'a' or the number in the stack,
         * respectively.
         *
         * \returns The number of bytes used of the buffer.
         */
        public string object_desc(Detail mode)
        {
            bool prefix = (int)(mode & Detail.PREFIX) != 0;
            bool spoil  = (int)(mode & Detail.SPOIL) != 0;

            int end = 0, i = 0;

            /* Simple description for null item */
            if (tval == 0)
            {
                return("(nothing)");
            }

            bool known = is_known() || (ident & Object.IDENT_STORE) != 0 || spoil;

            /* We've seen it at least once now we're aware of it */
            if (known && ego != null && !spoil)
            {
                ego.everseen = true;
            }


            /*** Some things get really simple descriptions ***/

            if (tval == TVal.TV_GOLD)
            {
                return(pval[Misc.DEFAULT_PVAL] + " gold pieces worth of " + kind.Name + (Squelch.item_ok(this) ? " {squelch}" : ""));
            }

            /** Construct the name **/

            /* Copy the base name to the buffer */
            string buf = "";

            end = obj_desc_name(ref buf, 80, end, this, prefix, mode, spoil);

            if ((mode & Detail.COMBAT) != 0)
            {
                if (tval == TVal.TV_CHEST)
                {
                    end = obj_desc_chest(this, ref buf, 80, end);
                }
                else if (tval == TVal.TV_LIGHT)
                {
                    end = obj_desc_light(this, ref buf, 80, end);
                }

                end = obj_desc_combat(this, ref buf, 80, end, spoil);
            }

            if ((mode & Detail.EXTRA) != 0)
            {
                for (i = 0; i < num_pvals; i++)
                {
                    if (spoil || this_pval_is_visible(i))
                    {
                        end = obj_desc_pval(this, buf, 80, end, spoil);
                        break;
                    }
                }

                end = obj_desc_charges(this, ref buf, 80, end);

                if ((mode & Detail.STORE) != 0)
                {
                    end = obj_desc_aware(this, ref buf, 80, end);
                }
                else
                {
                    end = obj_desc_inscrip(this, ref buf, 80, end);
                }
            }

            return(buf);
        }
示例#3
0
        /*
         * This function updates the monster record of the given monster
         *
         * This involves extracting the distance to the player (if requested),
         * and then checking for visibility (natural, infravision, see-invis,
         * telepathy), updating the monster visibility flag, redrawing (or
         * erasing) the monster when its visibility changes, and taking note
         * of any interesting monster flags (cold-blooded, invisible, etc).
         *
         * Note the new "mflag" field which encodes several monster state flags,
         * including "view" for when the monster is currently in line of sight,
         * and "mark" for when the monster is currently visible via detection.
         *
         * The only monster fields that are changed here are "cdis" (the
         * distance from the player), "ml" (visible to the player), and
         * "mflag" (to maintain the "MFLAG_VIEW" flag).
         *
         * Note the special "update_monsters()" function which can be used to
         * call this function once for every monster.
         *
         * Note the "full" flag which requests that the "cdis" field be updated,
         * this is only needed when the monster (or the player) has moved.
         *
         * Every time a monster moves, we must call this function for that
         * monster, and update the distance, and the visibility.  Every time
         * the player moves, we must call this function for every monster, and
         * update the distance, and the visibility.  Whenever the player "state"
         * changes in certain ways ("blindness", "infravision", "telepathy",
         * and "see invisible"), we must call this function for every monster,
         * and update the visibility.
         *
         * Routines that change the "illumination" of a grid must also call this
         * function for any monster in that grid, since the "visibility" of some
         * monsters may be based on the illumination of their grid.
         *
         * Note that this function is called once per monster every time the
         * player moves.  When the player is running, this function is one
         * of the primary bottlenecks, along with "update_view()" and the
         * "process_monsters()" code, so efficiency is important.
         *
         * Note the optimized "inline" version of the "distance()" function.
         *
         * A monster is "visible" to the player if (1) it has been detected
         * by the player, (2) it is close to the player and the player has
         * telepathy, or (3) it is close to the player, and in line of sight
         * of the player, and it is "illuminated" by some combination of
         * infravision, torch light, or permanent light (invisible monsters
         * are only affected by "light" if the player can see invisible).
         *
         * Monsters which are not on the current panel may be "visible" to
         * the player, and their descriptions will include an "offscreen"
         * reference.  Currently, offscreen monsters cannot be targeted
         * or viewed directly, but old targets will remain set.  XXX XXX
         *
         * The player can choose to be disturbed by several things, including
         * "OPT(disturb_move)" (monster which is viewable moves in some way), and
         * "OPT(disturb_near)" (monster which is "easily" viewable moves in some
         * way).  Note that "moves" includes "appears" and "disappears".
         */
        public static void update_mon(int m_idx, bool full)
        {
            Monster m_ptr = Cave.cave_monster(Cave.cave, m_idx);

            Monster_Race r_ptr = Misc.r_info[m_ptr.r_idx];

            Monster_Lore l_ptr = Misc.l_list[m_ptr.r_idx];

            if (l_ptr == null)
            {
                l_ptr = Misc.l_list[m_ptr.r_idx] = new Monster_Lore();
            }

            int d;

            /* Current location */
            int fy = m_ptr.fy;
            int fx = m_ptr.fx;

            /* Seen at all */
            bool flag = false;

            /* Seen by vision */
            bool easy = false;


            /* Compute distance */
            if (full)
            {
                int py = Misc.p_ptr.py;
                int px = Misc.p_ptr.px;

                /* Distance components */
                int dy = (py > fy) ? (py - fy) : (fy - py);
                int dx = (px > fx) ? (px - fx) : (fx - px);

                /* Approximate distance */
                d = (dy > dx) ? (dy + (dx >> 1)) : (dx + (dy >> 1));

                /* Restrict distance */
                if (d > 255)
                {
                    d = 255;
                }

                /* Save the distance */
                m_ptr.cdis = (byte)d;
            }

            /* Extract distance */
            else
            {
                /* Extract the distance */
                d = m_ptr.cdis;
            }


            /* Detected */
            if ((m_ptr.mflag & (Monster_Flag.MFLAG_MARK)) != 0)
            {
                flag = true;
            }


            /* Nearby */
            if (d <= Misc.MAX_SIGHT)
            {
                /* Basic telepathy */
                if (Misc.p_ptr.check_state(Object_Flag.TELEPATHY, Misc.p_ptr.state.flags))
                {
                    /* Empty mind, no telepathy */
                    if (r_ptr.flags.has(Monster_Flag.EMPTY_MIND.value))
                    {
                        /* Nothing! */
                    }

                    /* Weird mind, occasional telepathy */
                    else if (r_ptr.flags.has(Monster_Flag.WEIRD_MIND.value))
                    {
                        throw new NotImplementedException();
                        ///* One in ten individuals are detectable */
                        //if ((m_idx % 10) == 5)
                        //{
                        //    /* Detectable */
                        //    flag = true;

                        //    /* Check for LOS so that MFLAG_VIEW is set later */
                        //    if (player_has_los_bold(fy, fx)) easy = true;
                        //}
                    }

                    /* Normal mind, allow telepathy */
                    else
                    {
                        throw new NotImplementedException();
                        ///* Detectable */
                        //flag = true;

                        ///* Check for LOS to that MFLAG_VIEW is set later */
                        //if (player_has_los_bold(fy, fx)) easy = true;
                    }
                }

                /* Normal line of sight and player is not blind */
                if (Cave.player_has_los_bold(fy, fx) && Misc.p_ptr.timed[(int)Timed_Effect.BLIND] == 0)
                {
                    /* Use "infravision" */
                    if (d <= Misc.p_ptr.state.see_infra)
                    {
                        /* Learn about warm/cold blood */
                        l_ptr.flags.on(Monster_Flag.COLD_BLOOD.value);

                        /* Handle "warm blooded" monsters */
                        if (!r_ptr.flags.has(Monster_Flag.COLD_BLOOD.value))
                        {
                            /* Easy to see */
                            easy = flag = true;
                        }
                    }

                    /* See if the monster is emitting light */
                    /*if (rf_has(r_ptr.flags, RF_HAS_LIGHT)) easy = flag = true;*/

                    /* Use "illumination" */
                    if (Cave.player_can_see_bold(fy, fx))
                    {
                        /* Learn it emits light */
                        l_ptr.flags.on(Monster_Flag.HAS_LIGHT.value);

                        /* Learn about invisibility */
                        l_ptr.flags.on(Monster_Flag.INVISIBLE.value);

                        /* Handle "invisible" monsters */
                        if (r_ptr.flags.has(Monster_Flag.INVISIBLE.value))
                        {
                            /* See invisible */
                            if (Misc.p_ptr.check_state(Object_Flag.SEE_INVIS, Misc.p_ptr.state.flags))
                            {
                                /* Easy to see */
                                easy = flag = true;
                            }
                        }

                        /* Handle "normal" monsters */
                        else
                        {
                            /* Easy to see */
                            easy = flag = true;
                        }
                    }
                }
            }

            /* If a mimic looks like a squelched item, it's not seen */
            if (is_mimicking(m_idx))
            {
                throw new NotImplementedException();
                //object_type *o_ptr = object_byid(m_ptr.mimicked_o_idx);
                //if (squelch_item_ok(o_ptr))
                //    easy = flag = false;
            }

            /* The monster is now visible */
            if (flag)
            {
                /* Learn about the monster's mind */
                if (Misc.p_ptr.check_state(Object_Flag.TELEPATHY, Misc.p_ptr.state.flags))
                {
                    l_ptr.flags.set(Monster_Flag.EMPTY_MIND.value, Monster_Flag.WEIRD_MIND.value,
                                    Monster_Flag.SMART.value, Monster_Flag.STUPID.value);
                }

                /* It was previously unseen */
                if (!m_ptr.ml)
                {
                    /* Mark as visible */
                    m_ptr.ml = true;

                    /* Draw the monster */
                    Cave.cave_light_spot(Cave.cave, fy, fx);

                    /* Update health bar as needed */
                    if (Misc.p_ptr.health_who == m_idx)
                    {
                        Misc.p_ptr.redraw |= (Misc.PR_HEALTH);
                    }

                    /* Hack -- Count "fresh" sightings */
                    if (l_ptr.sights < short.MaxValue)
                    {
                        l_ptr.sights++;
                    }

                    /* Disturb on appearance */
                    if (Option.disturb_move.value)
                    {
                        Cave.disturb(Misc.p_ptr, 1, 0);
                    }

                    /* Window stuff */
                    Misc.p_ptr.redraw |= Misc.PR_MONLIST;
                }
            }

            /* The monster is not visible */
            else
            {
                /* It was previously seen */
                if (m_ptr.ml)
                {
                    /* Treat mimics differently */
                    if (m_ptr.mimicked_o_idx == 0 || Squelch.item_ok(Object.Object.byid(m_ptr.mimicked_o_idx)))
                    {
                        /* Mark as not visible */
                        m_ptr.ml = false;

                        /* Erase the monster */
                        Cave.cave_light_spot(Cave.cave, fy, fx);

                        /* Update health bar as needed */
                        if (Misc.p_ptr.health_who == m_idx)
                        {
                            Misc.p_ptr.redraw |= (Misc.PR_HEALTH);
                        }

                        /* Disturb on disappearance */
                        if (Option.disturb_move.value)
                        {
                            Cave.disturb(Misc.p_ptr, 1, 0);
                        }

                        /* Window stuff */
                        Misc.p_ptr.redraw |= Misc.PR_MONLIST;
                    }
                }
            }


            /* The monster is now easily visible */
            if (easy)
            {
                /* Change */
                if ((m_ptr.mflag & (Monster_Flag.MFLAG_VIEW)) == 0)
                {
                    /* Mark as easily visible */
                    m_ptr.mflag |= (Monster_Flag.MFLAG_VIEW);

                    /* Disturb on appearance */
                    if (Option.disturb_near.value)
                    {
                        Cave.disturb(Misc.p_ptr, 1, 0);
                    }

                    /* Re-draw monster window */
                    Misc.p_ptr.redraw |= Misc.PR_MONLIST;
                }
            }

            /* The monster is not easily visible */
            else
            {
                /* Change */
                if ((m_ptr.mflag & (Monster_Flag.MFLAG_VIEW)) != 0)
                {
                    /* Mark as not easily visible */
                    m_ptr.mflag &= ~(Monster_Flag.MFLAG_VIEW);

                    /* Disturb on disappearance */
                    if (Option.disturb_near.value)
                    {
                        Cave.disturb(Misc.p_ptr, 1, 0);
                    }

                    /* Re-draw monster list window */
                    Misc.p_ptr.redraw |= Misc.PR_MONLIST;
                }
            }
        }