diff options
author | admin@progandy.co.cc <admin@progandy.co.cc@eced67a3-f377-a0ae-92ae-d6de1850b05a> | 2010-09-07 20:56:58 +0000 |
---|---|---|
committer | admin@progandy.co.cc <admin@progandy.co.cc@eced67a3-f377-a0ae-92ae-d6de1850b05a> | 2010-09-07 20:56:58 +0000 |
commit | fabf8cf6652880668158c0160181055705fa947e (patch) | |
tree | 02865290dac031f7e64e4f4bf3a0107f34b1886b /MirOTR | |
parent | 3ab5329069479c9951ee1bf8ac26af73df500045 (diff) |
- add missing files
- beginning SMP implementation
git-svn-id: http://mirotr.googlecode.com/svn/trunk@4 eced67a3-f377-a0ae-92ae-d6de1850b05a
Diffstat (limited to 'MirOTR')
-rw-r--r-- | MirOTR/dialogs.cpp | 203 | ||||
-rw-r--r-- | MirOTR/language.h | 20 | ||||
-rw-r--r-- | MirOTR/mirotrmenu.cpp | 277 | ||||
-rw-r--r-- | MirOTR/mirotrmenu.h | 45 | ||||
-rw-r--r-- | MirOTR/svcs_proto.cpp | 5 |
5 files changed, 545 insertions, 5 deletions
diff --git a/MirOTR/dialogs.cpp b/MirOTR/dialogs.cpp index 15630cf..5b5c6f1 100644 --- a/MirOTR/dialogs.cpp +++ b/MirOTR/dialogs.cpp @@ -4,6 +4,209 @@ #include <commctrl.h>
#include <process.h>
+
+INT_PTR CALLBACK DlgProcSMPInitProc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam)
+{
+ switch ( msg ) {
+ case WM_INITDIALOG:
+ {
+ if (!lParam) {
+ EndDialog(hwndDlg, IDCANCEL);
+ return FALSE;
+ }
+ TranslateDialogDefault( hwndDlg );
+
+ ConnContext *context = (ConnContext*)lParam;
+ TCHAR title[512];
+ mir_sntprintf(title, 512, TranslateT(LANG_SMP_VERIFY_TITLE), contact_get_nameT((HANDLE)context->app_data));
+ SendMessage(hwndDlg, WM_SETTEXT, 0, (LPARAM)title);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_HEAD, title);
+ SetWindowLongPtr(hwndDlg, GWL_USERDATA, lParam);
+
+ // Move window to screen center
+ // Get the owner window and dialog box rectangles.
+ HWND hwndOwner; RECT rcOwner, rcDlg, rc;
+ if ((hwndOwner = GetParent(hwndDlg)) == NULL)
+ {
+ hwndOwner = GetDesktopWindow();
+ }
+
+ GetWindowRect(hwndOwner, &rcOwner);
+ GetWindowRect(hwndDlg, &rcDlg);
+ CopyRect(&rc, &rcOwner);
+
+ // Offset the owner and dialog box rectangles so that right and bottom
+ // values represent the width and height, and then offset the owner again
+ // to discard space taken up by the dialog box.
+
+ OffsetRect(&rcDlg, -rcDlg.left, -rcDlg.top);
+ OffsetRect(&rc, -rc.left, -rc.top);
+ OffsetRect(&rc, -rcDlg.right, -rcDlg.bottom);
+
+ // The new position is the sum of half the remaining space and the owner's
+ // original position.
+
+ SetWindowPos(hwndDlg,
+ HWND_TOP,
+ rcOwner.left + (rc.right / 2),
+ rcOwner.top + (rc.bottom / 2),
+ 0, 0, // Ignores size arguments.
+ SWP_NOSIZE);
+
+ // end center dialog
+
+
+ HWND cmb = GetDlgItem(hwndDlg, IDC_CBO_SMP_CHOOSE);
+ SendMessage(cmb, CB_ADDSTRING, 0, (WPARAM)TranslateT(LANG_SMPTYPE_QUESTION));
+ SendMessage(cmb, CB_ADDSTRING, 0, (WPARAM)TranslateT(LANG_SMPTYPE_PASSWORD));
+ SendMessage(cmb, CB_ADDSTRING, 0, (WPARAM)TranslateT(LANG_SMPTYPE_FINGERPRINT));
+ SendMessage(cmb, CB_SELECTSTRING, -1, (WPARAM)TranslateT(LANG_SMPTYPE_QUESTION));
+ EnableWindow(GetDlgItem(hwndDlg, IDC_CBO_SMP_CHOOSE), TRUE);
+
+
+ Fingerprint *fp = context->active_fingerprint;
+ if (!fp) {
+ EndDialog(hwndDlg, IDCANCEL);
+ return FALSE;
+ }
+ TCHAR buff[1024];
+ if (!fp->trust || fp->trust[0] == '\0')
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPQUESTION_VERIFY_DESC), contact_get_nameT((HANDLE)context->app_data));
+ else
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPQUESTION_VERIFIED_DESC), contact_get_nameT((HANDLE)context->app_data));
+
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_INFO, buff);
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD1, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD1, EM_SETREADONLY, FALSE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD1, TranslateT(LANG_SMP_QUESTION));
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD2, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD2, EM_SETREADONLY, FALSE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD2, TranslateT(LANG_SMP_ANSWER));
+
+
+ ShowWindow(GetDlgItem(hwndDlg, IDOK), SW_SHOWNA);
+ ShowWindow(GetDlgItem(hwndDlg, IDYES), SW_HIDE);
+ ShowWindow(GetDlgItem(hwndDlg, IDNO), SW_HIDE);
+ SetFocus(GetDlgItem(hwndDlg, IDC_CBO_SMP_CHOOSE));
+
+ return FALSE;
+ }
+
+ case WM_COMMAND:
+ switch ( HIWORD( wParam )) {
+ case BN_CLICKED:
+ switch ( LOWORD( wParam )) {
+ case IDYES:
+ case IDNO:
+ case IDCANCEL:
+ case IDOK:
+ EndDialog(hwndDlg, LOWORD( wParam ));
+ break;
+ }
+ case CBN_SELCHANGE:
+ switch ( LOWORD( wParam )) {
+ case IDC_CBO_SMP_CHOOSE:
+ {
+ ConnContext* context = (ConnContext*)GetWindowLongPtr(hwndDlg, GWL_USERDATA);
+ Fingerprint *fp = context->active_fingerprint;
+ if (!fp) {
+ EndDialog(hwndDlg, IDCANCEL);
+ return TRUE;
+ }
+ BOOL trusted = false;
+ if (fp->trust && fp->trust[0] != '\0') trusted = true;
+
+ TCHAR buff[512];
+ GetDlgItemText(hwndDlg, IDC_CBO_SMP_CHOOSE, buff, 255);
+ if (_tcsncmp(buff, TranslateT(LANG_SMPTYPE_QUESTION), 255)) {
+ if (trusted)
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPQUESTION_VERIFY_DESC), contact_get_nameT((HANDLE)context->app_data));
+ else
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPQUESTION_VERIFIED_DESC), contact_get_nameT((HANDLE)context->app_data));
+
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_INFO, buff);
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD1, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD1, EM_SETREADONLY, FALSE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD1, TranslateT(LANG_SMP_QUESTION));
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD2, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD2, EM_SETREADONLY, FALSE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD2, TranslateT(LANG_SMP_ANSWER));
+
+
+ ShowWindow(GetDlgItem(hwndDlg, IDOK), SW_SHOWNA);
+ ShowWindow(GetDlgItem(hwndDlg, IDYES), SW_HIDE);
+ ShowWindow(GetDlgItem(hwndDlg, IDNO), SW_HIDE);
+ } else if (_tcsncmp(buff, TranslateT(LANG_SMPTYPE_PASSWORD), 255)) {
+ if (trusted)
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPPASSWORD_VERIFY_DESC), contact_get_nameT((HANDLE)context->app_data));
+ else
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_SMPPASSWORD_VERIFIED_DESC), contact_get_nameT((HANDLE)context->app_data));
+
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_INFO, buff);
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD1, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD1, EM_SETREADONLY, FALSE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD1, TranslateT(LANG_SMP_PASSWORD));
+
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD2, _T(""));
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD2, EM_SETREADONLY, TRUE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD2, _T(""));
+
+
+ ShowWindow(GetDlgItem(hwndDlg, IDOK), SW_SHOWNA);
+ ShowWindow(GetDlgItem(hwndDlg, IDYES), SW_HIDE);
+ ShowWindow(GetDlgItem(hwndDlg, IDNO), SW_HIDE);
+ } else if (_tcsncmp(buff, TranslateT(LANG_SMPTYPE_FINGERPRINT), 255)) {
+ if (trusted)
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_FPVERIFY_DESC), contact_get_nameT((HANDLE)context->app_data));
+ else
+ mir_sntprintf(buff, 512, TranslateT(LANG_OTR_FPVERIFIED_DESC), contact_get_nameT((HANDLE)context->app_data));
+
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_INFO, buff);
+
+ unsigned char hash[20];
+ lib_cs_lock();
+ if (!otrl_privkey_fingerprint_raw(otr_user_state, hash, context->accountname, context->protocol)) {
+ lib_cs_unlock();
+ EndDialog(hwndDlg, IDCANCEL);
+ return FALSE;
+ }
+ otrl_privkey_hash_to_humanT(buff, hash);
+ lib_cs_unlock();
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD1, buff);
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD1, EM_SETREADONLY, TRUE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD1, TranslateT(LANG_YOUR_PRIVKEY));
+
+ otrl_privkey_hash_to_humanT(buff, fp->fingerprint);
+ SetDlgItemText(hwndDlg, IDC_EDT_SMP_FIELD2, buff);
+ SendDlgItemMessage(hwndDlg, IDC_EDT_SMP_FIELD2, EM_SETREADONLY, TRUE, 0);
+ SetDlgItemText(hwndDlg, IDC_STC_SMP_FIELD2, TranslateT(LANG_CONTACT_FINGERPRINT));
+
+ EnableWindow(GetDlgItem(hwndDlg, IDC_CBO_SMP_CHOOSE), FALSE);
+
+ ShowWindow(GetDlgItem(hwndDlg, IDOK), SW_HIDE);
+ ShowWindow(GetDlgItem(hwndDlg, IDYES), SW_SHOWNA);
+ ShowWindow(GetDlgItem(hwndDlg, IDNO), SW_SHOWNA);
+
+ }
+ }break;
+ }
+ }
+ break;
+
+ }
+
+ return FALSE;
+}
+void SMPInitDialog(ConnContext* context) {
+ if (!context) return;
+ CreateDialogParamW(hInst, MAKEINTRESOURCE(IDD_SMP_INPUT), 0, DlgProcSMPInitProc, (LPARAM) context);
+}
+
unsigned int CALLBACK verify_context_thread(void *param);
void VerifyContextDialog(ConnContext* context) {
if (!context) return;
diff --git a/MirOTR/language.h b/MirOTR/language.h index 941f1fc..1e6b81a 100644 --- a/MirOTR/language.h +++ b/MirOTR/language.h @@ -44,9 +44,9 @@ #define LANG_OTR_USERMESSAGE LPGEN("OTR: %s (%s)")
#define LANG_OTR_NOTIFY LPGEN("OTR %s (%s)")
-#define LANG_FINGERPRINT_CAPTION LPGEN("OTR New Fingerprint")
-#define LANG_FINGERPRINT_ASK_VERIFY LPGEN("OTR encrypted session with '%s'.\n\nFingerprint is UNVERIFIED.\n\n%s\n\nVerify?")
-#define LANG_FINGERPRINT_ASK_NEW LPGEN("A new fingerprint has been recieved from '%s'\n\n%s\n\nDo you trust it?")
+//#define LANG_FINGERPRINT_CAPTION LPGEN("OTR New Fingerprint")
+//#define LANG_FINGERPRINT_ASK_VERIFY LPGEN("OTR encrypted session with '%s'.\n\nFingerprint is UNVERIFIED.\n\n%s\n\nVerify?")
+//#define LANG_FINGERPRINT_ASK_NEW LPGEN("A new fingerprint has been recieved from '%s'\n\n%s\n\nDo you trust it?")
#define LANG_FINGERPRINT_VERIFIED LPGEN("OTR encrypted session with '%s' is now using a VERIFIED fingerprint")
#define LANG_FINGERPRINT_NOT_VERIFIED LPGEN("OTR encrypted session with '%s' is now using a NOT VERIFIED fingerprint")
@@ -85,5 +85,19 @@ #define LANG_YOUR_PRIVKEY LPGEN("Your Fingerprint to tell your contact (use a trusted channel!)")
#define LANG_CONTACT_FINGERPRINT LPGEN("VERIFY: Fingerprint from contact")
+#define LANG_SMP_VERIFY_TITLE LPGEN("OTR Authenticate %s")
+#define LANG_SMPTYPE_QUESTION LPGEN("Question / Answer")
+#define LANG_SMPTYPE_PASSWORD LPGEN("Known Password")
+#define LANG_SMPTYPE_FINGERPRINT LPGEN("Manual fingerprint comparison")
+#define LANG_SMP_ANSWER LPGEN("Answer")
+#define LANG_SMP_QUESTION LPGEN("Question")
+#define LANG_SMP_PASSWORD LPGEN("Password")
+
+#define LANG_OTR_SMPQUESTION_VERIFY_DESC LPGEN("OTR encrypted session with '%s' (UNVERIFIED).\nUse a question only your partner can answer.")
+#define LANG_OTR_SMPQUESTION_VERIFIED_DESC LPGEN("OTR encrypted session with '%s' (VERIFIED).\nVerify the session again using a question only your partner can answer.")
+
+#define LANG_OTR_SMPPASSWORD_VERIFY_DESC LPGEN("OTR encrypted session with '%s' (UNVERIFIED).\nUse a known password.")
+#define LANG_OTR_SMPPASSWORD_VERIFIED_DESC LPGEN("OTR encrypted session with '%s' (VERIFIED).\nVerify the session again using a known password.")
+
#define LANG_FINGERPRINT_STILL_IN_USE LPGEN("Fingerprint '%s' still in use in conversation with '%s'. You cannot delete it!")
#define LANG_FINGERPRINT_NOT_DELETED LPGEN("Fingerprint '%s' in use in conversation with '%s'. It could not be deleted!")
\ No newline at end of file diff --git a/MirOTR/mirotrmenu.cpp b/MirOTR/mirotrmenu.cpp new file mode 100644 index 0000000..65d512d --- /dev/null +++ b/MirOTR/mirotrmenu.cpp @@ -0,0 +1,277 @@ +#include "stdafx.h"
+#include "m_genmenu.h"
+#include "mirotrmenu.h"
+static HANDLE hMirOTRMenuObject;
+static HGENMENU hStatusInfoItem;
+HWND hDummyPaintWin;
+
+//contactmenu exec param(ownerdata)
+//also used in checkservice
+typedef struct
+{
+ char *szServiceName;
+}
+MirOTRMenuExecParam,*lpMirOTRMenuExecParam;
+
+/////////////////////////////////////////////////////////////////////////////////////////
+// MirOTR MENU
+
+static INT_PTR RemoveMirOTRMenuItem(WPARAM wParam, LPARAM)
+{
+ CallService(MO_REMOVEMENUITEM,wParam,0);
+ return 0;
+}
+
+static INT_PTR AddMirOTRMenuItem(WPARAM, LPARAM lParam)
+{
+ MIROTRMENUITEM *mi=(MIROTRMENUITEM*)lParam;
+ if ( mi->cbSize != sizeof( MIROTRMENUITEM ))
+ return 0;
+
+ TMO_MenuItem tmi = { 0 };
+ tmi.cbSize = sizeof(tmi);
+ tmi.flags = mi->flags;
+ tmi.hIcon = mi->hIcon;
+ tmi.hIcolibItem = mi->icolibItem;
+ tmi.hotKey = mi->hotKey;
+ tmi.position = mi->position;
+ tmi.ptszName = mi->ptszName;
+ tmi.root = mi->root;
+
+ //owner data
+ lpMirOTRMenuExecParam cmep = ( lpMirOTRMenuExecParam )mir_calloc(sizeof(MirOTRMenuExecParam));
+ cmep->szServiceName = mir_strdup( mi->pszService );
+ tmi.ownerdata = cmep;
+
+ INT_PTR menuHandle = CallService(MO_ADDNEWMENUITEM, (WPARAM) hMirOTRMenuObject, (LPARAM)&tmi );
+
+ return menuHandle;
+}
+
+static INT_PTR BuildMirOTRMenu(WPARAM wParam, LPARAM)
+{
+ HANDLE hContact = ( HANDLE )wParam;
+ //NotifyEventHooks(hPreBuildMirOTRMenuEvent,(WPARAM)hMirOTR,0);
+
+
+ ListParam param = { 0 };
+ param.MenuObjectHandle = hMirOTRMenuObject;
+ param.wParam = (WPARAM)otr_context_get_trust(otrl_context_find_miranda(otr_user_state, hContact));
+ HMENU hMenu = CreatePopupMenu();
+ CallService(MO_BUILDMENU,(WPARAM)hMenu,(LPARAM)¶m);
+
+ return (INT_PTR)hMenu;
+}
+
+//called with:
+//wparam - ownerdata
+//lparam - lparam from winproc
+INT_PTR MirOTRMenuExecService(WPARAM wParam,LPARAM lParam)
+{
+ if (wParam!=0) {
+ lpMirOTRMenuExecParam cmep=(lpMirOTRMenuExecParam)wParam;
+ //call with wParam=(WPARAM)(HANDLE)hContact
+ CallService(cmep->szServiceName,lParam,0);
+ }
+ return 0;
+}
+
+//true - ok,false ignore
+INT_PTR MirOTRMenuCheckService(WPARAM wParam,LPARAM)
+{
+ PCheckProcParam pcpp = ( PCheckProcParam )wParam;
+ lpMirOTRMenuExecParam cmep=NULL;
+ TMO_MenuItem mi;
+
+ if ( pcpp == NULL )
+ return FALSE;
+
+ cmep = ( lpMirOTRMenuExecParam )pcpp->MenuItemOwnerData;
+ if ( cmep == NULL ) //this is root...build it
+ return TRUE;
+
+ TrustLevel level = ( TrustLevel )pcpp->wParam;
+
+ mi.cbSize = sizeof(mi);
+ if ( CallService(MO_GETMENUITEM, ( WPARAM )pcpp->MenuItemHandle, ( LPARAM )&mi ) == 0 ) {
+
+ if ( mi.flags & CMIF_HIDDEN ) return FALSE;
+ if ( mi.flags & CMIF_NOTPRIVATE && level==TRUST_PRIVATE ) return FALSE;
+ if ( mi.flags & CMIF_NOTFINISHED && level==TRUST_FINISHED ) return FALSE;
+ if ( mi.flags & CMIF_NOTUNVERIFIED && level==TRUST_UNVERIFIED ) return FALSE;
+ if ( mi.flags & CMIF_NOTNOTPRIVATE && level==TRUST_NOT_PRIVATE ) return FALSE;
+
+ if (pcpp->MenuItemHandle == hStatusInfoItem) {
+ mi.flags = CMIM_NAME | CMIM_ICON | CMIF_ICONFROMICOLIB | CMIF_TCHAR;
+ switch (level) {
+ case TRUST_PRIVATE:
+ mi.hIcolibItem = GetIconHandle(ICON_PRIVATE);
+ mi.ptszName = TranslateT(LANG_STATUS_PRIVATE);
+ break;
+ case TRUST_UNVERIFIED:
+ mi.hIcolibItem = GetIconHandle(ICON_UNVERIFIED);
+ mi.ptszName = TranslateT(LANG_STATUS_UNVERIFIED);
+ break;
+ case TRUST_FINISHED:
+ mi.hIcolibItem = GetIconHandle(ICON_FINISHED);
+ mi.ptszName = TranslateT(LANG_STATUS_FINISHED);
+ break;
+ default:
+ mi.hIcolibItem = GetIconHandle(ICON_NOT_PRIVATE);
+ mi.ptszName = TranslateT(LANG_STATUS_DISABLED);
+ }
+ CallService(MO_MODIFYMENUITEM, (WPARAM)hStatusInfoItem, (LPARAM)&mi);
+ }
+ }
+ return TRUE;
+}
+
+INT_PTR FreeOwnerDataMirOTRMenu (WPARAM, LPARAM lParam)
+{
+ lpMirOTRMenuExecParam cmep = ( lpMirOTRMenuExecParam )lParam;
+ if ( cmep != NULL ) {
+ if (cmep->szServiceName) mir_free(cmep->szServiceName);
+ mir_free(cmep);
+ }
+ return 0;
+}
+
+INT_PTR OnAddMenuItemMirOTRMenu (WPARAM wParam, LPARAM lParam)
+{
+
+ MENUITEMINFO *mii = (MENUITEMINFO*)wParam;
+ if (!mii || mii->cbSize != sizeof(MENUITEMINFO)) return 0;
+
+ TMO_MenuItem mi;
+ mi.cbSize = sizeof(mi);
+ if ( CallService(MO_GETMENUITEM, ( WPARAM )lParam, ( LPARAM )&mi ) == 0 ) {
+ if (mi.flags & CMIF_DISABLED) {
+ mii->fMask |= MIIM_STATE;
+ mii->fState |= MF_DISABLED;
+ }
+ }
+ return 1;
+}
+
+
+LRESULT CALLBACK PopupMenuWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
+{
+ switch (message)
+ {
+ case WM_MEASUREITEM:
+ if (CallService(MS_CLIST_MENUMEASUREITEM, wParam, lParam)) return TRUE;
+ break;
+ case WM_DRAWITEM:
+ if (CallService(MS_CLIST_MENUDRAWITEM, wParam, lParam)) return TRUE;
+ break;
+ case WM_COMMAND:
+ if (CallService(MO_PROCESSCOMMANDBYMENUIDENT, wParam, GetWindowLongPtr(hwnd, GWL_USERDATA))) return TRUE;
+ break;
+ }
+ return DefWindowProc(hwnd, message, wParam, lParam);
+}
+
+void ShowOTRMenu(HANDLE hContact, POINT pt){
+ HMENU menu = (HMENU) CallService(MS_MIROTR_MENUBUILDMIROTR, (WPARAM)hContact, 0);
+ SetWindowLongPtr(hDummyPaintWin, GWL_USERDATA, (LONG_PTR)hContact);
+ TrackPopupMenu(menu, 0, pt.x, pt.y, 0, hDummyPaintWin, 0);
+ DestroyMenu(menu);
+}
+
+void InitMirOTRMenu(void)
+{
+
+ WNDCLASS wc = {0};
+ wc.hInstance = hInst;
+ wc.lpfnWndProc = PopupMenuWndProc;
+ wc.lpszClassName = _T("MirOTRPopUpMenuProcessor");
+ RegisterClass(&wc);
+ hDummyPaintWin = CreateWindowEx(0, _T("MirOTRPopUpMenuProcessor"), NULL, 0, 0, 0, 1, 1, 0, 0, hInst, 0);
+
+ CreateServiceFunction("MirOTRMenuExecService",MirOTRMenuExecService);
+ CreateServiceFunction("MirOTRMenuCheckService",MirOTRMenuCheckService);
+
+ //free services
+ CreateServiceFunction("MIROTRMENUS/FreeOwnerDataMirOTRMenu",FreeOwnerDataMirOTRMenu);
+ CreateServiceFunction("MIROTRMENUS/OnAddMenuItemMirOTRMenu",OnAddMenuItemMirOTRMenu);
+
+
+ CreateServiceFunction(MS_MIROTR_ADDMIROTRMENUITEM,AddMirOTRMenuItem);
+ CreateServiceFunction(MS_MIROTR_MENUBUILDMIROTR,BuildMirOTRMenu);
+ CreateServiceFunction(MS_MIROTR_REMOVEMIROTRMENUITEM,RemoveMirOTRMenuItem);
+
+ //hPreBuildMirOTRMenuEvent=CreateHookableEvent(ME_CLIST_PREBUILDMirOTRMENU);
+
+ //MirOTR menu
+ {
+ TMenuParam tmp = { 0 };
+ tmp.cbSize=sizeof(tmp);
+ tmp.CheckService="MirOTRMenuCheckService";
+ tmp.ExecService="MirOTRMenuExecService";
+ tmp.name="MirOTRMenu";
+ hMirOTRMenuObject=(HANDLE)CallService(MO_CREATENEWMENUOBJECT,(WPARAM)0,(LPARAM)&tmp);
+ }
+
+ OptParam params;
+ params.Handle = hMirOTRMenuObject;
+ params.Setting = OPT_USERDEFINEDITEMS;
+ params.Value = FALSE;
+ CallService(MO_SETOPTIONSMENUOBJECT, 0, (LPARAM)¶ms);
+
+ params.Setting = OPT_MENUOBJECT_SET_FREE_SERVICE;
+ params.Value = (INT_PTR)"MIROTRMENUS/FreeOwnerDataMirOTRMenu";
+ CallService(MO_SETOPTIONSMENUOBJECT, 0, (LPARAM)¶ms);
+
+ params.Setting = OPT_MENUOBJECT_SET_ONADD_SERVICE;
+ params.Value = (INT_PTR)"MIROTRMENUS/OnAddMenuItemMirOTRMenu";
+ CallService(MO_SETOPTIONSMENUOBJECT, 0, (LPARAM)¶ms);
+
+
+ MIROTRMENUITEM mi = {0};
+ mi.cbSize = sizeof(mi);
+
+ mi.flags = CMIF_DISABLED|CMIF_TCHAR|CMIF_ICONFROMICOLIB;
+ mi.ptszName = _T("OTR Status");
+ mi.position = 0;
+ hStatusInfoItem = (HGENMENU) AddMirOTRMenuItem(0, (LPARAM) &mi);
+
+ mi.flags = CMIF_TCHAR|CMIF_ICONFROMICOLIB|CMIF_NOTPRIVATE|CMIF_NOTUNVERIFIED;
+ mi.ptszName = _T(LANG_MENU_START);
+ mi.position = 100001;
+ mi.pszService = MS_OTR_MENUSTART;
+ mi.icolibItem = GetIconHandle(ICON_UNVERIFIED);
+ AddMirOTRMenuItem(0, (LPARAM) &mi);
+
+ mi.flags = CMIF_TCHAR|CMIF_ICONFROMICOLIB|CMIF_NOTNOTPRIVATE|CMIF_NOTFINISHED;
+ mi.ptszName = _T(LANG_MENU_REFRESH);
+ mi.position = 100002;
+ mi.pszService = MS_OTR_MENUREFRESH;
+ mi.icolibItem = GetIconHandle(ICON_FINISHED);
+ AddMirOTRMenuItem(0, (LPARAM) &mi);
+
+ mi.flags = CMIF_TCHAR|CMIF_ICONFROMICOLIB|CMIF_NOTNOTPRIVATE;
+ mi.ptszName = _T(LANG_MENU_STOP);
+ mi.position = 100003;
+ mi.pszService = MS_OTR_MENUSTOP;
+ mi.icolibItem = GetIconHandle(ICON_NOT_PRIVATE);
+ AddMirOTRMenuItem(0, (LPARAM) &mi);
+
+ mi.flags = CMIF_TCHAR|CMIF_ICONFROMICOLIB|CMIF_NOTNOTPRIVATE|CMIF_NOTFINISHED;
+ mi.ptszName = _T(LANG_MENU_VERIFY);
+ mi.position = 200001;
+ mi.pszService = MS_OTR_MENUVERIFY;
+ mi.icolibItem = GetIconHandle(ICON_PRIVATE);
+ AddMirOTRMenuItem(0, (LPARAM) &mi);
+
+
+
+}
+
+void UninitMirOTRMenu(void)
+{
+ DestroyWindow(hDummyPaintWin);
+ hDummyPaintWin = 0;
+ UnregisterClass(_T("MirOTRPopUpMenuProcessor"), hInst);
+ if ( hMirOTRMenuObject ) CallService( MO_REMOVEMENUOBJECT, (WPARAM)hMirOTRMenuObject, 0 );
+ hMirOTRMenuObject = 0;
+}
\ No newline at end of file diff --git a/MirOTR/mirotrmenu.h b/MirOTR/mirotrmenu.h new file mode 100644 index 0000000..fa24799 --- /dev/null +++ b/MirOTR/mirotrmenu.h @@ -0,0 +1,45 @@ +#pragma once
+#define MS_MIROTR_ADDMIROTRMENUITEM MODULENAME"/AddMirOTRMenuItem"
+#define MS_MIROTR_MENUBUILDMIROTR MODULENAME"/MenuBuildMirOTR"
+#define MS_MIROTR_REMOVEMIROTRMENUITEM MODULENAME"/RemoveMirOTRMenuItem"
+
+#define CMIF_NOTNOTPRIVATE CMIF_NOTOFFLINE
+#define CMIF_NOTUNVERIFIED CMIF_NOTONLINE
+#define CMIF_NOTPRIVATE CMIF_NOTONLIST
+#define CMIF_NOTFINISHED CMIF_NOTOFFLIST
+#define CMIF_DISABLED 0x8000
+
+//add a new item to the MirOTR Menu
+//wParam=0
+//lParam=(LPARAM)(CLISTMENUITEM*)&mi
+//returns a handle to the new item, or NULL on failure
+//the service that is called when the item is clicked is called with
+//wParam=0, lParam=hContact
+//dividers are inserted every 100000 positions
+//pszContactOwner is ignored for this service.
+//
+// WARNING: do not use Translate(TS) for p(t)szName or p(t)szPopupName as they
+// are translated by the core, which may lead to double translation.
+// Use LPGEN instead which are just dummy wrappers/markers for "lpgen.pl".
+typedef struct {
+ int cbSize; //size in bytes of this structure
+ union {
+ char* pszName; //[TRANSLATED-BY-CORE] text of the menu item
+ TCHAR* ptszName; //Unicode text of the menu item
+ };
+ int position; //approx position on the menu. lower numbers go nearer the top
+ HGENMENU root; //submenu where the item will be added, NULL for root
+ DWORD flags; //set of MOMIF_* flags
+ union {
+ HICON hIcon; //icon to put by the item. If this was not loaded from
+ //a resource, you can delete it straight after the call
+ HANDLE icolibItem; //set CMIF_ICONFROMICOLIB to pass this value
+ };
+ DWORD hotKey; //keyboard accelerator, same as lParam of WM_HOTKEY,0 for none
+ char* pszService; //name of service to call when the item gets selected
+} MIROTRMENUITEM;
+
+void InitMirOTRMenu(void);
+void UninitMirOTRMenu(void);
+
+void ShowOTRMenu(HANDLE hContact, POINT pt);
\ No newline at end of file diff --git a/MirOTR/svcs_proto.cpp b/MirOTR/svcs_proto.cpp index b46b33f..8bbb553 100644 --- a/MirOTR/svcs_proto.cpp +++ b/MirOTR/svcs_proto.cpp @@ -29,7 +29,9 @@ int SVC_OTRSendMessage(WPARAM wParam,LPARAM lParam){ oldmessage_utf = oldmessage;
} else if(ccs->wParam & PREF_UNICODE) {
//TODO: check if this is correct or oldmessage[strlen(oldmessage)+1] is needed
- oldmessage_utf = mir_utf8encodeW((wchar_t*)oldmessage);
+ //oldmessage_utf = mir_utf8encodeW((wchar_t*)oldmessage);
+ //should be the thing with strlen
+ oldmessage_utf = mir_utf8encodeW((wchar_t*)&oldmessage[strlen(oldmessage)+1]);
} else {
oldmessage_utf = mir_utf8encode(oldmessage);
}
@@ -138,7 +140,6 @@ int SVC_OTRRecvMessage(WPARAM wParam,LPARAM lParam){ #endif
if (pre->flags & PREF_BYPASS_OTR) { // bypass for our inline messages
- //TODO: check, whether this can be removed (then OTR status info should be still saved)
return CallService(MS_PROTO_CHAINRECV, wParam, lParam);
}
|