Links are working!

master
Melroy van den Berg 2021-02-15 19:03:07 +01:00
parent 3b6b72a36e
commit 1841bebc93
5 changed files with 140 additions and 33 deletions

View File

@ -1,5 +1,6 @@
#include "draw.h"
#include "node.h"
#include "mainwindow.h"
#include <gdk/gdkthreads.h>
#include <iostream>
#define PANGO_SCALE_XXX_LARGE ((double)1.98)
@ -11,8 +12,9 @@ struct DispatchData
std::string url;
};
Draw::Draw()
: buffer(Glib::unwrap(this->get_buffer())),
Draw::Draw(MainWindow &mainWindow)
: mainWindow(mainWindow),
buffer(Glib::unwrap(this->get_buffer())),
fontSize(10 * PANGO_SCALE),
fontFamily("Ubuntu Monospace"),
headingLevel(0),
@ -63,6 +65,62 @@ Draw::Draw()
heading5.set_weight(Pango::WEIGHT_BOLD);
heading6.set_size(fontSize * PANGO_SCALE_MEDIUM);
heading6.set_weight(Pango::WEIGHT_BOLD);
// Click event
signal_event_after().connect(sigc::mem_fun(this, &Draw::event_after));
}
/**
* Links can be activated by clicking or touching the screen.
*/
void Draw::event_after(GdkEvent *ev)
{
gdouble ex, ey;
Gtk::TextBuffer::iterator iter;
int x, y;
if (ev->type == GDK_BUTTON_RELEASE)
{
GdkEventButton *event;
event = (GdkEventButton *)ev;
if (event->button != GDK_BUTTON_PRIMARY)
return;
ex = event->x;
ey = event->y;
}
else if (ev->type == GDK_TOUCH_END)
{
GdkEventTouch *event;
event = (GdkEventTouch *)ev;
ex = event->x;
ey = event->y;
}
else
return;
// Get the textview coordinates and retrieve an iterator
window_to_buffer_coords(Gtk::TextWindowType::TEXT_WINDOW_WIDGET, ex, ey, x, y);
get_iter_at_location(iter, x, y);
// Find the links
followLink(iter);
}
/**
* Search for links
*/
void Draw::followLink(Gtk::TextBuffer::iterator &iter)
{
auto tags = iter.get_tags();
for (auto const &tag : tags)
{
char *url = static_cast<char *>(tag->get_data("url"));
if (url != 0 && (strlen(url) > 0))
{
// Get the URL
mainWindow.doRequest(url, true);
break;
}
}
}
void Draw::showMessage(const std::string &message, const std::string &detailed_info)
@ -81,7 +139,8 @@ void Draw::showStartPage()
this->clear();
insertHeading1("Welcome to the Decentralized Web (DWeb)");
insertText("For the test example, go to: ipfs://QmQzhn6hEfbYdCfwzYFsSt3eWpubVKA1dNqsgUwci5vHwq");
insertText("See also the: ");
insertLink("Example page on IPFS", "ipfs://QmQzhn6hEfbYdCfwzYFsSt3eWpubVKA1dNqsgUwci5vHwq");
}
/**
@ -298,7 +357,6 @@ void Draw::processNode(cmark_node *node, cmark_event_type ev_type)
// URL
else if (isLink)
{
std::cout << "Text: " << text << "With link: " << linkURL << std::endl;
insertLink(text, linkURL);
linkURL = "";
}

View File

@ -5,17 +5,24 @@
#include <pangomm/layout.h>
#include <cmark-gfm.h>
class MainWindow;
struct DispatchData;
class Draw : public Gtk::TextView
{
public:
Draw();
Draw(MainWindow &mainWindow);
void showMessage(const std::string &message, const std::string &detailed_info = "");
void showStartPage();
void processDocument(cmark_node *root_node);
protected:
// Signals
void event_after(GdkEvent *ev);
private:
void followLink(Gtk::TextBuffer::iterator &iter);
void processNode(cmark_node *node, cmark_event_type ev_type);
// Helper functions for inserting text
void insertText(const std::string &text);
@ -37,6 +44,7 @@ private:
static gboolean clearIdle(GtkTextBuffer *textBuffer);
static std::string const intToRoman(int num);
MainWindow &mainWindow;
GtkTextBuffer *buffer;
int fontSize;
std::string fontFamily;

View File

@ -12,6 +12,7 @@ MainWindow::MainWindow()
: m_vbox(Gtk::ORIENTATION_VERTICAL, 0),
m_hbox_bar(Gtk::ORIENTATION_HORIZONTAL, 0),
m_requestThread(nullptr),
m_draw(*this),
requestPath(""),
finalRequestPath(""),
currentContent("")
@ -29,7 +30,7 @@ MainWindow::MainWindow()
m_about.signal_response().connect(sigc::mem_fun(m_about, &About::hide_about)); /*!< Close about dialog */
m_refreshButton.signal_clicked().connect(sigc::mem_fun(this, &MainWindow::refresh)); /*!< Button for reloading the page */
m_homeButton.signal_clicked().connect(sigc::mem_fun(this, &MainWindow::go_home)); /*!< Button for home page */
m_inputField.signal_activate().connect(sigc::mem_fun(this, &MainWindow::input_activate)); /*!< User pressed enter in the input */
m_addressBar.signal_activate().connect(sigc::mem_fun(this, &MainWindow::address_bar_activate)); /*!< User pressed enter the address bar */
m_vbox.pack_start(m_menu, false, false, 0);
@ -59,7 +60,7 @@ MainWindow::MainWindow()
m_hbox_bar.pack_start(m_forwardButton, false, false, 0);
m_hbox_bar.pack_start(m_refreshButton, false, false, 0);
m_hbox_bar.pack_start(m_homeButton, false, false, 0);
m_hbox_bar.pack_start(m_inputField, true, true, 8);
m_hbox_bar.pack_start(m_addressBar, true, true, 8);
m_vbox.pack_start(m_hbox_bar, false, false, 6);
// Browser text drawing area
@ -71,7 +72,7 @@ MainWindow::MainWindow()
show_all_children();
// Grap focus to input field by default
m_inputField.grab_focus();
m_addressBar.grab_focus();
// Show start page by default
// Load test.md file on start-up
@ -79,23 +80,11 @@ MainWindow::MainWindow()
//go_home();
}
void MainWindow::go_home()
{
this->requestPath = "";
this->finalRequestPath = "";
this->currentContent = "";
this->m_inputField.set_text("");
m_draw.showStartPage();
}
/**
* Trigger when user input text in address bar
* Fetch document from disk or IPFS, using threading
*/
void MainWindow::input_activate()
void MainWindow::doRequest(const std::string &path, bool setAddressBar)
{
// QmQzhn6hEfbYdCfwzYFsSt3eWpubVKA1dNqsgUwci5vHwq
// Stop running thread (if applicable)
if (m_requestThread)
{
if (m_requestThread->joinable())
@ -107,8 +96,28 @@ void MainWindow::input_activate()
}
}
if (m_requestThread == nullptr)
m_requestThread = new std::thread(&MainWindow::doRequest, this, m_inputField.get_text());
if (m_requestThread == nullptr) {
if (setAddressBar)
m_addressBar.set_text(path);
m_requestThread = new std::thread(&MainWindow::processRequest, this, path);
}
}
void MainWindow::go_home()
{
this->requestPath = "";
this->finalRequestPath = "";
this->currentContent = "";
this->m_addressBar.set_text("");
m_draw.showStartPage();
}
/**
* Trigger when user input text in address bar
*/
void MainWindow::address_bar_activate()
{
doRequest(m_addressBar.get_text());
}
/**
@ -116,15 +125,14 @@ void MainWindow::input_activate()
*/
void MainWindow::refresh()
{
if (m_requestThread == nullptr)
m_requestThread = new std::thread(&MainWindow::doRequest, this, "");
doRequest();
}
/**
* Get the file from disk or IPFS network, from the provided path,
* parse the content, and display the document
*/
void MainWindow::doRequest(const std::string &path)
void MainWindow::processRequest(const std::string &path)
{
currentContent = "";
if (!path.empty())
@ -166,7 +174,7 @@ void MainWindow::doRequest(const std::string &path)
}
/**
* Helper method for doRequest(),
* Helper method for processRequest(),
* Display markdown file from IPFS network.
*/
void MainWindow::fetchFromIPFS()
@ -189,7 +197,7 @@ void MainWindow::fetchFromIPFS()
}
/**
* Helper method for doRequest(),
* Helper method for processRequest(),
* Display markdown file from disk.
*/
void MainWindow::openFromDisk()

