internal static void HandleUpDownArrows(KeyEventArgs e, IVwRootBox rootBox, SelectionHelper curSel, List<IWritingSystem> wsList, int flid) { if (curSel == null || !curSel.IsValid) // LT-13805: sometimes selection was null return; var index = GetCurrentSelectionIndex(curSel, wsList); if (index < 0) return; var maxWsIndex = wsList.Count - 1; if (e.KeyCode == Keys.Up) { // Handle Up arrow if ((index - 1) < 0) return; index--; } else { // Handle Down arrow if ((index + 1) > maxWsIndex) return; index++; } // make new selection at index var newSelection = GetSelAtStartOfWs(rootBox, flid, index, wsList[index]); newSelection.Install(); e.Handled = true; }
public SelectionWrapper(SimpleRootSite rootSite) { SelectionHelper = new SelectionHelper(rootSite.EditingHelper.CurrentSelection); ITsTextProps[] textProps; IVwPropertyStore[] propertyStores; int numberOfProps; SelectionHelper.GetSelectionProps(SelectionHelper.Selection, out textProps, out propertyStores, out numberOfProps); if (numberOfProps > 0) m_TextProps = textProps; }
internal static int GetCurrentSelectionIndex(SelectionHelper curSel, List<IWritingSystem> writingSystems) { var ws = curSel.SelProps.GetWs(); int index = -1; for (var i = 0; i < writingSystems.Count; i++) { if (writingSystems[i].Handle == ws) { index = i; break; } } return index; }
/// ------------------------------------------------------------------------------------ /// <summary> /// Initializes a new instance of the <see cref="SelectionRestorer"/> class. /// </summary> /// ------------------------------------------------------------------------------------ public SelectionRestorer(SimpleRootSite rootSite) { // we can't use EditingHelper.CurrentSelection here because the scroll position // of the selection may have changed. m_savedSelection = SelectionHelper.Create(rootSite); m_rootSite = rootSite; Rectangle rcSrc, rcDst; rootSite.GetCoordRects(out rcSrc, out rcDst); try { IVwSelection sel = rootSite.RootBox.MakeSelAt(5, 5, rcSrc, rcDst, false); m_topOfViewSelection = SelectionHelper.Create(sel, rootSite); } catch (COMException) { // Just ignore any errors } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Gets the displayed text for a footnote. /// </summary> /// <param name="iBook">Index of the book the footnote is in</param> /// <param name="iFootnote">Index of the footnote</param> /// <param name="footnote">The footnote object</param> /// <returns>The TsString representing the text of the footnote, including any displayed /// marker, reference, etc.</returns> /// ------------------------------------------------------------------------------------ public ITsString GetDisplayedTextForFootnote(int iBook, int iFootnote, IStFootnote footnote) { SelectionHelper helper = new SelectionHelper(); // Create selection in footnote marker SelLevInfo[] anchorLevInfo = new SelLevInfo[4]; anchorLevInfo[3].tag = BookFilter.Tag; anchorLevInfo[3].ihvo = iBook; anchorLevInfo[2].tag = ScrBookTags.kflidFootnotes; anchorLevInfo[2].ihvo = iFootnote; anchorLevInfo[1].tag = StTextTags.kflidParagraphs; anchorLevInfo[1].ihvo = 0; anchorLevInfo[0].tag = -1; anchorLevInfo[0].ihvo = 0; helper.SetLevelInfo(SelectionHelper.SelLimitType.Anchor, anchorLevInfo); helper.SetTextPropId(SelectionHelper.SelLimitType.Anchor, (int)VwSpecialAttrTags.ktagGapInAttrs); helper.IchAnchor = 0; SelLevInfo[] endLevInfo = new SelLevInfo[3]; endLevInfo[2].tag = BookFilter.Tag; endLevInfo[2].ihvo = iBook; endLevInfo[1].tag = ScrBookTags.kflidFootnotes; endLevInfo[1].ihvo = iFootnote; endLevInfo[0].tag = StTextTags.kflidParagraphs; endLevInfo[0].ihvo = 0; helper.SetLevelInfo(SelectionHelper.SelLimitType.End, endLevInfo); helper.SetTextPropId(SelectionHelper.SelLimitType.End, StTxtParaTags.kflidContents); string footnoteText = ((IStTxtPara)footnote.ParagraphsOS[0]).Contents.Text; helper.IchEnd = footnoteText.Length; helper.SetTextPropId(SelectionHelper.SelLimitType.End, StTxtParaTags.kflidContents); helper.SetSelection(this, true, true); IVwSelection sel = RootBox.Selection; ITsString tss; sel.GetSelectionString(out tss, string.Empty); return tss; }
/// ------------------------------------------------------------------------------------ /// <summary> /// Refreshes all highlighting (revision and current draft diff views, and revision and /// current footnote diff views. /// </summary> /// ------------------------------------------------------------------------------------ private void RefreshAllHighlighting() { if (m_diffViewWrapper == null) return; // if there is a footnote selection, refresh highlighting and scroll to it. // Before we refresh the highlighting, we must save the selection helper because // it is cleared when we refresh the highlighting and the selection is not in the view. if (m_diffViewWrapper.CurrentDiffFootnoteView != null && m_diffViewWrapper.CurrentDiffFootnoteView.Visible && m_diffViewWrapper.CurrentDiffFootnoteView.EditingHelper.CurrentSelection != null) { m_diffViewWrapper.CurrentDiffFootnoteView.ScrollSelectionIntoView(m_diffViewWrapper.CurrentDiffFootnoteView.RootBox.Selection, VwScrollSelOpts.kssoDefault); SelectionHelper selHelper = null; if (m_diffViewWrapper.CurrentDiffFootnoteView.EditingHelper.CurrentSelection != null) selHelper = new SelectionHelper(m_diffViewWrapper.CurrentDiffFootnoteView.EditingHelper.CurrentSelection); RefreshDiffViewHighlighting(m_diffViewWrapper.CurrentDiffFootnoteView.EditingHelper.CurrentSelection); if (selHelper != null) selHelper.SetSelection(m_diffViewWrapper.CurrentDiffFootnoteView, true, true); } if (m_diffViewWrapper.RevisionDiffFootnoteView != null && m_diffViewWrapper.RevisionDiffFootnoteView.Visible && m_diffViewWrapper.RevisionDiffFootnoteView.EditingHelper.CurrentSelection != null) { m_diffViewWrapper.RevisionDiffFootnoteView.ScrollSelectionIntoView( m_diffViewWrapper.RevisionDiffFootnoteView.RootBox.Selection, VwScrollSelOpts.kssoDefault); SelectionHelper selHelper = null; if (m_diffViewWrapper.RevisionDiffFootnoteView.EditingHelper.CurrentSelection != null) selHelper = new SelectionHelper(m_diffViewWrapper.RevisionDiffFootnoteView.EditingHelper.CurrentSelection); RefreshDiffViewHighlighting(m_diffViewWrapper.RevisionDiffFootnoteView.EditingHelper.CurrentSelection); if (selHelper != null) selHelper.SetSelection(m_diffViewWrapper.RevisionDiffFootnoteView, true, true); } // Refresh highlighted text when window is resized. if (m_diffViewWrapper.CurrentDiffView != null && m_diffViewWrapper.CurrentDiffView.EditingHelper.CurrentSelection != null) { RefreshDiffViewHighlighting(m_diffViewWrapper.CurrentDiffView.EditingHelper.CurrentSelection); } if (m_diffViewWrapper.RevisionDiffView != null && m_diffViewWrapper.RevisionDiffView.EditingHelper.CurrentSelection != null) { RefreshDiffViewHighlighting(m_diffViewWrapper.RevisionDiffView.EditingHelper.CurrentSelection); } // Scroll selections from draft and revision into view. ScrollToDiff(m_differences.CurrentDifference); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Remember if a picture is selected so that it can be deselected on mouse up, /// if necessary. /// </summary> /// <param name="pt"></param> /// <param name="rcSrcRoot"></param> /// <param name="rcDstRoot"></param> /// ------------------------------------------------------------------------------------ protected override void CallMouseDown(Point pt, Rectangle rcSrcRoot, Rectangle rcDstRoot) { IVwSelection sel = m_rootb.MakeSelAt(pt.X, pt.Y, rcSrcRoot, rcDstRoot, false); if (sel != null && sel.SelType == VwSelType.kstPicture) { // If the picture selected is a translation status box, remember which picture is // selected (so that the status only changes if the same status box is selected // on mouse up and mouse down). SelectionHelper selHelper = SelectionHelper.Create(sel, this); SelLevInfo[] info = selHelper.LevelInfo; if (info[0].tag == StTxtParaTags.kflidTranslations) { m_selectedTransHvo = info[0].hvo; m_pictureSelected = true; m_selectionHelper = EditingHelper.CurrentSelection; } } else { m_pictureSelected = false; m_selectedTransHvo = 0; } base.CallMouseDown (pt, rcSrcRoot, rcDstRoot); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Find and select the next translation meeting a given condition /// </summary> /// <param name="selection">The selection where to start the search. /// NOTE: The selection must have all of the info set in the LevelInfo (hvo, ihvo)</param> /// <param name="condition">Condition the cack translation must meet</param> /// ------------------------------------------------------------------------------------ private void MoveToNextTranslation(SelectionHelper selection, Func<ICmTranslation, bool> condition) { SelLevInfo bookInfo; SelLevInfo paraInfo; SelLevInfo sectionInfo; bool fFoundBookLevel = selection.GetLevelInfoForTag(BookFilter.Tag, out bookInfo); bool fFoundSectionLevel = selection.GetLevelInfoForTag( ScrBookTags.kflidSections, out sectionInfo); int secLev = selection.GetLevelForTag(ScrBookTags.kflidSections); bool fFoundParaLevel = selection.GetLevelInfoForTag( StTextTags.kflidParagraphs, out paraInfo); if (!fFoundBookLevel || !fFoundParaLevel) return; // Look through all the books in the book filter int bookStartIndex = bookInfo.ihvo; int sectionStartIndex = 0; int sectionTag; int paraStartIndex = paraInfo.ihvo + 1; int paraIndex; if (fFoundSectionLevel) { // start with current section sectionStartIndex = sectionInfo.ihvo; sectionTag = selection.LevelInfo[secLev - 1].tag; } else { // no section, so this must be the title - Look through the title paragraphs IScrBook checkBook = BookFilter.GetBook(bookStartIndex); paraIndex = FindNextTranslationInText(checkBook.TitleOA, paraStartIndex, condition); if (paraIndex >= 0) { // select the title paragraph SetInsertionPoint(ScrBookTags.kflidTitle, bookStartIndex, 0, paraIndex); return; } // continue the search with the current book sectionTag = ScrSectionTags.kflidHeading; paraStartIndex = 0; } for (int bookIndex = bookStartIndex; bookIndex < BookFilter.BookCount; bookIndex++) { IScrBook checkBook = BookFilter.GetBook(bookIndex); if (bookIndex > bookStartIndex) { // Look through the title paragraphs paraIndex = FindNextTranslationInText(checkBook.TitleOA, 0, condition); if (paraIndex >= 0) { // select the title paragraph SetInsertionPoint(ScrBookTags.kflidTitle, bookIndex, 0, paraIndex); return; } } // Look through the sections in order. for (int sectionIndex = sectionStartIndex; sectionIndex < checkBook.SectionsOS.Count; sectionIndex++) { IScrSection checkSection = checkBook.SectionsOS[sectionIndex]; // Look in the paragraphs (could be either content or heading) IStText text = (sectionTag == ScrSectionTags.kflidHeading) ? checkSection.HeadingOA : checkSection.ContentOA; paraIndex = FindNextTranslationInText(text, paraStartIndex, condition); if (paraIndex >= 0) { // select the paragraph SetInsertionPoint(sectionTag, bookIndex, sectionIndex, paraIndex); return; } // Look in the content paragraphs, if we haven't already if (sectionTag == ScrSectionTags.kflidHeading) { sectionTag = ScrSectionTags.kflidContent; paraIndex = FindNextTranslationInText(checkSection.ContentOA, 0, condition); if (paraIndex >= 0) { // select the content paragraph SetInsertionPoint(sectionTag, bookIndex, sectionIndex, paraIndex); return; } } sectionTag = ScrSectionTags.kflidHeading; paraStartIndex = 0; } sectionStartIndex = 0; } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Convert the scripture book tag to a filter tag. Also, convert book indices to /// filtered book indices. This is done when loading a selection to make it work /// in the context of the book filter. /// </summary> /// <param name="helper"></param> /// <param name="selType"></param> /// ------------------------------------------------------------------------------------ private void ConvertBookTagAndIndex(SelectionHelper helper, SelectionHelper.SelLimitType selType) { SelLevInfo[] info = helper.GetLevelInfo(selType); int bookPos = info.Length - 1; if (info[bookPos].tag == ScriptureTags.kflidScriptureBooks) { info[bookPos].tag = BookFilter.Tag; info[bookPos].ihvo = BookFilter.GetBookIndex( m_fdoCache.ServiceLocator.GetInstance<IScrBookRepository>().GetObject(info[bookPos].hvo)); helper.SetLevelInfo(selType, info); } }
/// ----------------------------------------------------------------------------------- /// <summary> /// Focus got set to the draft view /// </summary> /// <param name="e">The event data</param> /// ----------------------------------------------------------------------------------- protected override void OnGotFocus(EventArgs e) { base.OnGotFocus(e); if (DesignMode || !m_fRootboxMade) return; // Reset the previous selected paragraph value to reset the optimization // for scrolling the footnote pane. m_prevSelectedParagraph = 0; if (m_selectionHelper != null) { if (m_selectionHelper.SetSelection(this) == null) { // Set selection to beginning of first book if project has any books if (BookFilter.BookCount > 0) SetInsertionPoint(ScrBookTags.kflidTitle, 0, 0); } m_selectionHelper = null; } // A draft view which has focus cannot display selected-segment highlighting. if (m_vc != null) m_vc.SetupOverrides(null, 0, 0, null, RootBox); }
private bool SelIsInEmptyTranslation(SelectionHelper helper, int flid, int hvo) { if (helper.IsRange) return false; // range can't be in empty comment. if (flid != SegmentTags.kflidFreeTranslation && flid != SegmentTags.kflidLiteralTranslation) return false; // translation is always a comment. if (helper.GetTss(SelectionHelper.SelLimitType.Anchor).Length != 0) return false; // translation is non-empty. return true; }
protected bool RemoveFromOutput(bool forward, SelectionHelper sel, out int index) { index = -1; bool reconstruct = false; ICmObject[] mappings = Rule.OutputOS.Cast<ICmObject>().ToArray(); if (sel.IsRange) { int[] indices = GetIndicesToRemove(mappings, sel); if (indices.Length > 0) index = indices[0] - 1; foreach (int idx in indices) { var mapping = (IMoRuleMapping) mappings[idx]; if (!IsFinalLastVariableMapping(mapping)) { Rule.OutputOS.Remove(mapping); reconstruct = true; } } } else { int idx = GetIndexToRemove(mappings, sel, forward); if (idx > -1) { var mapping = (IMoRuleMapping) mappings[idx]; index = idx - 1; if (!IsFinalLastVariableMapping(mapping)) { Rule.OutputOS.Remove(mapping); reconstruct = true; } } } return reconstruct; }
protected override int RemoveItems(SelectionHelper sel, bool forward, out int cellIndex) { cellIndex = -1; int cellId = GetCell(sel); if (cellId == -1 || cellId == -2) return -1; switch (cellId) { case AffixRuleFormulaVc.ktagLeftEmpty: case AffixRuleFormulaVc.ktagRightEmpty: return -1; case MoAffixProcessTags.kflidOutput: return RemoveFromOutput(forward, sel, out cellIndex) ? cellId : -1; default: var ctxtOrVar = m_cache.ServiceLocator.GetInstance<IPhContextOrVarRepository>().GetObject(cellId); if (ctxtOrVar.ClassID == PhSequenceContextTags.kClassId) { var seqCtxt = (IPhSequenceContext) ctxtOrVar; if (seqCtxt.MembersRS.Count == 0 && forward) { // remove an empty column int prevCellId = GetPrevCell(seqCtxt.Hvo); cellIndex = GetCellCount(prevCellId) - 1; Rule.InputOS.Remove(seqCtxt); return prevCellId; } bool reconstruct = RemoveContextsFrom(forward, sel, seqCtxt, false, out cellIndex); // if the column is empty, schedule it to be removed when the selection has changed if (seqCtxt.MembersRS.Count == 0) m_removeCol = seqCtxt; return reconstruct ? seqCtxt.Hvo : -1; } int idx = GetIndexToRemove(new ICmObject[] { ctxtOrVar }, sel, forward); if (idx > -1 && !IsLastVariable(ctxtOrVar)) { var seqCtxt = m_cache.ServiceLocator.GetInstance<IPhSequenceContextFactory>().Create(); Rule.InputOS.Insert(ctxtOrVar.IndexInOwner, seqCtxt); // if the column is empty, schedule it to be removed when the selection has changed m_removeCol = seqCtxt; UpdateMappings(ctxtOrVar, seqCtxt); ctxtOrVar.PreRemovalSideEffects(); Rule.InputOS.Remove(ctxtOrVar); return seqCtxt.Hvo; } return -1; } }
protected override int InsertVariable(SelectionHelper sel, out int cellIndex) { return InsertContext(m_cache.ServiceLocator.GetInstance<IPhVariableFactory>().Create(), sel, out cellIndex); }
protected override int InsertIndex(int index, SelectionHelper sel, out int cellIndex) { var copy = m_cache.ServiceLocator.GetInstance<IMoCopyFromInputFactory>().Create(); cellIndex = InsertIntoOutput(copy, sel); copy.ContentRA = Rule.InputOS[index - 1]; return MoAffixProcessTags.kflidOutput; }
/// ----------------------------------------------------------------------------------- /// <summary> /// Notifies the site that something about the selection has changed. /// </summary> /// <param name="prootb"></param> /// <param name="vwselNew">Selection</param> /// <remarks>When overriding you should call the base class first.</remarks> /// ----------------------------------------------------------------------------------- protected override void HandleSelectionChange(IVwRootBox prootb, IVwSelection vwselNew) { if (m_fInSelectionChanged) return; // don't need to reprocess our own changes. m_fInSelectionChanged = true; try { base.HandleSelectionChange(prootb, vwselNew); IVwSelection sel = vwselNew; if (!sel.IsValid) sel = prootb.Selection; if (sel == null) return; SelectionHelper helper = SelectionHelper.Create(sel, prootb.Site); // Check whether the selection is on the proper line of a multilingual // annotation and, if not, fix it. See LT-9421. if (m_cpropPrevForInsert > 0 && !sel.IsRange && (helper.GetNumberOfPreviousProps(SelectionHelper.SelLimitType.Anchor) == 0 || helper.GetNumberOfPreviousProps(SelectionHelper.SelLimitType.End) == 0)) { try { helper.SetNumberOfPreviousProps(SelectionHelper.SelLimitType.Anchor, m_cpropPrevForInsert); helper.SetNumberOfPreviousProps(SelectionHelper.SelLimitType.End, m_cpropPrevForInsert); helper.MakeBest(true); m_cpropPrevForInsert = -1; // we've used this the one time it was needed. } catch (Exception exc) { if (exc != null) Debug.WriteLine(String.Format( "InterlinDocChild.SelectionChanged() trying to display prompt in proper line of annotation: {0}", exc.Message)); } } int flid = helper.GetTextPropId(SelectionHelper.SelLimitType.Anchor); //If the flid is -2 and it is an insertion point then we may have encountered a case where the selection has landed at the boundary between our (possibly empty) //translation field and a literal string containing our magic Bidi marker character that helps keep things in the right order. //Sometimes AssocPrev gets set so that we read the (non-existent) flid of the literal string and miss the fact that on the other side //of the insertion point is the field we're looking for. The following code will attempt to make a selection that associates in //the other direction to see if the flid we want is on the other side. [LT-10568] if (flid == -2 && !sel.IsRange && sel.SelType == VwSelType.kstText) { helper.AssocPrev = !helper.AssocPrev; try { var newSel = helper.MakeRangeSelection(this.RootBox, false); helper = SelectionHelper.Create(newSel, this); flid = helper.GetTextPropId(SelectionHelper.SelLimitType.Anchor); } catch (COMException) { // Ignore HResult E_Fail caused by Extended Keys (PgUp/PgDown) in non-editable text (LT-13500) } } //Fixes LT-9884 Crash when clicking on the blank space in Text & Words--->Print view area! if (helper.LevelInfo.Length == 0) return; int hvo = helper.LevelInfo[0].hvo; // If the selection is in a freeform or literal translation that is empty, display the prompt. if (SelIsInEmptyTranslation(helper, flid, hvo) && !m_rootb.IsCompositionInProgress) { var handlerExtensions = Cache.ActionHandlerAccessor as IActionHandlerExtensions; if (handlerExtensions != null && handlerExtensions.IsUndoTaskActive) { // Wait to make the changes until the task (typically typing backspace) completes. m_setupPromptHelper = helper; m_setupPromptFlid = flid; handlerExtensions.DoAtEndOfPropChanged(handlerExtensions_PropChangedCompleted); } else { // No undo task to tag on the end of, so do it now. SetupTranslationPrompt(helper, flid); } } else if (flid != kTagUserPrompt) { m_vc.SetActiveFreeform(0, 0, 0, 0); // clear any current prompt. } // do not extend the selection for a user prompt if the user is currently entering an IME composition, // since we are about to switch the prompt to a real comment field else if (helper.GetTextPropId(SelectionHelper.SelLimitType.End) == SimpleRootSite.kTagUserPrompt && !m_rootb.IsCompositionInProgress) { // If the selection is entirely in a user prompt then extend the selection to cover the // entire prompt. This covers changes within the prompt, like clicking within it or continuing // a drag while making it. sel.ExtendToStringBoundaries(); EditingHelper.SetKeyboardForSelection(sel); } } finally { m_fInSelectionChanged = false; } }
private void SetupTranslationPrompt(SelectionHelper helper, int flid) { IVwSelection sel; m_vc.SetActiveFreeform(helper.LevelInfo[0].hvo, flid, helper.Ws, helper.NumberOfPreviousProps); helper.SetTextPropId(SelectionHelper.SelLimitType.Anchor, kTagUserPrompt); helper.SetTextPropId(SelectionHelper.SelLimitType.End, kTagUserPrompt); helper.NumberOfPreviousProps = 0; // only ever one occurrence of prompt. helper.SetNumberOfPreviousProps(SelectionHelper.SelLimitType.End, 0); // Even though the helper method is called MakeRangeSelection, it will initially make // an IP, because we haven't set any different offset for the end. // Since it's at the start of the prompt, we need it to associate with the prompt, // not the preceding (zero width direction-control) character. helper.AssocPrev = false; try { sel = helper.MakeRangeSelection(m_rootb, true); sel.ExtendToStringBoundaries(); } // Prevent the crash described in LT-9399 by swallowing the exception. catch (Exception exc) { if (exc != null) Debug.WriteLine(String.Format( "InterlinDocChild.SelectionChanged() trying to display prompt for empty translation: {0}", exc.Message)); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Makes a selection in the specified annotation (without scrolling the annotation in /// the view). /// </summary> /// <param name="vc">The notes view constructor</param> /// <param name="fScrollNearTop">if set to <c>true</c> scrolls the specified note to a /// position near the top of the view.</param> /// <param name="bookIndex">Index of the book.</param> /// <param name="iAnnotation">Index of the annotation.</param> /// <param name="iResponse">Index of the response (0 if setting the selection in one of /// the StJournalText fields rather than in a response.</param> /// <param name="noteTag">The tag indicating the field of the annotation where the /// selection is to be made.</param> /// <param name="rootSite">The root site.</param> /// <param name="fNoteIsExpanded">if <c>true</c> make a selection at the start and end so /// that the whole annotation can be scrolled into view. if set to <c>false</c> only /// make a selection at the start of the annotation.</param> /// ------------------------------------------------------------------------------------ internal void MakeSelectionInNote(TeNotesVc vc, bool fScrollNearTop, int bookIndex, int iAnnotation, int iResponse, ScrScriptureNote.ScrScriptureNoteTags noteTag, IVwRootSite rootSite, bool fNoteIsExpanded) { if (vc == null || vc.NotesSequenceHandler == null) return; SelectionHelper selHelper; if (fScrollNearTop) { // Make an un-installed selection at the top of the annotation in order to scroll the // annotation to the top of the view. selHelper = new SelectionHelper(); selHelper.NumberOfLevels = 2; selHelper.LevelInfo[0].cpropPrevious = 0; selHelper.LevelInfo[0].ich = -1; selHelper.LevelInfo[0].ihvo = iAnnotation; selHelper.LevelInfo[0].tag = vc.NotesSequenceHandler.Tag; selHelper.LevelInfo[0].ws = 0; selHelper.LevelInfo[1].cpropPrevious = 0; selHelper.LevelInfo[1].ich = -1; selHelper.LevelInfo[1].ihvo = bookIndex; selHelper.LevelInfo[1].tag = (int)Scripture.ScriptureTags.kflidBookAnnotations; selHelper.LevelInfo[1].ws = 0; selHelper.SetTextPropId(SelectionHelper.SelLimitType.Anchor, -2); selHelper.IchAnchor = 0; selHelper.AssocPrev = false; selHelper.NumberOfPreviousProps = 2; if (fNoteIsExpanded) { selHelper.SetSelection(rootSite, true, true, VwScrollSelOpts.kssoNearTop); } else { // Annotation is collapsed. Only attempt a selection at the start of it. selHelper.SetSelection(rootSite, true, true); return; } } else EnsureNoteIsVisible(vc, bookIndex, iAnnotation, rootSite); // Now make the real (installed) selection in the desired field of the annotation. bool fIsResponse = (noteTag == ScrScriptureNote.ScrScriptureNoteTags.kflidResponses); selHelper = new SelectionHelper(); selHelper.NumberOfLevels = 4; selHelper.LevelInfo[0].tag = (int)StText.StTextTags.kflidParagraphs; selHelper.LevelInfo[0].ihvo = 0; selHelper.LevelInfo[1].tag = (int)noteTag; selHelper.LevelInfo[1].ihvo = iResponse; selHelper.LevelInfo[1].cpropPrevious = (fIsResponse ? 0 : 1); selHelper.LevelInfo[2].tag = vc.NotesSequenceHandler.Tag; selHelper.LevelInfo[2].ihvo = iAnnotation; selHelper.LevelInfo[3].tag = (int)Scripture.ScriptureTags.kflidBookAnnotations; selHelper.LevelInfo[3].ihvo = bookIndex; selHelper.IchAnchor = 0; selHelper.AssocPrev = false; selHelper.SetSelection(rootSite, true, true); }
///------------------------------------------------------------------------------------- /// <summary> /// Load settings from the registry /// </summary> /// <param name="key">Location in the registry</param> ///------------------------------------------------------------------------------------- protected override void OnLoadSettings(RegistryKey key) { base.OnLoadSettings(key); object objTemp = key.GetValue(Name); if (objTemp != null) { // Restore the selection try { using (MemoryStream stream = new MemoryStream((byte[])objTemp)) { m_selectionHelper = (SelectionHelper)Persistence.DeserializeFromBinary(stream); } // Determine whether or not the FwMainWnd is a copy of another. bool fMainWndIsCopy = (TheMainWnd != null ? ((TeMainWnd)TheMainWnd).WindowIsCopy : false); if (m_selectionHelper != null) { // the selection helper book information needs to be converted to the // filter information ConvertBookTagAndIndex(m_selectionHelper, SelectionHelper.SelLimitType.Anchor); ConvertBookTagAndIndex(m_selectionHelper, SelectionHelper.SelLimitType.End); if (!fMainWndIsCopy && m_selectionHelper.NumberOfLevels > 2) { // Level where we find paragraph depends on type of content int paraLevel = 0; if (ContentType == StVc.ContentTypes.kctSimpleBT) paraLevel ++; else if (ContentType == StVc.ContentTypes.kctSegmentBT) paraLevel += 2; if (m_selectionHelper.LevelInfo[paraLevel].tag == StTextTags.kflidParagraphs) { if (ContentType != StVc.ContentTypes.kctSegmentBT) { // Set IP to the beginning of the section contents m_selectionHelper.IchAnchor = 0; m_selectionHelper.LevelInfo[paraLevel].ihvo = 0; m_selectionHelper.LevelInfo[paraLevel + 1].ihvo = 0; } // In the segment BT view we don't currently force to top of section. // Doing so is tricky because we need the first editable segment, not // just the first segment. } else { // We are in a picture. When in a picture the level // zero is not useful and seems to keep the views from // making the selection. SelectionHelper tempHelper = new SelectionHelper(); tempHelper.TextPropId = StTxtParaTags.kflidContents; tempHelper.NumberOfLevels = 4; for (int i = 0; i < tempHelper.NumberOfLevels - 1; i++) tempHelper.LevelInfo[i] = m_selectionHelper.LevelInfo[i + 1]; m_selectionHelper = tempHelper; } } m_selectionHelper.ReduceToIp(SelectionHelper.SelLimitType.Anchor); } } catch { // go on with life } // JohnT: I added this because, after some other changes I needed to make, // the selection was not getting restored, because the selection helper // was null during the only OnGotFocus call that happened (when not running // with a breakpoint in OnGotFocus!). It might be sufficient now to just // always do it here. However, it may also be that there are other // circumstances in which it won't work here, perhaps because the window's // handle has not yet been created. if (IsHandleCreated && (m_selectionHelper == null || m_selectionHelper.MakeBest(this, true) == null)) { try { m_rootb.MakeSimpleSel(true, true, false, true); } catch { // ignore any errors! This can happen if, for example, the view is empty. } } m_selectionHelper = null; } else { try { if (m_rootb != null) m_rootb.MakeSimpleSel(true, true, false, true); } catch { // ignore any errors! This can happen if, for example, the view is empty. } } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Makes the selection in in the Scripture reference of the specified annotation. /// </summary> /// <param name="vc">The vc.</param> /// <param name="bookIndex">Index of the book.</param> /// <param name="iAnnotation">Index of the annotation.</param> /// <param name="notesDataEntryView">The notes data entry view.</param> /// ------------------------------------------------------------------------------------ internal void MakeSelectionInNoteRef(TeNotesVc vc, int bookIndex, int iAnnotation, NotesDataEntryView notesDataEntryView) { EnsureNoteIsVisible(vc, bookIndex, iAnnotation, notesDataEntryView); SelectionHelper selHelper = new SelectionHelper(); selHelper.NumberOfLevels = 2; selHelper.LevelInfo[0].cpropPrevious = 0; selHelper.LevelInfo[0].ich = -1; selHelper.LevelInfo[0].ihvo = iAnnotation; selHelper.LevelInfo[0].tag = vc.NotesSequenceHandler.Tag; selHelper.LevelInfo[0].ws = 0; selHelper.LevelInfo[1].cpropPrevious = 0; selHelper.LevelInfo[1].ich = -1; selHelper.LevelInfo[1].ihvo = bookIndex; selHelper.LevelInfo[1].tag = (int)Scripture.ScriptureTags.kflidBookAnnotations; selHelper.LevelInfo[1].ws = 0; selHelper.IchAnchor = 0; selHelper.AssocPrev = false; selHelper.SetTextPropId(SelectionHelper.SelLimitType.Anchor, (int)CmBaseAnnotation.CmBaseAnnotationTags.kflidBeginRef); selHelper.SetSelection(notesDataEntryView, true, true, VwScrollSelOpts.kssoDefault); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Synchronizes the footnote view. /// </summary> /// <param name="helper">The helper.</param> /// ------------------------------------------------------------------------------------ private void SynchFootnoteView(SelectionHelper helper) { IStFootnote footnote = TeEditingHelper.FindFootnoteNearSelection(helper); if (footnote != null) { FwEditingHelper.IgnoreSelectionChanges = true; TheDraftViewWrapper.FootnoteView.ScrollToFootnote(footnote, false); FwEditingHelper.IgnoreSelectionChanges = false; } else { TheDraftViewWrapper.FootnoteView.ScrollToTop(); if (TheDraftViewWrapper.FootnoteView.EditingHelper.CurrentSelection == null) { try { TheDraftViewWrapper.FootnoteView.RootBox.MakeSimpleSel(true, true, false, true); } catch { // unable to make a selection } } } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Ensures the annotation is mostly visible by making an uninstalled selection /// toward the end of the modified date. /// </summary> /// ------------------------------------------------------------------------------------ internal void EnsureNoteIsVisible(TeNotesVc vc, int bookIndex, int iAnnotation, IVwRootSite notesDataEntryView) { SelectionHelper selHelper = new SelectionHelper(); selHelper.NumberOfLevels = 2; selHelper.LevelInfo[0].cpropPrevious = 0; selHelper.LevelInfo[0].ich = -1; selHelper.LevelInfo[0].ihvo = iAnnotation; selHelper.LevelInfo[0].tag = vc.NotesSequenceHandler.Tag; selHelper.LevelInfo[0].ws = 0; selHelper.LevelInfo[1].cpropPrevious = 0; selHelper.LevelInfo[1].ich = -1; selHelper.LevelInfo[1].ihvo = bookIndex; selHelper.LevelInfo[1].tag = (int)Scripture.ScriptureTags.kflidBookAnnotations; selHelper.LevelInfo[1].ws = 0; selHelper.AssocPrev = false; // Put the selection at the end of the shortest possible date value. It doesn't // have to be right at the end, but the closer it is, the more reliable it will // be that it is fully scrolled into view. selHelper.IchAnchor = 8; selHelper.SetTextPropId(SelectionHelper.SelLimitType.Anchor, (int)CmAnnotation.CmAnnotationTags.kflidDateModified); selHelper.SetSelection(notesDataEntryView, false, true, VwScrollSelOpts.kssoDefault); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Replace the filter book tag with a scrpiture books tag. This is done before /// persisting the selection because the filter tag is not valid across sessions. /// Also, any filtered book indices are replaced with real scripture book indices /// for the same reason. /// </summary> /// <param name="helper"></param> /// <param name="selType"></param> /// ------------------------------------------------------------------------------------ private void ReplaceBookTagAndIndex(SelectionHelper helper, SelectionHelper.SelLimitType selType) { SelLevInfo[] info = helper.GetLevelInfo(selType); int bookPos = info.Length - 1; if (info[bookPos].tag == BookFilter.Tag) { info[bookPos].tag = ScriptureTags.kflidScriptureBooks; info[bookPos].ihvo = BookFilter.GetUnfilteredIndex(info[bookPos].ihvo); helper.SetLevelInfo(selType, info); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// If we need to make a selection, but we can't because edits haven't been updated in /// the view, this method requests creation of a selection after the unit of work is /// complete. It will also scroll the selection into view. /// Derived classes should implement this if they have any hope of supporting multi- /// paragraph editing. /// </summary> /// <param name="helper">The selection to restore</param> /// ------------------------------------------------------------------------------------ public void RequestVisibleSelectionAtEndOfUow(SelectionHelper helper) { // Creating one hooks it up; it will free itself when invoked. new RequestSelectionByHelper((IActionHandlerExtensions)m_cache.ActionHandlerAccessor, helper); // We don't want to continue using the old, out-of-date selection. if (helper.RootSite != null && helper.RootSite.RootBox != null) helper.RootSite.RootBox.DestroySelection(); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Find and select the previous translation with a given state /// </summary> /// <param name="selection">The selection where to start the search. /// NOTE: The selection must have all of the info set in the LevelInfo (hvo, ihvo)</param> /// <param name="searchStatus">Back translation status to search for</param> /// ------------------------------------------------------------------------------------ private void MoveToPrevTranslation(SelectionHelper selection, BackTranslationStatus searchStatus) { SelLevInfo bookInfo; SelLevInfo paraInfo; SelLevInfo sectionInfo; bool fFoundBookLevel = selection.GetLevelInfoForTag(BookFilter.Tag, out bookInfo); bool fFoundSectionLevel = selection.GetLevelInfoForTag( ScrBookTags.kflidSections, out sectionInfo); int secLev = selection.GetLevelForTag(ScrBookTags.kflidSections); bool fFoundParaLevel = selection.GetLevelInfoForTag( StTextTags.kflidParagraphs, out paraInfo); if (!fFoundBookLevel || !fFoundParaLevel) return; // Look through all the books in the book filter int bookStartIndex = bookInfo.ihvo; int sectionStartIndex = -1; int sectionTag = ScrSectionTags.kflidContent; int paraStartIndex = paraInfo.ihvo - 1; int paraIndex; if (fFoundSectionLevel) { // start with current section sectionStartIndex = sectionInfo.ihvo; sectionTag = selection.LevelInfo[secLev - 1].tag; } else { // no section, so this must be the title - Look through the title paragraphs IScrBook checkBook = BookFilter.GetBook(bookStartIndex); paraIndex = FindPrevTranslationInText(checkBook.TitleOA, searchStatus, paraStartIndex); if (paraIndex >= 0) { // select the title paragraph SetInsertionPoint(ScrBookTags.kflidTitle, bookStartIndex, 0, paraIndex); return; } // continue the search with the previous book bookStartIndex--; paraStartIndex = -2; } for (int bookIndex = bookStartIndex; bookIndex >= 0 ; bookIndex--) { IScrBook checkBook = BookFilter.GetBook(bookIndex); if (sectionStartIndex == -1) { sectionStartIndex = checkBook.SectionsOS.Count - 1; sectionTag = ScrSectionTags.kflidContent; } // Look through the sections in reverse order. for (int sectionIndex = sectionStartIndex; sectionIndex >= 0; sectionIndex--) { IScrSection checkSection = checkBook.SectionsOS[sectionIndex]; if (paraStartIndex == -2) { paraStartIndex = checkSection.ContentOA.ParagraphsOS.Count - 1; sectionTag = ScrSectionTags.kflidContent; } // Look in the paragraphs (could be either content or heading) IStText text = (sectionTag == ScrSectionTags.kflidHeading) ? checkSection.HeadingOA : checkSection.ContentOA; paraIndex = FindPrevTranslationInText(text, searchStatus, paraStartIndex); if (paraIndex >= 0) { // select the paragraph SetInsertionPoint(sectionTag, bookIndex, sectionIndex, paraIndex); return; } // Look in the heading paragraphs, if we haven't already if (sectionTag == ScrSectionTags.kflidContent) { sectionTag = ScrSectionTags.kflidHeading; int startHeadPara = checkSection.HeadingOA.ParagraphsOS.Count - 1; paraIndex = FindPrevTranslationInText(checkSection.HeadingOA, searchStatus, startHeadPara); if (paraIndex >= 0) { // select the heading paragraph SetInsertionPoint(sectionTag, bookIndex, sectionIndex, paraIndex); return; } } paraStartIndex = -2; } sectionStartIndex = -1; // Look through the title paragraphs int startTitlePara = checkBook.TitleOA.ParagraphsOS.Count - 1; paraIndex = FindPrevTranslationInText(checkBook.TitleOA, searchStatus, startTitlePara); if (paraIndex >= 0) { // select the title paragraph SetInsertionPoint(ScrBookTags.kflidTitle, bookIndex, 0, paraIndex); return; } } }
internal UndoRedoTagTextTaskHelper(InterlinTaggingChild itc, string undo, string redo, SelectionHelper originalSelectionInfo) : base(itc.Cache, undo, redo) { m_itc = itc; m_originalSelectionInfo = originalSelectionInfo; // add the undo action first, since this will be the last action undone. AddAction(new UndoRedoTextTag(itc, false, m_originalSelectionInfo)); }
/// ----------------------------------------------------------------------------------- /// <summary> /// Call MouseUp on the rootbox /// </summary> /// <param name="pt"></param> /// <param name="rcSrcRoot"></param> /// <param name="rcDstRoot"></param> /// ----------------------------------------------------------------------------------- protected override void CallMouseUp(Point pt, Rectangle rcSrcRoot, Rectangle rcDstRoot) { base.CallMouseUp(pt, rcSrcRoot, rcDstRoot); // if a picture was selected on mouse down but not on mouse up, // make sure the selection is still cleared. if (m_pictureSelected) { if (m_selectionHelper == null) m_selectionHelper = EditingHelper.CurrentSelection; if (m_selectionHelper != null) m_selectionHelper.SetSelection(this, true, false); m_selectionHelper = null; m_pictureSelected = false; m_selectedTransHvo = 0; } }
/// <summary> /// /// </summary> /// <param name="interlinDoc"></param> /// <param name="fForRedo">true for adding a redo action, false for adding undo action</param> internal UndoRedoTextTag(InterlinTaggingChild interlinDoc, bool fForRedo, SelectionHelper originalSelectionInfo) { m_fForRedo = fForRedo; m_interlinDoc = interlinDoc; m_cache = interlinDoc.Cache; m_originalSelection = originalSelectionInfo; m_affectedXfics = m_interlinDoc.GetAllXficsPossiblyAffectedByTagging(m_interlinDoc.SelectedWfics); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Refresh highlighted text in diff view. /// </summary> /// <param name="selHelper">selection used to get hvo of paragraph to notify for /// refreshing diff highlight</param> /// ------------------------------------------------------------------------------------ private void RefreshDiffViewHighlighting(SelectionHelper selHelper) { if (selHelper != null) { int paraIndex = selHelper.GetLevelForTag((int)StText.StTextTags.kflidParagraphs); NotifyParagraph(selHelper.LevelInfo[paraIndex].hvo); } }
public void ScrollFootnotePane_OnDraftViewSelectionChange() { // make sure the option is set to enable synchronous scrolling bool saveOldSynchSetting = Options.FootnoteSynchronousScrollingSetting; Options.FootnoteSynchronousScrollingSetting = true; // Show the footnote pane m_firstMainWnd.TheDraftViewWrapper.ShowFootnoteView(null); // Set the insertion point into James, just after it's 10th footnote. m_firstMainWnd.TheDraftView.SetInsertionPoint(1, 8, 1, 402, false); Application.DoEvents(); // Set up a selection pointing to tenth footnote in footnote pane SelectionHelper selHelper = new SelectionHelper(); selHelper.AssocPrev = false; selHelper.NumberOfLevels = 3; selHelper.LevelInfo[0].tag = StTextTags.kflidParagraphs; selHelper.LevelInfo[0].ihvo = 0; selHelper.LevelInfo[1].tag = ScrBookTags.kflidFootnotes; selHelper.LevelInfo[1].ihvo = 9; selHelper.LevelInfo[2].tag = m_firstDraftView.BookFilter.Tag; selHelper.LevelInfo[2].ihvo = 1; //James selHelper.IchAnchor = 0; selHelper.TextPropId = StTxtParaTags.kflidContents; // Verify that our desired footnote selection is visible. FootnoteView fnView = m_firstMainWnd.TheDraftViewWrapper.FootnoteView; selHelper.SetSelection(fnView, true, false); // not forced to be visible Assert.IsTrue(fnView.IsSelectionVisible(selHelper.Selection)); // reset the synchronous scrolling setting Options.FootnoteSynchronousScrollingSetting = saveOldSynchSetting; }