Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 11 additions & 11 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,24 +42,24 @@ Please star ⭐ the repo to support us! 😀

### Introduction

Welcome to OpenSign, the premier open-source docusign alternative - document e-signing solution designed to provide a secure, reliable, and free alternative to commercial platforms like DocuSign, PandaDoc, SignNow, Adobe Sign, Smartwaiver, SignRequest, HelloSign & Zoho sign. Developed under the OpenSignLabs organization, our mission is to democratize the e-signing process, making it accessible and straightforward for everyone.
Welcome to OpenSign, the premier open source docusign alternative - document e-signing solution designed to provide a secure, reliable and free alternative to commercial esign platforms like DocuSign, PandaDoc, SignNow, Adobe Sign, Smartwaiver, SignRequest, HelloSign & Zoho sign. Our mission is to democratize the e-signing process, making it accessible and straightforward for everyone.

---

### Features

- **Secure PDF E-Signing:** With the help of Robust encryption algorithms, OpenSign™ ensures maximum security, privacy & compatibility.
- **Annotate Documents:** OpenSign™ allows you to annotate PDF documents with an advanced signing pad that comes with hand drawn signatures support as well as uploaded images & saved signatures for the simplest signing experience.
- **User-Friendly Interface:** OpenSign™ was built while keeping Intuitive design in mind for ease of use. Features like "Sign yourself", "One click signatures" and "OpenSign Drive" makes it stand out of the crowd and even makes it better than a lot of so-called industry leaders.
- **Multi-signer Support:** OpenSign's ability to invite multiple signers for signing along with the ability to invite witnesses & being able to enforce signing in a sequence makes it the only open source solution that is fully loaded and allows it to compete head-to-head with established players.
- **Secure PDF E-Signing:** With the help of robust encryption algorithms, OpenSign™ ensures maximum security, privacy & compatibility.
- **Annotate Documents:** OpenSign™ allows you to annotate PDF documents with an advanced signing pad that allows hand drawn signatures, uploaded images, typed signatures & saved signatures for the simplest signing experience ever.
- **User-Friendly Interface:** OpenSign™ was built while keeping Intuitive design in mind for ease of use. Features like "Sign yourself", "Templates", "One click signatures" and "OpenSign Drive" makes it stand out of the crowd and even makes it better than a lot of so-called industry leaders.
- **Multi-signer Support:** OpenSign's ability to invite multiple signers for signing along with the ability to invite witnesses & being able to enforce signing in a sequence makes it the only open source solution that is fully loaded and allows it to compete head-to-head with established players in e-signature space.
- **Email Unique Code(OTP) verification support for guest signers:** With OpenSign™, your documents are fully secure even when being signed by guest users. Guest signers can only sign the document after entering a unique code sent to their email address. 
- **"Expiring Docs" & "Rejection":** You can set documents to expire after certain number of days after which nobody will be able to sign it. Not just this, OpenSign also allows signers to reject signing a document.
- **"Expiring Docs" & "Rejection":** You can set documents to expire after certain number of days after which nobody will be able to sign. Not just this, OpenSign also allows signers to reject signing a document.
- **Beautiful email templates:** All document signing invitations, completion notifications & reminders are formatted using great looking email templates.
- **PDF Template Creation(coming soon):** OpenSign™ allows you to create and store PDF document templates for repeated use thereby saving you a lot of time.
- **OpenSign™ Drive:** It is a centralised secure vault for your signed documents that makes storing, signing, organizing, sharing & achieving your docs a breeze.
- **PDF Template Creation:** OpenSign™ allows you to create and store PDF document templates for repeated use thereby saving you a lot of time & collect e-signatures seamlessly.
- **OpenSign™ Drive:** It is a centralised secure vault for your digital documents that makes storing, signing, organizing, sharing & achieving your docs a breeze.
- **Audit Trails & completion certificate:** Being a security focused solution, OpenSign™ makes it a top priority to save detailed logs for tracking document activities along with time-stamps, IP addresses, email IDs & phone numbers. A completion certificate is generated as soon as document is completed which contains all the document related logs for added safety.
- **API Support(coming soon):** OpenSign™ API allows seamless integration into existing systems and software. APIs will soon be available as a cloud hosted solution.
- **Integrations:** Seamless integrations with various Cloud storage systems, CRMs & enterprise platforms is coming soon.
- **API Support:** OpenSign™ API allows seamless integration into existing systems and software. You can generate an API key from the app and refer the [docs](https://docs.opensignlabs.com) to start integrating it in your existing applications.
- **Integrations:** Seamless integrations with various Cloud storage systems, CRMs & enterprise platforms is available. We also have a Zapier integration that allows you to integrate it with virtually any application.

<img src=https://github.com/OpenSignLabs/OpenSign/assets/5486116/b37ff443-7099-4273-9aeb-21c46d7154cf height='200'>
<img src=https://github.com/OpenSignLabs/OpenSign/assets/5486116/86db91b7-6c2f-4885-a33c-58f4fd35ec89 height='200'>
Expand All @@ -76,7 +76,7 @@ Please refer to the [Installation Guide](INSTALLATION.md) for detailed instructi

### Usage

For comprehensive guidelines on how to use OpenSign, please consult our [User Manual](USAGE.md).
For comprehensive guidelines on how to use OpenSign, please consult our [User Manual](USAGE.md).

---

Expand Down
2 changes: 1 addition & 1 deletion apps/OpenSign/src/components/dashboard/DashboardCard.js
Original file line number Diff line number Diff line change
Expand Up @@ -353,7 +353,7 @@ const DashboardCard = (props) => {
</div>
</div>
</div>
<div className="text-xs absolute top-1 right-1">
<div className="text-xs absolute top-2 right-1">
<Tooltip id={props.Label} iconColor={"white"} message={props?.Data?.tourMessage} />
</div>
</div>
Expand Down
1 change: 1 addition & 0 deletions apps/OpenSign/src/components/pdf/Placeholder.js
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,7 @@ function Placeholder(props) {
}
};
const handleOnClickPlaceholder = () => {
props.setCurrWidgetsDetails && props.setCurrWidgetsDetails(props.pos);
if (!props.isNeedSign) {
props.setWidgetType(props.pos.type);
}
Expand Down
5 changes: 5 additions & 0 deletions apps/OpenSign/src/components/pdf/PlaceholderType.js
Original file line number Diff line number Diff line change
Expand Up @@ -307,6 +307,7 @@ function PlaceholderType(props) {
return props.pos.SignUrl ? (
<img
alt="signimg"
draggable="false"
src={props.pos.SignUrl}
style={{
width: "99%",
Expand All @@ -328,6 +329,7 @@ function PlaceholderType(props) {
return props.pos.SignUrl ? (
<img
alt="signimg"
draggable="false"
src={props.pos.SignUrl}
style={{
width: "99%",
Expand Down Expand Up @@ -483,6 +485,7 @@ function PlaceholderType(props) {
return props.pos.SignUrl ? (
<img
alt="signimg"
draggable="false"
src={props.pos.SignUrl}
style={{
width: "99%",
Expand Down Expand Up @@ -668,6 +671,7 @@ function PlaceholderType(props) {
return props.pos.SignUrl ? (
<img
alt="signimg"
draggable="false"
src={props.pos.SignUrl}
style={{
width: "99%",
Expand Down Expand Up @@ -787,6 +791,7 @@ function PlaceholderType(props) {
<div style={{ pointerEvents: "none" }}>
<img
alt="signimg"
draggable="false"
src={props.pos.SignUrl}
style={{
width: "99%",
Expand Down
8 changes: 7 additions & 1 deletion apps/OpenSign/src/components/pdf/RecipientList.js
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,13 @@ const RecipientList = (props) => {
data-tut="reactourFirst"
onMouseEnter={() => setIsHover(ind)}
onMouseLeave={() => setIsHover(null)}
className={props.sendInOrder && "dragCursor"}
className={
props.sendInOrder
? props.isMailSend
? "disabled"
: "dragCursor"
: props.isMailSend && "disabled"
}
style={
(!isMobile && isHover === ind) || props.isSelectListId === ind
? onHoverStyle(ind, obj?.blockColor)
Expand Down
1 change: 1 addition & 0 deletions apps/OpenSign/src/components/pdf/RenderPdf.js
Original file line number Diff line number Diff line change
Expand Up @@ -272,6 +272,7 @@ function RenderPdf({
unSignedWidgetId={unSignedWidgetId}
setSelectWidgetId={setSelectWidgetId}
selectWidgetId={selectWidgetId}
setCurrWidgetsDetails={setCurrWidgetsDetails}
/>
</React.Fragment>
)
Expand Down
55 changes: 36 additions & 19 deletions apps/OpenSign/src/components/pdf/SignPad.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,9 @@ function SignPad({
isInitial,
setIsInitial,
setIsStamp,
widgetType
widgetType,
currWidgetsDetails,
setCurrWidgetsDetails
}) {
const [penColor, setPenColor] = useState("blue");
const allColor = ["blue", "red", "black"];
Expand All @@ -31,6 +33,7 @@ function SignPad({
const [signValue, setSignValue] = useState("");
const [textWidth, setTextWidth] = useState(null);
const [textHeight, setTextHeight] = useState(null);
const [signatureType, setSignatureType] = useState("draw");
const fontOptions = [
{ value: "Fasthand" },
{ value: "Dancing Script" },
Expand All @@ -48,19 +51,11 @@ function SignPad({
`Parse/${localStorage.getItem("parseAppId")}/currentUser`
);
const jsonSender = JSON.parse(senderUser);

const currentUserName = jsonSender && jsonSender.name;

useEffect(() => {
const trimmedName = currentUserName.trim();
const firstCharacter = trimmedName.charAt(0);
const userName = isInitial ? firstCharacter : currentUserName;
setSignValue(userName);
setFontSelect("Fasthand");
// eslint-disable-next-line react-hooks/exhaustive-deps
}, []);
//function for clear signature image
const handleClear = () => {
setCurrWidgetsDetails({});
if (isTab === "draw") {
if (canvasRef.current) {
canvasRef.current.clear();
Expand All @@ -72,7 +67,7 @@ function SignPad({
} else if (isTab === "uploadImage") {
setImage("");
}
setIsInitial(false);
// setIsInitial(false);
};
//function for set signature url
const handleSignatureChange = () => {
Expand Down Expand Up @@ -100,27 +95,28 @@ function SignPad({

<button
onClick={() => {
setCurrWidgetsDetails({});
if (!image) {
if (isTab === "mysignature") {
setIsSignImg("");
if (isInitial) {
onSaveSign("initials");
onSaveSign(signatureType, "initials");
} else {
onSaveSign("default");
onSaveSign(null, "default");
}
} else {
if (isTab === "type") {
setIsSignImg("");
onSaveSign(false, textWidth, textHeight);
onSaveSign(null, false, textWidth, textHeight);
} else {
onSaveSign();
onSaveSign(signatureType);
}
}

setPenColor("blue");
} else {
setIsSignImg("");
onSaveImage();
onSaveImage(signatureType);
}
setIsSignPad(false);
setIsInitial(false);
Expand Down Expand Up @@ -150,11 +146,27 @@ function SignPad({
</div>
);
};

//useEffect for set already draw or save signature url/text url of signature text type and draw type for initial type and signature type widgets
useEffect(() => {
if (canvasRef.current && isSignImg) {
canvasRef.current.fromDataURL(isSignImg);
if (currWidgetsDetails && canvasRef.current) {
const isWidgetType = currWidgetsDetails?.type;
const signatureType = currWidgetsDetails?.signatureType;
const url = currWidgetsDetails?.SignUrl;

//checking widget type and draw type signature url
if (isInitial) {
if (isWidgetType === "initials" && signatureType === "draw" && url) {
canvasRef.current.fromDataURL(url);
}
} else if (
isWidgetType === "signature" &&
signatureType === "draw" &&
url
) {
canvasRef.current.fromDataURL(url);
}
}

const trimmedName = currentUserName.trim();
const firstCharacter = trimmedName.charAt(0);
const userName = isInitial ? firstCharacter : currentUserName;
Expand Down Expand Up @@ -349,6 +361,7 @@ function SignPad({
setIsDefaultSign(false);
setIsImageSelect(true);
setIsTab("uploadImage");
setSignatureType("");
}}
style={{
color:
Expand All @@ -373,6 +386,7 @@ function SignPad({
setIsDefaultSign(false);
setIsImageSelect(false);
setIsTab("type");
setSignatureType("");
setImage();
}}
style={{
Expand Down Expand Up @@ -400,6 +414,7 @@ function SignPad({
setIsDefaultSign(true);
setIsImageSelect(true);
setIsTab("mysignature");
setSignatureType("");
setImage();
}}
style={{
Expand Down Expand Up @@ -430,6 +445,7 @@ function SignPad({
setIsDefaultSign(true);
setIsImageSelect(true);
setIsTab("mysignature");
setSignatureType("");
setImage();
}}
style={{
Expand Down Expand Up @@ -469,6 +485,7 @@ function SignPad({
setIsDefaultSign(false);
setImage();
setIsTab("draw");
setSignatureType("draw");
setSignValue("");
setIsStamp(false);
}}
Expand Down
4 changes: 4 additions & 0 deletions apps/OpenSign/src/components/pdf/SignerListPlace.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ function SignerListPlace(props) {
data-tut="reactourAddbtn"
className="p-[10px] my-[2px] flex flex-row items-center justify-center border-[1px] border-[#47a3ad] hover:bg-[#47a3ad] text-[#47a3ad] hover:text-white cursor-pointer"
onClick={() => props.handleAddSigner()}
style={{
opacity: props.isMailSend && "0.5",
pointerEvents: props.isMailSend && "none"
}}
>
<i className="fa-solid fa-plus"></i>
<span style={{ marginLeft: 2 }}>Add role</span>
Expand Down
7 changes: 6 additions & 1 deletion apps/OpenSign/src/components/pdf/WidgetComponent.js
Original file line number Diff line number Diff line change
Expand Up @@ -364,7 +364,12 @@ function WidgetComponent({
</div>
)
) : (
<div data-tut={dataTut} className="signerComponent">
<div
data-tut={dataTut}
className={
isMailSend ? "disabled signerComponent " : "signerComponent"
}
>
<div
style={{
background: themeColor,
Expand Down
2 changes: 1 addition & 1 deletion apps/OpenSign/src/components/shared/fields/SelectFolder.js
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,7 @@ const SelectFolder = ({ required, onSuccess, folderCls, isReset }) => {
{selectFolder && selectFolder.Name ? `(${folderPath})` : ""}
</p>
</div>
<div className="absolute top-1 right-1 cursor-pointer">
<div className="absolute top-2 right-1 cursor-pointer">
<Tooltip
message={
"If you do not select a folder, your signed document will be saved in the Main OpenSign drive folder."
Expand Down
2 changes: 1 addition & 1 deletion apps/OpenSign/src/components/shared/fields/SignersInput.js
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ const SignersInput = (props) => {

return (
<div className="text-xs mt-2 ">
<label className="block">
<label className="block relative">
Signers
{props.required && <span className="text-red-500 text-[13px]">*</span>}
<span className="absolute ml-1 text-xs z-50">
Expand Down
2 changes: 2 additions & 0 deletions apps/OpenSign/src/constant/Utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -935,6 +935,7 @@ export const embedDocId = async (pdfDoc, documentId, allPages) => {

//function for save button to save signature or image url
export function onSaveSign(
type,
xyPostion,
index,
signKey,
Expand Down Expand Up @@ -975,6 +976,7 @@ export function onSaveSign(
Width: posWidth,
Height: posHeight,
SignUrl: signatureImg,
signatureType: type && type,
options: {
...position.options,
response: signatureImg
Expand Down
Loading