Esempio n. 1
0
        /// <summary>
        /// Replaces the specified range of characters with the specified string.
        /// This method is only used by Views.
        /// </summary>
        public void ReplaceRgch(int ichMin, int ichLim, string rgchIns, int cchIns, ITsTextProps ttp)
        {
            ThrowIfCharOffsetOutOfRange("ichMin", ichMin, ichLim);
            ThrowIfCharOffsetOutOfRange("ichLim", ichLim, Length);
            ThrowIfCharOffsetOutOfRange("cchIns", cchIns, rgchIns == null ? 0 : rgchIns.Length);

            // Don't do anything if there is nothing to insert or delete and we are not empty.
            if (cchIns == 0 && ichMin == ichLim && Length > 0)
            {
                return;
            }

            TsTextProps textProps;

            if (ttp == null)
            {
                // If ichMin equals ichLim, use the previous characters properties.
                int charIndex = ichMin == ichLim && ichMin > 0 ? ichMin - 1 : ichMin;
                textProps = m_runs[get_RunAt(charIndex)].TextProps;
            }
            else
            {
                textProps = ttp as TsTextProps;
                if (textProps == null && ttp != null)
                {
                    // if it came from C++, could be wrapped in a way that prevents a simple cast.
                    textProps = ((TsPropsFactory)TsStringUtils.TsPropsFactory).FromITsTextProps(ttp);
                }
            }

            TsRun run = new TsRun(cchIns, textProps);

            ReplaceInternal(ichMin, ichLim, rgchIns == null ? string.Empty : rgchIns.Substring(0, cchIns), new[] { run });
        }
Esempio n. 2
0
        /// <summary>
        /// Sets the text properties for the specified range of characters.
        /// </summary>
        public void SetProperties(int ichMin, int ichLim, ITsTextProps ttp)
        {
            ThrowIfCharOffsetOutOfRange("ichMin", ichMin, ichLim);
            ThrowIfCharOffsetOutOfRange("ichLim", ichLim, Length);
            ThrowIfParamNull("ttp", ttp);

            var textProps = ttp as TsTextProps;

            if (textProps == null)
            {
                // if it came from C++, could be wrapped in a way that prevents a simple cast.
                textProps = ((TsPropsFactory)TsStringUtils.TsPropsFactory).FromITsTextProps(ttp);
            }

            if (ichMin == ichLim)
            {
                if (Length == 0)
                {
                    m_runs[0] = new TsRun(0, textProps);
                }
                return;
            }

            int minRunIndex = get_RunAt(ichMin);
            int limRunIndex = get_RunAt(ichLim);

            TsRun run = new TsRun(ichLim - ichMin, textProps);

            SetPropertiesInternal(ichMin, ichLim, minRunIndex, limRunIndex, 0, new[] { run });
        }
Esempio n. 3
0
        private void ReplaceInternal(int ichMin, int ichLim, string insertText, IList <TsRun> insertRuns)
        {
            // This is the only case where we can end up with an empty run.
            if (insertText.Length == 0)
            {
                // If we're deleting everything and we were passed a run, use it.
                if (ichMin == 0 && ichLim == Length)
                {
                    m_text.Clear();
                    // If we were given some run properties, let them become those of the empty string.
                    TsTextProps props = insertRuns.Count > 0 ? insertRuns[0].TextProps : m_runs[0].TextProps;
                    m_runs.Clear();
                    m_runs.Add(new TsRun(0, props));
                    return;
                }

                // We're not deleting everything, therefore any run we were passed describes
                // no characters and should be ignored.
                if (insertRuns.Count > 0)
                {
                    insertRuns = new TsRun[0];
                }
            }

            int minRunIndex = get_RunAt(ichMin);
            int limRunIndex = get_RunAt(ichLim);

            m_text.Remove(ichMin, ichLim - ichMin);
            m_text.Insert(ichMin, insertText);

            // dich is the amount that indices >= ichLim should be adjusted by after the replace.
            int dich = insertText.Length - ichLim + ichMin;

            SetPropertiesInternal(ichMin, ichLim, minRunIndex, limRunIndex, dich, insertRuns);
        }
