mirror of
https://github.com/rkd77/elinks.git
synced 2024-12-04 14:46:47 -05:00
ECMAScript: Preserve all of Unicode when setting the accessKey property.
Well, almost all. U+0000 cannot be used because ELinks thinks that means the link has no access key.
This commit is contained in:
parent
45b194d1e7
commit
2d898272c1
@ -283,13 +283,17 @@ input_put(struct SEE_interpreter *interp, struct SEE_object *o,
|
||||
if (linknum >= 0) link = &document->links[linknum];
|
||||
|
||||
if (p == s_accessKey) {
|
||||
if (link) {
|
||||
string = SEE_value_to_unsigned_char(interp, val);
|
||||
if (!string)
|
||||
return;
|
||||
link->accesskey = accesskey_string_to_unicode(string);
|
||||
mem_free(string);
|
||||
}
|
||||
struct SEE_value conv;
|
||||
unicode_val_T accesskey;
|
||||
|
||||
SEE_ToString(interp, val, &conv);
|
||||
if (conv.u.string->length)
|
||||
accesskey = SEE_string_to_unicode(interp, conv.u.string);
|
||||
else
|
||||
accesskey = 0;
|
||||
|
||||
if (link)
|
||||
link->accesskey = accesskey;
|
||||
} else if (p == s_alt) {
|
||||
string = SEE_value_to_unsigned_char(interp, val);
|
||||
mem_free_set(&fc->alt, string);
|
||||
|
@ -123,3 +123,24 @@ append_unicode_to_SEE_string(struct SEE_interpreter *interp,
|
||||
(unsigned int) u);
|
||||
}
|
||||
}
|
||||
|
||||
unicode_val_T
|
||||
SEE_string_to_unicode(struct SEE_interpreter *interp, struct SEE_string *S)
|
||||
{
|
||||
/* This implementation ignores extra characters in the string. */
|
||||
if (S->length < 1) {
|
||||
SEE_error_throw(interp, interp->Error,
|
||||
"String is empty");
|
||||
} else if (S->data[0] < 0xD800 || S->data[0] > 0xDFFF) {
|
||||
return S->data[0];
|
||||
} else if (S->length >= 2
|
||||
&& S->data[0] >= 0xD800 && S->data[0] <= 0xDBFF
|
||||
&& S->data[1] >= 0xDC00 && S->data[1] <= 0xDFFF) {
|
||||
return 0x10000
|
||||
+ ((S->data[0] & 0x3FF) << 10)
|
||||
+ (S->data[1] & 0x3FF);
|
||||
} else {
|
||||
SEE_error_throw(interp, interp->Error,
|
||||
"Invalid UTF-16 sequence");
|
||||
}
|
||||
}
|
||||
|
@ -13,5 +13,6 @@ unsigned char *SEE_value_to_unsigned_char(struct SEE_interpreter *, struct SEE_v
|
||||
struct SEE_string *string_to_SEE_string(struct SEE_interpreter *, unsigned char *);
|
||||
void append_unicode_to_SEE_string(struct SEE_interpreter *, struct SEE_string *,
|
||||
unicode_val_T);
|
||||
unicode_val_T SEE_string_to_unicode(struct SEE_interpreter *, struct SEE_string *);
|
||||
|
||||
#endif
|
||||
|
@ -118,6 +118,7 @@ static const JSFunctionSpec input_funcs[] = {
|
||||
};
|
||||
|
||||
static JSString *unicode_to_jsstring(JSContext *ctx, unicode_val_T u);
|
||||
static unicode_val_T jsval_to_accesskey(JSContext *ctx, jsval *vp);
|
||||
|
||||
static JSBool
|
||||
input_get_property(JSContext *ctx, JSObject *obj, jsval id, jsval *vp)
|
||||
@ -253,6 +254,7 @@ input_set_property(JSContext *ctx, JSObject *obj, jsval id, jsval *vp)
|
||||
struct form_control *fc = find_form_control(document, fs);
|
||||
int linknum;
|
||||
struct link *link = NULL;
|
||||
unicode_val_T accesskey;
|
||||
|
||||
assert(fc);
|
||||
assert(fc->form && fs);
|
||||
@ -266,8 +268,11 @@ input_set_property(JSContext *ctx, JSObject *obj, jsval id, jsval *vp)
|
||||
|
||||
switch (JSVAL_TO_INT(id)) {
|
||||
case JSP_INPUT_ACCESSKEY:
|
||||
if (link)
|
||||
link->accesskey = accesskey_string_to_unicode(jsval_to_string(ctx, vp));
|
||||
accesskey = jsval_to_accesskey(ctx, vp);
|
||||
if (accesskey == UCS_NO_CHAR)
|
||||
return JS_FALSE;
|
||||
else if (link)
|
||||
link->accesskey = accesskey;
|
||||
break;
|
||||
case JSP_INPUT_ALT:
|
||||
mem_free_set(&fc->alt, stracpy(jsval_to_string(ctx, vp)));
|
||||
@ -1001,3 +1006,30 @@ unicode_to_jsstring(JSContext *ctx, unicode_val_T u)
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
/* Convert the string *@vp to an access key. Return 0 for no access
|
||||
* key, UCS_NO_CHAR on error, or the access key otherwise. */
|
||||
static unicode_val_T
|
||||
jsval_to_accesskey(JSContext *ctx, jsval *vp)
|
||||
{
|
||||
size_t len;
|
||||
const jschar *chr;
|
||||
|
||||
/* Convert the value in place, to protect the result from GC. */
|
||||
if (JS_ConvertValue(ctx, *vp, JSTYPE_STRING, vp) == JS_FALSE)
|
||||
return UCS_NO_CHAR;
|
||||
len = JS_GetStringLength(JSVAL_TO_STRING(*vp));
|
||||
chr = JS_GetStringChars(JSVAL_TO_STRING(*vp));
|
||||
|
||||
/* This implementation ignores extra characters in the string. */
|
||||
if (len < 1)
|
||||
return 0; /* which means no access key */
|
||||
if (chr[0] < 0xD800 || chr[0] > 0xDFFF)
|
||||
return chr[0];
|
||||
if (len >= 2
|
||||
&& chr[0] >= 0xD800 && chr[0] <= 0xDBFF
|
||||
&& chr[1] >= 0xDC00 && chr[1] <= 0xDFFF)
|
||||
return 0x10000 + ((chr[0] & 0x3FF) << 10) + (chr[1] & 0x3FF);
|
||||
JS_ReportError(ctx, "Invalid UTF-16 sequence");
|
||||
return UCS_NO_CHAR; /* which the caller will reject */
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user