Надстройка Word VSTO: изменение текста абзаца через его диапазон - PullRequest
0 голосов
/ 02 июня 2018

Я программирую надстройку, которая использует GroupContentControl (GCC) для защиты от записи каждого абзаца, который использует стиль «Заголовок 1».После защиты эти заголовки могут быть изменены только через надстройку.С этой целью я написал простой метод, который удаляет GCC абзаца, назначает новое значение свойству Range.Text абзаца, снова устанавливает стиль для заголовка 1, а затем устанавливает новый GCC для защиты абзаца.

Я все еще новичок в программировании Office, и я предположил, что объект Range можно использовать на протяжении всего процесса.Однако метод ведет себя неправильно: он вставляет возврат каретки после текста нового абзаца, а затем берет следующий абзац в документе и делает его абзацем заголовка 1, а затем защищает от записи.

Вот мой метод,наряду с вызовами функции регистрации, чтобы увидеть, как эволюционирует Range:

void ChangeParagraphText (Word.Paragraph p, string NewText)
{
    Log("Range 1 : " + p.Range.Start + " - " + p.Range.End);
    UnlockTitle(p);     // remove the paragraph's GroupContentControl     
    Log("Range 2 : " + p.Range.Start + " - " + p.Range.End);
    p.Range.Text = NewText;   // change the paragraph's text
    Log("Range 3 : " + p.Range.Start + " - " + p.Range.End);
    p.Range.set_Style(Globals.ThisAddIn.Application.ActiveDocument.Styles[Word.WdBuiltinStyle.wdStyleHeading1]);
    Log("Range 4 : " + p.Range.Start + " - " + p.Range.End);
    LockTitle(p);       // write-protect the paragraph with a GroupContentControl
    Log("Range 5 : " + p.Range.Start + " - " + p.Range.End);
}

Как только он запустится, вот содержимое файла журнала:

Range 1 : 90 - 99
Range 2 : 90 - 97
Range 3 : 100 - 102
Range 4 : 100 - 102
Range 5 : 100 - 104

Это научило меня некоторыминтересные вещи.Для начала длина диапазона уменьшается на два после удаления GCC и увеличивается на два при добавлении GCC.Важной частью, однако, является третья запись в журнале: она показывает, что как только я назначаю Range.Text параграфа, Range полностью изменяется.Значения соответствуют параграфу next в моем тестовом документе.

Чтение свойства Range.Text также показывает, что оно заканчивается символом перевода строки (ASCII 13).Если я опущу его, я получу следующий абзац, добавленный к моему абзацу заголовка 1.Если я вставлю это, я получу второй абзац, который будет считаться абзацем заголовка 1.У меня не работает ни одно из этих поведений.

Мой вопрос: как программно изменить текст абзаца?Я предполагаю, что это должно быть возможно, но если это не так, какой обходной путь?Я думал о создании нового абзаца после того, который я хочу изменить, а затем об удалении старого, но это выглядит не элегантно.

1 Ответ

0 голосов
/ 02 июня 2018

Во-первых, быстрый ответ на заданный вами вопрос: как заменить текст абзаца, оставив сам абзац без изменений.Я не могу использовать предоставленный вами код, так как он не показывает, как вы получаете p.Поэтому я беру произвольный Paragraph объект:

Word.Range rngPara = doc.Paragraphs[1].Range;
object unitCharacter = Word.WdUnits.wdCharacter;
object backOne = -1;
rngPara.MoveEnd(ref unitCharacter, ref backOne);
rngPara.Text = "replacement text";

Справочная информация :

Самый важный аспект вашей проблемы - понимание объектов Word Range.

Во-первых, никогда не полагайтесь на свойства Start и End для определения диапазона.Они подходят для «моментальных снимков» или для динамической установки начальной или конечной точки одного диапазона на секунду.Но как только в документе происходит какое-либо редактирование, вы можете выбросить их.

Когда вам нужно работать с диапазонами, используйте Range объекты (переменные) для продолжительности выполняющегося кода.

Да, как вы анализируете, Paragraph.Range.Text включает знак конца абзаца.Это ANSI 13, а не просто возврат каретки;под обложками хранится информация о форматировании абзаца.Если вы хотите работать только с текстом, сократите диапазон на один символ, чтобы знак абзаца не попал в диапазон.Это можно сделать с помощью метода MoveEnd.

...