@embedpdf/plugin-redaction 1.0.18 → 1.0.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("@embedpdf/core"),t=require("@embedpdf/models"),i="START_REDACTION",n="END_REDACTION",a="ADD_PENDING",s="REMOVE_PENDING",r="CLEAR_PENDING",o="SELECT_PENDING",c="DESELECT_PENDING",l=e=>({type:a,payload:e}),d=(e,t)=>({type:s,payload:{page:e,id:t}}),g=()=>({type:r});const u=class extends e.BasePlugin{constructor(a,s,r,o){var c,d,g,u,h;super(a,s),this.redactionSelection$=e.createBehaviorEmitter(),this.pending$=e.createBehaviorEmitter(),this.selected$=e.createBehaviorEmitter(),this.engine=r,this.config=o,this.selectionCapability=null==(c=this.registry.getPlugin("selection"))?void 0:c.provides(),this.interactionManagerCapability=null==(d=this.registry.getPlugin("interaction-manager"))?void 0:d.provides(),this.interactionManagerCapability&&this.interactionManagerCapability.registerMode({id:"marqueeRedact",scope:"page",exclusive:!0,cursor:"crosshair"}),this.interactionManagerCapability&&this.selectionCapability&&(this.interactionManagerCapability.registerMode({id:"redactSelection",scope:"page",exclusive:!1}),this.selectionCapability.enableForMode("redactSelection")),this.unsubscribeModeChange=null==(g=this.interactionManagerCapability)?void 0:g.onModeChange((e=>{"redactSelection"===e.activeMode||"marqueeRedact"===e.activeMode?this.dispatch({type:i}):this.dispatch({type:n})})),this.unsubscribeSelectionChange=null==(u=this.selectionCapability)?void 0:u.onSelectionChange((()=>{if(!this.selectionCapability)return;if(!this.state.isRedacting)return;const e=this.selectionCapability.getFormattedSelection();this.redactionSelection$.emit(e)})),this.unsubscribeEndSelection=null==(h=this.selectionCapability)?void 0:h.onEndSelection((()=>{if(!this.selectionCapability)return;if(!this.state.isRedacting)return;const e=this.selectionCapability.getFormattedSelection().map((e=>({id:t.uuidV4(),kind:"text",page:e.pageIndex,boundingRect:e.rect,rects:e.segmentRects})));this.dispatch(l(e)),this.redactionSelection$.emit([]),this.selectionCapability.clear(),this.pending$.emit(this.state.pending),e.length&&this.selectPending(e[e.length-1].page,e[e.length-1].id)}))}async initialize(e){}buildCapability(){return{onRedactionSelectionChange:this.redactionSelection$.on,queueCurrentSelectionAsPending:()=>this.queueCurrentSelectionAsPending(),enableMarqueeRedact:()=>this.enableMarqueeRedact(),toggleMarqueeRedact:()=>this.toggleMarqueeRedact(),isMarqueeRedactActive:()=>{var e;return"marqueeRedact"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())},enableRedactSelection:()=>this.enableRedactSelection(),toggleRedactSelection:()=>this.toggleRedactSelection(),isRedactSelectionActive:()=>{var e;return"redactSelection"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())},onPendingChange:this.pending$.on,removePending:(e,t)=>{this.dispatch(d(e,t)),this.pending$.emit(this.state.pending)},clearPending:()=>{this.dispatch(g()),this.pending$.emit(this.state.pending)},commitAllPending:()=>this.commitAllPending(),commitPending:(e,t)=>this.commitPendingOne(e,t),endRedaction:()=>this.endRedaction(),startRedaction:()=>this.startRedaction(),onSelectionChange:this.selected$.on,selectPending:(e,t)=>this.selectPending(e,t),deselectPending:()=>this.deselectPending(),registerMarqueeOnPage:e=>this.registerMarqueeOnPage(e)}}selectPending(e,t){var i;this.dispatch(((e,t)=>({type:o,payload:{page:e,id:t}}))(e,t)),null==(i=this.selectionCapability)||i.clear(),this.selected$.emit(this.state.selected)}deselectPending(){this.dispatch({type:c}),this.selected$.emit(this.state.selected)}enableRedactSelection(){var e;null==(e=this.interactionManagerCapability)||e.activate("redactSelection")}toggleRedactSelection(){var e,t,i;"redactSelection"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())?null==(t=this.interactionManagerCapability)||t.activateDefaultMode():null==(i=this.interactionManagerCapability)||i.activate("redactSelection")}enableMarqueeRedact(){var e;null==(e=this.interactionManagerCapability)||e.activate("marqueeRedact")}toggleMarqueeRedact(){var e,t,i;"marqueeRedact"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())?null==(t=this.interactionManagerCapability)||t.activateDefaultMode():null==(i=this.interactionManagerCapability)||i.activate("marqueeRedact")}startRedaction(){var e;null==(e=this.interactionManagerCapability)||e.activate("redactSelection")}endRedaction(){var e;null==(e=this.interactionManagerCapability)||e.activateDefaultMode()}registerMarqueeOnPage(i){if(!this.interactionManagerCapability)throw new Error("[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction");const n=this.coreState.core.document;if(!n)throw new Error("[RedactionPlugin] Document not found");const a=n.pages[i.pageIndex];if(!a)throw new Error("[RedactionPlugin] Page not found");const s=function(t){const{pageSize:i,scale:n,minDragPx:a=5,onPreview:s,onCommit:r}=t;let o=null,c=null;return{onPointerDown:(e,t)=>{var i;o=e,c={origin:{x:e.x,y:e.y},size:{width:0,height:0}},null==s||s(c),null==(i=t.setPointerCapture)||i.call(t)},onPointerMove:t=>{if(!o)return;const n=e.clamp(t.x,0,i.width),a=e.clamp(t.y,0,i.height);c={origin:{x:Math.min(o.x,n),y:Math.min(o.y,a)},size:{width:Math.abs(n-o.x),height:Math.abs(a-o.y)}},null==s||s(c)},onPointerUp:(e,t)=>{var i;c&&Math.max(c.size.width,c.size.height)*n>a&&(null==r||r(c)),o=null,c=null,null==s||s(null),null==(i=t.releasePointerCapture)||i.call(t)},onPointerCancel:(e,t)=>{var i;o=null,c=null,null==s||s(null),null==(i=t.releasePointerCapture)||i.call(t)}}}({pageSize:a.size,scale:i.scale,onPreview:i.callback.onPreview,onCommit:e=>{var n,a;const s={id:t.uuidV4(),kind:"area",page:i.pageIndex,rect:e};this.dispatch(l([s])),this.pending$.emit(this.state.pending),null==(a=(n=i.callback).onCommit)||a.call(n,e),this.enableRedactSelection(),this.selectPending(i.pageIndex,s.id)}}),r=this.interactionManagerCapability.registerAlways({handlers:{onPointerDown:(e,t)=>{t.target===t.currentTarget&&this.deselectPending()}},scope:{type:"page",pageIndex:i.pageIndex}}),o=this.interactionManagerCapability.registerHandlers({modeId:"marqueeRedact",handlers:s,pageIndex:i.pageIndex});return()=>{r(),o()}}queueCurrentSelectionAsPending(){var e;if(!this.selectionCapability)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"[RedactionPlugin] selection plugin required"});if(!this.coreState.core.document)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const i=this.selectionCapability.getFormattedSelection();if(!i.length)return t.PdfTaskHelper.resolve(!0);const n=t.uuidV4(),a=i.map((e=>({id:n,kind:"text",page:e.pageIndex,boundingRect:e.rect,rects:e.segmentRects})));this.enableRedactSelection(),this.dispatch(l(a)),this.pending$.emit(this.state.pending);const s=a[a.length-1];return this.selectPending(s.page,s.id),this.redactionSelection$.emit([]),null==(e=this.selectionCapability)||e.clear(),t.PdfTaskHelper.resolve(!0)}commitPendingOne(i,n){const a=this.coreState.core.document;if(!a)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const s=(this.state.pending[i]??[]).find((e=>e.id===n));if(!s)return t.PdfTaskHelper.resolve(!0);const r="text"===s.kind?s.rects:[s.rect],o=a.pages[i];if(!o)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Page not found"});const c=new t.Task;return this.engine.redactTextInRects(a,o,r,!1,this.config.blackbox).wait((()=>{this.dispatch(d(i,n)),this.pending$.emit(this.state.pending),this.dispatchCoreAction(e.refreshPages([i])),c.resolve(!0)}),(()=>c.reject({code:t.PdfErrorCode.Unknown,message:"Failed to commit redactions"}))),c}commitAllPending(){const i=this.coreState.core.document;if(!i)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const n=new Map;for(const[e,t]of Object.entries(this.state.pending)){const i=Number(e),a=n.get(i)??[];for(const e of t)"text"===e.kind?a.push(...e.rects):a.push(e.rect);n.set(i,a)}const a=Array.from(n.entries()).filter((([e,t])=>t.length>0)).map((([e])=>e)),s=[];for(const[e,t]of n){const n=i.pages[e];n&&(t.length&&s.push(this.engine.redactTextInRects(i,n,t,!1,this.config.blackbox)))}const r=new t.Task;return t.Task.all(s).wait((()=>{this.dispatch(g()),this.dispatchCoreAction(e.refreshPages(a)),this.pending$.emit(this.state.pending),r.resolve(!0)}),(()=>r.reject({code:t.PdfErrorCode.Unknown,message:"Failed to commit redactions"}))),r}onStoreUpdated(e,t){this.pending$.emit(t.pending),this.selected$.emit(t.selected)}async destroy(){var e,t,i;this.redactionSelection$.clear(),this.pending$.clear(),null==(e=this.unsubscribeSelectionChange)||e.call(this),null==(t=this.unsubscribeEndSelection)||t.call(this),null==(i=this.unsubscribeModeChange)||i.call(this),await super.destroy()}};u.id="redaction";let h=u;const p="redaction",m={id:p,name:"Redaction Plugin",version:"1.0.0",provides:["redaction"],requires:[],optional:["interaction-manager","selection"],defaultConfig:{enabled:!0,blackbox:!0}},b={isRedacting:!1,pending:{},selected:null},P={manifest:m,create:(e,t,i)=>new h(p,e,t,i),reducer:(e=b,t)=>{switch(t.type){case a:{const i={...e.pending};for(const e of t.payload)i[e.page]=(i[e.page]??[]).concat(e);return{...e,pending:i}}case s:{const{page:i,id:n}=t.payload,a=(e.pending[i]??[]).filter((e=>e.id!==n)),s={...e.pending,[i]:a},r=e.selected&&!(e.selected.page===i&&e.selected.id===n);return{...e,pending:s,selected:r?e.selected:null}}case r:return{...e,pending:{},selected:null};case o:return{...e,selected:{page:t.payload.page,id:t.payload.id}};case c:return{...e,selected:null};case i:return{...e,isRedacting:!0};case n:return{...e,pending:{},selected:null,isRedacting:!1};default:return e}},initialState:b};exports.REDACTION_PLUGIN_ID=p,exports.RedactionPlugin=h,exports.RedactionPluginPackage=P,exports.getPendingRedactionsCount=e=>Object.values(e.pending).reduce(((e,t)=>e+((null==t?void 0:t.length)??0)),0),exports.hasPendingRedactions=e=>Object.values(e.pending).some((e=>((null==e?void 0:e.length)??0)>0)),exports.manifest=m;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("@embedpdf/core"),t=require("@embedpdf/models"),i="START_REDACTION",n="END_REDACTION",a="ADD_PENDING",s="REMOVE_PENDING",r="CLEAR_PENDING",o="SELECT_PENDING",c="DESELECT_PENDING",l=e=>({type:a,payload:e}),d=(e,t)=>({type:s,payload:{page:e,id:t}}),g=()=>({type:r});const u=class extends e.BasePlugin{constructor(a,s,r){var o,c,d,g,u;super(a,s),this.redactionSelection$=e.createBehaviorEmitter(),this.pending$=e.createBehaviorEmitter(),this.selected$=e.createBehaviorEmitter(),this.config=r,this.selectionCapability=null==(o=this.registry.getPlugin("selection"))?void 0:o.provides(),this.interactionManagerCapability=null==(c=this.registry.getPlugin("interaction-manager"))?void 0:c.provides(),this.interactionManagerCapability&&this.interactionManagerCapability.registerMode({id:"marqueeRedact",scope:"page",exclusive:!0,cursor:"crosshair"}),this.interactionManagerCapability&&this.selectionCapability&&(this.interactionManagerCapability.registerMode({id:"redactSelection",scope:"page",exclusive:!1}),this.selectionCapability.enableForMode("redactSelection")),this.unsubscribeModeChange=null==(d=this.interactionManagerCapability)?void 0:d.onModeChange((e=>{"redactSelection"===e.activeMode||"marqueeRedact"===e.activeMode?this.dispatch({type:i}):this.dispatch({type:n})})),this.unsubscribeSelectionChange=null==(g=this.selectionCapability)?void 0:g.onSelectionChange((()=>{if(!this.selectionCapability)return;if(!this.state.isRedacting)return;const e=this.selectionCapability.getFormattedSelection();this.redactionSelection$.emit(e)})),this.unsubscribeEndSelection=null==(u=this.selectionCapability)?void 0:u.onEndSelection((()=>{if(!this.selectionCapability)return;if(!this.state.isRedacting)return;const e=this.selectionCapability.getFormattedSelection().map((e=>({id:t.uuidV4(),kind:"text",page:e.pageIndex,boundingRect:e.rect,rects:e.segmentRects})));this.dispatch(l(e)),this.redactionSelection$.emit([]),this.selectionCapability.clear(),this.pending$.emit(this.state.pending),e.length&&this.selectPending(e[e.length-1].page,e[e.length-1].id)}))}async initialize(e){}buildCapability(){return{onRedactionSelectionChange:this.redactionSelection$.on,queueCurrentSelectionAsPending:()=>this.queueCurrentSelectionAsPending(),enableMarqueeRedact:()=>this.enableMarqueeRedact(),toggleMarqueeRedact:()=>this.toggleMarqueeRedact(),isMarqueeRedactActive:()=>{var e;return"marqueeRedact"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())},enableRedactSelection:()=>this.enableRedactSelection(),toggleRedactSelection:()=>this.toggleRedactSelection(),isRedactSelectionActive:()=>{var e;return"redactSelection"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())},onPendingChange:this.pending$.on,removePending:(e,t)=>{this.dispatch(d(e,t)),this.pending$.emit(this.state.pending)},clearPending:()=>{this.dispatch(g()),this.pending$.emit(this.state.pending)},commitAllPending:()=>this.commitAllPending(),commitPending:(e,t)=>this.commitPendingOne(e,t),endRedaction:()=>this.endRedaction(),startRedaction:()=>this.startRedaction(),onSelectionChange:this.selected$.on,selectPending:(e,t)=>this.selectPending(e,t),deselectPending:()=>this.deselectPending(),registerMarqueeOnPage:e=>this.registerMarqueeOnPage(e)}}selectPending(e,t){var i;this.dispatch(((e,t)=>({type:o,payload:{page:e,id:t}}))(e,t)),null==(i=this.selectionCapability)||i.clear(),this.selected$.emit(this.state.selected)}deselectPending(){this.dispatch({type:c}),this.selected$.emit(this.state.selected)}enableRedactSelection(){var e;null==(e=this.interactionManagerCapability)||e.activate("redactSelection")}toggleRedactSelection(){var e,t,i;"redactSelection"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())?null==(t=this.interactionManagerCapability)||t.activateDefaultMode():null==(i=this.interactionManagerCapability)||i.activate("redactSelection")}enableMarqueeRedact(){var e;null==(e=this.interactionManagerCapability)||e.activate("marqueeRedact")}toggleMarqueeRedact(){var e,t,i;"marqueeRedact"===(null==(e=this.interactionManagerCapability)?void 0:e.getActiveMode())?null==(t=this.interactionManagerCapability)||t.activateDefaultMode():null==(i=this.interactionManagerCapability)||i.activate("marqueeRedact")}startRedaction(){var e;null==(e=this.interactionManagerCapability)||e.activate("redactSelection")}endRedaction(){var e;null==(e=this.interactionManagerCapability)||e.activateDefaultMode()}registerMarqueeOnPage(i){if(!this.interactionManagerCapability)throw new Error("[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction");const n=this.coreState.core.document;if(!n)throw new Error("[RedactionPlugin] Document not found");const a=n.pages[i.pageIndex];if(!a)throw new Error("[RedactionPlugin] Page not found");const s=function(t){const{pageSize:i,scale:n,minDragPx:a=5,onPreview:s,onCommit:r}=t;let o=null,c=null;return{onPointerDown:(e,t)=>{var i;o=e,c={origin:{x:e.x,y:e.y},size:{width:0,height:0}},null==s||s(c),null==(i=t.setPointerCapture)||i.call(t)},onPointerMove:t=>{if(!o)return;const n=e.clamp(t.x,0,i.width),a=e.clamp(t.y,0,i.height);c={origin:{x:Math.min(o.x,n),y:Math.min(o.y,a)},size:{width:Math.abs(n-o.x),height:Math.abs(a-o.y)}},null==s||s(c)},onPointerUp:(e,t)=>{var i;c&&Math.max(c.size.width,c.size.height)*n>a&&(null==r||r(c)),o=null,c=null,null==s||s(null),null==(i=t.releasePointerCapture)||i.call(t)},onPointerCancel:(e,t)=>{var i;o=null,c=null,null==s||s(null),null==(i=t.releasePointerCapture)||i.call(t)}}}({pageSize:a.size,scale:i.scale,onPreview:i.callback.onPreview,onCommit:e=>{var n,a;const s={id:t.uuidV4(),kind:"area",page:i.pageIndex,rect:e};this.dispatch(l([s])),this.pending$.emit(this.state.pending),null==(a=(n=i.callback).onCommit)||a.call(n,e),this.enableRedactSelection(),this.selectPending(i.pageIndex,s.id)}}),r=this.interactionManagerCapability.registerAlways({handlers:{onPointerDown:(e,t)=>{t.target===t.currentTarget&&this.deselectPending()}},scope:{type:"page",pageIndex:i.pageIndex}}),o=this.interactionManagerCapability.registerHandlers({modeId:"marqueeRedact",handlers:s,pageIndex:i.pageIndex});return()=>{r(),o()}}queueCurrentSelectionAsPending(){var e;if(!this.selectionCapability)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"[RedactionPlugin] selection plugin required"});if(!this.coreState.core.document)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const i=this.selectionCapability.getFormattedSelection();if(!i.length)return t.PdfTaskHelper.resolve(!0);const n=t.uuidV4(),a=i.map((e=>({id:n,kind:"text",page:e.pageIndex,boundingRect:e.rect,rects:e.segmentRects})));this.enableRedactSelection(),this.dispatch(l(a)),this.pending$.emit(this.state.pending);const s=a[a.length-1];return this.selectPending(s.page,s.id),this.redactionSelection$.emit([]),null==(e=this.selectionCapability)||e.clear(),t.PdfTaskHelper.resolve(!0)}commitPendingOne(i,n){const a=this.coreState.core.document;if(!a)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const s=(this.state.pending[i]??[]).find((e=>e.id===n));if(!s)return t.PdfTaskHelper.resolve(!0);const r="text"===s.kind?s.rects:[s.rect],o=a.pages[i];if(!o)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Page not found"});const c=new t.Task;return this.engine.redactTextInRects(a,o,r,{drawBlackBoxes:this.config.drawBlackBoxes}).wait((()=>{this.dispatch(d(i,n)),this.pending$.emit(this.state.pending),this.dispatchCoreAction(e.refreshPages([i])),c.resolve(!0)}),(()=>c.reject({code:t.PdfErrorCode.Unknown,message:"Failed to commit redactions"}))),c}commitAllPending(){const i=this.coreState.core.document;if(!i)return t.PdfTaskHelper.reject({code:t.PdfErrorCode.NotFound,message:"Document not found"});const n=new Map;for(const[e,t]of Object.entries(this.state.pending)){const i=Number(e),a=n.get(i)??[];for(const e of t)"text"===e.kind?a.push(...e.rects):a.push(e.rect);n.set(i,a)}const a=Array.from(n.entries()).filter((([e,t])=>t.length>0)).map((([e])=>e)),s=[];for(const[e,t]of n){const n=i.pages[e];n&&(t.length&&s.push(this.engine.redactTextInRects(i,n,t,{drawBlackBoxes:this.config.drawBlackBoxes})))}const r=new t.Task;return t.Task.all(s).wait((()=>{this.dispatch(g()),this.dispatchCoreAction(e.refreshPages(a)),this.pending$.emit(this.state.pending),r.resolve(!0)}),(()=>r.reject({code:t.PdfErrorCode.Unknown,message:"Failed to commit redactions"}))),r}onStoreUpdated(e,t){this.pending$.emit(t.pending),this.selected$.emit(t.selected)}async destroy(){var e,t,i;this.redactionSelection$.clear(),this.pending$.clear(),null==(e=this.unsubscribeSelectionChange)||e.call(this),null==(t=this.unsubscribeEndSelection)||t.call(this),null==(i=this.unsubscribeModeChange)||i.call(this),await super.destroy()}};u.id="redaction";let h=u;const p="redaction",m={id:p,name:"Redaction Plugin",version:"1.0.0",provides:["redaction"],requires:[],optional:["interaction-manager","selection"],defaultConfig:{enabled:!0,drawBlackBoxes:!0}},P={isRedacting:!1,pending:{},selected:null},b={manifest:m,create:(e,t)=>new h(p,e,t),reducer:(e=P,t)=>{switch(t.type){case a:{const i={...e.pending};for(const e of t.payload)i[e.page]=(i[e.page]??[]).concat(e);return{...e,pending:i}}case s:{const{page:i,id:n}=t.payload,a=(e.pending[i]??[]).filter((e=>e.id!==n)),s={...e.pending,[i]:a},r=e.selected&&!(e.selected.page===i&&e.selected.id===n);return{...e,pending:s,selected:r?e.selected:null}}case r:return{...e,pending:{},selected:null};case o:return{...e,selected:{page:t.payload.page,id:t.payload.id}};case c:return{...e,selected:null};case i:return{...e,isRedacting:!0};case n:return{...e,pending:{},selected:null,isRedacting:!1};default:return e}},initialState:P};exports.REDACTION_PLUGIN_ID=p,exports.RedactionPlugin=h,exports.RedactionPluginPackage=b,exports.getPendingRedactionsCount=e=>Object.values(e.pending).reduce(((e,t)=>e+((null==t?void 0:t.length)??0)),0),exports.hasPendingRedactions=e=>Object.values(e.pending).some((e=>((null==e?void 0:e.length)??0)>0)),exports.manifest=m;
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":["../src/lib/actions.ts","../src/lib/redaction-plugin.ts","../src/lib/handlers/marquee-redact.handler.ts","../src/lib/manifest.ts","../src/lib/reducer.ts","../src/lib/index.ts","../src/lib/selectors.ts"],"sourcesContent":["import { Action } from '@embedpdf/core';\nimport { RedactionItem } from './types';\n\nexport const START_REDACTION = 'START_REDACTION';\nexport const END_REDACTION = 'END_REDACTION';\n\nexport const ADD_PENDING = 'ADD_PENDING';\nexport const REMOVE_PENDING = 'REMOVE_PENDING';\nexport const CLEAR_PENDING = 'CLEAR_PENDING';\n\nexport const SELECT_PENDING = 'SELECT_PENDING';\nexport const DESELECT_PENDING = 'DESELECT_PENDING';\n\nexport interface StartRedactionAction extends Action {\n type: typeof START_REDACTION;\n}\nexport interface EndRedactionAction extends Action {\n type: typeof END_REDACTION;\n}\n\nexport interface AddPendingAction extends Action {\n type: typeof ADD_PENDING;\n payload: RedactionItem[];\n}\nexport interface RemovePendingAction extends Action {\n type: typeof REMOVE_PENDING;\n payload: { page: number; id: string };\n}\nexport interface ClearPendingAction extends Action {\n type: typeof CLEAR_PENDING;\n}\n\nexport interface SelectPendingAction extends Action {\n type: typeof SELECT_PENDING;\n payload: { page: number; id: string };\n}\nexport interface DeselectPendingAction extends Action {\n type: typeof DESELECT_PENDING;\n}\n\nexport type RedactionAction =\n | StartRedactionAction\n | EndRedactionAction\n | AddPendingAction\n | RemovePendingAction\n | ClearPendingAction\n | SelectPendingAction\n | DeselectPendingAction;\n\nexport const addPending = (items: RedactionItem[]): AddPendingAction => ({\n type: ADD_PENDING,\n payload: items,\n});\nexport const removePending = (page: number, id: string): RemovePendingAction => ({\n type: REMOVE_PENDING,\n payload: { page, id },\n});\nexport const clearPending = (): ClearPendingAction => ({ type: CLEAR_PENDING });\n\nexport const startRedaction = (): StartRedactionAction => ({ type: START_REDACTION });\nexport const endRedaction = (): EndRedactionAction => ({ type: END_REDACTION });\n\nexport const selectPending = (page: number, id: string): SelectPendingAction => ({\n type: SELECT_PENDING,\n payload: { page, id },\n});\nexport const deselectPending = (): DeselectPendingAction => ({ type: DESELECT_PENDING });\n","import {\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState,\n RegisterMarqueeOnPageOptions,\n RedactionItem,\n SelectedRedaction,\n} from './types';\nimport {\n BasePlugin,\n createBehaviorEmitter,\n PluginRegistry,\n refreshDocument,\n refreshPages,\n Unsubscribe,\n} from '@embedpdf/core';\nimport {\n ignore,\n PdfEngine,\n PdfErrorCode,\n PdfErrorReason,\n PdfTask,\n PdfTaskHelper,\n Rect,\n Task,\n uuidV4,\n} from '@embedpdf/models';\nimport {\n FormattedSelection,\n SelectionCapability,\n SelectionPlugin,\n} from '@embedpdf/plugin-selection';\nimport {\n InteractionManagerCapability,\n InteractionManagerPlugin,\n} from '@embedpdf/plugin-interaction-manager';\nimport {\n addPending,\n clearPending,\n deselectPending,\n endRedaction,\n removePending,\n selectPending,\n startRedaction,\n} from './actions';\nimport { createMarqueeHandler } from './handlers';\n\nexport class RedactionPlugin extends BasePlugin<\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState\n> {\n static readonly id = 'redaction' as const;\n private engine: PdfEngine;\n private config: RedactionPluginConfig;\n\n private selectionCapability: SelectionCapability | undefined;\n private interactionManagerCapability: InteractionManagerCapability | undefined;\n\n private readonly redactionSelection$ = createBehaviorEmitter<FormattedSelection[]>();\n private readonly pending$ = createBehaviorEmitter<Record<number, RedactionItem[]>>();\n private readonly selected$ = createBehaviorEmitter<SelectedRedaction | null>();\n\n private readonly unsubscribeSelectionChange: Unsubscribe | undefined;\n private readonly unsubscribeEndSelection: Unsubscribe | undefined;\n private readonly unsubscribeModeChange: Unsubscribe | undefined;\n\n constructor(\n id: string,\n registry: PluginRegistry,\n engine: PdfEngine,\n config: RedactionPluginConfig,\n ) {\n super(id, registry);\n this.engine = engine;\n this.config = config;\n\n this.selectionCapability = this.registry.getPlugin<SelectionPlugin>('selection')?.provides();\n this.interactionManagerCapability = this.registry\n .getPlugin<InteractionManagerPlugin>('interaction-manager')\n ?.provides();\n\n if (this.interactionManagerCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'marqueeRedact',\n scope: 'page',\n exclusive: true,\n cursor: 'crosshair',\n });\n }\n\n if (this.interactionManagerCapability && this.selectionCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'redactSelection',\n scope: 'page',\n exclusive: false,\n });\n this.selectionCapability.enableForMode('redactSelection');\n }\n\n this.unsubscribeModeChange = this.interactionManagerCapability?.onModeChange((state) => {\n if (state.activeMode === 'redactSelection' || state.activeMode === 'marqueeRedact')\n this.dispatch(startRedaction());\n else this.dispatch(endRedaction());\n });\n\n this.unsubscribeSelectionChange = this.selectionCapability?.onSelectionChange(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n this.redactionSelection$.emit(formattedSelection);\n });\n\n this.unsubscribeEndSelection = this.selectionCapability?.onEndSelection(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n\n const items: RedactionItem[] = formattedSelection.map((s) => ({\n id: uuidV4(),\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.dispatch(addPending(items));\n this.redactionSelection$.emit([]);\n this.selectionCapability.clear();\n this.pending$.emit(this.state.pending);\n if (items.length) {\n this.selectPending(items[items.length - 1].page, items[items.length - 1].id);\n }\n });\n }\n\n async initialize(_config: RedactionPluginConfig): Promise<void> {}\n\n protected buildCapability(): RedactionCapability {\n return {\n onRedactionSelectionChange: this.redactionSelection$.on,\n\n queueCurrentSelectionAsPending: () => this.queueCurrentSelectionAsPending(),\n\n enableMarqueeRedact: () => this.enableMarqueeRedact(),\n toggleMarqueeRedact: () => this.toggleMarqueeRedact(),\n isMarqueeRedactActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact',\n\n enableRedactSelection: () => this.enableRedactSelection(),\n toggleRedactSelection: () => this.toggleRedactSelection(),\n isRedactSelectionActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'redactSelection',\n\n onPendingChange: this.pending$.on,\n removePending: (page, id) => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n },\n clearPending: () => {\n this.dispatch(clearPending());\n this.pending$.emit(this.state.pending);\n },\n commitAllPending: () => this.commitAllPending(),\n commitPending: (page, id) => this.commitPendingOne(page, id),\n\n endRedaction: () => this.endRedaction(),\n startRedaction: () => this.startRedaction(),\n\n onSelectionChange: this.selected$.on,\n selectPending: (page, id) => this.selectPending(page, id),\n deselectPending: () => this.deselectPending(),\n\n registerMarqueeOnPage: (opts) => this.registerMarqueeOnPage(opts),\n };\n }\n\n private selectPending(page: number, id: string) {\n this.dispatch(selectPending(page, id));\n this.selectionCapability?.clear();\n this.selected$.emit(this.state.selected);\n }\n private deselectPending() {\n this.dispatch(deselectPending());\n this.selected$.emit(this.state.selected);\n }\n\n private enableRedactSelection() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private toggleRedactSelection() {\n if (this.interactionManagerCapability?.getActiveMode() === 'redactSelection')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('redactSelection');\n }\n\n private enableMarqueeRedact() {\n this.interactionManagerCapability?.activate('marqueeRedact');\n }\n private toggleMarqueeRedact() {\n if (this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('marqueeRedact');\n }\n\n private startRedaction() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private endRedaction() {\n this.interactionManagerCapability?.activateDefaultMode();\n }\n\n public registerMarqueeOnPage(opts: RegisterMarqueeOnPageOptions) {\n if (!this.interactionManagerCapability)\n throw new Error(\n '[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction',\n );\n\n const document = this.coreState.core.document;\n if (!document) throw new Error('[RedactionPlugin] Document not found');\n\n const page = document.pages[opts.pageIndex];\n if (!page) throw new Error('[RedactionPlugin] Page not found');\n\n const handlers = createMarqueeHandler({\n pageSize: page.size,\n scale: opts.scale,\n onPreview: opts.callback.onPreview,\n onCommit: (r) => {\n const item: RedactionItem = {\n id: uuidV4(),\n kind: 'area',\n page: opts.pageIndex,\n rect: r,\n };\n this.dispatch(addPending([item]));\n this.pending$.emit(this.state.pending);\n opts.callback.onCommit?.(r);\n this.enableRedactSelection();\n this.selectPending(opts.pageIndex, item.id);\n },\n });\n\n const off = this.interactionManagerCapability.registerAlways({\n handlers: {\n onPointerDown: (_, evt) => {\n if (evt.target === evt.currentTarget) {\n this.deselectPending();\n }\n },\n },\n scope: {\n type: 'page',\n pageIndex: opts.pageIndex,\n },\n });\n\n const off2 = this.interactionManagerCapability.registerHandlers({\n modeId: 'marqueeRedact',\n handlers,\n pageIndex: opts.pageIndex,\n });\n\n return () => {\n off();\n off2();\n };\n }\n\n private queueCurrentSelectionAsPending(): Task<boolean, PdfErrorReason> {\n if (!this.selectionCapability)\n return PdfTaskHelper.reject({\n code: PdfErrorCode.NotFound,\n message: '[RedactionPlugin] selection plugin required',\n });\n\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const formatted = this.selectionCapability.getFormattedSelection();\n if (!formatted.length) return PdfTaskHelper.resolve(true);\n\n const id = uuidV4();\n\n const items: RedactionItem[] = formatted.map((s) => ({\n id,\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.enableRedactSelection();\n this.dispatch(addPending(items));\n this.pending$.emit(this.state.pending);\n // optional: auto-select the last one added\n const last = items[items.length - 1];\n this.selectPending(last.page, last.id);\n\n // clear live UI selection\n this.redactionSelection$.emit([]);\n this.selectionCapability?.clear();\n\n return PdfTaskHelper.resolve(true);\n }\n\n private commitPendingOne(page: number, id: string): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const item = (this.state.pending[page] ?? []).find((it) => it.id === id);\n if (!item) return PdfTaskHelper.resolve(true);\n\n const rects: Rect[] = item.kind === 'text' ? item.rects : [item.rect];\n const pdfPage = doc.pages[page];\n if (!pdfPage)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Page not found' });\n\n const task = new Task<boolean, PdfErrorReason>();\n this.engine.redactTextInRects(doc, pdfPage, rects, false, this.config.blackbox).wait(\n () => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n this.dispatchCoreAction(refreshPages([page]));\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n private commitAllPending(): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n // group rects per page\n const perPage = new Map<number, Rect[]>();\n for (const [page, items] of Object.entries(this.state.pending)) {\n const p = Number(page);\n const list = perPage.get(p) ?? [];\n for (const it of items) {\n if (it.kind === 'text') list.push(...it.rects);\n else list.push(it.rect);\n }\n perPage.set(p, list);\n }\n\n const pagesToRefresh = Array.from(perPage.entries())\n .filter(([_, rects]) => rects.length > 0)\n .map(([pageIndex]) => pageIndex);\n\n const tasks: PdfTask<boolean>[] = [];\n for (const [pageIndex, rects] of perPage) {\n const page = doc.pages[pageIndex];\n if (!page) continue;\n if (!rects.length) continue;\n tasks.push(this.engine.redactTextInRects(doc, page, rects, false, this.config.blackbox));\n }\n\n const task = new Task<boolean, PdfErrorReason>();\n Task.all(tasks).wait(\n () => {\n this.dispatch(clearPending());\n this.dispatchCoreAction(refreshPages(pagesToRefresh));\n this.pending$.emit(this.state.pending);\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n override onStoreUpdated(_: RedactionState, newState: RedactionState): void {\n // keep external listeners in sync\n this.pending$.emit(newState.pending);\n this.selected$.emit(newState.selected);\n }\n\n async destroy(): Promise<void> {\n this.redactionSelection$.clear();\n this.pending$.clear();\n\n this.unsubscribeSelectionChange?.();\n this.unsubscribeEndSelection?.();\n this.unsubscribeModeChange?.();\n\n await super.destroy();\n }\n}\n","import { Position, Rect, Size } from '@embedpdf/models';\nimport { clamp } from '@embedpdf/core';\nimport {\n EmbedPdfPointerEvent,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\n\nexport function createMarqueeHandler(opts: {\n pageSize: Size;\n scale: number;\n minDragPx?: number;\n onPreview?: (rect: Rect | null) => void;\n onCommit?: (rect: Rect) => void;\n}): PointerEventHandlersWithLifecycle<EmbedPdfPointerEvent> {\n const { pageSize, scale, minDragPx = 5, onPreview, onCommit } = opts;\n\n let start: Position | null = null;\n let last: Rect | null = null;\n\n return {\n onPointerDown: (pos, evt) => {\n start = pos;\n last = { origin: { x: pos.x, y: pos.y }, size: { width: 0, height: 0 } };\n onPreview?.(last);\n evt.setPointerCapture?.();\n },\n onPointerMove: (pos) => {\n if (!start) return;\n const x = clamp(pos.x, 0, pageSize.width);\n const y = clamp(pos.y, 0, pageSize.height);\n last = {\n origin: { x: Math.min(start.x, x), y: Math.min(start.y, y) },\n size: { width: Math.abs(x - start.x), height: Math.abs(y - start.y) },\n };\n onPreview?.(last);\n },\n onPointerUp: (_pos, evt) => {\n if (last) {\n const dragPx = Math.max(last.size.width, last.size.height) * scale;\n if (dragPx > minDragPx) onCommit?.(last);\n }\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n onPointerCancel: (_pos, evt) => {\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n };\n}\n","import { PluginManifest } from '@embedpdf/core';\nimport { RedactionPluginConfig } from './types';\n\nexport const REDACTION_PLUGIN_ID = 'redaction';\n\nexport const manifest: PluginManifest<RedactionPluginConfig> = {\n id: REDACTION_PLUGIN_ID,\n name: 'Redaction Plugin',\n version: '1.0.0',\n provides: ['redaction'],\n requires: [],\n optional: ['interaction-manager', 'selection'],\n defaultConfig: {\n enabled: true,\n blackbox: true,\n },\n};\n","import { RedactionState } from './types';\nimport {\n RedactionAction,\n ADD_PENDING,\n CLEAR_PENDING,\n END_REDACTION,\n REMOVE_PENDING,\n START_REDACTION,\n SELECT_PENDING,\n DESELECT_PENDING,\n} from './actions';\n\nexport const initialState: RedactionState = {\n isRedacting: false,\n pending: {},\n selected: null,\n};\n\nexport const redactionReducer = (state = initialState, action: RedactionAction): RedactionState => {\n switch (action.type) {\n case ADD_PENDING: {\n const next = { ...state.pending };\n for (const item of action.payload) {\n next[item.page] = (next[item.page] ?? []).concat(item);\n }\n return { ...state, pending: next };\n }\n\n case REMOVE_PENDING: {\n const { page, id } = action.payload;\n const list = state.pending[page] ?? [];\n const filtered = list.filter((it) => it.id !== id);\n const next = { ...state.pending, [page]: filtered };\n\n // if the removed one was selected → clear selection\n const stillSelected =\n state.selected && !(state.selected.page === page && state.selected.id === id);\n\n return { ...state, pending: next, selected: stillSelected ? state.selected : null };\n }\n\n case CLEAR_PENDING:\n return { ...state, pending: {}, selected: null };\n\n case SELECT_PENDING:\n return { ...state, selected: { page: action.payload.page, id: action.payload.id } };\n\n case DESELECT_PENDING:\n return { ...state, selected: null };\n\n case START_REDACTION:\n return { ...state, isRedacting: true };\n case END_REDACTION:\n return { ...state, pending: {}, selected: null, isRedacting: false };\n default:\n return state;\n }\n};\n","import { PluginPackage } from '@embedpdf/core';\nimport { RedactionPluginConfig, RedactionState } from './types';\nimport { RedactionPlugin } from './redaction-plugin';\nimport { manifest, REDACTION_PLUGIN_ID } from './manifest';\nimport { RedactionAction } from './actions';\nimport { initialState, redactionReducer } from './reducer';\n\nexport const RedactionPluginPackage: PluginPackage<\n RedactionPlugin,\n RedactionPluginConfig,\n RedactionState,\n RedactionAction\n> = {\n manifest,\n create: (registry, engine, config) =>\n new RedactionPlugin(REDACTION_PLUGIN_ID, registry, engine, config),\n reducer: redactionReducer,\n initialState: initialState,\n};\n\nexport * from './redaction-plugin';\nexport * from './types';\nexport * from './manifest';\nexport * from './selectors';\n","import { RedactionState } from './types';\n\nexport const getPendingRedactionsCount = (s: RedactionState) =>\n Object.values(s.pending).reduce((sum, list) => sum + (list?.length ?? 0), 0);\n\nexport const hasPendingRedactions = (s: RedactionState) =>\n Object.values(s.pending).some((list) => (list?.length ?? 0) > 0);\n"],"names":["START_REDACTION","END_REDACTION","ADD_PENDING","REMOVE_PENDING","CLEAR_PENDING","SELECT_PENDING","DESELECT_PENDING","addPending","items","type","payload","removePending","page","id","clearPending","_RedactionPlugin","BasePlugin","constructor","registry","engine","config","super","this","redactionSelection$","createBehaviorEmitter","pending$","selected$","selectionCapability","_a","getPlugin","provides","interactionManagerCapability","_b","registerMode","scope","exclusive","cursor","enableForMode","unsubscribeModeChange","_c","onModeChange","state","activeMode","dispatch","unsubscribeSelectionChange","_d","onSelectionChange","isRedacting","formattedSelection","getFormattedSelection","emit","unsubscribeEndSelection","_e","onEndSelection","map","s","uuidV4","kind","pageIndex","boundingRect","rect","rects","segmentRects","clear","pending","length","selectPending","initialize","_config","buildCapability","onRedactionSelectionChange","on","queueCurrentSelectionAsPending","enableMarqueeRedact","toggleMarqueeRedact","isMarqueeRedactActive","getActiveMode","enableRedactSelection","toggleRedactSelection","isRedactSelectionActive","onPendingChange","commitAllPending","commitPending","commitPendingOne","endRedaction","startRedaction","deselectPending","registerMarqueeOnPage","opts","selected","activate","activateDefaultMode","Error","document","coreState","core","pages","handlers","pageSize","scale","minDragPx","onPreview","onCommit","start","last","onPointerDown","pos","evt","origin","x","y","size","width","height","setPointerCapture","call","onPointerMove","clamp","Math","min","abs","onPointerUp","_pos","max","releasePointerCapture","onPointerCancel","createMarqueeHandler","callback","r","item","off","registerAlways","_","target","currentTarget","off2","registerHandlers","modeId","PdfTaskHelper","reject","code","PdfErrorCode","NotFound","message","formatted","resolve","doc","find","it","pdfPage","task","Task","redactTextInRects","blackbox","wait","dispatchCoreAction","refreshPages","Unknown","perPage","Map","Object","entries","p","Number","list","get","push","set","pagesToRefresh","Array","from","filter","tasks","all","onStoreUpdated","newState","destroy","RedactionPlugin","REDACTION_PLUGIN_ID","manifest","name","version","requires","optional","defaultConfig","enabled","initialState","RedactionPluginPackage","create","reducer","action","next","concat","filtered","stillSelected","values","reduce","sum","some"],"mappings":"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"}
1
+ {"version":3,"file":"index.cjs","sources":["../src/lib/actions.ts","../src/lib/redaction-plugin.ts","../src/lib/handlers/marquee-redact.handler.ts","../src/lib/manifest.ts","../src/lib/reducer.ts","../src/lib/index.ts","../src/lib/selectors.ts"],"sourcesContent":["import { Action } from '@embedpdf/core';\nimport { RedactionItem } from './types';\n\nexport const START_REDACTION = 'START_REDACTION';\nexport const END_REDACTION = 'END_REDACTION';\n\nexport const ADD_PENDING = 'ADD_PENDING';\nexport const REMOVE_PENDING = 'REMOVE_PENDING';\nexport const CLEAR_PENDING = 'CLEAR_PENDING';\n\nexport const SELECT_PENDING = 'SELECT_PENDING';\nexport const DESELECT_PENDING = 'DESELECT_PENDING';\n\nexport interface StartRedactionAction extends Action {\n type: typeof START_REDACTION;\n}\nexport interface EndRedactionAction extends Action {\n type: typeof END_REDACTION;\n}\n\nexport interface AddPendingAction extends Action {\n type: typeof ADD_PENDING;\n payload: RedactionItem[];\n}\nexport interface RemovePendingAction extends Action {\n type: typeof REMOVE_PENDING;\n payload: { page: number; id: string };\n}\nexport interface ClearPendingAction extends Action {\n type: typeof CLEAR_PENDING;\n}\n\nexport interface SelectPendingAction extends Action {\n type: typeof SELECT_PENDING;\n payload: { page: number; id: string };\n}\nexport interface DeselectPendingAction extends Action {\n type: typeof DESELECT_PENDING;\n}\n\nexport type RedactionAction =\n | StartRedactionAction\n | EndRedactionAction\n | AddPendingAction\n | RemovePendingAction\n | ClearPendingAction\n | SelectPendingAction\n | DeselectPendingAction;\n\nexport const addPending = (items: RedactionItem[]): AddPendingAction => ({\n type: ADD_PENDING,\n payload: items,\n});\nexport const removePending = (page: number, id: string): RemovePendingAction => ({\n type: REMOVE_PENDING,\n payload: { page, id },\n});\nexport const clearPending = (): ClearPendingAction => ({ type: CLEAR_PENDING });\n\nexport const startRedaction = (): StartRedactionAction => ({ type: START_REDACTION });\nexport const endRedaction = (): EndRedactionAction => ({ type: END_REDACTION });\n\nexport const selectPending = (page: number, id: string): SelectPendingAction => ({\n type: SELECT_PENDING,\n payload: { page, id },\n});\nexport const deselectPending = (): DeselectPendingAction => ({ type: DESELECT_PENDING });\n","import {\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState,\n RegisterMarqueeOnPageOptions,\n RedactionItem,\n SelectedRedaction,\n} from './types';\nimport {\n BasePlugin,\n createBehaviorEmitter,\n PluginRegistry,\n refreshDocument,\n refreshPages,\n Unsubscribe,\n} from '@embedpdf/core';\nimport {\n ignore,\n PdfEngine,\n PdfErrorCode,\n PdfErrorReason,\n PdfTask,\n PdfTaskHelper,\n Rect,\n Task,\n uuidV4,\n} from '@embedpdf/models';\nimport {\n FormattedSelection,\n SelectionCapability,\n SelectionPlugin,\n} from '@embedpdf/plugin-selection';\nimport {\n InteractionManagerCapability,\n InteractionManagerPlugin,\n} from '@embedpdf/plugin-interaction-manager';\nimport {\n addPending,\n clearPending,\n deselectPending,\n endRedaction,\n removePending,\n selectPending,\n startRedaction,\n} from './actions';\nimport { createMarqueeHandler } from './handlers';\n\nexport class RedactionPlugin extends BasePlugin<\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState\n> {\n static readonly id = 'redaction' as const;\n private config: RedactionPluginConfig;\n\n private selectionCapability: SelectionCapability | undefined;\n private interactionManagerCapability: InteractionManagerCapability | undefined;\n\n private readonly redactionSelection$ = createBehaviorEmitter<FormattedSelection[]>();\n private readonly pending$ = createBehaviorEmitter<Record<number, RedactionItem[]>>();\n private readonly selected$ = createBehaviorEmitter<SelectedRedaction | null>();\n\n private readonly unsubscribeSelectionChange: Unsubscribe | undefined;\n private readonly unsubscribeEndSelection: Unsubscribe | undefined;\n private readonly unsubscribeModeChange: Unsubscribe | undefined;\n\n constructor(id: string, registry: PluginRegistry, config: RedactionPluginConfig) {\n super(id, registry);\n this.config = config;\n\n this.selectionCapability = this.registry.getPlugin<SelectionPlugin>('selection')?.provides();\n this.interactionManagerCapability = this.registry\n .getPlugin<InteractionManagerPlugin>('interaction-manager')\n ?.provides();\n\n if (this.interactionManagerCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'marqueeRedact',\n scope: 'page',\n exclusive: true,\n cursor: 'crosshair',\n });\n }\n\n if (this.interactionManagerCapability && this.selectionCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'redactSelection',\n scope: 'page',\n exclusive: false,\n });\n this.selectionCapability.enableForMode('redactSelection');\n }\n\n this.unsubscribeModeChange = this.interactionManagerCapability?.onModeChange((state) => {\n if (state.activeMode === 'redactSelection' || state.activeMode === 'marqueeRedact')\n this.dispatch(startRedaction());\n else this.dispatch(endRedaction());\n });\n\n this.unsubscribeSelectionChange = this.selectionCapability?.onSelectionChange(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n this.redactionSelection$.emit(formattedSelection);\n });\n\n this.unsubscribeEndSelection = this.selectionCapability?.onEndSelection(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n\n const items: RedactionItem[] = formattedSelection.map((s) => ({\n id: uuidV4(),\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.dispatch(addPending(items));\n this.redactionSelection$.emit([]);\n this.selectionCapability.clear();\n this.pending$.emit(this.state.pending);\n if (items.length) {\n this.selectPending(items[items.length - 1].page, items[items.length - 1].id);\n }\n });\n }\n\n async initialize(_config: RedactionPluginConfig): Promise<void> {}\n\n protected buildCapability(): RedactionCapability {\n return {\n onRedactionSelectionChange: this.redactionSelection$.on,\n\n queueCurrentSelectionAsPending: () => this.queueCurrentSelectionAsPending(),\n\n enableMarqueeRedact: () => this.enableMarqueeRedact(),\n toggleMarqueeRedact: () => this.toggleMarqueeRedact(),\n isMarqueeRedactActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact',\n\n enableRedactSelection: () => this.enableRedactSelection(),\n toggleRedactSelection: () => this.toggleRedactSelection(),\n isRedactSelectionActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'redactSelection',\n\n onPendingChange: this.pending$.on,\n removePending: (page, id) => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n },\n clearPending: () => {\n this.dispatch(clearPending());\n this.pending$.emit(this.state.pending);\n },\n commitAllPending: () => this.commitAllPending(),\n commitPending: (page, id) => this.commitPendingOne(page, id),\n\n endRedaction: () => this.endRedaction(),\n startRedaction: () => this.startRedaction(),\n\n onSelectionChange: this.selected$.on,\n selectPending: (page, id) => this.selectPending(page, id),\n deselectPending: () => this.deselectPending(),\n\n registerMarqueeOnPage: (opts) => this.registerMarqueeOnPage(opts),\n };\n }\n\n private selectPending(page: number, id: string) {\n this.dispatch(selectPending(page, id));\n this.selectionCapability?.clear();\n this.selected$.emit(this.state.selected);\n }\n private deselectPending() {\n this.dispatch(deselectPending());\n this.selected$.emit(this.state.selected);\n }\n\n private enableRedactSelection() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private toggleRedactSelection() {\n if (this.interactionManagerCapability?.getActiveMode() === 'redactSelection')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('redactSelection');\n }\n\n private enableMarqueeRedact() {\n this.interactionManagerCapability?.activate('marqueeRedact');\n }\n private toggleMarqueeRedact() {\n if (this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('marqueeRedact');\n }\n\n private startRedaction() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private endRedaction() {\n this.interactionManagerCapability?.activateDefaultMode();\n }\n\n public registerMarqueeOnPage(opts: RegisterMarqueeOnPageOptions) {\n if (!this.interactionManagerCapability)\n throw new Error(\n '[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction',\n );\n\n const document = this.coreState.core.document;\n if (!document) throw new Error('[RedactionPlugin] Document not found');\n\n const page = document.pages[opts.pageIndex];\n if (!page) throw new Error('[RedactionPlugin] Page not found');\n\n const handlers = createMarqueeHandler({\n pageSize: page.size,\n scale: opts.scale,\n onPreview: opts.callback.onPreview,\n onCommit: (r) => {\n const item: RedactionItem = {\n id: uuidV4(),\n kind: 'area',\n page: opts.pageIndex,\n rect: r,\n };\n this.dispatch(addPending([item]));\n this.pending$.emit(this.state.pending);\n opts.callback.onCommit?.(r);\n this.enableRedactSelection();\n this.selectPending(opts.pageIndex, item.id);\n },\n });\n\n const off = this.interactionManagerCapability.registerAlways({\n handlers: {\n onPointerDown: (_, evt) => {\n if (evt.target === evt.currentTarget) {\n this.deselectPending();\n }\n },\n },\n scope: {\n type: 'page',\n pageIndex: opts.pageIndex,\n },\n });\n\n const off2 = this.interactionManagerCapability.registerHandlers({\n modeId: 'marqueeRedact',\n handlers,\n pageIndex: opts.pageIndex,\n });\n\n return () => {\n off();\n off2();\n };\n }\n\n private queueCurrentSelectionAsPending(): Task<boolean, PdfErrorReason> {\n if (!this.selectionCapability)\n return PdfTaskHelper.reject({\n code: PdfErrorCode.NotFound,\n message: '[RedactionPlugin] selection plugin required',\n });\n\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const formatted = this.selectionCapability.getFormattedSelection();\n if (!formatted.length) return PdfTaskHelper.resolve(true);\n\n const id = uuidV4();\n\n const items: RedactionItem[] = formatted.map((s) => ({\n id,\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.enableRedactSelection();\n this.dispatch(addPending(items));\n this.pending$.emit(this.state.pending);\n // optional: auto-select the last one added\n const last = items[items.length - 1];\n this.selectPending(last.page, last.id);\n\n // clear live UI selection\n this.redactionSelection$.emit([]);\n this.selectionCapability?.clear();\n\n return PdfTaskHelper.resolve(true);\n }\n\n private commitPendingOne(page: number, id: string): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const item = (this.state.pending[page] ?? []).find((it) => it.id === id);\n if (!item) return PdfTaskHelper.resolve(true);\n\n const rects: Rect[] = item.kind === 'text' ? item.rects : [item.rect];\n const pdfPage = doc.pages[page];\n if (!pdfPage)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Page not found' });\n\n const task = new Task<boolean, PdfErrorReason>();\n this.engine\n .redactTextInRects(doc, pdfPage, rects, {\n drawBlackBoxes: this.config.drawBlackBoxes,\n })\n .wait(\n () => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n this.dispatchCoreAction(refreshPages([page]));\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n private commitAllPending(): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n // group rects per page\n const perPage = new Map<number, Rect[]>();\n for (const [page, items] of Object.entries(this.state.pending)) {\n const p = Number(page);\n const list = perPage.get(p) ?? [];\n for (const it of items) {\n if (it.kind === 'text') list.push(...it.rects);\n else list.push(it.rect);\n }\n perPage.set(p, list);\n }\n\n const pagesToRefresh = Array.from(perPage.entries())\n .filter(([_, rects]) => rects.length > 0)\n .map(([pageIndex]) => pageIndex);\n\n const tasks: PdfTask<boolean>[] = [];\n for (const [pageIndex, rects] of perPage) {\n const page = doc.pages[pageIndex];\n if (!page) continue;\n if (!rects.length) continue;\n tasks.push(\n this.engine.redactTextInRects(doc, page, rects, {\n drawBlackBoxes: this.config.drawBlackBoxes,\n }),\n );\n }\n\n const task = new Task<boolean, PdfErrorReason>();\n Task.all(tasks).wait(\n () => {\n this.dispatch(clearPending());\n this.dispatchCoreAction(refreshPages(pagesToRefresh));\n this.pending$.emit(this.state.pending);\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n override onStoreUpdated(_: RedactionState, newState: RedactionState): void {\n // keep external listeners in sync\n this.pending$.emit(newState.pending);\n this.selected$.emit(newState.selected);\n }\n\n async destroy(): Promise<void> {\n this.redactionSelection$.clear();\n this.pending$.clear();\n\n this.unsubscribeSelectionChange?.();\n this.unsubscribeEndSelection?.();\n this.unsubscribeModeChange?.();\n\n await super.destroy();\n }\n}\n","import { Position, Rect, Size } from '@embedpdf/models';\nimport { clamp } from '@embedpdf/core';\nimport {\n EmbedPdfPointerEvent,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\n\nexport function createMarqueeHandler(opts: {\n pageSize: Size;\n scale: number;\n minDragPx?: number;\n onPreview?: (rect: Rect | null) => void;\n onCommit?: (rect: Rect) => void;\n}): PointerEventHandlersWithLifecycle<EmbedPdfPointerEvent> {\n const { pageSize, scale, minDragPx = 5, onPreview, onCommit } = opts;\n\n let start: Position | null = null;\n let last: Rect | null = null;\n\n return {\n onPointerDown: (pos, evt) => {\n start = pos;\n last = { origin: { x: pos.x, y: pos.y }, size: { width: 0, height: 0 } };\n onPreview?.(last);\n evt.setPointerCapture?.();\n },\n onPointerMove: (pos) => {\n if (!start) return;\n const x = clamp(pos.x, 0, pageSize.width);\n const y = clamp(pos.y, 0, pageSize.height);\n last = {\n origin: { x: Math.min(start.x, x), y: Math.min(start.y, y) },\n size: { width: Math.abs(x - start.x), height: Math.abs(y - start.y) },\n };\n onPreview?.(last);\n },\n onPointerUp: (_pos, evt) => {\n if (last) {\n const dragPx = Math.max(last.size.width, last.size.height) * scale;\n if (dragPx > minDragPx) onCommit?.(last);\n }\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n onPointerCancel: (_pos, evt) => {\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n };\n}\n","import { PluginManifest } from '@embedpdf/core';\nimport { RedactionPluginConfig } from './types';\n\nexport const REDACTION_PLUGIN_ID = 'redaction';\n\nexport const manifest: PluginManifest<RedactionPluginConfig> = {\n id: REDACTION_PLUGIN_ID,\n name: 'Redaction Plugin',\n version: '1.0.0',\n provides: ['redaction'],\n requires: [],\n optional: ['interaction-manager', 'selection'],\n defaultConfig: {\n enabled: true,\n drawBlackBoxes: true,\n },\n};\n","import { RedactionState } from './types';\nimport {\n RedactionAction,\n ADD_PENDING,\n CLEAR_PENDING,\n END_REDACTION,\n REMOVE_PENDING,\n START_REDACTION,\n SELECT_PENDING,\n DESELECT_PENDING,\n} from './actions';\n\nexport const initialState: RedactionState = {\n isRedacting: false,\n pending: {},\n selected: null,\n};\n\nexport const redactionReducer = (state = initialState, action: RedactionAction): RedactionState => {\n switch (action.type) {\n case ADD_PENDING: {\n const next = { ...state.pending };\n for (const item of action.payload) {\n next[item.page] = (next[item.page] ?? []).concat(item);\n }\n return { ...state, pending: next };\n }\n\n case REMOVE_PENDING: {\n const { page, id } = action.payload;\n const list = state.pending[page] ?? [];\n const filtered = list.filter((it) => it.id !== id);\n const next = { ...state.pending, [page]: filtered };\n\n // if the removed one was selected → clear selection\n const stillSelected =\n state.selected && !(state.selected.page === page && state.selected.id === id);\n\n return { ...state, pending: next, selected: stillSelected ? state.selected : null };\n }\n\n case CLEAR_PENDING:\n return { ...state, pending: {}, selected: null };\n\n case SELECT_PENDING:\n return { ...state, selected: { page: action.payload.page, id: action.payload.id } };\n\n case DESELECT_PENDING:\n return { ...state, selected: null };\n\n case START_REDACTION:\n return { ...state, isRedacting: true };\n case END_REDACTION:\n return { ...state, pending: {}, selected: null, isRedacting: false };\n default:\n return state;\n }\n};\n","import { PluginPackage } from '@embedpdf/core';\nimport { RedactionPluginConfig, RedactionState } from './types';\nimport { RedactionPlugin } from './redaction-plugin';\nimport { manifest, REDACTION_PLUGIN_ID } from './manifest';\nimport { RedactionAction } from './actions';\nimport { initialState, redactionReducer } from './reducer';\n\nexport const RedactionPluginPackage: PluginPackage<\n RedactionPlugin,\n RedactionPluginConfig,\n RedactionState,\n RedactionAction\n> = {\n manifest,\n create: (registry, config) => new RedactionPlugin(REDACTION_PLUGIN_ID, registry, config),\n reducer: redactionReducer,\n initialState: initialState,\n};\n\nexport * from './redaction-plugin';\nexport * from './types';\nexport * from './manifest';\nexport * from './selectors';\n","import { RedactionState } from './types';\n\nexport const getPendingRedactionsCount = (s: RedactionState) =>\n Object.values(s.pending).reduce((sum, list) => sum + (list?.length ?? 0), 0);\n\nexport const hasPendingRedactions = (s: RedactionState) =>\n Object.values(s.pending).some((list) => (list?.length ?? 0) > 0);\n"],"names":["START_REDACTION","END_REDACTION","ADD_PENDING","REMOVE_PENDING","CLEAR_PENDING","SELECT_PENDING","DESELECT_PENDING","addPending","items","type","payload","removePending","page","id","clearPending","_RedactionPlugin","BasePlugin","constructor","registry","config","super","this","redactionSelection$","createBehaviorEmitter","pending$","selected$","selectionCapability","_a","getPlugin","provides","interactionManagerCapability","_b","registerMode","scope","exclusive","cursor","enableForMode","unsubscribeModeChange","_c","onModeChange","state","activeMode","dispatch","unsubscribeSelectionChange","_d","onSelectionChange","isRedacting","formattedSelection","getFormattedSelection","emit","unsubscribeEndSelection","_e","onEndSelection","map","s","uuidV4","kind","pageIndex","boundingRect","rect","rects","segmentRects","clear","pending","length","selectPending","initialize","_config","buildCapability","onRedactionSelectionChange","on","queueCurrentSelectionAsPending","enableMarqueeRedact","toggleMarqueeRedact","isMarqueeRedactActive","getActiveMode","enableRedactSelection","toggleRedactSelection","isRedactSelectionActive","onPendingChange","commitAllPending","commitPending","commitPendingOne","endRedaction","startRedaction","deselectPending","registerMarqueeOnPage","opts","selected","activate","activateDefaultMode","Error","document","coreState","core","pages","handlers","pageSize","scale","minDragPx","onPreview","onCommit","start","last","onPointerDown","pos","evt","origin","x","y","size","width","height","setPointerCapture","call","onPointerMove","clamp","Math","min","abs","onPointerUp","_pos","max","releasePointerCapture","onPointerCancel","createMarqueeHandler","callback","r","item","off","registerAlways","_","target","currentTarget","off2","registerHandlers","modeId","PdfTaskHelper","reject","code","PdfErrorCode","NotFound","message","formatted","resolve","doc","find","it","pdfPage","task","Task","engine","redactTextInRects","drawBlackBoxes","wait","dispatchCoreAction","refreshPages","Unknown","perPage","Map","Object","entries","p","Number","list","get","push","set","pagesToRefresh","Array","from","filter","tasks","all","onStoreUpdated","newState","destroy","RedactionPlugin","REDACTION_PLUGIN_ID","manifest","name","version","requires","optional","defaultConfig","enabled","initialState","RedactionPluginPackage","create","reducer","action","next","concat","filtered","stillSelected","values","reduce","sum","some"],"mappings":"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"}
package/dist/index.js CHANGED
@@ -66,13 +66,12 @@ function createMarqueeHandler(opts) {
66
66
  };
67
67
  }
68
68
  const _RedactionPlugin = class _RedactionPlugin extends BasePlugin {
69
- constructor(id, registry, engine, config) {
69
+ constructor(id, registry, config) {
70
70
  var _a, _b, _c, _d, _e;
71
71
  super(id, registry);
72
72
  this.redactionSelection$ = createBehaviorEmitter();
73
73
  this.pending$ = createBehaviorEmitter();
74
74
  this.selected$ = createBehaviorEmitter();
75
- this.engine = engine;
76
75
  this.config = config;
77
76
  this.selectionCapability = (_a = this.registry.getPlugin("selection")) == null ? void 0 : _a.provides();
78
77
  this.interactionManagerCapability = (_b = this.registry.getPlugin("interaction-manager")) == null ? void 0 : _b.provides();
@@ -289,7 +288,9 @@ const _RedactionPlugin = class _RedactionPlugin extends BasePlugin {
289
288
  if (!pdfPage)
290
289
  return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: "Page not found" });
291
290
  const task = new Task();
292
- this.engine.redactTextInRects(doc, pdfPage, rects, false, this.config.blackbox).wait(
291
+ this.engine.redactTextInRects(doc, pdfPage, rects, {
292
+ drawBlackBoxes: this.config.drawBlackBoxes
293
+ }).wait(
293
294
  () => {
294
295
  this.dispatch(removePending(page, id));
295
296
  this.pending$.emit(this.state.pending);
@@ -320,7 +321,11 @@ const _RedactionPlugin = class _RedactionPlugin extends BasePlugin {
320
321
  const page = doc.pages[pageIndex];
321
322
  if (!page) continue;
322
323
  if (!rects.length) continue;
323
- tasks.push(this.engine.redactTextInRects(doc, page, rects, false, this.config.blackbox));
324
+ tasks.push(
325
+ this.engine.redactTextInRects(doc, page, rects, {
326
+ drawBlackBoxes: this.config.drawBlackBoxes
327
+ })
328
+ );
324
329
  }
325
330
  const task = new Task();
326
331
  Task.all(tasks).wait(
@@ -360,7 +365,7 @@ const manifest = {
360
365
  optional: ["interaction-manager", "selection"],
361
366
  defaultConfig: {
362
367
  enabled: true,
363
- blackbox: true
368
+ drawBlackBoxes: true
364
369
  }
365
370
  };
366
371
  const initialState = {
@@ -403,7 +408,7 @@ const getPendingRedactionsCount = (s) => Object.values(s.pending).reduce((sum, l
403
408
  const hasPendingRedactions = (s) => Object.values(s.pending).some((list) => ((list == null ? void 0 : list.length) ?? 0) > 0);
404
409
  const RedactionPluginPackage = {
405
410
  manifest,
406
- create: (registry, engine, config) => new RedactionPlugin(REDACTION_PLUGIN_ID, registry, engine, config),
411
+ create: (registry, config) => new RedactionPlugin(REDACTION_PLUGIN_ID, registry, config),
407
412
  reducer: redactionReducer,
408
413
  initialState
409
414
  };
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../src/lib/actions.ts","../src/lib/handlers/marquee-redact.handler.ts","../src/lib/redaction-plugin.ts","../src/lib/manifest.ts","../src/lib/reducer.ts","../src/lib/selectors.ts","../src/lib/index.ts"],"sourcesContent":["import { Action } from '@embedpdf/core';\nimport { RedactionItem } from './types';\n\nexport const START_REDACTION = 'START_REDACTION';\nexport const END_REDACTION = 'END_REDACTION';\n\nexport const ADD_PENDING = 'ADD_PENDING';\nexport const REMOVE_PENDING = 'REMOVE_PENDING';\nexport const CLEAR_PENDING = 'CLEAR_PENDING';\n\nexport const SELECT_PENDING = 'SELECT_PENDING';\nexport const DESELECT_PENDING = 'DESELECT_PENDING';\n\nexport interface StartRedactionAction extends Action {\n type: typeof START_REDACTION;\n}\nexport interface EndRedactionAction extends Action {\n type: typeof END_REDACTION;\n}\n\nexport interface AddPendingAction extends Action {\n type: typeof ADD_PENDING;\n payload: RedactionItem[];\n}\nexport interface RemovePendingAction extends Action {\n type: typeof REMOVE_PENDING;\n payload: { page: number; id: string };\n}\nexport interface ClearPendingAction extends Action {\n type: typeof CLEAR_PENDING;\n}\n\nexport interface SelectPendingAction extends Action {\n type: typeof SELECT_PENDING;\n payload: { page: number; id: string };\n}\nexport interface DeselectPendingAction extends Action {\n type: typeof DESELECT_PENDING;\n}\n\nexport type RedactionAction =\n | StartRedactionAction\n | EndRedactionAction\n | AddPendingAction\n | RemovePendingAction\n | ClearPendingAction\n | SelectPendingAction\n | DeselectPendingAction;\n\nexport const addPending = (items: RedactionItem[]): AddPendingAction => ({\n type: ADD_PENDING,\n payload: items,\n});\nexport const removePending = (page: number, id: string): RemovePendingAction => ({\n type: REMOVE_PENDING,\n payload: { page, id },\n});\nexport const clearPending = (): ClearPendingAction => ({ type: CLEAR_PENDING });\n\nexport const startRedaction = (): StartRedactionAction => ({ type: START_REDACTION });\nexport const endRedaction = (): EndRedactionAction => ({ type: END_REDACTION });\n\nexport const selectPending = (page: number, id: string): SelectPendingAction => ({\n type: SELECT_PENDING,\n payload: { page, id },\n});\nexport const deselectPending = (): DeselectPendingAction => ({ type: DESELECT_PENDING });\n","import { Position, Rect, Size } from '@embedpdf/models';\nimport { clamp } from '@embedpdf/core';\nimport {\n EmbedPdfPointerEvent,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\n\nexport function createMarqueeHandler(opts: {\n pageSize: Size;\n scale: number;\n minDragPx?: number;\n onPreview?: (rect: Rect | null) => void;\n onCommit?: (rect: Rect) => void;\n}): PointerEventHandlersWithLifecycle<EmbedPdfPointerEvent> {\n const { pageSize, scale, minDragPx = 5, onPreview, onCommit } = opts;\n\n let start: Position | null = null;\n let last: Rect | null = null;\n\n return {\n onPointerDown: (pos, evt) => {\n start = pos;\n last = { origin: { x: pos.x, y: pos.y }, size: { width: 0, height: 0 } };\n onPreview?.(last);\n evt.setPointerCapture?.();\n },\n onPointerMove: (pos) => {\n if (!start) return;\n const x = clamp(pos.x, 0, pageSize.width);\n const y = clamp(pos.y, 0, pageSize.height);\n last = {\n origin: { x: Math.min(start.x, x), y: Math.min(start.y, y) },\n size: { width: Math.abs(x - start.x), height: Math.abs(y - start.y) },\n };\n onPreview?.(last);\n },\n onPointerUp: (_pos, evt) => {\n if (last) {\n const dragPx = Math.max(last.size.width, last.size.height) * scale;\n if (dragPx > minDragPx) onCommit?.(last);\n }\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n onPointerCancel: (_pos, evt) => {\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n };\n}\n","import {\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState,\n RegisterMarqueeOnPageOptions,\n RedactionItem,\n SelectedRedaction,\n} from './types';\nimport {\n BasePlugin,\n createBehaviorEmitter,\n PluginRegistry,\n refreshDocument,\n refreshPages,\n Unsubscribe,\n} from '@embedpdf/core';\nimport {\n ignore,\n PdfEngine,\n PdfErrorCode,\n PdfErrorReason,\n PdfTask,\n PdfTaskHelper,\n Rect,\n Task,\n uuidV4,\n} from '@embedpdf/models';\nimport {\n FormattedSelection,\n SelectionCapability,\n SelectionPlugin,\n} from '@embedpdf/plugin-selection';\nimport {\n InteractionManagerCapability,\n InteractionManagerPlugin,\n} from '@embedpdf/plugin-interaction-manager';\nimport {\n addPending,\n clearPending,\n deselectPending,\n endRedaction,\n removePending,\n selectPending,\n startRedaction,\n} from './actions';\nimport { createMarqueeHandler } from './handlers';\n\nexport class RedactionPlugin extends BasePlugin<\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState\n> {\n static readonly id = 'redaction' as const;\n private engine: PdfEngine;\n private config: RedactionPluginConfig;\n\n private selectionCapability: SelectionCapability | undefined;\n private interactionManagerCapability: InteractionManagerCapability | undefined;\n\n private readonly redactionSelection$ = createBehaviorEmitter<FormattedSelection[]>();\n private readonly pending$ = createBehaviorEmitter<Record<number, RedactionItem[]>>();\n private readonly selected$ = createBehaviorEmitter<SelectedRedaction | null>();\n\n private readonly unsubscribeSelectionChange: Unsubscribe | undefined;\n private readonly unsubscribeEndSelection: Unsubscribe | undefined;\n private readonly unsubscribeModeChange: Unsubscribe | undefined;\n\n constructor(\n id: string,\n registry: PluginRegistry,\n engine: PdfEngine,\n config: RedactionPluginConfig,\n ) {\n super(id, registry);\n this.engine = engine;\n this.config = config;\n\n this.selectionCapability = this.registry.getPlugin<SelectionPlugin>('selection')?.provides();\n this.interactionManagerCapability = this.registry\n .getPlugin<InteractionManagerPlugin>('interaction-manager')\n ?.provides();\n\n if (this.interactionManagerCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'marqueeRedact',\n scope: 'page',\n exclusive: true,\n cursor: 'crosshair',\n });\n }\n\n if (this.interactionManagerCapability && this.selectionCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'redactSelection',\n scope: 'page',\n exclusive: false,\n });\n this.selectionCapability.enableForMode('redactSelection');\n }\n\n this.unsubscribeModeChange = this.interactionManagerCapability?.onModeChange((state) => {\n if (state.activeMode === 'redactSelection' || state.activeMode === 'marqueeRedact')\n this.dispatch(startRedaction());\n else this.dispatch(endRedaction());\n });\n\n this.unsubscribeSelectionChange = this.selectionCapability?.onSelectionChange(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n this.redactionSelection$.emit(formattedSelection);\n });\n\n this.unsubscribeEndSelection = this.selectionCapability?.onEndSelection(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n\n const items: RedactionItem[] = formattedSelection.map((s) => ({\n id: uuidV4(),\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.dispatch(addPending(items));\n this.redactionSelection$.emit([]);\n this.selectionCapability.clear();\n this.pending$.emit(this.state.pending);\n if (items.length) {\n this.selectPending(items[items.length - 1].page, items[items.length - 1].id);\n }\n });\n }\n\n async initialize(_config: RedactionPluginConfig): Promise<void> {}\n\n protected buildCapability(): RedactionCapability {\n return {\n onRedactionSelectionChange: this.redactionSelection$.on,\n\n queueCurrentSelectionAsPending: () => this.queueCurrentSelectionAsPending(),\n\n enableMarqueeRedact: () => this.enableMarqueeRedact(),\n toggleMarqueeRedact: () => this.toggleMarqueeRedact(),\n isMarqueeRedactActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact',\n\n enableRedactSelection: () => this.enableRedactSelection(),\n toggleRedactSelection: () => this.toggleRedactSelection(),\n isRedactSelectionActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'redactSelection',\n\n onPendingChange: this.pending$.on,\n removePending: (page, id) => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n },\n clearPending: () => {\n this.dispatch(clearPending());\n this.pending$.emit(this.state.pending);\n },\n commitAllPending: () => this.commitAllPending(),\n commitPending: (page, id) => this.commitPendingOne(page, id),\n\n endRedaction: () => this.endRedaction(),\n startRedaction: () => this.startRedaction(),\n\n onSelectionChange: this.selected$.on,\n selectPending: (page, id) => this.selectPending(page, id),\n deselectPending: () => this.deselectPending(),\n\n registerMarqueeOnPage: (opts) => this.registerMarqueeOnPage(opts),\n };\n }\n\n private selectPending(page: number, id: string) {\n this.dispatch(selectPending(page, id));\n this.selectionCapability?.clear();\n this.selected$.emit(this.state.selected);\n }\n private deselectPending() {\n this.dispatch(deselectPending());\n this.selected$.emit(this.state.selected);\n }\n\n private enableRedactSelection() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private toggleRedactSelection() {\n if (this.interactionManagerCapability?.getActiveMode() === 'redactSelection')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('redactSelection');\n }\n\n private enableMarqueeRedact() {\n this.interactionManagerCapability?.activate('marqueeRedact');\n }\n private toggleMarqueeRedact() {\n if (this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('marqueeRedact');\n }\n\n private startRedaction() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private endRedaction() {\n this.interactionManagerCapability?.activateDefaultMode();\n }\n\n public registerMarqueeOnPage(opts: RegisterMarqueeOnPageOptions) {\n if (!this.interactionManagerCapability)\n throw new Error(\n '[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction',\n );\n\n const document = this.coreState.core.document;\n if (!document) throw new Error('[RedactionPlugin] Document not found');\n\n const page = document.pages[opts.pageIndex];\n if (!page) throw new Error('[RedactionPlugin] Page not found');\n\n const handlers = createMarqueeHandler({\n pageSize: page.size,\n scale: opts.scale,\n onPreview: opts.callback.onPreview,\n onCommit: (r) => {\n const item: RedactionItem = {\n id: uuidV4(),\n kind: 'area',\n page: opts.pageIndex,\n rect: r,\n };\n this.dispatch(addPending([item]));\n this.pending$.emit(this.state.pending);\n opts.callback.onCommit?.(r);\n this.enableRedactSelection();\n this.selectPending(opts.pageIndex, item.id);\n },\n });\n\n const off = this.interactionManagerCapability.registerAlways({\n handlers: {\n onPointerDown: (_, evt) => {\n if (evt.target === evt.currentTarget) {\n this.deselectPending();\n }\n },\n },\n scope: {\n type: 'page',\n pageIndex: opts.pageIndex,\n },\n });\n\n const off2 = this.interactionManagerCapability.registerHandlers({\n modeId: 'marqueeRedact',\n handlers,\n pageIndex: opts.pageIndex,\n });\n\n return () => {\n off();\n off2();\n };\n }\n\n private queueCurrentSelectionAsPending(): Task<boolean, PdfErrorReason> {\n if (!this.selectionCapability)\n return PdfTaskHelper.reject({\n code: PdfErrorCode.NotFound,\n message: '[RedactionPlugin] selection plugin required',\n });\n\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const formatted = this.selectionCapability.getFormattedSelection();\n if (!formatted.length) return PdfTaskHelper.resolve(true);\n\n const id = uuidV4();\n\n const items: RedactionItem[] = formatted.map((s) => ({\n id,\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.enableRedactSelection();\n this.dispatch(addPending(items));\n this.pending$.emit(this.state.pending);\n // optional: auto-select the last one added\n const last = items[items.length - 1];\n this.selectPending(last.page, last.id);\n\n // clear live UI selection\n this.redactionSelection$.emit([]);\n this.selectionCapability?.clear();\n\n return PdfTaskHelper.resolve(true);\n }\n\n private commitPendingOne(page: number, id: string): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const item = (this.state.pending[page] ?? []).find((it) => it.id === id);\n if (!item) return PdfTaskHelper.resolve(true);\n\n const rects: Rect[] = item.kind === 'text' ? item.rects : [item.rect];\n const pdfPage = doc.pages[page];\n if (!pdfPage)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Page not found' });\n\n const task = new Task<boolean, PdfErrorReason>();\n this.engine.redactTextInRects(doc, pdfPage, rects, false, this.config.blackbox).wait(\n () => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n this.dispatchCoreAction(refreshPages([page]));\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n private commitAllPending(): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n // group rects per page\n const perPage = new Map<number, Rect[]>();\n for (const [page, items] of Object.entries(this.state.pending)) {\n const p = Number(page);\n const list = perPage.get(p) ?? [];\n for (const it of items) {\n if (it.kind === 'text') list.push(...it.rects);\n else list.push(it.rect);\n }\n perPage.set(p, list);\n }\n\n const pagesToRefresh = Array.from(perPage.entries())\n .filter(([_, rects]) => rects.length > 0)\n .map(([pageIndex]) => pageIndex);\n\n const tasks: PdfTask<boolean>[] = [];\n for (const [pageIndex, rects] of perPage) {\n const page = doc.pages[pageIndex];\n if (!page) continue;\n if (!rects.length) continue;\n tasks.push(this.engine.redactTextInRects(doc, page, rects, false, this.config.blackbox));\n }\n\n const task = new Task<boolean, PdfErrorReason>();\n Task.all(tasks).wait(\n () => {\n this.dispatch(clearPending());\n this.dispatchCoreAction(refreshPages(pagesToRefresh));\n this.pending$.emit(this.state.pending);\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n override onStoreUpdated(_: RedactionState, newState: RedactionState): void {\n // keep external listeners in sync\n this.pending$.emit(newState.pending);\n this.selected$.emit(newState.selected);\n }\n\n async destroy(): Promise<void> {\n this.redactionSelection$.clear();\n this.pending$.clear();\n\n this.unsubscribeSelectionChange?.();\n this.unsubscribeEndSelection?.();\n this.unsubscribeModeChange?.();\n\n await super.destroy();\n }\n}\n","import { PluginManifest } from '@embedpdf/core';\nimport { RedactionPluginConfig } from './types';\n\nexport const REDACTION_PLUGIN_ID = 'redaction';\n\nexport const manifest: PluginManifest<RedactionPluginConfig> = {\n id: REDACTION_PLUGIN_ID,\n name: 'Redaction Plugin',\n version: '1.0.0',\n provides: ['redaction'],\n requires: [],\n optional: ['interaction-manager', 'selection'],\n defaultConfig: {\n enabled: true,\n blackbox: true,\n },\n};\n","import { RedactionState } from './types';\nimport {\n RedactionAction,\n ADD_PENDING,\n CLEAR_PENDING,\n END_REDACTION,\n REMOVE_PENDING,\n START_REDACTION,\n SELECT_PENDING,\n DESELECT_PENDING,\n} from './actions';\n\nexport const initialState: RedactionState = {\n isRedacting: false,\n pending: {},\n selected: null,\n};\n\nexport const redactionReducer = (state = initialState, action: RedactionAction): RedactionState => {\n switch (action.type) {\n case ADD_PENDING: {\n const next = { ...state.pending };\n for (const item of action.payload) {\n next[item.page] = (next[item.page] ?? []).concat(item);\n }\n return { ...state, pending: next };\n }\n\n case REMOVE_PENDING: {\n const { page, id } = action.payload;\n const list = state.pending[page] ?? [];\n const filtered = list.filter((it) => it.id !== id);\n const next = { ...state.pending, [page]: filtered };\n\n // if the removed one was selected → clear selection\n const stillSelected =\n state.selected && !(state.selected.page === page && state.selected.id === id);\n\n return { ...state, pending: next, selected: stillSelected ? state.selected : null };\n }\n\n case CLEAR_PENDING:\n return { ...state, pending: {}, selected: null };\n\n case SELECT_PENDING:\n return { ...state, selected: { page: action.payload.page, id: action.payload.id } };\n\n case DESELECT_PENDING:\n return { ...state, selected: null };\n\n case START_REDACTION:\n return { ...state, isRedacting: true };\n case END_REDACTION:\n return { ...state, pending: {}, selected: null, isRedacting: false };\n default:\n return state;\n }\n};\n","import { RedactionState } from './types';\n\nexport const getPendingRedactionsCount = (s: RedactionState) =>\n Object.values(s.pending).reduce((sum, list) => sum + (list?.length ?? 0), 0);\n\nexport const hasPendingRedactions = (s: RedactionState) =>\n Object.values(s.pending).some((list) => (list?.length ?? 0) > 0);\n","import { PluginPackage } from '@embedpdf/core';\nimport { RedactionPluginConfig, RedactionState } from './types';\nimport { RedactionPlugin } from './redaction-plugin';\nimport { manifest, REDACTION_PLUGIN_ID } from './manifest';\nimport { RedactionAction } from './actions';\nimport { initialState, redactionReducer } from './reducer';\n\nexport const RedactionPluginPackage: PluginPackage<\n RedactionPlugin,\n RedactionPluginConfig,\n RedactionState,\n RedactionAction\n> = {\n manifest,\n create: (registry, engine, config) =>\n new RedactionPlugin(REDACTION_PLUGIN_ID, registry, engine, config),\n reducer: redactionReducer,\n initialState: initialState,\n};\n\nexport * from './redaction-plugin';\nexport * from './types';\nexport * from './manifest';\nexport * from './selectors';\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sources":["../src/lib/actions.ts","../src/lib/handlers/marquee-redact.handler.ts","../src/lib/redaction-plugin.ts","../src/lib/manifest.ts","../src/lib/reducer.ts","../src/lib/selectors.ts","../src/lib/index.ts"],"sourcesContent":["import { Action } from '@embedpdf/core';\nimport { RedactionItem } from './types';\n\nexport const START_REDACTION = 'START_REDACTION';\nexport const END_REDACTION = 'END_REDACTION';\n\nexport const ADD_PENDING = 'ADD_PENDING';\nexport const REMOVE_PENDING = 'REMOVE_PENDING';\nexport const CLEAR_PENDING = 'CLEAR_PENDING';\n\nexport const SELECT_PENDING = 'SELECT_PENDING';\nexport const DESELECT_PENDING = 'DESELECT_PENDING';\n\nexport interface StartRedactionAction extends Action {\n type: typeof START_REDACTION;\n}\nexport interface EndRedactionAction extends Action {\n type: typeof END_REDACTION;\n}\n\nexport interface AddPendingAction extends Action {\n type: typeof ADD_PENDING;\n payload: RedactionItem[];\n}\nexport interface RemovePendingAction extends Action {\n type: typeof REMOVE_PENDING;\n payload: { page: number; id: string };\n}\nexport interface ClearPendingAction extends Action {\n type: typeof CLEAR_PENDING;\n}\n\nexport interface SelectPendingAction extends Action {\n type: typeof SELECT_PENDING;\n payload: { page: number; id: string };\n}\nexport interface DeselectPendingAction extends Action {\n type: typeof DESELECT_PENDING;\n}\n\nexport type RedactionAction =\n | StartRedactionAction\n | EndRedactionAction\n | AddPendingAction\n | RemovePendingAction\n | ClearPendingAction\n | SelectPendingAction\n | DeselectPendingAction;\n\nexport const addPending = (items: RedactionItem[]): AddPendingAction => ({\n type: ADD_PENDING,\n payload: items,\n});\nexport const removePending = (page: number, id: string): RemovePendingAction => ({\n type: REMOVE_PENDING,\n payload: { page, id },\n});\nexport const clearPending = (): ClearPendingAction => ({ type: CLEAR_PENDING });\n\nexport const startRedaction = (): StartRedactionAction => ({ type: START_REDACTION });\nexport const endRedaction = (): EndRedactionAction => ({ type: END_REDACTION });\n\nexport const selectPending = (page: number, id: string): SelectPendingAction => ({\n type: SELECT_PENDING,\n payload: { page, id },\n});\nexport const deselectPending = (): DeselectPendingAction => ({ type: DESELECT_PENDING });\n","import { Position, Rect, Size } from '@embedpdf/models';\nimport { clamp } from '@embedpdf/core';\nimport {\n EmbedPdfPointerEvent,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\n\nexport function createMarqueeHandler(opts: {\n pageSize: Size;\n scale: number;\n minDragPx?: number;\n onPreview?: (rect: Rect | null) => void;\n onCommit?: (rect: Rect) => void;\n}): PointerEventHandlersWithLifecycle<EmbedPdfPointerEvent> {\n const { pageSize, scale, minDragPx = 5, onPreview, onCommit } = opts;\n\n let start: Position | null = null;\n let last: Rect | null = null;\n\n return {\n onPointerDown: (pos, evt) => {\n start = pos;\n last = { origin: { x: pos.x, y: pos.y }, size: { width: 0, height: 0 } };\n onPreview?.(last);\n evt.setPointerCapture?.();\n },\n onPointerMove: (pos) => {\n if (!start) return;\n const x = clamp(pos.x, 0, pageSize.width);\n const y = clamp(pos.y, 0, pageSize.height);\n last = {\n origin: { x: Math.min(start.x, x), y: Math.min(start.y, y) },\n size: { width: Math.abs(x - start.x), height: Math.abs(y - start.y) },\n };\n onPreview?.(last);\n },\n onPointerUp: (_pos, evt) => {\n if (last) {\n const dragPx = Math.max(last.size.width, last.size.height) * scale;\n if (dragPx > minDragPx) onCommit?.(last);\n }\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n onPointerCancel: (_pos, evt) => {\n start = null;\n last = null;\n onPreview?.(null);\n evt.releasePointerCapture?.();\n },\n };\n}\n","import {\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState,\n RegisterMarqueeOnPageOptions,\n RedactionItem,\n SelectedRedaction,\n} from './types';\nimport {\n BasePlugin,\n createBehaviorEmitter,\n PluginRegistry,\n refreshDocument,\n refreshPages,\n Unsubscribe,\n} from '@embedpdf/core';\nimport {\n ignore,\n PdfEngine,\n PdfErrorCode,\n PdfErrorReason,\n PdfTask,\n PdfTaskHelper,\n Rect,\n Task,\n uuidV4,\n} from '@embedpdf/models';\nimport {\n FormattedSelection,\n SelectionCapability,\n SelectionPlugin,\n} from '@embedpdf/plugin-selection';\nimport {\n InteractionManagerCapability,\n InteractionManagerPlugin,\n} from '@embedpdf/plugin-interaction-manager';\nimport {\n addPending,\n clearPending,\n deselectPending,\n endRedaction,\n removePending,\n selectPending,\n startRedaction,\n} from './actions';\nimport { createMarqueeHandler } from './handlers';\n\nexport class RedactionPlugin extends BasePlugin<\n RedactionPluginConfig,\n RedactionCapability,\n RedactionState\n> {\n static readonly id = 'redaction' as const;\n private config: RedactionPluginConfig;\n\n private selectionCapability: SelectionCapability | undefined;\n private interactionManagerCapability: InteractionManagerCapability | undefined;\n\n private readonly redactionSelection$ = createBehaviorEmitter<FormattedSelection[]>();\n private readonly pending$ = createBehaviorEmitter<Record<number, RedactionItem[]>>();\n private readonly selected$ = createBehaviorEmitter<SelectedRedaction | null>();\n\n private readonly unsubscribeSelectionChange: Unsubscribe | undefined;\n private readonly unsubscribeEndSelection: Unsubscribe | undefined;\n private readonly unsubscribeModeChange: Unsubscribe | undefined;\n\n constructor(id: string, registry: PluginRegistry, config: RedactionPluginConfig) {\n super(id, registry);\n this.config = config;\n\n this.selectionCapability = this.registry.getPlugin<SelectionPlugin>('selection')?.provides();\n this.interactionManagerCapability = this.registry\n .getPlugin<InteractionManagerPlugin>('interaction-manager')\n ?.provides();\n\n if (this.interactionManagerCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'marqueeRedact',\n scope: 'page',\n exclusive: true,\n cursor: 'crosshair',\n });\n }\n\n if (this.interactionManagerCapability && this.selectionCapability) {\n this.interactionManagerCapability.registerMode({\n id: 'redactSelection',\n scope: 'page',\n exclusive: false,\n });\n this.selectionCapability.enableForMode('redactSelection');\n }\n\n this.unsubscribeModeChange = this.interactionManagerCapability?.onModeChange((state) => {\n if (state.activeMode === 'redactSelection' || state.activeMode === 'marqueeRedact')\n this.dispatch(startRedaction());\n else this.dispatch(endRedaction());\n });\n\n this.unsubscribeSelectionChange = this.selectionCapability?.onSelectionChange(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n this.redactionSelection$.emit(formattedSelection);\n });\n\n this.unsubscribeEndSelection = this.selectionCapability?.onEndSelection(() => {\n if (!this.selectionCapability) return;\n if (!this.state.isRedacting) return;\n\n const formattedSelection = this.selectionCapability.getFormattedSelection();\n\n const items: RedactionItem[] = formattedSelection.map((s) => ({\n id: uuidV4(),\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.dispatch(addPending(items));\n this.redactionSelection$.emit([]);\n this.selectionCapability.clear();\n this.pending$.emit(this.state.pending);\n if (items.length) {\n this.selectPending(items[items.length - 1].page, items[items.length - 1].id);\n }\n });\n }\n\n async initialize(_config: RedactionPluginConfig): Promise<void> {}\n\n protected buildCapability(): RedactionCapability {\n return {\n onRedactionSelectionChange: this.redactionSelection$.on,\n\n queueCurrentSelectionAsPending: () => this.queueCurrentSelectionAsPending(),\n\n enableMarqueeRedact: () => this.enableMarqueeRedact(),\n toggleMarqueeRedact: () => this.toggleMarqueeRedact(),\n isMarqueeRedactActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact',\n\n enableRedactSelection: () => this.enableRedactSelection(),\n toggleRedactSelection: () => this.toggleRedactSelection(),\n isRedactSelectionActive: () =>\n this.interactionManagerCapability?.getActiveMode() === 'redactSelection',\n\n onPendingChange: this.pending$.on,\n removePending: (page, id) => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n },\n clearPending: () => {\n this.dispatch(clearPending());\n this.pending$.emit(this.state.pending);\n },\n commitAllPending: () => this.commitAllPending(),\n commitPending: (page, id) => this.commitPendingOne(page, id),\n\n endRedaction: () => this.endRedaction(),\n startRedaction: () => this.startRedaction(),\n\n onSelectionChange: this.selected$.on,\n selectPending: (page, id) => this.selectPending(page, id),\n deselectPending: () => this.deselectPending(),\n\n registerMarqueeOnPage: (opts) => this.registerMarqueeOnPage(opts),\n };\n }\n\n private selectPending(page: number, id: string) {\n this.dispatch(selectPending(page, id));\n this.selectionCapability?.clear();\n this.selected$.emit(this.state.selected);\n }\n private deselectPending() {\n this.dispatch(deselectPending());\n this.selected$.emit(this.state.selected);\n }\n\n private enableRedactSelection() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private toggleRedactSelection() {\n if (this.interactionManagerCapability?.getActiveMode() === 'redactSelection')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('redactSelection');\n }\n\n private enableMarqueeRedact() {\n this.interactionManagerCapability?.activate('marqueeRedact');\n }\n private toggleMarqueeRedact() {\n if (this.interactionManagerCapability?.getActiveMode() === 'marqueeRedact')\n this.interactionManagerCapability?.activateDefaultMode();\n else this.interactionManagerCapability?.activate('marqueeRedact');\n }\n\n private startRedaction() {\n this.interactionManagerCapability?.activate('redactSelection');\n }\n private endRedaction() {\n this.interactionManagerCapability?.activateDefaultMode();\n }\n\n public registerMarqueeOnPage(opts: RegisterMarqueeOnPageOptions) {\n if (!this.interactionManagerCapability)\n throw new Error(\n '[RedactionPlugin] Make sure the interaction-manager plugin is loaded, if you want to use marquee redaction',\n );\n\n const document = this.coreState.core.document;\n if (!document) throw new Error('[RedactionPlugin] Document not found');\n\n const page = document.pages[opts.pageIndex];\n if (!page) throw new Error('[RedactionPlugin] Page not found');\n\n const handlers = createMarqueeHandler({\n pageSize: page.size,\n scale: opts.scale,\n onPreview: opts.callback.onPreview,\n onCommit: (r) => {\n const item: RedactionItem = {\n id: uuidV4(),\n kind: 'area',\n page: opts.pageIndex,\n rect: r,\n };\n this.dispatch(addPending([item]));\n this.pending$.emit(this.state.pending);\n opts.callback.onCommit?.(r);\n this.enableRedactSelection();\n this.selectPending(opts.pageIndex, item.id);\n },\n });\n\n const off = this.interactionManagerCapability.registerAlways({\n handlers: {\n onPointerDown: (_, evt) => {\n if (evt.target === evt.currentTarget) {\n this.deselectPending();\n }\n },\n },\n scope: {\n type: 'page',\n pageIndex: opts.pageIndex,\n },\n });\n\n const off2 = this.interactionManagerCapability.registerHandlers({\n modeId: 'marqueeRedact',\n handlers,\n pageIndex: opts.pageIndex,\n });\n\n return () => {\n off();\n off2();\n };\n }\n\n private queueCurrentSelectionAsPending(): Task<boolean, PdfErrorReason> {\n if (!this.selectionCapability)\n return PdfTaskHelper.reject({\n code: PdfErrorCode.NotFound,\n message: '[RedactionPlugin] selection plugin required',\n });\n\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const formatted = this.selectionCapability.getFormattedSelection();\n if (!formatted.length) return PdfTaskHelper.resolve(true);\n\n const id = uuidV4();\n\n const items: RedactionItem[] = formatted.map((s) => ({\n id,\n kind: 'text',\n page: s.pageIndex,\n boundingRect: s.rect,\n rects: s.segmentRects,\n }));\n\n this.enableRedactSelection();\n this.dispatch(addPending(items));\n this.pending$.emit(this.state.pending);\n // optional: auto-select the last one added\n const last = items[items.length - 1];\n this.selectPending(last.page, last.id);\n\n // clear live UI selection\n this.redactionSelection$.emit([]);\n this.selectionCapability?.clear();\n\n return PdfTaskHelper.resolve(true);\n }\n\n private commitPendingOne(page: number, id: string): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n const item = (this.state.pending[page] ?? []).find((it) => it.id === id);\n if (!item) return PdfTaskHelper.resolve(true);\n\n const rects: Rect[] = item.kind === 'text' ? item.rects : [item.rect];\n const pdfPage = doc.pages[page];\n if (!pdfPage)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Page not found' });\n\n const task = new Task<boolean, PdfErrorReason>();\n this.engine\n .redactTextInRects(doc, pdfPage, rects, {\n drawBlackBoxes: this.config.drawBlackBoxes,\n })\n .wait(\n () => {\n this.dispatch(removePending(page, id));\n this.pending$.emit(this.state.pending);\n this.dispatchCoreAction(refreshPages([page]));\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n private commitAllPending(): Task<boolean, PdfErrorReason> {\n const doc = this.coreState.core.document;\n if (!doc)\n return PdfTaskHelper.reject({ code: PdfErrorCode.NotFound, message: 'Document not found' });\n\n // group rects per page\n const perPage = new Map<number, Rect[]>();\n for (const [page, items] of Object.entries(this.state.pending)) {\n const p = Number(page);\n const list = perPage.get(p) ?? [];\n for (const it of items) {\n if (it.kind === 'text') list.push(...it.rects);\n else list.push(it.rect);\n }\n perPage.set(p, list);\n }\n\n const pagesToRefresh = Array.from(perPage.entries())\n .filter(([_, rects]) => rects.length > 0)\n .map(([pageIndex]) => pageIndex);\n\n const tasks: PdfTask<boolean>[] = [];\n for (const [pageIndex, rects] of perPage) {\n const page = doc.pages[pageIndex];\n if (!page) continue;\n if (!rects.length) continue;\n tasks.push(\n this.engine.redactTextInRects(doc, page, rects, {\n drawBlackBoxes: this.config.drawBlackBoxes,\n }),\n );\n }\n\n const task = new Task<boolean, PdfErrorReason>();\n Task.all(tasks).wait(\n () => {\n this.dispatch(clearPending());\n this.dispatchCoreAction(refreshPages(pagesToRefresh));\n this.pending$.emit(this.state.pending);\n task.resolve(true);\n },\n () => task.reject({ code: PdfErrorCode.Unknown, message: 'Failed to commit redactions' }),\n );\n\n return task;\n }\n\n override onStoreUpdated(_: RedactionState, newState: RedactionState): void {\n // keep external listeners in sync\n this.pending$.emit(newState.pending);\n this.selected$.emit(newState.selected);\n }\n\n async destroy(): Promise<void> {\n this.redactionSelection$.clear();\n this.pending$.clear();\n\n this.unsubscribeSelectionChange?.();\n this.unsubscribeEndSelection?.();\n this.unsubscribeModeChange?.();\n\n await super.destroy();\n }\n}\n","import { PluginManifest } from '@embedpdf/core';\nimport { RedactionPluginConfig } from './types';\n\nexport const REDACTION_PLUGIN_ID = 'redaction';\n\nexport const manifest: PluginManifest<RedactionPluginConfig> = {\n id: REDACTION_PLUGIN_ID,\n name: 'Redaction Plugin',\n version: '1.0.0',\n provides: ['redaction'],\n requires: [],\n optional: ['interaction-manager', 'selection'],\n defaultConfig: {\n enabled: true,\n drawBlackBoxes: true,\n },\n};\n","import { RedactionState } from './types';\nimport {\n RedactionAction,\n ADD_PENDING,\n CLEAR_PENDING,\n END_REDACTION,\n REMOVE_PENDING,\n START_REDACTION,\n SELECT_PENDING,\n DESELECT_PENDING,\n} from './actions';\n\nexport const initialState: RedactionState = {\n isRedacting: false,\n pending: {},\n selected: null,\n};\n\nexport const redactionReducer = (state = initialState, action: RedactionAction): RedactionState => {\n switch (action.type) {\n case ADD_PENDING: {\n const next = { ...state.pending };\n for (const item of action.payload) {\n next[item.page] = (next[item.page] ?? []).concat(item);\n }\n return { ...state, pending: next };\n }\n\n case REMOVE_PENDING: {\n const { page, id } = action.payload;\n const list = state.pending[page] ?? [];\n const filtered = list.filter((it) => it.id !== id);\n const next = { ...state.pending, [page]: filtered };\n\n // if the removed one was selected → clear selection\n const stillSelected =\n state.selected && !(state.selected.page === page && state.selected.id === id);\n\n return { ...state, pending: next, selected: stillSelected ? state.selected : null };\n }\n\n case CLEAR_PENDING:\n return { ...state, pending: {}, selected: null };\n\n case SELECT_PENDING:\n return { ...state, selected: { page: action.payload.page, id: action.payload.id } };\n\n case DESELECT_PENDING:\n return { ...state, selected: null };\n\n case START_REDACTION:\n return { ...state, isRedacting: true };\n case END_REDACTION:\n return { ...state, pending: {}, selected: null, isRedacting: false };\n default:\n return state;\n }\n};\n","import { RedactionState } from './types';\n\nexport const getPendingRedactionsCount = (s: RedactionState) =>\n Object.values(s.pending).reduce((sum, list) => sum + (list?.length ?? 0), 0);\n\nexport const hasPendingRedactions = (s: RedactionState) =>\n Object.values(s.pending).some((list) => (list?.length ?? 0) > 0);\n","import { PluginPackage } from '@embedpdf/core';\nimport { RedactionPluginConfig, RedactionState } from './types';\nimport { RedactionPlugin } from './redaction-plugin';\nimport { manifest, REDACTION_PLUGIN_ID } from './manifest';\nimport { RedactionAction } from './actions';\nimport { initialState, redactionReducer } from './reducer';\n\nexport const RedactionPluginPackage: PluginPackage<\n RedactionPlugin,\n RedactionPluginConfig,\n RedactionState,\n RedactionAction\n> = {\n manifest,\n create: (registry, config) => new RedactionPlugin(REDACTION_PLUGIN_ID, registry, config),\n reducer: redactionReducer,\n initialState: initialState,\n};\n\nexport * from './redaction-plugin';\nexport * from './types';\nexport * from './manifest';\nexport * from './selectors';\n"],"names":[],"mappings":"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"}
@@ -1,9 +1,7 @@
1
1
  import { RedactionPluginConfig, RedactionCapability, RedactionState, RegisterMarqueeOnPageOptions } from './types';
2
2
  import { BasePlugin, PluginRegistry } from '@embedpdf/core';
3
- import { PdfEngine } from '@embedpdf/models';
4
3
  export declare class RedactionPlugin extends BasePlugin<RedactionPluginConfig, RedactionCapability, RedactionState> {
5
4
  static readonly id: "redaction";
6
- private engine;
7
5
  private config;
8
6
  private selectionCapability;
9
7
  private interactionManagerCapability;
@@ -13,7 +11,7 @@ export declare class RedactionPlugin extends BasePlugin<RedactionPluginConfig, R
13
11
  private readonly unsubscribeSelectionChange;
14
12
  private readonly unsubscribeEndSelection;
15
13
  private readonly unsubscribeModeChange;
16
- constructor(id: string, registry: PluginRegistry, engine: PdfEngine, config: RedactionPluginConfig);
14
+ constructor(id: string, registry: PluginRegistry, config: RedactionPluginConfig);
17
15
  initialize(_config: RedactionPluginConfig): Promise<void>;
18
16
  protected buildCapability(): RedactionCapability;
19
17
  private selectPending;
@@ -32,7 +32,7 @@ export interface RegisterMarqueeOnPageOptions {
32
32
  callback: MarqueeRedactCallback;
33
33
  }
34
34
  export interface RedactionPluginConfig extends BasePluginConfig {
35
- blackbox: boolean;
35
+ drawBlackBoxes: boolean;
36
36
  }
37
37
  export interface RedactionCapability {
38
38
  queueCurrentSelectionAsPending: () => Task<boolean, PdfErrorReason>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@embedpdf/plugin-redaction",
3
- "version": "1.0.18",
3
+ "version": "1.0.19",
4
4
  "type": "module",
5
5
  "main": "./dist/index.cjs",
6
6
  "module": "./dist/index.js",
@@ -23,24 +23,24 @@
23
23
  }
24
24
  },
25
25
  "dependencies": {
26
- "@embedpdf/models": "1.0.18"
26
+ "@embedpdf/models": "1.0.19"
27
27
  },
28
28
  "devDependencies": {
29
29
  "@types/react": "^18.2.0",
30
30
  "typescript": "^5.0.0",
31
31
  "@embedpdf/build": "1.0.0",
32
- "@embedpdf/plugin-selection": "1.0.18",
33
- "@embedpdf/core": "1.0.18",
34
- "@embedpdf/plugin-interaction-manager": "1.0.18"
32
+ "@embedpdf/core": "1.0.19",
33
+ "@embedpdf/plugin-selection": "1.0.19",
34
+ "@embedpdf/plugin-interaction-manager": "1.0.19"
35
35
  },
36
36
  "peerDependencies": {
37
37
  "preact": "^10.26.4",
38
38
  "react": ">=16.8.0",
39
39
  "react-dom": ">=16.8.0",
40
40
  "vue": ">=3.2.0",
41
- "@embedpdf/core": "1.0.18",
42
- "@embedpdf/plugin-interaction-manager": "1.0.18",
43
- "@embedpdf/plugin-selection": "1.0.18"
41
+ "@embedpdf/core": "1.0.19",
42
+ "@embedpdf/plugin-selection": "1.0.19",
43
+ "@embedpdf/plugin-interaction-manager": "1.0.19"
44
44
  },
45
45
  "files": [
46
46
  "dist",