`IndexOutOfRangeException` during penalty check
// includes and public void Main() ...
11: var segments = QrSegment.MakeSegments("testing");
12: var qr = QrCode.EncodeSegments(segments, QrCode.Ecc.Medium, 40, 40, -1, true);
An unhandled exception of type 'System.IndexOutOfRangeException' occurred in QrCodeGenerator.dll: 'Index was outside the bounds of the array.'
at Net.Codecrete.QrCodeGenerator.QrCode.FinderPenalty.AddHistory(Int32 run)
at Net.Codecrete.QrCodeGenerator.QrCode.FinderPenalty.TerminateAndCount(Boolean currentRunColor, Int32 currentRunLength)
at Net.Codecrete.QrCodeGenerator.QrCode.GetPenaltyScore()
at Net.Codecrete.QrCodeGenerator.QrCode.HandleConstructorMasking(Int32 mask)
at Net.Codecrete.QrCodeGenerator.QrCode..ctor(Int32 version, Ecc ecl, Byte[] dataCodewords, Int32 mask)
at Net.Codecrete.QrCodeGenerator.QrCode.EncodeSegments(List`1 segments, Ecc ecl, Int32 minVersion, Int32 maxVersion, Int32 mask, Boolean boostEcl)
at QrCodeGenerator.Program.Main() in c:\Users\Richard\Source\qrcodegenerator\Program.cs:line 12
I found this because I am translating the library to PowerShell (to avoid distributing a dll along with the text based script). I've been testing various inputs and comparing the output images to verify that I translated correctly.
The exception happens because FinderPenalty._length exceeds 176. I was able to get this to complete by changing FinderPenalty..ctor to
internal FinderPenalty(int size)
{
_length = 0;
_runHistory = new short[179]; // HACK was 177
_size = size;
}
but I'm not sure if this is the actual maximum value. Logically, the maximum should be 177 because that's the maximum number of modules in a vertical or horizontal run, but I'm guessing the algorithm is doing something strange.
Thank you for reporting this. You've detected an edge case with your settings. The correct size for the array should indeed be 179 (or version * 4 + 19).
For C#, it's now fixed with version 2.0.6.