\n";
/*
Colored rectangle. Each user can pick one. His name will show under the selected rectangle.
When the user place a digit on the grid, the selected rectangle color will be used.
*/
//lines += "
\n";
lines += "
\n";
}
VARVAL v;
v.var = VAR_CONTENT;
v.val = lines;
res.push_back(v);
}else if (strcmp(var,REQ_FOCUS)==0){
// Does not work with the keyboard at all.
}else if (strcmp(var,REQ_CHAT)==0){
VARVAL notify_var;
notify_var.var = VAR_NOTIFY;
appendchat(val,notify_var.val,res,ctx);
res.emplace_back(move(notify_var));
}else if (ctx.maywrite){
if (strcmp(var,"place")==0){
unsigned lo,co,guess;
if (splitline(val,',',limits(lo,0u,8u),limits(co,0u,8u),enums(guess,{1u,2u}))){
auto &gg = grid[lo][co];
if (gg.visible){
error = MSG_U(E_CANTSELTHISCELL,"You can't set this cell");
}else{
// We can set a value. If it is wrong, it will show in red.
// If you click over again, it will erase itself.
unsigned newval = seldigs[ctx.session]+1;
const char *color = "black";
const char *gcolor = "none";
unsigned gnewval = 0;
VARVAL var;
var.var = VAR_NOTIFY;
var.val = string_f ("var doc = document.getElementById('grid-%s');\n",gameid.c_str());
var.val += "if (doc != null){\n";
if (gg.user_value == 0){
auto a = prefs.find(ctx.username);
if (guess == 2){
if (a != prefs.end()){
if (gg.user_guess == newval && gg.guess_color == a->second.color){
// The user erased is guess
gg.user_guess = 0;
gg.guess_color = 0;
gcolor = "none";
gnewval = 0;
}else{
gg.user_guess = newval;
gg.guess_color = a->second.color;
gcolor = colors[a->second.color];
gnewval = newval;
}
color="none";
}
}else{
gg.user_value = newval;
gg.username = ctx.username;
gg.user_guess = 0;
gg.guess_color = 0;
if (gg.user_value != gg.value){
color = "red";
}else{
auto a = prefs.find(ctx.username);
if (a != prefs.end()){
color = colors[a->second.color];
var.val += "\tvar circles = doc.getElementsByTagName('circle');\n";
var.val += "\tfor(var i = 0; i< circles.length;i++){\n";
var.val += "\t\tvar e = circles[i];\n";
if (a->second.last_line != lo || a->second.last_column != co){
// Erase the last solved cell circle
var.val += string_f("\t\tif (e.getAttribute('id') == 'c%u,%u'){\n"
,a->second.last_line,a->second.last_column);
var.val += string_f("\t\t\te.style.stroke = 'none';\n");
var.val += "\t\t}else";
}
// Draw the new solved cell circle
var.val += string_f(" if (e.getAttribute('id') == 'c%u,%u'){\n",lo,co);
var.val += string_f("\t\t\te.style.stroke = '%s';\n",color);
var.val += "\t\t}\n";
var.val += "\t}\n";
a->second.last_column = co;
a->second.last_line = lo;
}
}
}
}else if (gg.user_value == newval){
gg.user_value = 0;
color = "white";
}
setmodified(ctx.username);
var.val += "\tvar txts = doc.getElementsByTagName('text');\n";
var.val += "\tfor(var i = 0; i< txts.length;i++){\n";
var.val += "\t\tvar e = txts[i];\n";
var.val += string_f("\t\tif (e.getAttribute('id') == 'g%u,%u'){\n",lo,co);
var.val += string_f("\t\t\te.style.fill = '%s';\n",gcolor);
var.val += string_f("\t\t\te.style.stroke = '%s';\n",gcolor);
var.val += string_f("\t\t\te.textContent = '%u';\n",gnewval);
var.val += string_f("\t\t}else if (e.getAttribute('id') == '%u,%u'){\n",lo,co);
var.val += string_f("\t\t\te.style.fill = '%s';\n",color);
var.val += string_f("\t\t\te.style.stroke = '%s';\n",color);
var.val += string_f("\t\t\te.textContent = '%u';\n",newval);
var.val += "\t\t\tbreak;\n";
var.val += "\t\t}\n";
var.val += "\t}\n";
var.val += "}\n";
// Update the digit selector on the side to tell which digits have been solved (all 9 has been found)
compute_grid_full();
var.val += string_f ("var doc = document.getElementById('sudosel-%s');\n",gameid.c_str());
var.val += "if (doc != null){\n";
var.val += "\tvar txts = doc.getElementsByTagName('text');\n";
for (unsigned i=0; i<9; i++){
if (grid_full[i]){
var.val += string_f("\ttxts[%u].style.stroke='lightgray';\n",i);
var.val += string_f("\ttxts[%u].style.fill='lightgray';\n",i);
}
}
var.val += "}\n";
res.push_back(var);
documentd_setchanges (res);
}
}else{
error = MSG_U(E_IVLDPLACESUD,"Invalid place command (need 2 value)");
}
}else if (strcmp(var,"select")==0){
unsigned sel = atoi(val);
if (sel > 0 && sel < 10){
sel--;
if (grid_full[sel]){
error = MSG_U(E_ALLDIGITFOUND,"The nine positions are known for this digit");
}else{
seldigs[ctx.session] = sel;
setmodified(ctx.username);
VARVAL var;
var.var = VAR_SCRIPT;
var.val = string_f ("var doc = document.getElementById('sudosel-%s');\n",gameid.c_str());
var.val += "if (doc != null){\n";
var.val += "\tvar paths = doc.getElementsByTagName('path');\n";
for (unsigned i=0; i<9; i++){
var.val += string_f("\tpaths[%u].style.fill='%s';\n",i,i==sel ? "pink" : "white");
}
var.val += "}\n";
res.push_back(var);
}
}
}else if (strcmp(var,"avatar")==0){
unsigned avatar = atoi(val);
if (avatar < nbcolor){
// User is not allowed to pick an avatar used by another user
bool fail = false;
for (auto &a:prefs){
if (a.second.color == avatar && a.first != ctx.username){
error = MSG_U(E_USEDAVATAR,"This color is already used!");
fail = true;
break;
}
}
if (!fail){
auto &u = prefs[ctx.username];
unsigned old_avatar = u.color;
u.color = avatar;
// Change all the guess color
for (auto &g:grid){
for (auto &gg:g){
if (gg.user_guess != 0 && gg.guess_color == old_avatar){
gg.guess_color = avatar;
}
}
}
redraw_notify(res);
}
}else{
documentd_error (res,"Color selection from 0 to 5");
}
}else if (strcmp(var,"newgame")==0){
glocal grid;
unsigned uval = atoi(val);
if (uval > 3){
documentd_error (res,"Difficulty from 0 to 3");
}else{
difficulty = uval;
static const char *tbdiff[]={"simple", "easy", "intermediate", "expert"};
(string_f("qqwing --generate 1 --compact --solution --difficulty %s",tbdiff[difficulty]),10);
debug_printf (D_SUDOKU,"read qqwing %s\n",line);
if (noline < 9){
auto &g = glocal.grid[noline];
for (unsigned i=0; i<9; i++){
char car = line[i];
auto &gg = g[i];
gg.reset();
if (car != '.'){
gg.visible = 1;
gg.value = car - '0';
}
}
}
if (noline >= 10 && noline < 19){
auto &g = glocal.grid[noline-10];
for (unsigned i=0; i<9; i++){
g[i].value = line[i]-'0';
}
}
return 0;
tlmp_error ("sudoku command=%s line=%s\n",command,line);
return 0;
setmodified(ctx.username);
compute_grid_full();
redraw_notify(res);
// Make all nine digits available
VARVAL var;
var.var = VAR_NOTIFY;
var.val = string_f ("var doc = document.getElementById('sudosel-%s');\n",gameid.c_str());
var.val += "if (doc != null){\n";
var.val += "\tvar txts = doc.getElementsByTagName('text');\n";
for (unsigned i=0; i<9; i++){
var.val += string_f("\ttxts[%u].style.stroke='black';\n",i);
var.val += string_f("\ttxts[%u].style.fill='black';\n",i);
}
var.val += "}\n";
res.push_back(var);
}
}else{
tlmp_error ("sudoku invalid command %s\n",var);
}
}else{
error = MSG_U(E_READONLY,"You do not have write access to this game");
}
if (error.size() > 0){
update_msg(false,error,"red",res);
}else{
update_msg(false," ","white",res);
}
}