Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

main -> latest #222

Merged
merged 7 commits into from
Nov 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ jobs:

strategy:
matrix:
ruby: ['3.2', '3.1']
ruby: ['3.3', '3.2']
node-version: [20.x]

services:
Expand Down
14 changes: 14 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,19 @@
# Changelog

## 0.13.2

### Patch Changes

- [#220](https://github.com/KonnorRogers/rhino-editor/pull/220) [`5fcb5ac`](https://github.com/KonnorRogers/rhino-editor/commit/5fcb5aca2f8e6b99eb419badfd5bfabe017a8bab) Thanks [@KonnorRogers](https://github.com/KonnorRogers)! - Fixed a CSS bug with inline code

- [#220](https://github.com/KonnorRogers/rhino-editor/pull/220) [`5fcb5ac`](https://github.com/KonnorRogers/rhino-editor/commit/5fcb5aca2f8e6b99eb419badfd5bfabe017a8bab) Thanks [@KonnorRogers](https://github.com/KonnorRogers)! - Fixed link dialogs not showing when the selection is not in view

## 0.13.1

### Patch Changes

- [`61241c0`](https://github.com/KonnorRogers/rhino-editor/commit/61241c0d9706b1ccfe6857853730876e047f08b0) Thanks [@KonnorRogers](https://github.com/KonnorRogers)! - Fix some bugs around prosemirror-view versioning

## 0.13.0

### Minor Changes
Expand Down
10 changes: 5 additions & 5 deletions docs/src/rhino-editor/exports/styles/trix.css

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "rhino-editor",
"version": "0.13.0",
"version": "0.13.2",
"description": "A custom element wrapped rich text editor",
"type": "module",
"main": "exports/index.js",
Expand Down Expand Up @@ -82,6 +82,7 @@
"prosemirror-codemark": "^0.4.2",
"prosemirror-utils": "^1.2.2",
"role-components": "^3.1.0",
"prosemirror-view": "^1.0.0",
"tslib": "^2.8.0"
},
"repository": "[email protected]:KonnorRogers/rhino-editor.git",
Expand Down
3 changes: 3 additions & 0 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

135 changes: 74 additions & 61 deletions src/exports/elements/tip-tap-editor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,59 @@ import { stringMap } from "../../internal/string-map.js";
import { isExactNodeActive } from "../../internal/is-exact-node-active.js";
import RoleAnchoredRegion from "role-components/exports/components/anchored-region/anchored-region.js";
import { findNodeViewAnchor } from "../extensions/bubble-menu.js";
import { isNodeSelection, posToDOMRect } from "@tiptap/core";
import { Editor, isNodeSelection, posToDOMRect } from "@tiptap/core";

function findElement(editor: Editor) {
if (!editor) {
return null;
}

const state = editor.state;
const { selection } = state;
const view = editor.view;

if (view.composing) {
return null;
}

// support for CellSelections
const { ranges } = selection;
const from = Math.min(...ranges.map((range) => range.$from.pos));
const to = Math.max(...ranges.map((range) => range.$to.pos));

let clientRect: null | (() => DOMRect) = null;

if (isNodeSelection(state.selection)) {
const node =
findNodeViewAnchor?.({
editor,
view,
from,
}) || (view.nodeDOM(from) as HTMLElement);

if (node) {
node.scrollIntoView({ block: "nearest" });
clientRect = () => {
const rect = node.getBoundingClientRect();
return rect;
};
}
} else {
const toNode = view.domAtPos(to).node;
if (toNode instanceof HTMLElement) {
// Scroll it into view so we can see the bubble menu
toNode.scrollIntoView({ block: "nearest" });
}

clientRect = () => {
const rect = posToDOMRect(view, from, to);
rect.x = rect.x - rect.width / 2;
return rect;
};
}

return clientRect;
}

/**
* This is the meat and potatoes. This is the <rhino-editor> element you'll
Expand Down Expand Up @@ -264,9 +316,11 @@ export class TipTapEditor extends TipTapEditorBase {
this.__invalidLink__ = false;
this.linkDialogExpanded = true;
setTimeout(() => {
if (inputElement != null) {
inputElement.focus();
}
requestAnimationFrame(() => {
if (inputElement != null) {
inputElement.focus();
}
});
});
}

Expand Down Expand Up @@ -1367,55 +1421,9 @@ export class TipTapEditor extends TipTapEditorBase {
};

renderLinkDialogAnchoredRegion() {
const findClientRect = () => {
const editor = this.editor;
if (!editor) {
return null;
}

const state = editor.state;
const { selection } = state;
const view = editor.view;

if (view.composing) {
return null;
}

// support for CellSelections
const { ranges } = selection;
const from = Math.min(...ranges.map((range) => range.$from.pos));
const to = Math.max(...ranges.map((range) => range.$to.pos));

let clientRect: null | (() => DOMRect) = null;

if (isNodeSelection(state.selection)) {
const node =
findNodeViewAnchor({
view,
from,
editor,
}) || (view.nodeDOM(from) as HTMLElement);

if (node) {
const domRect = node.getBoundingClientRect();
clientRect = () =>
Object.assign(domRect, {
// Center it.
x: domRect.x - domRect.width / 2,
});
}
} else {
const domRect = posToDOMRect(view, from, to);
clientRect = () =>
Object.assign(domRect, {
// Center it.
x: domRect.x - domRect.width / 2,
});
}

return clientRect;
};
const clientRect = this.linkDialogExpanded ? findClientRect() : null;
const clientRect = this.linkDialogExpanded
? findElement(this.editor as Editor)
: null;

return html`
<role-anchored-region
Expand All @@ -1434,6 +1442,7 @@ export class TipTapEditor extends TipTapEditorBase {
distance="4"
.active=${this.linkDialogExpanded}
.shiftBoundary=${this.querySelector(".ProseMirror") || this}
.flipBoundary=${this.querySelector(".ProseMirror") || this}
.anchor=${typeof clientRect === "function"
? { getBoundingClientRect: clientRect }
: null}
Expand Down Expand Up @@ -1550,20 +1559,24 @@ export class TipTapEditor extends TipTapEditorBase {
if (e.defaultPrevented) {
return;
}

const self = e.currentTarget as RoleAnchoredRegion;
self.anchor = { getBoundingClientRect: e.clientRect };
self.shiftBoundary = this.querySelector(".ProseMirror") || this;
self.active = true;
console.log("show");

const anchoredRegion = e.currentTarget as RoleAnchoredRegion;
anchoredRegion.anchor = { getBoundingClientRect: e.clientRect };
anchoredRegion.shiftBoundary =
this.querySelector(".ProseMirror") || this;
anchoredRegion.flipBoundary =
this.querySelector(".ProseMirror") || this;
anchoredRegion.active = true;
}}
@rhino-bubble-menu-hide=${(e: Event) => {
if (e.defaultPrevented) {
return;
}

const self = e.currentTarget as RoleAnchoredRegion;
self.anchor = null;
self.active = false;
const anchoredRegion = e.currentTarget as RoleAnchoredRegion;
anchoredRegion.anchor = null;
anchoredRegion.active = false;
}}
anchored-popover-type="manual"
distance="4"
Expand Down
2 changes: 1 addition & 1 deletion src/exports/extensions/attachment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -683,7 +683,7 @@ export const Attachment = Node.create<AttachmentOptions>({
}

let mouseIsDown = false;
let mouseTimeout: number | null = null;
let mouseTimeout: ReturnType<typeof setTimeout> | null = null;

// This is a very simple drag handler. This allows us to drag non-previewable nodes.
// https://discuss.prosemirror.net/t/dragndrop-a-drag-handle-element/4563
Expand Down
1 change: 0 additions & 1 deletion src/exports/extensions/bubble-menu.ts
Original file line number Diff line number Diff line change
Expand Up @@ -294,7 +294,6 @@ export class BubbleMenuView {
if (node) {
clientRect = () => {
const rect = node.getBoundingClientRect();
rect.x = rect.x - rect.width / 2;
return rect;
};
}
Expand Down
2 changes: 1 addition & 1 deletion src/exports/styles/trix-core.css
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,7 @@
}

/** This is for `` inline code code elements. */
.trix-content :where(:not(pre code)) code {
.trix-content :not(pre) code {
background-color: #eee;
border-radius: 2px;
padding: 2px;
Expand Down
2 changes: 1 addition & 1 deletion src/exports/styles/trix.css
Original file line number Diff line number Diff line change
Expand Up @@ -204,7 +204,7 @@
}

/** This is for `` inline code code elements. */
.trix-content :where(:not(pre code)) code {
.trix-content :not(pre) code {
background-color: #eee;
border-radius: 2px;
padding: 2px;
Expand Down
2 changes: 1 addition & 1 deletion tests/rails/app/controllers/posts_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ def create

respond_to do |format|
if @post.save
format.html { redirect_to post_url(@post) + "#my-post", notice: "Post was successfully created." }
format.html { redirect_to post_url(@post), notice: "Post was successfully created." }
format.json { render :show, status: :created, location: @post }
else
format.html { render :new, status: :unprocessable_entity }
Expand Down
28 changes: 17 additions & 11 deletions tests/rails/app/frontend/controllers/embed_controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -33,15 +33,21 @@ export default class EmbedController extends Controller {
}

async embed() {
const attrs = await this.fetch()
console.log(attrs)
let trixAttachment = new Trix.Attachment({ ...attrs })
const trix = document.querySelector("trix-editor")
trix.editor.insertAttachment(trixAttachment)
trix.focus()

let attachment = new AttachmentManager({...attrs})
const tiptap = document.querySelector("rhino-editor")
tiptap.editor.chain().focus().setAttachment(attachment).run();
}
const isRhino = this.element.closest("rhino-editor")
const isTrix = this.element.parentElement.querySelector("trix-editor")
const attrs = await this.fetch()

if (isTrix) {
let trixAttachment = new Trix.Attachment({ ...attrs })
const trix = document.querySelector("trix-editor")
trix.editor.insertAttachment(trixAttachment)
trix.focus()
}

if (isRhino) {
let attachment = new AttachmentManager({...attrs})
const tiptap = document.querySelector("rhino-editor")
tiptap.editor.chain().focus().setAttachment(attachment).run();
}
}
}
41 changes: 19 additions & 22 deletions tests/rails/app/frontend/controllers/tip_tap_mirror_controller.js
Original file line number Diff line number Diff line change
@@ -1,28 +1,25 @@
import { Controller } from "@hotwired/stimulus"

export default class TipTapMirrorController extends Controller {
get trixInput () {
return document.querySelector(`#${document.querySelector("trix-editor").getAttribute("input")}`)
}
connect () {
const editor = this.element
setTimeout(() => {
replaceWithWrapper(this.trixInput, "value", (_obj, _property, value) => {
editor.editor.commands.setContent(value)
})
}, 30)
}
}
get trixInput () {
return document.querySelector("trix-editor")
}
connect () {
this.trixInput.addEventListener("trix-change", this.handleChange)

}

disconnect () {
this.trixInput.removeEventListener("trix-change", this.handleChange)
}


function replaceWithWrapper(obj, property, callback) {
Object.defineProperty(obj, property, {
set (value) {
obj.setAttribute(property, value)
callback(obj, property, value)
},
get: function() {
return _value;
}
});

handleChange = () => {
const editor = this.element
const value = this.trixInput.value
editor.editor.commands.setContent(value)
}
}


Loading
Loading