summaryrefslogtreecommitdiffabout
path: root/T42.cpp
Unidiff
Diffstat (limited to 'T42.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--T42.cpp468
1 files changed, 468 insertions, 0 deletions
diff --git a/T42.cpp b/T42.cpp
new file mode 100644
index 0000000..9388d62
--- a/dev/null
+++ b/T42.cpp
@@ -0,0 +1,468 @@
1// T42.cpp : Defines the class behaviors for the application.
2//
3
4#include "stdafx.h"
5#include "T42.h"
6#include "T42Dlg.h"
7
8#include "T42Frame.h"
9#include "T42Document.h"
10#include "T42View.h"
11
12#include "SoundsPage.h"
13#include "FontsPage.h"
14#include "SecretaryPage.h"
15#include "GeneralPage.h"
16
17#ifdef _DEBUG
18#define new DEBUG_NEW
19#undef THIS_FILE
20static char THIS_FILE[] = __FILE__;
21#endif
22
23/////////////////////////////////////////////////////////////////////////////
24// CT42App
25
26BEGIN_MESSAGE_MAP(CT42App, CWinApp)
27 //{{AFX_MSG_MAP(CT42App)
28 //}}AFX_MSG
29 ON_COMMAND(ID_HELP, CWinApp::OnHelp)
30END_MESSAGE_MAP()
31
32/////////////////////////////////////////////////////////////////////////////
33// CT42App construction
34
35CT42App::CT42App()
36 : m_T42STimeLimit(0,0,2,0),
37 m_T42SBytesLimit(2048),
38 m_T42SWinLimit(10)
39{
40 m_maxT42Callees = 20;
41 m_maxT42Callers = 20;
42 m_bt42AutosaveLayout = FALSE;
43 m_nT42Calls = m_t42Call = -1;
44 m_pT42Dlg = NULL;
45 memset(&m_fmtT42Local,0,sizeof(m_fmtT42Local));
46 memset(&m_fmtT42Remote,0,sizeof(m_fmtT42Remote));
47 memset(&m_fmtT42System,0,sizeof(m_fmtT42System));
48 m_crT42LocalBG=RGB(255,255,255);
49 m_crT42RemoteBG=RGB(255,255,192);
50 m_bAwayOnScreenSaver = TRUE;
51 m_T42LinesBusy = 0;
52}
53
54/////////////////////////////////////////////////////////////////////////////
55// The one and only CT42App object
56
57CT42App theApp;
58
59/////////////////////////////////////////////////////////////////////////////
60// CT42App initialization
61
62BOOL CT42App::InitInstance()
63{
64 if (!AfxSocketInit())
65 {
66 AfxMessageBox(IDP_SOCKETS_INIT_FAILED);
67 return FALSE;
68 }
69
70 // Standard initialization
71 // If you are not using these features and wish to reduce the size
72 // of your final executable, you should remove from the following
73 // the specific initialization routines you do not need.
74
75#ifdef _AFXDLL
76 Enable3dControls(); // Call this when using MFC in a shared DLL
77#else
78 Enable3dControlsStatic();// Call this when linking to MFC statically
79#endif
80
81 SetRegistryKey(IDS_REGISTRYKEY);
82 m_HelpFile = m_pszHelpFilePath;
83 m_HelpFile+=">Standard";
84 m_pszHelpFilePath=(LPCTSTR)m_HelpFile;
85
86 m_pTemplate = new CMultiDocTemplate(IDR_T42FRAME,
87 RUNTIME_CLASS(T42Document),
88 RUNTIME_CLASS(T42Frame),
89 RUNTIME_CLASS(T42View)
90 );
91 AddDocTemplate(m_pTemplate);
92
93 Initialize();
94 LoadSettings();
95
96 if(!OpenT42CallsLog()){
97 AfxMessageBox(IDS_CALLOG_OPEN_FAILED,MB_OK|MB_ICONSTOP);
98 return FALSE;
99 }
100
101CT42Dlg dlg;
102 m_pMainWnd = &dlg;
103 m_pT42Dlg = &dlg;
104 dlg.DoModal();
105 m_pT42Dlg = NULL;
106
107 SaveSettings();
108
109 if(!CloseT42CallsLog())
110 AfxMessageBox(IDS_CALLOG_CLOSE_FAILED,MB_OK|MB_ICONSTOP);
111
112
113 // Since the dialog has been closed, return FALSE so that we exit the
114 // application, rather than start the application's message pump.
115 return FALSE;
116}
117
118BOOL CT42App::LastCallee(LPCTSTR callee)
119{
120POSITION p = m_t42Callees.Find(callee);
121 if(p){
122 m_t42Callees.RemoveAt(p);
123 m_t42Callees.AddHead(callee);
124 return FALSE;
125 }
126 m_t42Callees.AddHead(callee);
127 while(m_t42Callees.GetCount()>m_maxT42Callees)
128 m_t42Callees.RemoveTail();
129 return TRUE;
130}
131
132void CT42App::SaveSettings()
133{
134 WriteProfileInt("Settings","AwayOnScreenSaver",m_bAwayOnScreenSaver);
135
136 Klever::SaveStringList(m_t42Callees,"T42HotList");
137 Klever::SaveStringList(m_t42Callers,"T42Callers");
138 WriteProfileInt("T42Window","AutosaveLayout",m_bt42AutosaveLayout);
139 WriteProfileInt("Settings","T42MaxCallers",m_maxT42Callers);
140 WriteProfileInt("Settings","T42MaxCallees",m_maxT42Callees);
141 WriteProfileString("Settings","T42CallsLog",m_t42CallsFile);
142 WriteProfileInt("Settings","T42TalkPort",m_T42TalkPort);
143
144 WriteProfileString("Sounds","T42Bell",m_sndT42Bell);
145 WriteProfileString("Sounds","T42Prompt",m_sndT42Prompt);
146 WriteProfileInt("Sounds","T42PromptLoop",m_bT42PromptLoop);
147 WriteProfileString("Sounds","T42Wake",m_sndT42Wake);
148
149 Klever::WriteProfileString("Secretary","T42Greeting",m_T42SGreeting);
150 WriteProfileInt("Secretary","T42BytesLimit",m_T42SBytesLimit);
151 WriteProfileInt("Secretary","T42TimeLimit",m_T42STimeLimit.GetTotalSeconds());
152 WriteProfileInt("Secretary","T42WinLimit",m_T42SWinLimit);
153
154 WriteProfileInt("Fonts","T42LocalBG",m_crT42LocalBG);
155 WriteProfileInt("Fonts","T42RemoteBG",m_crT42RemoteBG);
156 WriteProfileBinary("Fonts","T42Local",(LPBYTE)&m_fmtT42Local,sizeof(m_fmtT42Local));
157 WriteProfileBinary("Fonts","T42Remote",(LPBYTE)&m_fmtT42Remote,sizeof(m_fmtT42Remote));
158 WriteProfileBinary("Fonts","T42System",(LPBYTE)&m_fmtT42System,sizeof(m_fmtT42System));
159
160 FlushT42CallsLog();
161}
162
163void CT42App::LoadSettings()
164{
165 m_bAwayOnScreenSaver = GetProfileInt("Settings","AwayOnScreenSaver",m_bAwayOnScreenSaver);
166
167 Klever::LoadStringList(m_t42Callees,"T42HotList");
168 Klever::LoadStringList(m_t42Callers,"T42Callers");
169 m_bt42AutosaveLayout = GetProfileInt("T42Window","AutosaveLayout",m_bt42AutosaveLayout);
170 m_maxT42Callers = GetProfileInt("Settings","T42MaxCallers",m_maxT42Callers);
171 m_maxT42Callees = GetProfileInt("Settings","T42MaxCallees",m_maxT42Callees);
172 m_t42CallsFile = GetProfileString("Settings","T42CallsLog",m_t42CallsFile);
173 m_T42TalkPort = GetProfileInt("Settings","T42TalkPort",m_T42TalkPort);
174
175 m_sndT42Bell = GetProfileString("Sounds","T42Bell",m_sndT42Bell);
176 m_sndT42Prompt = GetProfileString("Sounds","T42Prompt",m_sndT42Prompt);
177 m_bT42PromptLoop = GetProfileInt("Sounds","T42PromptLoop",m_bT42PromptLoop);
178 m_sndT42Wake = GetProfileString("Sounds","T42Wake",m_sndT42Wake);
179
180 m_T42SGreeting = Klever::GetProfileString("Secretary","T42Greeting",m_T42SGreeting);
181 m_T42SBytesLimit = GetProfileInt("Secretary","T42BytesLimit",m_T42SBytesLimit);
182 m_T42STimeLimit = CTimeSpan(GetProfileInt("Secretary","T42TimeLimit",m_T42STimeLimit.GetTotalSeconds()));
183 m_T42SWinLimit = GetProfileInt("Secretary","T42WinLimit",m_T42SWinLimit);
184
185 m_crT42LocalBG = GetProfileInt("Fonts","T42LocalBG",m_crT42LocalBG);
186 m_crT42RemoteBG = GetProfileInt("Fonts","T42RemoteBG",m_crT42RemoteBG);
187LPBYTE pdata;
188UINT pbytes;
189 if(GetProfileBinary("Fonts","T42Local",&pdata,&pbytes)){
190 if(pbytes==sizeof(m_fmtT42Local))
191 memmove(&m_fmtT42Local,pdata,sizeof(m_fmtT42Local));
192 delete pdata;
193 }
194 if(GetProfileBinary("Fonts","T42Remote",&pdata,&pbytes)){
195 if(pbytes==sizeof(m_fmtT42Remote))
196 memmove(&m_fmtT42Remote,pdata,sizeof(m_fmtT42Remote));
197 delete pdata;
198 }
199 if(GetProfileBinary("Fonts","T42System",&pdata,&pbytes)){
200 if(pbytes==sizeof(m_fmtT42System))
201 memmove(&m_fmtT42System,pdata,sizeof(m_fmtT42System));
202 delete pdata;
203 }
204}
205
206BOOL CT42App::LastCaller(LPCTSTR caller)
207{
208POSITION p = m_t42Callers.Find(caller);
209 if(p){
210 m_t42Callers.RemoveAt(p);
211 m_t42Callers.AddHead(caller);
212 return FALSE;
213 }
214 m_t42Callers.AddHead(caller);
215 while(m_t42Callers.GetCount()>m_maxT42Callers)
216 m_t42Callers.RemoveTail();
217 return TRUE;
218}
219
220void CT42App::Initialize()
221{
222 VERIFY(m_T42SGreeting.LoadString(IDS_DEFAULTGREETING));
223
224 VERIFY(
225 m_sndTeaDrop.LoadString(IDS_SND_TEADROP)
226 && m_sndBoilingTeapot.LoadString(IDS_SND_BOILINGTEAPOT)
227 && m_sndTeapotWhistle.LoadString(IDS_SND_TEAPOTWHISTLE)
228 );
229
230 m_sndT42Bell = m_sndTeaDrop;
231 m_sndT42Prompt = m_sndBoilingTeapot;
232 m_bT42PromptLoop = TRUE;
233 m_sndT42Wake = m_sndTeapotWhistle;
234
235 VERIFY(m_t42CallsFile.LoadString(IDS_FILE_T42CALLS));
236CString exepa;
237 VERIFY(GetModuleFileName(m_hInstance,exepa.GetBuffer(_MAX_PATH),_MAX_PATH));
238 exepa.ReleaseBuffer();
239int bs = exepa.ReverseFind('\\');
240 VERIFY(bs>=0);
241 exepa = exepa.Left(bs);
242 m_t42CallsFile = Klever::GluePathAndFile(exepa,m_t42CallsFile);
243
244servent* se = getservbyname("ntalk","udp");
245 if(se)
246 m_T42TalkPort = ntohs(se->s_port);
247 else
248 m_T42TalkPort = 518;
249}
250
251BOOL CT42App::StartSound(LPCTSTR snd,BOOL bLoop)
252{
253 // Return TRUE if looped sound started.
254LPCSTR s = snd;
255UINT flags = SND_ASYNC|SND_NODEFAULT|SND_NOWAIT|SND_RESOURCE;
256 if(!m_sndTeaDrop.Compare(s)){
257 s = MAKEINTRESOURCE(IDW_BEEP_DROP);
258 }else if(!m_sndBoilingTeapot.Compare(s)){
259 s = MAKEINTRESOURCE(IDW_ANNOUNCE_BOILING);
260 }else if(!m_sndTeapotWhistle.Compare(s)){
261 s = MAKEINTRESOURCE(IDW_WAKE_WHISTLE);
262 }else{
263 flags&=~SND_RESOURCE;
264 flags|=SND_FILENAME;
265 }
266 if(bLoop)
267 flags|=SND_LOOP;
268 if(PlaySound(s,AfxGetInstanceHandle(),flags))
269 return bLoop;
270 MessageBeep(0xFFFFFFFF);
271 return FALSE;
272}
273
274void CT42App::StopSound(LPCTSTR snd)
275{
276LPCSTR s = snd;
277UINT flags = SND_ASYNC|SND_NODEFAULT|SND_NOWAIT|SND_RESOURCE|SND_PURGE;
278 if(!m_sndTeaDrop.Compare(s)){
279 s = MAKEINTRESOURCE(IDW_BEEP_DROP);
280 }else if(!m_sndBoilingTeapot.Compare(s)){
281 s = MAKEINTRESOURCE(IDW_ANNOUNCE_BOILING);
282 }else if(!m_sndTeapotWhistle.Compare(s)){
283 s = MAKEINTRESOURCE(IDW_WAKE_WHISTLE);
284 }else{
285 flags&=~SND_RESOURCE;
286 flags|=SND_FILENAME;
287 }
288 PlaySound(s,AfxGetInstanceHandle(),flags);
289}
290
291void CT42App::Options(CWnd* pParent)
292{
293CSoundsPage sp;
294CFontsPage fp;
295CSecretaryPage sep;
296CGeneralPage gp;
297CPropertySheet ps(IDS_TITLE_OPTIONS,pParent);
298 ps.AddPage(&gp);
299 ps.AddPage(&fp);
300 ps.AddPage(&sp);
301 ps.AddPage(&sep);
302
303 gp.m_ntalkPort = m_T42TalkPort;
304
305 sp.m_T42Bell = m_sndT42Bell;
306 sp.m_T42Prompt = m_sndT42Prompt;
307 sp.m_bT42PromptLoop = m_bT42PromptLoop;
308 sp.m_T42Wake = m_sndT42Wake;
309
310 memmove(&fp.m_fmtT42Local.m_fmtChar,&m_fmtT42Local,sizeof(fp.m_fmtT42Local.m_fmtChar));
311 memmove(&fp.m_fmtT42Remote.m_fmtChar,&m_fmtT42Remote,sizeof(fp.m_fmtT42Remote.m_fmtChar));
312 memmove(&fp.m_fmtT42System.m_fmtChar,&m_fmtT42System,sizeof(fp.m_fmtT42System.m_fmtChar));
313 fp.m_fmtT42Local.m_bgColor=m_crT42LocalBG;
314 fp.m_fmtT42Remote.m_bgColor=m_crT42RemoteBG;
315
316 sep.m_bLimitTime = m_T42STimeLimit.GetTotalSeconds()?TRUE:FALSE;
317 sep.m_limitTime = m_T42STimeLimit.GetTotalSeconds()/60;
318 sep.m_bLimitBytes = m_T42SBytesLimit?TRUE:FALSE;
319 sep.m_limitBytes = m_T42SBytesLimit;
320 sep.m_Greeting = m_T42SGreeting;
321 sep.m_limitWin = m_T42SWinLimit;
322 sep.m_bLimitWin = m_T42SWinLimit?TRUE:FALSE;
323
324 if(ps.DoModal()==IDOK){
325 m_T42TalkPort = gp.m_ntalkPort;
326
327 m_sndT42Bell = sp.m_T42Bell;
328 m_sndT42Prompt = sp.m_T42Prompt;
329 m_bT42PromptLoop = sp.m_bT42PromptLoop;
330 m_sndT42Wake = sp.m_T42Wake;
331
332 memmove(&m_fmtT42Local,&fp.m_fmtT42Local.m_fmtChar,sizeof(m_fmtT42Local));
333 memmove(&m_fmtT42Remote,&fp.m_fmtT42Remote.m_fmtChar,sizeof(m_fmtT42Remote));
334 memmove(&m_fmtT42System,&fp.m_fmtT42System.m_fmtChar,sizeof(m_fmtT42System));
335 m_crT42LocalBG=fp.m_fmtT42Local.m_bgColor;
336 m_crT42RemoteBG=fp.m_fmtT42Remote.m_bgColor;
337
338 m_T42STimeLimit = CTimeSpan(sep.m_bLimitTime?sep.m_limitTime*60:0);
339 m_T42SBytesLimit = sep.m_bLimitBytes?sep.m_limitBytes:0;
340 m_T42SWinLimit = sep.m_bLimitWin?sep.m_limitWin:0;
341 m_T42SGreeting = sep.m_Greeting;
342 }
343}
344
345BOOL CT42App::OpenT42CallsLog()
346{
347 if(!m_T42Calls.Open(m_t42CallsFile,FALSE)){
348 if(!m_T42Calls.Create(m_t42CallsFile))
349 return FALSE;
350 FlushT42CallsLog();
351 }
352 return TRUE;
353}
354
355BOOL CT42App::CloseT42CallsLog()
356{
357 return m_T42Calls.Close();
358}
359
360LONG CT42App::GetT42Calls()
361{
362 if(m_nT42Calls<0){
363 m_nT42Calls=0;
364 m_t42Call = -1;
365 if(!m_T42Calls.GoFirst())
366 return 0;
367 m_nT42Calls++;
368 while(m_T42Calls.GoNext())
369 m_nT42Calls++;
370 }
371 return m_nT42Calls;
372}
373
374BOOL CT42App::GetT42Call(LONG call,CT42CallLogEntry& entry)
375{
376LONG calls = GetT42Calls();
377 if(calls<=0)
378 return FALSE;
379 call = calls-call-1;
380 if(call<0 || calls<=call)
381 return FALSE;
382 if(m_t42Call<0){
383 if(call<(calls/2)){
384 VERIFY(m_T42Calls.GoFirst());
385 m_t42Call=0;
386 }else{
387 VERIFY(m_T42Calls.GoLast());
388 m_t42Call=calls-1;
389 }
390 }
391 if(call<m_t42Call){
392 while(call<m_t42Call){
393 VERIFY(m_T42Calls.GoPrev());
394 m_t42Call--;
395 }
396 }else if(call>m_t42Call){
397 while(call>m_t42Call){
398 VERIFY(m_T42Calls.GoNext());
399 m_t42Call++;
400 }
401 }
402 ASSERT(call==m_t42Call);
403CTime ct;
404 VERIFY(m_T42Calls.GetThis(ct,entry));
405 ASSERT(ct==entry.m_Time);
406 return TRUE;
407}
408
409BOOL CT42App::AddT42Call(CT42CallLogEntry& entry)
410{
411 m_t42Call=-1;
412 if(GetT42Calls()<=0){
413 if(m_T42Calls.Add(entry.m_Time,entry)){
414 FlushT42CallsLog();
415 ASSERT(!m_nT42Calls);
416 m_nT42Calls++;
417 ASSERT(m_pT42Dlg);
418 m_pT42Dlg->OnAddT42Call();
419 return TRUE;
420 }
421 return FALSE;
422 }
423CT42CallLogEntry cle;
424CTimeSpan inc(0,0,0,1);
425 while(m_T42Calls.Lookup(entry.m_Time,cle))
426 entry.m_Time+=inc;
427 if(m_T42Calls.Add(entry.m_Time,entry)){
428 FlushT42CallsLog();
429 m_nT42Calls++;
430 ASSERT(m_pT42Dlg);
431 m_pT42Dlg->OnAddT42Call();
432 return TRUE;
433 }
434 return FALSE;
435}
436
437
438BOOL CT42App::DelT42Call(CTime& time)
439{
440 m_t42Call=-1;
441 if(GetT42Calls()<=0)
442 return FALSE;
443 if(m_T42Calls.Delete(time)){
444 FlushT42CallsLog();
445 m_nT42Calls--;
446 ASSERT(m_pT42Dlg);
447 m_pT42Dlg->OnDelT42Call();
448 return TRUE;
449 }
450 return FALSE;
451}
452
453BOOL CT42App::UpdateT42Call(CT42CallLogEntry& entry)
454{
455 m_t42Call=-1;
456 #ifdef_DEBUG
457CT42CallLogEntry cle;
458 ASSERT(m_T42Calls.Lookup(entry.m_Time,cle));
459#endif
460 m_T42Calls.Add(entry.m_Time,entry);
461 FlushT42CallsLog();
462 return TRUE;
463}
464
465void CT42App::FlushT42CallsLog()
466{
467 m_T42Calls.m_BT.m_File->Flush();
468}