Merge branch 'main' of gitlab.alibaba-inc.com:aidc-innovation/ComfyUI-Copilot into main
This commit is contained in:
Vendored
+6
@@ -0,0 +1,6 @@
|
||||
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["copilot_web/workflowChat-nlzNpdzN.js","copilot_web/input.js","copilot_web/assets/input-BiPrIQoG.css"].map(path => {
|
||||
const apiBase = window.comfyAPI?.api?.api?.api_base;
|
||||
const prefix = apiBase ? `${apiBase.substring(1)}/` : '';
|
||||
return `${prefix}${path}`;
|
||||
}))))=>i.map(i=>d[i]);
|
||||
import{r as t,j as s,R as w,_}from"./input.js";const D=9999999,f={EXPLAIN_NODE:"copilot:explain-node"},b=w.lazy(()=>_(()=>import("./workflowChat-nlzNpdzN.js"),__vite__mapDeps([0,1,2])));function N(){const g=t.useRef(null),[E,r]=t.useState(!1),[i,l]=t.useState(),[o,u]=t.useState(!1),[a,m]=t.useState({x:0,y:0}),[h,c]=t.useState(!1);t.useEffect(()=>{const e=()=>{console.log("Explain node event received"),r(!0),c(!0)};return window.addEventListener(f.EXPLAIN_NODE,e),()=>window.removeEventListener(f.EXPLAIN_NODE,e)},[]),t.useEffect(()=>{l({x:window.innerWidth-160,y:20})},[]);const x=e=>{e.preventDefault(),u(!0);const n=e.currentTarget.getBoundingClientRect();m({x:e.clientX-n.left,y:e.clientY-n.top})};return t.useEffect(()=>{const e=d=>{if(o){const p=Math.min(Math.max(0,d.clientX-a.x),window.innerWidth-100),v=Math.min(Math.max(0,d.clientY-a.y),window.innerHeight-40);l({x:p,y:v})}},n=()=>{u(!1)};return o&&(document.addEventListener("mousemove",e),document.addEventListener("mouseup",n)),()=>{document.removeEventListener("mousemove",e),document.removeEventListener("mouseup",n)}},[o,a]),i?s.jsx("div",{ref:g,children:s.jsxs("div",{className:"fixed",style:{zIndex:D,left:i.x,top:i.y,cursor:o?"grabbing":"grab"},children:[s.jsx("button",{onMouseDown:x,onClick:()=>{r(!0)},className:"px-4 py-2 border border-gray-300 rounded-md bg-white text-black hover:bg-green-600 transition-colors select-none",children:"copilot"}),s.jsx(b,{onClose:()=>{r(!1),c(!1)},visible:E,triggerUsage:h,onUsageTriggered:()=>c(!1)})]})}):null}export{N as default};
|
||||
Vendored
-6
@@ -1,6 +0,0 @@
|
||||
const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["copilot_web/workflowChat-2b2JOI-A.js","copilot_web/input.js","copilot_web/assets/input-BiPrIQoG.css"].map(path => {
|
||||
const apiBase = window.comfyAPI?.api?.api?.api_base;
|
||||
const prefix = apiBase ? `${apiBase.substring(1)}/` : '';
|
||||
return `${prefix}${path}`;
|
||||
}))))=>i.map(i=>d[i]);
|
||||
import{r as t,j as s,R as p,_ as v}from"./input.js";const w=9999999,E=p.lazy(()=>v(()=>import("./workflowChat-2b2JOI-A.js"),__vite__mapDeps([0,1,2])));function y(){const d=t.useRef(null),[f,a]=t.useState(!1),[r,c]=t.useState(),[o,u]=t.useState(!1),[i,m]=t.useState({x:0,y:0});t.useEffect(()=>{c({x:window.innerWidth-160,y:20})},[]);const h=e=>{e.preventDefault(),u(!0);const n=e.currentTarget.getBoundingClientRect();m({x:e.clientX-n.left,y:e.clientY-n.top})};return t.useEffect(()=>{const e=l=>{if(o){const x=Math.min(Math.max(0,l.clientX-i.x),window.innerWidth-100),g=Math.min(Math.max(0,l.clientY-i.y),window.innerHeight-40);c({x,y:g})}},n=()=>{u(!1)};return o&&(document.addEventListener("mousemove",e),document.addEventListener("mouseup",n)),()=>{document.removeEventListener("mousemove",e),document.removeEventListener("mouseup",n)}},[o,i]),r?s.jsx("div",{ref:d,children:s.jsxs("div",{className:"fixed",style:{zIndex:w,left:r.x,top:r.y,cursor:o?"grabbing":"grab"},children:[s.jsx("button",{onMouseDown:h,onClick:()=>a(!0),className:"px-4 py-2 border border-gray-300 rounded-md bg-white text-black hover:bg-green-600 transition-colors select-none",children:"copilot"}),s.jsx(E,{onClose:()=>a(!1),visible:f})]})}):null}export{y as default};
|
||||
Vendored
+1
-1
File diff suppressed because one or more lines are too long
+47
-47
File diff suppressed because one or more lines are too long
@@ -0,0 +1,31 @@
|
||||
import { app } from "../../scripts/app.js";
|
||||
import { api } from "../../scripts/api.js";
|
||||
|
||||
// 定义事件常量
|
||||
const COPILOT_EVENTS = {
|
||||
EXPLAIN_NODE: 'copilot:explain-node'
|
||||
};
|
||||
|
||||
function addExtraMenuOptions(nodeType, nodeData, app) {
|
||||
const original_getExtraMenuOptions = nodeType.prototype.getExtraMenuOptions;
|
||||
nodeType.prototype.getExtraMenuOptions = function (_, options) {
|
||||
original_getExtraMenuOptions?.apply(this, arguments);
|
||||
options.push({
|
||||
content: "Explain with Copilot",
|
||||
callback: async () => {
|
||||
const nodeTypeUniqueId = nodeType?.comfyClass;
|
||||
// 触发自定义事件
|
||||
window.dispatchEvent(new CustomEvent(COPILOT_EVENTS.EXPLAIN_NODE, {
|
||||
detail: { nodeType: nodeTypeUniqueId }
|
||||
}));
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
app.registerExtension({
|
||||
name: "ComfyUI-Copilot-Bridge",
|
||||
async beforeRegisterNodeDef(nodeType, nodeData, app) {
|
||||
addExtraMenuOptions(nodeType, nodeData, app);
|
||||
},
|
||||
})
|
||||
+25
-2
@@ -1,5 +1,6 @@
|
||||
import React, { useRef, useState, useEffect } from "react";
|
||||
import { DRAWER_Z_INDEX } from "./const";
|
||||
import { COPILOT_EVENTS } from "./constants/events";
|
||||
const WorkflowChat = React.lazy(() => import("./workflowChat/workflowChat"));
|
||||
|
||||
export default function App() {
|
||||
@@ -8,6 +9,18 @@ export default function App() {
|
||||
const [position, setPosition] = useState<{ x: number; y: number }>();
|
||||
const [isDragging, setIsDragging] = useState(false);
|
||||
const [dragOffset, setDragOffset] = useState({ x: 0, y: 0 });
|
||||
const [shouldTriggerUsage, setShouldTriggerUsage] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
const handleExplainNode = () => {
|
||||
console.log("Explain node event received");
|
||||
setShowChat(true);
|
||||
setShouldTriggerUsage(true);
|
||||
};
|
||||
|
||||
window.addEventListener(COPILOT_EVENTS.EXPLAIN_NODE, handleExplainNode);
|
||||
return () => window.removeEventListener(COPILOT_EVENTS.EXPLAIN_NODE, handleExplainNode);
|
||||
}, []);
|
||||
|
||||
useEffect(() => {
|
||||
setPosition({
|
||||
@@ -65,12 +78,22 @@ export default function App() {
|
||||
>
|
||||
<button
|
||||
onMouseDown={handleMouseDown}
|
||||
onClick={() => setShowChat(true)}
|
||||
onClick={() => {
|
||||
setShowChat(true);
|
||||
}}
|
||||
className="px-4 py-2 border border-gray-300 rounded-md bg-white text-black hover:bg-green-600 transition-colors select-none"
|
||||
>
|
||||
copilot
|
||||
</button>
|
||||
<WorkflowChat onClose={() => setShowChat(false)} visible={showChat} />
|
||||
<WorkflowChat
|
||||
onClose={() => {
|
||||
setShowChat(false);
|
||||
setShouldTriggerUsage(false);
|
||||
}}
|
||||
visible={showChat}
|
||||
triggerUsage={shouldTriggerUsage}
|
||||
onUsageTriggered={() => setShouldTriggerUsage(false)}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
export const COPILOT_EVENTS = {
|
||||
EXPLAIN_NODE: 'copilot:explain-node'
|
||||
} as const;
|
||||
+1334
-201
File diff suppressed because it is too large
Load Diff
@@ -14,9 +14,11 @@ import React from "react";
|
||||
interface WorkflowChatProps {
|
||||
onClose?: () => void;
|
||||
visible?: boolean;
|
||||
triggerUsage?: boolean;
|
||||
onUsageTriggered?: () => void;
|
||||
}
|
||||
|
||||
export default function WorkflowChat({ onClose, visible = true }: WorkflowChatProps) {
|
||||
export default function WorkflowChat({ onClose, visible = true, triggerUsage = false, onUsageTriggered }: WorkflowChatProps) {
|
||||
const [messages, setMessages] = useState<Message[]>([]);
|
||||
const [input, setInput] = useState<string>('');
|
||||
const [latestInput, setLatestInput] = useState<string>('');
|
||||
@@ -285,6 +287,13 @@ export default function WorkflowChat({ onClose, visible = true }: WorkflowChatPr
|
||||
};
|
||||
}, [uploadedImages]);
|
||||
|
||||
useEffect(() => {
|
||||
if (triggerUsage && onUsageTriggered) {
|
||||
handleSendMessageWithIntent('node_explain');
|
||||
onUsageTriggered();
|
||||
}
|
||||
}, [triggerUsage]);
|
||||
|
||||
return (
|
||||
<div
|
||||
className="fixed top-0 right-0 h-full shadow-lg bg-white
|
||||
|
||||
Reference in New Issue
Block a user