diff --git a/apps/client/src/stylesheets/style.css b/apps/client/src/stylesheets/style.css index c3e2810fc8..2a6d66ed6c 100644 --- a/apps/client/src/stylesheets/style.css +++ b/apps/client/src/stylesheets/style.css @@ -153,6 +153,11 @@ textarea, background: var(--input-background-color); } +.form-control:disabled { + background-color: var(--input-background-color); + opacity: 0.6; +} + .form-control:focus { color: var(--input-text-color); background: var(--input-background-color); diff --git a/apps/client/src/translations/en/translation.json b/apps/client/src/translations/en/translation.json index d2892456de..e2f00acec5 100644 --- a/apps/client/src/translations/en/translation.json +++ b/apps/client/src/translations/en/translation.json @@ -2110,7 +2110,8 @@ "raster": "Raster", "vector_light": "Vector (Light)", "vector_dark": "Vector (Dark)", - "show-scale": "Show scale" + "show-scale": "Show scale", + "show-labels": "Show marker names" }, "table_context_menu": { "delete_row": "Delete row" diff --git a/apps/client/src/widgets/collections/geomap/index.tsx b/apps/client/src/widgets/collections/geomap/index.tsx index 6e490a81e8..8be547fa3a 100644 --- a/apps/client/src/widgets/collections/geomap/index.tsx +++ b/apps/client/src/widgets/collections/geomap/index.tsx @@ -22,7 +22,7 @@ import { ViewModeProps } from "../interface"; import { createNewNote, moveMarker } from "./api"; import openContextMenu, { openMapContextMenu } from "./context_menu"; import Map from "./map"; -import { DEFAULT_MAP_LAYER_NAME } from "./map_layer"; +import { DEFAULT_MAP_LAYER_NAME, MAP_LAYERS, MapLayer } from "./map_layer"; import Marker, { GpxTrack } from "./marker"; const DEFAULT_COORDINATES: [number, number] = [3.878638227135724, 446.6630455551659]; @@ -45,10 +45,11 @@ export default function GeoView({ note, noteIds, viewConfig, saveConfig }: ViewM const [ state, setState ] = useState(State.Normal); const [ coordinates, setCoordinates ] = useState(viewConfig?.view?.center); const [ zoom, setZoom ] = useState(viewConfig?.view?.zoom); - const [ layerName ] = useNoteLabel(note, "map:style"); const [ hasScale ] = useNoteLabelBoolean(note, "map:scale"); + const [ hideLabels ] = useNoteLabelBoolean(note, "map:hideLabels"); const [ isReadOnly ] = useNoteLabelBoolean(note, "readOnly"); const [ notes, setNotes ] = useState([]); + const layerData = useLayerData(note); const spacedUpdate = useSpacedUpdate(() => { if (viewConfig) { saveConfig(viewConfig); @@ -152,7 +153,7 @@ export default function GeoView({ note, noteIds, viewConfig, saveConfig }: ViewM apiRef={apiRef} containerRef={containerRef} coordinates={coordinates} zoom={zoom} - layerName={layerName ?? DEFAULT_MAP_LAYER_NAME} + layerData={layerData} viewportChanged={(coordinates, zoom) => { if (!viewConfig) viewConfig = {}; viewConfig.view = { center: coordinates, zoom }; @@ -162,13 +163,35 @@ export default function GeoView({ note, noteIds, viewConfig, saveConfig }: ViewM onContextMenu={onContextMenu} scale={hasScale} > - {notes.map(note => )} + {notes.map(note => )} } ); } +function useLayerData(note: FNote) { + const [ layerName ] = useNoteLabel(note, "map:style"); + // Memo is needed because it would generate unnecessary reloads due to layer change. + const layerData = useMemo(() => { + // Custom layers. + if (layerName?.startsWith("http")) { + return { + name: "Custom", + type: "raster", + url: layerName, + attribution: "" + } satisfies MapLayer; + } + + // Built-in layers. + const layerData = MAP_LAYERS[layerName ?? ""] ?? MAP_LAYERS[DEFAULT_MAP_LAYER_NAME]; + return layerData; + }, [ layerName ]); + + return layerData; +} + function ToggleReadOnlyButton({ note }: { note: FNote }) { const [ isReadOnly, setReadOnly ] = useNoteLabelBoolean(note, "readOnly"); @@ -179,22 +202,26 @@ function ToggleReadOnlyButton({ note }: { note: FNote }) { />; } -function NoteWrapper({ note, isReadOnly }: { note: FNote, isReadOnly: boolean }) { +function NoteWrapper({ note, isReadOnly, hideLabels }: { + note: FNote, + isReadOnly: boolean, + hideLabels: boolean +}) { const mime = useNoteProperty(note, "mime"); const [ location ] = useNoteLabel(note, LOCATION_ATTRIBUTE); if (mime === "application/gpx+xml") { - return ; + return ; } if (location) { const latLng = location?.split(",", 2).map((el) => parseFloat(el)) as [ number, number ] | undefined; if (!latLng) return; - return ; + return ; } } -function NoteMarker({ note, editable, latLng }: { note: FNote, editable: boolean, latLng: [number, number] }) { +function NoteMarker({ note, editable, latLng, hideLabels }: { note: FNote, editable: boolean, latLng: [number, number], hideLabels: boolean }) { // React to changes const [ color ] = useNoteLabel(note, "color"); const [ iconClass ] = useNoteLabel(note, "iconClass"); @@ -202,8 +229,9 @@ function NoteMarker({ note, editable, latLng }: { note: FNote, editable: boolean const title = useNoteProperty(note, "title"); const icon = useMemo(() => { - return buildIcon(note.getIcon(), note.getColorClass() ?? undefined, title, note.noteId, archived); - }, [ iconClass, color, title, note.noteId, archived]); + const titleOrNone = hideLabels ? undefined : title; + return buildIcon(note.getIcon(), note.getColorClass() ?? undefined, titleOrNone, note.noteId, archived); + }, [ iconClass, color, title, note.noteId, archived, hideLabels ]); const onClick = useCallback(() => { appContext.triggerCommand("openInPopup", { noteIdOrPath: note.noteId }); @@ -235,7 +263,7 @@ function NoteMarker({ note, editable, latLng }: { note: FNote, editable: boolean />; } -function NoteGpxTrack({ note }: { note: FNote }) { +function NoteGpxTrack({ note, hideLabels }: { note: FNote, hideLabels?: boolean }) { const [ xmlString, setXmlString ] = useState(); const blob = useNoteBlob(note); @@ -256,7 +284,7 @@ function NoteGpxTrack({ note }: { note: FNote }) { const options = useMemo(() => ({ markers: { - startIcon: buildIcon(note.getIcon(), note.getColorClass(), note.title), + startIcon: buildIcon(note.getIcon(), note.getColorClass(), hideLabels ? undefined : note.title), endIcon: buildIcon("bxs-flag-checkered"), wptIcons: { "": buildIcon("bx bx-pin") @@ -265,7 +293,7 @@ function NoteGpxTrack({ note }: { note: FNote }) { polyline_options: { color: note.getLabelValue("color") ?? "blue" } - }), [ color, iconClass ]); + }), [ color, iconClass, hideLabels ]); return xmlString && ; } diff --git a/apps/client/src/widgets/collections/geomap/map.tsx b/apps/client/src/widgets/collections/geomap/map.tsx index 035f863cc8..19a4586c83 100644 --- a/apps/client/src/widgets/collections/geomap/map.tsx +++ b/apps/client/src/widgets/collections/geomap/map.tsx @@ -1,7 +1,7 @@ import { useEffect, useImperativeHandle, useRef, useState } from "preact/hooks"; import L, { control, LatLng, Layer, LeafletMouseEvent } from "leaflet"; import "leaflet/dist/leaflet.css"; -import { MAP_LAYERS } from "./map_layer"; +import { MAP_LAYERS, type MapLayer } from "./map_layer"; import { ComponentChildren, createContext, RefObject } from "preact"; import { useElementSize, useSyncedRef } from "../../react/hooks"; @@ -12,7 +12,7 @@ interface MapProps { containerRef?: RefObject; coordinates: LatLng | [number, number]; zoom: number; - layerName: string; + layerData: MapLayer; viewportChanged: (coordinates: LatLng, zoom: number) => void; children: ComponentChildren; onClick?: (e: LeafletMouseEvent) => void; @@ -21,7 +21,7 @@ interface MapProps { scale: boolean; } -export default function Map({ coordinates, zoom, layerName, viewportChanged, children, onClick, onContextMenu, scale, apiRef, containerRef: _containerRef, onZoom }: MapProps) { +export default function Map({ coordinates, zoom, layerData, viewportChanged, children, onClick, onContextMenu, scale, apiRef, containerRef: _containerRef, onZoom }: MapProps) { const mapRef = useRef(null); const containerRef = useSyncedRef(_containerRef); @@ -49,8 +49,6 @@ export default function Map({ coordinates, zoom, layerName, viewportChanged, chi const [ layer, setLayer ] = useState(); useEffect(() => { async function load() { - const layerData = MAP_LAYERS[layerName]; - if (layerData.type === "vector") { const style = (typeof layerData.style === "string" ? layerData.style : await layerData.style()); await import("@maplibre/maplibre-gl-leaflet"); @@ -68,7 +66,7 @@ export default function Map({ coordinates, zoom, layerName, viewportChanged, chi } load(); - }, [ layerName ]); + }, [ layerData ]); // Attach layer to the map. useEffect(() => { @@ -139,7 +137,7 @@ export default function Map({ coordinates, zoom, layerName, viewportChanged, chi return (
{children} diff --git a/apps/client/src/widgets/collections/geomap/map_layer.ts b/apps/client/src/widgets/collections/geomap/map_layer.ts index 7b12a10761..bb5f6174e6 100644 --- a/apps/client/src/widgets/collections/geomap/map_layer.ts +++ b/apps/client/src/widgets/collections/geomap/map_layer.ts @@ -1,20 +1,17 @@ -export interface MapLayer { - name: string; - isDarkTheme?: boolean; -} - -interface VectorLayer extends MapLayer { +export type MapLayer = ({ type: "vector"; style: string | (() => Promise<{}>) -} - -interface RasterLayer extends MapLayer { +} | { type: "raster"; url: string; attribution: string; -} +}) & { + // Common properties + name: string; + isDarkTheme?: boolean; +}; -export const MAP_LAYERS: Record = { +export const MAP_LAYERS: Record = { "openstreetmap": { name: "OpenStreetMap", type: "raster", diff --git a/apps/client/src/widgets/layout/ActiveContentBadges.tsx b/apps/client/src/widgets/layout/ActiveContentBadges.tsx index 3049e46243..fcccd00f29 100644 --- a/apps/client/src/widgets/layout/ActiveContentBadges.tsx +++ b/apps/client/src/widgets/layout/ActiveContentBadges.tsx @@ -251,10 +251,13 @@ function useActiveContentInfo(note: FNote | null | undefined) { for (const labelToCheck of activeContentLabels) { if (note.hasLabel(labelToCheck)) { type = labelToCheck; + isEnabled = true; + canToggleEnabled = true; break; } else if (note.hasLabel(`disabled:${labelToCheck}`)) { type = labelToCheck; isEnabled = false; + canToggleEnabled = true; break; } } diff --git a/apps/client/src/widgets/react/NotePropertyMenu.tsx b/apps/client/src/widgets/react/NotePropertyMenu.tsx index 6d8070741d..72c7a12d86 100644 --- a/apps/client/src/widgets/react/NotePropertyMenu.tsx +++ b/apps/client/src/widgets/react/NotePropertyMenu.tsx @@ -7,7 +7,7 @@ import FNote from "../../entities/fnote"; import NoteContextAwareWidget from "../note_context_aware_widget"; import { FormDropdownDivider, FormDropdownSubmenu, FormListItem, FormListToggleableItem } from "./FormList"; import FormTextBox from "./FormTextBox"; -import { useNoteLabel, useNoteLabelBoolean, useNoteLabelWithDefault } from "./hooks"; +import { useNoteLabel, useNoteLabelBoolean } from "./hooks"; import { ParentComponent } from "./react_utils"; export interface ClickContext { @@ -20,6 +20,8 @@ export interface CheckBoxProperty { label: string; bindToLabel: FilterLabelsByType; icon?: string; + /** When true, the checkbox will be checked when the label value is false. Useful when the label represents a "hide" action, without exposing double negatives to the user. */ + reverseValue?: boolean; } export interface ButtonProperty { @@ -203,8 +205,8 @@ function CheckBoxPropertyView({ note, property }: { note: FNote, property: Check setValue(property.reverseValue ? !newValue : newValue)} /> ); } diff --git a/apps/client/src/widgets/ribbon/collection-properties-config.tsx b/apps/client/src/widgets/ribbon/collection-properties-config.tsx index 2d6c051e91..b4a46a89bc 100644 --- a/apps/client/src/widgets/ribbon/collection-properties-config.tsx +++ b/apps/client/src/widgets/ribbon/collection-properties-config.tsx @@ -96,6 +96,13 @@ export const bookPropertiesConfig: Record = { icon: "bx bx-ruler", type: "checkbox", bindToLabel: "map:scale" + }, + { + label: t("book_properties_config.show-labels"), + icon: "bx bx-label", + type: "checkbox", + bindToLabel: "map:hideLabels", + reverseValue: true } ] }, diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Basic Concepts and Features/Active content.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Basic Concepts and Features/Active content.html index f45db3c93d..cc2294d9ef 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Basic Concepts and Features/Active content.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Basic Concepts and Features/Active content.html @@ -5,116 +5,109 @@

Active content problem of safety, especially when this active content comes from a third-party such as if it is downloaded from a website and then imported into Trilium.

-

When importing .zip - archives into Trilium, safe mode is active by default which will - try to prevent untrusted code from executing. For example, a custom widget needs - the #widget label in - order to function; safe import works by renaming that label to #disabled:widget.

+

When importing .zip archives into Trilium, safe mode is + active by default which will try to prevent untrusted code from executing. + For example, a custom widget needs the + #widget label in order to function; + safe import works by renaming that label to #disabled:widget.

Safe mode

Sometimes active content can cause issues with the UI or the server, preventing - it from functioning properly. Safe mode allows + it from functioning properly. Safe mode allows starting Trilium in such a way that active content is not loaded by default at start-up, allowing the user to fix the problematic scripts or widgets.

Types of active content

These are the types of active content in Trilium, along with a few examples of what untrusted content of that type could cause:

-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
NameDisabled on a safe import - DescriptionPotential risks of untrusted code
Front-end scripts - YesAllow running arbitrary code on the client (UI) of Trilium, which can - alter the user interface.A malicious script can execute server-side code, access un-encrypted notes - or change their contents.
Custom Widgets - YesCan add new UI features to Trilium, for example by adding a new section - in the Right Sidebar.The UI can be altered in such a way that it can be used to extract sensitive - information or it can simply cause the application to crash.
Backend scripts - YesCan run custom code on the server of Trilium (Node.js environment), with - full access to the notes and the database.Has access to all the unencrypted notes, but with full access to the database - it can completely destroy the data. It also has access to execute other - applications or alter the files and folders on the server).
Web View - YesDisplays a website inside a note.Can point to a phishing website which can collect the data (for example - on a log in page).
Render Note - YesRenders custom content inside a note, such as a dashboard or a new editor - that is not officially supported by Trilium.Can affect the UI similar to front-end scripts or custom widgets since - the scripts are not completely encapsulated, or they can act similar to - a web view where they can collect data entered by the user.
Custom app-wide CSS - NoCan alter the layout and style of the UI using CSS, applied regardless - of theme.Generally less problematic than the rest of active content, but a badly - written CSS can affect the layout of the application, requiring the use - of Safe mode to - be able to use the application.
Custom themes - NoCan change the style of the entire UI.Similar to custom app-wide CSS.
Icon Packs - NoIntroduces new icons that can be used for notes.Generally are more contained and less prone to cause issues, but they - can cause performance issues (for example if the icon pack has millions - of icons in it).
-
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
NameDisabled on a safe import + DescriptionPotential risks of untrusted code
Front-end scripts + YesAllow running arbitrary code on the client (UI) of Trilium, which can + alter the user interface.A malicious script can execute server-side code, access un-encrypted notes + or change their contents.
Custom Widgets + YesCan add new UI features to Trilium, for example by adding a new section + in the Right Sidebar.The UI can be altered in such a way that it can be used to extract sensitive + information or it can simply cause the application to crash.
Backend scripts + YesCan run custom code on the server of Trilium (Node.js environment), with + full access to the notes and the database.Has access to all the unencrypted notes, but with full access to the database + it can completely destroy the data. It also has access to execute other + applications or alter the files and folders on the server).
Web View + YesDisplays a website inside a note.Can point to a phishing website which can collect the data (for example + on a log in page).
Render Note + YesRenders custom content inside a note, such as a dashboard or a new editor + that is not officially supported by Trilium.Can affect the UI similar to front-end scripts or custom widgets since + the scripts are not completely encapsulated, or they can act similar to + a web view where they can collect data entered by the user.
Custom app-wide CSS + NoCan alter the layout and style of the UI using CSS, applied regardless + of theme.Generally less problematic than the rest of active content, but a badly + written CSS can affect the layout of the application, requiring the use + of Safe mode to + be able to use the application.
Custom themes + NoCan change the style of the entire UI.Similar to custom app-wide CSS.
Icon Packs + NoIntroduces new icons that can be used for notes.Generally are more contained and less prone to cause issues, but they + can cause performance issues (for example if the icon pack has millions + of icons in it).
+

Active content badge

-

Starting with v0.102.0, on the New Layout a +

Starting with v0.102.0, on the New Layout a badge will be displayed near the note title, indicating that an active content is detected. Clicking the badge will reveal a menu with various options related to that content type, for example to open the documentation @@ -122,5 +115,4 @@ style="width:100%;">

For some active content types, such as backend scripts with custom triggering conditions a toggle button will appear. This makes it possible to easily disable scripts or widgets, but also to re-enable them if an import was - made with safe mode active.

-

 

\ No newline at end of file + made with safe mode active.

\ No newline at end of file diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Collections/Geo Map.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Collections/Geo Map.html index cfee0ce25f..e86e58f98a 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Collections/Geo Map.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Collections/Geo Map.html @@ -1,9 +1,8 @@

Creating a new geo map

- - - - - - - - - - - - - - - - - - - - -
1 -
- -
-
Right click on any note on the note tree and select Insert child noteGeo Map (beta).
2 -
- -
-
By default the map will be empty and will show the entire world.
- +
+ + + + + + + + + + + + + + + + + + + + +
   
1 +
+ +
+
Right click on any note on the note tree and select Insert child noteGeo Map (beta).
2 +
+ +
+
By default the map will be empty and will show the entire world.
+

Repositioning the map

  • Click and drag the map in order to move across the map.
  • @@ -55,59 +55,60 @@ restored when visiting again the note.

    Adding a marker using the map

    Adding a new note using the plus button

    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    1To create a marker, first navigate to the desired point on the map. Then - press the - button in the Floating buttons (top-right) - area.     -
    -
    If the button is not visible, make sure the button section is visible - by pressing the chevron button ( - ) in the top-right of the map.
    2 - - Once pressed, the map will enter in the insert mode, as illustrated by - the notification.        -
    -
    Simply click the point on the map where to place the marker, or the Escape - key to cancel.
    3 - - Enter the name of the marker/note to be created.
    4 - - Once confirmed, the marker will show up on the map and it will also be - displayed as a child note of the map.
    - +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
       
    1To create a marker, first navigate to the desired point on the map. Then + press the + button in the Floating buttons (top-right) + area.      +
    +
    If the button is not visible, make sure the button section is visible + by pressing the chevron button ( + ) in the top-right of the map.
     
    2 + + Once pressed, the map will enter in the insert mode, as illustrated by + the notification.         +
    +
    Simply click the point on the map where to place the marker, or the Escape + key to cancel.
    3 + + Enter the name of the marker/note to be created.
    4 + + Once confirmed, the marker will show up on the map and it will also be + displayed as a child note of the map.
    +

    Adding a new note using the contextual menu

    1. Right click anywhere on the map, where to place the newly created marker @@ -120,15 +121,18 @@

      Adding an existing note on note from the note tree

      1. Select the desired note in the Note Tree.
      2. -
      3. Hold the mouse on the note and drag it to the map to the desired location.
      4. -
      5. The map should be updated with the new marker.
      6. +
      7. Hold the mouse on the note and drag it to the map to the desired location.
      8. +
      9. The map should be updated with the new marker.

      This works for:

      • Notes that are not part of the geo map, case in which a clone will be created.
      • Notes that are a child of the geo map but not yet positioned on the map.
      • -
      • Notes that are a child of the geo map and also positioned, case in which +
      • Notes that are a child of the geo map and also positioned, case in which the marker will be relocated to the new position.
    2. Middle-clicking the marker will open the note in a new tab.
    3. Right-clicking the marker will open a contextual menu (as described below).
    4. -
    5. If the map is in read-only mode, clicking on a marker will open a  +
    6. If the map is in read-only mode, clicking on a marker will open a  Quick edit popup for the corresponding note.
@@ -206,211 +213,239 @@ width="1288" height="278">

The value of the attribute is made up of the latitude and longitude separated by a comma.

Adding from Google Maps

- - - - - - - - - - - - - - - - - - - - - - - - - -
1 -
- -
-
Go to Google Maps on the web and look for a desired location, right click - on it and a context menu will show up.        -
-
Simply click on the first item displaying the coordinates and they will - be copied to clipboard.        -
-
Then paste the value inside the text box into the #geolocation attribute - of a child note of the map (don't forget to surround the value with a - "character).
2 -
- -
-
In Trilium, create a child note under the map.
3 -
- -
-
And then go to Owned Attributes and type #geolocation=", - then paste from the clipboard as-is and then add the ending " character. - Press Enter to confirm and the map should now be updated to contain the - new note.
- +
+ + + + + + + + + + + + + + + + + + + + + + + + + +
   
1 +
+ +
+
Go to Google Maps on the web and look for a desired location, right click + on it and a context menu will show up.         +
+
Simply click on the first item displaying the coordinates and they will + be copied to clipboard.         +
+
Then paste the value inside the text box into the #geolocation attribute + of a child note of the map (don't forget to surround the value with a + "character).
2 +
+ +
+
In Trilium, create a child note under the map.
3 +
+ +
+
And then go to Owned Attributes and type #geolocation=", + then paste from the clipboard as-is and then add the ending " character. + Press Enter to confirm and the map should now be updated to contain the + new note.
+

Adding from OpenStreetMap

Similarly to the Google Maps approach:

- - - - - - - - - - - - - - - - - - - - - - - - - -
1 - - Go to any location on openstreetmap.org and right click to bring up the - context menu. Select the “Show address” item.
2 - - The address will be visible in the top-left of the screen, in the place - of the search bar.        -
-
Select the coordinates and copy them into the clipboard.
3 - - Simply paste the value inside the text box into the #geolocation attribute - of a child note of the map and then it should be displayed on the map.
- +
+ + + + + + + + + + + + + + + + + + + + + + + + + +
   
1 + + Go to any location on openstreetmap.org and right click to bring up the + context menu. Select the “Show address” item.
2 + + The address will be visible in the top-left of the screen, in the place + of the search bar.         +
+
Select the coordinates and copy them into the clipboard.
3 + + Simply paste the value inside the text box into the #geolocation attribute + of a child note of the map and then it should be displayed on the map.
+

Adding GPS tracks (.gpx)

Trilium has basic support for displaying GPS tracks on the geo map.

- - - - - - - - - - - - - - - - - - - - - - - - - -
1 -
- -
-
To add a track, simply drag & drop a .gpx file inside the geo map - in the note tree.
2 -
- -
-
In order for the file to be recognized as a GPS track, it needs to show - up as application/gpx+xml in the File type field.
3 -
- -
-
When going back to the map, the track should now be visible.        -
-
The start and end points of the track are indicated by the two blue markers.
- -

Read-only mode

-

When a map is in read-only all editing features will be disabled such - as:

-
    -
  • The add button in the Floating buttons.
  • -
  • Dragging markers.
  • -
  • Editing from the contextual menu (removing locations or adding new items).
  • -
-

To enable read-only mode simply press the Lock icon from the  - Floating buttons. To disable it, press the button again.

-

Configuration

-

Map Style

-

The styling of the map can be adjusted in the Collection Properties tab - in the Ribbon or - manually via the #map:style attribute.

-

The geo map comes with two different types of styles:

-
    -
  • Raster styles -
      -
    • For these styles the map is represented as a grid of images at different - zoom levels. This is the traditional way OpenStreetMap used to work.
    • -
    • Zoom is slightly restricted.
    • -
    • Currently, the only raster theme is the original OpenStreetMap style.
    • +
      + + + + + + + + + + + + + + + + + + + + + + + + + +
         
      1 +
      + +
      +
      To add a track, simply drag & drop a .gpx file inside the geo map + in the note tree.
      2 +
      + +
      +
      In order for the file to be recognized as a GPS track, it needs to show + up as application/gpx+xml in the File type field.
      3 +
      + +
      +
      When going back to the map, the track should now be visible.         +
      +
      The start and end points of the track are indicated by the two blue markers.
      +
      + +

      Read-only mode

      +

      When a map is in read-only all editing features will be disabled such + as:

      +
        +
      • The add button in the Floating buttons.
      • +
      • Dragging markers.
      • +
      • Editing from the contextual menu (removing locations or adding new items).
      • +
      +

      To enable read-only mode simply press the Lock icon from the  + Floating buttons. To disable it, press the button again.

      +

      Configuration

      +

      Map Style

      +

      The styling of the map can be adjusted in the Collection Properties (above + the map, by pressing on the Gear icon) or manually via the #map:style attribute.

      +

      The geo map comes with two different types of styles:

      +
        +
      • Raster styles +
          +
        • For these styles the map is represented as a grid of images at different + zoom levels. This is the traditional way OpenStreetMap used to work.
        • +
        • Zoom is slightly restricted.
        • +
        • Currently, the only raster theme is the original OpenStreetMap style.
        -
      • -
      • Vector styles -
          -
        • Vector styles are not represented as images, but as geometrical shapes. - This makes the rendering much smoother, especially when zooming and looking - at the building edges, for example.
        • -
        • The map can be zoomed in much further.
        • -
        • These come both in a light and a dark version.
        • -
        • The vector styles come from VersaTiles, - a free and open-source project providing map tiles based on OpenStreetMap.
        • -
        -
      • -
      - -

      Scale

      -

      Activating this option via the Ribbon or - manually via #map:scale will display an indicator - in the bottom-left of the scale of the map.

      -

      Troubleshooting

      -
      - -
      - -

      Grid-like artifacts on the map

      -

      This occurs if the application is not at 100% zoom which causes the pixels - of the map to not render correctly due to fractional scaling. The only - possible solution is to set the UI zoom at 100% (default keyboard shortcut - is Ctrl+0).

      \ No newline at end of file + +
    • Vector styles +
        +
      • Vector styles are not represented as images, but as geometrical shapes. + This makes the rendering much smoother, especially when zooming and looking + at the building edges, for example.
      • +
      • The map can be zoomed in much further.
      • +
      • These come both in a light and a dark version.
      • +
      • The vector styles come from VersaTiles, + a free and open-source project providing map tiles based on OpenStreetMap.
      • +
      +
    • +
    +

    Custom map style / tiles

    +

    Starting with v0.102.0 it is possible to use custom tile sets, but only + in raster format.

    +

    To do so, manually set the #map:style + labelto the URL of the tile set. For example, to use Esri.NatGeoWorldMap, + set the value to https://server.arcgisonline.com/ArcGIS/rest/services/NatGeo_World_Map/MapServer/tile/{z}/{y}/{x}. +

    + +

    Custom vector map support is planned, but not yet implemented.

    +

    Other options

    +

    The following options can be configured either via the Collection properties + pane above the map, by clicking on the settings (Gear icon). Alternatively, + each of these options also have a corresponding label that + can be set manually.

    +
      +
    • +

      Scale, which illustrates the scale of the map in kilometers and miles + in the bottom-left of the map.

      +
    • +
    • +

      The name of the markers is displayed by default underneath the pin on + the map. Since v0.102.0, it is possible to hide these labels which increases + the performance and decreases clutter when there are many markers on the + map.

      +
    • +
    +

    Troubleshooting

    +
    + +
    +

    Grid-like artifacts on the map

    +

    This occurs if the application is not at 100% zoom which causes the pixels + of the map to not render correctly due to fractional scaling. The only + possible solution is to set the UI zoom at 100% (default keyboard shortcut + is Ctrl+0).

    \ No newline at end of file diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Note Types/Render Note.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Note Types/Render Note.html index 1bac949e3e..7e6b8cddbe 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Note Types/Render Note.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Note Types/Render Note.html @@ -2,7 +2,7 @@
-

Render Note is a special case of front-end scripting which +

Render Note is a special case of front-end scripting which allows rendering custom content inside a note. This makes it possible to create custom dashboards, or to use a custom note editor.

The content can either be a vanilla HTML, or Preact JSX.

@@ -13,13 +13,11 @@
  1. HTML language for the legacy/vanilla method, with what needs to be displayed (for example <p>Hello world.</p>).
  2. -
  3. JSX for the Preact-based approach (see below).
  4. -
+
  • JSX for the Preact-based approach (see below).
  • +
  • Create a Render Note.
  • -
  • Assign the renderNote relation to +
  • Assign the renderNote relation to point at the previously created code note.
  • Legacy scripting using jQuery

    @@ -48,9 +46,10 @@ $dateEl.text(new Date()); need to provide a HTML anymore.

    Here are the steps to creating a simple render note:

      -
    1. Create a note of type Render Note.
    2. -
    3. +
    4. +

      Create a note of type Render Note.

      +
    5. +
    6. Create a child Code note with JSX as the language.
      As an example, use the following content:

      export default function() {
      @@ -60,17 +59,20 @@ $dateEl.text(new Date());
      </> ); } -
    7. -
    8. In the parent render note, define a ~renderNote relation - pointing to the newly created child.
    9. -
    10. Refresh the render note and it should display a “Hello world” message.
    11. + +
    12. +

      In the parent render note, define a ~renderNote relation + pointing to the newly created child.

      +
    13. +
    14. +

      Refresh the render note and it should display a “Hello world” message.

      +

    Refreshing the note

    It's possible to refresh the note via:

    Examples

    diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts.html index 80cbebbfeb..8691c4c054 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts.html @@ -1,11 +1,11 @@ -

    Unlike front-end scripts which - run on the client / browser-side, back-end scripts run directly on the - Node.js environment of the Trilium server.

    +

    Unlike front-end scripts which run on the + client / browser-side, back-end scripts run directly on the Node.js environment + of the Trilium server.

    Back-end scripts can be used both on a Server Installation (where - it will run on the device the server is running on), or on the  - Desktop Installation (where it will run on the PC).

    + href="#root/_help_WOcw2SLH6tbX">Server Installation (where it will run + on the device the server is running on), or on the Desktop Installation (where it will + run on the PC).

    Advantages of backend scripts

    The benefit of backend scripts is that they can be pretty powerful, for example to have access to the underlying system, for example it can read @@ -14,7 +14,7 @@ access to the notes since the information about them is already loaded in memory. Whereas on the client, notes have to be manually loaded first.

    Creating a backend script

    -

    Create a new Code note +

    Create a new Code note and select the language JS backend.

    Running backend scripts

    Backend scripts can be either run manually (via the Execute button on @@ -22,8 +22,8 @@

    In addition, scripts can be run automatically when the server starts up, on a fixed time interval or when a certain event occurs (such as an attribute being modified). For more information, see the dedicated Events page.

    + href="#root/_help_GPERMystNGTB">Events page.

    Script API

    Trilium exposes a set of APIs that can be directly consumed by scripts, under the api object. For a reference of - this API, see Backend API.

    \ No newline at end of file + this API, see Backend API.

    \ No newline at end of file diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts/Events.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts/Events.html index 3e54232a5d..de4beda67f 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts/Events.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Backend scripts/Events.html @@ -5,139 +5,137 @@

    Global events are attached to the script note via label. Simply create e.g. "run" label with some of these values and script note will be executed once the event occurs.

    -
    - - - - - - - - - - - - - - - - - - - - - -
    LabelDescription
    run - -

    Defines on which events script should run. Possible values are:

    -
      -
    • backendStartup - when Trilium backend starts - up
    • -
    • hourly - run once an hour. You can use - additional label runAtHour to specify at - which hour, on the back-end.
    • -
    • daily - run once a day, on the back-end
    • -
    -
    runOnInstance - Specifies that the script should only run on a particular Trilium instance.
    runAtHour - On which hour should this run. Should be used together with #run=hourly. - Can be defined multiple times for more runs during the day.
    -
    + + + + + + + + + + + + + + + + + + + + + +
    LabelDescription
    run + +

    Defines on which events script should run. Possible values are:

    +
      +
    • backendStartup - when Trilium backend starts + up
    • +
    • hourly - run once an hour. You can use + additional label runAtHour to specify at + which hour, on the back-end.
    • +
    • daily - run once a day, on the back-end
    • +
    +
    runOnInstance + Specifies that the script should only run on a particular Trilium instance.
    runAtHour + On which hour should this run. Should be used together with #run=hourly. + Can be defined multiple times for more runs during the day.
    +

    Entity events

    Other events are bound to some entity, these are defined as relations - meaning that script is triggered only if note has this script attached to it through relations (or it can inherit it).

    -
    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    RelationTrigger conditionOrigin entity (see below)
    runOnNoteCreation - executes when note is created on backend. Use this relation if you want - to run the script for all notes created under a specific subtree. In that - case, create it on the subtree root note and make it inheritable. A new - note created within the subtree (any depth) will trigger the script.The BNote that got created.
    runOnChildNoteCreation - executes when new note is created under the note where this relation is - definedThe BNote of the child that got created.
    runOnNoteTitleChange - executes when note title is changed (includes note creation as well)The BNote of the note whose title got changed.
    runOnNoteContentChange - executes when note content is changed (includes note creation as well).The BNote of the note whose content got - changed.
    runOnNoteChange - executes when note is changed (includes note creation as well). Does not - include content changesThe BNote of the note that got changed.
    runOnNoteDeletion - executes when note is being deletedThe BNote of the note that got (soft) deleted.
    runOnBranchCreation - executes when a branch is created. Branch is a link between parent note - and child note and is created e.g. when cloning or moving note.The BBranch that got created.
    runOnBranchChange - executes when a branch is updated. (since v0.62)The BBranch that got changed.
    runOnBranchDeletion - executes when a branch is deleted. Branch is a link between parent note - and child note and is deleted e.g. when moving note (old branch/link is - deleted).The BBranch that got (soft) deleted.
    runOnAttributeCreation - executes when new attribute is created for the note which defines this - relationThe BAttribute that got created.
    runOnAttributeChange - executes when the attribute is changed of a note which defines this relation. - This is triggered also when the attribute is deletedThe BAttribute that got changed.
    -
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    RelationTrigger conditionOrigin entity (see below)
    runOnNoteCreation + executes when note is created on backend. Use this relation if you want + to run the script for all notes created under a specific subtree. In that + case, create it on the subtree root note and make it inheritable. A new + note created within the subtree (any depth) will trigger the script.The BNote that got created.
    runOnChildNoteCreation + executes when new note is created under the note where this relation is + definedThe BNote of the child that got created.
    runOnNoteTitleChange + executes when note title is changed (includes note creation as well)The BNote of the note whose title got changed.
    runOnNoteContentChange + executes when note content is changed (includes note creation as well).The BNote of the note whose content got + changed.
    runOnNoteChange + executes when note is changed (includes note creation as well). Does not + include content changesThe BNote of the note that got changed.
    runOnNoteDeletion + executes when note is being deletedThe BNote of the note that got (soft) deleted.
    runOnBranchCreation + executes when a branch is created. Branch is a link between parent note + and child note and is created e.g. when cloning or moving note.The BBranch that got created.
    runOnBranchChange + executes when a branch is updated. (since v0.62)The BBranch that got changed.
    runOnBranchDeletion + executes when a branch is deleted. Branch is a link between parent note + and child note and is deleted e.g. when moving note (old branch/link is + deleted).The BBranch that got (soft) deleted.
    runOnAttributeCreation + executes when new attribute is created for the note which defines this + relationThe BAttribute that got created.
    runOnAttributeChange + executes when the attribute is changed of a note which defines this relation. + This is triggered also when the attribute is deletedThe BAttribute that got changed.
    +

    Origin entity

    When a script is run by an event such as the ones described above, Front-end scripts are custom JavaScript notes that are run on the client (browser environment)

    There are four flavors of front-end scripts:

    -
    - - - - - - - - - - - - - - - - - - - - - - - -
    Regular scriptsThese are run with the current app and note context. These can be run - either manually or automatically on start-up.
    Custom Widgets - These can introduce new UI elements in various positions, such as near - the Note Tree, - content area or even the Right Sidebar.
    Launch Bar Widgets - Similar to Custom Widgets, - but dedicated to the Launch Bar. - These can simply introduce new buttons or graphical elements to the bar.
    Render Note - This allows rendering custom content inside a note, using either HTML - or Preact JSX.
    -
    + + + + + + + + + + + + + + + + + + + + + + + + + +
    Regular scriptsThese are run with the current app and note context. These can be run + either manually or automatically on start-up.
    Custom Widgets + These can introduce new UI elements in various positions, such as near + the Note Tree, + content area or even the Right Sidebar.
    Launch Bar Widgets + Similar to Custom Widgets, + but dedicated to the Launch Bar. + These can simply introduce new buttons or graphical elements to the bar.
    Render Note + This allows rendering custom content inside a note, using either HTML + or Preact JSX.

    For more advanced behaviors that do not require a user interface (e.g. - batch modifying notes), see Backend scripts.

    + batch modifying notes), see Backend scripts.

    Scripts

    Scripts don't have any special requirements. They can be run manually using the Execute button on the code note or they can be run automatically; - to do so, set the run label to + to do so, set the run label to either:

    • frontendStartup - when Trilium frontend @@ -55,23 +54,23 @@ style="width:100%;"> they can run automatically on a hourly or daily basis, but also on events such as when a note is created or an attribute is modified. See the server-side  Events for more information.

      + class="reference-link" href="#root/_help_GPERMystNGTB">Events for more information.

      Widgets

      Widgets require a certain format in order for Trilium to be able to integrate them into the UI.

      • For legacy widgets, the script note must export a BasicWidget or - a derived one (see Note context aware widget or  + a derived one (see Note context aware widget or  Right pane widget).
      • + class="reference-link" href="#root/_help_M8IppdwVHSjG">Right pane widget).
      • For Preact widgets, a built-in helper called defineWidget needs to be used.
      -

      For more information, see Custom Widgets.

      +

      For more information, see Custom Widgets.

      Script API

      The front-end API of Trilium is available to all scripts running in the front-end context as global variable api. - For a reference of the API, see Frontend API.

      + For a reference of the API, see Frontend API.

      Tutorial

      For more information on building widgets, take a look at Widget Basics.

      \ No newline at end of file diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Custom Widgets.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Custom Widgets.html index 416c15c107..dc99ba8553 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Custom Widgets.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Custom Widgets.html @@ -20,15 +20,14 @@

      Creating a custom widget

      1. Create a Code note.
      2. -
      3. Set the language to: +
      4. Set the language to:
        1. JavaScript (frontend) for legacy widgets using jQuery.
        2. JSX for Preact widgets. You might need to go to Options → Code to enable the language first.
        -
      5. -
      6. Apply the #widget label.
      7. + +
      8. Apply the #widget label.

      Getting started with a simple example

      Let's start by creating a widget that shows a message near the content @@ -62,81 +61,79 @@ export default defineWidget({ should appear underneath the content area.

      Widget location (parent widget)

      A widget can be placed in one of the following sections of the applications:

      -
      - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
      Value for parentWidget - DescriptionSample widgetSpecial requirements
      left-pane - Appears within the same pane that holds the Note Tree.Same as above, with only a different parentWidget.None.
      center-pane - In the content area. If a split is open, the widget will span all of the - splits.See example above.None.
      note-detail-pane - -

      In the content area, inside the note detail area. If a split is open, - the widget will be contained inside the split.

      -

      This is ideal if the widget is note-specific.

      -
      Note context aware widget - -
        -
      • The widget must export a class and not an - instance of the class (e.g. no new) because - it needs to be multiplied for each note, so that splits work correctly.
      • -
      • Since the class is exported instead of an - instance, the parentWidget getter must be - static, otherwise the widget is ignored.
      • -
      -
      right-pane - In the Right Sidebar, - as a dedicated section.Right pane widget - -
        -
      • Although not mandatory, it's best to use a RightPanelWidget instead - of a BasicWidget or a NoteContextAwareWidget.
      • -
      -
      + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
      Value for parentWidget + DescriptionSample widgetSpecial requirements
      left-pane + Appears within the same pane that holds the Note Tree.Same as above, with only a different parentWidget.None.
      center-pane + In the content area. If a split is open, the widget will span all of the + splits.See example above.None.
      note-detail-pane + +

      In the content area, inside the note detail area. If a split is open, + the widget will be contained inside the split.

      +

      This is ideal if the widget is note-specific.

      +
      Note context aware widget + +
        +
      • The widget must export a class and not an + instance of the class (e.g. no new) because + it needs to be multiplied for each note, so that splits work correctly.
      • +
      • Since the class is exported instead of an + instance, the parentWidget getter must be + static, otherwise the widget is ignored.
      • +
      +
      right-pane + In the Right Sidebar, + as a dedicated section.Right pane widget + +
        +
      • Although not mandatory, it's best to use a RightPanelWidget instead + of a BasicWidget or a NoteContextAwareWidget.
      • +
      +
      -

      To position the widget somewhere else, just change the value passed to get parentWidget()for legacy widgets or the parent field diff --git a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Launch Bar Widgets.html b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Launch Bar Widgets.html index c2b91ba4ed..acf5a50e35 100644 --- a/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Launch Bar Widgets.html +++ b/apps/server/src/assets/doc_notes/en/User Guide/User Guide/Scripting/Frontend Basics/Launch Bar Widgets.html @@ -20,16 +20,11 @@

    • Don't set #widget, as that attribute is reserved for Custom Widgets.
    • -
    • In the Global menu, +
    • In the Global menu, select Configure launchbar.
    • -
    • In the Visible Launchers section, select Add a custom widget.
    • -
    • Give the newly created launcher a name (and optionally a name).
    • -
    • In the Promoted Attributes section, - modify the widget field to point to the newly created note.
    • -
    • Refresh the - UI.
    • +
    • In the Visible Launchers section, select Add a custom widget.
    • +
    • Give the newly created launcher a name (and optionally a name).
    • +
    • In the Promoted Attributes section, + modify the widget field to point to the newly created note.
    • +
    • Refresh the UI.
    • \ No newline at end of file diff --git a/docs/Developer Guide/Developer Guide/Documentation.md b/docs/Developer Guide/Developer Guide/Documentation.md index 6631466e38..8e669ac866 100644 --- a/docs/Developer Guide/Developer Guide/Documentation.md +++ b/docs/Developer Guide/Developer Guide/Documentation.md @@ -1,5 +1,5 @@ # Documentation -There are multiple types of documentation for Trilium: +There are multiple types of documentation for Trilium: * The _User Guide_ represents the user-facing documentation. This documentation can be browsed by users directly from within Trilium, by pressing F1. * The _Developer's Guide_ represents a set of Markdown documents that present the internals of Trilium, for developers. diff --git a/docs/User Guide/!!!meta.json b/docs/User Guide/!!!meta.json index 817f450e42..f9136647f9 100644 --- a/docs/User Guide/!!!meta.json +++ b/docs/User Guide/!!!meta.json @@ -6459,6 +6459,97 @@ "type": "text", "mime": "text/html", "attributes": [ + { + "type": "relation", + "name": "internalLink", + "value": "mHbBMPDPkVV5", + "isInheritable": false, + "position": 10 + }, + { + "type": "relation", + "name": "internalLink", + "value": "MgibgPcfeuGz", + "isInheritable": false, + "position": 20 + }, + { + "type": "relation", + "name": "internalLink", + "value": "HI6GBBIduIgv", + "isInheritable": false, + "position": 30 + }, + { + "type": "relation", + "name": "internalLink", + "value": "64ZTlUPgEPtW", + "isInheritable": false, + "position": 40 + }, + { + "type": "relation", + "name": "internalLink", + "value": "yIhgI5H7A2Sm", + "isInheritable": false, + "position": 50 + }, + { + "type": "relation", + "name": "internalLink", + "value": "RnaPdbciOfeq", + "isInheritable": false, + "position": 60 + }, + { + "type": "relation", + "name": "internalLink", + "value": "SPirpZypehBG", + "isInheritable": false, + "position": 70 + }, + { + "type": "relation", + "name": "internalLink", + "value": "1vHRoWCEjj0L", + "isInheritable": false, + "position": 80 + }, + { + "type": "relation", + "name": "internalLink", + "value": "HcABDtFCkbFN", + "isInheritable": false, + "position": 90 + }, + { + "type": "relation", + "name": "internalLink", + "value": "AlhDUqhENtH7", + "isInheritable": false, + "position": 100 + }, + { + "type": "relation", + "name": "internalLink", + "value": "pKK96zzmvBGf", + "isInheritable": false, + "position": 110 + }, + { + "type": "relation", + "name": "internalLink", + "value": "gOKqSJgXLcIj", + "isInheritable": false, + "position": 120 + }, + { + "type": "relation", + "name": "internalLink", + "value": "IjZS7iK5EXtb", + "isInheritable": false, + "position": 130 + }, { "type": "label", "name": "iconClass", @@ -6472,97 +6563,6 @@ "value": "active-content", "isInheritable": false, "position": 40 - }, - { - "type": "relation", - "name": "internalLink", - "value": "MgibgPcfeuGz", - "isInheritable": false, - "position": 50 - }, - { - "type": "relation", - "name": "internalLink", - "value": "1vHRoWCEjj0L", - "isInheritable": false, - "position": 70 - }, - { - "type": "relation", - "name": "internalLink", - "value": "yIhgI5H7A2Sm", - "isInheritable": false, - "position": 100 - }, - { - "type": "relation", - "name": "internalLink", - "value": "HcABDtFCkbFN", - "isInheritable": false, - "position": 110 - }, - { - "type": "relation", - "name": "internalLink", - "value": "RnaPdbciOfeq", - "isInheritable": false, - "position": 120 - }, - { - "type": "relation", - "name": "internalLink", - "value": "SPirpZypehBG", - "isInheritable": false, - "position": 130 - }, - { - "type": "relation", - "name": "internalLink", - "value": "mHbBMPDPkVV5", - "isInheritable": false, - "position": 150 - }, - { - "type": "relation", - "name": "internalLink", - "value": "AlhDUqhENtH7", - "isInheritable": false, - "position": 160 - }, - { - "type": "relation", - "name": "internalLink", - "value": "pKK96zzmvBGf", - "isInheritable": false, - "position": 170 - }, - { - "type": "relation", - "name": "internalLink", - "value": "gOKqSJgXLcIj", - "isInheritable": false, - "position": 180 - }, - { - "type": "relation", - "name": "internalLink", - "value": "64ZTlUPgEPtW", - "isInheritable": false, - "position": 190 - }, - { - "type": "relation", - "name": "internalLink", - "value": "HI6GBBIduIgv", - "isInheritable": false, - "position": 200 - }, - { - "type": "relation", - "name": "internalLink", - "value": "IjZS7iK5EXtb", - "isInheritable": false, - "position": 210 } ], "format": "markdown", @@ -9943,7 +9943,7 @@ { "type": "relation", "name": "internalLink", - "value": "CdNpE2pqjmI6", + "value": "yIhgI5H7A2Sm", "isInheritable": false, "position": 10 }, @@ -9971,31 +9971,38 @@ { "type": "relation", "name": "internalLink", - "value": "XpOYSgsLkTJy", + "value": "CdNpE2pqjmI6", "isInheritable": false, "position": 50 }, { "type": "relation", "name": "internalLink", - "value": "A9Oc6YKKc65v", + "value": "XpOYSgsLkTJy", "isInheritable": false, "position": 60 }, { "type": "relation", "name": "internalLink", - "value": "R7abl2fc6Mxi", + "value": "A9Oc6YKKc65v", "isInheritable": false, "position": 70 }, { "type": "relation", "name": "internalLink", - "value": "6tZeKvSHEUiB", + "value": "R7abl2fc6Mxi", "isInheritable": false, "position": 80 }, + { + "type": "relation", + "name": "internalLink", + "value": "6tZeKvSHEUiB", + "isInheritable": false, + "position": 90 + }, { "type": "label", "name": "iconClass", @@ -10009,13 +10016,6 @@ "value": "render-note", "isInheritable": false, "position": 70 - }, - { - "type": "relation", - "name": "internalLink", - "value": "yIhgI5H7A2Sm", - "isInheritable": false, - "position": 90 } ], "format": "markdown", @@ -11175,20 +11175,6 @@ "type": "text", "mime": "text/html", "attributes": [ - { - "type": "relation", - "name": "internalLink", - "value": "zEY4DaJG4YT5", - "isInheritable": false, - "position": 10 - }, - { - "type": "relation", - "name": "internalLink", - "value": "OFXdgB2nNk1F", - "isInheritable": false, - "position": 20 - }, { "type": "relation", "name": "internalLink", @@ -11238,13 +11224,6 @@ "isInheritable": false, "position": 90 }, - { - "type": "relation", - "name": "internalLink", - "value": "BlN9DFI679QC", - "isInheritable": false, - "position": 100 - }, { "type": "label", "name": "iconClass", @@ -11258,6 +11237,13 @@ "value": "geomap", "isInheritable": false, "position": 90 + }, + { + "type": "relation", + "name": "internalLink", + "value": "HI6GBBIduIgv", + "isInheritable": false, + "position": 110 } ], "format": "markdown", @@ -16248,10 +16234,94 @@ { "type": "relation", "name": "internalLink", - "value": "SynTBQiBsdYJ", + "value": "MgibgPcfeuGz", + "isInheritable": false, + "position": 10 + }, + { + "type": "relation", + "name": "internalLink", + "value": "oPVyFC7WL2Lp", + "isInheritable": false, + "position": 20 + }, + { + "type": "relation", + "name": "internalLink", + "value": "RnaPdbciOfeq", "isInheritable": false, "position": 30 }, + { + "type": "relation", + "name": "internalLink", + "value": "4Gn3psZKsfSm", + "isInheritable": false, + "position": 40 + }, + { + "type": "relation", + "name": "internalLink", + "value": "xYmIYSP6wE3F", + "isInheritable": false, + "position": 50 + }, + { + "type": "relation", + "name": "internalLink", + "value": "HcABDtFCkbFN", + "isInheritable": false, + "position": 60 + }, + { + "type": "relation", + "name": "internalLink", + "value": "SPirpZypehBG", + "isInheritable": false, + "position": 70 + }, + { + "type": "relation", + "name": "internalLink", + "value": "HI6GBBIduIgv", + "isInheritable": false, + "position": 80 + }, + { + "type": "relation", + "name": "internalLink", + "value": "GPERMystNGTB", + "isInheritable": false, + "position": 90 + }, + { + "type": "relation", + "name": "internalLink", + "value": "GhurYZjh8e1V", + "isInheritable": false, + "position": 100 + }, + { + "type": "relation", + "name": "internalLink", + "value": "M8IppdwVHSjG", + "isInheritable": false, + "position": 110 + }, + { + "type": "relation", + "name": "internalLink", + "value": "Q2z6av6JZVWm", + "isInheritable": false, + "position": 120 + }, + { + "type": "relation", + "name": "internalLink", + "value": "SynTBQiBsdYJ", + "isInheritable": false, + "position": 130 + }, { "type": "label", "name": "shareAlias", @@ -16265,90 +16335,6 @@ "value": "bx bx-window", "isInheritable": false, "position": 40 - }, - { - "type": "relation", - "name": "internalLink", - "value": "Q2z6av6JZVWm", - "isInheritable": false, - "position": 50 - }, - { - "type": "relation", - "name": "internalLink", - "value": "GhurYZjh8e1V", - "isInheritable": false, - "position": 60 - }, - { - "type": "relation", - "name": "internalLink", - "value": "M8IppdwVHSjG", - "isInheritable": false, - "position": 70 - }, - { - "type": "relation", - "name": "internalLink", - "value": "MgibgPcfeuGz", - "isInheritable": false, - "position": 80 - }, - { - "type": "relation", - "name": "internalLink", - "value": "SPirpZypehBG", - "isInheritable": false, - "position": 90 - }, - { - "type": "relation", - "name": "internalLink", - "value": "RnaPdbciOfeq", - "isInheritable": false, - "position": 100 - }, - { - "type": "relation", - "name": "internalLink", - "value": "oPVyFC7WL2Lp", - "isInheritable": false, - "position": 110 - }, - { - "type": "relation", - "name": "internalLink", - "value": "4Gn3psZKsfSm", - "isInheritable": false, - "position": 120 - }, - { - "type": "relation", - "name": "internalLink", - "value": "xYmIYSP6wE3F", - "isInheritable": false, - "position": 130 - }, - { - "type": "relation", - "name": "internalLink", - "value": "HcABDtFCkbFN", - "isInheritable": false, - "position": 140 - }, - { - "type": "relation", - "name": "internalLink", - "value": "HI6GBBIduIgv", - "isInheritable": false, - "position": 150 - }, - { - "type": "relation", - "name": "internalLink", - "value": "GPERMystNGTB", - "isInheritable": false, - "position": 160 } ], "format": "markdown", @@ -16980,6 +16966,13 @@ "isInheritable": false, "position": 60 }, + { + "type": "relation", + "name": "internalLink", + "value": "s8alTXmpFR61", + "isInheritable": false, + "position": 70 + }, { "type": "label", "name": "iconClass", @@ -16993,13 +16986,6 @@ "value": "launch-bar-widgets", "isInheritable": false, "position": 40 - }, - { - "type": "relation", - "name": "internalLink", - "value": "s8alTXmpFR61", - "isInheritable": false, - "position": 70 } ], "format": "markdown", @@ -17444,6 +17430,48 @@ "type": "text", "mime": "text/html", "attributes": [ + { + "type": "relation", + "name": "internalLink", + "value": "yIhgI5H7A2Sm", + "isInheritable": false, + "position": 10 + }, + { + "type": "relation", + "name": "internalLink", + "value": "WOcw2SLH6tbX", + "isInheritable": false, + "position": 20 + }, + { + "type": "relation", + "name": "internalLink", + "value": "poXkQfguuA0U", + "isInheritable": false, + "position": 30 + }, + { + "type": "relation", + "name": "internalLink", + "value": "6f9hih2hXXZk", + "isInheritable": false, + "position": 40 + }, + { + "type": "relation", + "name": "internalLink", + "value": "GPERMystNGTB", + "isInheritable": false, + "position": 50 + }, + { + "type": "relation", + "name": "internalLink", + "value": "MEtfsqa5VwNi", + "isInheritable": false, + "position": 60 + }, { "type": "label", "name": "shareAlias", @@ -17457,48 +17485,6 @@ "value": "bx bx-server", "isInheritable": false, "position": 40 - }, - { - "type": "relation", - "name": "internalLink", - "value": "yIhgI5H7A2Sm", - "isInheritable": false, - "position": 50 - }, - { - "type": "relation", - "name": "internalLink", - "value": "WOcw2SLH6tbX", - "isInheritable": false, - "position": 60 - }, - { - "type": "relation", - "name": "internalLink", - "value": "poXkQfguuA0U", - "isInheritable": false, - "position": 70 - }, - { - "type": "relation", - "name": "internalLink", - "value": "MEtfsqa5VwNi", - "isInheritable": false, - "position": 80 - }, - { - "type": "relation", - "name": "internalLink", - "value": "6f9hih2hXXZk", - "isInheritable": false, - "position": 90 - }, - { - "type": "relation", - "name": "internalLink", - "value": "GPERMystNGTB", - "isInheritable": false, - "position": 100 } ], "format": "markdown", diff --git a/docs/User Guide/User Guide.md b/docs/User Guide/User Guide.md index d02f4ecc38..ce5357b26e 100644 --- a/docs/User Guide/User Guide.md +++ b/docs/User Guide/User Guide.md @@ -15,7 +15,7 @@ Trilium is an open-source solution for note-taking and organizing a personal kno * Desktop Installation * Server Installation -* [missing note] or [missing note] +* Frontend API or [missing note] * [ETAPI reference](User%20Guide/Advanced%20Usage/ETAPI%20\(REST%20API\)/API%20Reference.dat) ## External links diff --git a/docs/User Guide/User Guide/Collections/Geo Map.md b/docs/User Guide/User Guide/Collections/Geo Map.md index f79e99ebf7..91d583b193 100644 --- a/docs/User Guide/User Guide/Collections/Geo Map.md +++ b/docs/User Guide/User Guide/Collections/Geo Map.md @@ -1,6 +1,6 @@ # Geo Map > [!IMPORTANT] -> AttributesPromoted AttributesAttributesStarting with Trilium v0.97.0, the geo map has been converted from a standalone [note type](../Note%20Types.md) to a type of view for the Note List.  +> Starting with Trilium v0.97.0, the geo map has been converted from a standalone [note type](../Note%20Types.md) to a type of view for the Note List
      @@ -26,8 +26,8 @@ The position on the map and the zoom are saved inside the map note and restored | | | | | --- | --- | --- | -| 1 | To create a marker, first navigate to the desired point on the map. Then press the ![](10_Geo%20Map_image.png) button in the [Floating buttons](../Basic%20Concepts%20and%20Features/UI%20Elements/Floating%20buttons.md) (top-right) area.    

      If the button is not visible, make sure the button section is visible by pressing the chevron button (![](17_Geo%20Map_image.png)) in the top-right of the map. | | -| 2 | | Once pressed, the map will enter in the insert mode, as illustrated by the notification.       

      Simply click the point on the map where to place the marker, or the Escape key to cancel. | +| 1 | To create a marker, first navigate to the desired point on the map. Then press the ![](10_Geo%20Map_image.png) button in the [Floating buttons](../Basic%20Concepts%20and%20Features/UI%20Elements/Floating%20buttons.md) (top-right) area.     

      If the button is not visible, make sure the button section is visible by pressing the chevron button (![](17_Geo%20Map_image.png)) in the top-right of the map. | | +| 2 | | Once pressed, the map will enter in the insert mode, as illustrated by the notification.        

      Simply click the point on the map where to place the marker, or the Escape key to cancel. | | 3 | | Enter the name of the marker/note to be created. | | 4 | | Once confirmed, the marker will show up on the map and it will also be displayed as a child note of the map. | @@ -109,7 +109,7 @@ The value of the attribute is made up of the latitude and longitude separated by | | | | | --- | --- | --- | -| 1 |
      | Go to Google Maps on the web and look for a desired location, right click on it and a context menu will show up.       

      Simply click on the first item displaying the coordinates and they will be copied to clipboard.       

      Then paste the value inside the text box into the `#geolocation` attribute of a child note of the map (don't forget to surround the value with a `"` character). | +| 1 |
      | Go to Google Maps on the web and look for a desired location, right click on it and a context menu will show up.        

      Simply click on the first item displaying the coordinates and they will be copied to clipboard.        

      Then paste the value inside the text box into the `#geolocation` attribute of a child note of the map (don't forget to surround the value with a `"` character). | | 2 |
      | In Trilium, create a child note under the map. | | 3 |
      | And then go to Owned Attributes and type `#geolocation="`, then paste from the clipboard as-is and then add the ending `"` character. Press Enter to confirm and the map should now be updated to contain the new note. | @@ -120,7 +120,7 @@ Similarly to the Google Maps approach: | | | | | --- | --- | --- | | 1 | | Go to any location on openstreetmap.org and right click to bring up the context menu. Select the “Show address” item. | -| 2 | | The address will be visible in the top-left of the screen, in the place of the search bar.       

      Select the coordinates and copy them into the clipboard. | +| 2 | | The address will be visible in the top-left of the screen, in the place of the search bar.        

      Select the coordinates and copy them into the clipboard. | | 3 | | Simply paste the value inside the text box into the `#geolocation` attribute of a child note of the map and then it should be displayed on the map. | ## Adding GPS tracks (.gpx) @@ -131,7 +131,7 @@ Trilium has basic support for displaying GPS tracks on the geo map. | --- | --- | --- | | 1 |
      | To add a track, simply drag & drop a .gpx file inside the geo map in the note tree. | | 2 |
      | In order for the file to be recognized as a GPS track, it needs to show up as `application/gpx+xml` in the _File type_ field. | -| 3 |
      | When going back to the map, the track should now be visible.       

      The start and end points of the track are indicated by the two blue markers. | +| 3 |
      | When going back to the map, the track should now be visible.        

      The start and end points of the track are indicated by the two blue markers. | > [!NOTE] > The starting point of the track will be displayed as a marker, with the name of the note underneath. The start marker will also respect the icon and the `color` of the note. The end marker is displayed with a distinct icon. @@ -152,7 +152,7 @@ To enable read-only mode simply press the _Lock_ icon from the Ribbon or manually via the `#map:style` attribute. +The styling of the map can be adjusted in the _Collection Properties_ (above the map, by pressing on the Gear icon) or manually via the `#map:style` attribute. The geo map comes with two different types of styles: @@ -166,12 +166,23 @@ The geo map comes with two different types of styles: * These come both in a light and a dark version. * The vector styles come from [VersaTiles](https://versatiles.org/), a free and open-source project providing map tiles based on OpenStreetMap. +### Custom map style / tiles + +Starting with v0.102.0 it is possible to use custom tile sets, but only in raster format. + +To do so, manually set the `#map:style` [label](../Advanced%20Usage/Attributes/Labels.md) to the URL of the tile set. For example, to use Esri.NatGeoWorldMap, set the value to [`https://server.arcgisonline.com/ArcGIS/rest/services/NatGeo_World_Map/MapServer/tile/{z}/{y}/{x}`.](https://server.arcgisonline.com/ArcGIS/rest/services/NatGeo_World_Map/MapServer/tile/{z}/{y}/{x}.) + > [!NOTE] -> Currently it is not possible to use a custom map style. +> For a list of tile sets, see the [Leaflet Providers preview](https://leaflet-extras.github.io/leaflet-providers/preview/) page. Select a desired tile set and just copy the URL from the _Plain JavaScript_ example. -### Scale +Custom vector map support is planned, but not yet implemented. -Activating this option via the Ribbon or manually via `#map:scale` will display an indicator in the bottom-left of the scale of the map. +### Other options + +The following options can be configured either via the Collection properties pane above the map, by clicking on the settings (Gear icon). Alternatively, each of these options also have a corresponding [label](../Advanced%20Usage/Attributes/Labels.md) that can be set manually. + +* Scale, which illustrates the scale of the map in kilometers and miles in the bottom-left of the map. +* The name of the markers is displayed by default underneath the pin on the map. Since v0.102.0, it is possible to hide these labels which increases the performance and decreases clutter when there are many markers on the map. ## Troubleshooting diff --git a/packages/commons/src/lib/attribute_names.ts b/packages/commons/src/lib/attribute_names.ts index 10d7538875..ce58c131bb 100644 --- a/packages/commons/src/lib/attribute_names.ts +++ b/packages/commons/src/lib/attribute_names.ts @@ -53,6 +53,7 @@ type Labels = { "calendar:initialDate": string; "map:style": string; "map:scale": boolean; + "map:hideLabels": boolean; "board:groupBy": string; maxNestingDepth: number; includeArchived: boolean;