# HG changeset patch
# User Dan Pascu <[EMAIL PROTECTED]>
# Date 1146009163 25200
# Branch wm_0_92
# Node ID bd0c670bda80aab916c22b627adfe8cc9978d1ab
# Parent 6c6cf07271fc30e7be53e03b9cb6972e812c9ea8
Applied patches from Stanislav Maslovski <[EMAIL PROTECTED]> to
fix the 2 problems mentioend below:
- Fixed buggy handling of UTF8 characters in textfields in WINGs.
- Fixed segfault in WPrefs when some font description is missing from the
configuration file.
(transplanted from 84918d13ba317bfe1de6f734c5e32458de6f61ce)
diff -r 6c6cf07271fc -r bd0c670bda80 ChangeLog
--- a/ChangeLog Tue Apr 25 13:01:51 2006 -0700
+++ b/ChangeLog Tue Apr 25 16:52:43 2006 -0700
@@ -33,6 +33,10 @@
- Improved Info panel layout and fonts.
- Fixed missing library paths when linking some binaries on certain
platforms with a recent pkg-config (debian unstable/sid for one)
+- Fixed buggy handling of UTF8 characters in textfields in WINGs.
+ (Stanislav Maslovski <[EMAIL PROTECTED]>)
+- Fixed segfault in WPrefs when some font description is missing from the
+ configuration file (Stanislav Maslovski <[EMAIL PROTECTED]>)
diff -r 6c6cf07271fc -r bd0c670bda80 WINGs/wtextfield.c
--- a/WINGs/wtextfield.c Tue Apr 25 13:01:51 2006 -0700
+++ b/WINGs/wtextfield.c Tue Apr 25 16:52:43 2006 -0700
@@ -30,15 +30,15 @@
#endif
char *text;
- int textLen; /* size of text */
- int bufferSize; /* memory allocated for text */
+ int textLen; /* size of text */
+ int bufferSize; /* memory allocated for text */
- int viewPosition; /* position of text being shown */
+ int viewPosition; /* position of text being shown */
- int cursorPosition; /* position of the insertion
cursor */
+ int cursorPosition; /* position of the insertion cursor */
short usableWidth;
- short offsetWidth; /* offset of text from border */
+ short offsetWidth; /* offset of text from border */
WMRange selection;
@@ -47,7 +47,7 @@
WMTextFieldDelegate *delegate;
#if 0
- WMHandlerID timerID; /* for cursor blinking */
+ WMHandlerID timerID; /* for cursor blinking */
#endif
struct {
WMAlignment alignment:2;
@@ -62,7 +62,7 @@
unsigned int cursorOn:1;
- unsigned int secure:1; /* password entry style */
+ unsigned int secure:1; /* password entry style */
unsigned int pointerGrabbed:1;
@@ -77,7 +77,7 @@
} TextField;
-#define NOTIFY(T,C,N,A) { WMNotification *notif =
WMCreateNotification(N,T,A);\
+#define NOTIFY(T,C,N,A) { WMNotification *notif = WMCreateNotification(N,T,A);\
if ((T)->delegate && (T)->delegate->C)\
(*(T)->delegate->C)((T)->delegate,notif);\
WMPostNotification(notif);\
@@ -136,11 +136,45 @@
};
-#define TEXT_WIDTH(tPtr, start) (WMWidthOfString((tPtr)->font, \
- &((tPtr)->text[(start)]), (tPtr)->textLen - (start) + 1))
+#define TEXT_WIDTH(tPtr, start) (WMWidthOfString((tPtr)->font, \
+ &((tPtr)->text[(start)]), (tPtr)->textLen - (start)))
#define TEXT_WIDTH2(tPtr, start, end) (WMWidthOfString((tPtr)->font, \
- &((tPtr)->text[(start)]), (end) - (start) + 1))
+ &((tPtr)->text[(start)]), (end) - (start)))
+
+
+static INLINE int
+oneUTF8CharBackward(char *str, int len)
+{
+ unsigned char* ustr = (unsigned char*) str;
+ int pos = 0;
+
+ while (len-- > 0 && ustr[--pos] >= 0x80 && ustr[pos] <= 0xbf);
+ return pos;
+}
+
+
+static INLINE int
+oneUTF8CharForward(char *str, int len)
+{
+ unsigned char* ustr = (unsigned char*) str;
+ int pos = 0;
+
+ while (len-- > 0 && ustr[++pos] >= 0x80 && ustr[pos] <= 0xbf);
+ return pos;
+}
+
+
+// find the beginning of the UTF8 char pointed by str
+static INLINE int
+seekUTF8CharStart(char *str, int len)
+{
+ unsigned char* ustr = (unsigned char*) str;
+ int pos = 0;
+
+ while (len-- > 0 && ustr[pos] >= 0x80 && ustr[pos] <= 0xbf) --pos;
+ return pos;
+}
static void
@@ -177,6 +211,7 @@
range->count = tPtr->textLen - range->position;
}
+
static void
memmv(char *dest, char *src, int size)
{
@@ -200,7 +235,8 @@
int vp = tPtr->viewPosition;
while (TEXT_WIDTH(tPtr, tPtr->viewPosition) > tPtr->usableWidth) {
- tPtr->viewPosition++;
+ tPtr->viewPosition +=
oneUTF8CharForward(&tPtr->text[tPtr->viewPosition],
+ tPtr->textLen -
tPtr->viewPosition);
}
return vp!=tPtr->viewPosition;
}
@@ -210,11 +246,11 @@
incrToFit2(TextField *tPtr)
{
int vp = tPtr->viewPosition;
+
while (TEXT_WIDTH2(tPtr, tPtr->viewPosition, tPtr->cursorPosition)
>= tPtr->usableWidth)
- tPtr->viewPosition++;
-
-
+ tPtr->viewPosition +=
oneUTF8CharForward(&tPtr->text[tPtr->viewPosition],
+ tPtr->cursorPosition -
tPtr->viewPosition);
return vp!=tPtr->viewPosition;
}
@@ -222,14 +258,16 @@
static void
decrToFit(TextField *tPtr)
{
- while (TEXT_WIDTH(tPtr, tPtr->viewPosition-1) < tPtr->usableWidth
- && tPtr->viewPosition>0)
- tPtr->viewPosition--;
+ int vp = tPtr->viewPosition;
+
+ while (vp > 0 && (vp += oneUTF8CharBackward(&tPtr->text[vp], vp),
+ TEXT_WIDTH(tPtr, vp)) < tPtr->usableWidth) {
+ tPtr->viewPosition = vp;
+ }
}
#undef TEXT_WIDTH
#undef TEXT_WIDTH2
-
static WMData*
@@ -419,11 +457,9 @@
if (position < 0 || position >= tPtr->textLen) {
/* append the text at the end */
strcat(tPtr->text, text);
-
- incrToFit(tPtr);
-
tPtr->textLen += len;
tPtr->cursorPosition += len;
+ incrToFit(tPtr);
} else {
/* insert text at position */
memmv(&(tPtr->text[position+len]), &(tPtr->text[position]),
@@ -456,12 +492,11 @@
memmv(&(tPtr->text[range.position]),
&(tPtr->text[range.position+range.count]),
tPtr->textLen - (range.position+range.count) + 1);
+ /* better than nothing ;) */
+ if (tPtr->cursorPosition > range.position)
+ tPtr->viewPosition +=
oneUTF8CharBackward(&tPtr->text[tPtr->viewPosition],
+ tPtr->viewPosition);
tPtr->textLen -= range.count;
-
- /* try to keep cursorPosition at the same place */
- tPtr->viewPosition -= range.count;
- if (tPtr->viewPosition < 0)
- tPtr->viewPosition = 0;
tPtr->cursorPosition = range.position;
decrToFit(tPtr);
@@ -1096,16 +1131,18 @@
#endif
case XK_Left:
if (tPtr->cursorPosition > 0) {
+ int i;
paintCursor(tPtr);
+
+ i = tPtr->cursorPosition;
+ i += oneUTF8CharBackward(&tPtr->text[i], i);
if (controled) {
- int i = tPtr->cursorPosition - 1;
-
while (i > 0 && tPtr->text[i] != ' ') i--;
while (i > 0 && tPtr->text[i] == ' ') i--;
tPtr->cursorPosition = (i > 0) ? i + 1 : 0;
} else
- tPtr->cursorPosition--;
+ tPtr->cursorPosition = i;
if (tPtr->cursorPosition < tPtr->viewPosition) {
tPtr->viewPosition = tPtr->cursorPosition;
@@ -1131,24 +1168,20 @@
#endif
case XK_Right:
if (tPtr->cursorPosition < tPtr->textLen) {
+ int i;
paintCursor(tPtr);
+
+ i = tPtr->cursorPosition;
if (controled) {
- int i = tPtr->cursorPosition;
-
while (tPtr->text[i] && tPtr->text[i] != ' ') i++;
while (tPtr->text[i] == ' ') i++;
+ } else {
+ i += oneUTF8CharForward(&tPtr->text[i], tPtr->textLen - i);
+ }
+ tPtr->cursorPosition = i;
- tPtr->cursorPosition = i;
- } else {
- tPtr->cursorPosition++;
- }
- while (WMWidthOfString(tPtr->font,
- &(tPtr->text[tPtr->viewPosition]),
- tPtr->cursorPosition-tPtr->viewPosition)
- > tPtr->usableWidth) {
- tPtr->viewPosition++;
- refresh = 1;
- }
+ refresh = incrToFit2(tPtr);
+
if (!refresh)
paintCursor(tPtr);
}
@@ -1201,13 +1234,9 @@
paintCursor(tPtr);
tPtr->cursorPosition = tPtr->textLen;
tPtr->viewPosition = 0;
- while (WMWidthOfString(tPtr->font,
- &(tPtr->text[tPtr->viewPosition]),
- tPtr->textLen-tPtr->viewPosition)
- > tPtr->usableWidth) {
- tPtr->viewPosition++;
- refresh = 1;
- }
+
+ refresh = incrToFit(tPtr);
+
if (!refresh)
paintCursor(tPtr);
}
@@ -1231,9 +1260,11 @@
data = (void*)WMDeleteTextEvent;
textEvent = WMTextDidChangeNotification;
} else if (tPtr->cursorPosition > 0) {
+ int i = oneUTF8CharBackward(&tPtr->text[tPtr->cursorPosition],
+ tPtr->cursorPosition);
WMRange range;
- range.position = tPtr->cursorPosition - 1;
- range.count = 1;
+ range.position = tPtr->cursorPosition + i;
+ range.count = -i;
WMDeleteTextFieldRange(tPtr, range);
data = (void*)WMDeleteTextEvent;
textEvent = WMTextDidChangeNotification;
@@ -1261,7 +1292,8 @@
} else if (tPtr->cursorPosition < tPtr->textLen) {
WMRange range;
range.position = tPtr->cursorPosition;
- range.count = 1;
+ range.count =
oneUTF8CharForward(&tPtr->text[tPtr->cursorPosition],
+ tPtr->textLen -
tPtr->cursorPosition);
WMDeleteTextFieldRange(tPtr, range);
data = (void*)WMDeleteTextEvent;
textEvent = WMTextDidChangeNotification;
@@ -1356,21 +1388,24 @@
a = tPtr->viewPosition;
b = tPtr->textLen;
- while (a < b && b-a>1) {
+ while (a < b) {
mid = (a+b)/2;
+ mid += seekUTF8CharStart(&tPtr->text[mid], mid - a);
tw = WMWidthOfString(tPtr->font, &(tPtr->text[tPtr->viewPosition]),
- mid - tPtr->viewPosition);
- if (tw > x)
+ mid - tPtr->viewPosition + 1);
+ if (tw > x) {
b = mid;
- else if (tw < x)
- a = mid;
- else
+ } else if (tw < x) {
+ if (a == mid)
+ a += oneUTF8CharForward(&tPtr->text[mid], b - a);
+ else
+ a = mid;
+ } else {
return mid;
+ }
}
-
- return (a+b)/2;
+ return b;
}
-
static void
@@ -1447,11 +1482,13 @@
&(tPtr->text[tPtr->viewPosition]),
tPtr->cursorPosition-tPtr->viewPosition)
> tPtr->usableWidth) {
- tPtr->viewPosition++;
+ tPtr->viewPosition +=
oneUTF8CharForward(&tPtr->text[tPtr->viewPosition],
+ tPtr->textLen -
tPtr->viewPosition);
}
} else if (tPtr->viewPosition > 0 && event->xmotion.x < 0) {
paintCursor(tPtr);
- tPtr->viewPosition--;
+ tPtr->viewPosition +=
oneUTF8CharBackward(&tPtr->text[tPtr->viewPosition],
+ tPtr->viewPosition);
}
tPtr->cursorPosition =
diff -r 6c6cf07271fc -r bd0c670bda80 WPrefs.app/FontSimple.c
--- a/WPrefs.app/FontSimple.c Tue Apr 25 13:01:51 2006 -0700
+++ b/WPrefs.app/FontSimple.c Tue Apr 25 16:52:43 2006 -0700
@@ -312,9 +312,14 @@
getSelectedFont(_Panel *panel, FcChar8 *curfont)
{
WMListItem *item;
- FcPattern *pat= FcNameParse(curfont);
+ FcPattern *pat;
char *name;
+ if (curfont)
+ pat= FcNameParse(curfont);
+ else
+ pat= FcPatternCreate();
+
item= WMGetListSelectedItem(panel->familyL);
if (item)
{
@@ -358,12 +363,13 @@
WMMenuItem *item= WMGetPopUpButtonMenuItem(panel->optionP,
WMGetPopUpButtonSelectedItem(panel->optionP));
char *fn= WMGetMenuItemRepresentedObject(item);
- WMFont *font= WMCreateFont(WMWidgetScreen(panel->box), fn);
- if (font)
- {
- WMSetTextFieldFont(panel->sampleT, font);
- WMReleaseFont(font);
+ if (fn) {
+ WMFont *font= WMCreateFont(WMWidgetScreen(panel->box), fn);
+ if (font) {
+ WMSetTextFieldFont(panel->sampleT, font);
+ WMReleaseFont(font);
+ }
}
}
@@ -451,8 +457,8 @@
ofont= (FcChar8*)WMGetMenuItemRepresentedObject(item);
nfont= getSelectedFont(panel, ofont);
- wfree(ofont);
-
+ if (ofont)
+ wfree(ofont);
WMSetMenuItemRepresentedObject(item, nfont);
}
updateSampleFont(panel);
@@ -471,7 +477,8 @@
ofont = (FcChar8*)WMGetMenuItemRepresentedObject(item);
nfont= getSelectedFont(panel, ofont);
- wfree(ofont);
+ if (ofont)
+ wfree(ofont);
WMSetMenuItemRepresentedObject(item, nfont);
--
To unsubscribe, send mail to [EMAIL PROTECTED]