Convert Topaz Sigweb sigstring to Base64

前端 未结 3 1718
春和景丽
春和景丽 2021-02-08 23:15

I am working on a mobile application(ionic) where there is a field for user\'s signature. Users needs to sign with their finger in canvas.

Now this application has web v

3条回答
  •  小蘑菇
    小蘑菇 (楼主)
    2021-02-08 23:43

    I realise this is a bit old but I'm sure there are plenty of others with the same issue.

    I had exactly the same issues when I needed to display the signatures to end users in a standard desktop or mobile browser with no plug-ins or installs required. Spoke to Topaz and there is a an option to run the ActiveX on the server side using the PHP Component Object Model to create the image. Unfortunately, this only works on a Windows server and takes a lot of fiddling with. I only managed to get it working on my test bench and it was useless for my linux production servers. I contacted Topaz again and they said the ONLY other option was a Java applet!?

    ActiveX! Java Applets! It's 2019, not 2009! (Sorry, I overdosed on exclamation marks there but Jeez).

    In the end I decided to try and decode it myself and eventually came up with this PHP function to create an SVG. The format they use is proprietary (and is actually a bit of a hacky mess) but essentially it is only hex, coordinates and stroke lengths - so it should be easy enough for someone to convert the below to any other platform.

    //Requires $SigString and accepts optional filename.
    //If filename is supplied the image will be written to that file
    //If no filename is supplied the SVG image will be returned as a string which can be echoed out directly
    
    function sigstring2svg($SigString, $filename = NULL)
    {
        $raw = hex2bin($SigString); //Convert Hex
        $arr = explode(PHP_EOL, $raw); //Split into array
        if ($arr[1] > 0) { //Check if signature is empty
            $coords = array_slice($arr, 2, $arr[0]); //Separate off coordinate pairs
            $lines = array_slice($arr, ($arr[0] + 2), $arr[1]); //Separate off number of coordinates pairs per stroke
            if ($arr[1] == 1) {
                $lines[] = ($arr[0] + 2); //If there is only 1 line the end has to be marked
            }
            $done = 0;
            foreach ($lines as $line => $linevalue) {
                if ($linevalue > $done) {
                    $strokes[$line] = array_slice($coords, $done, $linevalue); //Split coordinate pairs into separate strokes
                }
                $done = $linevalue;
            }
            //Split X and Y to calculate the maximum and minimum coordinates on both axis
            $xmax = 0;
            $xmin = 999999;
            $ymax = 0;
            $ymin = 999999;
            foreach ($strokes as $stroke => $xycoords) {
                foreach ($xycoords as $xycoord) {
                    $xyc = explode(' ', $xycoord);
                    $xy[$stroke]['x'][] = $xyc[0];
                    if ($xyc[0] > $xmax) $xmax = $xyc[0];
                    if ($xyc[0] < $xmin) $xmin = $xyc[0];
                    $xy[$stroke]['y'][] = $xyc[1];
                    if ($xyc[1] > $ymax) $ymax = $xyc[1];
                    if ($xyc[1] < $ymin) $ymin = $xyc[1];
                }
            }
            //Add in 10 pixel border to allow for stroke
            $xmax += 10;
            $xmin -= 10;
            $ymax += 10;
            $ymin -= 10;
            //Calculate the canvas size and offset out anything below the minimum value to trim whitespace from top and left
            $xmax -= $xmin;
            $ymax -= $ymin;
    
            //Iterate through each stroke and each coordinate pair to make the points on the stroke to build each polyline as a string array
            foreach ($xy as $lines => $axis) {
                $polylines[$lines] = '';
            }
            //Build SVG image string
            $image = '
        
          
            
          
          Signature
          
            ';
            foreach ($polylines as $polyline) {
                $image .= $polyline;
            }
            $image .= '
          
        ';
    
            //If file name is supplied write to file
            if ($filename) {
                try {
                    $file = fopen($filename, 'w');
                    fwrite($file, $image);
                    fclose($file);
                    return $filename;
                } catch (Exception $e) {
                    return false;
                }
            } else {
                //If file name is not supplied return the SVG image as a string
                return $image;
            }
        } else {
            return "Signature is empty";
        }
    }
    

提交回复
热议问题