17 |
18 | ## Juggl
19 | Juggl is a completely interactive, stylable and expandable graph view for [Obsidian](https://obsidian.md). It is designed as an advanced 'local' graph view called the 'workspace', where you can juggle all your thoughts with ease: By navigating your vault through a beautiful graph!
20 |
21 | For example, you can select what parts of the graph to expand, to make sure there is never too much information on the screen. You will have complete control over the style of your graph using the powerful [Cytoscape.js library](https://js.cytoscape.org): Juggl has a useful styling pane nodes colors, shapes, sizes, and icons. This helps you get an immediate overview over what the content of each node is.
22 |
23 | 
24 |
25 | ## Features
26 | Juggl has many features unique to its graph view compared to the Obsidian graph view:
27 | - Complete control over the style of your graph using [CSS](https://juggl.io/features/styling/css-styling.html), [YAML](https://juggl.io/features/styling/yaml-styling.html) and the [Style Pane](https://juggl.io/features/styling/style-pane.html) .
28 | - Include images!
29 | - A [Workspace mode](https://juggl.io/Features/Workspace+mode/Workspace+mode) that lets you build your graph with all nodes that are relevant to your current project
30 | - Selectively browse and hide nodes, and pin their location so you never lose them
31 | - Write new ideas and see your graph evolve
32 | - Save your graph and continue working on it later
33 | - 4 different [layouts](https://juggl.io/features/layouts.html) to get unique insights
34 | - A [code block](https://juggl.io/features/juggl-code-block.html) that displays the graph within Obsidian notes
35 | - Link type support to label edges
36 | - [Tight integration](https://juggl.io/features/breadcrumbs-integration.html) with the very useful [Breadcrumbs plugin](https://github.com/SkepticMystic/breadcrumbs)
37 | - Extendable through other plugins
38 | - Works on mobile!
39 |
40 | ## Getting started
41 | You can open Juggl from the 'more options' menu on files:
42 | 
43 |
44 | You can interact with the graph with many of the same options as in Obsidian. For further documentation, check out [juggl.io](https://juggl.io/), where you can find information on for example [styling](https://juggl.io/features/styling/styling.html) or the syntax of the [code block](https://juggl.io/features/juggl-code-block.html).
45 | You can also open the help vault with this button in Juggl:
46 | 
47 |
48 |
49 | ## Extending Juggl
50 | Juggl is completely open source and has an API available for creating Obsidian plugins that extend or use Juggl. See https://github.com/HEmile/juggl-api . You will have complete control over the internals of [Cytoscape.js](https://js.cytoscape.org), which is an extremely powerful graph visualization library!
51 |
--------------------------------------------------------------------------------
/docs/Archived/Edge styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | image: files/bloom_screenshot.jpg
4 | ---
5 |
6 | An example of node styling for [[Neo4j Graph View Plugin]] is provided at [[Semantic Obsidian edge styling]].
7 |
8 | Styling of edges is done in .json format. The first key determines what types of links to apply this style to.
9 | For instance, `{"hasTopic":{"color":"yellow"}}` would color all edge with type `hasTopic` yellow.
10 |
11 | ## Special types
12 | - Use `{"defaultStyle": {}}` for the default styling of edges
13 | - Use`{"inline":{} }` for the styling of untyped links
14 |
15 | See [this link](https://visjs.github.io/vis-network/docs/network/edges.html)for all options for styling edges.
16 |
17 | ---
18 | #howto
19 | - hasTopic [[Neo4j Graph View Plugin]]
20 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Installation of Neo4j Graph View Plugin.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [installation, install]
3 | ---
4 |
5 | **Warning: The [[Neo4j Graph View Plugin]] is deprecated and no longer supported. You can still [manually install it from Github](https://github.com/HEmile/obsidian-neo4j-graph-view/releases/tag/0.2.5) if you need the [[Neo4j]] support.**
6 |
7 | The general steps to install the plugin are as follows:
8 | 1. Make sure you have [[Python]] 3.6+ installed. See [[Installation of Neo4j Graph View Plugin#Install Python]].
9 | 2. Make sure you have [[Neo4j Desktop]] installed. See [[Installation of Neo4j Graph View Plugin#Install Neo4j Desktop]].
10 | 3. Create a new database in Neo4j desktop and start it. See [[Installation of Neo4j Graph View Plugin#Creating a Neo4j database]].
11 | 5. Install the Obsidian plugin from the Third-party plugins list. See [[Installation of Neo4j Graph View Plugin#Installing the Obsidian plugin]]
12 | 6. In the settings of the plugin, enter the password. Then run the restart command. See [[Installation of Neo4j Graph View Plugin#Configuring the Obsidian plugin]].
13 |
14 | If you are still running into problems after thorougly following these steps, see the [[Installation of Neo4j Graph View Plugin#Troubleshooting]] section.
15 |
16 | The next goal of the plugin (see [[Roadmap]]) is to remove the [[Python]] installation. This should make installation much more accessible. If you are not very technical and the installation of Python is failing, you can wait until this dependency is removed. The goal is to have this done before mid-end January 2021.
17 |
18 | ## 1. Install Python
19 | Make sure you've installed [Python 3.6+](https://www.python.org/downloads/) as your system Python 3. If you think you might already have it, run `python3 -V` in the terminal, which should return the Python version.
20 |
21 | Also make sure to add Python to PATH, especially on [[Windows]]! During the installation, enable the 'Add Python 3.x to PATH' to ensure this happens.
22 |
23 | 
24 |
25 | [[Linux]] might already have Python installed by default. If a version lower than 3.6 is installed, update Python. Run `python3 -V` in the terminal to find out what version you have installed.
26 |
27 | ### Possible problems
28 | For plugin versions under 0.2.5, the plugin doesn't work if Python's package manager "pip" is outdated. Please update to plugin version 0.2.5, as it updates pip for you.
29 |
30 | On [[Mac]], some people got `xcrun: error: invalid active developer path... missing xcrun at...`: [Install xcrun)](https://apple.stackexchange.com/questions/254380/why-am-i-getting-an-invalid-active-developer-path-when-attempting-to-use-git-a) in terminal using `xcode-select --install`
31 |
32 | ## 2. Install Neo4j Desktop
33 | Download [Neo4j desktop](https://neo4j.com/download/). Neo4j wants you to fill a form before giving you the link. Save the Neo4j Desktop Activation Key they provide for later.
34 |
35 | ![[Pasted image 20210112215108.png]]
36 |
37 | One user reported the activation key doesn't appear. [According to the Neo4j developers](https://community.neo4j.com/t/installing-and-activation-key/6173), that doesn't actually matter and you can proceed without using a key, curiously. I haven't tried this, though.
38 |
39 | The download can take a while because it's a pretty big file and the servers aren't very quick.
40 |
41 | Installation of Neo4j desktop is pretty straightforward. You have to input the key Neo4j gave you after registration. There's an [installation video](https://www.youtube.com/watch?v=pPhJi9twN9Q&feature=emb_title) if you need more help.
42 |
43 |
44 | ## 3. Creating a Neo4j database
45 | In a Project in Neo4j Desktop, click "+ Add Database" under projects:
46 | ![[Pasted image 20201231174344.png|300]]
47 |
48 | Then select "Create a Local Database". Next follows this screen:
49 |
50 | ![[Pasted image 20201231174425.png|300]]
51 |
52 | You have to set a password here. We're also going to use it in the plugin. Make sure not to choose a sensitive password here! [[Neo4j Graph View Plugin]] doesn't store passwords encrypted.
53 | You can choose any name. For the Neo4j version, I have tested on 4.2.0, but it should not matter much.
54 |
55 | It'll create your database! Then, click the "Start" button. Note that you have to start your database every time whenever your computer reboots: It needs to remain active while you use the plugin.
56 |
57 | ### Possible problems
58 | Every now and then, the Graph database fails to start.
59 | - Sometimes, it just says it 'timed out'. Retrying it a few times may help.
60 | - Port in use: It's unlikely the port is actually in use. Restart Neo4j desktop and try again. It's currently not possible to set a port different than the default port (request on [[Github]] if needed).
61 | - "Could not change the password": This has been reported with a [[Windows]] user. See [this post](https://stackoverflow.com/questions/49342422/neo4j-database-failed-to-create-error-could-not-change-password) for possible guidance.
62 |
63 | ## 4. Installing the Obsidian plugin
64 | Time to install the plugin! Since Neo4j Graph View is an old version of Juggl, you will have to download and install it manually.
65 |
66 | 1. Download the plugin from [this link](https://github.com/HEmile/obsidian-neo4j-graph-view/releases/tag/0.2.5).
67 | 1. Open the Obsidian settings, and go to Third-party plugins. Disable the "Safe mode" toggle, then click "Turn off safe mode" to confirm this.
68 | 2. Now, more options appear. Click on the "open plugin folders" icon
69 | 3. In the resulting folder, create a new directory called `neo4j-graph-view`
70 | 4. Extract the downloaded file into this folder.
71 | 5. Close the current screen. In the Third-party plugins settings, enable Neo4j graph view with the slider.
72 | 6. It should look like this:
73 |
74 | ![[Pasted image 20201231175530.png]]
75 |
76 |
77 | ## 5. Configuring the Obsidian plugin
78 | We need to do one more thing before we can get playing with the plugin: Setting the password.
79 | 1. Go to the [[Neo4j Graph View settings]], which has appeared under Plugin options in the [[Obsidian]] settings.
80 | 2. In the password field, input the password you set during [[Installation of Neo4j Graph View Plugin#Creating a Neo4j database]]. ![[Pasted image 20201231180930.png]]
81 | 3. Close the settings view.
82 | 4. Run the Obsidian command: "Neo4j Graph View: Restart Neo4j stream". You can run a command by using ctrl/cmd + p. ![[Pasted image 20201231181003.png]]
83 | 5. The plugin is succesfully installed if the following notice appears in the top-right corner: ![[Pasted image 20201231181103.png|300]] (note: for some reason, it doesn't always appear even though the server did properly start...)
84 |
85 | If a different notice appears, something went wrong. Let's try to figure out what!
86 | ## Troubleshooting
87 | If a notice appears that doesn't say the Neo4j stream is online, something went wrong. Two simple notices are
88 | - "Please provide a password in the Neo4j Graph View settings": This means your user credentials weren't accepted by the Neo4j database. Check if the password is set correctly during [[Installation of Neo4j Graph View Plugin#Configuring the Obsidian plugin]].
89 | - "No connection to Neo4j database. Please start Neo4j Database in Neo4j Desktop": This means there's no connection to a Neo4j database on port 7687. Check Neo4j desktop if the database is online.
90 |
91 | The third notice is scariest: "Error during initialization of the Neo4j stream. Check the console for crash report.". Here are some steps to help figure out how to resolve this:
92 | 1. Enable "Debug" mode in the Neo4j Graph View settings ![[Pasted image 20201231181917.png]]
93 | 2. Open the Developer Tools. This option is under the View menu. If the View menu doesn't show, the keyboard shortcut to open it is ctrl+shift+i on windows and option+cmd+i on mac.
94 | 3. Look at the error in the Console.
95 |
96 | If the error is related to `pip3`, or `smdc` not being found, there's likely something wrong with your Python installation. See [[Installation of Neo4j Graph View Plugin#Install Python]] for a bit of guidance.
97 | Otherwise, it's likely that there's some bug in the plugin in that it cannot handle something that's present in your vault. Since this version is not supported by me anymore, you will have to fork the plugin to fix this. There are plans to add Neo4j support to [[Juggl]] sometime through an external plugin.
98 | You can also contact [[Emile van Krieken|me]] on Twitter, Github or [[Discord]] if you need help.
99 |
100 | ---
101 | #howto
102 | - hasTopic [[Neo4j Graph View]]
103 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Neo4j Graph View Plugin.md:
--------------------------------------------------------------------------------
1 | This plugin is deprecated and replaced by [[Juggl]]. It will be removed from the community plugins store in the near future.
2 |
3 | ![[styled_screenshot.png]]
4 |
5 |
6 | Adds a much more customizable and interactable [[Neo4j Graph View|graph view]] to [[Obsidian]]. It does so by connecting to a [[Neo4j]] database. Features:
7 | - Selectively [[Node styling|style nodes]] and [[Edge styling|edges]] by tags, folders and link types ^87894b
8 | - Selectively expand and hide parts of the grapha
9 | - View images within the graph
10 | - Execute advanced queries using [[Cypher]]
11 | - [[Link Types]]
12 | - Optional [[Hierarchical layout]]
13 |
14 | This vault acts as a demo for the Graph View. You can [download](https://github.com/HEmile/semantic-obsidian) the documentation as an Obsidian vault, and use the Graph View to visualize it. Styling is provided at [[Semantic Obsidian node styling]] and [[Semantic Obsidian edge styling]].
15 |
16 | ## Install and use
17 | First [[Installation of Neo4j Graph View Plugin|install]] the plugin. Then, read [[Using the Neo4j Graph View|this guide with a lot of videos]] to get started with the graph view.
18 |
19 | To get a feel for how the plugin interprets your data, see [[Semantic Markdown Converter Semantics|the explanation on semantics]].
20 |
21 | There are more graph visualization options available! See [[Neo4j graph visualizations]] for some options.
22 |
23 | ## Development
24 | Lots of ideas exist to extend this plugin! There is a [[Roadmap]] available. A [[Juggl API]] is also being planned, which allows for easily extending the Graph View.
25 |
26 | Contributions are very much welcomed. The easiest way to get started is to join the [[Discord]] server! See [[Contributing]] for an overview of ways you can help.
27 |
28 |
29 | ---
30 | #plugin
31 | - hasTopic [[Neo4j]]
32 | - hasTopic [[Obsidian]]
33 |
34 |
35 |
--------------------------------------------------------------------------------
/docs/Archived/Neo4j Stream/Installing the Neo4j Stream Plugin.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [installation, install]
3 | ---
4 |
5 |
6 |
7 | The general steps to install the plugin are as follows:
8 | 1. Make sure you have [[Neo4j Desktop]] installed. See [[Install Neo4j Stream Plugin#Install Neo4j Desktop]].
9 | 3. Create a new database in Neo4j desktop and start it. See [[Install Neo4j Stream Plugin#Creating a Neo4j database]].
10 | 5. Install the Obsidian plugin from the Third-party plugins list. See [[Install Neo4j Stream Plugin#Installing the Obsidian plugin]]
11 | 6. In the settings of the plugin, enter the password. Then run the restart command. See [[Install Neo4j Stream Plugin#Configuring the Obsidian plugin]].
12 |
13 | If you are still running into problems after thorougly following these steps, see the [[Install Neo4j Stream Plugin#Troubleshooting]] section.
14 |
15 | ## 1. Install Neo4j Desktop
16 | Download [Neo4j desktop](https://neo4j.com/download/). Neo4j wants you to fill a form before giving you the link. Save the Neo4j Desktop Activation Key they provide for later.
17 |
18 | ![[Pasted image 20210112215108.png]]
19 |
20 | One user reported the activation key doesn't appear. [According to the Neo4j developers](https://community.neo4j.com/t/installing-and-activation-key/6173), that doesn't actually matter and you can proceed without using a key, curiously. I haven't tried this, though.
21 |
22 | The download can take a while because it's a pretty big file and the servers aren't very quick.
23 |
24 | Installation of Neo4j desktop is pretty straightforward. You have to input the key Neo4j gave you after registration. There's an [installation video](https://www.youtube.com/watch?v=pPhJi9twN9Q&feature=emb_title) if you need more help.
25 |
26 |
27 | ## 2. Creating a Neo4j database
28 | In a Project in Neo4j Desktop, click "+ Add Database" under projects:
29 | ![[Pasted image 20201231174344.png|300]]
30 |
31 | Then select "Create a Local Database". Next follows this screen:
32 |
33 | ![[Pasted image 20201231174425.png|300]]
34 |
35 | You have to set a password here. We're also going to use it in the plugin. Make sure not to choose a sensitive password here! [[Neo4j Stream Plugin]] doesn't store passwords encrypted. You can choose any name. For the Neo4j version, I have tested on 4.2.0, but it should not matter much.
36 |
37 | It'll create your database! Then, click the "Start" button. Note that you have to start your database every time whenever your computer reboots: It needs to remain active while you use the plugin.
38 |
39 | ### Possible problems
40 | Every now and then, the Graph database fails to start.
41 | - Sometimes, it just says it 'timed out'. Retrying it a few times may help.
42 | - Port in use: It's unlikely the port is actually in use. Restart Neo4j desktop and try again. It's currently not possible to set a port different than the default port (request on [[Github]] if needed).
43 | - "Could not change the password": This has been reported with a [[Windows]] user. See [this post](https://stackoverflow.com/questions/49342422/neo4j-database-failed-to-create-error-could-not-change-password) for possible guidance.
44 |
45 | ## 3. Installing the Obsidian plugin
46 | Time to install the plugin! Since Neo4j Stream is unfinished, you will have to download and install it manually.
47 |
48 | 1. Download the plugin from [this link](https://github.com/HEmile/obsidian-neo4j-stream/releases).
49 | 1. Open the Obsidian settings, and go to Third-party plugins. Disable the "Safe mode" toggle, then click "Turn off safe mode" to confirm this.
50 | 2. Now, more options appear. Click on the "open plugin folders" icon
51 | 3. In the resulting folder, create a new directory called `neo4j-stream`
52 | 4. Extract the downloaded file into this folder.
53 | 5. Close the current screen. In the Third-party plugins settings, enable Neo4j Stream with the slider.
54 |
55 | ## 4. Configuring Neo4j Stream
56 | We need to do one more thing before we can get playing with the plugin: Setting the password.
57 | 1. Go to the Neo4j Stream settings, which has appeared under Plugin options in the Obsidian settings.
58 | 2. In the password field, input the password you set during [[Install Neo4j Stream Plugin#Creating a Neo4j database]]. ![[Pasted image 20201231180930.png]]
59 | 3. Close the settings view.
60 | 4. Run the Obsidian command: "Neo4j Graph View: Restart Neo4j stream". You can run a command by using ctrl/cmd + p. ![[Pasted image 20201231181003.png]]
61 | 5. The plugin is succesfully installed if the following notice appears in the top-right corner: ![[Pasted image 20201231181103.png|300]] (note: for some reason, it doesn't always appear even though the server did properly start...)
62 |
63 | If a different notice appears, something went wrong. Let's try to figure out what!
64 |
65 | ## Troubleshooting
66 | If a notice appears that doesn't say the Neo4j stream is online, something went wrong. Two simple notices are
67 | - "Please provide a password in the Neo4j Stream settings": This means your user credentials weren't accepted by the Neo4j database. Check if the password is set correctly during [[Install Neo4j Stream Plugin#Configuring the Obsidian plugin]].
68 | - "No connection to Neo4j database. Please start Neo4j Database in Neo4j Desktop": This means there's no connection to a Neo4j database on port 7687. Check Neo4j desktop if the database is online.
69 |
70 | The third notice is scariest: "Error during initialization of the Neo4j stream. Check the console for crash report.". Here are some steps to help figure out how to resolve this:
71 | 1. Enable "Debug" mode in the Neo4j Stream settings ![[Pasted image 20201231181917.png]]
72 | 2. Open the Developer Tools. This option is under the View menu. If the View menu doesn't show, the keyboard shortcut to open it is Ctrl+Shift+I on windows and Option+Cmd+I on mac.
73 | 3. Look at the error in the Console.
74 |
75 | Otherwise, it's likely that there's some bug in the plugin in that it cannot handle something that's present in your vault. Since this version is unfinished, you will have to fork the plugin to fix this.
76 |
77 | You can also contact [[Emile van Krieken|me]] on Twitter, Github or [[Discord]] if you need help.
78 |
79 | ---
80 | #howto
81 | - hasTopic [[Neo4j Graph View]]
82 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Neo4j Stream/Neo4j Stream Plugin.md:
--------------------------------------------------------------------------------
1 | This plugin helps by streaming your vault to a [Neo4j](https://neo4j.com/) database. This is a separate plugin to ensure non-advanced users of [[Juggl]] will not have to deal with installing Neo4j, and is completely optional for advanced users.
2 |
3 | ⚠ Note: This is an unfinshed pluggin. Absolutely no guarantees are given that this works.
4 | ⚠ Note: Development on this project has stopped out of lack of personal interest for the use case. Anyone interested in further developing this can contact me.
5 |
6 | Please refer to [[Install Neo4j Stream Plugin]] and [[Neo4j graph visualizations]] for more information
7 |
8 | ## Development
9 | [[Roadmap]]: [[Roadmap#^2d1fd7]]
10 |
11 | Contributions are very much welcomed. The easiest way to get started is to join the [[Discord]] server! See [[Contributing]] for an overview of ways you can help.
12 |
13 | [HEmile/obsidian-neo4j-stream](https://github.com/HEmile/obsidian-neo4j-stream "HEmile/obsidian-neo4j-stream")
14 |
15 | ---
16 | #plugin
17 | - hasTopic [[Neo4j]]
18 | - hasTopic [[Obsidian]]
19 |
20 |
21 |
--------------------------------------------------------------------------------
/docs/Archived/Neo4j Stream/Neo4j graph visualizations.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | The main use case for the [[Neo4j Stream Plugin]] is to use your Obsidian vault in one of the many apps in the [[Neo4j Desktop]]
6 | Graph Apps Store. Using with this plugin active will automatically connect it to your vault. Here are some suggestions:
7 |
8 | ### Neo4j Bloom
9 | [Neo4j Bloom](https://neo4j.com/product/bloom/) is very powerful graph visualization software. Compared to the embedded
10 | graph view in Obsidian, it offers much more freedom in customization.
11 |
12 | ![[bloom_screenshot.jpg]]
13 |
14 |
15 | ### GraphXR
16 | [GraphXR](https://www.kineviz.com/) is a 3D graph view, which looks quite gorgeous!
17 |
18 | ![[graphxr.gif]]
19 |
20 |
21 | ### Neo4j Browser
22 | A query browser that uses the [[Cypher]] language to query your vault. Can be used for advanced queries or data anlysis of your vault.
23 |
24 | ![[browser_screenshot.png]]
25 |
26 | ### Gephi
27 | Neo4j can export to the graph visualization software [[Gephi]]. See the [Neo4j document](https://neo4j.com/labs/apoc/4.1/export/gephi/) for help on how to do this. Note that it requires installing the "APOC" plugin to your Neo4j Graph Database.
28 |
29 |
30 |
31 | ---
32 | #topic
33 | - hasTopic [[Neo4j]], [[Neo4j Stream Plugin]]
34 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Neo4j graph visualizations.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Another use case for the [[Neo4j Graph View Plugin]] is to use your Obsidian vault in one of the many apps in the [[Neo4j Desktop]]
6 | Graph Apps Store. Using with this plugin active will automatically connect it to your vault. Here are some suggestions:
7 |
8 | ### Neo4j Bloom
9 | [Neo4j bloom](https://neo4j.com/product/bloom/) is very powerful graph visualization software. Compared to the embedded
10 | graph view in Obsidian, it offers much more freedom in customization.
11 |
12 | ![[bloom_screenshot.jpg]]
13 |
14 |
15 | ### GraphXR
16 | [GraphXR](https://www.kineviz.com/) is a 3D graph view, which looks quite gorgeous!
17 |
18 | ![[graphxr.gif]]
19 |
20 |
21 | ### Neo4j Browser
22 | A query browser that uses the [[Cypher]] language to query your vault. Can be used for advanced queries or data anlysis of your vault.
23 |
24 | ![[browser_screenshot.png]]
25 |
26 | ### Gephi
27 | Neo4j can export to the graph visualization software [[Gephi]]. See the [Neo4j document](https://neo4j.com/labs/apoc/4.1/export/gephi/) for help on how to do this. Note that it requires installing the "APOC" plugin to your Neo4j Graph Database.
28 |
29 |
30 |
31 | ---
32 | #topic
33 | - hasTopic [[Neo4j]], [[Neo4j Graph View Plugin]]
34 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Node styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | image: https://raw.githubusercontent.com/HEmile/obsidian-neo4j-graph-view/main/neo4j-graph-view/resources/styled_screenshot.png
4 | ---
5 |
6 | An example of node styling for this vault is provided at [[Semantic Obsidian node styling]].
7 |
8 | Styling of nodes is done in .json format.
9 | The first key determines what tags or folders to apply this style to. For instance, `{"exampleTag":{"color":"yellow"}}` would color all notes with \#exampleTag yellow. You can style nodes using images in your vault with `{"shape": "image", "image": "http://localhost:3000/path/to/image"}.`
10 |
11 | When color-coding is set to Folders, use the path to the folder for this key. For instance, if you have a folder called `dailies`, use `{"dailies": {}}`. Use `{"/": {}}` for the root folder.
12 |
13 |
14 | See [this link](https://visjs.github.io/vis-network/docs/network/nodes.html) for all options for styling the nodes.
15 |
16 | Join the [[Discord]] for additional help (and to show off your configuration!).
17 |
18 | ## Special types
19 | - Use `{"defaultStyle": {}}` for the default styling of nodes
20 | - Use `{"image": {}}` to style images
21 | - Use `{"SMD_dangling": {}}` to style dangling notes (notes that don't have a real file, but are linked to)
22 |
23 | ---
24 | #howto
25 | - hasTopic [[Neo4j Graph View Plugin]]
26 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Semantic Markdown Converter Semantics.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | [[Semantic Markdown Converter]] collects all notes with extension .md in the input directory (default: `markdown/`). Each note is interpreted as follows:
6 | - Interprets [[tags]] as [[entity types]]
7 | - Interprets YAML frontmatter as entity properties
8 | - Interprets wikilinks as links with type `inline`, and adds content
9 | - Lines of the format `"- linkType [[note 1]], [[note 2|alias]]"` creates links with type `linkType` from the current note to `note 1` and `note 2`.
10 | - The name of the note is stored in the property `name`
11 | - The content of the note (everything except YAML frontmatter and typed links) is stored in the property `content`
12 | - Links to notes that do not exist yet are created without any types.
13 |
14 | This uses a very simple syntax for typed links. There is no agreed-upon [[Markdown]] syntax for this as of yet. See [[Link Types]] for a discussion on different formalizations.
15 |
16 |
17 | ---
18 | #howto
19 | - hasTopic
20 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Semantic Markdown Converter.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | This article is about the [[Python]] code that the [[Neo4j Graph View Plugin]] uses. In the near future, this code will be replaced with [[Javascript]]. See [[Roadmap#Port semantic markdown convert to Javascript]].
6 |
7 | ## Semantic Markdown to Neo4j
8 | The [[Neo4j Graph View Plugin]] uses the Python package `semantic-markdown-converter`. The code is [in the same repository](https://github.com/HEmile/semantic-markdown-converter/tree/main/smdc).
9 | It creates an active data stream from a folder of Markdown notes to a Neo4j database.
10 |
11 | ### Getting started
12 | Note: The obsidian plugin automatically installs this package!
13 |
14 | Requires python 3.5+ and Neo4j desktop
15 |
16 | - Install with `pip install --upgrade semantic-markdown-converter`
17 | - Create a new database in Neo4j desktop and start it
18 | - Run `smds --input "folder with notes" --password "neo4j database password"`
19 |
20 | WARNING: This clears all current data in the active neo4j database!
21 | ### Supported input formats
22 | There is currently only one input format supported. An issue or use a pull request for different formats are appreciated! In particular for different markdown syntax for interpreting semantic links.
23 |
24 | ### Semantic Markdown to Neo4j server
25 | The command `smds` first uploads the complete folder of notes into the active Neo4j database. Then, it listens to changes in the notes to update the Neo4j database.
26 |
27 | #### Options
28 | - `--password`: Provide the password of the Neo4j database
29 | - `--input`: Provide the folder where to look for notes
30 | - `--index_content`: Set to true if you want Neo4j Bloom to search through the content of your notes when using the search bar. Can impact performance.
31 |
32 | ### Conversion mode
33 | The command `smdc` only converts the input folder, but does not create a stream.
34 | #### Neo4j
35 | Streams the input into the currently active Neo4j database. WARNING: This clears all the data in your database by default! Run with `--retaindb` if this is not desired.
36 | 1. Start the database in Neo4j you want to use
37 | 2. Run using `smdc --input "folder with notes" --password "neo4j database password"`. This can take a couple of minutes for large vaults.
38 |
39 | ---
40 | #project #topic
41 | - hasTopic [[Semantic Obsidian]]
42 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Semantic Obsidian edge styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | An example of edge styling which can be used for the [[Semantic Obsidian]] vault (ie, this vault).
6 |
7 | ```json
8 | {"defaultStyle":{
9 | "font":{"size":12,"strokeWidth":2},
10 | "width":0.5
11 | }, "inline": {
12 | "width": 0.3,
13 | "color": "gray"
14 | }, "hasTopic": {
15 | "width": 1,
16 | "color": "#F79767"
17 | }, "subset": {
18 | "width": 2.7,
19 | "color": "#F79767"
20 | }, "author": {
21 | "width": 0.3,
22 | "color": "black",
23 | "arrows": "",
24 | "font": {"size": 0}
25 | }
26 | }
27 | ```
28 |
29 | ---
30 | #example
31 | - hasTopic [[Edge styling]]
32 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Archived/Semantic Obsidian node styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | An example of node styling which can be used for the [[Semantic Obsidian]] vault (ie, this vault).
6 |
7 | ```json
8 | {"defaultStyle":{
9 | "size":9,
10 | "font":{"size":12,"strokeWidth":1},
11 | "borderWidth":0,
12 | "widthConstraint":{"maximum":150},
13 | "shape": "dot"
14 | },"image":{
15 | "size":40,
16 | "font":{"size": 0}
17 | },"author":{
18 | "size":5,
19 | "color":"black",
20 | "font":{"size": 8, "strokeWidth": 0, "color": "black"},
21 | "shape": "text"
22 | }, "howto":{
23 | "color": "#90cfff",
24 | "shape": "box",
25 | "font": {"size": 10, "strokeWidth": 1}
26 | }, "topic": {
27 | "color": "#F79767",
28 | "size": 18,
29 | "font": {"size": 16, "strokeWidth": 1},
30 | "shape": "ellipse"
31 | }
32 | ```
33 |
34 | ---
35 | #example
36 | - author [[Emile van Krieken]]
37 | - hasTopic [[Node styling]]
--------------------------------------------------------------------------------
/docs/Archived/Using the Neo4j Graph View.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 | ## Getting started
5 | ### Opening the Graph View
6 | On an open note, click the three dots in the right-upper corner, and select: "Open Neo4j Graph View":
7 |
8 | ![[Screen Recording 2021-01-02 at 15.32.58.mp4]]
9 |
10 | You can also use the command "Neo4j Graph View: Open local graph of note". You can run commands using ctrl/cmd+p. Alternatively, you can bind this command to a hotkey in the Obsidian settings.
11 |
12 | ![[Pasted image 20210101144050.png]]
13 |
14 | Finally, you can right-click on a file and open the graph from there:
15 | ![[Pasted image 20210102141546.png|300]]
16 |
17 | The local graph of a node shows the opened note and all other notes that are linked to it (including 'backlinks'). It will show also show images in your notes within the graph. I'll work on doing a preview of videos as well.
18 |
19 | Hovering over a node or a relationship gives a preview of the corresponding note and context of the relation.
20 | ![[Screen Recording 2021-01-02 at 15.38.11.mp4]]
21 | ### Interacting with the graph
22 | Click on a node to open it in Obsidian:
23 |
24 | ![[Screen Recording 2021-01-02 at 15.01.02.mp4|300]]
25 |
26 | Double-click on a node to show ("expand") its neighbors. Neighbors are the outgoing links and the backlinks.
27 |
28 | ![[Screen Recording 2021-01-02 at 15.05.43.mp4]]
29 |
30 | Hold shift, then click and drag in the graph view to select nodes.
31 | ![[Screen Recording 2021-01-02 at 15.09.51.mp4]]
32 |
33 | Right-click in the graph view to open the context menu. This can be used to open the corresponding file in several places.
34 |
35 | ![[Screen Recording 2021-01-02 at 15.14.06.mp4]]
36 |
37 | The context menu has some options to manipulate what you see in the graph. One very useful thing is to hide some nodes that clutter up the view. This is done by shift-draggin to select the nodes to hide, then using the context menu and click on "Hide selection". You can also use the "H" button to hide the selected nodes.
38 |
39 | ![[Screen Recording 2021-01-02 at 15.24.43.mp4]]
40 |
41 | The other options are:
42 | -
43 | - **Expand selection** (hotkey E): "Expand" the neighbors of all selected nodes. This will add all nodes related to the selected nodes.
44 | - **Invert selection** (hotkey I): Select all the nodes that are not currently selected.
45 | - **Select all** (hotkey A): Select all nodes.
46 |
47 | The graph view will also add nodes corresponding to files you visit in Obsidian, to create a "path" of nodes you visited.
48 |
49 | ![[Screen Recording 2021-01-02 at 15.43.17.mp4]]
50 |
51 | The graph view will also automatically update with changes you make in the note.
52 |
53 | ![[Screen Recording 2021-01-02 at 14.19.42.mp4]]
54 |
55 | The settings contains several options, such as coloring based on folders and a hierarchical layout.
56 |
57 | ## Advanced use
58 | ### Styling
59 | You can style both nodes and edges, as shown in the above videos. See [[Node styling]] and [[Edge styling]] for guidance on how to do this.
60 | ### Cypher Querying
61 | You can do very complicated querying using the [[Cypher]] query language. Create code blocks with language `cypher`. In this code block, create your Cypher query. Then, when the cursor is on this code block, use the Obsidian command 'Neo4j Graph View: Execute Cypher query'. Example:
62 |
63 | ![[cypher_querying.png]]
64 |
65 | [[Contributing]]
66 |
67 | ---
68 | #howto
69 | - hasTopic [[Neo4j Graph View Plugin]]
70 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Contributing.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Contributions are very much welcomed. The easiest way to get started is to join the [[Discord]] server to get talking! Here are some ways to help:
6 |
7 | ## Designing plugins
8 | Ideally, the features of [[Juggl]] and plugins using the [[Juggl API]] would be designed with the Obsidian community. Your input is very welcome, especially on features mentioned on the [[Roadmap]]. The best way to help here is by joining the [[Discord]] server.
9 |
10 | ## Contributing to this vault
11 | This vault is publicly available at https://github.com/HEmile/juggl/tree/main/docs. If you know of a cool way to contribute, for example by writing or improving a guide or sharing something cool you made with a plugin, please submit a pull request!
12 | If you do, please add - author \[\[\]\] links to your profile.
13 |
14 | ## Help develop Juggl and other plugins
15 | If you know some programming, help is definitely appreciated! See the [[Roadmap]] for possible features to help on, or submit a pull request to the github repo https://github.com/HEmile/juggl .
16 |
17 |
18 | ---
19 | #development
20 | - hasTopic [[Juggl]]
21 | - author [[Emile van Krieken]]
22 |
--------------------------------------------------------------------------------
/docs/Discord.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | image: https://cdn4.iconfinder.com/data/icons/logos-and-brands/512/91_Discord_logo_logos-512.png
4 | ---
5 |
6 | The [Discord](https://discord.com/) server for [[Juggl]] is open for everyone! You can join the server with [this link](https://discord.gg/sAmSGpaPgM).
7 |
8 | Current goals of the server:
9 | - Discuss [[Juggl]]
10 | - Show off graphs
11 | - Discussing advanced use
12 | - [[Styling]] of the graph, in particular [[CSS Styling|CSS]] and [[YAML Styling|YAML]].
13 | - [[Workspace mode]]
14 | - Usage of the [[Juggl code block|code fence]]
15 | - Feature requests and discussion
16 | - Discuss ideas related to [[Semantic Obsidian]]
17 | - [[Obsidian]] plugin ideas
18 | - [[Link Types]] formalizations
19 | - Provide a space to collaborate on plugins using the [[Juggl API]]
20 |
21 | ---
22 | #development
23 | - hasTopic [[Semantic Obsidian]]
24 | - hasTopic [[Juggl]]
25 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Emile van Krieken.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [Emile]
3 | image: https://pbs.twimg.com/profile_images/1087342750679347200/mQMh0604_400x400.jpg
4 | ---
5 |
6 | I am the developer of [[Juggl]]! Nice to meet you :)
7 |
8 | ## Links
9 | - [Twitter](https://twitter.com/EmilevanKrieken)
10 | - [Github](https://github.com/HEmile)
11 | - [Personal website](https://emilevankrieken.com/)
12 | - [LinkedIn](https://www.linkedin.com/in/emile-van-krieken-135a43b7)
13 |
14 |
15 | ---
16 | #author
17 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Breadcrumbs code blocks.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | As part of the [[Breadcrumbs integration]], you can use code blocks for querying in the Breadcrumbs plugin can visualize the results using [[Juggl]]! See this guide for more information https://github.com/SkepticMystic/breadcrumbs/wiki/Codeblocks .
6 |
7 | These code blocks support the same options as [[Juggl code block]]s:
8 | ![[Juggl code block#Code block options]]
9 |
10 | ---
11 |
12 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Breadcrumbs integration.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Juggl is tightly integrated with the [Breadcrumbs](https://github.com/SkepticMystic/breadcrumbs) plugin! If you have Breadcrumbs installed, it will add all its edges to your Juggl graphs using [[Link Types]]. This can be used to incorporate the Dataview inline attributes syntax, such as `hasTopic:: [[artificial intelligence]]`.
6 |
7 | You can visualize the *up* and down *hierarchies* using the [Juggl View](https://github.com/SkepticMystic/breadcrumbs/wiki/Views#juggl-view). It uses a custom [[Layouts|hierarchical layout]] for the best insight. See [the Breadcrumbs wiki for documentation](https://github.com/SkepticMystic/breadcrumbs/wiki/Views#juggl-view).
8 |
9 | ![[Pasted image 20220127142903.png]]
10 |
11 | Custom hierarchy visualizations can also be created using [[Breadcrumbs code blocks]].
12 |
13 | ---
14 |
15 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Export to other programs.md:
--------------------------------------------------------------------------------
1 | Juggl supports exporting the graph to [Cytoscape](https://cytoscape.org/ "Cytoscape: An Open Source Platform for Complex Network Analysis and Visualization").
2 |
3 | # Cytoscape
4 | You can save the graph in the [[Workspace mode]], then look in the Juggl plugin folder for the saved json file. You should be able to import this into Cytoscape desktop
5 |
6 | ---
7 | #feature
8 |
--------------------------------------------------------------------------------
/docs/Features/Filtering.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [Filter, filter, filters]
3 | ---
4 |
5 | You can filter the nodes in the graph using the Filter toolbar:
6 |
7 | ![[Pasted image 20210413145227.png]]
8 |
9 | This filter also appears in the [[Style Pane]]:
10 |
11 | ![[Pasted image 20210413145921.png]]
12 |
13 | The syntax of this simulates [the search syntax in Obsidian](https://help.obsidian.md/Plugins/Search), with some limitations and extra features.
14 |
15 | # Search Operators
16 | - `file:`, `path:`, `content:` and `tag:` all work as documented in the [Obsidian help vault](https://help.obsidian.md/Plugins/Search)
17 | - `class:` Search based on [[CSS Styling#Classes|CSS class]].
18 | - `raw:` Search using a [[CSS Styling#Selectors|CSS selector]]. For example, if you have a YAML attribute like `year`, you can get all nodes after 2000 using `raw:[year>2000]`.
19 | - Any attribute you use in your YAML frontmatter can be used for querying, for instance `aliases:`, `color:` and `title:`.
20 |
21 | ## Tips
22 | - Hiding **attachments**: `-class:file`
23 | - Hiding **images**: `-class:image`
24 | - Hiding **dangling nodes**: `-class:dangling`
25 | - You can add those filters to the [[Style Pane]] to quickly hide and unhide them
26 |
27 | ## Limitations
28 | Regex does not work, nor do the `section:`, `line:` and `block:` operators.
29 |
30 | ---
31 | #feature
32 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Global Graph mode.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [global graph]
3 | ---
4 |
5 | [[Juggl]] supports a global graph like the one in [[Obsidian]] that shows all your notes in a single graph. You can open it from the left ribbon:
6 |
7 | ![[Pasted image 20210330193014.png]]
8 |
9 | You will get a warning sign when you first open the Global Graph view:
10 | ![[Pasted image 20210402152820.png]]
11 |
12 | Like this warning says, Juggl is not designed for larger vaults, and opening the global graph will very likely freeze Obsidian! This functionality is only provided as a convenience option for smaller vaults (like the one you're looking at).
13 |
14 | If you are looking for a global graph for larger vaults, we advise to stick with the vanilla [[Obsidian]] graph. It is exceptionally well optimized and can look very beautiful with the color group functionality. While there are plans to include a performance mode to scale to slightly larger graphs, it is highly unlikely Juggl will ever manage graphs as large as in the vanilla Obsidian graph.
15 |
16 | ---
17 | #feature
18 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Juggl code block.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [code fence, code block]
3 | ---
4 |
5 | ![[code_fence.gif|400]]
6 |
7 | You can use 'code fences' to embed [[Juggl]] graphs inside notes. You can also do this using the [[Breadcrumbs]] plugin with [[Breadcrumbs code blocks]]. These code blocks have tonnes of (shared) options. See [[#Code block options]] for a full overview.
8 |
9 | For example, the following code block:
10 |
11 | ~~~
12 | ```juggl
13 | local: Juggl code fence
14 | ```
15 | ~~~
16 |
17 | will display when using Juggl as:
18 |
19 | ![[Pasted image 20210413150208.png|300]]
20 |
21 | The code fence is in the familiar YAML syntax.
22 |
23 | ## Creating a Juggl code block
24 | The code fence requires one of currently two **modes**. You can use either `local` for the graph around a node... (To write!)
25 |
26 | ## Code block options
27 | Add these fields as options in YAML syntax. The default value is in between parentheses.
28 | - `layout` (force-directed). The layout used for the graph. Choose from `force-directed, circle, grid, hierarchy`
29 | - `fdgdLayout` (cola): The algorithm to use for force-directed layouts. Choose from `cola, d3-force`
30 | - `filter` (''): A [[Filtering|Filter]] to use on the graph
31 | - `width` (100%): The width of the canvas created by the code block
32 | - `height` (750px): The height of the canvas created by the code block
33 | - `limit` (250): The maximum amount of nodes to display in the visualization
34 | - `metaKeyHover` (true): Whether to only show hover previews when the meta key (ctrl/cmd) is down
35 | - `navigator` (true): Whether to show the 'mini-map' in the bottom-right corner
36 | - `toolbar` (true): Whether to show the toolbar on top
37 | - `zoomSpeed` (1): How quickly to zoom in and out
38 | - `autoAddNodes` (false): Whether to automatically add the corresponding node when you switch to a note
39 | - `autoExpand` (false):
40 | - `autoZoom` (false): Whether to automatically zoom such that the whole graph is visible. This is done when a layout is finished
41 | - `expandInitial`: (false): Whether to automatically expand the sets of nodes from the query. Warning: This can create very big graphs!
42 |
43 | ---
44 | #feature
45 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Layouts.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [layout, hierarchical layout]
3 | ---
4 |
5 | ![[layouts.gif|400]]
6 |
7 | [[Juggl]] contains (currently) four different layout options. You can choose a layout from the buttons on the left of the toolbar:
8 | ![[Pasted image 20210403151424.png|400]]
9 |
10 | In order, these are the following layouts:
11 |
12 | - **Force directed layout**: A standard force directed layout, where nodes push each other away and links try to keep nodes together. Juggl uses the [Cola layout](https://github.com/cytoscape/cytoscape.js-cola) by default, but this can sometimes give weird vertical results. A more standard approach that is [like Obsidians graph](https://github.com/shichuanpo/cytoscape.js-d3-force) can be used from the settings under **Extensions > Force Directed Layout**. ![[Pasted image 20210408165620.png|400]]
13 | - **Concentric**: Puts all nodes in a circle, with the 'focused nodes' in the center. The focused nodes are the nodes around which we use the local mode, or expanded nodes. ![[Pasted image 20210408165722.png|400]]
14 | - **Grid**: A standard grid-like layout, similar to Roam Research. ![[Pasted image 20210408165744.png||400]]
15 | - **Hierarchical**: Puts the notes in a hierarchy over links. This uses the [Dagre algorithm](https://github.com/cytoscape/cytoscape.js-dagre). Used in the [[Breadcrumbs integration]] for best effect. ![[Pasted image 20210408165833.png|400]]
16 |
17 |
18 | ---
19 | #feature
20 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Local Graph mode.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | The local graph mode simulates the local graph of [[Obsidian]]. It will display the currently active note and the notes around it.
6 |
7 | I'm planning to implement a depth-slider for this later!
8 |
9 | ---
10 | #feature
11 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Nodes Pane.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 | The nodes pane opens, together with the [[Style Pane]], in the right sidebar of [[Obsidian]]. It shows a list of nodes in the currently active [[Juggl]] graph.
5 |
6 | Clicking on an item in the list currently opens the associated file. You can also right-click on items in the list to open a context menu.
7 |
8 | The Nodes Pane can also be used to restore nodes you filtered from the graph under 'Hidden nodes'.
9 |
10 | ![[Pasted image 20210403151146.png]]
11 |
12 | The color of the items is the same as the color of the nodes in the graph.
13 |
14 | ---
15 | #feature
16 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Styling/CSS Styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [CSS]
3 | image: "files/CypherQuerying.png"
4 | ---
5 |
6 | For complete control over [[Styling]], you can use CSS. This has a somewhat higher learning curve, but is extremely powerful! It allows you to create rule-based styling so you can visually represent concepts or attributes in your vault.
7 |
8 | To use the CSS functionality, edit `.obsidian/plugins/juggl/graph.css`. Edits in this file should automatically change the style of currently open graphs.
9 | You can also open this file from the Juggl settings:
10 |
11 | ![[Pasted image 20210422092407.png]]
12 |
13 | This document acts as an overview of common and useful options for Juggl. For documentation on everything that's possible (_a lot!_), see the [Cytoscape.js styling documentation](https://js.cytoscape.org/#style).
14 |
15 | We will first discuss how to [[#Selectors|select certain objects]], then discuss common [[#Properties|properties]] you might want to change, then finally show a couple of [[#Snippets|snippets]] to get started.
16 |
17 | If you prefer to start off with examples, I'd recommend immediately jumping to [[#Snippets]].
18 |
19 | If you need more help, feel free to join the [[Discord]] where help is provided for all your styling questions!
20 |
21 | # Selectors
22 | [Selectors](https://www.w3schools.com/cssref/css_selectors.asp) are used to filter what objects to style. The two main 'elements' that can be targeted are `node` and `edge`.
23 | ## Classes
24 | Classes can be selected using `.class`. Available classes that are useful to style different nodes in Juggl are:
25 | - `.tag-tagname`: Targets all nodes with the tag #tagname
26 | - `.type-typename`: Targets all edges with the [[Link Types|type]] 'typename'
27 | - `.has-incoming-typename`: Targets all nodes that have an edge with [[type]] 'typename' coming into it.
28 | - `.has-outgoing-typename`: Targets all nodes that have an edge with [[type]] 'typename' going out of it.
29 | - Any class in the `cssclass` property in your [[YAML Styling|YAML]] frontmatter is also available on that node.
30 | - `.dangling`: Targets dangling nodes (nodes that aren't created as a file)
31 | - `.image`: Targets all nodes that are rendered as images. This is image files, but also notes that are styled with the `image` [[YAML Styling|YAML]] property. Similar for `.audio`, `.video` and `.pdf`.
32 | - `.file`: Targets all attachments (everything that does not have the `.md` extension)
33 | - `.note`: Targets all nodes that represent `.md` files.
34 | - `.global-3`: Targets nodes in the **fourth** global [[Style Pane|style group]](note: zero-based indexing!)
35 | - `.local-5`: Targets nodes in the fifth local style group
36 |
37 | There are also several classes to target nodes with a certain state:
38 | - `:selected`: Targets selected nodes
39 | - `.pinned`: Targets 'locked' nodes
40 | - `.expanded`: Targets [[Workspace mode|expanded]] nodes
41 | - `.hover`, `.unhover`: Targets hovered nodes
42 | - `.active-node`: Targets currently active node (usually currently open note)
43 | - `.connected-active-node`: Targets neighbours of active node
44 | - `.inactive-node`: Targets nodes not in the neigbourhood of the active node
45 | - `.filtered`: Targets nodes filtered using the [[Filtering|filter]] toolbar
46 | - `.hard-filtered`: Targets nodes filtered using user interaction
47 | - `.protected`: Internal class that targets nodes that cannot be automatically removed
48 | - `:loop`: Targets edges that are self-loops (same source and target)
49 |
50 | ## Attributes
51 | Attributes are values on nodes that you can use for styling. You can refer to these attributes using `data(attribute_name)`. You can also use them to create linear maps using `mapData(attribute_name, in_min, in_max, out_min, out_max);`. Attributes can also be used to select elements, see [this page](https://js.cytoscape.org/#selectors/data) for all options.
52 |
53 | ### Nodes
54 | - Any [[YAML Styling|YAML]] property can be referenced by name. For example, if you have `cooking_time: 34` in your YAML frontmatter, you can use
55 | ```css
56 | node[cooking_time] {
57 | width: data(cooking_time);
58 | }
59 | ```
60 | to scale the width of nodes by cooking time.
61 | - `name`: The name of the node
62 | - `path`: The path (relative to vault) of the file the node represents. This can be used to select based on folders:
63 | ```css
64 | node[path ^= 'folder1/folder2/'] {
65 | background-color: red;
66 | }
67 | ```
68 | This means: Select all nodes with paths that start with `folder1/folder2`, ie files in that folder.
69 | - `content`: The content of the note. You can use this to search for some text, for instance:
70 | ```css
71 | node[content @*= 'juggl'] {
72 | background-color: red;
73 | }
74 | ```
75 | This means: Select all notes that contain 'juggl', case insensitive.
76 |
77 | ### Edges
78 | - `context`: The line the link is in. This gives some context about where the link is used and is used in the edge hover preview. Can be used to filter for certain lines with the same structure.
79 | - `alias`: The alias used on the link. Only present if an alias is used.
80 | - `degree`: The amount of edges connected to the node.
81 | - `edgeCount`: When edges are merged (default), this is the total amount of edges of a certain type that are merged together. This is used by default to make lines thicker for merged edges that represent more links.
82 | # Properties
83 | Cytoscape.js provides many properties to target for styling, both for [nodes](https://js.cytoscape.org/#style/node-body) and [edges](https://js.cytoscape.org/#style/edge-line).
84 |
85 | ## Nodes
86 | Useful common properties are listed as following. See [this link](https://js.cytoscape.org/#style/node-body) for all options. There are _way_ more than listed here, so if you're looking for something specific, make sure to check out that link.
87 | - `width`, `height`: Change width and height, individually
88 | - `shape`: Node shape, choose from the same options as in the [[Style Pane]].
89 | - `background-color`: Color of the node
90 | - Check [this link](https://js.cytoscape.org/#style/node-body) for options with gradient-coloring
91 | - `background-opacity`: Opacity of the node
92 | - `border-width`, `border-color`, `border-opacity`: Style the border of the node
93 | - `border-style`: Choose from `solid, dotted, dashed, double`
94 | - `background-image`: URL to the background image. See [this link](https://js.cytoscape.org/#style/background-image) and [[YAML Styling]] for nuances
95 | - There is a significant amount of options for dealing with images, such as how it is contained in the node, smoothing, opacity, offset, etc. See [this link](https://js.cytoscape.org/#style/background-image).
96 | - `label`: The text on the node, usually the name of a note.
97 | - Many standard options for styling this are available like the `font-family`, see [this link](https://js.cytoscape.org/#style/labels). You can for example change the positioning of the text to be inside the node. The
98 | - `display`: Set to none to not display the element.
99 |
100 | ## Edges
101 | Edges can also be completely styled. See [this link](https://js.cytoscape.org/#style/edge-line) for all options.
102 | - `width`: Width of the line
103 | - `curve-style`: The style of the curve of the line. There are many, complex options. See [the full documentation](https://js.cytoscape.org/#style/edge-line). By default, Juggl uses Bezier edges, which is relatively expensive. For performance reasons, you can use the haystack style.
104 | - `line-color`: Color of the edge
105 | - `line-style`: Choose from `solid, dotted, dashed`
106 | - `line-opacity`: Opacity of the edge.
107 | - `label`: The text on the node
108 | # Snippets
109 | **Style [[Link Types]]**: Color links with the `author` type red.
110 | ```css
111 | .type-author {
112 | line-color: red;
113 | }
114 | ```
115 |
116 | **Map cooking time to colour**: Changes from the color blue to red depending on how long it takes to cook a meal:
117 | ```css
118 | node[cooking-time] {
119 | background-color: mapData(cooking-time, 1, 120, blue, red);
120 | }
121 | ```
122 |
123 | **Change opacity and width of a line**, depending on how many connections (from 1 to 15) there are from one node to the other:
124 | ```css
125 | edge[edgeCount] {
126 | width: mapData(edgeCount, 1, 15, 0.5, 3);
127 | line-opacity: mapData(edgeCount, 1, 15, 0.5, 0.9);
128 | }
129 | ```
130 |
131 | **Display the context of a link**: This will display the sentences around where the link appears. This can be a bit messy!
132 | ```css
133 | edge.inline {
134 | label: data(context);
135 | text-opacity: 0.8;
136 | font-size: 2;
137 | text-wrap: ellipsis;
138 | text-max-width: 100px;
139 | }
140 | ```
141 |
142 | ![[Pasted image 20210414175943.png|500]]
143 |
144 | You can also only show this whenever you are hovering over the edge. You have to activate 'Hover on edges' in the Juggl settings for this feature:
145 | ```css
146 | edge.inline.hover {
147 | label: data(context);
148 | ...
149 | }
150 | ```
151 |
152 | **Text in a box**: One styling I love is to have rectangle nodes that contain some text. This can be achieved (imperfectly!) using
153 | ```css
154 | .tag-paper {
155 | shape: rectangle;
156 | width: 50px;
157 | height: 45px;
158 | font-size: 5;
159 | text-valign: center;
160 | text-max-width: 45px;
161 | text-opacity: 1;
162 | }
163 | ```
164 |
165 | ![[Pasted image 20210414182140.png|400]]
166 |
167 | **Text wrapping for non-Latin script**: The text in a box will not work for languages using different script, like Japanese. For these, you could try the following snippet by Kazdon:
168 | ```css
169 | .note {
170 | shape: rectangle;
171 | width: 40px;
172 | height: 20px;
173 | text-valign: center;
174 | text-max-width: 35px;
175 | text-overflow-wrap: anywhere;
176 | }
177 | ```
178 | And similar for inline context on edges:
179 | ```css
180 | edge.inline {
181 | label:data(context);
182 | text-wrap: wrap;
183 | text-max-width: 250px;
184 | text-overflow-wrap: anywhere;
185 | }
186 | ```
187 | **Only show icons, not shapes**: If you only want to show the icon of a node and not the shape around it, you can use
188 | ```css
189 | node {
190 | background-opacity: 0;
191 | border: 0;
192 | shape: rectangle;
193 | }
194 | ```
195 | ![[Pasted image 20220121103800.png]]
196 |
197 | # Current limitations
198 |
199 | - CSS variables like `var(--background-primary)` will not be recognized. If this is something you need, please add a pull request.
200 |
201 | - `not()` does not seem to work.
202 |
203 | ---
204 | #feature
205 | - author [[Emile van Krieken]]
206 | - hasTopic [[Styling]]
--------------------------------------------------------------------------------
/docs/Features/Styling/Images.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Images are implemented using a bit of a hack with a local server that hosts the images in your vault. Importantly, **if you use multiple vaults** you will need to assign a unique port to each vault to ensure Juggl knows what vault to look up.
6 | This can be done in the settings under `Advanced -> Image Server Port`.
7 |
8 | ---
9 | - hasTopic [[Styling]]
10 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Styling/Style Pane.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [style group]
3 | ---
4 |
5 | ![[style_pane.gif|400]]
6 |
7 | The easiest way to [[Styling|style]] a group of nodes is the Style Pane. You can style nodes using a simple user interface that already provides a large amount of options.
8 |
9 | The style pane is a separate view which opens by default in the right sidebar of [[Obsidian]]:
10 |
11 | ![[Screen Recording 2021-04-14 at 17.29.09.mp4]]
12 |
13 | A group of nodes is chosen using a [[Filtering|Filter]]. The styling options for each group of nodes are
14 | - Show or hide the group
15 | - Shape and color
16 | - Icon and icon color
17 | - Relative size of the nodes and text
18 |
19 |
20 |
21 | ## Global and local style groups
22 | With the style pane you can create both local and global style groups. What's the difference?
23 |
24 | ### Global style groups
25 | Global style groups are applied to every [[Juggl]] graph you open. They are saved together with your global Juggl settings.
26 |
27 | ### Local style groups
28 | Local style groups are specific to one graph. The style pane will show the local style groups of your currently active graph. So, if you click on the workspace leaf where your graph is opened, it will show the local style groups associated with that graph!
29 |
30 | Local style groups are saved together with a [[Workspace graph]].
31 |
32 | ---
33 | #feature
34 | - author [[Emile van Krieken]]
35 | - hasTopic [[Styling]]
--------------------------------------------------------------------------------
/docs/Features/Styling/Styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [style]
3 | ---
4 |
5 | You can style the graph of [[Juggl]] in many ways. On this page you can find for each use case how best to use the styling options provided.
6 |
7 | ## Styling groups of nodes and edges
8 | Styling groups of nodes can be done using the [[Style Pane]], which is easy but limited, and using [[CSS Styling|CSS]], which has a lot more options but is also harder to get started with.
9 |
10 | It is recommended to start with the Style Pane, but if you want to go all-in to the plugin, it can be worth it to learn CSS styling!
11 |
12 | ## Styling individual nodes
13 | The third option for styling is using the [[YAML Styling|YAML frontmatter]] of Obsidian notes. This allows for styling individual nodes. You can for example add an image in YAML that Juggl will show in the node to make it easily recognizable.
14 |
15 | ## Styling individual edges
16 | Juggl does not yet support styling individual edges, but this will be possible in the future through the new implementationo [[Link Types]]. You can use [[CSS Styling|CSS]] to style based on simple link types, though!
17 |
18 | ## FAQ
19 | ### What priority does each styling option get?
20 | In general, the idea is to make more specific styling options have higher priority. That is, in decreasing order of priority, we have [[YAML Styling|YAML]], local [[Style Pane|style groups]], global style groups, CSS and default styling.
21 |
22 |
23 |
24 | ---
25 | #howto
26 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Features/Styling/YAML Styling.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [YAML, YAML frontmatter]
3 | title: YAML
4 | color: blue
5 | image: files/img.png
6 | ---
7 |
8 | YAML frontmatter styling is used to selectively style individual nodes. A cool application is to assign images to nodes!
9 | The following properties are supported out of the box, but you can use any property you like (read on!).
10 | - `title`: Change the displayed label on a node. Works very well with Zettlkasten workflows
11 | - `color`: Change the color of a node. For example, you can do hexidecimals like `color: '#123456'` or with color names: `color: blue`.
12 | - `shape`: Change the shape of a node. You can use the same shapes as in the [[Style Pane]].
13 | - `width` and `height`: Change the width and height of a node.
14 | - `image`: Use the given image as a background image on the node. You can use both external links (https) to a website image, or an image in your vault. Some caveats: External images can only be used if the site is configured to accept cross-reference requests! This means it won't work for the majority of external links.
15 | - `cssclass`: Can be used to assign [[CSS Styling#Classes|classes]] to the notes for [[CSS Styling]].
16 | A better option is to download the image and save it to your vault. To reference an image in your vault, you need to use the **path to the image**, not just the name of the image. For instance, if your image `img.png` is in the `files` folder, you should do `image: files/img.png`.
17 | - `cssclass`: List of [[CSS Styling|CSS]] classes that can be used for additional styling of nodes.
18 |
19 | ## Using other YAML properties
20 | If you have been using other YAML properties that you would like to map to some styling option, that's possible! You will need to use some [[CSS Styling|CSS]] though.
21 |
22 | Here is how some of the given properties above are implemented in CSS:
23 |
24 | ```css
25 | node[title] {
26 | label: data(title);
27 | }
28 |
29 | node[shape] {
30 | shape: data(shape);
31 | }
32 |
33 | node[image] {
34 | background-image: data(image);
35 | }
36 | ```
37 |
38 | Something similar can be done for any YAML property! Select nodes that have the property using `node[property_name]`, then assign the styling attribute using `attribute: data(property_name)`.
39 |
40 | If you have been using categories, like the genre of an album, you can use the following CSS:
41 |
42 | ```css
43 | node[genre = 'drama'] {
44 | background-color: black;
45 | }
46 | ```
47 |
48 | More ways to filter data are found in the [Cytoscape.js documentation](https://js.cytoscape.org/#selectors/data).
49 |
50 | ---
51 | #feature
52 | - author [[Emile van Krieken]]
53 | - hasTopic [[Styling]]
--------------------------------------------------------------------------------
/docs/Features/Workspace mode/Workspace graph.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | ---
6 | #feature
7 | - author [[Emile van Krieken]]
8 | - hasTopic [[Workspace mode]]
--------------------------------------------------------------------------------
/docs/Features/Workspace mode/Workspace mode.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | The Workspace Mode is the unique graph interactivity mode implemented in [[Juggl]]. It gives you full control over navigation in the graph, over what nodes are displayed and how nodes are laid out. Furthermore, you can save and load [[Workspace graph]]s to continue working on a graph.
6 |
7 | As an introduction, the design of the Workspace Mode can be compared to:
8 | 1. A 'desktop' of ideas, where everything you're currently working on is spatially laid out.
9 | 2. A 'brain' of visual concepts, that you can search through in a nonlinear fashion: Expand concepts and see where they lead, and find new connections between ideas.
10 |
11 | # Getting Started
12 | You can open the Workspace Mode by starting from a note. The easiest is using the 'file options' menu just like the local graph. This can be found in the hamburger menu above a note:
13 |
14 | ![[Pasted image 20210402154645.png|400]]
15 |
16 | With the default setting this opens the [[Local mode]]. You can activate the Workspace mode by clicking on this button in the toolbar:
17 |
18 | ![[Pasted image 20210402155246.png]]
19 |
20 | You can set Juggl to always open in the Workspace mode in the settings under **Extensions > Default mode**.
21 |
22 | ## Basic interaction
23 | In the workspace mode, you can drag around the screen to move it, and also drag nodes around to move them, like in other modes. However, the workspace mode contains additional interaction options.
24 |
25 | While holding shift, you can click and drag around the screen to select a group of nodes:
26 | ![[selectdrag.mp4]]
27 |
28 | Selected nodes can be interacted with through the [[#Toolbar]].
29 |
30 | ### Radial context menu
31 | To interact with a single node, click and hold on that node to open the **radial context menu**:
32 | ![[Screen Recording 2021-04-03 at 13.58.20.mp4]]
33 |
34 | **Open file**:
35 | ![[Pasted image 20210403140754.png|200]]
36 | This opens the select file in an existing or new leaf. Clicking on a node also opens the file.
37 |
38 | **Expand or Collapse**
39 | ![[Pasted image 20210403141344.png|200]]
40 |
41 | Expanding and collapsing is a central concept of the Workspace mode. When you **expand** a node, all its neighbors are added to the graph. When you **collapse** an expanded node, its neighbors are removed again. There are some subtleties here, which we will discuss later.
42 | Expanding nodes is the easiest way to explore your graph! You can also expand by **double-clicking** a node, or by pressing the **E** button.
43 |
44 | **Locking and unlocking**
45 | ![[Pasted image 20210403142046.png|200]]
46 | With this button, you can lock and unlock a node into one spot. This means it won't move using the layout options. This can be useful when you want to manually choose the positions of some nodes to ensure they're always in the same position.
47 |
48 |
49 | **Filter node**
50 | ![[Pasted image 20210403144754.png|200]]
51 |
52 | Filters the node from the view. You can add the node back again using the [[Nodes Pane]].
53 |
54 | **Fit view**
55 | ![[Pasted image 20210403143207.png|200]]
56 |
57 | Focus on the selected nodes and its neighbors, and zoom the view to fit on its neighborhood.
58 |
59 | ### Toolbar
60 | The toolbar is the set of buttons on the top of the Juggl view, with the following functions:
61 | ![[Pasted image 20210402162157.png]]
62 |
63 | These functions will apply to the full selection of nodes selected using shift-dragging! For instance, to hide a group of nodes, you would do:
64 |
65 | ![[Screen Recording 2021-04-03 at 14.59.13.mp4]]
66 |
67 | The first four buttons allow you to choose a [[Layouts|layout]]. To the right of that, you have the 'fit view' button which centers the view on the graph, a button to return to the [[Local mode]], and a button that navigates to the help vault (that you are reading right now).
68 |
69 | ### Saving and loading
70 | ![[save_workspace.gif||400]]
71 | ![[Screenshot 2021-04-03 at 15.01.44.png|200]]
72 |
73 | The highlighted button will let you save and load [[Workspace graph]]s. Click the button to open the Manage Workspace Graphs UI:
74 |
75 | ![[Pasted image 20210403150726.png]]
76 |
77 | This UI functions just like the [Manage Workspaces UI in Obsidian](https://help.obsidian.md/Plugins/Workspaces).
78 |
79 | ---
80 | #howto #feature
81 | - author [[Emile van Krieken]]
82 | - hasTopic [[Juggl]]
--------------------------------------------------------------------------------
/docs/Installing Juggl.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Installing Juggl is as easy as downloading and installing it from the 'Community plugins' section of the [[Obsidian]] settings.
6 | 1. Make sure 'safe mode' is turned off
7 | 2. Browse the Community plugins
8 | 3. Search for 'Juggl'
9 | 4. Click on the 'install' button. This might take a while, Juggl is 12+mb.
10 | 5. Activate the plugin ![[Pasted image 20210320161754.png]]
11 |
12 | # Pre-release versions
13 | There are currently no pre-release versions.
14 |
15 | ## Installation instructions for pre-release versions
16 | Unzip the downloaded file in `.obsidian/plugins/juggl/`. The easiest way to find this folder is to follow these steps:
17 | - Open the settings in Obsidian
18 | - Go to the 'Community plugins' tab
19 | - Make sure you deactivated safe mode
20 | - Click on the Open Plugins Folder icon: ![[Pasted image 20210320161536.png]]
21 | - In the resulting folder, create the `juggl` folder if you haven't already, then extract the downloaded file in there.
22 | - Activate the plugin ![[Pasted image 20210320161754.png]]
23 |
24 | ---
25 | #development
26 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Juggl API.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [API]
3 | ---
4 |
5 | The first release of the Juggl API is now available from https://github.com/HEmile/juggl-api .
6 |
7 | ![[Roadmap#^82c7c4]]
8 |
9 | ## Requirements
10 | Users of the API should be able to extend [[Juggl]] in the following ways. If something is missing, please [[Discord|let me know.]]
11 |
12 | ### Add additional data
13 | Add additional nodes and relations to the graph. This could for instance be used to [connect papers to their citations](https://forum.obsidian.md/t/show-online-literature-connections/10924) (and to papers they cite), like in [Connected Papers](https://www.connectedpapers.com/). There are many other sources of information to extract data from.
14 |
15 | Other ideas might be extracting a graph from the Markdown, such as adding the outline of a note like in the [Mind Map plugin](https://github.com/lynchjames/obsidian-mind-map), or developing new syntax for generating graphs.
16 |
17 | ### Manipulate the Graph View
18 | Add UI's on top of the graph view, or add ways of interacting with the visualization.
19 | Possible hooks:
20 | - Initialization of the visualization
21 | - Context menu
22 | - Before query
23 | - After nodes are added
24 |
25 | ### Manipulate styling of the graph
26 | Allow plugins to further manipulate styling of the graph.
27 |
28 | ## Development
29 | - All interfaces
30 | - Utility methods like tags parsing
31 |
32 | ---
33 | #development
34 | - hasTopic [[Juggl]]
35 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Juggl.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | Welcome to the documentation of Juggl.
6 |
7 | Juggl is the next generation of PKM-focused graph views! It is completely customizable and extendable, with many advanced features out of the box.
8 |
9 | - **Code** is on Github: https://github.com/HEmile/juggl
10 | - **Support the development** of Juggl:
11 | - Buy me a kofi: https://ko-fi.com/Emile
12 | - Paypal.me: https://paypal.me/EvanKrieken
13 |
14 | # Features
15 | ![[juggl trailer.gif]]
16 | ## Styling
17 | With Juggl you have completely control over the [[Styling|Style]] of your graph. You can use a special [[Style Pane]] that is very easy to use. For more advanced styling, you can use [[CSS Styling|CSS]] and [[YAML Styling|YAML]].
18 |
19 | ## Workspace mode
20 | A very extensive new [[Workspace mode]] designed for keeping the focus on just the right notes.
21 | **Interactivity**: You can control the highly interactive graph using a special **[[Workspace mode#Radial context menu|radial context menu]]** and the [[Workspace mode#Toolbar|toolbar]].
22 | - Select, expand and collapse nodes
23 | - Pin nodes in place
24 | - Hide and filter nodes from view
25 |
26 | **[[Workspace mode#Saving and loading|Save and load graphs]]** so you can always continue your work from where you left it.
27 |
28 | You can choose from **four [[Layouts|layout]] options**:
29 | 1. Force-directed
30 | 2. Circle
31 | 3. Grid
32 | 4. Hierarchical
33 |
34 | ### Breadcrumbs integration
35 | The popular Obsidian plugin for maintaining hierarchies '[Breadcrumbs](https://github.com/SkepticMystic/breadcrumbs)' is [[Breadcrumbs integration|tightly integrated]] with Juggl! You can render hierachies using Juggl or create custom [[Breadcrumbs code blocks]]! This one of the most useful applications of Juggl.
36 |
37 | ![[Pasted image 20220127142536.png]]
38 |
39 | ### Code block
40 | You can use "[[Juggl code block|code block]]s" to embed graphs within your Obsidian note! You can even use the graph you saved in the [[Workspace mode]].
41 |
42 | ### More!
43 | - **Mobile ready!** While still buggy, the graph works on mobile
44 | - Has a **navigation element** that keeps an overview of the total graph
45 | - Supports stylable [[Link Types]]. You can use this to add labels to edges, for example
46 | - Supports a [[Global Graph mode|global graph]] for small vaults, and an Obsidian-like [[Local Graph mode|local graph]].
47 | - Ready to be extended by other plugins through the [[Juggl API]]
48 |
49 | # Implementations and licensing
50 | Juggl currently only has an implementation for [[Obsidian]]. However, the meat of the code is not necessarily reliant on Obsidian and could be ported to other PKM software. If you are interested, you can contact [[Emile van Krieken|me]], preferrably on [[Discord]].
51 |
52 | Note that Juggl is GPL3 **dual-**licensed. Contact me for details.
53 |
54 |
55 |
56 |
57 | ---
58 | #plugin
59 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Link Types.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: [type]
3 | ---
4 | You can created Typed Links using the following list-based syntax:
5 | `- linkType [[note 1]], [[note 2|alias]]`. If you have [[Breadcrumbs integration|Breadcrumbs]] installed, its typed links such as `linkType:: [[note 1]]` are also added.
6 |
7 | For example, if you have a \[\[Rembrant\]\] note and you want to link it to \[\[The Night Watch\]\], you would add `- painted [[The Night Watch]]` to your Rembrant note.
8 |
9 | This vault contains many examples of such links at the bottom of the page. These will be visualized by [[Juggl]] as text on edges. For example, the typed links at the bottom of this page will be displayed as follows:
10 |
11 | ![[Pasted image 20210421133609.png|500]]
12 |
13 | Additionally, you can apply different styling using [[CSS Styling|CSS]] based on the type of the links to make these more distinct. This will [[Roadmap|in the future]] be possible using the [[Style Pane]]:
14 |
15 | ![[Pasted image 20210421133938.png|500]]
16 |
17 | Note: The `linkType` can only be a single word! This means `- has painted [[The Night Watch]]` will not be parsed as a typed link `has painted`.
18 |
19 | Furthermore, if you have the Breadcrumbs plugin installed, then with the [[Breadcrumbs integration]], it will also add all typed edges from that plugin. This includes those created with the Dataview inline attributes syntax `hasPainted:: [[The Night Watch]]`.
20 |
21 | ## Development
22 | This syntax has multiple issues. In this section we discuss ways to improve it that are not currently implemented:
23 | 1. It is metadata, and not inline. Most of the links people write in Obsidian are 'inline': They are part of the text, instead of seperate lines.
24 | 2. This syntax doesn't allow adding properties. For example, the relation `publishedIn` could have useful additional metadata, such as the year it was published. Similarly, when creating a list of ingredients, it'd be useful to also register the quantity needed for each ingredient.
25 | 3. You can only link the current note as a source. However, if, for example, you are writing a daily note, you might write that "Today, Joe Biden becomes the president of the US". The corresponding link might be \[Joe Biden\] -President->\[US\]. Otherwise, one would have to write this in a new "Joe Biden" note, even if this doesn't necessarily make sense while writing.
26 |
27 | To solve these issues we will work on a new, more general syntax. Currently, the idea is the following: `This recipe requires 20 grams of [[Rice|rice|ingredient|quantity=20 grams]]`. This is an inline syntax of the form `[[Note name|alias|linkType|property1=value1|property2=value]]`. However, this does not yet solve issue 3!
28 |
29 | A similar idea which is used in [Semantic Mediawiki](https://www.semantic-mediawiki.org/wiki/Semantic_MediaWiki) and which is going to be used in [Keypoints](https://keypoints.app), is `This recipe requires 20 grams of [[quantity=20 grams::ingredient::Rice|rice]]`. This puts the link type in the beginning, which can be more natural to read. It also helps standardize this syntax.
30 |
31 | Input for this syntax and ease of use is highly appreciated. We welcome you to join the discussion at [[Discord]].
32 |
33 |
34 | ---
35 | #topic
36 | - subset [[Semantic Obsidian]]
37 | - author [[Emile van Krieken]]
38 | - hasTopic [[Juggl]]
--------------------------------------------------------------------------------
/docs/Recommend plugins.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 | These plugins work especially well together with [[Juggl]], and are kept in mind while developing Juggl to ensure compatibility.
5 |
6 | - **[Breadcrumbs](https://github.com/SkepticMystic/breadcrumbs/)**: [[Breadcrumbs integration|Tightly integrated]] with Juggl using a custom view. Can render its hierarchies within [[Juggl]] using [[Breadcrumbs code blocks]]
7 | ![[Pasted image 20220127142903.png]]
8 | - **[Supercharged links](https://github.com/mdelobelle/obsidian_supercharged_links)**: Can be used to mimic the styling of links such that they have the same color as the juggl nodes.
9 | - **[Pane Relief](https://github.com/pjeby/pane-relief)**: Pane-based history is very useful when you use Juggl in the [[Workspace mode]] next to a markdown view.
10 | - **[Hover editor](https://github.com/nothingislost/obsidian-hover-editor)**: Allows editing notes right from within Juggl by hovering over nodes.
11 | ---
12 |
13 | - author [[Emile van Krieken]]
14 |
--------------------------------------------------------------------------------
/docs/Roadmap.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 |
6 | # Juggl
7 | ## Planned
8 | ### [[Neo4j Stream]]
9 | Export your vault to [[Neo4j]].
10 | Later on, this will allow for [[Cypher]] querying in [[Juggl]] ^2d1fd7
11 |
12 |
13 | ### [[Link Types]]
14 | Add better support for creating and maintaining link types. Also provide new syntax for inline link types and properties on links. A discussion on syntax is in [[Link Types]].
15 | - Inline typed links
16 | - Properties on links
17 | - Preview typed links using templates
18 | - Autocomplete typed links
19 |
20 | ### [[Style Pane]] for edges
21 |
22 | Makes it easier to style typed links, and to filter edges.
23 | ### Outline in compound nodes
24 |
25 | The outline of a note is essentially a tree. As it is completely hierarchical wrt the node representing the note, it can be nicely rendered and collapsed using compound nodes, like in
26 |
27 | __
28 |
29 | This will likely be used in the Style Pane for edges.
30 |
31 | ### Edit your data in the graph
32 | - Create edges by dragging nodes together
33 | - Add new nodes to the graph
34 | - Rename files from the graph
35 | - Edit YAML metadata
36 | - Drag files into the graph
37 |
38 | ### [[Juggl API]]
39 | It is easy using [[Cytoscape.js]] to create an API for other plugin developers to use, to interact with [[Juggl]]. This could allow extending the graph view with eg automatically adding data from external sources, such as citation graphs, or with a different syntax for creating graphs. ^82c7c4
40 |
41 | ### Minor
42 | - Preview movie and pdf files using thumbnails
43 | - Add external (Markdown) links to the graph. Clicking on that node opens the link in your browser
44 | - Size individual notes using YAML metadata
45 |
46 | ## Ideas to discuss
47 |
48 | ### Compound nodes to represent hierachies
49 |
50 |
51 | ---
52 | #development
53 | - hasTopic [[Semantic Obsidian]], [[Juggl]]
54 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Screen Recording 2021-04-14 at 17.29.09.mov:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/Screen Recording 2021-04-14 at 17.29.09.mov
--------------------------------------------------------------------------------
/docs/Search on Internet Plugin.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | ![[context_iframe.gif]]
6 | See the plugin [on Github](https://github.com/HEmile/obsidian-search-on-internet).
7 |
8 | ## Search on Internet
9 | Adds the option to search selected text on external websites, like Google and Wikipedia. You can add your own websites!
10 |
11 | 
12 |
13 | It also adds the search options to the file context menu to search based on the title of a note:
14 |
15 | 
16 |
17 | You can also right-click on an internal link to perform a search on that link:
18 |
19 | 
20 |
21 |
22 | ### Settings
23 | By default, the plugin comes with searches on Google and Wikipedia.
24 | You can add your own websites to search on in the settings.
25 |
26 | 
27 |
28 | For each website, fill in the following three fields:
29 | - Name: The name of the search. This will be displayed in the search bar and the context menu.
30 | - URL: The URL to open. `{{title}}` will be replaced by the current notes title. This is used as the 'query'.
31 | - Tags (optional): A list of tags for notes to display the search option on.
32 | In the example screenshot, this is used to only add the IMDB search on notes tagged with `#actor`, `#movie` or `#director` (in Dutch!)
33 |
34 | It's recommended to assign the command: "Search on Internet: Perform search" to a hotkey:
35 |
36 | 
37 |
38 |
39 | ### Credits
40 | Settings code is mainly taken from the [Templater plugin](https://github.com/SilentVoid13/Templater) by [SilentVoid13](https://github.com/SilentVoid13)
41 |
42 | Modal code is inspired by the [Citation plugin](https://github.com/hans/obsidian-citation-plugin/blob/master/src/modals.ts)
43 |
44 | ---
45 | #plugin
46 | - hasTopic [[Semantic Obsidian]]
47 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/Semantic Obsidian.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | ## Introduction
6 | Semantic Obsidian is a long-term project to think of and develop plugins inspired by [[Semantic Markdown]], [[Property Graphs]] and [[Semantic Desktop]]s.
7 |
8 | The goal is to create from Obsidian a [[Personal Knowledge Management]] system that is traversed mainly from graphs in [[Juggl]]. This requires very strong and interactable graph visualization. It also requires a data-format that can easily be queried and extended, and can model linear, non-linear and hierarchical relations between files and notes.
9 |
10 | In Semantic Obsidian, notes are the main entities. They have both loose associations through inline wikilinks and backlinks, and strong links through [[Link Types]] with properties. They can be used to provide cues for files that are related.
11 |
12 | This gives the following requirements for the Graph View Plugin:
13 | - A clear and interactable graph view
14 | - Save and load graphs
15 | - Style the graphs
16 | - A text-first data format
17 | - Data format should easily be extended and converted to other formats
18 | - Data format should be local
19 | - Data format should be optional
20 | - Users should be free to choose to formalize data to any degree
21 | - Advanced use should not be in view if not needed.
22 | - Annotate links with [[Link Types]] and properties
23 | - Easily extendable through an [[Juggl API|API]]
24 |
25 | ---
26 | #topic #project
27 | - hasTopic [[Obsidian]]
28 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/docs/files/CypherQuerying.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/CypherQuerying.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231174344.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231174344.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231174425.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231174425.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231175530.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231175530.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231180930.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231180930.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231181003.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231181003.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231181103.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231181103.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20201231181917.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20201231181917.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210101144050.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210101144050.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210101144311.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210101144311.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210102141444.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210102141444.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210102141514.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210102141514.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210102141546.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210102141546.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210112215108.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210112215108.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210315210604.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210315210604.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210320161536.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210320161536.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210320161754.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210320161754.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210329191901.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210329191901.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210330193014.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210330193014.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210402152820.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210402152820.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210402154645.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210402154645.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210402155246.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210402155246.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210402162157.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210402162157.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403140754.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403140754.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403141344.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403141344.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403142046.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403142046.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403143207.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403143207.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403144754.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403144754.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403150555.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403150555.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403150726.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403150726.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403151146.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403151146.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210403151424.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210403151424.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210408165620.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210408165620.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210408165722.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210408165722.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210408165744.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210408165744.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210408165833.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210408165833.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210410161017.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210410161017.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210410161051.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210410161051.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210413145227.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210413145227.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210413145921.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210413145921.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210413150208.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210413150208.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210414175943.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210414175943.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210414182140.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210414182140.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210421133609.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210421133609.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210421133938.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210421133938.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20210422092407.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20210422092407.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20220121103800.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20220121103800.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20220127142536.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20220127142536.png
--------------------------------------------------------------------------------
/docs/files/Pasted image 20220127142903.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Pasted image 20220127142903.png
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 14.19.42.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 14.19.42.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.01.02.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.01.02.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.05.43.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.05.43.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.09.51.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.09.51.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.14.06.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.14.06.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.21.34.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.21.34.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.24.43.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.24.43.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.32.58 1.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.32.58 1.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.32.58.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.32.58.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.38.11.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.38.11.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-01-02 at 15.43.17.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-01-02 at 15.43.17.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-04-02 at 16.48.29.mov:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-04-02 at 16.48.29.mov
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-04-03 at 13.58.20.mov:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-04-03 at 13.58.20.mov
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-04-03 at 13.58.20.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-04-03 at 13.58.20.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-04-03 at 14.59.13.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-04-03 at 14.59.13.mp4
--------------------------------------------------------------------------------
/docs/files/Screen Recording 2021-04-14 at 17.29.09.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screen Recording 2021-04-14 at 17.29.09.mp4
--------------------------------------------------------------------------------
/docs/files/Screenshot 2021-04-03 at 15.01.44.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/Screenshot 2021-04-03 at 15.01.44.png
--------------------------------------------------------------------------------
/docs/files/bloom_screenshot.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/bloom_screenshot.jpg
--------------------------------------------------------------------------------
/docs/files/browser_screenshot.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/browser_screenshot.png
--------------------------------------------------------------------------------
/docs/files/code_fence.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/code_fence.gif
--------------------------------------------------------------------------------
/docs/files/context_iframe.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/context_iframe.gif
--------------------------------------------------------------------------------
/docs/files/demo.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/demo.gif
--------------------------------------------------------------------------------
/docs/files/graphxr.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/graphxr.gif
--------------------------------------------------------------------------------
/docs/files/img.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/img.png
--------------------------------------------------------------------------------
/docs/files/juggl trailer.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/juggl trailer.gif
--------------------------------------------------------------------------------
/docs/files/juggl_screenshot.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/juggl_screenshot.png
--------------------------------------------------------------------------------
/docs/files/layouts.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/layouts.gif
--------------------------------------------------------------------------------
/docs/files/main.db.json:
--------------------------------------------------------------------------------
1 | {"creationTime":1613388819658,"updateTime":1613388819665,"id":"files","notes":[],"links":[],"idCounter":0,"screenPosition":{"translateX":200,"translateY":200,"scale":1},"initialNodePosition":{"x":0,"y":0},"pinnedNotes":[]}
--------------------------------------------------------------------------------
/docs/files/obsidian neo4j plugin.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/obsidian neo4j plugin.gif
--------------------------------------------------------------------------------
/docs/files/save_workspace.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/save_workspace.gif
--------------------------------------------------------------------------------
/docs/files/selectdrag.mp4:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/selectdrag.mp4
--------------------------------------------------------------------------------
/docs/files/style_pane.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/style_pane.gif
--------------------------------------------------------------------------------
/docs/files/styled_screenshot.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/HEmile/juggl/4c18c9ed009b8074da704ae3053df607f21e66ed/docs/files/styled_screenshot.png
--------------------------------------------------------------------------------
/docs/templates/Template.md:
--------------------------------------------------------------------------------
1 | ---
2 | aliases: []
3 | ---
4 |
5 | ---
6 |
7 | - author [[Emile van Krieken]]
--------------------------------------------------------------------------------
/manifest.json:
--------------------------------------------------------------------------------
1 | {
2 | "id": "juggl",
3 | "name": "Juggl",
4 | "version": "1.5.0",
5 | "minAppVersion": "1.4.16",
6 | "description": "Adds a completely interactive, stylable and expandable graph view to Obsidian.",
7 | "author": "Emile",
8 | "authorUrl": "https://emilevankrieken.com",
9 | "isDesktopOnly": false
10 | }
11 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "juggl",
3 | "version": "1.5.0",
4 | "description": "Adds a completely interactive, stylable and expandable graph view to Obsidian.",
5 | "main": "main.js",
6 | "type": "module",
7 | "repository": {
8 | "type": "git",
9 | "url": "https://github.com/HEmile/juggl.git"
10 | },
11 | "scripts": {
12 | "dev": "node_modules/.bin/rollup --config rollup.config.js -w",
13 | "build": "node_modules/.bin/rollup --config rollup.config.js",
14 | "release": "node_modules/.bin/standard-version"
15 | },
16 | "standard-version": {
17 | "t": ""
18 | },
19 | "keywords": [],
20 | "author": "",
21 | "devDependencies": {
22 | "@egjs/hammerjs": "^2.0.17",
23 | "@rollup/plugin-commonjs": "^25.0.7",
24 | "@rollup/plugin-json": "^6.0.1",
25 | "@rollup/plugin-node-resolve": "^15.2.3",
26 | "@rollup/plugin-terser": "^0.4.4",
27 | "@rollup/plugin-typescript": "^11.1.5",
28 | "@tsconfig/svelte": "^5.0.2",
29 | "@types/cytoscape": "^3.19.14",
30 | "@types/jquery": "^3.5.25",
31 | "@types/node": "^20.8.9",
32 | "@typescript-eslint/eslint-plugin": "^6.9.0",
33 | "@typescript-eslint/parser": "^6.9.0",
34 | "component-emitter": "^1.3.0",
35 | "eslint": "^8.52.0",
36 | "eslint-config-google": "^0.14.0",
37 | "eslint-config-standard": "^17.1.0",
38 | "eslint-plugin-import": "^2.29.0",
39 | "eslint-plugin-node": "^11.1.0",
40 | "eslint-plugin-promise": "^6.1.1",
41 | "hammerjs": "^2.0.8",
42 | "keycharm": "^0.4.0",
43 | "moment": "^2.29.4",
44 | "obsidian": "^1.4.11",
45 | "rollup": "^4.0.0",
46 | "rollup-plugin-copy": "^3.5.0",
47 | "rollup-plugin-ignore": "^1.0.10",
48 | "rollup-plugin-svelte": "7.1.6",
49 | "svelte": "^4.2.2",
50 | "svelte-check": "^3.5.2",
51 | "svelte-preprocess": "5.0.4",
52 | "timsort": "^0.3.0",
53 | "tslib": "^2.6.2",
54 | "typescript": "^5.2.2",
55 | "uuid": "^9.0.1"
56 | },
57 | "dependencies": {
58 | "@mdi/js": "^7.3.67",
59 | "cytoscape": "^3.26.0",
60 | "cytoscape-avsdf": "^1.0.0",
61 | "cytoscape-cola": "^2.5.1",
62 | "cytoscape-cose-bilkent": "^4.1.0",
63 | "cytoscape-cxtmenu": "https://github.com/HEmile/cytoscape.js-cxtmenu/tarball/master",
64 | "cytoscape-d3-force": "^1.1.4",
65 | "cytoscape-dagre": "github:HEmile/cytoscape.js-dagre",
66 | "cytoscape-dblclick": "^0.3.1",
67 | "cytoscape-navigator": "^2.0.2",
68 | "cytoscape-popper": "^2.0.0",
69 | "juggl-api": "github:HEmile/juggl-api",
70 | "search-query-parser": "^1.6.0",
71 | "standard-version": "^9.5.0"
72 | }
73 | }
74 |
--------------------------------------------------------------------------------
/rollup.config.js:
--------------------------------------------------------------------------------
1 | import svelte from 'rollup-plugin-svelte';
2 | import typescript from '@rollup/plugin-typescript';
3 | import {nodeResolve} from '@rollup/plugin-node-resolve';
4 | import commonjs from '@rollup/plugin-commonjs';
5 | import copy from 'rollup-plugin-copy';
6 | import autoPreprocess from 'svelte-preprocess';
7 | import ignore from 'rollup-plugin-ignore';
8 | import json from '@rollup/plugin-json';
9 | import {env} from 'process';
10 | import terser from "@rollup/plugin-terser";
11 |
12 | const plugins = [
13 | ignore(["path", "url"], { commonjsBugFix: true }),
14 | commonjs({
15 | include: ['node_modules/**', '../cytoscape.js-cxtmenu/**'],
16 | }),
17 | json(),
18 | svelte({
19 | emitCss: false,
20 | preprocess: autoPreprocess(),
21 | }),
22 | typescript({sourceMap: false}),
23 | nodeResolve({browser: true,
24 | dedupe: ['svelte'],
25 | })]
26 |
27 | const DEV = env.npm_lifecycle_event === "dev";
28 |
29 | if (!DEV) {
30 | plugins.push(terser());
31 | }
32 |
33 | plugins.push(copy({
34 | targets: [
35 | {src: 'main.js', dest: 'docs/.obsidian/plugins/juggl'},
36 | {src: 'styles.css', dest: 'docs/.obsidian/plugins/juggl'},
37 | ],
38 | hook: 'writeBundle',
39 | }));
40 |
41 | export default {
42 | input: 'src/main.ts',
43 | output: {
44 | dir: '.',
45 | sourcemap: DEV ? 'inline' : false,
46 | format: 'cjs',
47 | exports: 'default',
48 | // banner: '/* This file is bundled with rollup. For the source code, see Github */',
49 | },
50 | external: ['obsidian'],
51 | plugins: plugins,
52 | };
53 |
--------------------------------------------------------------------------------
/src/.eslintrc.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | 'env': {
3 | 'browser': true,
4 | 'es2015': true,
5 | },
6 | 'extends': [
7 | 'google',
8 | ],
9 | 'parser': '@typescript-eslint/parser',
10 | 'parserOptions': {
11 | 'ecmaVersion': 12,
12 | 'sourceType': 'module',
13 | },
14 | 'plugins': [
15 | '@typescript-eslint',
16 | ],
17 | 'rules': {
18 | },
19 | 'ignorePatterns': [
20 | 'main.js',
21 | ],
22 | };
23 |
--------------------------------------------------------------------------------
/src/.gitignore:
--------------------------------------------------------------------------------
1 | # Intellij
2 | *.iml
3 | .idea
4 |
5 | # npm
6 | node_modules
7 |
8 | # build
9 | *.js.map
--------------------------------------------------------------------------------
/src/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # Changelog
2 |
3 | All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
4 |
5 | ### [1.1.3](https://github.com/HEmile/juggl/compare/v1.1.2...v1.1.3) (2022-01-11)
6 |
7 | ### [1.1.2](https://github.com/HEmile/juggl/compare/v1.0.2...v1.1.2) (2022-01-11)
8 |
9 | ### 1.0.2 (2022-01-11)
10 |
11 |
12 | ### Bug Fixes
13 |
14 | * Raw filter queries were broken ([1a5c1ab](https://github.com/HEmile/juggl/commit/1a5c1abf6444f31d3c135614d5cf43ae34c94373))
15 |
--------------------------------------------------------------------------------
/src/constants.ts:
--------------------------------------------------------------------------------
1 | import type {Vault} from 'obsidian';
2 |
3 | export const CLASS_PINNED = 'pinned';
4 | export const CLASS_EXPANDED = 'expanded';
5 | export const CLASS_ACTIVE_NODE = 'active-node';
6 | export const CLASS_INACTIVE_NODE = 'inactive-node';
7 | export const CLASS_CONNECTED_ACTIVE_NODE = 'connected-active-node';
8 | export const CLASS_HOVER = 'hover';
9 | export const CLASS_UNHOVER = 'unhover';
10 | export const CLASS_PROTECTED = 'protected';
11 | export const CLASS_CONNECTED_HOVER = 'connected-hover';
12 | export const CLASS_FILTERED = 'filtered';
13 | export const CLASS_HARD_FILTERED = 'hard-filtered';
14 | export const CLASSES = [CLASS_PINNED, CLASS_EXPANDED, CLASS_ACTIVE_NODE,
15 | CLASS_INACTIVE_NODE, CLASS_CONNECTED_ACTIVE_NODE, CLASS_HOVER, CLASS_UNHOVER,
16 | CLASS_CONNECTED_HOVER, CLASS_PROTECTED, CLASS_FILTERED, CLASS_HARD_FILTERED];
17 |
18 |
19 | export const VIEWPORT_ANIMATION_TIME = 250;
20 | export const LAYOUT_ANIMATION_TIME = 1500;
21 | export const DISCRETE_LAYOUT_ANIMATION_TIME = 500;
22 | export const DISCRETE_SPACING_FACTOR = 0.5;
23 | export const DEBOUNCE_FOLLOW = 500;
24 | export const DEBOUNCE_LAYOUT = 2300;
25 |
26 | export const MIN_NODE_SIZE = 5;
27 | export const MAX_NODE_SIZE = 35;
28 | export const MIN_FONT_SIZE = 5;
29 | export const MAX_FONT_SIZE = 11;
30 | export const MIN_TEXT_WIDTH = 65;
31 | export const MAX_TEXT_WIDTH = 100;
32 |
33 |
34 | export const DATA_FOLDER = function(vault: Vault) {
35 | return `${vault.configDir}/plugins/juggl/`;
36 | };
37 |
--------------------------------------------------------------------------------
/src/declarations.d.ts:
--------------------------------------------------------------------------------
1 | declare module 'cytoscape-popper';
2 | declare module 'cytoscape-navigator';
3 | declare module 'cytoscape-dagre';
4 | declare module 'cytoscape-d3-force';
5 | declare module 'cytoscape-cola';
6 | declare module 'cytoscape-avsdf';
7 | declare module 'cytoscape-cxtmenu'
8 |
--------------------------------------------------------------------------------
/src/events.ts:
--------------------------------------------------------------------------------
1 | import {EventRef, Events} from 'obsidian';
2 |
3 | export class DataStoreEvents extends Events {
4 | trigger(name: 'renameNode', oldName: string, newName: string): void;
5 | trigger(name: 'deleteNode', param: string): void;
6 | trigger(name: 'modifyNode', param: string): void;
7 | trigger(name: 'createNode', param: string): void;
8 | trigger(name: string, ...data: any[]): void {
9 | super.trigger(name, ...data);
10 | }
11 |
12 | public on(name: 'renameNode', callback: (oldName: string, newName: string) => any, ctx?: any): EventRef;
13 | public on(name: 'deleteNode', callback: (name: string) => any, ctx?: any): EventRef;
14 | public on(name: 'modifyNode', callback: (name: string) => any, ctx?: any): EventRef;
15 | public on(name: 'createNode', callback: (name: string) => any, ctx?: any): EventRef;
16 | on(name: string, callback: (...data: any[]) => any, ctx?: any): EventRef {
17 | return super.on(name, callback, ctx);
18 | }
19 | }
20 |
--------------------------------------------------------------------------------
/src/image-server.ts:
--------------------------------------------------------------------------------
1 | import type {IncomingMessage, Server, ServerResponse} from 'http';
2 | import {Component, FileSystemAdapter, Notice, Platform, TFile} from 'obsidian';
3 | import type {IJugglPluginSettings} from './settings';
4 | import type JugglPlugin from './main';
5 |
6 | export class ImageServer extends Component {
7 | settings: IJugglPluginSettings;
8 | plugin: JugglPlugin;
9 | imgServer: Server;
10 |
11 | constructor(plugin: JugglPlugin) {
12 | super();
13 | this.settings = plugin.settings;
14 | this.plugin = plugin;
15 | this.imgServer = null;
16 | }
17 |
18 | public async onload() {
19 | super.onload();
20 | if (Platform.isMobile || !this.settings.useImgServer) {
21 | return;
22 | }
23 | const path = require('path');
24 | const http = require('http');
25 | const fs = require('fs');
26 |
27 | let dir:string = null;
28 | try {
29 | dir = path.join(this.plugin.path);
30 | } catch (e) {
31 | console.log('Couldn\'t start image server. This is likely because we\'re on mobile!');
32 | console.log('Alternatively, windows might block it using the firewall');
33 | console.log(e);
34 | return;
35 | }
36 |
37 | const mime = {
38 | gif: 'image/gif',
39 | jpg: 'image/jpeg',
40 | jpeg: 'image/jpeg',
41 | png: 'image/png',
42 | svg: 'image/svg+xml',
43 | };
44 | const settings = this.settings;
45 | const vault = this.plugin.app.vault;
46 | this.imgServer = http.createServer(function(req: IncomingMessage, res: ServerResponse) {
47 | const reqpath = req.url.toString().split('?')[0];
48 | if (req.method !== 'GET') {
49 | res.statusCode = 501;
50 | res.setHeader('Content-Type', 'text/plain');
51 | return res.end('Method not implemented');
52 | }
53 | let file = path.join(dir, decodeURI(reqpath.replace(/\/$/, '/index.html')));
54 | file = (vault.adapter as FileSystemAdapter).getFullPath(file);
55 | // console.log(vault.getResourcePath(nFile as TFile));
56 | if (settings.debug) {
57 | console.log('entering server query');
58 | console.log(req);
59 | console.log(file);
60 | }
61 | // if (file.indexOf(dir + path.sep) !== 0) {
62 | // res.statusCode = 403;
63 | // res.setHeader('Content-Type', 'text/plain');
64 | // return res.end('Forbidden');
65 | // }
66 | // @ts-ignore
67 | const type = mime[path.extname(file).slice(1)];
68 | const s = fs.createReadStream(file);
69 | s.on('open', function() {
70 | res.setHeader('Content-Type', type);
71 | res.setHeader('Access-Control-Allow-Origin', '*');
72 | s.pipe(res);
73 | });
74 | s.on('error', function() {
75 | console.log('Here3');
76 | res.setHeader('Content-Type', 'text/plain');
77 | res.statusCode = 404;
78 | res.end('Not found');
79 | });
80 | });
81 | try {
82 | const port = this.settings.imgServerPort;
83 | this.imgServer.listen(port, function() {
84 | console.log('Image server listening on http://localhost:' + port + '/');
85 | });
86 | } catch (e) {
87 | console.log(e);
88 | new Notice('Juggl: Couldn\'t start image server, see console');
89 | }
90 | }
91 |
92 | public async onunload() {
93 | super.onunload();
94 | if (this.imgServer) {
95 | this.imgServer.close();
96 | this.imgServer = null;
97 | }
98 | }
99 | }
100 |
--------------------------------------------------------------------------------
/src/interfaces.ts:
--------------------------------------------------------------------------------
1 |
2 | // From https://github.com/jplattel/obsidian-query-language/blob/4840e5da6ff5d94dfcba8ff6c900421300466de6/src/search.ts#L3
3 | export interface IFuseFile {
4 | [index:string]: any;
5 | title: string;
6 | path: string;
7 | content: string;
8 | created: any;
9 | modified: any;
10 | tags?: string[];
11 | frontmatter?: any;
12 | }
13 |
--------------------------------------------------------------------------------
/src/obsidian-store.ts:
--------------------------------------------------------------------------------
1 | import {
2 | CachedMetadata,
3 | Component, FrontmatterLinkCache,
4 | getLinkpath,
5 | iterateCacheRefs,
6 | MetadataCache, Reference, ReferenceCache,
7 | TFile,
8 | Vault,
9 | } from 'obsidian';
10 | import type {ICoreDataStore, IMergedToGraph, IJuggl} from 'juggl-api';
11 | import {DataStoreEvents} from './events';
12 | import type JugglPlugin from './main';
13 | import type {
14 | NodeDefinition,
15 | EdgeDefinition,
16 | NodeCollection, EdgeDataDefinition,
17 | } from 'cytoscape';
18 | import {CLASS_EXPANDED} from './constants';
19 | import {nodeDangling, nodeFromFile, parseRefCache, VizId} from 'juggl-api';
20 |
21 | export const OBSIDIAN_STORE_NAME = 'Obsidian';
22 |
23 | export class ObsidianStore extends Component implements ICoreDataStore {
24 | plugin: JugglPlugin;
25 | events: DataStoreEvents;
26 | metadata: MetadataCache;
27 | vault: Vault
28 | constructor(plugin: JugglPlugin) {
29 | super();
30 | this.plugin = plugin;
31 | this.events = new DataStoreEvents();
32 | this.metadata = plugin.app.metadataCache;
33 | this.vault = plugin.app.vault;
34 | }
35 |
36 | getEvents(view: IJuggl): DataStoreEvents {
37 | return this.events;
38 | }
39 |
40 | async createEdges(srcFile: TFile, srcId: string, toNodes: NodeCollection, view: IJuggl): Promise {
41 | if (!(srcFile.extension === 'md')) {
42 | return [];
43 | }
44 | const cache = this.metadata.getFileCache(srcFile);
45 | if (!cache) {
46 | return [];
47 | }
48 |
49 | const edges: Record = {};
50 | const content = (await this.vault.cachedRead(srcFile)).split('\n');
51 | this.iterLinks(cache, (ref, isRefCache) => {
52 | // Iterate over all links (both in frontmatter and document)
53 | const otherId = this.getOtherId(ref, srcFile.path).toId();
54 | if (toNodes.$id(otherId).length > 0) {
55 | const edgeId = `${srcId}->${otherId}`;
56 | const count = edgeId in edges ? edges[edgeId].length + 1 : 1;
57 | const id = `${edgeId}${count}`
58 | let edge;
59 | if (isRefCache) {
60 | // Add edges for the links appearing in the document
61 | edge = parseRefCache(ref as ReferenceCache, content, id, srcId, otherId, this.plugin.settings.typedLinkPrefix);
62 | }
63 | else {
64 | // Add typed edges for the links appearing in the frontmatter
65 | // TODO: Probably worth including line number etc.
66 | const link = ref as FrontmatterLinkCache;
67 | const split = link.key.split(".")
68 | let type;
69 | if (split.length > 1)
70 | type = split.slice(0, -1).join();
71 | else
72 | type = link.key;
73 | edge = {
74 | group: 'edges',
75 | data: {
76 | id,
77 | source: srcId,
78 | target: otherId,
79 | context: "",
80 | edgeCount: 1,
81 | type
82 | } as EdgeDataDefinition,
83 | classes: [type, "type-" + type, "type-" + type.replaceAll(" ", "-")]
84 | } as EdgeDefinition;
85 | }
86 | if (edgeId in edges) {
87 | edges[edgeId].push(edge);
88 | } else {
89 | edges[edgeId] = [edge];
90 | }
91 | }
92 | });
93 | if (view.settings.mergeEdges) {
94 | // Merges inline edges.
95 | const returnEdges: EdgeDefinition[] = [];
96 | for (const edgeId of Object.keys(edges)) {
97 | const connectedEdges: EdgeDefinition[] = edges[edgeId];
98 | let inlineEdge: EdgeDefinition = null;
99 | let countInline = 0;
100 | for (const edge of connectedEdges) {
101 | if (edge.classes === ' inline') {
102 | if (inlineEdge) {
103 | inlineEdge.data.context += `
104 |
105 | ---
106 |
107 | ${edge.data.context}`;
108 | countInline += 1;
109 | } else {
110 | inlineEdge = edge;
111 | countInline = 1;
112 | }
113 | } else {
114 | returnEdges.push(edge);
115 | }
116 | }
117 | if (inlineEdge) {
118 | inlineEdge.data.edgeCount = countInline;
119 | returnEdges.push(inlineEdge);
120 | }
121 | }
122 | return returnEdges;
123 | }
124 | return [].concat(...Object.values(edges));
125 | }
126 |
127 | async connectNodes(allNodes: NodeCollection, newNodes: NodeCollection, view: IJuggl): Promise {
128 | const edges: EdgeDefinition[] = [];
129 | // Find edges from newNodes to other nodes
130 | // @ts-ignore
131 | for (const node of newNodes) {
132 | const id = VizId.fromNode(node);
133 | if (id.storeId === this.storeId()) {
134 | const file = this.getFile(id);
135 | if (file) {
136 | const srcId = id.toId();
137 |
138 | edges.push(...await this.createEdges(file, srcId, allNodes, view));
139 | }
140 | }
141 | }
142 | // @ts-ignore
143 | for (const node of allNodes.difference(newNodes)) {
144 | // For all nodes other than the new nodes
145 | const id = VizId.fromNode(node);
146 | if (id.storeId === this.storeId()) {
147 | const file = this.getFile(id);
148 | if (file) {
149 | const srcId = id.toId();
150 |
151 | // Connect only to newNodes!
152 | edges.push(...await this.createEdges(file, srcId, newNodes, view));
153 | }
154 | }
155 | }
156 | return edges;
157 | }
158 |
159 | getOtherId(link: Reference, sourcePath: string) : VizId {
160 | const path = getLinkpath(link.link);
161 | const file = this.metadata.getFirstLinkpathDest(path, sourcePath);
162 | if (file) {
163 | return new VizId(file.name, this.storeId());
164 | } else {
165 | return new VizId(path, this.storeId() );
166 | }
167 | }
168 |
169 | async getNodeFromLink(link: Reference, sourcePath: string, graph: IJuggl) : Promise {
170 | const path = getLinkpath(link.link);
171 | const file = this.metadata.getFirstLinkpathDest(path, sourcePath);
172 | if (file) {
173 | return await nodeFromFile(file, this.plugin, graph.settings);
174 | } else {
175 | return nodeDangling(path);
176 | }
177 | }
178 |
179 | getFile(nodeId: VizId): TFile | null {
180 | return this.metadata.getFirstLinkpathDest(nodeId.id, '');
181 | }
182 |
183 | async fillWithBacklinks(nodes: Record, nodeId: VizId, graph: IJuggl) {
184 | // Could be an expensive operation... No cached backlinks implementation is available in the Obsidian API though.
185 | if (nodeId.storeId === 'core') {
186 | const file = this.getFile(nodeId);
187 | if (!file) {
188 | console.log("Couldn't get file when filling with backlinks. This should not happen.");
189 | return;
190 | }
191 | const path = file.path;
192 | const resolvedLinks = this.metadata.resolvedLinks;
193 | for (const otherPath of Object.keys(resolvedLinks)) {
194 | if (path in resolvedLinks[otherPath]) {
195 | const file = this.vault.getAbstractFileByPath(otherPath) as TFile;
196 | const id = VizId.fromFile(file).toId();
197 | if (!(id in nodes)) {
198 | nodes[id] = await nodeFromFile(file, this.plugin, graph.settings);
199 | }
200 | }
201 | }
202 | }
203 | }
204 |
205 |
206 | iterLinks(cache: CachedMetadata, cb: (ref: Reference, refCache: boolean) => void): void {
207 | iterateCacheRefs(cache, (ref_) => cb(ref_, true));
208 | if (cache.frontmatterLinks) {
209 | for (const link of cache.frontmatterLinks) {
210 | cb(link, false);
211 | }
212 | }
213 | }
214 |
215 |
216 | async getNeighbourhood(nodeIds: VizId[], viz: IJuggl): Promise {
217 | const nodes: Record = {};
218 | for (const nodeId of nodeIds) {
219 | if (nodeId.storeId === this.storeId()) {
220 | const file = this.getFile(nodeId);
221 | if (file === null) {
222 | continue;
223 | }
224 | const cache = this.metadata.getFileCache(file);
225 | if (cache === null) {
226 | continue;
227 | }
228 | if (!(nodeId.toId() in nodes)) {
229 | nodes[nodeId.toId()] = await nodeFromFile(file, this.plugin, viz.settings);
230 | }
231 | const promiseNodes: Record> = {};
232 | this.iterLinks(cache, (ref, _) => {
233 | const id = this.getOtherId(ref, file.path).toId();
234 | if (!(id in nodes)) {
235 | promiseNodes[id] = this.getNodeFromLink(ref, file.path, viz);
236 | }
237 | });
238 | for (const id of Object.keys(promiseNodes)) {
239 | if (!(id in nodes)) {
240 | nodes[id] = await promiseNodes[id];
241 | }
242 | }
243 | await this.fillWithBacklinks(nodes, nodeId, viz);
244 | }
245 | }
246 | return Object.values(nodes);
247 | }
248 |
249 | storeId(): string {
250 | return 'core';
251 | }
252 |
253 | get(nodeId: VizId, view: IJuggl): Promise {
254 | const file = this.getFile(nodeId);
255 | if (file === null) {
256 | return Promise.resolve(null);
257 | }
258 | const cache = this.metadata.getFileCache(file);
259 | if (cache === null) {
260 | console.log('returning empty cache', nodeId, view);
261 | return Promise.resolve(null);
262 | }
263 | return Promise.resolve(nodeFromFile(file, this.plugin, view.settings));
264 | }
265 |
266 | async refreshNode(id: VizId, view: IJuggl) {
267 | const idS = id.toId();
268 | let correctEdges: IMergedToGraph;
269 | let node = view.viz.$id(idS);
270 | if (this.getFile(id) === null) {
271 | // File does not exist
272 | if (node) {
273 | // If a node exists for this file, remove it.
274 | node.remove();
275 | view.onGraphChanged(true, true);
276 | }
277 | return;
278 | }
279 | if (node.length > 0 && node.hasClass(CLASS_EXPANDED)) {
280 | correctEdges = await view.expand(node, true, false);
281 | } else {
282 | const nodeDef = await this.get(id, view);
283 | if (!nodeDef) {
284 | console.log("Failed to get node definition on refresh. This should not happen!");
285 | return;
286 | }
287 | view.mergeToGraph([nodeDef], true, false);
288 | node = view.viz.$id(idS);
289 | const edges = await view.buildEdges(node);
290 | correctEdges = view.mergeToGraph(edges, true, false);
291 | }
292 | // Remove outgoing edges that no longer exist.
293 | const removed = node.connectedEdges()
294 | .difference(correctEdges.merged)
295 | .remove();
296 | if (removed.length > 0 || correctEdges.added.length > 0) {
297 | view.onGraphChanged(true, true);
298 | }
299 | }
300 |
301 | onload() {
302 | super.onload();
303 | const store = this;
304 | this.registerEvent(
305 | this.metadata.on('changed', (file) => {
306 | store.plugin.activeGraphs().forEach(async (v) => {
307 | await store.refreshNode(VizId.fromFile(file), v);
308 | });
309 | }));
310 | this.registerEvent(
311 | this.vault.on('rename', (file, oldPath) => {
312 | if (file instanceof TFile) {
313 | const id = VizId.fromFile(file);
314 | const oldId = VizId.fromPath(oldPath);
315 | store.plugin.activeGraphs().forEach(async (v) => {
316 | setTimeout(async ()=> {
317 | // Changing the ID of a node in Cytoscape is not allowed, so remove and then restore.
318 | // Put in setTimeout because Obsidian doesn't immediately update the metadata on rename...
319 | v.viz.$id(oldId.toId()).remove();
320 | await store.refreshNode(id, v);
321 | }, 500);
322 | });
323 | }
324 | }));
325 | this.registerEvent(
326 | this.vault.on('delete', (file) => {
327 | if (file instanceof TFile) {
328 | store.plugin.activeGraphs().forEach((v) => {
329 | v.viz.$id(VizId.fromFile(file).toId()).remove();
330 | });
331 | }
332 | }));
333 | }
334 | }
335 |
--------------------------------------------------------------------------------
/src/pane/NodesList.svelte:
--------------------------------------------------------------------------------
1 |
17 |
18 |
19 | {name}
20 |
21 | {#if displayList}
22 | {#each nodes.sort((a, b) => a.data("name").localeCompare(b.data("name"))) as v}
23 |