Better suggestion accept on mobile and word wrap offset fix
This commit is contained in:
@@ -146,25 +146,6 @@
|
||||
autofocus
|
||||
placeholder="Start typing here..."
|
||||
></textarea>
|
||||
<button
|
||||
id="accept-suggestion-btn"
|
||||
class="btn-floating"
|
||||
title="Accept Suggestion"
|
||||
>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="24"
|
||||
height="24"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
>
|
||||
<polyline points="20 6 9 17 4 12"></polyline>
|
||||
</svg>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
|
||||
30
ui/script.js
30
ui/script.js
@@ -14,7 +14,6 @@ document.addEventListener("DOMContentLoaded", () => {
|
||||
const generateBtn = document.getElementById("generate-more-btn");
|
||||
const sidebarToggle = document.getElementById("sidebar-toggle");
|
||||
const sidebar = document.getElementById("sidebar");
|
||||
const acceptSuggestionBtn = document.getElementById("accept-suggestion-btn");
|
||||
|
||||
let currentSuggestion = "";
|
||||
let isFetching = false;
|
||||
@@ -101,15 +100,29 @@ document.addEventListener("DOMContentLoaded", () => {
|
||||
};
|
||||
|
||||
const updateSuggestion = () => {
|
||||
suggestionOverlay.innerHTML = "";
|
||||
|
||||
const editorText = editor.value;
|
||||
const space = editorText.length > 0 && !/\s$/.test(editorText) ? " " : "";
|
||||
suggestionOverlay.textContent = editorText + space + currentSuggestion;
|
||||
|
||||
// Show/hide accept button
|
||||
// Create invisible text span to match editor content exactly
|
||||
const textSpan = document.createElement("span");
|
||||
textSpan.textContent = editorText + space;
|
||||
textSpan.style.color = "transparent";
|
||||
suggestionOverlay.appendChild(textSpan);
|
||||
|
||||
if (currentSuggestion) {
|
||||
acceptSuggestionBtn.classList.add("visible");
|
||||
} else {
|
||||
acceptSuggestionBtn.classList.remove("visible");
|
||||
const suggestionSpan = document.createElement("span");
|
||||
suggestionSpan.textContent = currentSuggestion;
|
||||
suggestionSpan.className = "suggestion-highlight";
|
||||
|
||||
// Add Tab Icon (Better SVG for Tab Key)
|
||||
const iconSpan = document.createElement("span");
|
||||
iconSpan.style.pointerEvents = "none"; // Ensure clicks pass through to suggestionSpan
|
||||
iconSpan.innerHTML = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="tab-icon"><path d="M21 9V15"/><path d="M3 12H17"/><path d="m14 9 3 3-3 3"/></svg>`;
|
||||
suggestionSpan.appendChild(iconSpan);
|
||||
|
||||
suggestionOverlay.appendChild(suggestionSpan);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -145,8 +158,9 @@ document.addEventListener("DOMContentLoaded", () => {
|
||||
}
|
||||
});
|
||||
|
||||
acceptSuggestionBtn.addEventListener("click", () => {
|
||||
if (currentSuggestion) {
|
||||
// Handle click on suggestion
|
||||
suggestionOverlay.addEventListener("click", (e) => {
|
||||
if (e.target.classList.contains("suggestion-highlight")) {
|
||||
insertText(currentSuggestion);
|
||||
fetchPrediction(editor.value);
|
||||
editor.focus();
|
||||
|
||||
91
ui/style.css
91
ui/style.css
@@ -117,44 +117,6 @@ body {
|
||||
}
|
||||
}
|
||||
|
||||
/* Floating Action Button for Suggestions */
|
||||
.btn-floating {
|
||||
position: absolute;
|
||||
bottom: 1.5rem;
|
||||
right: 1.5rem;
|
||||
width: 3.5rem;
|
||||
height: 3.5rem;
|
||||
border-radius: 50%;
|
||||
background-color: var(--primary);
|
||||
color: var(--primary-foreground);
|
||||
border: none;
|
||||
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.3);
|
||||
cursor: pointer;
|
||||
display: none; /* Hidden by default, shown when suggestion exists */
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
z-index: 10;
|
||||
transition:
|
||||
transform 0.2s,
|
||||
opacity 0.2s;
|
||||
}
|
||||
|
||||
.btn-floating:active {
|
||||
transform: scale(0.95);
|
||||
}
|
||||
|
||||
@media (max-width: 768px) {
|
||||
.btn-floating.visible {
|
||||
display: flex;
|
||||
}
|
||||
}
|
||||
|
||||
@media (min-width: 769px) {
|
||||
.btn-floating.visible {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.sidebar-header {
|
||||
margin-bottom: 2.5rem;
|
||||
}
|
||||
@@ -376,7 +338,7 @@ label {
|
||||
#suggestion-overlay {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
padding: 2rem;
|
||||
padding: 2rem 2rem 10rem 2rem;
|
||||
font-family: "SF Mono", "Fira Code", monospace;
|
||||
font-size: 1.1rem;
|
||||
line-height: 1.8;
|
||||
@@ -391,7 +353,7 @@ label {
|
||||
@media (max-width: 768px) {
|
||||
#editor,
|
||||
#suggestion-overlay {
|
||||
padding: 1rem;
|
||||
padding: 1rem 1rem 10rem 1rem;
|
||||
font-size: 1rem;
|
||||
}
|
||||
}
|
||||
@@ -402,16 +364,59 @@ label {
|
||||
color: var(--foreground);
|
||||
outline: none;
|
||||
resize: none;
|
||||
overflow-y: auto;
|
||||
overflow-y: scroll;
|
||||
}
|
||||
|
||||
#editor::-webkit-scrollbar {
|
||||
width: 16px;
|
||||
}
|
||||
|
||||
#editor::-webkit-scrollbar-thumb {
|
||||
background-color: var(--muted);
|
||||
border: 4px solid var(--card);
|
||||
border-radius: 8px;
|
||||
}
|
||||
|
||||
#editor::-webkit-scrollbar-track {
|
||||
background-color: transparent;
|
||||
}
|
||||
|
||||
#suggestion-overlay {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
color: var(--muted-foreground);
|
||||
z-index: 3;
|
||||
color: transparent;
|
||||
pointer-events: none;
|
||||
opacity: 0.5;
|
||||
overflow: hidden;
|
||||
overflow-y: scroll;
|
||||
}
|
||||
|
||||
#suggestion-overlay::-webkit-scrollbar {
|
||||
width: 16px; /* Width must match standard scrollbar width to align text */
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
#suggestion-overlay::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.suggestion-highlight {
|
||||
color: var(--muted-foreground);
|
||||
cursor: pointer;
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
.tab-icon {
|
||||
display: inline-block;
|
||||
width: 1.8em;
|
||||
height: 1.2em;
|
||||
vertical-align: middle;
|
||||
margin-left: 0.5em;
|
||||
opacity: 0.8;
|
||||
border: 1px solid var(--muted-foreground);
|
||||
border-radius: 4px;
|
||||
padding: 2px;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user