4
// Todd Berman <tberman@off.net>
6
// Copyright (c) 2007 Todd Berman
8
// Permission is hereby granted, free of charge, to any person obtaining a copy
9
// of this software and associated documentation files (the "Software"), to deal
10
// in the Software without restriction, including without limitation the rights
11
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12
// copies of the Software, and to permit persons to whom the Software is
13
// furnished to do so, subject to the following conditions:
15
// The above copyright notice and this permission notice shall be included in
16
// all copies or substantial portions of the Software.
18
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
35
using MonoDevelop.Core.Gui;
36
using MonoDevelop.Core.Gui.WebBrowser;
37
using MonoDevelop.Core;
38
using MonoDevelop.Projects.Dom.Parser;
40
namespace MonoDevelop.Ide.Gui
43
public class HelpViewer : AbstractViewContent
45
IWebBrowser html_viewer;
48
public override bool IsViewOnly {
52
public override Gtk.Widget Control {
53
get { return widget; }
56
public override string ContentName {
57
get { return GettextCatalog.GetString ("Documentation"); }
60
public override void Dispose ()
66
public static bool CanLoadHelpViewer {
67
get { return WebBrowserService.CanGetWebBrowser; }
72
if (WebBrowserService.CanGetWebBrowser) {
73
html_viewer = WebBrowserService.GetWebBrowser ();
74
html_viewer.LinkClicked += LinkClicked;
75
html_viewer.LinkStatusChanged += onLinkMessage;
76
widget = (Widget) html_viewer;
78
Label lab = new Label (GettextCatalog.GetString ("The help viewer could not be loaded, because an embedded web browser is not available."));
84
void onLinkMessage (object sender, StatusMessageChangedEventArgs args)
86
IdeApp.Workbench.StatusBar.ShowMessage (args.Message ?? string.Empty);
89
void LinkClicked (object o, LocationChangingEventArgs args)
91
LoadUrl (args.NextLocation);
92
args.SuppressChange = true;
95
public void LoadNode (string nodeText, Node node, string url)
97
if (html_viewer == null)
100
string tempFile = buildTempDocDirectory (nodeText);
101
html_viewer.LoadUrl (string.Format ("file://{0}#{1}", tempFile, string.Empty));
102
} catch (Exception e) {
103
LoadErrorHtml (e, url);
107
public void LoadErrorHtml (Exception e, string missingUrl)
109
LoggingService.LogError ("Could not load help url {0}\n{1}", missingUrl, e.ToString ());
110
html_viewer.LoadHtml (GettextCatalog.GetString("{0}Error: the help topic '{2}' could not be loaded.{1}",
112
"</h1></body></html>",
116
public void LoadUrl (string url)
118
if (html_viewer == null || url.StartsWith("#"))
121
if (ProjectDomService.HelpTree != null) {
123
string res = ProjectDomService.HelpTree.RenderUrl (url, out node);
124
LoadNode (res, node, url);
128
string buildTempDocDirectory (string fileText)
130
if (fileText == null)
131
throw new ArgumentNullException ("fileText");
133
string tempDir = Path.GetTempFileName ();
134
File.Delete (tempDir);
135
Directory.CreateDirectory (tempDir);
137
StringBuilder builder = new StringBuilder ();
138
builder.Append ("<html><body>");
139
ProcessImages (fileText, builder, tempDir);
140
builder.Append ("</body></html>");
142
using (StreamWriter writer = File.CreateText (Path.Combine (tempDir, "index.html"))) {
143
writer.Write (builder.ToString ());
145
return Path.Combine (tempDir, "index.html"); //FIXME: and the anchor too
148
void ProcessImages (string input, StringBuilder output, string tempDir)
152
bool inCDATA = false;
153
bool inComment = false;
154
int previousCaptureEndedAt = 0;
156
while (pos < (input.Length - 9)) {
157
//escape from comments
159
while (pos < input.Length - 3) {
160
if (input[pos] == '-' && input[pos+1] == '-' && input [pos+2] == '>') {
170
while (pos < input.Length - 3) {
171
if (input[pos] == ']' && input[pos+1] == ']' && input [pos+2] == '>') {
180
else if (input[pos] == '<') {
181
//enter CDATA or comment
182
if (input[pos+1] == '!') {
183
if (input[pos+2] == '-' && input [pos+3] == '-') {
187
} else if (input.Substring (pos+2, 7) == "[CDATA[") {
192
//IMG tags; what we're looking for!
193
else if (input[pos+1] == 'i' && input [pos+2] == 'm' && input [pos+3] == 'm' ){
196
//string path = Path.Combine (tempDir, "image" + imageIndex);
197
//WriteImage (path, url);
199
System.Console.WriteLine(input.Substring (pos, 10));
204
output.Append (input.Substring (previousCaptureEndedAt));
207
void WriteImage (string path, string url)
209
using (Stream s = ProjectDomService.HelpTree.GetImage (url)) {
210
using (FileStream fs = new FileStream (path, FileMode.Create)) {
211
byte[] buffer = new byte [8192];
213
while ((n = s.Read (buffer, 0, 8192)) != 0)
214
fs.Write (buffer, 0, n);
219
public override void Load (string s)