/// ------------------------------------------------------------------------------------ /// <summary> /// Inserts a footnote at the given selection /// </summary> /// <param name="selHelper">Current selection information</param> /// <param name="styleName">style name for created footnote</param> /// <param name="iFootnote">out: If selHelper is in vernacular para, the ihvo of the /// footnote just inserted. If selHelper is in back trans, the ihvo of the footnote /// corresponding to the ref ORC just inserted in the BT, or -1 no corresponding</param> /// <returns>The created/corresponding footnote</returns> /// ------------------------------------------------------------------------------------ public virtual IStFootnote InsertFootnote(SelectionHelper selHelper, string styleName, out int iFootnote) { CheckDisposed(); // Get any selected text. ITsString tssSelectedText; IVwSelection vwsel = selHelper.Selection; if (!IsSelectionInUserPrompt && IsSelectionInOneEditableProp(vwsel)) vwsel.GetSelectionString(out tssSelectedText, string.Empty); else tssSelectedText = TsStringUtils.MakeTss(string.Empty, m_cache.DefaultVernWs); int hvoObj; ITsString tssSel; // This is either the vernacular or the BT, depending on the selection location. int propTag; int ws; selHelper.ReduceToIp(SelectionHelper.SelLimitType.Bottom, false, false); int ichSel = GetSelectionInfo(selHelper, out hvoObj, out propTag, out tssSel, out ws); if (propTag == StTxtParaTags.kflidContents) ws = Cache.DefaultVernWs; // Make sure the selection is updated with the new ich position in case it was wrong // (e.g. If the selection is in a user prompt) (TE-8919) selHelper.IchAnchor = selHelper.IchEnd = ichSel; // get book info IScrBook book = GetCurrentBook(m_cache); // get paragraph info int paraHvo = selHelper.GetLevelInfoForTag(StTextTags.kflidParagraphs).hvo; IScrTxtPara para = m_repoScrTxtPara.GetObject(paraHvo); tssSelectedText = TsStringUtils.GetCleanTsString(tssSelectedText, ScrStyleNames.ChapterAndVerse); Debug.Assert(tssSelectedText != null); if (tssSelectedText.Length > 0) { ITsStrBldr bldr = tssSelectedText.GetBldr(); bldr.SetStrPropValue(0, bldr.Length, (int)FwTextPropType.ktptNamedStyle, ScrStyleNames.ReferencedText); bldr.ReplaceRgch(bldr.Length, bldr.Length, " ", 1, StyleUtils.CharStyleTextProps(null, ws)); tssSelectedText = bldr.GetString(); } //Cache.ActionHandlerAccessor.AddAction(new UndoWithRefreshAction()); IScrFootnote footnote = null; iFootnote = -1; if (propTag == StTxtParaTags.kflidContents) { // Inserting footnote into the vernacular paragraph iFootnote = FindFootnotePosition(book, selHelper); ITsStrBldr tsStrBldr = para.Contents.GetBldr(); // create the footnote and insert its marker into the paragraph's string // builder. footnote = book.InsertFootnoteAt(iFootnote, tsStrBldr, ichSel); // BEFORE we insert the ORC in the paragraph, we need to insert an empty // paragraph into the new StFootnote, because the para style is needed to // determine the footnote marker type. IStTxtPara footnotePara = footnote.AddNewTextPara(styleName); // update the paragraph contents to include the footnote marker para.Contents = tsStrBldr.GetString(); // Insert the selected text (or an empty run) into the footnote paragraph. footnotePara.Contents = tssSelectedText; } else { IMultiString bt = null; if (propTag == SegmentTags.kflidFreeTranslation) { // Inserting footnote reference ORC into a segment free translation ISegment segment = m_repoSegment.GetObject(selHelper.GetLevelInfoForTag(StTxtParaTags.kflidSegments).hvo); bt = segment.FreeTranslation; footnote = FindVernParaFootnote(segment, ws); } else if (propTag == CmTranslationTags.kflidTranslation) { // Inserting footnote reference ORC into a back translation footnote = FindVernParaFootnote(ichSel, tssSel, para); bt = para.GetBT().Translation; } if (footnote != null) { // Insert footnote reference ORC into back translation paragraph. ITsStrBldr tssBldr = tssSel.GetBldr(); //if reference to footnote already somewhere else in para, delete it first int ichDel = TsStringUtils.DeleteOrcFromBuilder(tssBldr, footnote.Guid); if (ichDel >= 0 && ichSel > ichDel) ichSel--; TsStringUtils.InsertOrcIntoPara(footnote.Guid, FwObjDataTypes.kodtNameGuidHot, tssBldr, ichSel, ichSel, ws); bt.set_String(ws, tssBldr.GetString()); iFootnote = footnote.IndexInOwner; if (tssSelectedText.Length > 0) { ICmTranslation btFootnoteTrans = ((IStTxtPara)footnote.ParagraphsOS[0]).GetBT(); ITsString btFootnoteTss = btFootnoteTrans.Translation.get_String(ws); // Insert any selected text into this back translation for the footnote paragraph. btFootnoteTrans.Translation.set_String(ws, tssSelectedText); } } } if (footnote == null) MiscUtils.ErrorBeep(); // No footnote reference ORC inserted else { // Update the selection in the view that the footnote was inserted. selHelper.UpdateScrollLocation(); // Make sure this is up-to-date selHelper = new SelectionHelper(selHelper); // Get a new copy, so any subsequent changes won't affect us. selHelper.IchAnchor++; selHelper.AssocPrev = false; // Associate away from the newly inserted marker to avoid shifting scroll position by a couple pixels selHelper.IchEnd = selHelper.IchAnchor; Callbacks.RequestVisibleSelectionAtEndOfUow(selHelper); } return footnote; }