Merge branch 'master' into develop
# Conflicts: # package.json
This commit is contained in:
144
README.md
144
README.md
@@ -13,6 +13,19 @@ Under the hood, it uses the excellent [MiniSearch](https://github.com/lucaong/mi
|
||||
|
||||

|
||||
|
||||
|
||||
## Documentation
|
||||
|
||||
https://publish.obsidian.md/omnisearch/Index
|
||||
|
||||
## Installation
|
||||
|
||||
- Omnisearch is available on [the official Community Plugins repository](https://obsidian.md/plugins?search=Omnisearch).
|
||||
- Beta releases can be installed through [BRAT](https://github.com/TfTHacker/obsidian42-brat). **Be advised that those
|
||||
versions can be buggy and break things.**
|
||||
|
||||
You can check the [CHANGELOG](./CHANGELOG.md) for more information on the different versions.
|
||||
|
||||
## Features
|
||||
|
||||
> Omnisearch's first goal is to _locate_ files instantly. You can see it as a _Quick Switcher_ on steroids.
|
||||
@@ -37,137 +50,6 @@ Under the hood, it uses the excellent [MiniSearch](https://github.com/lucaong/mi
|
||||
on [this additional plugin](https://github.com/aidenlx/cm-chs-patch). Please read its documentation for more
|
||||
information.
|
||||
|
||||
## Installation
|
||||
|
||||
- Omnisearch is available on [the official Community Plugins repository](https://obsidian.md/plugins?search=Omnisearch).
|
||||
- Beta releases can be installed through [BRAT](https://github.com/TfTHacker/obsidian42-brat). **Be advised that those
|
||||
versions can be buggy and break things.**
|
||||
|
||||
You can check the [CHANGELOG](./CHANGELOG.md) for more information on the different versions.
|
||||
|
||||
## Usage
|
||||
|
||||
Omnisearch can be used within 2 different contexts:
|
||||
|
||||
### Vault Search
|
||||
|
||||
Omnisearch's core feature, accessible with the Command Palette "**_Omnisearch: Vault search_**". This modal searches
|
||||
through your vault and returns the most relevant notes. That's all you need to _find_ a note.
|
||||
|
||||
If you want to list all the search matches of a single note, you can do so by using `tab` to open the In-File Search.
|
||||
|
||||
### In-File Search
|
||||
|
||||
Also accessible through the Command Palette "**_Omnisearch: In-file search_**". This modal searches through the active
|
||||
note's content and lists the matching results. Just press enter to automatically scroll to the right place.
|
||||
|
||||
## URL Scheme & Public API
|
||||
|
||||
You can open Omnisearch with the following scheme: `obsidian://omnisearch?query=foo bar`
|
||||
|
||||
----
|
||||
|
||||
For plugin developers and Dataview users, Omnisearch is also accessible through the global
|
||||
object `omnisearch` (`window.omnisearch`)
|
||||
|
||||
> This API is an experimental feature, the `ResultNote` interface may change in the future. The `search()` function
|
||||
> returns at most 50 results.
|
||||
|
||||
```ts
|
||||
// API:
|
||||
type OmnisearchApi = {
|
||||
// Returns a promise that will contain the same results as the Vault modal
|
||||
search: (query: string) => Promise<ResultNoteApi[]>,
|
||||
// Refreshes the index
|
||||
refreshIndex: () => Promise<void>
|
||||
// Register a callback that will be called when the indexing is done
|
||||
registerOnIndexed: (callback: () => void) => void,
|
||||
// Unregister a callback that was previously registered
|
||||
unregisterOnIndexed: (callback: () => void) => void,
|
||||
}
|
||||
|
||||
type ResultNoteApi = {
|
||||
score: number
|
||||
path: string
|
||||
basename: string
|
||||
foundWords: string[]
|
||||
matches: SearchMatchApi[]
|
||||
excerpt: string
|
||||
}
|
||||
|
||||
type SearchMatchApi = {
|
||||
match: string
|
||||
offset: number
|
||||
}
|
||||
```
|
||||
|
||||
### Dataview Integration
|
||||
|
||||
You can use the Omnisearch API directly within the [Dataview](https://blacksmithgu.github.io/obsidian-dataview/) plugin.
|
||||
|
||||
~~~js
|
||||
```dataviewjs
|
||||
const results = await omnisearch.search('your query')
|
||||
const arr = dv.array(results).sort(r => r.score, 'desc')
|
||||
dv.table(['File', 'Score'], arr.map(o => [dv.fileLink(o.path), Math.round(o.score)]))
|
||||
```
|
||||
~~~
|
||||
|
||||
## CSS Customization
|
||||
|
||||
There are several CSS classes you can use to customize the appearance of Omnisearch.
|
||||
|
||||
```css
|
||||
.omnisearch-modal
|
||||
.omnisearch-result
|
||||
.omnisearch-result__title
|
||||
.omnisearch-result__counter
|
||||
.omnisearch-result__body
|
||||
.omnisearch-highlight
|
||||
.omnisearch-input-container
|
||||
.omnisearch-input-field
|
||||
```
|
||||
|
||||
See [styles.css](./assets/styles.css) for more information.
|
||||
|
||||
## Issues & Solutions
|
||||
|
||||
**Omnisearch makes Obsidian sluggish/freeze at startup.**
|
||||
|
||||
- While Omnisearch does its best to work smoothly in the background, bigger vaults and files can make Obsidian stutter
|
||||
during indexing.
|
||||
- If you have several thousands of files, Obsidian may freeze a few seconds at startup while the Omnisearch cache is
|
||||
loaded in memory.
|
||||
|
||||
**Omnisearch seems to make Obsidian slower.**
|
||||
|
||||
- Once Obsidian has indexed your files at startup, it doesn't do anything while its modal is closed. Your changes are
|
||||
not indexed until you open the modal again. If you experience slowdowns while using Obsidian, it's unlikely that
|
||||
Omnisearch is responsible.
|
||||
- However, Text Extractor can make Obsidian slower while indexing PDFs and images for the first time. If you don't need
|
||||
those features, you can disable them in the plugin settings.
|
||||
|
||||
**Omnisearch is slow to index my PDFs and images**
|
||||
|
||||
- The first time Text Extractor reads those files, it can take a long time to extract their text. The results are then
|
||||
cached for the text startup.
|
||||
|
||||
**Omnisearch gives inconsistent/invalid results, there are errors in the developer console**
|
||||
|
||||
- Restart Obsidian to force a reindex of Omnisearch.
|
||||
- The cache could be corrupted; you can clear it at the bottom of the settings page, then restart Obsidian.
|
||||
|
||||
**A query should return a result that does not appear.**
|
||||
|
||||
- If applicable, make sure that "*Ignore diacritics*" is enabled.
|
||||
- If you have modified them, reset weightings to their original values.
|
||||
- Rewrite your query and avoid numbers and common words.
|
||||
|
||||
**I'm still having an issue**
|
||||
|
||||
You can write your issue [here](https://github.com/scambier/obsidian-omnisearch/issues) with as much details as
|
||||
possible.
|
||||
|
||||
## LICENSE
|
||||
|
||||
Omnisearch is licensed under [GPL-3](https://tldrlegal.com/license/gnu-general-public-license-v3-(gpl-3)).
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"id": "omnisearch",
|
||||
"name": "Omnisearch",
|
||||
"version": "1.12.2",
|
||||
"version": "1.13.0-beta.2",
|
||||
"minAppVersion": "1.0.0",
|
||||
"description": "A search engine that just works",
|
||||
"author": "Simon Cambier",
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"id": "omnisearch",
|
||||
"name": "Omnisearch",
|
||||
"version": "1.12.2",
|
||||
"version": "1.12.3",
|
||||
"minAppVersion": "1.0.0",
|
||||
"description": "A search engine that just works",
|
||||
"author": "Simon Cambier",
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
type ResultNote,
|
||||
type SearchMatch,
|
||||
} from 'src/globals'
|
||||
import { loopIndex } from 'src/tools/utils'
|
||||
import { getCtrlKeyLabel, loopIndex } from 'src/tools/utils'
|
||||
import { onDestroy, onMount, tick } from 'svelte'
|
||||
import { MarkdownView } from 'obsidian'
|
||||
import ModalContainer from './ModalContainer.svelte'
|
||||
@@ -36,6 +36,7 @@
|
||||
eventBus.enable('infile')
|
||||
|
||||
eventBus.on('infile', 'enter', openSelection)
|
||||
eventBus.on('infile', 'open-in-new-pane', openSelectionInNewTab)
|
||||
eventBus.on('infile', 'arrow-up', () => moveIndex(-1))
|
||||
eventBus.on('infile', 'arrow-down', () => moveIndex(1))
|
||||
eventBus.on('infile', 'tab', switchToVaultModal)
|
||||
@@ -108,15 +109,17 @@
|
||||
elem?.scrollIntoView({ behavior: 'auto', block: 'nearest' })
|
||||
}
|
||||
|
||||
async function openSelection(
|
||||
evt?: MouseEvent | KeyboardEvent
|
||||
): Promise<void> {
|
||||
async function openSelectionInNewTab(): Promise<void> {
|
||||
return openSelection(true)
|
||||
}
|
||||
|
||||
async function openSelection(newTab = false): Promise<void> {
|
||||
if (note) {
|
||||
modal.close()
|
||||
if (parent) parent.close()
|
||||
|
||||
// Open (or switch focus to) the note
|
||||
await openNote(note, evt?.ctrlKey)
|
||||
await openNote(note, newTab)
|
||||
|
||||
// Move cursor to the match
|
||||
const view = app.workspace.getActiveViewOfType(MarkdownView)
|
||||
@@ -157,7 +160,10 @@
|
||||
index="{i}"
|
||||
selected="{i === selectedIndex}"
|
||||
on:mousemove="{_e => (selectedIndex = i)}"
|
||||
on:click="{openSelection}" />
|
||||
on:click="{evt => openSelection(evt.ctrlKey)}"
|
||||
on:auxclick="{evt => {
|
||||
if (evt.button == 1) openSelection(true)
|
||||
}}" />
|
||||
{/each}
|
||||
{:else}
|
||||
<div style="text-align: center;">
|
||||
@@ -174,7 +180,7 @@
|
||||
<span class="prompt-instruction-command">↵</span><span>to open</span>
|
||||
</div>
|
||||
<div class="prompt-instruction">
|
||||
<span class="prompt-instruction-command">↹</span>
|
||||
<span class="prompt-instruction-command">tab</span>
|
||||
<span>to switch to Vault Search</span>
|
||||
</div>
|
||||
<div class="prompt-instruction">
|
||||
@@ -185,4 +191,9 @@
|
||||
<span>to close</span>
|
||||
{/if}
|
||||
</div>
|
||||
|
||||
<div class="prompt-instruction">
|
||||
<span class="prompt-instruction-command">{getCtrlKeyLabel()} ↵</span>
|
||||
<span>to open in a new pane</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -266,7 +266,10 @@
|
||||
selected="{i === selectedIndex}"
|
||||
note="{result}"
|
||||
on:mousemove="{_ => (selectedIndex = i)}"
|
||||
on:click="{onClick}" />
|
||||
on:click="{onClick}"
|
||||
on:auxclick="{evt => {
|
||||
if (evt.button == 1) openNoteInNewPane()
|
||||
}}" />
|
||||
{/each}
|
||||
<div style="text-align: center;">
|
||||
{#if !resultNotes.length && searchQuery && !searching}
|
||||
@@ -298,12 +301,10 @@
|
||||
<span class="prompt-instruction-command">↵</span><span>to open</span>
|
||||
</div>
|
||||
<div class="prompt-instruction">
|
||||
<span class="prompt-instruction-command">↹</span>
|
||||
<span class="prompt-instruction-command">tab</span>
|
||||
<span>to switch to In-File Search</span>
|
||||
</div>
|
||||
|
||||
<br />
|
||||
|
||||
<div class="prompt-instruction">
|
||||
<span class="prompt-instruction-command">{getCtrlKeyLabel()} ↵</span>
|
||||
<span>to open in a new pane</span>
|
||||
@@ -317,8 +318,6 @@
|
||||
<span>to create in a new pane</span>
|
||||
</div>
|
||||
|
||||
<br />
|
||||
|
||||
<div class="prompt-instruction">
|
||||
<span class="prompt-instruction-command">alt ↵</span>
|
||||
<span>to insert a link</span>
|
||||
|
||||
@@ -20,7 +20,8 @@
|
||||
id="{index.toString()}"
|
||||
selected="{selected}"
|
||||
on:mousemove
|
||||
on:click>
|
||||
on:click
|
||||
on:auxclick>
|
||||
<div class="omnisearch-result__body">
|
||||
{@html cleanedContent.replace(reg, highlighterGroups)}
|
||||
</div>
|
||||
|
||||
@@ -63,6 +63,7 @@
|
||||
glyph="{glyph}"
|
||||
id="{note.path}"
|
||||
on:click
|
||||
on:auxclick
|
||||
on:mousemove
|
||||
selected="{selected}">
|
||||
<div>
|
||||
|
||||
@@ -99,5 +99,8 @@
|
||||
"1.12.0": "1.0.0",
|
||||
"1.12.1-beta.1": "1.0.0",
|
||||
"1.12.1": "1.0.0",
|
||||
"1.12.2": "1.0.0"
|
||||
"1.12.2": "1.0.0",
|
||||
"1.12.3": "1.0.0",
|
||||
"1.13.0-beta.1": "1.0.0",
|
||||
"1.13.0-beta.2": "1.0.0"
|
||||
}
|
||||
Reference in New Issue
Block a user