View File

@ -18,12 +18,13 @@ class MainWindow : public Gtk::Window
{
public:
MainWindow();
void doRequest(const std::string &path= std::string(), bool setAddressBar = false);
protected:
// Signal handlers:
// Our new improved on_button_clicked(). (see below)
void go_home();
void input_activate();
void address_bar_activate();
void refresh();
void on_button_clicked(Glib::ustring data);
void show_about();
@ -38,7 +39,7 @@ protected:
Gtk::Button m_forwardButton;
Gtk::Button m_refreshButton;
Gtk::Button m_homeButton;
Gtk::Entry m_inputField;
Gtk::Entry m_addressBar;
Gtk::Image backIcon;
Gtk::Image forwardIcon;
Gtk::Image refreshIcon;
@ -55,7 +56,7 @@ private:
std::string finalRequestPath;
std::string currentContent;
void doRequest(const std::string &path);
void processRequest(const std::string &path);
void fetchFromIPFS();
void openFromDisk();
};

34
test.md
View File

@ -1,2 +1,34 @@
Hello *World*, What a **happy** day!
blabla.
[test](ipfs://QmQzhn6hEfbYdCfwzYFsSt3eWpubVKA1dNqsgUwci5vHwq)
[test](ipfs://blablabalba)
# Heading 1
## Heading 2
### Heading 3
***New*** paragraph.
New line.
* list 1
* list 2
* list 3
* list 3.1
* list 3.2
* list 4
1. first
2. second
3. third
1. 1st
2. 2nd
3. grappig
4. he
4. four
Extra text.
----------
Dit is een nieuwe test.