/// <summary> /// Handle a selection change by growing it to a word (unless the new selection IS /// the one we're growing to a word). /// </summary> /// <param name="prootb"></param> /// <param name="vwselNew"></param> public override void SelectionChanged(IVwRootBox prootb, IVwSelection vwselNew) { CheckDisposed(); base.SelectionChanged(prootb, vwselNew); if (!m_fInSelChange) { m_fInSelChange = true; try { if (!vwselNew.IsRange) { vwselNew.GrowToWord().Install(); } } finally { m_fInSelChange = false; } } if (SelChanged != null) { SelChanged(this, new EventArgs()); } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Handle a selection change by growing it to a word (unless the new selection IS /// the one we're growing to a word). /// </summary> /// ------------------------------------------------------------------------------------ private void HandleSelectionChange(object sender, VwSelectionArgs args) { CheckDisposed(); IVwRootBox rootb = args.RootBox; IVwSelection vwselNew = args.Selection; Debug.Assert(vwselNew != null); if (!m_fInSelChange) { m_fInSelChange = true; try { if (!vwselNew.IsRange) { vwselNew.GrowToWord().Install(); } } finally { m_fInSelChange = false; } } if (SelChanged != null) { SelChanged(this, new EventArgs()); } }
public void FindInDictionary(IOleDbEncap ode, IFwMetaDataCache mdc, IVwOleDbDa oleDbAccess, IVwSelection sel) { using (FdoCache cache = new FdoCache(ode, mdc, oleDbAccess)) { if (sel == null) { return; } IVwSelection sel2 = sel.EndPoint(false); if (sel2 == null) { return; } IVwSelection sel3 = sel2.GrowToWord(); if (sel3 == null) { return; } ITsString tss; int ichMin, ichLim, hvo, tag, ws; bool fAssocPrev; sel3.TextSelInfo(false, out tss, out ichMin, out fAssocPrev, out hvo, out tag, out ws); sel3.TextSelInfo(true, out tss, out ichLim, out fAssocPrev, out hvo, out tag, out ws); // TODO (TimS): need to supply help information (last 2 params) LexEntryUi.DisplayOrCreateEntry(cache, hvo, tag, ws, ichMin, ichLim, null, null, null, string.Empty); return; } }
/// <summary> /// Handle a right mouse up, invoking an appropriate context menu. /// </summary> /// <param name="pt"></param> /// <param name="rcSrcRoot"></param> /// <param name="rcDstRoot"></param> /// <returns></returns> protected override bool DoContextMenu(IVwSelection sel, Point pt, Rectangle rcSrcRoot, Rectangle rcDstRoot) { // Allow base method to handle spell check problems, if any. if (base.DoContextMenu(sel, pt, rcSrcRoot, rcDstRoot)) { return(true); } XWindow mainWind = this.ParentForm as XWindow; if (mainWind == null || sel == null) { return(false); } ITsString tssWord; sel.GrowToWord().GetSelectionString(out tssWord, " "); TemporaryColleagueParameter tempColleague = null; if (tssWord != null && !string.IsNullOrEmpty(tssWord.Text)) { // We can have a WfiWordformUi as an additional colleague to handle more menu items. // The temporaray colleague handles adding and removing it. int form = WfiWordform.FindOrCreateWordform(Cache, tssWord, true); CmObjectUi ui = CmObjectUi.MakeUi(Cache, form); ui.Mediator = m_mediator; tempColleague = new TemporaryColleagueParameter(m_mediator, ui, false); } mainWind.ShowContextMenu("mnuIText-RawText", new Point(Cursor.Position.X, Cursor.Position.Y), tempColleague, null); return(true); }
/// ------------------------------------------------------------------------------------ /// <summary> /// Assuming the selection can be expanded to a word and a corresponding LexEntry can /// be found, show the related words dialog with the words related to the selected one. /// </summary> /// <param name="cache">The cache.</param> /// <param name="sel">The sel.</param> /// <param name="owner">The owner.</param> /// <param name="mediator"></param> /// <param name="propertyTable"></param> /// <param name="helpProvider"></param> /// <param name="helpFileKey"></param> /// ------------------------------------------------------------------------------------ public static void DisplayRelatedEntries(LcmCache cache, IVwSelection sel, IWin32Window owner, Mediator mediator, PropertyTable propertyTable, IHelpTopicProvider helpProvider, string helpFileKey) { if (sel == null) { return; } IVwSelection sel2 = sel.EndPoint(false); if (sel2 == null) { return; } IVwSelection sel3 = sel2.GrowToWord(); if (sel3 == null) { return; } ITsString tss; int ichMin, ichLim, hvo, tag, ws; bool fAssocPrev; sel3.TextSelInfo(false, out tss, out ichMin, out fAssocPrev, out hvo, out tag, out ws); sel3.TextSelInfo(true, out tss, out ichLim, out fAssocPrev, out hvo, out tag, out ws); if (tss.Text == null) { return; } ITsString tssWf = tss.GetSubstring(ichMin, ichLim); using (LexEntryUi leui = FindEntryForWordform(cache, tssWf)) { // This doesn't work as well (unless we do a commit) because it may not see current typing. //LexEntryUi leui = LexEntryUi.FindEntryForWordform(cache, hvo, tag, ichMin, ichLim); if (leui == null) { if (tssWf != null && tssWf.Length > 0) { RelatedWords.ShowNotInDictMessage(owner); } return; } int hvoEntry = leui.Object.Hvo; int[] domains; int[] lexrels; IVwCacheDa cdaTemp; if (!RelatedWords.LoadDomainAndRelationInfo(cache, hvoEntry, out domains, out lexrels, out cdaTemp, owner)) { return; } IVwStylesheet styleSheet = GetStyleSheet(cache, propertyTable); using (RelatedWords rw = new RelatedWords(cache, sel3, hvoEntry, domains, lexrels, cdaTemp, styleSheet, mediator, false)) { rw.ShowDialog(owner); } } }
/// <summary> /// Return a word selection based on the beginning of the current selection. /// Here the "beginning" of the selection is the offset corresponding to word order, /// not the selection anchor. /// </summary> /// <returns>null if we couldn't handle the selection</returns> static public IVwSelection SelectionBeginningGrowToWord(IVwSelection sel) { if (sel == null) { return(null); } // REVISIT (EricP) Need to check if Ws is IsRightToLeft? IVwSelection sel2 = sel.EndBeforeAnchor ? sel.EndPoint(true) : sel.EndPoint(false); if (sel2 == null) { return(null); } IVwSelection sel3 = sel2.GrowToWord(); return(sel3); }
public void PasteSelectionSpanningTwoSections() { StText title = m_scrInMemoryCache.AddTitleToMockedBook(m_gen.Hvo, "paragraph with main title style"); m_hvoRoot = title.Hvo; // The IntroParagraph style in a book title would be illegal in TE, but we're not TE. // We're just a test that needs two paragraphs with different styles. StTxtPara titlePara2 = m_scrInMemoryCache.AddParaToMockedText(m_hvoRoot, ScrStyleNames.IntroParagraph); m_scrInMemoryCache.AddRunToMockedPara(titlePara2, "paragraph with different style", m_inMemoryCache.Cache.DefaultVernWs); ShowForm(); // Make a selection from the top of the view to the bottom. IVwSelection sel0 = m_basicView.RootBox.MakeSimpleSel(true, false, false, false); IVwSelection sel1 = m_basicView.RootBox.MakeSimpleSel(false, false, false, false); m_basicView.RootBox.MakeRangeSelection(sel0, sel1, true); // Copy the selection and then paste it over the existing selection. // This is an illegal paste, so the paste will fail. // However, we expect the contents to remain intact. Assert.IsTrue(m_basicView.EditingHelper.CopySelection()); // Select just a single word in the text to confirm the paste operation better. sel0.GrowToWord(); m_basicView.m_OnInsertDiffParasResponse = VwInsertDiffParaResponse.kidprFail; m_inMemoryCache.MockActionHandler.Strict = true; m_inMemoryCache.MockActionHandler.Expect("BeginUndoTask", "&Undo Paste", "&Redo Paste"); // We don't really CARE whether we get these additional Begin/EndUndoTask calls, but we do, so we have to 'expect' them. // There is only one EndUndoTask because we intentionally make the paste fail (by having the mock return kidprFail). m_inMemoryCache.MockActionHandler.Expect("BeginUndoTask", "&Undo Typing", "&Redo Typing"); m_inMemoryCache.MockActionHandler.Expect("EndUndoTask"); //m_inMemoryCache.MockActionHandler.Expect("AddAction", new IsAnything()); m_inMemoryCache.MockActionHandler.Expect("Rollback", 0); m_basicView.EditingHelper.PasteClipboard(false); m_inMemoryCache.MockActionHandler.Verify(); // GrowToWord causes a Char Property Engine to be created, and somehow the test runner fails if we don't // shut the factory down. m_inMemoryCache.Cache.LanguageWritingSystemFactoryAccessor.Shutdown(); }
private LexEntryUi GetSelWord() { IVwSelection sel = m_view.RootBox.Selection; if (sel == null) { return(null); } IVwSelection sel2 = sel.EndPoint(false); if (sel2 == null) { return(null); } IVwSelection sel3 = sel2.GrowToWord(); if (sel3 == null) { return(null); } ITsString tss; int ichMin, ichLim, hvo, tag, ws; bool fAssocPrev; sel3.TextSelInfo(false, out tss, out ichMin, out fAssocPrev, out hvo, out tag, out ws); sel3.TextSelInfo(true, out tss, out ichLim, out fAssocPrev, out hvo, out tag, out ws); ITsString tssWf = (m_cdaTemp as ISilDataAccess).get_StringProp(hvo, tag); if (tssWf == null || tssWf.Length == 0) { return(null); } // Ignore what part of it is selected...we want the entry whose whole citation form // the selection is part of. //string wf = tssWf.Text.Substring(ichMin, ichLim - ichMin); return(LexEntryUi.FindEntryForWordform(m_cache, tssWf)); }
/// <summary> /// Returns true if there's anything to select. This is needed so that the toolbar /// button is disabled when there's nothing to select and look up. Otherwise, crashes /// can result when it's clicked but there's nothing there to process! It's misleading /// to the user if nothing else. It would be nice if the processing could be minimized, /// but this seems to be minimal. /// </summary> /// <returns>true</returns> public bool LexiconLookupEnabled() { CheckDisposed(); if (m_rootb == null) { return(false); } IVwSelection sel = m_rootb.Selection; if (sel == null) { return(false); } IVwSelection sel2 = sel.EndPoint(false); if (sel2 == null) { return(false); } IVwSelection sel3 = sel2.GrowToWord(); if (sel3 == null) { return(false); } ITsString tss; int ichLim, hvo, tag, ws; bool fAssocPrev; sel3.TextSelInfo(true, out tss, out ichLim, out fAssocPrev, out hvo, out tag, out ws); if (ichLim == 0) { return(false); } // We're not disqualified, so we must be enabled! return(true); }
/// <summary> /// Handle a selection change by growing it to a word (unless the new selection IS /// the one we're growing to a word). /// </summary> /// <param name="prootb"></param> /// <param name="vwselNew"></param> public override void SelectionChanged(IVwRootBox prootb, IVwSelection vwselNew) { CheckDisposed(); base.SelectionChanged (prootb, vwselNew); if (!m_fInSelChange) { m_fInSelChange = true; try { if (!vwselNew.IsRange) { vwselNew.GrowToWord().Install(); } } finally { m_fInSelChange = false; } } if (SelChanged != null) SelChanged(this, new EventArgs()); }
/// <summary> /// If we are in ReadOnlySelect mode, intercept the click, and select the appropriate row /// without installing a normal selection. /// </summary> /// <param name="e"></param> protected override void OnMouseUp(MouseEventArgs e) { //If XmlBrouseView did not receive a mouse down event then we do not want to //do anything on the mouseUp because the mouseUp would have come from clicking //somewhere else. LT-8939 if (!m_fMouseUpEnabled) { return; } try { if (m_selectedIndex == -1) { return; // Can't do much in an empty list, so quit. } m_fHandlingMouseUp = true; #pragma warning disable 219 int oldSelectedIndex = m_selectedIndex; #pragma warning restore 219 // Note all the stuff we might want to know about what was clicked that we will // use later. We want to get this now before anything changes, because there can // be scrolling effects from converting dummy objects to real. IVwSelection vwsel = MakeSelectionAt(e); int newSelectedIndex = GetRowIndexFromSelection(vwsel, true); // If we're changing records, we need to do some tricks to keep the selection in the place // clicked and the focus here. Save the information we will need. SelectionHelper clickSel = null; if (newSelectedIndex != SelectedIndex && vwsel != null && SelectionHelper.IsEditable(vwsel)) { clickSel = SelectionHelper.Create(vwsel, this); } ITsString tssWord = null; // word clicked for click copy ITsString tssSource = null; // whole source string of clicked cell for click copy int hvoNewSelRow = 0; // hvo of new selected row (only for click copy) int ichStart = 0; // of tssWord in tssSource if (ClickCopy != null && e.Button == MouseButtons.Left && newSelectedIndex >= 0) { if (vwsel != null && vwsel.SelType == VwSelType.kstText) { int icol = vwsel.get_BoxIndex(false, 3); if (icol != Vc.OverrideAllowEditColumn + 1) { IVwSelection vwSelWord = vwsel.GrowToWord(); // GrowToWord() can return a null -- see LT-9163 and LT-9349. if (vwSelWord != null) { vwSelWord.GetSelectionString(out tssWord, " "); tssWord = StripTrailingNewLine(tssWord); hvoNewSelRow = m_sda.get_VecItem(m_hvoRoot, m_fakeFlid, newSelectedIndex); int hvoObj, tag, ws; bool fAssocPrev; vwSelWord.TextSelInfo(false, out tssSource, out ichStart, out fAssocPrev, out hvoObj, out tag, out ws); } } } } // We need to manually change the index for ReadOnly views. // SimpleRootSite delegates RightMouseClickEvent to our RecordBrowseView parent, // which also makes the selection for us.. if (ReadOnlySelect && e.Button != MouseButtons.Right) { if (this.m_xbvvc.HasSelectColumn && e.X < m_xbvvc.SelectColumnWidth) { base.OnMouseUp(e); // allows check box to operate. } } else { // If we leave this set, the base method call's side effects like updating the WS combo // don't happen. m_fHandlingMouseUp = false; base.OnMouseUp(e); // normal behavior. m_fHandlingMouseUp = true; } SetSelectedIndex(newSelectedIndex); if (tssWord != null) { // We're doing click copies; generate an event. // Do this AFTER other actions which may change the current line. ClickCopy(this, new ClickCopyEventArgs(tssWord, hvoNewSelRow, tssSource, ichStart)); } if (clickSel != null) { IVwSelection finalSel = null; // There seem to be some cases where the selection helper can't restore the selection. // One that came up in FWR-3666 was clicking on a check box. // If we can't re-establish an editiable selection just let the default behavior continue. try { finalSel = clickSel.MakeRangeSelection(RootBox, false); } catch (Exception) { } if (finalSel != null && SelectionHelper.IsEditable(finalSel)) { finalSel.Install(); FocusMe(); } } } finally { m_fHandlingMouseUp = false; m_fMouseUpEnabled = false; } }
/// ------------------------------------------------------------------------------------ /// <summary> /// Get a list of suggested corrections if the selection is a spelling or similar error. /// Returns null if there is no problem at the selection location. /// Note that it may also return an empty list; this has a distinct meaning, namely, /// that there IS a problem, but we have no useful suggestions for what to change it to. /// nonSpellingError is set true when the error is not simply a mis-spelled word in a /// single writing system; currently this should disable or hide the commands to add /// the word to the dictionary or change multiple occurrences. /// The input arguments indicate where the user clicked and allow us to find the /// text he might be trying to correct. The other output arguments indicate which WS /// (wasAlt -- 0 for simple string) of which property (tag) of which object (hvoObj) /// is affected by the change, the ws of the mis-spelled word, and the corresponding /// spelling engine. Much of this information is already known to the /// SpellCorrectMenuItems returned, but some clients use it in creating other menu options. /// </summary> /// ------------------------------------------------------------------------------------ public ICollection <SpellCorrectMenuItem> GetSuggestions(Point mousePos, SimpleRootSite rootsite, out int hvoObj, out int tag, out int wsAlt, out int wsText, out string word, out ISpellEngine dict, out bool nonSpellingError) { hvoObj = tag = wsAlt = wsText = 0; // make compiler happy for early returns word = null; dict = null; nonSpellingError = true; IVwRootBox rootb = rootsite != null ? rootsite.RootBox : null; if (rootb == null) { return(null); } // Get a selection at the indicated point. IVwSelection sel = rootsite.GetSelectionAtPoint(mousePos, false); // Get the selected word and verify that it is a single run within a single // editable string. if (sel != null) { sel = sel.GrowToWord(); } if (sel == null || !sel.IsRange || sel.SelType != VwSelType.kstText || !SelectionHelper.IsEditable(sel)) { return(null); } ITsString tss; bool fAssocPrev; int ichAnchor; sel.TextSelInfo(false, out tss, out ichAnchor, out fAssocPrev, out hvoObj, out tag, out wsAlt); int ichEnd, hvoObjE, tagE, wsE; sel.TextSelInfo(true, out tss, out ichEnd, out fAssocPrev, out hvoObjE, out tagE, out wsE); if (hvoObj != hvoObjE || tag != tagE || wsAlt != wsE) { return(null); } int ichMin = Math.Min(ichEnd, ichAnchor); int ichLim = Math.Max(ichEnd, ichAnchor); ILgWritingSystemFactory wsf = rootsite.RootBox.DataAccess.WritingSystemFactory; // May need to enlarge the word beyond what GrowToWord does, if there is adjacent wordforming material. int ichMinAdjust = AdjustWordBoundary(wsf, tss, false, ichMin, 0) + 1; // further expanded start of word. int ichLimAdjust = AdjustWordBoundary(wsf, tss, true, ichLim - 1, tss.Length); // further expanded lim of word. // From the ends we can strip stuff with different spell-checking properties. IVwStylesheet styles = rootsite.RootBox.Stylesheet; int spellProps = SpellCheckProps(tss, ichMin, styles); while (ichMinAdjust < ichMin && SpellCheckProps(tss, ichMinAdjust, styles) != spellProps) { ichMinAdjust++; } while (ichLimAdjust > ichLim && SpellCheckProps(tss, ichLimAdjust - 1, styles) != spellProps) { ichLimAdjust--; } ichMin = ichMinAdjust; ichLim = ichLimAdjust; // Now we have the specific range we will check. Get the actual string. ITsStrBldr bldr = tss.GetBldr(); if (ichLim < bldr.Length) { bldr.ReplaceTsString(ichLim, bldr.Length, null); } if (ichMin > 0) { bldr.ReplaceTsString(0, ichMin, null); } ITsString tssWord = bldr.GetString(); // See whether we need the special blue underline, which is used mainly for adjacent words in different writing systems. List <int> wss = TsStringUtils.GetWritingSystems(tssWord); if (wss.Count > 1) { return(MakeWssSuggestions(tssWord, wss, rootb, hvoObj, tag, wsAlt, ichMin, ichLim)); } ITsString keepOrcs; // holds any ORCs we found in the original word that we need to keep rather than reporting. IList <SpellCorrectMenuItem> result = MakeEmbeddedNscSuggestion(ref tssWord, styles, rootb, hvoObj, tag, wsAlt, ichMin, ichLim, out keepOrcs); if (result.Count > 0) { return(result); } // Determine whether it is a spelling problem. wsText = TsStringUtils.GetWsOfRun(tssWord, 0); dict = SpellingHelper.GetSpellChecker(wsText, wsf); if (dict == null) { return(null); } word = tssWord.get_NormalizedForm(FwNormalizationMode.knmNFC).Text; if (word == null) { return(null); // don't think this can happen, but... } if (dict.Check(word)) { return(null); // not mis-spelled. } // Get suggestions. Make sure to return an empty collection rather than null, even if no suggestions, // to indicate an error. ICollection <string> suggestions = dict.Suggest(word); foreach (string suggest in suggestions) { ITsString replacement = TsStringUtils.MakeString(suggest, wsText); if (keepOrcs != null) { ITsStrBldr bldrRep = keepOrcs.GetBldr(); bldrRep.ReplaceTsString(0, 0, replacement); replacement = bldrRep.GetString(); } result.Add(new SpellCorrectMenuItem(rootb, hvoObj, tag, wsAlt, ichMin, ichLim, suggest, replacement)); } nonSpellingError = false; // it IS a spelling problem. return(result); }
/// <summary> /// Handle a right mouse up, invoking an appropriate context menu. /// </summary> /// <param name="pt"></param> /// <param name="rcSrcRoot"></param> /// <param name="rcDstRoot"></param> /// <returns></returns> protected override bool DoContextMenu(IVwSelection sel, Point pt, Rectangle rcSrcRoot, Rectangle rcDstRoot) { // Allow base method to handle spell check problems, if any. if (base.DoContextMenu(sel, pt, rcSrcRoot, rcDstRoot)) return true; XWindow mainWind = this.ParentForm as XWindow; if (mainWind == null || sel == null) return false; ITsString tssWord; sel.GrowToWord().GetSelectionString(out tssWord, " "); TemporaryColleagueParameter tempColleague = null; if (tssWord != null && !string.IsNullOrEmpty(tssWord.Text)) { // We can have a WfiWordformUi as an additional colleague to handle more menu items. // The temporaray colleague handles adding and removing it. int form = WfiWordform.FindOrCreateWordform(Cache, tssWord, true); CmObjectUi ui = CmObjectUi.MakeUi(Cache, form); ui.Mediator = m_mediator; tempColleague = new TemporaryColleagueParameter(m_mediator, ui, false); } mainWind.ShowContextMenu("mnuIText-RawText", new Point(Cursor.Position.X, Cursor.Position.Y), tempColleague, null); return true; }