/// <summary> /// Recursive function to scan the parsetree in a depth first manner. /// nodelist contains the current map from _old_ nodenames to nodes. it is used to update node references /// </summary> private static void ScanTree(TikzContainerParseItem tc, Dictionary <string, Tikz_Node> nodelist, Tikz_Picture tp) { foreach (var tpi in tc.Children) { if (tpi is Tikz_Node) { Tikz_Node tn = tpi as Tikz_Node; if (tn.name != null && tn.name.Trim() != "") { string name = CleanName(tn.name.Trim()); // remember the node with its old name (all coordinates referring to this name henceforth will be changed to the new name nodelist[name] = tn; if (tp.nodelist.ContainsKey(name)) { // we have to change the name tn.name = UniquefyName(name, tp); tn.UpdateText(); } tn.RegisterNodeAndStyleRefs(); } } else if (tpi is Tikz_Coord) { Tikz_Coord tco = tpi as Tikz_Coord; if (tco.type == Tikz_CoordType.Named) { string nameref = CleanName(tco.nameref); if (nodelist.ContainsKey(nameref)) { if (CleanName(nodelist[nameref].name) != nameref) { tco.nameref = CleanName(nodelist[nameref].name); tco.UpdateText(); } } } } else if (tpi is TikzContainerParseItem) { ScanTree(tpi as TikzContainerParseItem, nodelist, tp); } } }
public void ParseTest2() { string code = @"\begin{tikzpicture} \draw (1,2) -- (3,3); \end{tikzpicture} "; Tikz_ParseTree actual = TikzParser.Parse(code); Tikz_Picture tp = actual.GetTikzPicture(); Assert.AreEqual(0, tp.StartPosition()); Tikz_Path tpa = tp.Children.Find(tpi => tpi is Tikz_Path) as Tikz_Path; Assert.AreEqual(21, tpa.StartPosition()); Tikz_Coord tc = tpa.Children.Find(tpi => tpi is Tikz_Coord) as Tikz_Coord; Assert.AreEqual(1, tc.uX.number); Assert.AreEqual(2, tc.uY.number); Assert.AreEqual(27, tc.StartPosition()); }
static bool FillItem(TikzContainerParseItem item, CommonTree t, CommonTokenStream tokens) { int curToken = t.TokenStartIndex; if (item is Tikz_ParseTree) { curToken = 0; // for root, start at the beginning } if (t.Children == null) { return(false); } foreach (CommonTree childt in t.Children) { addSomething(item, tokens, curToken, childt.TokenStartIndex - 1); switch (childt.Type) { case simpletikzParser.IM_PICTURE: Tikz_Picture tp = new Tikz_Picture(); FillItem(tp, childt, tokens); item.AddChild(tp); break; case simpletikzParser.IM_STARTTAG: item.starttag = getTokensString(tokens, childt.TokenStartIndex, childt.TokenStopIndex); break; case simpletikzParser.IM_ENDTAG: item.endtag = getTokensString(tokens, childt.TokenStartIndex, childt.TokenStopIndex); break; case simpletikzParser.IM_PATH: Tikz_Path tpath = new Tikz_Path(); FillItem(tpath, childt, tokens); item.AddChild(tpath); break; case simpletikzParser.IM_SCOPE: Tikz_Scope tscope = new Tikz_Scope(); FillItem(tscope, childt, tokens); item.AddChild(tscope); break; case simpletikzParser.IM_COORD: Tikz_Coord tc = Tikz_Coord.FromCommonTree(childt, tokens); tc.text = getTokensString(tokens, childt); item.AddChild(tc); break; case simpletikzParser.IM_ARC: Tikz_Arc ta = Tikz_Arc.FromCommonTree(childt, tokens); ta.text = getTokensString(tokens, childt); item.AddChild(ta); break; case simpletikzParser.IM_NODE: Tikz_Node tn = Tikz_Node.FromCommonTree(childt, tokens); tn.text = getTokensString(tokens, childt); item.AddChild(tn); break; case simpletikzParser.IM_OPTION_KV: case simpletikzParser.IM_OPTION_STYLE: Tikz_Option topt = Tikz_Option.FromCommonTree(childt, tokens); if (topt == null) { break; } //topt.text = getTokensString(tokens, childt); String s = getTokensString(tokens, childt); topt.text = s; item.AddChild(topt); break; case simpletikzParser.IM_OPTIONS: //Tikz_Options to = Tikz_Options.FromCommonTree(childt); Tikz_Options to = new Tikz_Options(); FillItem(to, childt, tokens); item.AddChild(to); //to.text = getTokensString(tokens, childt); //item.AddChild(tn); if (item.options == null) { // determine whether option belongs to the item (e.g. \draw [this belongs to draw] blabla [thisnot]) // i.e., the scope of the options is the whole item's body // this is hacky if (item.Children.Count == 1 || (item.Children.Count == 2 && (item.Children[0] is Tikz_Something) && item.Children[0].ToString().Trim() == "")) { item.options = to; } } break; case simpletikzParser.IM_TIKZSET: Tikz_Options to2 = new Tikz_Options(); FillItem(to2, childt, tokens); item.AddChild(to2); break; case simpletikzParser.IM_STYLE: Tikz_Option topt2 = Tikz_Option.FromCommonTree(childt, tokens); //FillItem(to2, childt, tokens); topt2.text = getTokensString(tokens, childt); item.AddChild(topt2); break; case simpletikzParser.IM_CONTROLS: Tikz_Controls tcontrols = new Tikz_Controls(); FillItem(tcontrols, childt, tokens); item.AddChild(tcontrols); break; case simpletikzParser.IM_SIZE: Tikz_Size tsize = Tikz_Size.FromCommonTree(childt, tokens); tsize.text = getTokensString(tokens, childt); item.AddChild(tsize); //Tikz_Size tsize = new Tikz_Size(); //item.AddChild(tsize); break; //case simpletikzParser.ID: //case simpletikzParser.IM_STRING: //case simpletikzParser.COMMAND: //case simpletikzParser.T__57: // break; case simpletikzParser.IM_TIKZEDT_CMD: Tikz_EdtCommand cmd = new Tikz_EdtCommand(getTokensString(tokens, childt)); item.AddChild(cmd); break; case simpletikzParser.IM_DONTCARE: Tikz_Something st = new Tikz_Something(getTokensString(tokens, childt)); item.AddChild(st); break; default: // getting here is an error throw new Exception(" childt.Type not handled! " + childt.Type.ToString() + " (\"" + getTokensString(tokens, childt) + "\")"); //break; } curToken = childt.TokenStopIndex + 1; } if (t.TokenStartIndex >= 0) // rule out empty code { addSomething(item, tokens, curToken, t.TokenStopIndex); } return(true); }
public override void OnLeftMouseButtonDown(OverlayShape item, Point p, TEMouseArgs e) { if (!EnsureParseTreeExists()) { return; } p = overlay.Rasterizer.RasterizePixelToTikz(p); if (ContinueWithBigImage(p) == false) { return; } overlay.BeginUpdate(); //overlay.SetCorrectRaster(overlay.CurEditing, true); UpdateRaster(); //Point p = new Point(e.GetPosition(canvas1).X, Height - e.GetPosition(canvas1).Y); // find next tikzpicture and add bool lcreated; if (EnsureCurAddToExists(out lcreated)) { // on double click -> close path if (e.ClickCount == 2) { if (!lcreated) { //if (!Keyboard.Modifiers.HasFlag(ModifierKeys.Control)) curAddTo.AddChild(new Parser.Tikz_Something(" -- cycle")); //else // curAddTo.AddChild(new Parser.Tikz_Something(" cycle")); } } else { if (!lcreated) { if (!overlay.KeyboardModifiers.HasFlag(TEModifierKeys.Control)) { // add an edge curAddTo.AddChild(new Parser.Tikz_Something(" -- ")); } else { curAddTo.AddChild(new Parser.Tikz_Something(" ")); } } // create new coordinate. If some node was clicked, set a reference to that node. Otherwise, just make new coordinates Tikz_Coord tc = new Tikz_Coord(); curAddTo.AddChild(tc); if (item is OverlayNode && IsReferenceable(item)) { Tikz_Node tn = MakeReferenceableNode((item as OverlayNode).tikzitem); tc.type = Tikz_CoordType.Named; tc.nameref = tn.name; } else { // do it here since the coordinate calculation needs the parents' coord. transform tc.type = overlay.UsePolarCoordinates ? Tikz_CoordType.Polar : Tikz_CoordType.Cartesian; if (!lcreated) { tc.deco = overlay.NewNodeModifier; // first node should always be in absolute coordinates } tc.SetAbsPos(new Point(p.X, p.Y)); //hack // if a nonempty node style is selected, also add a node with that style if (overlay.NodeStyle.Trim() != "") { Tikz_Node tn = new Tikz_Node() { options = "[" + overlay.NodeStyle + "]", coord = null, text = "" }; curAddTo.AddChild(new Tikz_Something(" ")); curAddTo.AddChild(tn); } } //tn.UpdateText(); curAddTo.UpdateText(); //tpict.UpdateText(); // draw the added object in the overlay overlay.AddToDisplayTree(tc); } } overlay.EndUpdate(); UpdateRaster(); // doubleclick also stops path drawing if (e.ClickCount == 2) { overlay.ActivateDefaultTool(); } }