Add for use outline style, and reduce colors down to 5 (red, blue, green, yellow and black).

This commit is contained in:
Jason Lee 2018-09-06 19:33:18 +08:00
parent b6c3d3735d
commit 682aa39ec0
10 changed files with 144 additions and 344 deletions

View File

@ -1,3 +1,9 @@
2.3.0
-------
- Add `config.outline` for use outline style.
- Reduce colors down to 5 (red, blue, green, yellow and black).
2.2.0 2.2.0
----- -----

5
Makefile Normal file
View File

@ -0,0 +1,5 @@
compile:
rake clean
rake compile
test:
rake preview > ~/Desktop/rucaptcha-test.gif && open ~/Desktop/rucaptcha-test.gif

View File

@ -2,15 +2,20 @@
[![Gem Version](https://badge.fury.io/rb/rucaptcha.svg)](https://badge.fury.io/rb/rucaptcha) [![Gem Version](https://badge.fury.io/rb/rucaptcha.svg)](https://badge.fury.io/rb/rucaptcha)
[![Build Status](https://travis-ci.org/huacnlee/rucaptcha.svg)](https://travis-ci.org/huacnlee/rucaptcha) [![Build Status](https://travis-ci.org/huacnlee/rucaptcha.svg)](https://travis-ci.org/huacnlee/rucaptcha)
[![Code Climate](https://codeclimate.com/github/huacnlee/rucaptcha/badges/gpa.svg)](https://codeclimate.com/github/huacnlee/rucaptcha)
This is a Captcha gem for Rails Applications which generates captcha image by C code. This is a Captcha gem for Rails Applications which generates captcha image by C code.
[中文介绍和使用说明](https://ruby-china.org/topics/27832)
## Example ## Example
<img src="https://cloud.githubusercontent.com/assets/5518/22151425/e02390c8-df58-11e6-974d-5eb9b1a4e577.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151427/e4939d92-df58-11e6-9754-4a46a86acea8.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151431/e494576e-df58-11e6-9845-a5590904c175.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151432/e495066e-df58-11e6-92b8-38b40b73aba0.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151428/e49404ee-df58-11e6-8e2d-8b17b33a3710.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151430/e4942406-df58-11e6-9ff8-6e2325304b41.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151429/e4941ae2-df58-11e6-8107-757296573b2f.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151433/e4c7c89c-df58-11e6-9853-1ffbb4986962.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151435/e4c97ea8-df58-11e6-8959-b4c78716271d.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151436/e4cc09f2-df58-11e6-965c-673333b33c0d.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151434/e4c87788-df58-11e6-9490-c255aaafce71.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151445/ee35ff66-df58-11e6-8660-a3673ef3f5ee.gif" width="150px" /> <img src="https://cloud.githubusercontent.com/assets/5518/22151446/ee67b074-df58-11e6-9b95-7d53eec21c33.gif" width="150px" /> **default style**
[中文介绍和使用说明](https://ruby-china.org/topics/27832) ![rucaptcha-0](https://user-images.githubusercontent.com/5518/45154624-c471a780-b20a-11e8-8bec-6c133838d53a.gif) ![rucaptcha-1](https://user-images.githubusercontent.com/5518/45154625-c471a780-b20a-11e8-8d09-dfb6ace6e9ba.gif) ![rucaptcha-2](https://user-images.githubusercontent.com/5518/45154628-c50a3e00-b20a-11e8-9afd-7c200b663dbc.gif) ![rucaptcha-3](https://user-images.githubusercontent.com/5518/45154629-c50a3e00-b20a-11e8-88d1-536717664e88.gif) ![rucaptcha-4](https://user-images.githubusercontent.com/5518/45154630-c50a3e00-b20a-11e8-9aa8-9b896a177e84.gif)
**outline enable**
![rucaptcha-b0](https://user-images.githubusercontent.com/5518/45154631-c5a2d480-b20a-11e8-9b63-febdaa5e5c9c.gif) ![rucaptcha-b1](https://user-images.githubusercontent.com/5518/45154632-c5a2d480-b20a-11e8-896b-0fe17bc0b5c5.gif) ![rucaptcha-b2](https://user-images.githubusercontent.com/5518/45154633-c63b6b00-b20a-11e8-8226-7d516764634c.gif) ![rucaptcha-b3](https://user-images.githubusercontent.com/5518/45154634-c63b6b00-b20a-11e8-9781-c22a3109616b.gif) ![rucaptcha-b4](https://user-images.githubusercontent.com/5518/45154635-c63b6b00-b20a-11e8-8e12-52a30e686339.gif)
## Feature ## Feature
@ -46,6 +51,8 @@ RuCaptcha.configure do
# self.length = 5 # self.length = 5
# enable/disable Strikethrough. # enable/disable Strikethrough.
# self.strikethrough = true # self.strikethrough = true
# enable/disable Outline style, for hard mode
# self.outline = false
end end
``` ```

View File

@ -13,6 +13,7 @@ task default: :spec
task :preview do task :preview do
require 'rucaptcha' require 'rucaptcha'
res = RuCaptcha.create(1, 3, 1) res = RuCaptcha.create(1, 5, 1, 0)
$stderr.puts res[0]
puts res[1] puts res[1]
end end

View File

@ -1,345 +1,118 @@
// Colors from // Colors from
// https://material.io/guidelines/style/color.html#color-ui-color-palette // https://material.io/guidelines/style/color.html#color-ui-color-palette
// Color covert HEX RGB to \x??\x??\x??
static char *colors[] = { static char *colors[] = {
// Black 500 #000000 // Black 500 #000000
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\x11\x11\x11" "\x00\x00\x00"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04", "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Red 500 #F44336 // Red A700 #D50000
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xF4\x43\x36" "\xD5\x00\x00"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04", "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Pink 500 #E91E63 // Deep Orange A700 #DD2C00
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xE9\x1E\x63" "\xDD\x2C\x00"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04", "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Purple 500 #9C27B0 // Blue A700 #2962FF
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\x9C\x27\xB0" "\x29\x62\xFF"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04", "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Deep Purple 500 #673AB7 // Green A700 #00C853
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\x67\x3A\xB7" "\x00\xC8\x53"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04", "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Indigo 500 #3F51B5 // Yellow A700 #FFD600
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0" "GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\x3F\x51\xB5" "\xFF\xD6\x00"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Blue 500 #2196F3
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\x21\x96\xF3"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Light Blue 500 #03A9F4
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\x03\xA9\xF4"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Cyan 500 #00BCD4
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\x00\xBC\xD4"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Teal 500 #009688
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\x00\x96\x88"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Green 500 #4CAF50
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\x4C\xAF\x50"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Light Green 500 #8BC34A
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\x8B\xC3\x4A"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Lime 500 #CDDC39
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xCD\xDC\x39"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Yellow 500 #FFEB3B
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xFF\xEB\x3B"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Amber 500 #FFC107
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xFF\xC1\x07"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Orange 500 #FF9800
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xFF\x98\x00"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Deep Orange 500 #FF5722
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xFF\x57\x22"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04",
// Brown 500 #795548
"GIF89a" "\xc8\0\x46\0" "\x83" "\0\0"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\x79\x55\x48"
"\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04" "\xff\xff\xff" "," "\0\0\0\0" "\xc8\0\x46\0" "\0" "\x04"
}; };

View File

@ -1,6 +1,6 @@
// http://github.com/ITikhonov/captcha // http://github.com/ITikhonov/captcha
const int gifsize; const int gifsize;
void captcha(unsigned char im[70*200], unsigned char l[8], int length, int i_line); void captcha(unsigned char im[70*200], unsigned char l[8], int length, int i_line, int i_filter);
void makegif(unsigned char im[70*200], unsigned char gif[gifsize], int style); void makegif(unsigned char im[70*200], unsigned char gif[gifsize], int style);
#include <unistd.h> #include <unistd.h>
@ -85,10 +85,10 @@ static int letter(int n, int pos, unsigned char im[70*200], unsigned char swr[20
if((x-im)<70*200) *x=(*p)<<4; if((x-im)<70*200) *x=(*p)<<4;
i++; i++;
} }
return mpos; return mpos + 3;
} }
#define NDOTS 100 #define NDOTS 10
uint32_t dr[NDOTS]; uint32_t dr[NDOTS];
@ -97,7 +97,7 @@ static void line(unsigned char im[70*200], unsigned char swr[200], uint8_t s1) {
int sk1=s1; int sk1=s1;
for(x=0;x<199;x++) { for(x=0;x<199;x++) {
if(sk1>=200) sk1=sk1%200; if(sk1>=200) sk1=sk1%200;
int skew=sw[sk1]/16; int skew=sw[sk1]/20;
sk1+=swr[x]&0x3+1; sk1+=swr[x]&0x3+1;
unsigned char *i= im+(200*(45+skew)+x); unsigned char *i= im+(200*(45+skew)+x);
i[0]=0; i[1]=0; i[200]=0; i[201]=0; i[0]=0; i[1]=0; i[200]=0; i[201]=0;
@ -118,6 +118,7 @@ static void dots(unsigned char im[70*200]) {
i[202]=0xff; i[202]=0xff;
} }
} }
static void blur(unsigned char im[70*200]) { static void blur(unsigned char im[70*200]) {
unsigned char *i=im; unsigned char *i=im;
int x,y; int x,y;
@ -150,9 +151,9 @@ static void filter(unsigned char im[70*200]) {
memmove(im,om,sizeof(om)); memmove(im,om,sizeof(om));
} }
static const char *letters="abcdafahijklmnopqrstuvwxyz"; static const char *letters="abcdyfhhijklmnopqrstuvwxyz";
void captcha(unsigned char im[70*200], unsigned char l[8], int length, int i_line) { void captcha(unsigned char im[70*200], unsigned char l[8], int length, int i_line, int i_filter) {
unsigned char swr[200]; unsigned char swr[200];
uint8_t s1,s2; uint8_t s1,s2;
@ -173,11 +174,15 @@ void captcha(unsigned char im[70*200], unsigned char l[8], int length, int i_lin
for(x=0;x<length;x++){ for(x=0;x<length;x++){
p=letter(l[x],p,im,swr,s1,s2); p=letter(l[x],p,im,swr,s1,s2);
} }
//p=letter(l[0],p,im,swr,s1,s2); p=letter(l[1],p,im,swr,s1,s2); p=letter(l[2],p,im,swr,s1,s2); p=letter(l[3],p,im,swr,s1,s2); //letter(l[4],p,im,swr,s1,s2);
if (i_line == 1) { if (i_line == 1) {
line(im,swr,s1); line(im,swr,s1);
} }
dots(im); // blur(im); // filter(im); // dots(im);
if (i_filter == 1) {
blur(im);
filter(im);
}
for(x=0;x<length;x++){ for(x=0;x<length;x++){
l[x]=letters[l[x]]; l[x]=letters[l[x]];
@ -207,22 +212,23 @@ VALUE RuCaptcha = Qnil;
void Init_rucaptcha(); void Init_rucaptcha();
VALUE create(VALUE self, VALUE style, VALUE length, VALUE line); VALUE create(VALUE self, VALUE style, VALUE length, VALUE line, VALUE filter);
void Init_rucaptcha() { void Init_rucaptcha() {
RuCaptcha = rb_define_module("RuCaptcha"); RuCaptcha = rb_define_module("RuCaptcha");
rb_define_singleton_method(RuCaptcha, "create", create, 3); rb_define_singleton_method(RuCaptcha, "create", create, 4);
} }
VALUE create(VALUE self, VALUE style, VALUE length, VALUE line) { VALUE create(VALUE self, VALUE style, VALUE length, VALUE line, VALUE filter) {
char l[8]; char l[8];
unsigned char im[80*200]; unsigned char im[80*200];
unsigned char gif[gifsize]; unsigned char gif[gifsize];
int i_style = FIX2INT(style); int i_style = FIX2INT(style);
int i_length = FIX2INT(length); int i_length = FIX2INT(length);
int i_line = FIX2INT(line); int i_line = FIX2INT(line);
int i_filter = FIX2INT(filter);
captcha(im, l, i_length, i_line); captcha(im, l, i_length, i_line, i_filter);
makegif(im, gif, i_style); makegif(im, gif, i_style);
VALUE result = rb_ary_new2(2); VALUE result = rb_ary_new2(2);

View File

@ -18,6 +18,7 @@ module RuCaptcha
@config.style = :colorful @config.style = :colorful
@config.length = 5 @config.length = 5
@config.strikethrough = true @config.strikethrough = true
@config.outline = false
@config.expires_in = 2.minutes @config.expires_in = 2.minutes
if Rails.application if Rails.application
@ -42,7 +43,8 @@ module RuCaptcha
end end
strikethrough = config.strikethrough ? 1 : 0 strikethrough = config.strikethrough ? 1 : 0
self.create(style, length, strikethrough) outline = config.outline ? 1 : 0
self.create(style, length, strikethrough, outline)
end end
def check_cache_store! def check_cache_store!

View File

@ -11,5 +11,7 @@ module RuCaptcha
attr_accessor :length attr_accessor :length
# strikethrough, default: true # strikethrough, default: true
attr_accessor :strikethrough attr_accessor :strikethrough
# outline style for hard mode, default: false
attr_accessor :outline
end end
end end

View File

@ -1,3 +1,3 @@
module RuCaptcha module RuCaptcha
VERSION = '2.2.0' VERSION = '2.3.0'
end end

2
test
View File

@ -1,2 +0,0 @@
rake clean && rake compile > /dev/null 2& > /dev/null
rake preview > /tmp/rucaptcha-test.gif && open /tmp/rucaptcha-test.gif