1 #include "wikiattrib.h"
2 #include "wikiformat.h"
4 #include "util_check.h"
7 bool WikiAttrib1::readAttrib1 (WikiMotorObjVec* cell, bool& rc) {
12 if (cell->size () == 0) {
13 if (mode == M_ATTRIB || mode == M_ATTRIB_TEXT)
18 if (cell->splitChar_keyword ('=', key, vval)) {
19 if (paramID (key, vval, ferr)) {
20 } else if (paramClass (key, vval, ferr)) {
22 } else if (paramDataPrefix (key, vval, ferr)) {
24 } else if (paramOnClickCheck (key)) {
25 if (! checkScript (vval, onclick, ferr)) {
26 wiki->errorMsg.append (cell->dump ()).append (CharConst (": link script error.\n"));
29 } else if (paramOnFocusCheck (key)) {
30 if (! checkScript (vval, onfocus, ferr)) {
31 wiki->errorMsg.append (cell->dump ()).append (CharConst (": link script error.\n"));
34 } else if (paramOnBlurCheck (key)) {
35 if (! checkScript (vval, onblur, ferr)) {
36 wiki->errorMsg.append (cell->dump ()).append (CharConst (": link script error.\n"));
39 } else if (paramOnChangeCheck (key)) {
40 if (! checkScript (vval, onchange, ferr)) {
41 wiki->errorMsg.append (cell->dump ()).append (CharConst (": link script error.\n"));
44 } else if ((selector & SEL_TARGET) && paramTargetCheck (key)) {
45 paramTargetBody (key, vval.textOut (wiki), target, ferr);
46 } else if (readAttribMore (key, vval, ferr)) {
48 if (mode == M_ATTRIB) {
49 wiki->errorMsg.append (cell->dump ()).append (CharConst (": bad attribute.\n"));
55 if (selector & SEL_CLASS2) {
56 paramClassValue (*cell, classlist, ferr);
57 } else if (selector & SEL_TARGET2) {
58 paramTargetBody (uEmpty, cell->textOut (wiki), target, ferr);
59 } else if ((selector & SEL_ONCLICK2) && checkScript (*cell, onclick, ferr)) {
60 } else if ((selector & SEL_MULTIPLE2) && match (key, CharConst ("multiple"))) {
62 } else if ((selector & SEL_DEFAULT2) && match (key, CharConst ("default"))) {
64 } else if ((selector & SEL_SCRIPT2) && checkScript (*cell, script, ferr)) {
65 } else if (readAttribMore2 (key, *cell, ferr)) {
67 if (mode == M_ATTRIB) {
68 wiki->errorMsg.append (cell->dump ()).append (CharConst (": bad attribute.\n"));
82 bool WikiAttrib1::shiftAttrib (WikiMotorObjVecPtr& vec) {
84 WikiMotorObjVecPtr v2;
86 while (vec->size () > 0) {
89 v2 = WikiMotorObjVecPtr (new WikiMotorObjVec);
90 if (vec->splitChar (':', cell, *v2) || mode == M_ATTRIB || mode == M_ATTRIB_TEXT) {
91 if (! readAttrib1 (&cell, rc))
101 void WikiAttrib1::skipAttrib (WikiMotorObjVecPtr& vec) {
102 WikiMotorObjVecPtr v2;
104 if (vec->size () > 0) {
105 WikiMotorObjVec cell;
107 v2 = WikiMotorObjVecPtr (new WikiMotorObjVec);
108 if (vec->splitChar (':', cell, *v2)) {
114 bool WikiAttrib1::readAttrib (WikiMotorObjVecVec::const_iterator& b, const WikiMotorObjVecVec::const_iterator& e) {
118 WikiMotorObjVec* cell = b->get ();
119 if (! readAttrib1 (cell, rc))
126 bool WikiAttrib1::checkScript (WikiMotorObjVec& vec, ustring& scr, bool& ferr) {
130 for (i = 0; i < vec.size () && vec[i]->type == WikiMotorObj::wiki_funcLink; i ++) {
131 WikiMotorObjFuncLink* fn = WikiMotorObjFuncLink_type (&*vec[i]);
132 u = fn->execDefunArgs (wiki);
133 // XXX: 末尾の空白を除去し,セミコロンを確認する。
143 bool WikiAttrib1::shiftLink (WikiMotorObjVecPtr& vec, ustring& url, bool& fscript) {
146 WikiMotorObjVec cell;
147 WikiMotorObjVecPtr v2 (new WikiMotorObjVec);
149 rc = vec->splitChar (':', cell, *v2);
150 if (checkScript (cell, url, ferr)) {
154 } else if (rc && cell.match (CharConst ("http"), CharConst ("https"))) {
155 ustring proto = cell.dump ();
158 v2 = WikiMotorObjVecPtr (new WikiMotorObjVec);
159 rc = vec->splitChar (':', cell, *v2);
160 if (! cell.splitURL_2 (wiki, proto, url)) {
165 if (vec->size () > 0) {
167 v2 = WikiMotorObjVecPtr (new WikiMotorObjVec);
168 rc = vec->splitChar (':', cell, *v2);
169 if (cell.splitURL_3 (wiki, url, url))
173 } else if (cell.splitURLPath (wiki, url)) {
182 bool WikiAttrib1::readLink (WikiMotorObjVecVec::const_iterator& b, const WikiMotorObjVecVec::const_iterator& e, ustring& url, bool& fscript, bool noscript) {
185 WikiMotorObjVec* cell;
186 static uregex re (CharConst ("^[a-z]{3,6}$"));
192 if (! noscript && checkScript (*cell, url, ferr)) {
196 } else if (rc && cell->regmatch (re)) {
197 ustring proto = cell->dump ();
200 if (! cell->splitURL_2 (wiki, proto, url)) {
207 if (cell->splitURL_3 (wiki, url, url))
211 } else if (cell->splitURLPath (wiki, url)) {
220 bool WikiAttrib1::shiftName (WikiMotorObjVecPtr& vec, ustring& name) {
221 if (vec->size () > 0) {
222 WikiMotorObjVec cell;
223 WikiMotorObjVecPtr v2 (new WikiMotorObjVec);
225 vec->splitChar (':', cell, *v2);
226 name = cell.textOut (wiki);
234 void WikiAttrib1::output (MotorOutput* out) {
235 wiki->outputID (out, id);
236 wiki->outputClass (out, classlist);
238 // std::pair<ustring,ustring>::const_iterator b, e;
239 std::vector<datapre_t>::const_iterator b, e;
240 b = datapre.begin ();
242 for (; b < e; b ++) {
243 wiki->outputName (out, (*b).first.c_str (), (*b).first.size (), (*b).second);
247 wiki->outputNum (out, CharConst ("start"), start);
248 wiki->outputSubmitScript (out, CharConst ("onclick"), onclick, scriptcut);
249 wiki->outputSubmitScript (out, CharConst ("onfocus"), onfocus, scriptcut);
250 wiki->outputSubmitScript (out, CharConst ("onblur"), onblur, scriptcut);
251 wiki->outputSubmitScript (out, CharConst ("onchange"), onchange, scriptcut);
252 wiki->outputName (out, CharConst ("target"), target);
253 wiki->outputFlag (out, CharConst ("multiple"), fmultiple);
258 bool WikiAttrib1::paramID (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
259 if (match (key, CharConst ("id"))) {
260 paramIDValue (key, vval, id, ferr);
267 void WikiAttrib1::paramIDValue (const ustring& key, WikiMotorObjVec& vval, ustring& var, bool& ferr) {
268 ustring value (vval.textOut (wiki));
269 if (checkWikiID (value)) {
273 wiki->errorMsg.append (key).append (uEq).append (value).append (CharConst (": bad value\n"));
278 bool WikiAttrib1::paramClass (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
279 if (match (key, CharConst ("class"))) {
280 paramClassValue (vval, classlist, ferr);
287 void WikiAttrib1::paramClassValue (WikiMotorObjVec& vval, std::vector<ustring>& var, bool& ferr) {
288 WikiMotorObjVecVec args;
290 vval.splitCharA (',', args);
291 for (int i = 0; i < args.size (); i ++) {
292 ustring value (args[i]->textOut (wiki));
293 if (value.length () > 0) {
294 if (checkWikiID (value)) {
295 var.push_back (value);
297 wiki->errorMsg.append (value).append (CharConst (": bad class name\n"));
304 bool WikiAttrib1::paramWidth (const ustring& key, WikiMotorObjVec& vval, ustring& var, bool& ferr) {
305 if (match (key, CharConst ("width"), CharConst ("w"))) {
306 paramWidthValue (key, vval, var, ferr);
313 bool WikiAttrib1::paramHeight (const ustring& key, WikiMotorObjVec& vval, ustring& var, bool& ferr) {
314 if (match (key, CharConst ("height"), CharConst ("h"))) {
315 paramWidthValue (key, vval, var, ferr);
322 void WikiAttrib1::paramWidthValue (const ustring& key, WikiMotorObjVec& vval, ustring& var, bool& ferr) {
323 ustring value (vval.textOut (wiki));
324 if (checkWidth (value)) {
328 wiki->errorMsg.append (key).append (uEq).append (value).append (CharConst (": bad value\n"));
333 bool WikiAttrib1::paramSize (const char* name, size_t namelen, const ustring& key, WikiMotorObjVec& vval, ustring& var, bool& ferr) {
334 if (match (key, name, namelen)) {
335 ustring value (vval.textOut (wiki));
336 if (checkNum (value)) {
347 void WikiAttrib1::paramUNum (const ustring& value, int& var, const ustring& name) {
348 if (checkNum (value)) {
349 var = strtoul (value);
351 wiki->errorMsg.append (name).append (uEq).append (value).append (uErrorBadValue).append (uLF);
355 void WikiAttrib1::paramColor (const ustring& value, ustring& var, const ustring& name) {
356 if (checkColor (value)) {
359 wiki->errorMsg.append (name).append (uEq).append (value).append (uErrorBadValue).append (uLF);
363 bool WikiAttrib1::paramTargetCheck (const ustring& key) {
364 return match (key, CharConst ("target"));
367 void WikiAttrib1::paramTargetBody (const ustring& key, const ustring& value, ustring& var, bool& ferr) {
368 if (value.length () == 0 || checkWikiID (value)) {
371 if (key.length () > 0)
372 wiki->errorMsg.append (key).append (uEq).append (value).append (CharConst (": bad target name.\n"));
374 wiki->errorMsg.append (value).append (CharConst (": bad target name.\n"));
379 bool WikiAttrib1::paramOnClickCheck (const ustring& name) {
380 return match (name, CharConst ("onclick"));
383 bool WikiAttrib1::paramOnFocusCheck (const ustring& name) {
384 return match (name, CharConst ("onfocus"));
387 bool WikiAttrib1::paramOnBlurCheck (const ustring& name) {
388 return match (name, CharConst ("onblur"));
391 bool WikiAttrib1::paramOnChangeCheck (const ustring& name) {
392 return match (name, CharConst ("onchange"));
396 bool WikiAttrib1::paramDataPrefix (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
397 if (matchHead (key, CharConst ("data-")) && checkWikiID (key)) {
398 ustring value (vval.textOut (wiki));
399 if (checkWikiID (value)) {
400 datapre.push_back (std::pair<ustring,ustring> (key, value));
403 wiki->errorMsg.append (key).append (uEq).append (value).append (CharConst (": bad value\n"));
412 /* ============================================================ */
413 void WikiAttribTable::init () {
418 #ifdef WIKITABLEATTRIB
424 // halign = HAlignNone;
429 while (! classlist.empty ())
430 classlist.pop_back ();
437 void WikiAttribTable::copyFrom (WikiAttribTable& b) {
441 for (i = 0; i < b.classlist.size (); i ++)
442 classlist.push_back (b.classlist[i]);
453 bool WikiAttribTable::readAttribMore (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
454 if (paramWidth (key, vval, width, ferr)) {
455 } else if (paramHeight (key, vval, height, ferr)) {
456 } else if (match (key, CharConst ("bgcolor"), CharConst ("bg"))) {
457 paramColor (vval.textOut (wiki), bgcolor, key);
461 #ifdef WIKITABLEATTRIB
462 if (match (key, CharConst ("cellspacing"), CharConst ("spc"))) {
463 paramUNum (vval.textOut (wiki), cellspacing, key);
464 } else if (match (key, CharConst ("cellpadding"))) {
465 paramUNum (vval.textOut (wiki), cellpadding, key);
483 bool WikiAttribTable::readAttribMore2 (const ustring& key, WikiMotorObjVec& cell, bool& ferr) {
484 if (match (key, CharConst ("left"), CharConst ("l"))) {
486 } else if (match (key, CharConst ("right"), CharConst ("r"))) {
487 halign = HAlignRight;
488 } else if (match (key, CharConst ("center"), CharConst ("c"))) {
489 halign = HAlignCenter;
493 #ifdef WIKITABLEATTRIB
494 if (match (key, CharConst ("noborder"), CharConst ("nb"))) {
498 if (match (key, CharConst ("padding"), CharConst ("pad"))) {
500 } else if (match (key, CharConst ("expanding"), CharConst ("expand"))) {
502 } else if (match (key, CharConst ("nowhite"), CharConst ("nw"))) {
504 } else if (match (key, CharConst ("turn"))) {
512 if (match (key, CharConst ("header"), CharConst ("h"))) {
514 } else if (match (key, CharConst ("top"), CharConst ("t"))) {
516 } else if (match (key, CharConst ("middle"), CharConst ("m"))) {
517 valign = VAlignMiddle;
518 } else if (match (key, CharConst ("bottom"), CharConst ("b"))) {
519 valign = VAlignBottom;
520 } else if (match (key, CharConst ("nowrap"), CharConst ("nw"))) {
522 } else if (match (key, CharConst ("*"))) {
536 void WikiAttribTable::outputMore (MotorOutput* out) {
539 out->out_raw (CharConst (" align=\"left\""));
542 out->out_raw (CharConst (" align=\"center\""));
545 out->out_raw (CharConst (" align=\"right\""));
548 wiki->outputName (out, CharConst ("width"), width);
549 wiki->outputName (out, CharConst ("height"), height);
550 wiki->outputName (out, CharConst ("bgcolor"), bgcolor);
554 #ifdef WIKITABLEATTRIB
555 wiki->outputName (out, CharConst ("border"), fnoborder ? 0 : 1, false);
556 wiki->outputName (out, CharConst ("cellspacing"), cellspacing, false);
557 wiki->outputName (out, CharConst ("cellpadding"), cellpadding, false);
564 out->out_raw (CharConst (" valign=\"top\""));
567 out->out_raw (CharConst (" valign=\"middle\""));
570 out->out_raw (CharConst (" valign=\"bottom\""));
573 wiki->outputFlag (out, CharConst ("nowrap"), fnowrap);
580 /* ============================================================ */
581 bool WikiAttribImg::readAttribMore (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
582 if (paramWidth (key, vval, width, ferr)) {
583 if (checkNum (width))
584 width.append (CharConst ("px"));
585 } else if (paramHeight (key, vval, height, ferr)) {
586 if (checkNum (height))
587 height.append (CharConst ("px"));
588 } else if (match (key, CharConst ("alt"))) {
589 alt = vval.textOut (wiki);
596 void WikiAttribImg::outputMore (MotorOutput* out) {
597 // wiki->outputName (out, CharConst ("width"), width);
598 // wiki->outputName (out, CharConst ("height"), height);
599 if (width.length () > 0 || height.length () > 0) {
600 out->out_raw (CharConst (" style=\""));
601 if (width.length () > 0)
602 out->out_raw (CharConst ("width:"))->out_toHTML_noCtrl (width)->out_raw (CharConst (";"));
603 if (height.length () > 0)
604 out->out_raw (CharConst ("height:"))->out_toHTML_noCtrl (height)->out_raw (CharConst (";"));
605 out->out_raw (CharConst ("\""));
610 /* ============================================================ */
611 bool WikiAttribInput::readAttribMore (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
612 if ((selector2 & SEL_INPUT) && paramSize (CharConst ("size"), key, vval, psize, ferr)) {
613 } else if ((selector2 & SEL_ELSIZE) && match (key, CharConst ("size"))) {
614 ustring v = vval.textOut (wiki);
615 if (match (v, CharConst ("*"))) {
617 } else if (checkNum (v)) {
618 elsize = to_int32 (v);
619 if (elsize < 0 || elsize > 999) {
625 } else if (paramWidth (key, vval, pwidth, ferr)) {
626 } else if ((selector2 & SEL_TEXTAREA) && paramSize (CharConst ("cols"), key, vval, pcols, ferr)) {
627 } else if ((selector2 & SEL_TEXTAREA) && paramSize (CharConst ("rows"), key, vval, prows, ferr)) {
628 } else if ((selector2 & SEL_TEXTAREA) && match (key, CharConst ("wrap"))) {
629 ustring value (vval.textOut (wiki));
630 if (match (value, CharConst ("off"))) {
632 } else if (match (value, CharConst ("soft"))) {
634 } else if (match (value, CharConst ("hard"))) {
637 wiki->errorMsg.append (key).append (CharConst ("=")).append (vval.dump ()).append (CharConst (": link script error.\n"));
641 } else if (match (key, CharConst ("accept"))) {
642 ustring value (vval.textOut (wiki));
643 if (match (value, CharConst ("camera"))) {
644 paccept.assign (CharConst ("image/*;capture=camera"));
646 static uregex re ("^"
647 "(" "[a-z_0-9-]+/[a-z_0-9.+*-]+" ")"
648 "(" "," "(" "[a-z_0-9-]+/[a-z_0-9.+*-]+" ")" ")*"
649 "(" ";" "[a-z_0-9-]+=[a-zA-Z_0-9.+*-]+" ")*"
651 if (checkRe (value, re)) {
663 bool WikiAttribInput::readAttribMore2 (const ustring& key, WikiMotorObjVec& cell, bool& ferr) {
664 if (key == uDefault) {
666 } else if ((selector2 & SEL_CHECK) && match (key, CharConst ("checked"))) {
668 } else if ((selector2 & SEL_TEXTAREA) && match (key, CharConst ("tab"))) {
676 void WikiAttribInput::outputMore (MotorOutput* out) {
677 wiki->outputName (out, CharConst ("size"), psize);
678 wiki->outputName (out, CharConst ("size"), elsize);
679 if (pwidth.size () > 0) {
680 if (checkNum (pwidth)) {
681 out->out_raw (CharConst (" style=\"width:"))->out_toHTML_noCtrl (pwidth)->out_raw (CharConst ("px;\""));
683 out->out_raw (CharConst (" style=\"width:"))->out_toHTML_noCtrl (pwidth)->out_raw (CharConst (";\""));
686 if (selector2 & SEL_CHECK) {
687 wiki->outputFlag (out, CharConst ("checked"), pchecked);
689 if (selector2 & SEL_TEXTAREA) {
690 wiki->outputName (out, CharConst ("cols"), pcols, false);
691 wiki->outputName (out, CharConst ("rows"), prows);
694 out->out_raw (CharConst (" wrap=\"off\""));
697 out->out_raw (CharConst (" wrap=\"soft\""));
698 // out->out_raw (CharConst (" wrap=\"virtual\""));
701 out->out_raw (CharConst (" wrap=\"hard\""));
702 // out->out_raw (CharConst (" wrap=\"physical\""));
707 ->out_raw (CharConst ("onkeypress"))
708 ->out_raw (CharConst ("=\""))
709 ->out_toHTML (ustring (CharConst ("return insertTab(event,this);")))
712 ->out_raw (CharConst ("onkeydown"))
713 ->out_raw (CharConst ("=\""))
714 ->out_toHTML (ustring (CharConst ("return insertTab(event,this);")))
717 ->out_raw (CharConst ("onkeyup"))
718 ->out_raw (CharConst ("=\""))
719 ->out_toHTML (ustring (CharConst ("return insertTab(event,this);")))
723 if (paccept.length () > 0) {
724 out->out_raw (CharConst (" accept=\""))
725 ->out_toHTML (paccept)
730 /* ============================================================ */
731 bool WikiAttribButton::readAttrib (WikiMotorObjVecVec::const_iterator& b, const WikiMotorObjVecVec::const_iterator& e) {
735 WikiMotorObjVec* cell = b->get ();
739 if (! readAttrib1 (cell, rc)) {
740 name = cell->textOut (wiki);
746 WikiMotorObjVec* cell = b->get ();
747 if (! readAttrib1 (cell, rc))
754 /* ============================================================ */
755 bool WikiAttribItem::readAttribMore (const ustring& key, WikiMotorObjVec& vval, bool& ferr) {
756 if (match (key, CharConst ("ulclass"))) {
757 if (owner && owner->parent && owner->parent->attrib.classlist.size () == 0) {
758 paramClassValue (vval, owner->parent->attrib.classlist, ferr);
760 } else if (match (key, CharConst ("ulid"))) {
761 if (owner && owner->parent && owner->parent->attrib.id.size () == 0) {
762 paramIDValue (key, vval, owner->parent->attrib.id, ferr);
764 } else if (owner && owner->parent && (owner->parent->attrib.selector & SEL_START) && match (key, CharConst ("start"))) {
765 paramUNum (vval.textOut (wiki), owner->parent->attrib.start, key);
772 /* ============================================================ */