Esempio n. 4
0
        /// <summary>
        /// Gets the substring for the specified range returned as an <see cref="ITsString"/>.
        /// </summary>
        public ITsString GetSubstring(int ichMin, int ichLim)
        {
            ThrowIfCharOffsetOutOfRange("ichMin", ichMin, ichLim);
            ThrowIfCharOffsetOutOfRange("ichLim", ichLim, Length);

            if (ichMin == 0 && ichLim == Length)
            {
                return(this);
            }

            string newText = GetChars(ichMin, ichLim);

            var newRuns = new List <TsRun>();
            int irun    = get_RunAt(ichMin);

            for (int i = irun; i < m_runs.Length; i++)
            {
                TsRun run     = m_runs[i];
                bool  lastRun = ichLim <= run.IchLim;
                newRuns.Add(new TsRun((lastRun ? ichLim : run.IchLim) - ichMin, run.TextProps));
                if (lastRun)
                {
                    break;
                }
            }

            return(new TsString(newText, newRuns.ToArray()));
        }
Esempio n. 5
0
        /// <summary>
        /// Replaces the specified range of characters with the specified string.
        /// This method is only used by Views.
        /// </summary>
        public void ReplaceRgch(int ichMin, int ichLim, string rgchIns, int cchIns, ITsTextProps ttp)
        {
            ThrowIfCharOffsetOutOfRange("ichMin", ichMin, ichLim);
            ThrowIfCharOffsetOutOfRange("ichLim", ichLim, Length);
            ThrowIfCharOffsetOutOfRange("cchIns", cchIns, rgchIns == null ? 0 : rgchIns.Length);

            // Don't do anything if there is nothing to insert or delete and we are not empty.
            if (cchIns == 0 && ichMin == ichLim && Length > 0)
            {
                return;
            }

            TsTextProps textProps;

            if (ttp == null)
            {
                // If ichMin equals ichLim, use the previous characters properties.
                int charIndex = ichMin == ichLim && ichMin > 0 ? ichMin - 1 : ichMin;
                textProps = m_runs[get_RunAt(charIndex)].TextProps;
            }
            else
            {
                textProps = (TsTextProps)ttp;
            }

            TsRun run = new TsRun(cchIns, textProps);

            ReplaceInternal(ichMin, ichLim, rgchIns == null ? string.Empty : rgchIns.Substring(0, cchIns), new[] { run });
        }
Esempio n. 6
0
        /// <summary>
        /// Fetches the information for the specified run.
        /// </summary>
        public ITsTextProps FetchRunInfo(int irun, out TsRunInfo tri)
        {
            ThrowIfRunIndexOutOfRange("irun", irun);

            TsRun run = Runs[irun];

            tri = new TsRunInfo {
                ichMin = GetRunIchMin(irun), ichLim = run.IchLim, irun = irun
            };
            return(run.TextProps);
        }
Esempio n. 7
0
        /// <summary>
        /// Appends the specified string to end of the current text.
        /// </summary>
        public void Append(string bstrIns)
        {
            if (string.IsNullOrEmpty(bstrIns))
            {
                return;
            }

            m_text.Append(bstrIns);

            var newRun = new TsRun(m_text.Length, (TsTextProps)m_propsBldr.GetTextProps());

            if (m_runs.Count > 0 && m_runs[m_runs.Count - 1].TextProps.Equals(newRun.TextProps))
            {
                m_runs[m_runs.Count - 1] = newRun;
            }
            else
            {
                m_runs.Add(newRun);
            }
        }
