Annotation of capa/capa51/GUITools/grader.funct.c, revision 1.4
1.3 albertel 1: /* interfaces to the C portions of CAPA for grader
2: Copyright (C) 1992-2000 Michigan State University
3:
4: The CAPA system is free software; you can redistribute it and/or
5: modify it under the terms of the GNU Library General Public License as
6: published by the Free Software Foundation; either version 2 of the
7: License, or (at your option) any later version.
8:
9: The CAPA system is distributed in the hope that it will be useful,
10: but WITHOUT ANY WARRANTY; without even the implied warranty of
11: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12: Library General Public License for more details.
13:
14: You should have received a copy of the GNU Library General Public
15: License along with the CAPA system; see the file COPYING. If not,
16: write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17: Boston, MA 02111-1307, USA.
18:
19: As a special exception, you have permission to link this program
20: with the TtH/TtM library and distribute executables, as long as you
21: follow the requirements of the GNU GPL in regard to all of the
22: software in the executable aside from TtH/TtM.
23: */
24:
1.1 albertel 25: /*
26: * grader.funct.c
1.3 albertel 27: * Guy Albertelli II 1996
1.1 albertel 28: */
29: #include <stdio.h>
30: #include <tk.h>
1.4 ! albertel 31: #include <pProj/capaCommon.h>
1.1 albertel 32: #include <grader.h>
33: #include <common.h>
34: #include <ctype.h>
35: #include <time.h>
36:
37: /*
38: * used to remeber the weights and partial credit from a parse for when
39: * setting a DBHeader
40: */
41:
42: /* Reads a header form the file and sets up the time and date variables
43: */
44: int capaGetHeader(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
45: {
46: T_header header;
47: char * setNumber,buf[BUFFER_SIZE],*sectionNumber,dateStr[BUFFER_SIZE];
48: int set,section,result;
49:
50:
51: setNumber=Tcl_GetVar(interp,"gSetLoad",TCL_GLOBAL_ONLY);
52: sectionNumber=Tcl_GetVar(interp,"gSectionLoad",TCL_GLOBAL_ONLY);
53:
54: if ( setNumber[0] == '\0' ) return TCL_OK;
55: if ( sectionNumber[0] == '\0' ) return TCL_OK;
56:
57: set=atoi(setNumber);
58: section=atoi(sectionNumber);
59:
60: result=capa_get_header(&header,set);
61:
62: if ( result == -1 )
63: {
64: Tcl_ResetResult(interp);
65: Tcl_AppendElement(interp,"0");
66: return TCL_OK;
67: }
68:
69: result=capa_get_date(CHECK_OPEN_DATE,NULL,section,set,dateStr);
70: if (result<0) {
71: Tcl_ResetResult(interp);
72: Tcl_AppendElement(interp,"-1");
73: return TCL_OK;
74: }
75: sscanf(dateStr,"%10c",buf);
76: buf[10]='\0';
77: Tcl_SetVar(interp,"gOpenDate",buf,TCL_GLOBAL_ONLY);
78: sscanf((dateStr)+11,"%5c",buf);
79: buf[5]='\0';
80: Tcl_SetVar(interp,"gOpenTime",buf,TCL_GLOBAL_ONLY);
81:
82: result=capa_get_date(CHECK_DUE_DATE,NULL,section,set,dateStr);
83: if (result<0) {
84: Tcl_ResetResult(interp);
85: Tcl_AppendElement(interp,"-1");
86: return TCL_OK;
87: }
88: sscanf(dateStr,"%10c",buf);
89: buf[10]='\0';
90: Tcl_SetVar(interp,"gDueDate",buf,TCL_GLOBAL_ONLY);
91: sscanf((dateStr)+11,"%5c",buf);
92: buf[5]='\0';
93: Tcl_SetVar(interp,"gDueTime",buf,TCL_GLOBAL_ONLY);
94:
95: result=capa_get_date(CHECK_ANS_DATE,NULL,section,set,dateStr);
96: if (result<0) {
97: Tcl_ResetResult(interp);
98: Tcl_AppendElement(interp,"-1");
99: return TCL_OK;
100: }
101: sscanf(dateStr,"%10c",buf);
102: buf[10]='\0';
103: Tcl_SetVar(interp,"gAnswerDate",buf,TCL_GLOBAL_ONLY);
104: sscanf((dateStr)+11,"%5c",buf);
105: buf[5]='\0';
106: Tcl_SetVar(interp,"gAnswerTime",buf,TCL_GLOBAL_ONLY);
107:
108: Tcl_ResetResult(interp);
109: Tcl_AppendElement(interp,"1");
110: capa_mfree(header.weight);
111: capa_mfree(header.partial_credit);
112: return TCL_OK;
113: }
114:
115: /* get the information for all of the students in the current section
116: * and puts them into the listbox.
117: * Arguments: the name of the variable the widget name of the listbox
118: * is in.
119: */
120: int capaGetStudents(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
121: {
122: T_student *headStudent,*currentStudent;
123: int result,section,set,setScore,maxScore,num=0;
124: char buf[BUFFER_SIZE],buf2[BUFFER_SIZE],*answers,*listWidget;
125:
126: section=atoi(Tcl_GetVar(interp,"gSectionLoad",TCL_GLOBAL_ONLY));
127: set=atoi(Tcl_GetVar(interp,"gSetLoad",TCL_GLOBAL_ONLY));
128:
129: if ( (listWidget = Tcl_GetVar(interp,argv[1],
130: TCL_GLOBAL_ONLY|TCL_LEAVE_ERR_MSG)) == NULL)
131: {
132: fprintf(stderr,"Tcl_GetVar error\n");
133: fprintf(stderr,"%s\n",interp->result);
134: return TCL_ERROR;
135: }
136:
137: result=capa_sorted_section(&headStudent,section);
138:
139: if (result == -1 || result == 0)
140: {
141: Tcl_Eval(interp,"displayError \"Invalid section\"");
142: Tcl_ResetResult(interp);
143: return TCL_OK;
144: }
145:
146: currentStudent=headStudent;
147:
148: while(currentStudent!=NULL)
149: {
150: num++;
151: setScore = capa_get_score(currentStudent->s_sn,set,&maxScore,&answers);
152: if ( setScore == -1 ) setScore=0;
153: sprintf(buf,"%s %s %2d/%2d %2d ",currentStudent->s_nm,
154: currentStudent->s_sn,setScore,maxScore,
155: capa_PIN(currentStudent->s_sn,set,0));
156:
157: capaPrepareBuffer(buf,buf2,0);
158: sprintf(buf,"%s insert end \"%s\" ",listWidget,buf2);
159:
160: if (Tcl_Eval(interp,buf) != TCL_OK)
161: {
162: fprintf(stderr,"Tcl_Eval error\n");
163: fprintf(stderr,"%s\n",interp->result);
164: free_students(headStudent);
165: return TCL_ERROR;
166: }
167:
168: if (!(num%10)) {
169: if (Tcl_Eval(interp,"update") != TCL_OK)
170: {
171: fprintf(stderr,"Tcl_Eval error\n");
172: fprintf(stderr,"%s\n",interp->result);
173: free_students(headStudent);
174: return TCL_ERROR;
175: }
176: }
177: currentStudent=currentStudent->s_next;
178: capa_mfree(answers);
179: }
180:
181: free_students(headStudent);
182: if (!(num%5)) {
183: if (Tcl_Eval(interp,"update") != TCL_OK)
184: {
185: fprintf(stderr,"Tcl_Eval error\n");
186: fprintf(stderr,"%s\n",interp->result);
187: return TCL_ERROR;
188: }
189: }
190: return TCL_OK;
191: }
192:
193: /* searches for the section a student is in by either name or number
194: * Arguments: one of (name or number) and then the name or number to
195: * search for.
196: */
197: int capaFindSection(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
198: {
199: int errorNm;
200: char searchStr[MAX_NAME_CHAR+1],buf[MAX_NAME_CHAR+1];
201: T_student student;
202:
203: switch(argv[1][1])
204: {
205: case 'a':
206: strncpy(searchStr,argv[2],MAX_NAME_CHAR+1);
207: if ( (errorNm = capa_student_byname(searchStr,&student ))==0 )
208: {
209: sprintf(buf,"%d",0);
210: }
211: else
212: {
213: sprintf(buf,"%d",student.s_sec);
214: }
215: break;
216: case 'u':
217: strncpy(searchStr,argv[2],MAX_NAME_CHAR+1);
218: if ( (errorNm = capa_get_student(searchStr,&student ))==0 )
219: {
220: sprintf(buf,"%d",0);
221: }
222: else
223: {
224: sprintf(buf,"%d",student.s_sec);
225: }
226: break;
227: default:
228: break;
229: }
230: Tcl_ResetResult(interp);
231: Tcl_AppendElement(interp,buf);
232: return TCL_OK;
233: }
234:
235: /* makes a student report
236: * Arguments: the student number
237: */
238: int capaGetReportInfo(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
239: {
240: char studentNumber[MAX_STUDENT_NUMBER+1],
241: lineOne[BUFFER_SIZE],*wgt,*partialCredit;
242: T_header header;
243: T_entry entry;
244: int ii, setIdx, setScores, setValids,
245: totalSet, totalProbs, neverLogin;
246: int termScores, termValids;
247:
248: strncpy(studentNumber,argv[1], MAX_STUDENT_NUMBER+1);
249: totalSet = howManySetDBFile();
250:
251: Tcl_ResetResult(interp);
252:
253: for(termScores=0,termValids=0,setIdx=1;setIdx <= totalSet ;setIdx++)
254: {
255: capa_get_entry(&entry, studentNumber, setIdx);
256: totalProbs = entry.e_probs;
257: if( capa_get_header( &header, setIdx ) == -1 )
258: {
259: Tcl_ResetResult(interp);
260: Tcl_AppendElement(interp,"File Error");
261: return TCL_OK;
262: }
263: wgt=header.weight;
264: partialCredit=header.partial_credit;
265:
266: for(setScores=0, setValids=0,neverLogin=1,ii=0;ii<totalProbs;ii++)
267: {
268: switch(entry.answers[ii])
269: {
270: case 'Y': case 'y':
271: neverLogin = 0;
272: setScores += (wgt[ii] - '0');
273: setValids += (wgt[ii] - '0');
274: break;
275: case '-': case 'N': case 'n':
276: setValids += (wgt[ii] - '0');
277: break;
278: case 'E': case 'e':
279: break;
280: default :
281: if( entry.answers[ii] >= '0' && entry.answers[ii] <= '9' )
282: {
283: setScores += (entry.answers[ii] - '0');
284: setValids += (wgt[ii] - '0');
285: neverLogin = 0;
286: }
287: break;
288: }
289: }
290: entry.answers[totalProbs]='\0'; /* get rid of last unknown chars */
291: entry.tries[3*totalProbs]='\0';
292: termScores += setScores;
293: termValids += setValids;
294:
295: if(neverLogin)
296: {
297: sprintf(lineOne,"%3d -/%3d %s\n",setIdx,setValids,entry.answers);
298: }
299: else
300: {
301: sprintf(lineOne,"%3d %3d/%3d %s\n",setIdx,setScores,setValids,entry.answers);
302: }
303: Tcl_AppendResult(interp,lineOne,NULL);
304: sprintf(lineOne," %s\n",entry.tries);
305: Tcl_AppendResult(interp,lineOne,NULL);
306: capa_mfree(entry.answers);
307: capa_mfree(entry.tries);
308: }
309: sprintf(lineOne,"========================\n Total = %3d/%3d",termScores,termValids);
310: Tcl_AppendResult(interp,lineOne,NULL);
311: capa_mfree(header.weight);
312: capa_mfree(header.partial_credit);
313: return TCL_OK;
314: }
315:
316: int compare_string( a, b)
317: char *a, *b;
318: {
319: return( strcasecmp(a, b) );
320: }
321:
322: /* Builds a set summary
323: * Argument: the filename to write to
324: */
325: int capaGetSetSummary(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
326: {
327: T_student *stuPtr, *currentStudentPtr;
328: T_header a_header;
329: int section, set;
330: int studentCount,currentStudent, setScores, validScores;
331: char fmt1[64], fmt2[64],buf[BUFFER_SIZE],*str1="Student Name",*str2=" ";
332: char *answersPtr;
333: FILE *outputFile;
334:
335: section=atoi(Tcl_GetVar(interp,"gSectionLoad",TCL_GLOBAL_ONLY));
336: set=atoi(Tcl_GetVar(interp,"gSetLoad",TCL_GLOBAL_ONLY));
337: Tcl_ResetResult(interp);
338:
339: studentCount = capa_sorted_section(&stuPtr, section);
340: if( studentCount > 0 )
341: {
342: if( capa_get_header( &a_header, set) == -1 )
343: {
344: Tcl_Eval(interp,"displayerror \"Cannot open set.db file\"");
345: Tcl_ResetResult(interp);
346: free_students(stuPtr);
347: return TCL_OK;
348: }
349: capa_mfree(a_header.weight);
350: capa_mfree(a_header.partial_credit);
351: sprintf(fmt1,"%%-%ds\t%%%ss\t Score\n", MAX_NAME_CHAR,a_header.num_questions);
352:
353: outputFile=fopen(argv[1],"w");
354: fprintf(outputFile, "Section %-3d, Set %-3d Score Report\n",section, set);
355:
356: fprintf(outputFile, fmt1,str1,str2);
357:
358: sprintf(fmt1,"%%-%ds\t%%s\t -/%%3d\n", MAX_NAME_CHAR);
359: sprintf(fmt2,"%%-%ds\t%%s\t%%3d/%%3d\n", MAX_NAME_CHAR);
360:
361: for(currentStudentPtr=stuPtr,currentStudent=0;currentStudentPtr;
362: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
363: {
364: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
365: Tcl_Eval(interp,buf);
366: if( (setScores = capa_get_score(currentStudentPtr->s_sn,
367: set,&validScores,&answersPtr) ) == -2 )
368: {
369: Tcl_Eval(interp,"displayerror \"Cannot open set.db file\"");
370: Tcl_ResetResult(interp);
371: free_students(stuPtr);
372: capa_mfree(answersPtr);
373: fclose(outputFile);
374: return TCL_OK;
375: }
376: if( setScores < 0 )
377: {
378: fprintf(outputFile,fmt1,currentStudentPtr->s_nm,answersPtr,validScores );
379: }
380: else
381: {
382: fprintf(outputFile,fmt2,currentStudentPtr->s_nm,answersPtr,setScores,validScores );
383: }
384: capa_mfree(answersPtr);
385: }
386: free_students(stuPtr);
387: fclose(outputFile);
388: }
389: return TCL_OK;
390: }
391:
392: /* builds a term summary
393: * Arguments: filename
394: */
395: int capaGetTermSummary(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
396: {
397: T_student *studentPtr, *currentStudentPtr;
398: int section, totalSet;
399: int setIndex, setScores, termScores, validScores, termValids;
400: int studentCount,currentStudent=1;
401: char fmt[64];
402: char *answersPtr,buf[BUFFER_SIZE];
403: FILE *outputFile;
404:
405: outputFile=fopen(argv[1],"w");
406: section=atoi(Tcl_GetVar(interp,"gSectionLoad",TCL_GLOBAL_ONLY));
407: totalSet = howManySetDBFile();
408: Tcl_ResetResult(interp);
409:
410: studentCount = capa_sorted_section(&studentPtr, section);
411: if( studentCount > 0 )
412: {
413: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
414: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
415: {
416: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
417: Tcl_Eval(interp,buf);
418: sprintf(fmt,"%%-%ds\n", MAX_NAME_CHAR);
419: fprintf(outputFile,fmt,currentStudentPtr->s_nm);
420:
421: for( termScores = 0, termValids = 0, setIndex = 1; setIndex <= totalSet; setIndex++)
422: {
423: if( (setScores = capa_get_score(currentStudentPtr->s_sn,
424: setIndex,&validScores,&answersPtr) ) == -2 )
425: {
426: sprintf(buf,"displayerror \"Cannot open set%d.db file\"",setIndex);
427: Tcl_Eval(interp,buf);
428: Tcl_ResetResult(interp);
429: capa_mfree(answersPtr);
430: free_students(studentPtr);
431: fclose(outputFile);
432: return TCL_OK;
433: }
434: if( setScores < 0 )
435: {
436: fprintf(outputFile,"Set %-3d\t%s\t -/%3d\n", setIndex,answersPtr, validScores);
437: }
438: else
439: {
440: fprintf(outputFile, "Set %-3d\t%s\t%3d/%3d\n",
441: setIndex,answersPtr,setScores,validScores );
442: termScores += setScores;
443: }
444: capa_mfree(answersPtr);
445: termValids += validScores;
446: }
447: fprintf(outputFile,"\t\t\tTerm Score = %3d/%3d\n", termScores,termValids);
448: fprintf(outputFile, "-----------------------------------------------------------------------\n");
449: }
450: free_students(studentPtr);
451: }
452: fclose(outputFile);
453: return TCL_OK;
454: }
455:
456: extern int Parsemode_f;
457:
458: /* runs capaParse and puts the results into a text widget
459: * Arguments: the name it is registered under (enscriptParse, texParse,
460: * webParse, bubblerParse); what results of the parse to show
461: * 0 (Problem Only), 1 (Question and Answer), 2 (Answer Only);
462: * the set number; either (Random or Specific) student; section;
463: * student Number; student Name ; the name of the variable to
464: * find the widget name of the text widget to put the text into
465: */
466: int capaTclParse (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
467: {
468: extern char *EndText_p;
469: T_student student;
470: Problem_t *headProblem,*currentProblem;
471: int numOfQuestions,numAnswers,problemNumber=0;
472: int result,i=1,j,length;
473: char *buf, *buf2, *temp, *previewText=NULL;
474: char lower[32],upper[32],ans[32], unit[32];
475: double targetAns;
476: int c_set;
477: #ifdef GRADER_UPDATE
478: char *update=";update";
479: #else
480: char *update=" ";
481: #endif
482:
483: switch(argv[0][0])
484: {
485: case 'e':Parsemode_f = ASCII_MODE;break;
486: case 't':Parsemode_f = TeX_MODE;break;
487: case 'w':Parsemode_f = HTML_MODE;break;
488: case 'b':Parsemode_f = BUBBLE_MODE;break;
489: default:
490: Tcl_ResetResult(interp);
491: Tcl_AppendElement(interp,"Invalid call to capaTclParse\n");
492: return TCL_ERROR;
493: break;
494: }
495:
496: if ( (previewText = Tcl_GetVar(interp,argv[7],
497: TCL_GLOBAL_ONLY|TCL_LEAVE_ERR_MSG)) == NULL)
498: {
499: fprintf(stderr,"Tcl_GetVar error\n");
500: fprintf(stderr,"%s\n",interp->result);
501: return TCL_ERROR;
502: }
503: c_set = atoi(argv[2]);
504: switch (argv[3][0])
505: {
506: case 'R':
507: result = capa_pick_student(atoi(argv[4]),&student);
508: if (result == -1)
509: {
510: buf=capa_malloc(BUFFER_SIZE,1);
511: sprintf(buf,"displayError \"There are no students in section %d.\"",
512: atoi(argv[4]));
513: Tcl_Eval(interp,buf);
514: capa_mfree(buf);
515: Tcl_ResetResult(interp);
516: Tcl_AppendElement(interp,"-1");
517: return TCL_OK;
518: }
519:
520: result = capa_parse(atoi(argv[2]),&headProblem,student.s_sn,&numOfQuestions,NULL);
521: break;
522: case 'S':
523: result = capa_get_student(argv[5],&student);
524: if ((result == -1) || (result == 0))
525: {
526: buf=capa_malloc(BUFFER_SIZE,1);
527: sprintf(buf,"displayError \"The student %s does not exist.\"",
528: argv[5]);
529: Tcl_Eval(interp,buf);
530: capa_mfree(buf);
531: Tcl_ResetResult(interp);
532: Tcl_AppendElement(interp,"-1");
533: return TCL_OK;
534: }
535: result = capa_parse(atoi(argv[2]),&headProblem,argv[5],&numOfQuestions,NULL);
536: break;
537: default:
538: Tcl_ResetResult(interp);
539: Tcl_AppendElement(interp,"Invalid 2nd argument to capaTclParse\n");
540: return TCL_ERROR;
541: break;
542: }
543:
544: if (result==-1)
545: {
546: Tcl_ResetResult(interp);
547: Tcl_AppendElement(interp,"-1");
548: return TCL_OK;
549: }
550:
551: currentProblem=headProblem;
552:
553: if(argv[1][0] == Q_ANSWER)
554: {
555: /*
556: switch(Parsemode_f)
557: {
558: case ASCII_MODE:
559: sprintf(buf,"Section %d Set %d\n Name: %s PIN: %d\n\n",
560: student.s_sec, atoi(argv[2]), student.s_nm,
561: capa_PIN(student.s_sn, atoi(argv[2]),0));
562: break;
563: case TeX_MODE:
564: sprintf(buf,"{\\bf Section %d\\qquad Set %d}\\\\\\medskip \n{\\bf Name: \
565: %s\\qquad PIN: %d}\\\\ \\bigskip\n\n", student.s_sec, atoi(argv[2]), student.s_nm,
566: capa_PIN(student.s_sn, atoi(argv[2]),0));
567: break;
568: case HTML_MODE:
569: sprintf(buf,"Section %d Set %d\n Name: %s PIN: %d\n\n",
570: student.s_sec, atoi(argv[2]), student.s_nm,
571: capa_PIN(student.s_sn, atoi(argv[2]),0));
572: break;
573: case BUBBLE_MODE:
574: break;
575: }
576: j=capaPrepareBuffer(buf,buf2,0);
577:
578: sprintf(buf,"%s insert end \" %s \" header",previewText,buf2);
579:
580: if (Tcl_Eval(interp,buf) != TCL_OK)
581: {
582: fprintf(stderr,"Tcl_Eval error\n");
583: fprintf(stderr,"%s\n",interp->result);
584: return TCL_ERROR;
585: }
586: */
587: }
588:
589: while (currentProblem!=NULL)
590: {
591: switch (argv[1][0])
592: {
593: case Q_PROBLEM:
594: if (currentProblem->question) {
595: length=strlen(currentProblem->question);
596: } else {
597: length=0;
598: }
599: buf=capa_malloc(BUFFER_SIZE+(2*length),1);
600: buf2=capa_malloc(BUFFER_SIZE+(2*length),1);
601: if(currentProblem->question) {
602: j=capaPrepareBuffer(currentProblem->question,buf2,0);
603: buf2[j-1]='\n';
604: buf2[j]='\0';
605: } else {
606: buf2[0]='\n';buf2[1]='\0';
607: }
608: if(currentProblem->question) {
609: j=capaPrepareBuffer(currentProblem->question,buf2,0);
610: buf2[j-1]='\n';
611: buf2[j]='\0';
612: } else {
613: buf2[0]='\n';buf2[1]='\0';
614: }
615:
616: switch(Parsemode_f)
617: {
618: case ASCII_MODE:
619: sprintf(buf,"%s insert end \"%s \n-----------\n\n\" problem",
620: previewText,buf2);
621: break;
622: case TeX_MODE:
623: sprintf(buf,"%s insert end \"%s\" problem",previewText,buf2);
624: break;
625: case HTML_MODE:
626: sprintf(buf,"%s insert end \"%s\" problem",previewText,buf2);
627: break;
628: case BUBBLE_MODE:
629: break;
630: }
631: if (Tcl_Eval(interp,buf) != TCL_OK)
632: {
633: fprintf(stderr,"Tcl_Eval error\n");
634: fprintf(stderr,"%s\n",interp->result);
635: return TCL_ERROR;
636: }
637: capa_mfree(buf);
638: capa_mfree(buf2);
639: break;
640: case Q_PROBLEM_AND_ANSWER:
641: if (currentProblem->question) {
642: length=strlen(currentProblem->question);
643: } else {
644: length=0;
645: }
646: buf=capa_malloc(BUFFER_SIZE+(2*length),1);
647: buf2=capa_malloc(BUFFER_SIZE+(2*length),1);
648: temp=capa_malloc(BUFFER_SIZE+(2*length),1);
649: j=capaPrepareBuffer(currentProblem->question,buf2,0);
650:
651: switch(Parsemode_f)
652: {
653: case ASCII_MODE:
654: sprintf(buf,"%s insert end \"%s \n-----------\n\n\" problem",
655: previewText,buf2);
656: break;
657: case TeX_MODE:
658: sprintf(buf,"%s insert end \"%s\" problem",previewText,buf2);
659: break;
660: case HTML_MODE:
661: sprintf(buf,"%s insert end \"%s\" problem",previewText,buf2);
662: break;
663: case BUBBLE_MODE:
664: break;
665: }
666: if (Tcl_Eval(interp,buf) != TCL_OK)
667: {
668: fprintf(stderr,"Tcl_Eval error\n");
669: fprintf(stderr,"%s\n",interp->result);
670: return TCL_ERROR;
671: }
672:
673: capa_mfree(buf);
674: capa_mfree(buf2);
675: capa_mfree(temp);
676: capaInsertAnswer(currentProblem,interp,previewText);
677: break;
678: case Q_ANSWER:
679: print_begin_item(Parsemode_f,interp,previewText,problemNumber+1);
680: capaInsertAnswer(currentProblem,interp,previewText);
681: break;
682: }
683:
684: currentProblem=currentProblem->next;
685: problemNumber++;
686: }
687: if( ( EndText_p != NULL) )
688: {
689: buf=capa_malloc(BUFFER_SIZE+(2*strlen(EndText_p)),1);
690: buf2=capa_malloc(BUFFER_SIZE+(2*strlen(EndText_p)),1);
691: temp=capa_malloc(BUFFER_SIZE+(2*strlen(EndText_p)),1);
692: sprintf(temp,"%s", EndText_p);
693: j=capaPrepareBuffer(temp,buf2,0);
694:
695: sprintf(buf,"%s insert end \"%s\" answer%s",previewText,buf2,update);
696:
697: if (Tcl_Eval(interp,buf) != TCL_OK)
698: {
699: fprintf(stderr,"Tcl_Eval error 7\n");
700: fprintf(stderr,"%s\n",interp->result);
701: return TCL_ERROR;
702: }
703: capa_mfree(buf);
704: capa_mfree(buf2);
705: capa_mfree(temp);
706: }
707: free_problems(headProblem);
708:
709: if (result==0)
710: {
711: Tcl_ResetResult(interp);
712: Tcl_AppendElement(interp,"0");
713: }
714: else
715: {
716: buf=capa_malloc(BUFFER_SIZE,1);
717: sprintf(buf,"%d",result);
718: Tcl_ResetResult(interp);
719: Tcl_AppendElement(interp,buf);
720: capa_mfree(buf);
721: }
722:
723: return TCL_OK;
724: }
725:
726: /* setup gQuestionType for all of the questions
727: * Arguments: number of Questions
728: */
729: int capaGetQuestionTypes(ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
730: {
731: int numQuestions,result,i;
732: T_header header;
733: char buf[BUFFER_SIZE], buf2[BUFFER_SIZE],*weight;
734:
735: if (argc != 2)
736: {
737: Tcl_ResetResult(interp);
738: Tcl_AppendResult(interp,"Wrong number of arguments to getQuestionTypes",
739: NULL);
740: return TCL_ERROR;
741: }
742:
743: numQuestions=atoi(argv[1]);
744:
745: result = capa_get_header(&header,atoi(Tcl_GetVar(interp,"gSetLoad",
746: TCL_GLOBAL_ONLY)));
747: weight=header.weight;
748:
749: if (result == -1)
750: {
751: Tcl_ResetResult(interp);
752: Tcl_AppendResult(interp,"capa_get_header returned error.",NULL);
753: return TCL_ERROR;
754: }
755:
756: for(i=1;i<=numQuestions;i++)
757: {
758: sprintf(buf,"%d",i);
759: switch(header.partial_credit[i-1])
760: {
761: case '0':
762: Tcl_SetVar2(interp,"gQuestionType",buf,"autoGrade",TCL_GLOBAL_ONLY);
763: break;
764: case '1':
765: Tcl_SetVar2(interp,"gQuestionType",buf,"handGrade",TCL_GLOBAL_ONLY);
766: sprintf(buf,"max%d",i);
767: sprintf(buf2,"%c",weight[i-1]);
768: Tcl_SetVar2(interp,"gAnswer",buf,buf2,TCL_GLOBAL_ONLY);
769: break;
770: default:
771: Tcl_ResetResult(interp);
772: Tcl_AppendResult(interp,"Header for the set.db file is incorrect.",
773: NULL);
774: return TCL_ERROR;
775: break;
776: }
777: }
778: capa_mfree(header.weight);
779: capa_mfree(header.partial_credit);
780: Tcl_ResetResult(interp);
781: return TCL_OK;
782: }
783:
784: /* setup gAnswer for all of the questions
785: * Arguments: number of Questions
786: */
787: T_entry graderEntry;
788: int capaSetupGAnswer (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
789: {
790: int numQuestions,i,result;
791: char buf[BUFFER_SIZE],buf2[BUFFER_SIZE],*questionType;
792:
793: if (argc != 2)
794: {
795: Tcl_ResetResult(interp);
796: Tcl_AppendResult(interp,"Incorrect number of arguments to setup gAnswer",
797: NULL);
798: return TCL_ERROR;
799: }
800:
801: numQuestions=atoi(argv[1]);
802:
803: result = capa_get_entry(&graderEntry,Tcl_GetVar2(interp,"gGrading","number",
804: TCL_GLOBAL_ONLY),
805: atoi(Tcl_GetVar(interp,"gSetLoad",TCL_GLOBAL_ONLY)));
806:
807: if (result == 0)
808: {
809: Tcl_ResetResult(interp);
810: Tcl_AppendResult(interp,"capa_get_entry returned error.",NULL);
811: return TCL_ERROR;
812: }
813: for(i=1;i<=numQuestions;i++)
814: {
815: sprintf(buf,"%d.tries",i);
816: buf2[0]=graderEntry.tries[(i-1)*3];buf2[1]=graderEntry.tries[(i-1)*3+1];
817: buf2[2]='\0';
818: Tcl_SetVar2(interp,"gAnswer",buf,buf2,TCL_GLOBAL_ONLY);
819: sprintf(buf,"%d",i);
820: switch(graderEntry.answers[i-1])
821: {
822: case '-':
823: Tcl_SetVar2(interp,"gAnswer",buf,"-",TCL_GLOBAL_ONLY);
824: break;
825: case 'y':
826: case 'n':
827: case 'E':
828: sprintf(buf2,"%c",graderEntry.answers[i-1]);
829: Tcl_SetVar2(interp,"gAnswer",buf,buf2,TCL_GLOBAL_ONLY);
830: break;
831: case 'Y':
832: sprintf(buf2,"%c",graderEntry.answers[i-1]);
833: Tcl_SetVar2(interp,"gAnswer",buf,buf2,TCL_GLOBAL_ONLY);
834: questionType=Tcl_GetVar2(interp,"gQuestionType",buf,
835: TCL_GLOBAL_ONLY);
836: switch(questionType[0])
837: {
838: case 'a':
839: sprintf(buf,"$gGradeCanvas.dash%d configure -state disabled",i);
840: if (Tcl_Eval(interp,buf)!=TCL_OK)
841: return TCL_ERROR;
842: sprintf(buf,"$gGradeCanvas.y%d configure -state disabled",i);
843: if (Tcl_Eval(interp,buf)!=TCL_OK)
844: return TCL_ERROR;
845: sprintf(buf,"$gGradeCanvas.n%d configure -state disabled",i);
846: if (Tcl_Eval(interp,buf)!=TCL_OK)
847: return TCL_ERROR;
848: sprintf(buf,"$gGradeCanvas.e%d configure -state disabled",i);
849: if (Tcl_Eval(interp,buf)!=TCL_OK)
850: return TCL_ERROR;
851: break;
852: case 'h':
853: sprintf(buf,"$gGradeCanvas.hand%d configure -state disabled",i);
854: if (Tcl_Eval(interp,buf)!=TCL_OK)
855: return TCL_ERROR;
856: break;
857: default:
858: Tcl_ResetResult(interp);
859: Tcl_AppendElement(interp,"questionType contains invlaid data in capaSetupGAnswer.");
860: return TCL_ERROR;
861: break;
862: }
863: break;
864: default:
865: sprintf(buf2,"%c",graderEntry.answers[i-1]);
866: Tcl_SetVar2(interp,"gAnswer",buf,buf2,TCL_GLOBAL_ONLY);
867: break;
868: }
869: }
870:
871: Tcl_ResetResult(interp);
872: return TCL_OK;
873: }
874:
875: /* save gAnswer to the set.db file
876: * Arguments: number of Questions
877: */
878: int capaSaveGAnswer (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
879: {
880: T_entry entry;
881: int numQuestions,i,result;
882: char buf[BUFFER_SIZE],*gAnswer;
883:
884: if (argc != 2)
885: {
886: Tcl_ResetResult(interp);
887: Tcl_AppendResult(interp,"Incorrect number of arguments to save gAnswer",NULL);
888: return TCL_ERROR;
889: }
890:
891: numQuestions=atoi(argv[1]);
892:
893: entry.answers=capa_malloc(numQuestions+1,1);
894: entry.tries=capa_malloc(3*numQuestions+1,1);
895:
896: for(i=0;i<numQuestions;i++) {
897: sprintf(buf,"%d",i+1);
898: gAnswer=Tcl_GetVar2(interp,"gAnswer",buf,TCL_GLOBAL_ONLY);
899: if ( gAnswer[0] != graderEntry.answers[i] ) {
900: entry.answers[i]=gAnswer[0];
901: } else {
902: entry.answers[i]='?';
903: }
904: sprintf(buf,"%d.tries",i+1);
905: gAnswer=Tcl_GetVar2(interp,"gAnswer",buf,TCL_GLOBAL_ONLY);
906: if (atoi(gAnswer) != atoi(&(graderEntry.tries[i*3]))) {
907: sprintf(&(entry.tries[i*3]),"%2d",atoi(gAnswer));
908: if (i<numQuestions-1) entry.tries[i*3+2]=',';
909: } else {
910: entry.tries[i*3]='-';entry.tries[i*3+1]='1';
911: if (i<numQuestions-1) entry.tries[i*3+2]=',';
912: }
913: }
914: entry.answers[numQuestions]='\0';
915: entry.tries[numQuestions*3]='\0';
916: sprintf(entry.student_number,Tcl_GetVar2(interp,"gGrading","number",TCL_GLOBAL_ONLY));
917: entry.e_probs=numQuestions;
918: result = capa_change_entry(&entry,Tcl_GetVar2(interp,"gGrading","number",
919: TCL_GLOBAL_ONLY),
920: atoi(Tcl_GetVar(interp,"gSetLoad",TCL_GLOBAL_ONLY)));
921:
922: if (result == -1) {
923: Tcl_ResetResult(interp);
924: Tcl_AppendResult(interp,"capa_change_entry returned an error.",NULL);
925: return TCL_ERROR;
926: }
927:
928: Tcl_ResetResult(interp);
929: return TCL_OK;
930: }
931:
932: /* a wrapper for capa_excuse
933: * Arguments: set; problem; section
934: */
935: int capaExcuse (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
936: {
937: int result;
938:
939: result = capa_excuse(atoi(argv[1]),atoi(argv[2]),atoi(argv[3]));
940:
941: if (result == -1)
942: {
943: Tcl_ResetResult(interp);
944: Tcl_AppendResult(interp,"capa_excuse returned error.",NULL);
945: return TCL_ERROR;
946: }
947:
948: return TCL_OK;
949: }
950:
951: /* creates a summary report
952: * Arguments: the filename
953: */
954: int capaCreateSummary (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
955: {
956: int section = atoi(Tcl_GetVar2(interp,"gSummary","section",TCL_GLOBAL_ONLY)),
957: set = atoi(Tcl_GetVar2(interp,"gSummary","set",TCL_GLOBAL_ONLY));
958: int studentCount,currentStudent;
959: int setScores, termScores, validScores, termValids;
960: int setIndex, maxSet=0;
961: int whatSection;
962: char fmt[64];
963: char grades[4], sectionChar[4], *answersPtr, buf[BUFFER_SIZE], *who,*which,*sortOne,*sortTwo;
964: T_student *studentPtr, *currentStudentPtr;
965: FILE *outputFile;
966:
967: who=Tcl_GetVar2(interp,"gSummary","who",TCL_GLOBAL_ONLY);
968: which=Tcl_GetVar2(interp,"gSummary","which",TCL_GLOBAL_ONLY);
969: sortOne=Tcl_GetVar2(interp,"gSummary","first",TCL_GLOBAL_ONLY);
970: sortTwo=Tcl_GetVar2(interp,"gSummary","second",TCL_GLOBAL_ONLY);
971: maxSet=howManySetDBFile();
972: if ( ( ( strcmp(which,"upto") == 0 )
973: &&
974: ( ( set <= 0 )
975: ||
976: ( set >= NUM_SET_LIMIT ) ) )
977: ||
978: ( set > maxSet ) )
979: {
980: sprintf(buf,"displayError \"The set number (%d) doesn't exist.\"",set);
981: Tcl_Eval(interp,buf);
982: Tcl_ResetResult(interp);
983: Tcl_AppendResult(interp,"Error",NULL);
984: return TCL_ERROR;
985: }
986: outputFile=fopen(argv[1],"w");
987: if ( strcmp(who,"all") == 0 )
988: whatSection = GET_ALL_SECTIONS;
989: else
990: whatSection = section;
991: studentCount = capa_get_section(&studentPtr, whatSection);
992:
993: if (Tcl_Eval(interp,"updateStatusMessage \"Creating primary sort key\"") != TCL_OK)
994: {
995: free_students(studentPtr);
996: fclose(outputFile);
997: return TCL_ERROR;
998: }
999:
1000: if( studentCount > 0 )
1001: {
1002: switch (sortOne[1])
1003: {
1004: case 'a': /*BY_NAME*/
1005: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1006: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1007: {
1008: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1009: Tcl_Eval(interp,buf);
1010: sprintf(currentStudentPtr->s_key,"%s",currentStudentPtr->s_nm);
1011: }
1012: break;
1013: case 'u': /*BY_NUMBER*/
1014: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1015: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1016: {
1017: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1018: Tcl_Eval(interp,buf);
1019: sprintf(currentStudentPtr->s_key,"%s",currentStudentPtr->s_sn);
1020: }
1021: break;
1022: case 'e': /*BY_SECTION*/
1023: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1024: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1025: {
1026: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1027: Tcl_Eval(interp,buf);
1028: sprintf(currentStudentPtr->s_key,"%03d",currentStudentPtr->s_sec);
1029: }
1030: break;
1031: case 'r': /*BY_GRADE*/
1032: if(strcmp(which,"specific") == 0 )
1033: {
1034: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1035: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1036: {
1037: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1038: Tcl_Eval(interp,buf);
1039: if( (setScores = capa_get_score(currentStudentPtr->s_sn,set,
1040: &validScores,&answersPtr)) == -2 )
1041: break;
1042: if( setScores < 0 )
1043: sprintf(currentStudentPtr->s_key,"-");
1044: else
1045: sprintf(currentStudentPtr->s_key,"%03d",setScores);
1046: capa_mfree(answersPtr);
1047: }
1048: }
1049: else
1050: {
1051: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1052: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1053: {
1054: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1055: Tcl_Eval(interp,buf);
1056: for( termScores = 0, termValids = 0, setIndex = 1;
1057: setIndex <= set; setIndex++)
1058: {
1059: if( (setScores = capa_get_score(currentStudentPtr->s_sn,setIndex,
1060: &validScores,&answersPtr)) >= 0 )
1061: termScores += setScores;
1062: capa_mfree(answersPtr);
1063: termValids += validScores;
1064: }
1065: sprintf(currentStudentPtr->s_key,"%03d",termScores);
1066: }
1067: }
1068: break;
1069: }
1070: if (Tcl_Eval(interp,"updateStatusMessage \"Creating secondary sort key\"") != TCL_OK)
1071: {
1072: free_students(studentPtr);
1073: fclose(outputFile);
1074: return TCL_ERROR;
1075: }
1076: switch (sortTwo[1])
1077: {
1078: case 'a':/*BY_NAME*/
1079: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1080: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1081: {
1082: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1083: Tcl_Eval(interp,buf);
1084: strcat(currentStudentPtr->s_key,currentStudentPtr->s_nm);
1085: }
1086: break;
1087: case 'u':/*BY_NUMBER*/
1088: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1089: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1090: {
1091: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1092: Tcl_Eval(interp,buf);
1093: strcat(currentStudentPtr->s_key,currentStudentPtr->s_sn);
1094: }
1095: break;
1096: case 'e':/*BY_SECTION*/
1097: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1098: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1099: {
1100: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1101: Tcl_Eval(interp,buf);
1102: sprintf(sectionChar,"%03d",currentStudentPtr->s_sec);
1103: strcat(currentStudentPtr->s_key,sectionChar);
1104: }
1105: break;
1106: case 'r':/*BY_GRADE*/
1107: if(strcmp(which,"specific") == 0 )
1108: {
1109: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1110: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1111: {
1112: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1113: Tcl_Eval(interp,buf);
1114: if( (setScores = capa_get_score(currentStudentPtr->s_sn,set,&validScores,
1115: &answersPtr) ) == -2 )
1116: break;
1117: if( setScores < 0 )
1118: strcat(currentStudentPtr->s_key,"-");
1119: else
1120: {
1121: sprintf(grades,"%03d",setScores);
1122: strcat(currentStudentPtr->s_key,grades);
1123: }
1124: capa_mfree(answersPtr);
1125: }
1126: }
1127: else
1128: {
1129: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1130: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1131: {
1132: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1133: Tcl_Eval(interp,buf);
1134: for( termScores = 0, termValids = 0, setIndex = 1;
1135: setIndex <= set; setIndex++)
1136: {
1137: if( (setScores = capa_get_score(currentStudentPtr->s_sn,setIndex,
1138: &validScores,&answersPtr) ) >= 0 )
1139: termScores += setScores;
1140: capa_mfree(answersPtr);
1141: termValids += validScores;
1142: }
1143: sprintf(grades,"%03d",termScores);
1144: strcat(currentStudentPtr->s_key,grades);
1145: }
1146: }
1147: break;
1148: }
1149: if (Tcl_Eval(interp,"updateStatusMessage \"Sorting\"") != TCL_OK)
1150: {
1151: free_students(studentPtr);
1152: fclose(outputFile);
1153: return TCL_ERROR;
1154: }
1155: msort_main(&studentPtr);
1156: Tcl_ResetResult(interp);
1157:
1158: sprintf(fmt,"%%-%ds\t%%-%ds %%2d\t", MAX_NAME_CHAR,MAX_STUDENT_NUMBER);
1159: if (Tcl_Eval(interp,"updateStatusMessage \"Creating Report\"") != TCL_OK)
1160: {
1161: free_students(studentPtr);
1162: fclose(outputFile);
1163: return TCL_ERROR;
1164: }
1165: for(currentStudentPtr=studentPtr,currentStudent=1;currentStudentPtr;
1166: currentStudentPtr=currentStudentPtr->s_next,currentStudent++)
1167: {
1168: sprintf(buf,"updateStatusBar %f",(float)currentStudent/(float)studentCount);
1169: Tcl_Eval(interp,buf);
1170: fprintf(outputFile,fmt,currentStudentPtr->s_nm,currentStudentPtr->s_sn,
1171: currentStudentPtr->s_sec);
1172: if( strcmp(which,"specific") == 0)
1173: {
1174: setScores = 0; validScores = 0;
1175: if( (setScores =
1176: capa_get_score(currentStudentPtr->s_sn,set,&validScores,&answersPtr) ) == -2 )
1177: break;
1178: if( setScores < 0 )
1179: {
1180: fprintf(outputFile, " -\t%3d\n", validScores);
1181: }
1182: else
1183: {
1184: fprintf(outputFile, "%3d\t%3d\n",setScores, validScores);
1185: }
1186: capa_mfree(answersPtr);
1187: }
1188: else
1189: {
1190: for( setScores=0, validScores=0, termScores = 0, termValids = 0, setIndex = 1;
1191: setIndex <= set; setIndex++)
1192: {
1193: if( (setScores = capa_get_score(currentStudentPtr->s_sn,setIndex,
1194: &validScores,&answersPtr) ) >= 0 )
1195: termScores += setScores;
1196: capa_mfree(answersPtr);
1197: termValids += validScores;
1198: if( setScores >= 0 )
1199: {
1200: fprintf(outputFile, "%3d ",setScores);
1201: }
1202: else
1203: {
1204: fprintf(outputFile, " - ");
1205: }
1206: }
1207: fprintf(outputFile, "\t %3d\t%3d\n",termScores,termValids);
1208: }
1209: }
1210: free_students(studentPtr);
1211: }
1212: fclose(outputFile);
1213: return TCL_OK;
1214: }
1215:
1216: /* set the gAnswer score to what ever the user entered
1217: * Arguments: problemNumber
1218: */
1219: int capaSetHandGrade (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
1220: {
1221: int problemNumber=atoi(argv[1]),handGrade,maxGrade;
1222: char *handGradeChar,buf[BUFFER_SIZE];
1223:
1224: handGradeChar=Tcl_GetVar(interp,"gNewHandGrade",TCL_GLOBAL_ONLY);
1225: sprintf(buf,"max%d",problemNumber);
1226: maxGrade=atoi(Tcl_GetVar2(interp,"gAnswer",buf,TCL_GLOBAL_ONLY));
1227:
1228: if (isdigit(handGradeChar[0])) {
1229: handGrade=atoi(handGradeChar);
1230: if (handGrade > maxGrade) {
1231: sprintf(buf,"displayError \"Invalid response, you must enter a number between 0 and %d, or an E to excuse the problem.\"",maxGrade);
1232: if (Tcl_Eval(interp,buf)!=TCL_OK) {
1233: return TCL_ERROR;
1234: }
1235: } else {
1236: sprintf(buf,"%d",handGrade);
1237: Tcl_SetVar2(interp,"gAnswer",argv[1],buf,TCL_GLOBAL_ONLY);
1238: }
1239: } else {
1240: if (handGradeChar[0]=='E') {
1241: Tcl_SetVar2(interp,"gAnswer",argv[1],"E",TCL_GLOBAL_ONLY);
1242: } else {
1243: sprintf(buf,"displayError \"Invalid response, you must enter a number between 0 and %d, or an E to excuse the problem.\"",maxGrade);
1244: if (Tcl_Eval(interp,buf)!=TCL_OK) return TCL_ERROR;
1245:
1246: }
1247: }
1248: Tcl_ResetResult(interp);
1249: return TCL_OK;
1250: }
1251:
1252: /* save gAnswer to the set.db file
1253: * Arguments: setNum, questNum, stuId, score
1254: */
1255: int capaSetScore (ClientData clientdata, Tcl_Interp *interp, int argc, char *argv[])
1256: {
1257: T_entry entry;
1258: int score,i,result,question,numQuest,set;
1259: char buf[BUFFER_SIZE],*gAnswer,*stuId;
1260: T_header header;
1261:
1262: if (argc != 5)
1263: {
1264: Tcl_ResetResult(interp);
1265: Tcl_AppendResult(interp,"Incorrect number of arguments to save gAnswer",NULL);
1266: return TCL_ERROR;
1267: }
1268:
1269: set=atoi(argv[1]);
1270: question=atoi(argv[2]);
1271: stuId=argv[3];
1272: score=atoi(argv[4]);
1273:
1274: result=capa_get_header(&header,set);
1275:
1276: numQuest=atoi(header.num_questions);
1277: result = capa_get_entry(&entry,stuId,set);
1278:
1279: entry.answers=capa_malloc(numQuest+1,1);
1280: entry.tries=capa_malloc(3*numQuest+1,1);
1281:
1282: for(i=0;i<numQuest;i++) {
1283: if ( i==(question-1) ) {
1284: entry.answers[i]=score+'0';
1285: } else {
1286: entry.answers[i]='-';
1287: }
1288: entry.tries[i*3]='-';entry.tries[i*3+1]='1';
1289: if (i<numQuest-1) entry.tries[i*3+2]=',';
1290: }
1291:
1292: entry.answers[numQuest]='\0';
1293: entry.tries[(numQuest)*3]='\0';
1294: sprintf(entry.student_number,stuId);
1295: entry.e_probs=numQuest;
1296: result = capa_change_entry(&entry,stuId,set);
1297:
1298: if (result == -1) {
1299: Tcl_ResetResult(interp);
1300: Tcl_AppendResult(interp,"capa_change_entry returned an error.",NULL);
1301: return TCL_ERROR;
1302: }
1303:
1304: Tcl_ResetResult(interp);
1305: return TCL_OK;
1306: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>