2018-05-09 20:28:28 +01:00
/**
2018-05-09 21:13:09 +01:00
* @author Matt C [matt@artemisbot.uk]
* @copyright Crown Copyright 2018
2018-05-09 20:28:28 +01:00
* @license Apache-2.0
*/
2019-07-09 12:23:59 +01:00
import Operation from "../Operation.mjs" ;
import OperationError from "../errors/OperationError.mjs" ;
import { genPolybiusSquare } from "../lib/Ciphers.mjs" ;
2018-05-09 20:28:28 +01:00
/**
* Bifid Cipher Encode operation
*/
class BifidCipherEncode extends Operation {
/**
* BifidCipherEncode constructor
*/
constructor () {
super ();
this . name = "Bifid Cipher Encode" ;
this . module = "Ciphers" ;
this . description = "The Bifid cipher is a cipher which uses a Polybius square in conjunction with transposition, which can be fairly difficult to decipher without knowing the alphabet keyword." ;
2018-08-21 19:07:13 +01:00
this . infoURL = "https://wikipedia.org/wiki/Bifid_cipher" ;
2018-05-09 20:28:28 +01:00
this . inputType = "string" ;
this . outputType = "string" ;
this . args = [
{
"name" : "Keyword" ,
"type" : "string" ,
"value" : ""
}
];
}
/**
* @param {string} input
* @param {Object[]} args
* @returns {string}
2018-05-15 18:01:04 +01:00
*
* @throws {OperationError} if key is invalid
2018-05-09 20:28:28 +01:00
*/
run ( input , args ) {
const keywordStr = args [ 0 ]. toUpperCase (). replace ( "J" , "I" ),
keyword = keywordStr . split ( "" ). unique (),
alpha = "ABCDEFGHIKLMNOPQRSTUVWXYZ" ,
xCo = [],
yCo = [],
structure = [];
let output = "" ,
count = 0 ;
2018-05-09 21:13:09 +01:00
if ( ! /^[A-Z]+$/ . test ( keywordStr ) && keyword . length > 0 )
2018-05-11 16:32:19 +01:00
throw new OperationError ( "The key must consist only of letters in the English alphabet" );
2018-05-09 20:28:28 +01:00
const polybius = genPolybiusSquare ( keywordStr );
input . replace ( "J" , "I" ). split ( "" ). forEach ( letter => {
const alpInd = alpha . split ( "" ). indexOf ( letter . toLocaleUpperCase ()) >= 0 ;
let polInd ;
if ( alpInd ) {
for ( let i = 0 ; i < 5 ; i ++ ) {
polInd = polybius [ i ]. indexOf ( letter . toLocaleUpperCase ());
if ( polInd >= 0 ) {
xCo . push ( polInd );
yCo . push ( i );
}
}
if ( alpha . split ( "" ). indexOf ( letter ) >= 0 ) {
structure . push ( true );
} else if ( alpInd ) {
structure . push ( false );
}
} else {
structure . push ( letter );
}
});
const trans = ` ${ yCo . join ( "" ) }${ xCo . join ( "" ) } ` ;
structure . forEach ( pos => {
if ( typeof pos === "boolean" ) {
const coords = trans . substr ( 2 * count , 2 ). split ( "" );
output += pos ?
polybius [ coords [ 0 ]][ coords [ 1 ]] :
polybius [ coords [ 0 ]][ coords [ 1 ]]. toLocaleLowerCase ();
count ++ ;
} else {
output += pos ;
}
});
return output ;
}
/**
* Highlight Bifid Cipher Encode
*
* @param {Object[]} pos
* @param {number} pos[].start
* @param {number} pos[].end
* @param {Object[]} args
* @returns {Object[]} pos
*/
highlight ( pos , args ) {
return pos ;
}
/**
* Highlight Bifid Cipher Encode in reverse
*
* @param {Object[]} pos
* @param {number} pos[].start
* @param {number} pos[].end
* @param {Object[]} args
* @returns {Object[]} pos
*/
highlightReverse ( pos , args ) {
return pos ;
}
}
export default BifidCipherEncode ;