Esempio n. 8
0
        private void SetPropertyValue(int ichMin, int ichLim, Func <TsTextProps, TsTextProps> editTextPropsFunc)
        {
            if (ichMin == ichLim)
            {
                if (Length == 0)
                {
                    m_runs[0] = new TsRun(0, editTextPropsFunc(m_runs[0].TextProps));
                }
                return;
            }

            int minRunIndex = get_RunAt(ichMin);

            if (GetRunIchMin(minRunIndex) < ichMin)
            {
                m_runs.Insert(minRunIndex, new TsRun(ichMin, m_runs[minRunIndex].TextProps));
                minRunIndex++;
            }

            int limRunIndex = get_RunAt(ichLim - 1);

            if (ichLim < m_runs[limRunIndex].IchLim)
            {
                m_runs.Insert(limRunIndex, new TsRun(ichLim, m_runs[limRunIndex].TextProps));
            }

            for (int i = limRunIndex; i >= minRunIndex; i--)
            {
                m_runs[i] = new TsRun(m_runs[i].IchLim, editTextPropsFunc(m_runs[i].TextProps));
                if (i < m_runs.Count - 1 && m_runs[i].TextProps.Equals(m_runs[i + 1].TextProps))
                {
                    m_runs.RemoveAt(i);
                }
            }

            if (minRunIndex > 0 && m_runs[minRunIndex].TextProps.Equals(m_runs[minRunIndex - 1].TextProps))
            {
                m_runs.RemoveAt(minRunIndex - 1);
            }
        }
Esempio n. 9
0
        /// <summary>
        /// Sets the text properties for the specified range of characters.
        /// </summary>
        public void SetProperties(int ichMin, int ichLim, ITsTextProps ttp)
        {
            ThrowIfCharOffsetOutOfRange("ichMin", ichMin, ichLim);
            ThrowIfCharOffsetOutOfRange("ichLim", ichLim, Length);
            ThrowIfParamNull("ttp", ttp);

            var textProps = (TsTextProps)ttp;

            if (ichMin == ichLim)
            {
                if (Length == 0)
                {
                    m_runs[0] = new TsRun(0, textProps);
                }
                return;
            }

            int minRunIndex = get_RunAt(ichMin);
            int limRunIndex = get_RunAt(ichLim);

            TsRun run = new TsRun(ichLim - ichMin, textProps);

            SetPropertiesInternal(ichMin, ichLim, minRunIndex, limRunIndex, 0, new[] { run });
        }
Esempio n. 10
0
        private void SetPropertiesInternal(int ichMin, int ichLim, int minRunIndex, int limRunIndex, int dich, IList <TsRun> insertRuns)
        {
            // Ensure ichMin is on a run boundary.
            if (ichMin > GetRunIchMin(minRunIndex))
            {
                // Insertion is within a single run.
                if (minRunIndex == limRunIndex)
                {
                    // Split the run.
                    m_runs.Insert(minRunIndex, new TsRun(ichMin, m_runs[limRunIndex].TextProps));
                    limRunIndex++;
                }
                else
                {
                    // Adjust the boundary, even when not splitting.
                    m_runs[minRunIndex] = new TsRun(ichMin, m_runs[minRunIndex].TextProps);
                }
                minRunIndex++;
            }

            m_runs.RemoveRange(minRunIndex, limRunIndex - minRunIndex);
            m_runs.InsertRange(minRunIndex, insertRuns);

            limRunIndex = minRunIndex + insertRuns.Count;
            if (ichMin > 0)
            {
                for (int i = minRunIndex; i < limRunIndex; i++)
                {
                    m_runs[i] = new TsRun(m_runs[i].IchLim + ichMin, m_runs[i].TextProps);
                }
            }

            if (dich != 0)
            {
                for (int i = limRunIndex; i < m_runs.Count; i++)
                {
                    m_runs[i] = new TsRun(m_runs[i].IchLim + dich, m_runs[i].TextProps);
                }
            }

            // See if we can combine on the left.
            if (minRunIndex > 0)
            {
                if (m_runs[minRunIndex].TextProps.Equals(m_runs[minRunIndex - 1].TextProps))
                {
                    m_runs.RemoveAt(minRunIndex - 1);
                    limRunIndex--;
                }
            }

            // See if we can combine on the right.
            if (limRunIndex > 0)
            {
                // Empty right run, delete.
                if (m_runs[limRunIndex].IchLim == m_runs[limRunIndex - 1].IchLim)
                {
                    m_runs.RemoveAt(limRunIndex);
                }
                else if (m_runs[limRunIndex - 1].TextProps.Equals(m_runs[limRunIndex].TextProps))
                {
                    m_runs.RemoveAt(limRunIndex - 1);
                    // limRunIndex is no longer valid after the above delete.
                }
            }
        }