Release 0.41.92
[vala-gnome.git] / libvaladoc / taglets / tagletlink.vala
blobef270880fdb672b3413464debc08956cecff7ec0
1 /* taglet.vala
3 * Copyright (C) 2008-2009 Didier Villevalois
4 * Copyright (C) 2008-2014 Florian Brosch
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20 * Author:
21 * Didier 'Ptitjes Villevalois <ptitjes@free.fr>
25 using Valadoc.Content;
27 public class Valadoc.Taglets.Link : InlineTaglet {
28 public string symbol_name { internal set; get; }
30 /**
31 * Accept leading 's', e.g. #Widgets
33 public bool c_accept_plural { internal set; get; }
35 /**
36 * True if symbol_name could only be resolved after removing 's'
38 * E.g. true or #Widgets, false for #Widget
40 public bool c_is_plural { private set; get; }
43 private enum SymbolContext {
44 NORMAL,
45 FINISH,
46 TYPE
49 private SymbolContext _context = SymbolContext.NORMAL;
50 private Api.Node _symbol;
52 public override Rule? get_parser_rule (Rule run_rule) {
53 return Rule.seq ({
54 Rule.option ({
55 Rule.many ({
56 Rule.one_of({
57 TokenType.SPACE,
58 TokenType.EOL
61 }),
62 TokenType.any_word ().action ((token) => { symbol_name = token.to_string (); }),
63 Rule.option ({
64 Rule.many ({
65 Rule.one_of ({
66 TokenType.any_word ().action ((token) => { symbol_name += token.to_string (); }),
67 TokenType.MINUS.action ((token => { symbol_name += token.to_string (); }))
71 });
74 public override void check (Api.Tree api_root, Api.Node container, string file_path,
75 ErrorReporter reporter, Settings settings) {
77 if (symbol_name.has_prefix ("c::")) {
78 _symbol_name = _symbol_name.substring (3);
79 string? singular_symbol_name = (c_accept_plural && _symbol_name.has_suffix ("s"))
80 ? symbol_name.substring (0, _symbol_name.length - 1)
81 : null;
83 _symbol = api_root.search_symbol_cstr (container, symbol_name);
84 if (_symbol == null && singular_symbol_name != null) {
85 _symbol = api_root.search_symbol_cstr (container, singular_symbol_name);
86 c_is_plural = true;
88 _context = SymbolContext.NORMAL;
90 if (_symbol == null && _symbol_name.has_suffix ("_finish")) {
91 string tmp = _symbol_name.substring (0, _symbol_name.length - 7);
93 _symbol = api_root.search_symbol_cstr (container, tmp + "_async") as Api.Method;
94 if (_symbol != null && ((Api.Method) _symbol).is_yields) {
95 _context = SymbolContext.FINISH;
96 } else {
97 _symbol = api_root.search_symbol_cstr (container, tmp) as Api.Method;
98 if (_symbol != null && ((Api.Method) _symbol).is_yields) {
99 _context = SymbolContext.FINISH;
100 } else {
101 _symbol = null;
106 if (_symbol == null) {
107 _symbol = api_root.search_symbol_type_cstr (symbol_name);
108 if (_symbol == null && singular_symbol_name != null) {
109 _symbol = api_root.search_symbol_type_cstr (singular_symbol_name);
110 c_is_plural = true;
112 if (_symbol != null) {
113 _context = SymbolContext.TYPE;
117 if (_symbol != null) {
118 symbol_name = _symbol.name;
120 } else {
121 _symbol = api_root.search_symbol_str (container, symbol_name);
124 if (_symbol == null && symbol_name != "main") {
125 string node_segment = (container is Api.Package)? "" : container.get_full_name () + ": ";
126 reporter.simple_warning ("%s: %s@link".printf (file_path, node_segment),
127 "`%s' does not exist", symbol_name);
130 base.check (api_root, container, file_path, reporter, settings);
133 public override ContentElement produce_content () {
134 var link = new Content.SymbolLink ();
135 link.symbol = _symbol;
136 link.given_symbol_name = symbol_name;
138 Content.Inline content;
139 switch (_context) {
140 case SymbolContext.FINISH:
141 link.given_symbol_name += ".end";
142 content = link;
143 break;
145 case SymbolContext.TYPE:
146 Run run = new Content.Run (Run.Style.MONOSPACED);
147 content = run;
149 Content.Run keyword = new Content.Run (Run.Style.LANG_KEYWORD);
150 keyword.content.add (new Content.Text ("typeof"));
151 run.content.add (keyword);
153 run.content.add (new Content.Text (" ("));
154 run.content.add (link);
155 run.content.add (new Content.Text (")"));
156 break;
158 default:
159 content = link;
160 break;
163 if (c_is_plural == true) {
164 Run run = new Content.Run (Run.Style.NONE);
165 run.content.add (content);
166 run.content.add (new Content.Text ("s"));
167 return run;
170 return content;
173 public override bool is_empty () {
174 return false;
177 public override ContentElement copy (ContentElement? new_parent = null) {
178 Link link = new Link ();
179 link.parent = new_parent;
181 link.settings = settings;
182 link.locator = locator;
184 link.symbol_name = symbol_name;
185 link.c_accept_plural = c_accept_plural;
186 link.c_is_plural = c_is_plural;
187 link._context = _context;
188 link._symbol = _symbol;
190 return link;