aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSebastian Geerken <devnull@localhost>2012-11-02 18:48:01 +0100
committerSebastian Geerken <devnull@localhost>2012-11-02 18:48:01 +0100
commit163ea78f0fe31ed999d94407c780af7efa520b68 (patch)
tree0f9f5b7e29b830f06ee6217883dcd57d530a2899
parent76cf4173b653db09c3bacbb0d01c1e153e52eac4 (diff)
parentec742a77c99526479fe57afc5fbbdf860fed4003 (diff)
Merge.
-rw-r--r--dw/fltkui.cc49
-rw-r--r--dw/textblock.cc40
-rw-r--r--dw/textblock.hh16
3 files changed, 77 insertions, 28 deletions
diff --git a/dw/fltkui.cc b/dw/fltkui.cc
index 7d2f6cc5..5e4f3c56 100644
--- a/dw/fltkui.cc
+++ b/dw/fltkui.cc
@@ -75,6 +75,49 @@ int CustInput2::handle(int e)
return Fl_Input::handle(e);
}
+
+/*
+ * Used to handle some keystrokes as shortcuts to option menuitems
+ * (i.e. jump to the next menuitem whose label starts with the pressed key)
+ */
+class CustChoice : public Fl_Choice {
+public:
+ CustChoice (int x, int y, int w, int h, const char* l=0) :
+ Fl_Choice(x,y,w,h,l) {};
+ int handle(int e);
+};
+
+int CustChoice::handle(int e)
+{
+ int k = Fl::event_key();
+ unsigned modifier = Fl::event_state() & (FL_SHIFT|FL_CTRL|FL_ALT|FL_META);
+
+ _MSG("CustChoice::handle %p e=%d active=%d focus=%d\n",
+ this, e, active(), (Fl::focus() == this));
+ if (Fl::focus() != this) {
+ ; // Not Focused, let FLTK handle it
+ } else if (e == FL_KEYDOWN) {
+ if (modifier == 0 && isalnum(k)) {
+ int t = value()+1 >= size() ? 0 : value()+1;
+ while (t != value()) {
+ const Fl_Menu_Item *mi = &(menu()[t]);
+ if (mi->submenu()) // submenu?
+ ;
+ else if (mi->label() && mi->active()) { // menu item?
+ if (k == tolower(mi->label()[0])) {
+ value(mi);
+ return 1; // Let FLTK know we used this key
+ }
+ }
+ if (++t == size())
+ t = 0;
+ }
+ }
+ }
+
+ return Fl_Choice::handle(e);
+}
+
//----------------------------------------------------------------------------
namespace dw {
@@ -995,9 +1038,9 @@ Fl_Widget *FltkOptionMenuResource::createNewWidget (core::Allocation
*allocation)
{
Fl_Choice *choice =
- new Fl_Choice (allocation->x, allocation->y,
- allocation->width,
- allocation->ascent + allocation->descent);
+ new CustChoice (allocation->x, allocation->y,
+ allocation->width,
+ allocation->ascent + allocation->descent);
choice->menu(menu);
return choice;
}
diff --git a/dw/textblock.cc b/dw/textblock.cc
index 31493c15..0c291e1f 100644
--- a/dw/textblock.cc
+++ b/dw/textblock.cc
@@ -1791,22 +1791,9 @@ void Textblock::fillSpace (Word *word, core::style::Style *style)
// TODO: This line does not work: addBreakOption (word, style);
+ // Do not override a previously set break penalty.
if (!word->content.space) {
- // Do not override a previously set break penalty.
- if (!word->badnessAndPenalty.lineMustBeBroken()) {
- switch (style->whiteSpace) {
- case core::style::WHITE_SPACE_NORMAL:
- case core::style::WHITE_SPACE_PRE_LINE:
- word->badnessAndPenalty.setPenalty (0);
- break;
-
- case core::style::WHITE_SPACE_PRE:
- case core::style::WHITE_SPACE_NOWRAP:
- case core::style::WHITE_SPACE_PRE_WRAP:
- word->badnessAndPenalty.setPenaltyProhibitBreak ();
- break;
- }
- }
+ setBreakOption (word, style);
word->content.space = true;
word->effSpace = word->origSpace = style->font->spaceWidth +
@@ -1830,6 +1817,29 @@ void Textblock::fillSpace (Word *word, core::style::Style *style)
}
}
+/**
+ * Set a break option, if allowed by the style. Called by fillSpace
+ * (and so addSpace), but may be called, via addBreakOption(), as an
+ * alternative, e. g. for ideographic characters.
+ */
+void Textblock::setBreakOption (Word *word, core::style::Style *style)
+{
+ if (!word->badnessAndPenalty.lineMustBeBroken()) {
+ switch (style->whiteSpace) {
+ case core::style::WHITE_SPACE_NORMAL:
+ case core::style::WHITE_SPACE_PRE_LINE:
+ word->badnessAndPenalty.setPenalty (0);
+ break;
+
+ case core::style::WHITE_SPACE_PRE:
+ case core::style::WHITE_SPACE_NOWRAP:
+ case core::style::WHITE_SPACE_PRE_WRAP:
+ word->badnessAndPenalty.setPenaltyProhibitBreak ();
+ break;
+ }
+ }
+}
+
void Textblock::addHyphen ()
{
int wordIndex = words->size () - 1;
diff --git a/dw/textblock.hh b/dw/textblock.hh
index 70759079..ccc209c5 100644
--- a/dw/textblock.hh
+++ b/dw/textblock.hh
@@ -424,6 +424,7 @@ protected:
void fillWord (Word *word, int width, int ascent, int descent,
bool canBeHyphenated, core::style::Style *style);
void fillSpace (Word *word, core::style::Style *style);
+ void setBreakOption (Word *word, core::style::Style *style);
int textWidth (const char *text, int start, int len,
core::style::Style *style);
void calcTextSize (const char *text, size_t len, core::style::Style *style,
@@ -621,20 +622,15 @@ public:
bool addAnchor (const char *name, core::style::Style *style);
void addSpace (core::style::Style *style);
+ /**
+ * Add a break option (see setBreakOption() for details). Used
+ * instead of addStyle for ideographic characters.
+ */
inline void addBreakOption (core::style::Style *style)
{
int wordIndex = words->size () - 1;
if (wordIndex >= 0)
- addBreakOption (words->getRef(wordIndex), style);
- }
-
- // TODO Re-evaluate again. When needed, which penalty values, etc.
- inline void addBreakOption (Word *word, core::style::Style *style)
- {
- if (style->whiteSpace != core::style::WHITE_SPACE_NOWRAP &&
- style->whiteSpace != core::style::WHITE_SPACE_PRE)
- if (word->badnessAndPenalty.lineMustBeBroken())
- word->badnessAndPenalty.setPenalty (0);
+ setBreakOption (words->getRef(wordIndex), style);
}
void addHyphen();