This commit is contained in:
BlubbFish 2013-05-08 21:39:27 +00:00
parent da3fdf8db2
commit 8896edc368
135 changed files with 19164 additions and 0 deletions

View File

@ -0,0 +1,30 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace Speak.Core
{
internal class ActionClickEvent : EventArgs
{
private string action;
private bool autoSend;
public ActionClickEvent(string action, bool autoSend)
{
this.action = action;
this.autoSend = autoSend;
}
public string Action
{
get { return action; }
set { action = value; }
}
public bool AutoSend
{
get { return autoSend; }
set { autoSend = value; }
}
}
}

View File

@ -0,0 +1,86 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using Speak.Fork;
namespace Speak.Core
{
internal class ActionProcessor
{
private ContactManager cm;
private Buttons btns;
public ActionProcessor(ContactManager cm, Buttons btns)
{
this.cm = cm;
this.btns = btns;
btns.OnAction += ActionHandler;
cm.OnAction += ActionHandler;
}
private void ActionHandler(object sender, ActionEvent e)
{
string[] actionInfo = e.Action.Split('/');
switch (actionInfo[0])
{
case "autofork":
Settings.Instance.AutoFork = !Settings.Instance.AutoFork;
Settings.Save();
break;
case "forkdel":
DialogResult dr = MessageBox.Show(
"Ты уверен в том, что делаешь?" + Environment.NewLine +
"Хочешь удалить из контакт листа все псевдоконтакты с комментариями?",
"[xJuick] Подтверждение очистки контакт листа",
MessageBoxButtons.YesNoCancel,
MessageBoxIcon.Exclamation);
if (dr == DialogResult.Yes)
cm.ClearContacts();
break;
case "fork":
if (actionInfo.Length == 1)
return;
Match m = Sites.SitesManager.GetContactSite(e.HContact).NumRegex.Match(actionInfo[1]);
if (!m.Success)
return;
cm.ChangeForkState(e.HContact, m.Groups["post"].Value);
break;
case "avatars":
Settings.Instance.ShowAvatars = !Settings.Instance.ShowAvatars;
Settings.Save();
cm.Avatars();
break;
}
}
}
internal class ActionEvent : EventArgs
{
private string action;
private IntPtr hContact;
public ActionEvent(IntPtr hContact, string action)
{
this.hContact = hContact;
this.action = action;
}
public string Action
{
get { return action; }
}
public IntPtr HContact
{
get { return hContact; }
}
}
}

View File

@ -0,0 +1,172 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Xml;
using Speak.Sites;
namespace Speak.Core
{
internal class AvatarProcessor
{
private object lockObject = new object();
private /*volatile*/ Queue<AvatarQueueItem> queue;
private HTTP http;
private ISite site;
private string avatarsPath;
public AvatarProcessor(ISite site)
{
this.site = site;
avatarsPath = Settings.xJuickAvatarsFolder + "\\" + site.Name + "_{0}.png";
http = new HTTP();
queue = new Queue<AvatarQueueItem>();
}
public void AddToQueue(string userName, AvatarCallBack callback)
{
//string url = String.Format(ava32, userName);
//lock(lockObject)
{
foreach (AvatarQueueItem aItem in queue)
{
if (aItem.UserName.Equals(userName))
{
if (callback != null)
aItem.AddCallBack(callback);
return;
}
}
queue.Enqueue(new AvatarQueueItem(userName, callback));
}
}
private void Dequeue()
{
while (queue.Count != 0)
{
lock (lockObject)
{
if (queue.Count != 0)
{
AvatarQueueItem item = queue.Dequeue();
if (DownloadAvatar(item.UserName))
{
item.CallSubscribers(String.Format(avatarsPath, item.UserName));
}
}
}
}
}
public void Process()
{
if (queue.Count != 0)
{
Thread thread = new Thread(Dequeue);
thread.IsBackground = false;
thread.Start();
}
}
public string GetUserAvatar(string userName, AvatarCallBack callback)
{
string fullPath = Path.GetFullPath(String.Format(avatarsPath, userName));
if (File.Exists(fullPath))
return fullPath;
AddToQueue(userName, callback);
return String.Empty;
}
private bool DownloadAvatar(string user)
{
string avatarUrl = site.GetAvatarPath(user);
if (String.IsNullOrEmpty(avatarUrl))
return false;
Stream avatar = http.GetImage(avatarUrl);
if (avatar != null)
{
if (File.Exists(String.Format(avatarsPath, user)))
return false;
Stream fs = FileStream.Synchronized(File.Open(String.Format(avatarsPath, user), FileMode.Create, FileAccess.Write, FileShare.None));
byte[] bytes = new byte[255];
int count = 0;
while ((count = avatar.Read(bytes, 0, 255)) > 0)
{
fs.Write(bytes, 0, count);
}
avatar.Close();
fs.Close();
return true;
}
return false;
}
}
internal delegate void AvatarCallBack(string userName, string avatarPath);
internal class AvatarQueueItem
{
private string userName;
private List<AvatarCallBack> callbacks;
public AvatarQueueItem(string avatarUrl, AvatarCallBack callback)
{
this.userName = avatarUrl;
callbacks = new List<AvatarCallBack>();
callbacks.Add(callback);
}
public string UserName
{
get { return userName; }
}
public void AddCallBack(AvatarCallBack callBack)
{
callbacks.Add(callBack);
}
public void CallSubscribers(string avatarPath)
{
for (int i = 0, iCount = callbacks.Count; i < iCount; i++)
{
if (callbacks[i] != null)
callbacks[i].Invoke(userName, avatarPath);
}
}
public override bool Equals(object obj)
{
if (ReferenceEquals(null, obj)) return false;
if (ReferenceEquals(this, obj)) return true;
if (obj.GetType() != typeof (AvatarQueueItem)) return false;
return Equals((AvatarQueueItem) obj);
}
public bool Equals(AvatarQueueItem other)
{
if (ReferenceEquals(null, other)) return false;
if (ReferenceEquals(this, other)) return true;
return Equals(other.userName, userName);
}
public override int GetHashCode()
{
unchecked
{
return ((userName != null ? userName.GetHashCode() : 0)*397) ^ (callbacks != null ? callbacks.GetHashCode() : 0);
}
}
}
}

359
Speak/Speak/Core/Buttons.cs Normal file
View File

@ -0,0 +1,359 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Xml.Serialization;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Structs;
using Speak.Utils;
namespace Speak.Core
{
internal class Buttons
{
private bool hidden;
private bool enabled;
private List<ButtonInfo> buttons;
private List<ButtonInfo> hardcodedButtons;
private const string AUTOFORK_COMMAND = "xJuick://AutoFork";
private const string AVATARS_COMMAND = "xJuick://Avatars";
private const string FORKDEL_COMMAND = "xJuick://ForkDel";
public Buttons()
{
buttons = new List<ButtonInfo>();
hardcodedButtons = new List<ButtonInfo>();
hardcodedButtons.Add(new ButtonInfo("Отдельное окно для комментариев", AUTOFORK_COMMAND, "xJuick_Fork", true, true));
hardcodedButtons.Add(new ButtonInfo("Удалить контакты комментариев", FORKDEL_COMMAND, "xJuick_ForkDel"));
hardcodedButtons.Add(new ButtonInfo("Включить/Выключить аватары", AVATARS_COMMAND, "xJuick_Avatars"));
hidden = true;
enabled = false;
}
public void AddButton(string name, string command)
{
AddButton(name, command, name);
}
public void AddButton(string name, string command, string iconName)
{
buttons.Add(new ButtonInfo(name, command, iconName));
}
public void AddButtons(ButtonInfo[] buttons)
{
this.buttons.AddRange(buttons);
}
private IntPtr GetIcon(ButtonInfo btn)
{
UnmanagedStringHandle str = new UnmanagedStringHandle(btn.IconName, StringEncoding.Ansi);
IntPtr hIcon = new IntPtr(MirandaContext.Current.CallService(API.MS_SKIN2_GETICON, UIntPtr.Zero, str.IntPtr));
str.Free();
if (hIcon != IntPtr.Zero)
{
btn.HIcon = hIcon;
return btn.HIcon;
}
IconName iName = new IconName();
iName.Init();
iName.cbSize = Marshal.SizeOf(iName);
iName.szSection = Settings.IcoLibPath;
iName.szDescription = btn.Name;
iName.pszName = btn.IconName;
iName.hDefaultIcon = IconTable.GetDefaultIcon(btn.IconName);
hIcon = Marshal.AllocHGlobal(Marshal.SizeOf(iName));
Marshal.StructureToPtr(iName, hIcon, false);
btn.HIcon = new IntPtr(MirandaContext.Current.CallService(API.MS_SKIN2_ADDICON, UIntPtr.Zero, hIcon));
return btn.HIcon;
}
private void SetButtonState(IntPtr hContact, ButtonInfo btn, UInt32 state)
{
BBButton bbButton = new BBButton();
bbButton.cbSize = Marshal.SizeOf(bbButton);
bbButton.pszModuleName = Settings.ModuleName;
bbButton.szTooltip = btn.Name;
bbButton.dwButtonID = btn.ButtonID;
bbButton.iButtonWidth = 0;
bbButton.hIcon = btn.HIcon;
bbButton.bbbFlags = state;
IntPtr bbPtr = Marshal.AllocHGlobal(Marshal.SizeOf(bbButton));
Marshal.StructureToPtr(bbButton, bbPtr, false);
MirandaContext.Current.CallService(API.MS_BB_SETBUTTONSTATE, hContact, bbPtr);
}
public void Create()
{
Delete();
Create(290, hardcodedButtons);
Create(340, buttons);
}
private void Create(uint startIndex, List<ButtonInfo> btns)
{
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
ButtonInfo btn = btns[i];
if (!btn.Enabled)
continue;
BBButton bbButton = new BBButton();
bbButton.cbSize = Marshal.SizeOf(bbButton);
bbButton.pszModuleName = Settings.ModuleName;
bbButton.szTooltip = btn.Name;
bbButton.dwDefPos = startIndex + (uint)i + 1;
bbButton.dwButtonID = btn.ButtonID = bbButton.dwDefPos;
bbButton.iButtonWidth = 0;
bbButton.bbbFlags |= TabSRMMConstants.BBBF_ISCHATBUTTON | TabSRMMConstants.BBBF_ISIMBUTTON | TabSRMMConstants.BBBF_ISLSIDEBUTTON;
if (btn.IsPush)
bbButton.bbbFlags |= TabSRMMConstants.BBBF_ISPUSHBUTTON;
if (hidden)
bbButton.bbbFlags |= TabSRMMConstants.BBBF_HIDDEN;
bbButton.hIcon = btn.HIcon == IntPtr.Zero ? GetIcon(btn) : btn.HIcon;
IntPtr bbPtr = Marshal.AllocHGlobal(Marshal.SizeOf(bbButton));
Marshal.StructureToPtr(bbButton, bbPtr, false);
MirandaContext.Current.CallService(API.MS_BB_ADDBUTTON, IntPtr.Zero, bbPtr);
}
}
public void Click(UInt32 buttonID, IntPtr hContact)
{
if (!Click(buttonID, hContact, buttons))
Click(buttonID, hContact, hardcodedButtons);
}
private bool Click(UInt32 buttonID, IntPtr hContact, List<ButtonInfo> btns)
{
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
ButtonInfo btn = btns[i];
if (btn.ButtonID == buttonID)
{
// Нет, я не идиот (кажется).
// Просто MirandaContext.Current.HookEvent вызывается дважды
btn.Pressed = !btn.Pressed;
if (btn.Pressed)
return true;
if (btn.Command.StartsWith("http://", StringComparison.InvariantCultureIgnoreCase))
{
Util.OpenURL(btn.Command);
return true;
}
if (btn.Command.StartsWith("xJuick://", StringComparison.InvariantCultureIgnoreCase))
{
InvokeOnAction(hContact, btn.Command.Substring(9).ToLower());
return true;
}
CSSData css = new CSSData();
css.hContact = hContact;
css.szProtoService = API.PSS_MESSAGE;
css.wParam = IntPtr.Zero;
css.lParam = new UnmanagedStringHandle(btn.Command, StringEncoding.Ansi).IntPtr;
IntPtr cmdPtr = Marshal.AllocHGlobal(Marshal.SizeOf(css));
Marshal.StructureToPtr(css, cmdPtr, false);
MirandaContext.Current.CallService(API.MS_PROTO_CALLCONTACTSERVICE, IntPtr.Zero, cmdPtr);
return true;
}
}
return false;
}
private void Delete()
{
Delete(buttons);
Delete(hardcodedButtons);
}
private void Delete(List<ButtonInfo> btns)
{
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
if (btns[i].ButtonID == 0)
continue;
BBButton bbButton = new BBButton();
bbButton.cbSize = Marshal.SizeOf(bbButton);
bbButton.pszModuleName = Settings.ModuleName;
bbButton.dwButtonID = btns[i].ButtonID;
bbButton.iButtonWidth = 0;
bbButton.szTooltip = "";
IntPtr bbPtr = Marshal.AllocHGlobal(Marshal.SizeOf(bbButton));
Marshal.StructureToPtr(bbButton, bbPtr, false);
MirandaContext.Current.CallService(API.MS_BB_REMOVEBUTTON, IntPtr.Zero, bbPtr);
btns[i].ButtonID = 0;
}
}
public void Hide(IntPtr hContact)
{
hidden = true;
Hide(hContact, buttons);
Hide(hContact, hardcodedButtons);
}
private void Hide(IntPtr hContact, List<ButtonInfo> btns)
{
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
SetButtonState(hContact, btns[i], TabSRMMConstants.BBSF_HIDDEN);
}
}
public void Show(IntPtr hContact)
{
hidden = false;
Show(hContact, buttons);
Show(hContact, hardcodedButtons);
for (int i = 0, iCount = hardcodedButtons.Count; i < iCount; i++)
{
if (hardcodedButtons[i].Command.Equals(AUTOFORK_COMMAND))
{
SetButtonState(hContact, hardcodedButtons[i], Settings.Instance.AutoFork ? TabSRMMConstants.BBSF_PUSHED : TabSRMMConstants.BBSF_RELEASED);
}
// doesnt work in IE and HPP
else if (hardcodedButtons[i].Command.Equals(AVATARS_COMMAND))
{
SetButtonState(hContact, hardcodedButtons[i], Settings.CurrentLog != LogHandler.Default ? TabSRMMConstants.BBSF_HIDDEN : TabSRMMConstants.BBSF_RELEASED);
}
}
}
public void Show(IntPtr hContact, List<ButtonInfo> btns)
{
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
SetButtonState(hContact, btns[i], TabSRMMConstants.BBSF_RELEASED);
btns[i].Pressed = true;
}
}
public bool Hidden
{
get { return hidden; }
set { hidden = value; }
}
public bool Enabled
{
get { return enabled; }
set { enabled = value; }
}
public event EventHandler<ActionEvent> OnAction;
public void InvokeOnAction(IntPtr hContact, string action)
{
if (OnAction == null)
return;
OnAction(this, new ActionEvent(hContact, action));
}
}
[Serializable]
public class ButtonInfo
{
private uint buttonID;
private string name;
private string command;
private string iconName;
private bool pressed;
private bool isPush;
private bool enabled;
public ButtonInfo()
{
}
public ButtonInfo(string name, string command, string iconName) : this(name, command, iconName, false, true)
{
}
public ButtonInfo(string name, string command, string iconName, bool isPush, bool enabled) : this()
{
this.name = name;
this.command = command;
this.iconName = iconName;
this.isPush = isPush;
buttonID = 0;
pressed = true;
this.enabled = enabled;
}
[XmlAttribute(AttributeName = "enabled")]
public bool Enabled
{
get { return enabled; }
set { enabled = value; }
}
[XmlIgnore]
public bool Pressed
{
get { return pressed; }
set { pressed = value; }
}
[XmlIgnore]
public bool IsPush
{
get { return isPush; }
set { isPush = value; }
}
[XmlIgnore] [NonSerialized] public IntPtr HIcon;
[XmlIgnore]
public uint ButtonID
{
get { return buttonID; }
set { buttonID = value; }
}
[XmlAttribute(AttributeName = "name")]
public string Name
{
get { return name; }
set { name = value; }
}
[XmlAttribute(AttributeName = "command")]
public string Command
{
get { return command; }
set { command = value; }
}
[XmlAttribute(AttributeName = "iconname")]
public string IconName
{
get { return iconName; }
set { iconName = value; }
}
public ButtonInfo Clone()
{
return new ButtonInfo(name, command, iconName, isPush, enabled);
}
}
}

206
Speak/Speak/Core/HTTP.cs Normal file
View File

@ -0,0 +1,206 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Net;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Windows.Forms;
using Speak.Properties;
namespace Speak.Core
{
internal class HTTP
{
private readonly Encoding cp1251;
private readonly Encoding utf;
private static readonly Encoding staticUtf = Encoding.UTF8;
private static string UserAgent = "xJuick v0.0.6a http://xa0c.net";
public HTTP()
{
cp1251 = Encoding.GetEncoding(1251);
utf = Encoding.UTF8;
}
public event EventHandler<ContentEventArgs> OnContentReady;
private void InvokeOnContentReady(ContentEventArgs e)
{
EventHandler<ContentEventArgs> onContentReadyHandler = OnContentReady;
if (onContentReadyHandler != null) onContentReadyHandler(this, e);
}
public void SendGetAsync(string url)
{
Thread thread = new Thread(SendGet);
thread.IsBackground = true;
thread.Start(url);
}
private void SendGet(object urlObj)
{
SendGet(urlObj.ToString());
}
public string SendGet(string url)
{
return SendGet(url, false);
}
private string SendGet(string url, bool async)
{
try
{
HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url);
request.UserAgent = UserAgent;
request.Timeout = 4000;
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
string result = ReadResponse(response);
if (async)
InvokeOnContentReady(new ContentEventArgs(result));
return result;
}
catch (Exception)
{
InvokeOnContentReady(null);
}
return String.Empty;
}
public static string StaticSendGet(string url)
{
try
{
HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(url);
request.UserAgent = UserAgent;
request.Timeout = 4000;
HttpWebResponse response = (HttpWebResponse)request.GetResponse();
return StaticReadResponse(response);
}
catch (Exception)
{
// nah
}
return String.Empty;
}
public Stream GetImage(string url)
{
return GetImage(url, true);
}
public Stream GetImage(string url, bool returnBlankAvatar)
{
try
{
WebRequest wreq = WebRequest.Create(url);
HttpWebResponse httpResponse = (HttpWebResponse)wreq.GetResponse();
if (httpResponse.ContentType != "text/html")
{
return httpResponse.GetResponseStream();
}
else
{
Match m = Regexps.Image.Match(ReadResponse(httpResponse));
if (!m.Success)
{
return null;
}
else
{
string imgUrl = m.Groups["image"].Value;
if (!imgUrl.StartsWith("http://"))
{
if (imgUrl.StartsWith("//"))
imgUrl = "http:" + imgUrl;
else
imgUrl = "http://" + imgUrl;
}
return GetImage(imgUrl, returnBlankAvatar);
}
}
}
catch (Exception)
{
MemoryStream stream = new MemoryStream();
if (returnBlankAvatar)
{
//Resources.avatar_notfound.Save(stream, ImageFormat.Png);
stream.Seek(0, SeekOrigin.Begin);
}
return stream;
}
}
private string ReadResponse(HttpWebResponse response)
{
string result = "";
Stream stream = response.GetResponseStream();
//StreamReader reader = new StreamReader(stream, response.CharacterSet.ToLower().IndexOf("utf") == -1 ? cp1251 : utf);
StreamReader reader = new StreamReader(stream, utf);
char[] chars = new Char[256];
int count = reader.Read(chars, 0, 256);
while (count > 0)
{
string str = new String(chars, 0, count);
result = result + str;
count = reader.Read(chars, 0, 256);
}
response.Close();
stream.Close();
reader.Close();
return result;
}
public static string StaticReadResponse(HttpWebResponse response)
{
string result = "";
Stream stream = response.GetResponseStream();
//StreamReader reader = new StreamReader(stream, response.CharacterSet.ToLower().IndexOf("utf") == -1 ? cp1251 : utf);
StreamReader reader = new StreamReader(stream, staticUtf);
char[] chars = new Char[256];
int count = reader.Read(chars, 0, 256);
while (count > 0)
{
string str = new String(chars, 0, count);
result = result + str;
count = reader.Read(chars, 0, 256);
}
response.Close();
stream.Close();
reader.Close();
return result;
}
}
public class ContentEventArgs : EventArgs
{
private string content;
public ContentEventArgs(string content)
{
this.content = content;
}
public string Content
{
get { return content; }
set { content = value; }
}
}
}

View File

@ -0,0 +1,15 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace Speak.Core
{
internal interface IMessageProcessor : IDisposable
{
void Update();
void ShowThreads();
void Avatars();
void SettingsChanged();
event EventHandler<ActionClickEvent> JuickClicked;
}
}

View File

@ -0,0 +1,96 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Net;
using System.Text;
using System.Windows.Forms;
using Speak.UI;
namespace Speak.Core
{
internal static class ImagePreview
{
private static PreviewForm pForm = new PreviewForm();
private static string[] imageTypes;
static ImagePreview()
{
imageTypes = new string[] { ".jpg", ".png", ".gif" };
}
public static bool IsImage(string url)
{
string ext = Path.GetExtension(url);
for (int i = 0, iCount = imageTypes.Length; i < iCount; i++)
{
if (imageTypes[i].Equals(ext, StringComparison.InvariantCultureIgnoreCase))
return true;
}
return false;
}
public static void Show(Int32 x, Int32 y, string url)
{
pForm.Left = x;
pForm.Top = y;
if (!pForm.Visible)
{
pForm.Show();
}
string pUrl = Settings.Instance.PreviewEngine.Url;
pForm.Url = !pUrl.Equals("{0}") ? String.Format(pUrl, System.Web.HttpUtility.UrlEncode(url)) : url;
}
public static void Hide()
{
if (pForm.Visible)
{
pForm.Hide();
}
}
}
[Serializable]
public class PreviewEngine
{
private string name;
private string url;
private bool enabled;
public PreviewEngine()
{
}
public PreviewEngine(string name, string url, bool enabled)
{
this.name = name;
this.url = url;
this.enabled = enabled;
}
public string Name
{
get { return name; }
set { name = value; }
}
public string Url
{
get { return url; }
set { url = value; }
}
public bool Enabled
{
get { return enabled; }
set { enabled = value; }
}
public PreviewEngine Clone()
{
return new PreviewEngine(name, url, enabled);
}
}
}

View File

@ -0,0 +1,134 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Xml.Serialization;
namespace Speak.Core
{
[Serializable]
public class LinkButton
{
private string action;
private string displayName;
private string iconName;
private bool autoSend;
private bool enabled;
private LinkDisplayType displayType;
public LinkButton()
{
}
public LinkButton(string action, string displayName, bool autoSend, LinkDisplayType displayType) : this (action, displayName, String.Empty, autoSend, displayType, true)
{
}
public LinkButton(string action, string displayName, string iconName, bool autoSend, LinkDisplayType displayType, bool enabled) : this()
{
this.action = action;
this.displayName = displayName;
this.autoSend = autoSend;
this.displayType = displayType;
this.iconName = iconName;
this.enabled = enabled;
}
[XmlAttribute(AttributeName = "enabled")]
public bool Enabled
{
get { return enabled; }
set { enabled = value; }
}
[XmlAttribute("action")]
public string Action
{
get { return action; }
set { action = value; }
}
[XmlAttribute("displayname")]
public string DisplayName
{
get { return displayName; }
set { displayName = value; }
}
[XmlAttribute("autosend")]
public bool AutoSend
{
get { return autoSend; }
set { autoSend = value; }
}
[XmlAttribute("displayon")]
public LinkDisplayType DisplayType
{
get { return displayType; }
set { displayType = value; }
}
[XmlAttribute("iconname")]
public string IconName
{
get { return iconName; }
set { iconName = value; }
}
public LinkButton Clone()
{
return new LinkButton(action, displayName, iconName, autoSend, displayType, enabled);
}
}
[Serializable]
public class SimpleWordAction
{
private string action;
private bool autosend;
public SimpleWordAction()
{
}
public SimpleWordAction(string action, bool autosend)
{
this.action = action;
this.autosend = autosend;
}
[XmlAttribute("action")]
public string Action
{
get { return action; }
set { action = value; }
}
[XmlAttribute("autosend")]
public bool Autosend
{
get { return autosend; }
set { autosend = value; }
}
}
public enum LinkDisplayType
{
Nicks,
Posts,
Comments,
Always,
Image
}
public enum ActionWordType
{
None,
URL,
Comments,
Post,
Nick,
Tag
}
}

View File

@ -0,0 +1,164 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Speak.Fork;
using Speak.Interop;
using Speak.Structs;
using Speak.Utils;
namespace Speak.Core
{
internal static class LogWindow
{
private static ISettingOwner ownerTabSRMM;
private static ISettingOwner ownerScriver;
private static ISettingOwner ownerHistoryPP;
private static bool isIEInstalled;
private static bool isHPPInstalled;
public static bool hppImitated;
public static string CurrentLogEngine;
public static Color SRMMBackColor;
public const string TabSRMMEngine = "tabSRMM";
public const string ScriverEngine = "Scriver";
public const string ScriverEnginePlus = "Scriver+";
public const string SRMMEngine = "SRMM";
public const string SRMMEnginePlus = "SRMM+";
static LogWindow()
{
ownerTabSRMM = new ContactManager.SettingOwner("Tab_SRMsg");
ownerScriver = new ContactManager.SettingOwner("SRMM");
ownerHistoryPP = new ContactManager.SettingOwner("HistoryPlusPlus");
isIEInstalled = ServiceManager.ServiceExists(API.MS_IEVIEW_WINDOW);
isHPPInstalled = ServiceManager.ServiceExists(API.MS_HPP_EG_WINDOW);
SRMMBackColor = Color.Empty;
CurrentLogEngine = Util.CurrentMessageEngine(); // tabSRMM, Scriver, SRMM
}
//public static IntPtr FindRealLogWindow(IntPtr mainHandle, LogHandler currentLog)
//{
// return FindRealLogWindow(mainHandle, currentLog, IntPtr.Zero);
//}
public static IntPtr FindRealLogWindow(IntPtr mainHandle, LogHandler currentLog, IntPtr hContact, out LogHandler contactLog)
{
string className = String.Empty;
if (hContact != IntPtr.Zero)
{
LogHandler forcedLog = GetForcedContactLogSettings(hContact);
if (forcedLog != LogHandler.Default)
{
switch (forcedLog)
{
case LogHandler.ForcedHPP:
if (isHPPInstalled)
currentLog = LogHandler.HistoryPP;
else
currentLog = LogHandler.Default;
break;
case LogHandler.ForcedIEView:
if (isIEInstalled)
{
if (!hppImitated)
currentLog = LogHandler.IEView;
else
currentLog = LogHandler.ImitatedHPP;
}
else
{
currentLog = LogHandler.Default;
}
break;
case LogHandler.ForcedDefault:
currentLog = LogHandler.Default;
break;
}
}
}
switch (currentLog)
{
case LogHandler.ImitatedHPP:
case LogHandler.HistoryPP:
className = "TExtHistoryGrid";
break;
case LogHandler.IEView:
className = "Internet Explorer_Server";
break;
case LogHandler.Default:
SRMMBackColor = ColorTranslator.FromWin32(Convert.ToInt32(ContactInfo.ReadSetting(IntPtr.Zero, "BkgColour", ownerScriver, DatabaseSettingType.UInt32)));
className = CurrentLogEngine.Equals("tabSRMM") || CurrentLogEngine.Equals("SRMM") ? "RichEdit20A" : "RichEdit20W";
break;
default:
throw new ArgumentOutOfRangeException("currentLog");
}
contactLog = currentLog;
IntPtr logPtr = !CurrentLogEngine.Equals(ScriverEnginePlus) && !CurrentLogEngine.Equals(SRMMEnginePlus) ? WinApi.GetLogWindow(mainHandle, className) : WinApi.GetLogWindowByStyles(mainHandle, className);
return logPtr;
}
public static LogHandler GetForcedContactLogSettings(IntPtr hContact)
{
LogHandler result = LogHandler.Default;
if (CurrentLogEngine.Equals("tabSRMM"))
{
byte hppForced = Convert.ToByte(ContactInfo.ReadSetting(hContact, "hpplog", ownerTabSRMM, DatabaseSettingType.Byte));
byte ieviewForced = Convert.ToByte(ContactInfo.ReadSetting(hContact, "ieview", ownerTabSRMM, DatabaseSettingType.Byte));
return (hppForced == 1 ? LogHandler.ForcedHPP : (ieviewForced == 1 ? LogHandler.ForcedIEView : ((ieviewForced == 255 && hppForced == 255) ? LogHandler.ForcedDefault : LogHandler.Default)));
}
return result;
}
public static LogHandler GetViewMode()
{
bool useIE = false;
bool useHPP = false;
hppImitated = Convert.ToBoolean(ContactInfo.ReadSetting(IntPtr.Zero, "IEViewAPI", ownerHistoryPP, DatabaseSettingType.Byte));
switch (CurrentLogEngine)
{
case TabSRMMEngine:
useHPP = Convert.ToBoolean(ContactInfo.ReadSetting(IntPtr.Zero, "default_hpp", ownerTabSRMM, DatabaseSettingType.Byte));
useIE = Convert.ToBoolean(ContactInfo.ReadSetting(IntPtr.Zero, "default_ieview", ownerTabSRMM, DatabaseSettingType.Byte));
break;
case ScriverEngine:
useIE = Convert.ToBoolean(ContactInfo.ReadSetting(IntPtr.Zero, "UseIEView", ownerScriver, DatabaseSettingType.Byte));
break;
case SRMMEngine:
return LogHandler.Default;
}
return (isIEInstalled && useIE && !hppImitated)
? LogHandler.IEView
//: ((isHPPInstalled && (useHPP || (useIE && hppImitated))) ? LogHandler.HistoryPP : LogHandler.Default);
: ((isHPPInstalled && useHPP && !useIE)
? LogHandler.HistoryPP
: ((isHPPInstalled && useIE && hppImitated) ? LogHandler.ImitatedHPP : LogHandler.Default));
}
}
public enum LogHandler
{
Default,
IEView,
HistoryPP,
ImitatedHPP,
ForcedHPP,
ForcedIEView,
ForcedDefault
}
}

View File

@ -0,0 +1,194 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using Virtuoso.Miranda.Plugins.Helpers;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Structs;
using Speak.Utils;
namespace Speak.Core
{
internal static class MirandaDB
{
private static Type dbeType = typeof(DBEVENTINFO);
private static int dbeTypeSize = Marshal.SizeOf(dbeType);
public static DatabaseEventInfoEx GetEvent(IntPtr eventHandler)
{
if (eventHandler == IntPtr.Zero)
return null;
IntPtr hStruct = IntPtr.Zero;
DatabaseEventInfoEx result = null;
InteropBuffer buffer = null;
try
{
int blobSize = MirandaContext.Current.CallService(API.MS_DB_EVENT_GETBLOBSIZE, eventHandler, IntPtr.Zero);
if (blobSize == -1)
{
throw new ArgumentException();
}
buffer = InteropBufferPool.AcquireBuffer(blobSize);
buffer.Lock();
DBEVENTINFO dbev = new DBEVENTINFO(blobSize, buffer.IntPtr);
hStruct = Marshal.AllocHGlobal(dbeTypeSize);
Marshal.StructureToPtr(dbev, hStruct, false);
MirandaContext.Current.CallService(API.MS_DB_EVENT_GET, eventHandler, hStruct);
dbev = (DBEVENTINFO)Marshal.PtrToStructure(hStruct, dbeType);
result = new DatabaseEventInfoEx(dbev);
}
finally
{
if (buffer != null)
buffer.Unlock();
if (hStruct != IntPtr.Zero)
Marshal.FreeHGlobal(hStruct);
}
return result;
}
public static void DirectCopyHistory(IntPtr fromContact, IntPtr toContact, Regex condition)
{
if (fromContact == IntPtr.Zero || toContact == IntPtr.Zero)
return;
IntPtr hStruct = IntPtr.Zero;
InteropBuffer buffer = null;
IEnumerable<IntPtr> source = MirandaContext.Current.MirandaDatabase.GetEventHandles(fromContact);
List<IntPtr> deleteList = new List<IntPtr>();
foreach (IntPtr hist in source)
{
int blobSize = MirandaContext.Current.CallService(API.MS_DB_EVENT_GETBLOBSIZE, hist, IntPtr.Zero);
if (blobSize == -1)
{
throw new ArgumentException();
}
buffer = InteropBufferPool.AcquireBuffer(blobSize);
buffer.Lock();
DBEVENTINFO dbev = new DBEVENTINFO(blobSize, buffer.IntPtr);
hStruct = Marshal.AllocHGlobal(dbeTypeSize);
Marshal.StructureToPtr(dbev, hStruct, false);
MirandaContext.Current.CallService(API.MS_DB_EVENT_GET, hist, hStruct);
dbev = (DBEVENTINFO)Marshal.PtrToStructure(hStruct, dbeType);
if (condition != null)
{
if (dbev.EventType != (ushort)DatabaseEventType.Message)
continue;
DatabaseEventInfoEx dbevEx = new DatabaseEventInfoEx(dbev);
if (!condition.Match(dbevEx.Data).Success)
{
buffer.Unlock();
continue;
}
}
dbev.Flags = dbev.Flags & ~(uint)DatabaseEventProperties.First;
hStruct = Marshal.AllocHGlobal(dbeTypeSize);
Marshal.StructureToPtr(dbev, hStruct, false);
MirandaContext.Current.CallService(API.MS_DB_EVENT_ADD, toContact, hStruct);
deleteList.Add(hist);
buffer.Unlock();
Marshal.FreeHGlobal(hStruct);
}
for (int i = 0, iCount = deleteList.Count; i < iCount; i++)
{
DeleteEvent(fromContact, deleteList[i]);
}
}
public static void DeleteEvent(IntPtr hContact, IntPtr histHandle)
{
MirandaContext.Current.CallService(API.MS_DB_EVENT_DELETE, hContact, histHandle);
}
public static void AddEvent(IntPtr toContact, string data, ISettingOwner owner, DatabaseEventType type, DatabaseEventProperties flags, DateTime timestamp)
{
IntPtr hStruct = IntPtr.Zero;
IntPtr pBlob = IntPtr.Zero;
try
{
int blobSize;
pBlob = Util.GetStringPtr(data, out blobSize);
DBEVENTINFO dbev = new DBEVENTINFO(blobSize, pBlob);
dbev.EventType = (ushort)DatabaseEventType.Message;
dbev.Flags = (uint)flags | MainConstants.DBEF_UTF;
dbev.Module = Translate.ToHandle(owner.Name, StringEncoding.Ansi).IntPtr;
dbev.Timestamp = Utilities.GetTimestamp(timestamp);
hStruct = Marshal.AllocHGlobal(dbeTypeSize);
Marshal.StructureToPtr(dbev, hStruct, false);
MirandaContext.Current.CallService(API.MS_DB_EVENT_ADD, toContact, hStruct);
}
finally
{
if (hStruct != IntPtr.Zero)
Marshal.FreeHGlobal(hStruct);
if (pBlob != IntPtr.Zero)
Marshal.FreeHGlobal(pBlob);
}
}
}
internal class DatabaseEventInfoEx
{
private string data;
private DatabaseEventType eventType;
private DatabaseEventProperties flags;
private DateTime timeStamp;
private Protocol ownerModule;
public DatabaseEventInfoEx(DBEVENTINFO unmanagedDBEvent)
{
ownerModule = Protocol.UnknownProtocol;
if (unmanagedDBEvent.Module != IntPtr.Zero)
{
if(!MirandaContext.Current.Protocols.TryGetValue(Translate.ToString(unmanagedDBEvent.Module, StringEncoding.Ansi), out ownerModule))
ownerModule = Protocol.UnknownProtocol;
}
flags = (DatabaseEventProperties)unmanagedDBEvent.Flags;
eventType = (DatabaseEventType)((short)unmanagedDBEvent.EventType);
data = Util.GetNormalRussian(unmanagedDBEvent.BlobPtr, unmanagedDBEvent.BlobSize);
timeStamp = Util.GetDateTime(unmanagedDBEvent.Timestamp);
}
public string Data
{
get { return data; }
}
public DatabaseEventType EventType
{
get { return eventType; }
}
public DatabaseEventProperties Flags
{
get { return flags; }
}
public DateTime TimeStamp
{
get { return timeStamp; }
}
public Protocol OwnerModule
{
get { return ownerModule; }
}
}
}

107
Speak/Speak/Core/Regexps.cs Normal file
View File

@ -0,0 +1,107 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
namespace Speak.Core
{
internal static class Regexps
{
public static Regex _NumRegEx = new Regex(
"(?<full>(?<post>\\#\\d+)(?<cmnt>/\\d+)?)",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex UID = new Regex(
"/(?<uid>\\d+)\\.png",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex GetHistoryRegEx(string postNumber)
{
return new Regex(
String.Format("\\B(?<post>{0})", postNumber.Replace("#", "\\#")),
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
}
public static Regex TopNameRegEx = new Regex(
"\\B@(?<name>\\w+[-_\\.\\w]*\\w+)\\:",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex _NameRegEx = new Regex(
"(?<name>\\B@\\w+[-_\\.\\w]*\\w+)(?<isFirst>\\:{1})?",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex JidRegEx = new Regex(
"(?<name>\\B@[\\w-_\\.]+\\@[\\w-_\\.]+)",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex Russian = new Regex(
"[А-Я]+",
RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex Image = new Regex(
"<img.+?src=\"(?<image>[^\"]*)\"",
RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex PureReplyRegEx = new Regex(
"\\B(?<full>\\#(?<post>\\d+)(?:/(?<cmnt>\\d+))?)",
RegexOptions.IgnoreCase
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public static Regex ReplyRegEx = new Regex(
"(?<full>\\#(?<post>\\d+)(?:/(?<cmnt>\\d+)){1})\\ http://juick." +
"com/(?(post)\\k<post>)(?(cmnt)\\#\\k<cmnt>)", // do I need to add '$' to the end?
RegexOptions.IgnoreCase
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
}
}

View File

@ -0,0 +1,351 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Binary;
using System.Windows.Forms;
using System.Xml.Serialization;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Speak.Fork;
using Speak.Sites;
namespace Speak.Core
{
[Serializable]
public class Settings
{
private static string filepath = "";
public static string xJuickDataFolder = "";
public static string xJuickAvatarsFolder = "";
private static Settings instance;
private bool autoFork;
private bool fastIEView;
private bool showAvatars;
private bool showContextAvatars;
private string jabberProtocolName;
public static bool SomeEventsDoubled = LogWindow.CurrentLogEngine.Equals("tabSRMM");
public static readonly string ModuleName = "xJuick";
public static readonly string IcoLibPath = "TabSRMM/Toolbar/" + ModuleName;
public static readonly string DefaultProtocolName = "yours@jabber.protocol.name";
private static ContactManager.SettingOwner owner = new ContactManager.SettingOwner(ModuleName);
public static LogHandler CurrentLog = LogHandler.Default;
private SimpleWordAction srmmNickAction;
private SimpleWordAction srmmNumberAction;
private PreviewEngine currenPreview;
private ISite[] sites;
private ButtonInfo[] buttons;
private LinkButton[] srmmLinkButtons;
private PreviewEngine[] previewEngines;
private string[] activeContacts;
static Settings()
{
InitDirectories(Path.GetDirectoryName(Application.ExecutablePath));
}
public static void InitDirectories(string basePath)
{
try
{
xJuickDataFolder = Path.Combine(Path.Combine(basePath, "plugins"), "xJuick");
xJuickAvatarsFolder = Path.Combine(xJuickDataFolder, "Avatars");
if (!Directory.Exists(xJuickDataFolder))
Directory.CreateDirectory(xJuickDataFolder);
if (!Directory.Exists(xJuickAvatarsFolder))
Directory.CreateDirectory(xJuickAvatarsFolder);
filepath = Path.Combine(xJuickDataFolder, "config.xml");
}
catch
{
// eat this! >:)
}
}
[XmlIgnore]
public static Settings Instance
{
get
{
if (instance == null)
{
try
{
Load();
}
catch
{
instance = new Settings();
}
Save();
}
return instance;
}
}
public static void Reload()
{
instance = null;
}
private static void Load()
{
//LoadXML();
bool useXML = File.Exists(filepath);
if (useXML)
{
LoadXML();
}
else
{
IFormatter bs = new BinaryFormatter();
using (MemoryStream ms = new MemoryStream((byte[])ContactInfo.ReadSetting(IntPtr.Zero, "Settings", owner, DatabaseSettingType.Blob)))
{
instance = (Settings)bs.Deserialize(ms);
if (instance.PreviewEngines == null)
{
instance.PreviewEngines = DefaultEngines();
}
if (instance.Sites == null)
{
instance.Sites = GetSites();
}
}
}
}
private static void LoadXML()
{
using (FileStream fs = new FileStream(filepath, FileMode.Open))
{
XmlSerializer xs = new XmlSerializer(typeof(Settings));
instance = (Settings)xs.Deserialize(fs) ?? new Settings();
}
}
public static void Save()
{
bool useXML = File.Exists(filepath);
try
{
if (useXML)
{
SaveXML();
}
else
{
ContactInfo ci = ContactInfo.FromHandle(IntPtr.Zero);
IFormatter bs = new BinaryFormatter();
using (MemoryStream ms = new MemoryStream())
{
bs.Serialize(ms, instance);
byte[] data = new byte[ms.Length];
ms.Position = 0;
ms.Read(data, 0, (int)ms.Length);
ci.WriteSettingAsBlob("Settings", owner, data);
}
}
}
catch (Exception)
{
throw;
}
}
public static void SaveXML()
{
using (FileStream fs = new FileStream(filepath, FileMode.Create))
{
XmlSerializer xs = new XmlSerializer(typeof(Settings));
xs.Serialize(fs, instance);
}
}
public Settings()
{
List<ButtonInfo> buttons = new List<ButtonInfo>();
buttons.Add(new ButtonInfo("10 последних сообщений", "#+", ModuleName + "_GetLast"));
/*
buttons.Add(new ButtonInfo("10 горячих сообщений", "#", ModuleName + "_GetTop"));
buttons.Add(new ButtonInfo("10 популярных тегов", "*", ModuleName + "_GetTopTags"));
buttons.Add(new ButtonInfo("10 популярных пользователей", "@", ModuleName + "_GetTopUsers"));
buttons.Add(new ButtonInfo("Ваши подписки", "S", ModuleName + "_GetSubscriptions"));
*/
buttons.Add(new ButtonInfo("Ссылка для логина", "LOGIN", ModuleName + "_GetLogin"));
this.buttons = buttons.ToArray();
List<LinkButton> linkButtons = new List<LinkButton>();
linkButtons.Add(new LinkButton("%NUMBER%", "Прочитать", ModuleName + "_Magnifier", true, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("xJuick://Fork/%NUMBER%", "Отдельное окно", ModuleName + "_ForkSmall", true, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("%NUMBER%+", "Много прочитать", ModuleName + "_Plus", true, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("S %NUMBER%", "Хочу следить", ModuleName + "_Tick", true, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("U %NUMBER%", "Не хочу следить", ModuleName + "_Minus", true, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("! %NUMBER%", "SPAM it", ModuleName + "_Exclamation", false, LinkDisplayType.Posts, true));
linkButtons.Add(new LinkButton("%NUMBER%", "Перечитать пост", ModuleName + "_Magnifier", true, LinkDisplayType.Comments, true));
linkButtons.Add(new LinkButton("xJuick://Fork/%NUMBER%", "Отдельное окно", ModuleName + "_ForkSmall", true, LinkDisplayType.Comments, true));
linkButtons.Add(new LinkButton("U %NUMBER%", "Задолбали комменты", ModuleName + "_Minus", true, LinkDisplayType.Comments, true));
linkButtons.Add(new LinkButton("D %COMMENT%", "Удалить", ModuleName + "_Cross", false, LinkDisplayType.Comments, true));
linkButtons.Add(new LinkButton("%NICK%", "Инфо", ModuleName + "_Magnifier", true, LinkDisplayType.Nicks, true));
linkButtons.Add(new LinkButton("%NICK%+", "10 постов", ModuleName + "_Plus", true, LinkDisplayType.Nicks, true));
linkButtons.Add(new LinkButton("PM %NICK% ", "Приват", ModuleName + "_Ballon", false, LinkDisplayType.Nicks, true));
linkButtons.Add(new LinkButton("S %NICK%", "Хочу следить", ModuleName + "_Tick", true, LinkDisplayType.Nicks, true));
linkButtons.Add(new LinkButton("U %NICK%", "Не хочу следить", ModuleName + "_Minus", true, LinkDisplayType.Nicks, true));
linkButtons.Add(new LinkButton("BL %NICK%", "Занести в блэклист", ModuleName + "_BlackUser", false, LinkDisplayType.Nicks, true));
this.srmmLinkButtons = linkButtons.ToArray();
PreviewEngines = DefaultEngines();
jabberProtocolName = "yours@jabber.protocol.name";
activeContacts = new string[0];
this.sites = GetSites();
autoFork = false;
fastIEView = true;
showAvatars = true;
showContextAvatars = true;
srmmNickAction = new SimpleWordAction("%NICK% ", false);
srmmNumberAction = new SimpleWordAction("%NUMBER% ", false);
}
private static ISite[] GetSites()
{
List<ISite> sites = new List<ISite>();
foreach (KeyValuePair<string, ISite> site in SitesManager.Sites)
{
sites.Add(site.Value);
}
return sites.ToArray();
}
private static PreviewEngine[] DefaultEngines()
{
List<PreviewEngine> engines = new List<PreviewEngine>();
engines.Add(new PreviewEngine("m-software.de", "http://www.m-software.de/screenshot/Screenshot.png?url={0}&delay=10&type=jpg&scale=3", true));
engines.Add(new PreviewEngine("images.websnapr.com", "http://images.websnapr.com/?url={0}&size=s", false));
return engines.ToArray();
}
[XmlArrayItem("JID")]
public string[] ActiveContacts
{
get { return activeContacts; }
set { activeContacts = value; }
}
public ISite[] Sites
{
get { return sites; }
set { sites = value; }
}
public string JabberProtocolName
{
get { return jabberProtocolName; }
set { jabberProtocolName = value; }
}
public ButtonInfo[] Buttons
{
get { return buttons; }
set { buttons = value; }
}
public bool AutoFork
{
get { return autoFork; }
set { autoFork = value; }
}
public bool ShowAvatars
{
get { return showAvatars; }
set { showAvatars = value; }
}
public bool ShowContextAvatars
{
get { return showContextAvatars; }
set { showContextAvatars = value; }
}
public bool FastIEView
{
get { return fastIEView; }
set { fastIEView = value; }
}
public LinkButton[] SRMMLinkButtons
{
get { return srmmLinkButtons; }
set { srmmLinkButtons = value; }
}
[XmlIgnore]
public bool ShowPreview
{
get { return currenPreview != null; }
set { }
}
[XmlIgnore]
public PreviewEngine PreviewEngine
{
get { return currenPreview; }
set { }
}
public PreviewEngine[] PreviewEngines
{
get { return previewEngines; }
set
{
previewEngines = value;
for (int i = 0, iCount = previewEngines.Length; i < iCount; i++)
{
if (previewEngines[i].Enabled)
{
currenPreview = previewEngines[i];
return;
}
}
currenPreview = null;
}
}
public SimpleWordAction SRMMNickAction
{
get { return srmmNickAction; }
set { srmmNickAction = value; }
}
public SimpleWordAction SRMMNumberAction
{
get { return srmmNumberAction; }
set { srmmNumberAction = value; }
}
public static void ResetToDefault()
{
instance = new Settings();
}
}
}

View File

@ -0,0 +1,101 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Speak.Core;
using Speak.HPP;
using Speak.Interop;
using Speak.RichEdit;
using Speak.Sites;
namespace Speak.Fork
{
internal class ContactContainer : IDisposable
{
private ContactManager parent;
private ContactInfo contact;
private IMessageProcessor processor;
public ContactContainer(ContactManager parent, ContactInfo contact)
{
this.parent = parent;
this.contact = contact;
processor = null;
}
public ContactInfo Contact
{
get { return contact; }
}
internal IMessageProcessor Processor
{
get { return processor; }
}
public void UpdateProcessor()
{
if (processor != null)
processor.Update();
}
public void InitMessageProcessor(ISite site, IntPtr hContact, IntPtr hWnd)
{
if (processor == null)
{
LogHandler currenLog = Settings.CurrentLog;
IntPtr logHandle = currenLog != LogHandler.ImitatedHPP ? LogWindow.FindRealLogWindow(hWnd, currenLog, hContact, out currenLog) : IntPtr.Zero;
if (logHandle == IntPtr.Zero && currenLog != LogHandler.ImitatedHPP)
{
MessageBox.Show(
"Cant find LOG window of '" + LogWindow.CurrentLogEngine + "'." + Environment.NewLine +
"Links highlighting will be disabled",
"[xJuick] InitMessageProcessor() error",
MessageBoxButtons.OK,
MessageBoxIcon.Error);
return;
}
switch (currenLog)
{
case LogHandler.Default:
processor = new RichEditHandler(site, logHandle);
break;
case LogHandler.IEView:
processor = new IEHandler(site, logHandle);
break;
case LogHandler.HistoryPP:
processor = new HistoryppHandler(site, logHandle, false);
break;
case LogHandler.ImitatedHPP:
processor = new HistoryppHandler(site, hWnd, true);
break;
}
processor.JuickClicked += processor_JuickClicked;
}
}
private void processor_JuickClicked(object sender, ActionClickEvent e)
{
parent.OnJuickClicked(this, e);
}
public void Close()
{
if (processor != null)
{
processor.JuickClicked -= processor_JuickClicked;
processor = null;
}
}
public void Dispose()
{
Close();
}
}
}

View File

@ -0,0 +1,636 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Windows.Forms;
using Virtuoso.Miranda.Plugins.Helpers;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Core;
using Speak.HPP;
using Speak.RichEdit;
using Speak.Sites;
using Speak.Structs;
using Speak.UI;
using Speak.Utils;
namespace Speak.Fork
{
class ContactManager : IDisposable
{
internal class SettingOwner : ISettingOwner
{
private string name;
public SettingOwner(string name)
{
this.name = name;
}
public string Name
{
get { return name; }
set { name = value; }
}
}
private string ownerProtocol;
//private ContactContainer juickContact;
private List<ContactContainer> siteContacts;
// todo: FIX IT!!!111
private const string namePrefix = "[xJuick] ";
private const string xJuickSiteField = "Site";
private List<ContactContainer> forkContacts;
private SettingOwner pOwner;
private SettingOwner mpOwner;
private SettingOwner clOwner;
private SettingOwner sOwner;
private IntPtr rootName;
private bool addAsTemporary;
private StatusModes mode;
private Dictionary<string, ISite> additionalContacts;
public ContactManager(IntPtr rootName, ISite[] currentSites, string ownerProtocol)
{
siteContacts = new List<ContactContainer>();
this.rootName = rootName;
mode = StatusModes.OnThePhone;
additionalContacts = new Dictionary<string, ISite>();
forkContacts = new List<ContactContainer>();
pOwner = new SettingOwner("Protocol");
mpOwner = new SettingOwner(ownerProtocol);
clOwner = new SettingOwner("CList");
sOwner = new SettingOwner("xJuickSite");
List<string> mainContacts = new List<string>();
for (int i = 0, iCount = currentSites.Length; i < iCount; i++)
{
mainContacts.Add(currentSites[i].MainContact);
ISite site = currentSites[i];
for (int j = 0, jCount = currentSites[i].AdditionalContacts.Length; j < jCount; j++)
{
additionalContacts[currentSites[i].AdditionalContacts[j]] = site;
}
}
if (!FillContactList(mainContacts, ownerProtocol))
throw new Exception("No protocols found");
addAsTemporary = false;
MirandaContext.Current.MirandaDatabase.ContactDeleted += MirandaDatabase_ContactDeleted;
}
private bool MirandaDatabase_ContactDeleted(object sender, MirandaContactEventArgs e)
{
int deleteIndex = -1;
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == e.ContactInfo.MirandaHandle)
{
if (IsAdditional(forkContacts[i].Contact.UniqueID.ToString()))
return false;
deleteIndex = i;
break;
}
}
if (deleteIndex != -1)
{
CopyHistory(e.ContactInfo.MirandaHandle, GetMainContactHandle(e.ContactInfo.MirandaHandle), null);
forkContacts.RemoveAt(deleteIndex);
}
return false;
}
public bool IsMainContact(IntPtr hMainContact)
{
return GetMainContactContainer(hMainContact) != null;
}
private ContactContainer GetMainContactContainer(IntPtr hMainContact)
{
for (int i = 0, iCount = siteContacts.Count; i < iCount; i++)
{
if (hMainContact == siteContacts[i].Contact.MirandaHandle)
return siteContacts[i];
}
return null;
}
public IntPtr GetMainContactHandle(IntPtr childHContact)
{
ISite site = SitesManager.GetContactSite(childHContact);
if (site == null)
return IntPtr.Zero;
for (int i = 0, iCount = siteContacts.Count; i < iCount; i++)
{
if (siteContacts[i].Contact.UniqueID.ToString() == site.MainContact)
{
return siteContacts[i].Contact.MirandaHandle;
}
}
return IntPtr.Zero; // yeah. maybe will implement multi-juick later :)
}
private bool FillContactList(List<string> mainContacts, string ownerProtocol)
{
// quiet unload
if (Util.EnumProtocols().Count == 0)
return false;
Dictionary<string, Dictionary<string, ContactInfo>> protocols = new Dictionary<string, Dictionary<string, ContactInfo>>();
int contactsCount = 0;
IEnumerable<IntPtr> hContacts = MirandaContext.Current.MirandaDatabase.GetContactHandles();
foreach (IntPtr hContact in hContacts)
{
contactsCount++;
ContactInfo ci = ContactInfo.FromHandle(hContact);
if (ci == null || ci.UniqueID == null)
continue;
string jid = ci.UniqueID.ToString();
bool isAdditional = IsAdditional(jid);
if (jid.StartsWith(namePrefix) || isAdditional)
{
if (!IsOnContact(ci.MirandaHandle))
AddToContact(ci.MirandaHandle);
forkContacts.Add(new ContactContainer(this, ci));
string contactSite = (string)ci.ReadSetting(xJuickSiteField, sOwner, DatabaseSettingType.AsciiString);
if (!String.IsNullOrEmpty(contactSite))
{
ISite contactSiteObject = SitesManager.GetContactSite(contactSite, true);
if (contactSiteObject != null)
SitesManager.SitesInfo[ci.MirandaHandle] = contactSiteObject;
}
else if (isAdditional)
{
SitesManager.SitesInfo[ci.MirandaHandle] = additionalContacts[jid];
}
}
else if (mainContacts.IndexOf(jid) != -1)
{
ISite site = SitesManager.GetContactSite(jid, false);
if (site != null)
SitesManager.SitesInfo[hContact] = site;
string ownerProto = (string)ci.ReadSetting("p", pOwner, DatabaseSettingType.AsciiString);
if (!protocols.ContainsKey(jid))
protocols[jid] = new Dictionary<string, ContactInfo>();
protocols[jid].Add(ownerProto, ci);
}
}
if (contactsCount == 0)
return false;
bool found = false;
foreach (KeyValuePair<string, Dictionary<string, ContactInfo>> jp in protocols)
{
foreach (KeyValuePair<string, ContactInfo> p in jp.Value)
{
if (p.Key.Equals(ownerProtocol, StringComparison.InvariantCultureIgnoreCase))
{
this.ownerProtocol = ownerProtocol;
ContactInfo ci = jp.Value[this.ownerProtocol];
ContactContainer mainContact = new ContactContainer(this, ci);
siteContacts.Add(mainContact);
if (!IsOnContact(ci.MirandaHandle))
AddToContact(ci.MirandaHandle);
found = true;
}
}
}
if (found)
return true;
if (String.IsNullOrEmpty(this.ownerProtocol))
{
if (protocols.Count == 0)
{
System.Windows.Forms.MessageBox.Show("Found ZERO protocols with main accounts (check options)" + Environment.NewLine +
"xJuick plugin will be unloaded now.", "[xJuick] Jabber Protocol error", MessageBoxButtons.OK, MessageBoxIcon.Error);
return false;
}
/*ProtocolSelect ps = new ProtocolSelect(protocols);
if (ps.ShowDialog() != DialogResult.OK)
return false;
if (String.IsNullOrEmpty(ps.ResultProtocol) || ps.ResultContactInfo == null)
return false;
this.ownerProtocol = ps.ResultProtocol;
ContactInfo ci = ps.ResultContactInfo;
ContactContainer mainContact = new ContactContainer(this, ci);
siteContacts.Add(mainContact);
if (!IsOnContact(ci.MirandaHandle))
AddToContact(ci.MirandaHandle);
Settings.Instance.JabberProtocolName = this.ownerProtocol;
Settings.Save();*/
return true;
}
return false;
}
public bool IsForked(IntPtr hContact)
{
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == hContact)
{
return true;
}
}
return false;
}
public bool IsAdditional(string UID)
{
return additionalContacts.ContainsKey(UID);
}
public ContactInfo GetContactInfo(string mainContact, string name)
{
ContactInfo result = null;
string sname = namePrefix + name;
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact != null && forkContacts[i].Contact.UniqueID != null)
{
if (forkContacts[i].Contact.UniqueID.ToString().Equals(sname, StringComparison.InvariantCultureIgnoreCase))
{
result = forkContacts[i].Contact;
break;
}
}
else
{
MessageBox.Show("GetContactInfo() -> Null ID [???]");
}
}
if (result == null && Settings.Instance.AutoFork)
{
result = MakeFork(mainContact, name);
}
else if (result != null)
ChangeStatus(result, mode);
return result;
}
private ContactInfo MakeFork(string mainContact, string name)
{
ContactInfo result = AddNewContact(mainContact, name);
if (result != null)
{
SitesManager.SitesInfo[result.MirandaHandle] = SitesManager.GetContactSite(mainContact, false);
if (!IsOnContact(result.MirandaHandle))
AddToContact(result.MirandaHandle);
forkContacts.Add(new ContactContainer(this, result));
ChangeStatus(result, mode);
}
return result;
}
public void CopyHistory(IntPtr fromContact, IntPtr toContact, Regex condition)
{
MirandaDB.DirectCopyHistory(fromContact, toContact, condition);
}
public void SettingsChanged()
{
for (int i = 0, iCount = siteContacts.Count; i < iCount; i++)
{
if (siteContacts[i].Processor != null)
siteContacts[i].Processor.SettingsChanged();
}
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Processor != null)
{
forkContacts[i].Processor.SettingsChanged();
break;
}
}
}
public void OpenChat(IntPtr hContact, IntPtr hWnd)
{
ContactContainer contact = GetMainContactContainer(hContact);
ISite site = SitesManager.GetContactSite(hContact);
if (site == null)
{
if (contact != null)
{
string cintactID = contact.Contact.UniqueID.ToString();
site = SitesManager.GetContactSite(cintactID, true);
if (site != null)
SitesManager.SitesInfo[hContact] = site;
}
else
{
ContactInfo ci = ContactInfo.FromHandle(hContact);
string contactSite = (string)ci.ReadSetting(xJuickSiteField, pOwner, DatabaseSettingType.AsciiString);
if (!String.IsNullOrEmpty(contactSite))
{
site = SitesManager.GetContactSite(contactSite, false);
}
else if (IsAdditional(ci.UniqueID.ToString()))
{
site = additionalContacts[ci.UniqueID.ToString()];
}
}
if (site == null)
return;
}
if (contact != null)
{
contact.InitMessageProcessor(site, hContact, hWnd);
return;
}
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == hContact)
{
forkContacts[i].InitMessageProcessor(site, hContact, hWnd);
break;
}
}
}
public void CloseChat(IntPtr hContact)
{
//SitesManager.SitesInfo.Remove(hContact);
ContactContainer contact = GetMainContactContainer(hContact);
if (contact != null)
{
contact.Close();
return;
}
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == hContact)
{
forkContacts[i].Close();
break;
}
}
}
public void ProcessHistoryItem(IntPtr smallHandle, ItemRenderDetails ird)
{
ContactContainer item = null;
ContactContainer contact = GetMainContactContainer(ird.hContact);
if (contact != null)
{
item = contact;
}
else
{
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == ird.hContact)
{
item = forkContacts[i];
break;
}
}
}
if (item == null)
return;
if (item.Processor is HistoryppHandler)
((HistoryppHandler)item.Processor).ProcessHistoryItem(smallHandle, ird);
}
public void Avatars()
{
for (int i = 0, iCount = siteContacts.Count; i < iCount; i++)
{
if (siteContacts[i].Processor != null)
siteContacts[i].Processor.Avatars();
}
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Processor != null)
forkContacts[i].Processor.Avatars();
}
}
public void Update(IntPtr hContact)
{
ContactContainer contact = GetMainContactContainer(hContact);
if (contact != null)
{
contact.UpdateProcessor();
return;
}
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
if (forkContacts[i].Contact.MirandaHandle == hContact)
{
forkContacts[i].UpdateProcessor();
break;
}
}
}
private ContactInfo AddNewContact(string mainContact, string uid)
{
if (String.IsNullOrEmpty(ownerProtocol))
return null;
try
{
ContactInfo ci = ContactInfo.CreateContact();
ci.WriteSetting("FullName", mpOwner, uid, DatabaseSettingType.AsciiString);
ci.WriteSetting("jid", mpOwner, namePrefix + uid, DatabaseSettingType.AsciiString);
ci.WriteSetting("p", pOwner, ownerProtocol, DatabaseSettingType.AsciiString);
ci.WriteSetting(xJuickSiteField, sOwner, mainContact, DatabaseSettingType.AsciiString);
if (addAsTemporary)
{
ci.WriteSetting("NotOnList", clOwner, 1, DatabaseSettingType.Byte);
ci.WriteSetting("Delete", clOwner, 1, DatabaseSettingType.Byte);
}
return ci;
}
catch (Exception ex)
{
/*QuickDebug qd = new QuickDebug(ex.Message + Environment.NewLine + ex.StackTrace);
qd.ShowDialog();*/
MessageBox.Show(ex.Message + Environment.NewLine + ex.StackTrace);
return null;
}
}
public ContactInfo CheckForHandle(IntPtr hContact, string message)
{
Match m = Regexps.ReplyRegEx.Match(message);
if (m.Success)
{
string mainContact = SitesManager.GetContactSite(hContact).MainContact;
return GetContactInfo(mainContact, "#" + m.Groups["post"].Value);
}
return null;
}
public ContactInfo CheckForHandlePure(IntPtr hContact, string message)
{
Match m = Regexps.PureReplyRegEx.Match(message);
if (m.Success)
{
ISite site = SitesManager.GetContactSite(hContact);
string mainContact = site == null ? String.Empty : site.MainContact;
return GetContactInfo(mainContact, "#" + m.Groups["post"].Value);
}
return null;
}
public void ChangeForkState(IntPtr hContact, string name)
{
string mainContact = SitesManager.GetContactSite(hContact).MainContact;
ContactInfo result = GetContactInfo(mainContact, name);
if (result == null)
{
result = MakeFork(mainContact, name);
if (result != null)
CopyHistory(GetMainContactHandle(hContact), result.MirandaHandle, Regexps.GetHistoryRegEx(name));
}
else
{
result.OpenMessageWindow();
}
}
private void AddToContact(IntPtr hContact)
{
MirandaContext.Current.CallService(API.MS_PROTO_ADDTOCONTACT, hContact, rootName);
}
private bool IsOnContact(IntPtr hContact)
{
return Convert.ToBoolean(MirandaContext.Current.CallService(API.MS_PROTO_ISPROTOONCONTACT, hContact, rootName));
}
private void ChangeStatus(ContactInfo ci, StatusModes status)
{
try
{
ci.WriteSetting("Status", mpOwner, (UInt16)status, DatabaseSettingType.UInt16);
}
catch { }
}
public void ClearContacts()
{
ContactContainer[] fk = forkContacts.ToArray();
for (int i = 0, iCount = fk.Length; i < iCount; i++)
{
if (!IsAdditional(fk[i].Contact.UniqueID.ToString()))
{
fk[i].Contact.Delete();
}
}
forkContacts.Clear();
forkContacts = new List<ContactContainer>();
}
public void OnJuickClicked(object sender, ActionClickEvent e)
{
IntPtr hContact = ((ContactContainer) sender).Contact.MirandaHandle;
if (!e.AutoSend)
{
UnmanagedStringHandle str = new UnmanagedStringHandle(e.Action, StringEncoding.Ansi);
MirandaContext.Current.CallService(API.MS_MSG_SENDMESSAGE, hContact, str.IntPtr);
str.Free();
}
else
{
if (e.Action.StartsWith("http://", StringComparison.InvariantCultureIgnoreCase))
{
Util.OpenURL(e.Action);
}
else if (e.Action.StartsWith("xJuick://", StringComparison.InvariantCultureIgnoreCase))
{
InvokeOnAction(hContact, e.Action.Substring(9).ToLower());
}
else
{
CSSData css = new CSSData();
css.hContact = hContact; //juickContact.Contact.MirandaHandle;
css.szProtoService = API.PSS_MESSAGE;
css.wParam = IntPtr.Zero;
css.lParam = new UnmanagedStringHandle(e.Action, StringEncoding.Ansi).IntPtr;
IntPtr cmdPtr = Marshal.AllocHGlobal(Marshal.SizeOf(css));
Marshal.StructureToPtr(css, cmdPtr, false);
MirandaContext.Current.CallService(API.MS_PROTO_CALLCONTACTSERVICE, IntPtr.Zero, cmdPtr);
}
}
}
public event EventHandler<ActionEvent> OnAction;
public void InvokeOnAction(IntPtr hContact, string action)
{
if (OnAction == null)
return;
OnAction(this, new ActionEvent(hContact, action));
}
public void Dispose()
{
for (int i = 0, iCount = forkContacts.Count; i < iCount; i++)
{
forkContacts[i].Dispose();
}
}
}
}

View File

@ -0,0 +1,708 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Speak.Core;
using Speak.Interop;
using Speak.RichEdit;
using Speak.Sites;
using Speak.Structs;
using Speak.UI;
using Speak.Utils;
namespace Speak.HPP
{
internal class HistoryppHandler : IMessageProcessor
{
private IntPtr wHandle;
private ISite site;
private Subclassing subclass;
private List<HppActionOleObject> btns;
private List<HppAvatarObject> avatars;
private Dictionary<IntPtr, RichEditInfo> chachedRects;
private AvatarProcessor ap;
private ContextMenu context;
private SimpleWordAction srmmNickAction;
private SimpleWordAction srmmNumberAction;
private bool needRecalc;
private bool inRecalc;
private bool initialized;
private bool lazyInit;
private static Guid IID_IOleObject = typeof(IOleObject).GUID;
public HistoryppHandler(ISite site, IntPtr wHandle, bool lazyInit)
{
this.site = site;
Int32 hppVersion = MirandaContext.Current.CallService(API.MS_HPP_GETVERSION, IntPtr.Zero, IntPtr.Zero);
byte[] hppVBytes = BitConverter.GetBytes(hppVersion);
Version vHpp = new Version(hppVBytes[3], hppVBytes[2], hppVBytes[1], hppVBytes[0]);
if (vHpp < HppConstaints.MinumumVersion)
{
MessageBox.Show(
"You version of History++ plugin (" + vHpp.ToString() + ") is too old." + Environment.NewLine +
"Minimum supported version is " + HppConstaints.MinumumVersion.ToString() + Environment.NewLine +
"Links highlighting will be disabled",
"[xJuick] History++ version checking...",
MessageBoxButtons.OK,
MessageBoxIcon.Error);
initialized = false;
return;
}
needRecalc = inRecalc = false;
initialized = !lazyInit;
this.lazyInit = lazyInit;
this.wHandle = wHandle;
if (initialized)
{
subclass = new Subclassing(wHandle);
subclass.StartSubclassing(WndProc);
}
btns = new List<HppActionOleObject>();
avatars = new List<HppAvatarObject>();
chachedRects = new Dictionary<IntPtr, RichEditInfo>();
srmmNickAction = Settings.Instance.SRMMNickAction;
srmmNumberAction = Settings.Instance.SRMMNumberAction;
ap = new AvatarProcessor(site);
MakeContextMenu();
}
private void MakeContextMenu()
{
context = new ContextMenu();
foreach (LinkButton lb in Settings.Instance.SRMMLinkButtons)
{
if (!lb.Enabled)
continue;
ActionMenuItem mi = new ActionMenuItem(lb);
//mi.Image = IconTable.GetActionIcon(lb.IconName);
mi.Click += ActionMenuClick;
context.MenuItems.Add(mi);
}
ActionMenuItem contextAvatar = new ActionMenuItem(new LinkButton(String.Empty, String.Empty, false, LinkDisplayType.Image));
context.MenuItems.Add(contextAvatar);
}
public int WndProc(IntPtr hWnd, int Msg, int wParam, int lParam)
{
bool lmb = false;
switch (Msg)
{
case WinApi.WM_LBUTTONDBLCLK:
case WinApi.WM_LBUTTONDOWN:
case WinApi.WM_LBUTTONUP:
int x = Util.LoWord(lParam);
int y = Util.HiWord(lParam);
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
HppActionOleObject btn = btns[i];
RECT rect = chachedRects[btn.Owner].Rect;
if (rect.IsEmpty)
continue;
if (btn.HitTest(x, y - rect.Top))
{
if (Msg == WinApi.WM_LBUTTONDOWN)
{
btn.SetLMBDownState();
}
else if (Msg == WinApi.WM_LBUTTONUP)
{
btn.SetLMBUpState(hWnd, rect.Top);
}
lmb = true;
break;
}
}
break;
}
int result = 0;
if (!lmb)
result = subclass.CallParent(hWnd, Msg, wParam, lParam);
switch (Msg)
{
case WinApi.WM_MOUSEMOVE:
int x = Util.LoWord(lParam);
int y = Util.HiWord(lParam);
if (needRecalc)
{
RecalcRects();
needRecalc = false;
}
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
HppActionOleObject btn = btns[i];
RECT rect = chachedRects[btn.Owner].Rect;
if (!rect.IsEmpty)
btn.MouseMoving(x, y - rect.Top);
}
if (((wParam & WinApi.MK_CONTROL) == WinApi.MK_CONTROL) && Settings.Instance.ShowPreview)
{
foreach (KeyValuePair<IntPtr, RichEditInfo> rect in chachedRects)
{
if (!rect.Value.Rect.IsEmpty)
{
if (y > rect.Value.Rect.Top && y < rect.Value.Rect.Bottom)
{
string url = GetCurrentURL(x - rect.Value.Rect.Left, y - rect.Value.Rect.Top, RichEditHelpers.GetIText(rect.Key), rect.Key);
if (!String.IsNullOrEmpty(url))
{
POINT pt = new POINT(x, y);
WinApi.ClientToScreen(wHandle, ref pt);
ImagePreview.Show(pt.X, pt.Y + 10, url);
break;
}
else
{
ImagePreview.Hide();
}
break;
}
}
}
}
else
{
ImagePreview.Hide();
}
break;
//case WinApi.WM_PAINT:
case WinApi.WM_VSCROLL:
case WinApi.WM_RESIZE:
needRecalc = true;
break;
}
return result;
}
public void SettingsChanged()
{
MakeContextMenu();
}
public void Update()
{
if (!initialized)
return;
}
public void ShowThreads()
{
if (!initialized)
return;
}
public void Avatars()
{
if (!initialized)
return;
// not supported
}
private void ClearButtons(IntPtr oldOwner)
{
List<HppActionOleObject> newBtns = new List<HppActionOleObject>();
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
if (btns[i].Owner != oldOwner)
newBtns.Add(btns[i]);
}
btns = newBtns;
List<HppAvatarObject> newAvatars = new List<HppAvatarObject>();
for (int i = 0, iCount = newAvatars.Count; i < iCount; i++)
{
if (avatars[i].Owner != oldOwner)
newAvatars.Add(avatars[i]);
}
avatars = newAvatars;
}
private void RecalcRects()
{
inRecalc = true;
Dictionary<IntPtr, RichEditInfo> newRects = new Dictionary<IntPtr, RichEditInfo>();
foreach (KeyValuePair<IntPtr, RichEditInfo> rect in chachedRects)
{
IntPtr h = rect.Key;
RichEditInfo ri = RichEditHelpers.GetRichEditInfo(h, wHandle);
RECT r = ri.Rect;
newRects.Add(h, ri);
if (r.Top > 0)
{
SetActionObjectPosition(h, true);
}
else if (r.Bottom > 0 /*&& !rect.Value.Equals(r)*/)
{
SetActionObjectPosition(h, true);
}
}
for (int i = 0, iCount = avatars.Count; i < iCount; i++)
{
avatars[i].BgColor = newRects[avatars[i].Owner].BgColor;
}
chachedRects = newRects;
inRecalc = false;
}
public void ProcessHistoryItem(IntPtr smallHandle, ItemRenderDetails ird)
{
if (lazyInit)
{
LogHandler currentLog;
wHandle = LogWindow.FindRealLogWindow(wHandle, Settings.CurrentLog, ird.hContact, out currentLog);
if (wHandle != IntPtr.Zero)
{
subclass = new Subclassing(wHandle);
subclass.StartSubclassing(WndProc);
initialized = true;
}
lazyInit = false;
}
if (!initialized)
return;
IRichEditOle richEditOle = RichEditHelpers.SendMessage(smallHandle, REConstants.EM_GETOLEINTERFACE, 0);
ITextDocument itr = RichEditHelpers.GetIText(smallHandle);
if (!inRecalc)
{
if (chachedRects.ContainsKey(smallHandle))
ClearButtons(smallHandle);
chachedRects[smallHandle] = RichEditInfo.Empty;
}
if (itr != null)
Routine(itr, richEditOle, smallHandle);
needRecalc = true;
return;
}
private string GetRichEditText(ITextDocument richEdit)
{
string text = richEdit.Range(0, Int32.MaxValue).Text;
if (String.IsNullOrEmpty(text))
return String.Empty;
return text;
}
private void Routine(ITextDocument richEdit, IRichEditOle ole, IntPtr handle)
{
string text = GetRichEditText(richEdit);
bool readOnly = (WinApi.GetWindowLong(handle, WinApi.GWL_STYLE) & REConstants.ES_READONLY) != 0;
if (readOnly)
WinApi.SendMessage(handle, REConstants.EM_SETREADONLY, 0, 0);
richEdit.Freeze();
// posts/comments
Match m = site.NumRegex.Match(text);
while (m.Success)
{
string victimWord = m.Groups["full"].Value;
ActionWordType actionWord = !String.IsNullOrEmpty(m.Groups["cmnt"].Value)
? ActionWordType.Comments
: ActionWordType.Post;
int selStart = text.IndexOf(victimWord);
bool correctID = true;
if (victimWord.Length < 3)
correctID = false;
// fucking urls
if (correctID && victimWord.Length < 5)
{
richEdit.Selection.Start = selStart;
richEdit.Selection.End = selStart + 1;
CHARFORMAT2_STRUCT cf = new CHARFORMAT2_STRUCT();
cf.cbSize = (UInt32)Marshal.SizeOf(cf);
cf.szFaceName = new char[32];
IntPtr wpar = new IntPtr(REConstants.SCF_SELECTION);
IntPtr lpar = Marshal.AllocCoTaskMem(Marshal.SizeOf(cf));
Marshal.StructureToPtr(cf, lpar, false);
new IntPtr(WinApi.SendMessage(handle, REConstants.EM_GETCHARFORMAT, wpar, lpar));
cf = (CHARFORMAT2_STRUCT)Marshal.PtrToStructure(lpar, typeof(CHARFORMAT2_STRUCT));
if (
((cf.dwMask & REConstants.CFM_LINK) == REConstants.CFM_LINK) &&
((cf.dwEffects & REConstants.CFE_LINK) == REConstants.CFE_LINK)
)
{
correctID = false;
}
Marshal.FreeCoTaskMem(lpar);
}
if (correctID)
{
AddActionObject(richEdit, ole, handle, selStart, victimWord, actionWord);
text = GetRichEditText(richEdit);
}
m = m.NextMatch();
}
// JIDs
m = Regexps.JidRegEx.Match(text);
while (m.Success)
{
string victimWord = m.Groups["name"].Value;
AddActionObject(richEdit, ole, handle, text.IndexOf(victimWord), victimWord, ActionWordType.Nick);
text = GetRichEditText(richEdit);
m = m.NextMatch();
}
// @nicks
m = site.NameRegex.Match(text);
while (m.Success)
{
string victimWord = m.Groups["name"].Value;
ActionObjectType objectType = !String.IsNullOrEmpty(m.Groups["isFirst"].Value) ? ActionObjectType.FirstNick : ActionObjectType.Nick;
AddActionObject(richEdit, ole, handle, text.IndexOf(victimWord), victimWord, ActionWordType.Nick, objectType);
text = GetRichEditText(richEdit);
m = m.NextMatch();
}
richEdit.Unfreeze();
// avatars
if (Settings.Instance.ShowAvatars)
ShowAvatars(richEdit, ole, handle);
if (readOnly)
WinApi.SendMessage(handle, REConstants.EM_SETREADONLY, 1, 0);
}
private void ShowAvatars(ITextDocument richEdit, IRichEditOle richEditOle, IntPtr owner)
{
List<KeyValuePair<string, int>> avatars = new List<KeyValuePair<string, int>>();
//Int32 lastLine = -1;
for (int i = 0, iCount = richEditOle.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (richEditOle.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
if (reoObject.clsid == HppActionOleObject.Guid)
{
IntPtr iaolep;
Marshal.QueryInterface(reoObject.poleobj, ref IID_IOleObject, out iaolep);
IActionOleObject iao = (IActionOleObject)Marshal.GetTypedObjectForIUnknown(iaolep, typeof(IActionOleObject));
if (!iao.IsTailObjectSet && iao.ObjectType == ActionObjectType.FirstNick)
{
// select for yourself
//int lineIndex = WinApi.SendMessage(owner, REConstants.EM_EXLINEFROMCHAR, 0, reoObject.cp);
//int charOffset = reoObject.cp - WinApi.SendMessage(wHandle, REConstants.EM_LINEINDEX, lineIndex, 0);
//avatars.Add(new KeyValuePair<string, int>(iao.Text.Substring(1), reoObject.cp + avatars.Count - (lastLine != lineIndex ? charOffset : 0)));
avatars.Add(new KeyValuePair<string, int>(iao.Text.Substring(1), reoObject.cp + avatars.Count));
//lastLine = lineIndex;
iao.IsTailObjectSet = true;
}
}
}
}
int offset = 0;
foreach (KeyValuePair<string, int> ava in avatars)
{
int index = offset + ava.Value;
richEdit.Selection.Start = index;
richEdit.Selection.End = index;
RichEditHelpers.InsertControl(richEditOle, new HppAvatarObject(owner, wHandle, ap, ava.Key));
richEdit.Range(index + 1, index + 1).Text = " ";
offset += 1;
}
ap.Process();
needRecalc = true;
}
// well. it's not supported yet, since I dunno how to invalidate hpp window
private void DeleteAvatars(ITextDocument richEdit, IRichEditOle richEditOle)
{
for (int i = 0, iCount = richEditOle.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (richEditOle.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
if (reoObject.clsid == AvatarObject.Guid)
{
richEdit.Range(reoObject.cp, reoObject.cp + 2).Text = "";
}
}
}
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
if (btns[i].ObjectType == ActionObjectType.FirstNick)
btns[i].IsTailObjectSet = false;
}
}
private void AddActionObject(ITextDocument richEdit, IRichEditOle ole, IntPtr owner, int selStart, string fullWord, ActionWordType actionType)
{
AddActionObject(richEdit, ole, owner, selStart, fullWord, actionType, ActionObjectType.Default);
}
private void AddActionObject(ITextDocument richEdit, IRichEditOle ole, IntPtr owner, int selStart, string fullWord, ActionWordType actionType, ActionObjectType objectType)
{
richEdit.Selection.Start = selStart;
richEdit.Selection.End = selStart + fullWord.Length;
HppActionOleObject aoo = new HppActionOleObject();
aoo.ObjectType = objectType;
aoo.ActionType = actionType;
aoo.Owner = owner;
aoo.MainHandle = wHandle;
aoo.Left = 0;
aoo.ActionClicked += actionObject_JuickClicked;
aoo.Font = new Font(richEdit.Selection.Font.Name, richEdit.Selection.Font.Size);
aoo.ForeColor = ColorTranslator.FromWin32(richEdit.Selection.Font.ForeColor);
aoo.Text = fullWord;
btns.Add(aoo);
RichEditHelpers.InsertControl(ole, aoo);
}
private void SetActionObjectPosition(IntPtr owner, bool redraw)
{
IRichEditOle ole = RichEditHelpers.SendMessage(owner, REConstants.EM_GETOLEINTERFACE, 0);
ITextDocument richEdit = RichEditHelpers.GetIText(owner);
if (richEdit == null)
return;
ITextRange range = richEdit.Range(0, Int32.MaxValue);
for (int i = 0, iCount = ole.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (ole.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
bool isButton = reoObject.clsid == HppActionOleObject.Guid;
if ((isButton) || (Settings.Instance.ShowAvatars && reoObject.clsid == HppAvatarObject.Guid))
{
int x;
int y;
range.SetRange(reoObject.cp, reoObject.cp);
range.GetPoint(REConstants.TomStart | REConstants.TA_LEFT | REConstants.TA_BOTTOM, out x, out y);
IntPtr iaolep;
Marshal.QueryInterface(reoObject.poleobj, ref IID_IOleObject, out iaolep);
IActionOleObject iao = (IActionOleObject)Marshal.GetTypedObjectForIUnknown(iaolep, typeof(IActionOleObject));
POINT stc = new POINT(x, y);
WinApi.ScreenToClient(owner, ref stc);
iao.Left = stc.X;
iao.Bottom = stc.Y;
if (redraw)
{
if (isButton)
{
((HppActionOleObject) iao).Draw();
((HppActionOleObject) iao).Drawn = false;
}
/*
else
{
HppAvatarObject avo = (HppAvatarObject)iao;
if (!avo.Drawn && avo.Ready)
avo.Draw();
}
*/
}
}
}
}
}
private void ActionMenuClick(object sender, EventArgs e)
{
ActionMenuItem mi = (ActionMenuItem)sender;
InvokeJuick(new ActionClickEvent(mi.Action, mi.AutoSend));
}
private void actionObject_JuickClicked(object sender, ActionObjectClickEvent e)
{
ActionWordType actionWord = e.ActionType;
if (e.MenuLocation != Point.Empty)
{
if (actionWord == ActionWordType.None)
return;
for (int i = 0, iCount = context.MenuItems.Count; i < iCount; i++)
{
ActionMenuItem btn = (ActionMenuItem)context.MenuItems[i];
btn.MainWord = e.ActionText;
if (btn.DisplayType != LinkDisplayType.Always)
{
if (
(btn.DisplayType == LinkDisplayType.Comments && actionWord != ActionWordType.Comments) ||
(btn.DisplayType == LinkDisplayType.Posts && actionWord != ActionWordType.Post) ||
(btn.DisplayType == LinkDisplayType.Nicks && actionWord != ActionWordType.Nick)
)
{
btn.Visible = false;
continue;
}
}
if (btn.DisplayType == LinkDisplayType.Image)
{
if (Settings.Instance.ShowContextAvatars)
{
string avatarPath = ap.GetUserAvatar(btn.MainWord.Substring(1), null);
if (String.IsNullOrEmpty(avatarPath))
{
ap.Process();
btn.Visible = false;
continue;
}
else
{
btn.Image = Image.FromFile(avatarPath);
}
}
else
{
btn.Visible = false;
continue;
}
}
Match m = site.NumRegex.Match(btn.MainWord);
if (m.Success)
{
if (!String.IsNullOrEmpty(m.Groups["cmnt"].Value))
{
btn.AdditionalWord = m.Groups["full"].Value;
btn.MainWord = m.Groups["post"].Value;
}
}
btn.Visible = true;
continue;
}
context.Show(sender as Control, e.MenuLocation);
}
else
{
if (actionWord == ActionWordType.Nick)
InvokeJuick(new ActionClickEvent(srmmNickAction.Action.Replace("%NICK%", e.ActionText), srmmNickAction.Autosend));
else if (actionWord == ActionWordType.Post || actionWord == ActionWordType.Comments)
InvokeJuick(new ActionClickEvent(srmmNumberAction.Action.Replace("%NUMBER%", e.ActionText), srmmNumberAction.Autosend));
}
}
private string GetCurrentURL(int x, int y, ITextDocument richEdit, IntPtr handle)
{
POINTL pointl = new POINTL(x, y);
Subclassing.SetLastError(0);
int charIndex = WinApi.SendMessage(handle, REConstants.EM_CHARFROMPOS, 0, ref pointl);
int err = Marshal.GetLastWin32Error();
if (err != 0 && err != 6)
return String.Empty;
if (charIndex <= 0)
return null;
int lineIndex = WinApi.SendMessage(handle, REConstants.EM_EXLINEFROMCHAR, 0, charIndex);
int charOffset = charIndex - WinApi.SendMessage(handle, REConstants.EM_LINEINDEX, lineIndex, 0);
int len = WinApi.SendMessage(handle, REConstants.EM_LINELENGTH, charIndex, 0);
string line = richEdit.Range(charIndex - charOffset, (charIndex - charOffset) + len).Text;
if (String.IsNullOrEmpty(line))
return null;
if (charOffset == len)
return null;
string result = String.Empty;
int i = charOffset - 1;
int j = charOffset - 1;
try
{
while (i >= 0 && line[i] != ' ')
{
i--;
}
i = i + 1;
if (j == -1)
return null;
while (j < len && line[j] != ' ')
{
j++;
}
if (j < i)
return null;
result = line.Substring(i, j - i).Trim();
if (result.IndexOf("http://") != -1)
{
return result;
}
}
catch { return String.Empty; }
return String.Empty;
}
public event EventHandler<ActionClickEvent> JuickClicked;
private void InvokeJuick(ActionClickEvent e)
{
EventHandler<ActionClickEvent> handler = JuickClicked;
if (handler != null) handler(this, e);
}
public void Dispose()
{
if (subclass != null)
{
subclass.StopSubclass();
subclass.Dispose();
}
}
}
}

View File

@ -0,0 +1,157 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using Speak.Interop;
using Speak.RichEdit;
using Speak.Structs;
namespace Speak.HPP
{
[Guid("f16cc4c1-ea72-4777-9205-892fd50bf6e5")]
internal class HppActionOleObject: ActionOleObject
{
private IntPtr owner;
private IntPtr mainHandle;
private bool drawn;
new public static readonly Guid Guid = new Guid("f16cc4c1-ea72-4777-9205-892fd50bf6e5");
internal void Draw()
{
TFVCNDATA_NMHDR mh = new TFVCNDATA_NMHDR();
mh.cbSize = Marshal.SizeOf(mh);
mh.handleFrom = owner; // "mini" RE handle
mh.code = HppConstaints.NM_FIREVIEWCHANGE;
mh.bEvent = HppConstaints.FVCN_PREFIRE;
mh.bAction = HppConstaints.FVCA_DRAW;
mh.rcRect = new RECT(Left, Top, Right, Bottom);
mh.lparam = IntPtr.Zero;
IntPtr cmd = Marshal.AllocHGlobal(Marshal.SizeOf(mh));
Marshal.StructureToPtr(mh, cmd, false);
WinApi.SendMessage(mainHandle, WinApi.WM_NOTIFY, owner, cmd);
mh = (TFVCNDATA_NMHDR)Marshal.PtrToStructure(cmd, typeof(TFVCNDATA_NMHDR));
if (mh.bAction == HppConstaints.FVCA_CUSTOMDRAW && mh.hDC != IntPtr.Zero)
{
BackColor = mh.clrBackground.GetColor();
Rectangle rect = new Rectangle(Left, Top, Right - Left, Bottom - Top);
Graphics g = Graphics.FromHdc(mh.hDC);
DrawBackground(g, rect);
Draw(g, Left);
g.Dispose();
mh.bEvent = HppConstaints.FVCN_POSTFIRE;
cmd = Marshal.AllocHGlobal(Marshal.SizeOf(mh));
Marshal.StructureToPtr(mh, cmd, false);
WinApi.SendMessage(mainHandle, WinApi.WM_NOTIFY, owner, cmd);
drawn = true;
}
}
private void Draw(Graphics g, int leftOffset)
{
TextRenderer.DrawText(
g, Text, Font,
onControl ? new Point(leftOffset + 1, Top + (Height - textSize.Height) / 2) : new Point(leftOffset + 1, Top + Height - textSize.Height),
onControl ? hoverForeColor : ForeColor, TextFormatFlags.Default);
/*using (Bitmap bm = Properties.Resources.power)
{
g.DrawImage(bm, leftOffset + Width - iconWidth, Top + ((Height - iconHeight) / 2) + 1);
}*/
}
private void DrawBackground(Graphics g, Rectangle rect)
{
Rectangle activePart = rect;
switch (currentHover)
{
case HoverPart.None:
break;
case HoverPart.MainWord:
//activePart = new Rectangle(0, 0, textSize.Width, Height - 1);
activePart = new Rectangle(rect.Left, rect.Top, textSize.Width, rect.Height - 1);
break;
case HoverPart.Icon:
activePart = new Rectangle(rect.Left + textSize.Width, rect.Top, iconWidth-1, Height-1);
break;
default:
throw new ArgumentOutOfRangeException();
}
using (SolidBrush b = new SolidBrush(BackColor))
{
g.FillRectangle(b, rect);
}
if (onControl)
{
using (SolidBrush b = new SolidBrush(hoverBackColor))
{
g.FillRectangle(b, activePart);
}
using (Pen p = new Pen(borderColor, 1.0f))
{
g.DrawRectangle(p, activePart);
}
Rectangle border = new Rectangle(rect.Location, new Size(rect.Width-1, rect.Height-1));
using (Pen p = new Pen(borderColor, 1.0f))
{
g.DrawRectangle(p, border);
}
}
}
protected override void OnPaint(System.Windows.Forms.PaintEventArgs e)
{
if (!drawn)
{
base.OnPaint(e);
drawn = true;
}
}
public bool Drawn
{
get { return drawn; }
set { drawn = value; }
}
protected override void OnPaintBackground(System.Windows.Forms.PaintEventArgs pevent)
{
//base.OnPaintBackground(pevent);
}
protected override void Invalidate()
{
Draw();
}
public IntPtr Owner
{
get { return owner; }
set { owner = value; }
}
public IntPtr MainHandle
{
get { return mainHandle; }
set { mainHandle = value; }
}
new public Guid GUID
{
get { return Guid; }
}
}
}

View File

@ -0,0 +1,181 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Runtime.InteropServices;
using Speak.Core;
using Speak.Interop;
using Speak.RichEdit;
using Speak.Structs;
namespace Speak.HPP
{
// бляяя....
[Guid("04175c1c-6ab3-4688-837a-6b478fc64b65")]
internal class HppAvatarObject : AvatarObject, IActionOleGUID, IActionOleObject
{
private bool drawn;
private bool drawnInternal;
private volatile bool gotBottom;
private IntPtr owner;
private IntPtr mainHandle;
new public static readonly Guid Guid = new Guid("04175c1c-6ab3-4688-837a-6b478fc64b65");
public HppAvatarObject(IntPtr owner, IntPtr mainHandle, AvatarProcessor ap, string key) : base(ap, key, Color.Pink)
{
drawn = false;
Width = Height = 32;
this.mainHandle = mainHandle;
this.owner = owner;
}
internal void Draw()
{
//if (!gotBottom)
// return;
TFVCNDATA_NMHDR mh = new TFVCNDATA_NMHDR();
mh.cbSize = Marshal.SizeOf(mh);
mh.handleFrom = owner; // "mini" RE handle
mh.code = HppConstaints.NM_FIREVIEWCHANGE;
mh.bEvent = HppConstaints.FVCN_PREFIRE;
mh.bAction = HppConstaints.FVCA_DRAW;
mh.rcRect = new RECT(Left, Top, Right, Bottom);
mh.lparam = IntPtr.Zero;
IntPtr cmd = Marshal.AllocHGlobal(Marshal.SizeOf(mh));
Marshal.StructureToPtr(mh, cmd, false);
WinApi.SendMessage(mainHandle, WinApi.WM_NOTIFY, owner, cmd);
mh = (TFVCNDATA_NMHDR)Marshal.PtrToStructure(cmd, typeof(TFVCNDATA_NMHDR));
if (mh.bAction == HppConstaints.FVCA_CUSTOMDRAW && mh.hDC != IntPtr.Zero)
{
Graphics g = Graphics.FromHdc(mh.hDC);
g.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
g.DrawImage(image, Left, Top, Width, Height);
g.Dispose();
mh.bEvent = HppConstaints.FVCN_POSTFIRE;
cmd = Marshal.AllocHGlobal(Marshal.SizeOf(mh));
Marshal.StructureToPtr(mh, cmd, false);
WinApi.SendMessage(mainHandle, WinApi.WM_NOTIFY, owner, cmd);
drawn = true;
}
}
public override void AvatarCallback(string userName, string avatarPath)
{
drawnInternal = false;
image = Image.FromFile(avatarPath);
if (gotBottom)
Draw();
}
protected override void OnPaint(System.Windows.Forms.PaintEventArgs e)
{
if (!drawnInternal && Ready)
{
base.OnPaint(e);
drawnInternal = true;
}
}
protected override void OnPaintBackground(System.Windows.Forms.PaintEventArgs pevent)
{
//base.OnPaintBackground(pevent);
}
protected override void Invalidate()
{
//Draw();
}
public bool Ready
{
get { return image != null; }
}
public bool Drawn
{
get { return drawn; }
}
public Color BgColor
{
get
{
return BackColor;
}
set
{
drawn = false;
BackColor = value;
Invalidate();
}
}
public IntPtr Owner
{
get { return owner; }
}
new public Guid GUID
{
get { return Guid; }
}
new public int Bottom
{
set
{
Top = value - Height;
gotBottom = true;
if (Ready)
Draw();
}
get { return base.Bottom; }
}
public ActionObjectType ObjectType
{
get { return ActionObjectType.Default; }
set { }
}
public bool IsTailObjectSet
{
get { return true; }
set { }
}
public bool HitTest(int x, int y)
{
return false;
}
public void MouseMoving(int x, int y)
{
}
public void SetLMBDownState()
{
}
public void SetLMBUpState(IntPtr richEditHwnd, int topOffset)
{
}
public ActionWordType ActionType
{
get { return ActionWordType.None; }
set { }
}
}
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,110 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.Interfaces
{
[ComVisible(true), ComImport()]
[TypeLibType((short)4160)]
[InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIDispatch)]
[Guid("3050f613-98b5-11cf-bb82-00aa00bdce0b")]
public interface HTMLDocumentEvents2
{
/*
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONHELP)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onhelp([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
*/
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONCLICK)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onclick([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
/*
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDBLCLICK)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool ondblclick([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONKEYDOWN)]
void onkeydown([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONKEYUP)]
void onkeyup([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONKEYPRESS)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onkeypress([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEDOWN)]
void onmousedown([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEMOVE)]
void onmousemove([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEUP)]
void onmouseup([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEOUT)]
void onmouseout([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEOVER)]
void onmouseover([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONREADYSTATECHANGE)]
void onreadystatechange([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONBEFOREUPDATE)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onbeforeupdate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONAFTERUPDATE)]
void onafterupdate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONROWEXIT)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onrowexit([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONROWENTER)]
void onrowenter([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDRAGSTART)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool ondragstart([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONSELECTSTART)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onselectstart([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONERRORUPDATE)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onerrorupdate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONCONTEXTMENU)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool oncontextmenu([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONSTOP)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onstop([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONROWSDELETE)]
void onrowsdelete([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONROWSINSERTED)]
void onrowsinserted([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONCELLCHANGE)]
void oncellchange([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONPROPERTYCHANGE)]
void onpropertychange([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDATASETCHANGED)]
void ondatasetchanged([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDATAAVAILABLE)]
void ondataavailable([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDATASETCOMPLETE)]
void ondatasetcomplete([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONBEFOREEDITFOCUS)]
void onbeforeeditfocus([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONSELECTIONCHANGE)]
void onselectionchange([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONCONTROLSELECT)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool oncontrolselect([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONMOUSEWHEEL)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onmousewheel([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONFOCUSIN)]
void onfocusin([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONFOCUSOUT)]
void onfocusout([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONACTIVATE)]
void onactivate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONDEACTIVATE)]
void ondeactivate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONBEFOREACTIVATE)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onbeforeactivate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
[DispId(HTMLDispIDs.DISPID_HTMLDOCUMENTEVENTS2_ONBEFOREDEACTIVATE)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool onbeforedeactivate([In, MarshalAs(UnmanagedType.Interface)] IHTMLEventObj pEvtObj);
*/
}
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,784 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.Interfaces
{
[Guid("3050F1FF-98B5-11CF-BB82-00AA00BDCE0B")]
[ComImport]
[TypeLibType((short)4160)]
[InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIDispatch)]
public interface IHTMLElement
{
/// <summary><para><c>setAttribute</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>setAttribute</c> method was the following: <c>HRESULT setAttribute (BSTR strAttributeName, VARIANT AttributeValue, [optional, defaultvalue(1)] long lFlags)</c>;</para></remarks>
// IDL: HRESULT setAttribute (BSTR strAttributeName, VARIANT AttributeValue, [optional, defaultvalue(1)] long lFlags);
// VB6: Sub setAttribute (ByVal strAttributeName As String, ByVal AttributeValue As Any, [ByVal lFlags As Long = 1])
[DispId(HTMLDispIDs.DISPID_IHTMLELEMENT_SETATTRIBUTE)] // - 2147417611)]
void setAttribute([MarshalAs(UnmanagedType.BStr)] string strAttributeName, object AttributeValue, int lFlags);
/// <summary><para><c>getAttribute</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>getAttribute</c> method was the following: <c>HRESULT getAttribute (BSTR strAttributeName, [optional, defaultvalue(0)] long lFlags, [out, retval] VARIANT* ReturnValue)</c>;</para></remarks>
// IDL: HRESULT getAttribute (BSTR strAttributeName, [optional, defaultvalue(0)] long lFlags, [out, retval] VARIANT* ReturnValue);
// VB6: Function getAttribute (ByVal strAttributeName As String, [ByVal lFlags As Long = 0]) As Any
[DispId(-2147417610)]
object getAttribute([MarshalAs(UnmanagedType.BStr)] string strAttributeName, int lFlags);
/// <summary><para><c>removeAttribute</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>removeAttribute</c> method was the following: <c>HRESULT removeAttribute (BSTR strAttributeName, [optional, defaultvalue(1)] long lFlags, [out, retval] VARIANT_BOOL* ReturnValue)</c>;</para></remarks>
// IDL: HRESULT removeAttribute (BSTR strAttributeName, [optional, defaultvalue(1)] long lFlags, [out, retval] VARIANT_BOOL* ReturnValue);
// VB6: Function removeAttribute (ByVal strAttributeName As String, [ByVal lFlags As Long = 1]) As Boolean
[DispId(-2147417609)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool removeAttribute([MarshalAs(UnmanagedType.BStr)] string strAttributeName, int lFlags);
/// <summary><para><c>scrollIntoView</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>scrollIntoView</c> method was the following: <c>HRESULT scrollIntoView ([optional] VARIANT varargStart)</c>;</para></remarks>
// IDL: HRESULT scrollIntoView ([optional] VARIANT varargStart);
// VB6: Sub scrollIntoView ([ByVal varargStart As Any])
[DispId(-2147417093)]
void scrollIntoView(object varargStart);
/// <summary><para><c>contains</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>contains</c> method was the following: <c>HRESULT contains (IHTMLElement* pChild, [out, retval] VARIANT_BOOL* ReturnValue)</c>;</para></remarks>
// IDL: HRESULT contains (IHTMLElement* pChild, [out, retval] VARIANT_BOOL* ReturnValue);
// VB6: Function contains (ByVal pChild As IHTMLElement) As Boolean
[DispId(-2147417092)]
[return: MarshalAs(UnmanagedType.VariantBool)]
bool contains(IHTMLElement pChild);
/// <summary><para><c>insertAdjacentHTML</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>insertAdjacentHTML</c> method was the following: <c>HRESULT insertAdjacentHTML (BSTR where, BSTR html)</c>;</para></remarks>
// IDL: HRESULT insertAdjacentHTML (BSTR where, BSTR html);
// VB6: Sub insertAdjacentHTML (ByVal where As String, ByVal html As String)
[DispId(-2147417082)]
void insertAdjacentHTML([MarshalAs(UnmanagedType.BStr)] string where, [MarshalAs(UnmanagedType.BStr)] string html);
/// <summary><para><c>insertAdjacentText</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>insertAdjacentText</c> method was the following: <c>HRESULT insertAdjacentText (BSTR where, BSTR text)</c>;</para></remarks>
// IDL: HRESULT insertAdjacentText (BSTR where, BSTR text);
// VB6: Sub insertAdjacentText (ByVal where As String, ByVal text As String)
[DispId(-2147417081)]
void insertAdjacentText([MarshalAs(UnmanagedType.BStr)] string where, [MarshalAs(UnmanagedType.BStr)] string text);
/// <summary><para><c>click</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>click</c> method was the following: <c>HRESULT click (void)</c>;</para></remarks>
// IDL: HRESULT click (void);
// VB6: Sub click
[DispId(-2147417079)]
void click();
/// <summary><para><c>toString</c> method of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>toString</c> method was the following: <c>HRESULT toString ([out, retval] BSTR* ReturnValue)</c>;</para></remarks>
// IDL: HRESULT toString ([out, retval] BSTR* ReturnValue);
// VB6: Function toString As String
[DispId(-2147417076)]
[return: MarshalAs(UnmanagedType.BStr)]
string toString();
/// <summary><para><c>all</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>all</c> property was the following: <c>IDispatch* all</c>;</para></remarks>
// IDL: IDispatch* all;
// VB6: all As IDispatch
object all
{
// IDL: HRESULT all ([out, retval] IDispatch** ReturnValue);
// VB6: Function all As IDispatch
[DispId(-2147417074)]
[return: MarshalAs(UnmanagedType.IDispatch)]
get;
}
/// <summary><para><c>children</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>children</c> property was the following: <c>IDispatch* children</c>;</para></remarks>
// IDL: IDispatch* children;
// VB6: children As IDispatch
object children
{
// IDL: HRESULT children ([out, retval] IDispatch** ReturnValue);
// VB6: Function children As IDispatch
[DispId(-2147417075)]
[return: MarshalAs(UnmanagedType.IDispatch)]
get;
}
/// <summary><para><c>className</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>className</c> property was the following: <c>BSTR className</c>;</para></remarks>
// IDL: BSTR className;
// VB6: className As String
string className
{
// IDL: HRESULT className ([out, retval] BSTR* ReturnValue);
// VB6: Function className As String
[DispId(-2147417111)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT className (BSTR value);
// VB6: Sub className (ByVal value As String)
[DispId(-2147417111)]
set;
}
/// <summary><para><c>document</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>document</c> property was the following: <c>IDispatch* document</c>;</para></remarks>
// IDL: IDispatch* document;
// VB6: document As IDispatch
object document
{
// IDL: HRESULT document ([out, retval] IDispatch** ReturnValue);
// VB6: Function document As IDispatch
[DispId(-2147417094)]
[return: MarshalAs(UnmanagedType.IDispatch)]
get;
}
/// <summary><para><c>filters</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>filters</c> property was the following: <c>IHTMLFiltersCollection* filters</c>;</para></remarks>
// IDL: IHTMLFiltersCollection* filters;
// VB6: filters As IHTMLFiltersCollection
//IHTMLFiltersCollection filters
object filters
{
// IDL: HRESULT filters ([out, retval] IHTMLFiltersCollection** ReturnValue);
// VB6: Function filters As IHTMLFiltersCollection
[DispId(-2147417077)]
[return: MarshalAs(UnmanagedType.Interface)]
get;
}
/// <summary><para><c>id</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>id</c> property was the following: <c>BSTR id</c>;</para></remarks>
// IDL: BSTR id;
// VB6: id As String
string id
{
// IDL: HRESULT id ([out, retval] BSTR* ReturnValue);
// VB6: Function id As String
[DispId(-2147417110)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT id (BSTR value);
// VB6: Sub id (ByVal value As String)
[DispId(-2147417110)]
set;
}
/// <summary><para><c>innerHTML</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>innerHTML</c> property was the following: <c>BSTR innerHTML</c>;</para></remarks>
// IDL: BSTR innerHTML;
// VB6: innerHTML As String
string innerHTML
{
// IDL: HRESULT innerHTML ([out, retval] BSTR* ReturnValue);
// VB6: Function innerHTML As String
[DispId(-2147417086)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT innerHTML (BSTR value);
// VB6: Sub innerHTML (ByVal value As String)
[DispId(-2147417086)]
set;
}
/// <summary><para><c>innerText</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>innerText</c> property was the following: <c>BSTR innerText</c>;</para></remarks>
// IDL: BSTR innerText;
// VB6: innerText As String
string innerText
{
// IDL: HRESULT innerText ([out, retval] BSTR* ReturnValue);
// VB6: Function innerText As String
[DispId(-2147417085)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT innerText (BSTR value);
// VB6: Sub innerText (ByVal value As String)
[DispId(-2147417085)]
set;
}
/// <summary><para><c>isTextEdit</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>isTextEdit</c> property was the following: <c>VARIANT_BOOL isTextEdit</c>;</para></remarks>
// IDL: VARIANT_BOOL isTextEdit;
// VB6: isTextEdit As Boolean
bool isTextEdit
{
// IDL: HRESULT isTextEdit ([out, retval] VARIANT_BOOL* ReturnValue);
// VB6: Function isTextEdit As Boolean
[DispId(-2147417078)]
[return: MarshalAs(UnmanagedType.VariantBool)]
get;
}
/// <summary><para><c>lang</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>lang</c> property was the following: <c>BSTR lang</c>;</para></remarks>
// IDL: BSTR lang;
// VB6: lang As String
string lang
{
// IDL: HRESULT lang ([out, retval] BSTR* ReturnValue);
// VB6: Function lang As String
[DispId(-2147413103)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT lang (BSTR value);
// VB6: Sub lang (ByVal value As String)
[DispId(-2147413103)]
set;
}
/// <summary><para><c>language</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>language</c> property was the following: <c>BSTR language</c>;</para></remarks>
// IDL: BSTR language;
// VB6: language As String
string language
{
// IDL: HRESULT language ([out, retval] BSTR* ReturnValue);
// VB6: Function language As String
[DispId(-2147413012)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT language (BSTR value);
// VB6: Sub language (ByVal value As String)
[DispId(-2147413012)]
set;
}
/// <summary><para><c>offsetHeight</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>offsetHeight</c> property was the following: <c>long offsetHeight</c>;</para></remarks>
// IDL: long offsetHeight;
// VB6: offsetHeight As Long
int offsetHeight
{
// IDL: HRESULT offsetHeight ([out, retval] long* ReturnValue);
// VB6: Function offsetHeight As Long
[DispId(-2147417101)]
get;
}
/// <summary><para><c>offsetLeft</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>offsetLeft</c> property was the following: <c>long offsetLeft</c>;</para></remarks>
// IDL: long offsetLeft;
// VB6: offsetLeft As Long
int offsetLeft
{
// IDL: HRESULT offsetLeft ([out, retval] long* ReturnValue);
// VB6: Function offsetLeft As Long
[DispId(-2147417104)]
get;
}
/// <summary><para><c>offsetParent</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>offsetParent</c> property was the following: <c>IHTMLElement* offsetParent</c>;</para></remarks>
// IDL: IHTMLElement* offsetParent;
// VB6: offsetParent As IHTMLElement
IHTMLElement offsetParent
{
// IDL: HRESULT offsetParent ([out, retval] IHTMLElement** ReturnValue);
// VB6: Function offsetParent As IHTMLElement
[DispId(-2147417100)]
get;
}
/// <summary><para><c>offsetTop</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>offsetTop</c> property was the following: <c>long offsetTop</c>;</para></remarks>
// IDL: long offsetTop;
// VB6: offsetTop As Long
int offsetTop
{
// IDL: HRESULT offsetTop ([out, retval] long* ReturnValue);
// VB6: Function offsetTop As Long
[DispId(-2147417103)]
get;
}
/// <summary><para><c>offsetWidth</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>offsetWidth</c> property was the following: <c>long offsetWidth</c>;</para></remarks>
// IDL: long offsetWidth;
// VB6: offsetWidth As Long
int offsetWidth
{
// IDL: HRESULT offsetWidth ([out, retval] long* ReturnValue);
// VB6: Function offsetWidth As Long
[DispId(-2147417102)]
get;
}
/// <summary><para><c>onafterupdate</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onafterupdate</c> property was the following: <c>VARIANT onafterupdate</c>;</para></remarks>
// IDL: VARIANT onafterupdate;
// VB6: onafterupdate As Any
object onafterupdate
{
// IDL: HRESULT onafterupdate ([out, retval] VARIANT* ReturnValue);
// VB6: Function onafterupdate As Any
[DispId(-2147412090)]
get;
// IDL: HRESULT onafterupdate (VARIANT value);
// VB6: Sub onafterupdate (ByVal value As Any)
[DispId(-2147412090)]
set;
}
/// <summary><para><c>onbeforeupdate</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onbeforeupdate</c> property was the following: <c>VARIANT onbeforeupdate</c>;</para></remarks>
// IDL: VARIANT onbeforeupdate;
// VB6: onbeforeupdate As Any
object onbeforeupdate
{
// IDL: HRESULT onbeforeupdate ([out, retval] VARIANT* ReturnValue);
// VB6: Function onbeforeupdate As Any
[DispId(-2147412091)]
get;
// IDL: HRESULT onbeforeupdate (VARIANT value);
// VB6: Sub onbeforeupdate (ByVal value As Any)
[DispId(-2147412091)]
set;
}
/// <summary><para><c>onclick</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onclick</c> property was the following: <c>VARIANT onclick</c>;</para></remarks>
// IDL: VARIANT onclick;
// VB6: onclick As Any
object onclick
{
// IDL: HRESULT onclick ([out, retval] VARIANT* ReturnValue);
// VB6: Function onclick As Any
[DispId(-2147412104)]
get;
// IDL: HRESULT onclick (VARIANT value);
// VB6: Sub onclick (ByVal value As Any)
[DispId(-2147412104)]
set;
}
/// <summary><para><c>ondataavailable</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>ondataavailable</c> property was the following: <c>VARIANT ondataavailable</c>;</para></remarks>
// IDL: VARIANT ondataavailable;
// VB6: ondataavailable As Any
object ondataavailable
{
// IDL: HRESULT ondataavailable ([out, retval] VARIANT* ReturnValue);
// VB6: Function ondataavailable As Any
[DispId(-2147412071)]
get;
// IDL: HRESULT ondataavailable (VARIANT value);
// VB6: Sub ondataavailable (ByVal value As Any)
[DispId(-2147412071)]
set;
}
/// <summary><para><c>ondatasetchanged</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>ondatasetchanged</c> property was the following: <c>VARIANT ondatasetchanged</c>;</para></remarks>
// IDL: VARIANT ondatasetchanged;
// VB6: ondatasetchanged As Any
object ondatasetchanged
{
// IDL: HRESULT ondatasetchanged ([out, retval] VARIANT* ReturnValue);
// VB6: Function ondatasetchanged As Any
[DispId(-2147412072)]
get;
// IDL: HRESULT ondatasetchanged (VARIANT value);
// VB6: Sub ondatasetchanged (ByVal value As Any)
[DispId(-2147412072)]
set;
}
/// <summary><para><c>ondatasetcomplete</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>ondatasetcomplete</c> property was the following: <c>VARIANT ondatasetcomplete</c>;</para></remarks>
// IDL: VARIANT ondatasetcomplete;
// VB6: ondatasetcomplete As Any
object ondatasetcomplete
{
// IDL: HRESULT ondatasetcomplete ([out, retval] VARIANT* ReturnValue);
// VB6: Function ondatasetcomplete As Any
[DispId(-2147412070)]
get;
// IDL: HRESULT ondatasetcomplete (VARIANT value);
// VB6: Sub ondatasetcomplete (ByVal value As Any)
[DispId(-2147412070)]
set;
}
/// <summary><para><c>ondblclick</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>ondblclick</c> property was the following: <c>VARIANT ondblclick</c>;</para></remarks>
// IDL: VARIANT ondblclick;
// VB6: ondblclick As Any
object ondblclick
{
// IDL: HRESULT ondblclick ([out, retval] VARIANT* ReturnValue);
// VB6: Function ondblclick As Any
[DispId(-2147412103)]
get;
// IDL: HRESULT ondblclick (VARIANT value);
// VB6: Sub ondblclick (ByVal value As Any)
[DispId(-2147412103)]
set;
}
/// <summary><para><c>ondragstart</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>ondragstart</c> property was the following: <c>VARIANT ondragstart</c>;</para></remarks>
// IDL: VARIANT ondragstart;
// VB6: ondragstart As Any
object ondragstart
{
// IDL: HRESULT ondragstart ([out, retval] VARIANT* ReturnValue);
// VB6: Function ondragstart As Any
[DispId(-2147412077)]
get;
// IDL: HRESULT ondragstart (VARIANT value);
// VB6: Sub ondragstart (ByVal value As Any)
[DispId(-2147412077)]
set;
}
/// <summary><para><c>onerrorupdate</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onerrorupdate</c> property was the following: <c>VARIANT onerrorupdate</c>;</para></remarks>
// IDL: VARIANT onerrorupdate;
// VB6: onerrorupdate As Any
object onerrorupdate
{
// IDL: HRESULT onerrorupdate ([out, retval] VARIANT* ReturnValue);
// VB6: Function onerrorupdate As Any
[DispId(-2147412074)]
get;
// IDL: HRESULT onerrorupdate (VARIANT value);
// VB6: Sub onerrorupdate (ByVal value As Any)
[DispId(-2147412074)]
set;
}
/// <summary><para><c>onfilterchange</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onfilterchange</c> property was the following: <c>VARIANT onfilterchange</c>;</para></remarks>
// IDL: VARIANT onfilterchange;
// VB6: onfilterchange As Any
object onfilterchange
{
// IDL: HRESULT onfilterchange ([out, retval] VARIANT* ReturnValue);
// VB6: Function onfilterchange As Any
[DispId(-2147412069)]
get;
// IDL: HRESULT onfilterchange (VARIANT value);
// VB6: Sub onfilterchange (ByVal value As Any)
[DispId(-2147412069)]
set;
}
/// <summary><para><c>onhelp</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onhelp</c> property was the following: <c>VARIANT onhelp</c>;</para></remarks>
// IDL: VARIANT onhelp;
// VB6: onhelp As Any
object onhelp
{
// IDL: HRESULT onhelp ([out, retval] VARIANT* ReturnValue);
// VB6: Function onhelp As Any
[DispId(-2147412099)]
get;
// IDL: HRESULT onhelp (VARIANT value);
// VB6: Sub onhelp (ByVal value As Any)
[DispId(-2147412099)]
set;
}
/// <summary><para><c>onkeydown</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onkeydown</c> property was the following: <c>VARIANT onkeydown</c>;</para></remarks>
// IDL: VARIANT onkeydown;
// VB6: onkeydown As Any
object onkeydown
{
// IDL: HRESULT onkeydown ([out, retval] VARIANT* ReturnValue);
// VB6: Function onkeydown As Any
[DispId(-2147412107)]
get;
// IDL: HRESULT onkeydown (VARIANT value);
// VB6: Sub onkeydown (ByVal value As Any)
[DispId(-2147412107)]
set;
}
/// <summary><para><c>onkeypress</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onkeypress</c> property was the following: <c>VARIANT onkeypress</c>;</para></remarks>
// IDL: VARIANT onkeypress;
// VB6: onkeypress As Any
object onkeypress
{
// IDL: HRESULT onkeypress ([out, retval] VARIANT* ReturnValue);
// VB6: Function onkeypress As Any
[DispId(-2147412105)]
get;
// IDL: HRESULT onkeypress (VARIANT value);
// VB6: Sub onkeypress (ByVal value As Any)
[DispId(-2147412105)]
set;
}
/// <summary><para><c>onkeyup</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onkeyup</c> property was the following: <c>VARIANT onkeyup</c>;</para></remarks>
// IDL: VARIANT onkeyup;
// VB6: onkeyup As Any
object onkeyup
{
// IDL: HRESULT onkeyup ([out, retval] VARIANT* ReturnValue);
// VB6: Function onkeyup As Any
[DispId(-2147412106)]
get;
// IDL: HRESULT onkeyup (VARIANT value);
// VB6: Sub onkeyup (ByVal value As Any)
[DispId(-2147412106)]
set;
}
/// <summary><para><c>onmousedown</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onmousedown</c> property was the following: <c>VARIANT onmousedown</c>;</para></remarks>
// IDL: VARIANT onmousedown;
// VB6: onmousedown As Any
object onmousedown
{
// IDL: HRESULT onmousedown ([out, retval] VARIANT* ReturnValue);
// VB6: Function onmousedown As Any
[DispId(-2147412110)]
get;
// IDL: HRESULT onmousedown (VARIANT value);
// VB6: Sub onmousedown (ByVal value As Any)
[DispId(-2147412110)]
set;
}
/// <summary><para><c>onmousemove</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onmousemove</c> property was the following: <c>VARIANT onmousemove</c>;</para></remarks>
// IDL: VARIANT onmousemove;
// VB6: onmousemove As Any
object onmousemove
{
// IDL: HRESULT onmousemove ([out, retval] VARIANT* ReturnValue);
// VB6: Function onmousemove As Any
[DispId(-2147412108)]
get;
// IDL: HRESULT onmousemove (VARIANT value);
// VB6: Sub onmousemove (ByVal value As Any)
[DispId(-2147412108)]
set;
}
/// <summary><para><c>onmouseout</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onmouseout</c> property was the following: <c>VARIANT onmouseout</c>;</para></remarks>
// IDL: VARIANT onmouseout;
// VB6: onmouseout As Any
object onmouseout
{
// IDL: HRESULT onmouseout ([out, retval] VARIANT* ReturnValue);
// VB6: Function onmouseout As Any
[DispId(-2147412111)]
get;
// IDL: HRESULT onmouseout (VARIANT value);
// VB6: Sub onmouseout (ByVal value As Any)
[DispId(-2147412111)]
set;
}
/// <summary><para><c>onmouseover</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onmouseover</c> property was the following: <c>VARIANT onmouseover</c>;</para></remarks>
// IDL: VARIANT onmouseover;
// VB6: onmouseover As Any
object onmouseover
{
// IDL: HRESULT onmouseover ([out, retval] VARIANT* ReturnValue);
// VB6: Function onmouseover As Any
[DispId(-2147412112)]
get;
// IDL: HRESULT onmouseover (VARIANT value);
// VB6: Sub onmouseover (ByVal value As Any)
[DispId(-2147412112)]
set;
}
/// <summary><para><c>onmouseup</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onmouseup</c> property was the following: <c>VARIANT onmouseup</c>;</para></remarks>
// IDL: VARIANT onmouseup;
// VB6: onmouseup As Any
object onmouseup
{
// IDL: HRESULT onmouseup ([out, retval] VARIANT* ReturnValue);
// VB6: Function onmouseup As Any
[DispId(-2147412109)]
get;
// IDL: HRESULT onmouseup (VARIANT value);
// VB6: Sub onmouseup (ByVal value As Any)
[DispId(-2147412109)]
set;
}
/// <summary><para><c>onrowenter</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onrowenter</c> property was the following: <c>VARIANT onrowenter</c>;</para></remarks>
// IDL: VARIANT onrowenter;
// VB6: onrowenter As Any
object onrowenter
{
// IDL: HRESULT onrowenter ([out, retval] VARIANT* ReturnValue);
// VB6: Function onrowenter As Any
[DispId(-2147412093)]
get;
// IDL: HRESULT onrowenter (VARIANT value);
// VB6: Sub onrowenter (ByVal value As Any)
[DispId(-2147412093)]
set;
}
/// <summary><para><c>onrowexit</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onrowexit</c> property was the following: <c>VARIANT onrowexit</c>;</para></remarks>
// IDL: VARIANT onrowexit;
// VB6: onrowexit As Any
object onrowexit
{
// IDL: HRESULT onrowexit ([out, retval] VARIANT* ReturnValue);
// VB6: Function onrowexit As Any
[DispId(-2147412094)]
get;
// IDL: HRESULT onrowexit (VARIANT value);
// VB6: Sub onrowexit (ByVal value As Any)
[DispId(-2147412094)]
set;
}
/// <summary><para><c>onselectstart</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>onselectstart</c> property was the following: <c>VARIANT onselectstart</c>;</para></remarks>
// IDL: VARIANT onselectstart;
// VB6: onselectstart As Any
object onselectstart
{
// IDL: HRESULT onselectstart ([out, retval] VARIANT* ReturnValue);
// VB6: Function onselectstart As Any
[DispId(-2147412075)]
get;
// IDL: HRESULT onselectstart (VARIANT value);
// VB6: Sub onselectstart (ByVal value As Any)
[DispId(-2147412075)]
set;
}
/// <summary><para><c>outerHTML</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>outerHTML</c> property was the following: <c>BSTR outerHTML</c>;</para></remarks>
// IDL: BSTR outerHTML;
// VB6: outerHTML As String
string outerHTML
{
// IDL: HRESULT outerHTML ([out, retval] BSTR* ReturnValue);
// VB6: Function outerHTML As String
[DispId(-2147417084)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT outerHTML (BSTR value);
// VB6: Sub outerHTML (ByVal value As String)
[DispId(-2147417084)]
set;
}
/// <summary><para><c>outerText</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>outerText</c> property was the following: <c>BSTR outerText</c>;</para></remarks>
// IDL: BSTR outerText;
// VB6: outerText As String
string outerText
{
// IDL: HRESULT outerText ([out, retval] BSTR* ReturnValue);
// VB6: Function outerText As String
[DispId(-2147417083)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT outerText (BSTR value);
// VB6: Sub outerText (ByVal value As String)
[DispId(-2147417083)]
set;
}
/// <summary><para><c>parentElement</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>parentElement</c> property was the following: <c>IHTMLElement* parentElement</c>;</para></remarks>
// IDL: IHTMLElement* parentElement;
// VB6: parentElement As IHTMLElement
IHTMLElement parentElement
{
// IDL: HRESULT parentElement ([out, retval] IHTMLElement** ReturnValue);
// VB6: Function parentElement As IHTMLElement
[DispId(-2147418104)]
get;
}
/// <summary><para><c>parentTextEdit</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>parentTextEdit</c> property was the following: <c>IHTMLElement* parentTextEdit</c>;</para></remarks>
// IDL: IHTMLElement* parentTextEdit;
// VB6: parentTextEdit As IHTMLElement
IHTMLElement parentTextEdit
{
// IDL: HRESULT parentTextEdit ([out, retval] IHTMLElement** ReturnValue);
// VB6: Function parentTextEdit As IHTMLElement
[DispId(-2147417080)]
get;
}
/// <summary><para><c>recordNumber</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>recordNumber</c> property was the following: <c>VARIANT recordNumber</c>;</para></remarks>
// IDL: VARIANT recordNumber;
// VB6: recordNumber As Any
object recordNumber
{
// IDL: HRESULT recordNumber ([out, retval] VARIANT* ReturnValue);
// VB6: Function recordNumber As Any
[DispId(-2147417087)]
get;
}
/// <summary><para><c>sourceIndex</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>sourceIndex</c> property was the following: <c>long sourceIndex</c>;</para></remarks>
// IDL: long sourceIndex;
// VB6: sourceIndex As Long
int sourceIndex
{
// IDL: HRESULT sourceIndex ([out, retval] long* ReturnValue);
// VB6: Function sourceIndex As Long
[DispId(-2147417088)]
get;
}
/// <summary><para><c>style</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>style</c> property was the following: <c>IHTMLStyle* style</c>;</para></remarks>
// IDL: IHTMLStyle* style;
// VB6: style As IHTMLStyle
IHTMLStyle style
{
// IDL: HRESULT style ([out, retval] IHTMLStyle** ReturnValue);
// VB6: Function style As IHTMLStyle
[DispId(-2147418038)]
get;
}
/// <summary><para><c>tagName</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>tagName</c> property was the following: <c>BSTR tagName</c>;</para></remarks>
// IDL: BSTR tagName;
// VB6: tagName As String
string tagName
{
// IDL: HRESULT tagName ([out, retval] BSTR* ReturnValue);
// VB6: Function tagName As String
[DispId(-2147417108)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
}
/// <summary><para><c>title</c> property of <c>IHTMLElement</c> interface.</para></summary>
/// <remarks><para>An original IDL definition of <c>title</c> property was the following: <c>BSTR title</c>;</para></remarks>
// IDL: BSTR title;
// VB6: title As String
string title
{
// IDL: HRESULT title ([out, retval] BSTR* ReturnValue);
// VB6: Function title As String
[DispId(-2147418043)]
[return: MarshalAs(UnmanagedType.BStr)]
get;
// IDL: HRESULT title (BSTR value);
// VB6: Sub title (ByVal value As String)
[DispId(-2147418043)]
set;
}
}
}

View File

@ -0,0 +1,65 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.Interfaces
{
[ComVisible(true), ComImport()]
[TypeLibType((short)4160)] //TypeLibTypeFlags.FDispatchable
[InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIDispatch)]
[Guid("3050f32d-98b5-11cf-bb82-00aa00bdce0b")]
public interface IHTMLEventObj
{
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_SRCELEMENT)]
IHTMLElement SrcElement { [return: MarshalAs(UnmanagedType.Interface)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_ALTKEY)]
bool AltKey { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_CTRLKEY)]
bool CtrlKey { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_SHIFTKEY)]
bool ShiftKey { get; }
//VARIANT
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_RETURNVALUE)]
Object ReturnValue { set; get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_CANCELBUBBLE)]
bool CancelBubble { set; [return: MarshalAs(UnmanagedType.VariantBool)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_FROMELEMENT)]
IHTMLElement FromElement { [return: MarshalAs(UnmanagedType.Interface)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_TOELEMENT)]
IHTMLElement ToElement { [return: MarshalAs(UnmanagedType.Interface)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_KEYCODE)]
int keyCode { set; get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_BUTTON)]
int Button { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_TYPE)]
string EventType { [return: MarshalAs(UnmanagedType.BStr)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_QUALIFIER)]
string Qualifier { [return: MarshalAs(UnmanagedType.BStr)] get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_REASON)]
int Reason { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_X)]
int X { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_Y)]
int Y { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_CLIENTX)]
int ClientX { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_CLIENTY)]
int ClientY { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_OFFSETX)]
int OffsetX { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_OFFSETY)]
int OffsetY { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_SCREENX)]
int ScreenX { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_SCREENY)]
int ScreenY { get; }
[DispId(HTMLDispIDs.DISPID_IHTMLEVENTOBJ_SRCFILTER)]
object SrcFilter { [return: MarshalAs(UnmanagedType.IDispatch)] get; }
}
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,310 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices.ComTypes;
using System.Threading;
using System.Windows.Forms;
using Speak.Core;
using Speak.Interfaces;
using Speak.Sites;
using Speak.Utils;
namespace Speak.Interop
{
internal class IEHandler : Invokable, IMessageProcessor
{
private string documentBody;
private IHTMLDocument2 doc;
private IntPtr wHandle;
private static Guid IID_IHTMLDocument = new Guid("626FC520-A41E-11CF-A731-00A0C9082637");
private static Guid IID_HTMLDocumentEvents2 = typeof(HTMLDocumentEvents2).GUID;
private int cookie = -1;
private IConnectionPoint connPoint;
private IConnectionPointContainer connPointContainer;
private Handler handler;
private const int MAX_UPDATETIME_WAITING = 1500; // 1.5 секунды
private bool inUpdate;
private bool jsExists;
private bool doBrake;
private Settings settings;
private AvatarProcessor ap;
private ISite site;
public IEHandler(ISite site, IntPtr wHandle) : base (wHandle)
{
jsExists = true;
inUpdate = true;
this.site = site;
settings = Settings.Instance;
this.wHandle = wHandle;
documentBody = String.Empty;
doc = IEDocumentFromHandle(this.wHandle);
handler = new Handler(this);
connPointContainer = (IConnectionPointContainer)doc;
connPointContainer.FindConnectionPoint(ref IID_HTMLDocumentEvents2, out connPoint);
connPoint.Advise(handler, out cookie);
//script = (HTMLWindow2Class)doc.Script;
//scriptWindow = typeof (HTMLWindow2Class);
try
{
// По-хорошему, это надо бы в OnDownloadComplete, но мне лень. :)
object joinedString = doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInit();" });
if (Settings.Instance.ShowAvatars)
InsertAvatars(joinedString.ToString());
//doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInit();" });
}
catch(Exception ex)
{
jsExists = false;
MessageBox.Show(
"Cant find javascript:jInit() function." + Environment.NewLine +
"Have you edit IEView template file?" + Environment.NewLine + Environment.NewLine +
ex.Message,
"[xJuick] JavaScript init error",
MessageBoxButtons.OK,
MessageBoxIcon.Error);
}
documentBody = doc.body.innerHTML;
}
private void InsertAvatars(string unsplittedUsers)
{
if (String.IsNullOrEmpty(unsplittedUsers))
return;
ap = new AvatarProcessor(site);
string[] users = unsplittedUsers.Split('#');
List<KeyValuePair<string, string>> avatars = new List<KeyValuePair<string, string>>();
for (int i = 0, iCount = users.Length; i < iCount; i++)
{
string avatarPath = ap.GetUserAvatar(users[i].Substring(1), AvatarCallBack);
if (!String.IsNullOrEmpty(avatarPath))
{
avatars.Add(new KeyValuePair<string, string>(users[i], avatarPath.Replace('\\', '/')));
}
}
for (int i = 0, iCount = avatars.Count; i < iCount; i++)
{
try
{
doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInsertAvatar('" + avatars[i].Key + "', '" + avatars[i].Value + "');" });
}
catch { }
}
if (avatars.Count != users.Length)
ap.Process();
}
private delegate void UpdateAvatar(string userName, string avatarPath);
private void PerformAvatarCallBack(string userName, string avatarPath)
{
try
{
doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInsertAvatar('@" + userName + "', '" + avatarPath + "');" });
}
catch { }
}
private void AvatarCallBack(string userName, string avatarPath)
{
avatarPath = avatarPath.Replace('\\', '/');
if (InvokeRequired)
{
UpdateAvatar d = PerformAvatarCallBack;
Invoke(d, new object[] { userName, avatarPath });
}
else
{
PerformAvatarCallBack(userName, avatarPath);
}
}
public bool FoundIEView
{
get { return doc != null; }
}
private delegate void UpdateChecker();
public void Update()
{
inUpdate = !inUpdate;
if (inUpdate)
return;
if (!jsExists)
return;
// Мда... Вы этого не видели :)
// Нет. Не надо смотреть на этот апдейт. :)
documentBody = doc.body.innerHTML;
UpdateChecker updater = InfinityLoop;
updater.BeginInvoke(UpdateCallback, updater);
}
public void SettingsChanged()
{
}
public void ShowThreads()
{
}
public void Avatars()
{
// not implemented :)
}
private delegate void UpdatePerformer();
private void PerformUpdate()
{
try
{
object joinedString = doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInit();" });
if (Settings.Instance.ShowAvatars)
InsertAvatars(joinedString.ToString());
}
catch { }
}
private void UpdateCallback(IAsyncResult result)
{
UpdateChecker flusher = (UpdateChecker)result.AsyncState;
flusher.EndInvoke(result);
if (doBrake)
return;
if (InvokeRequired)
{
UpdatePerformer d = PerformUpdate;
Invoke(d, null);
return;
}
try
{
doc.Script.GetType().InvokeMember("eval", System.Reflection.BindingFlags.InvokeMethod, null, doc.Script, new object[] { "jInit();" });
}
catch { }
}
private void InfinityLoop()
{
int currentTime = 0;
while (true)
{
if (doBrake)
return;
// Ещё вариант: if (doc.containsElementWithID("jText")) { .. }
// ...но опасно :)
if (settings.FastIEView && !documentBody.Equals(doc.body.innerHTML, StringComparison.InvariantCultureIgnoreCase))
{
documentBody = doc.body.innerHTML;
return;
}
Thread.Sleep(100);
currentTime += 100;
// well... не дождались апдейта
if (currentTime >= MAX_UPDATETIME_WAITING)
return;
}
}
private static IHTMLDocument2 IEDocumentFromHandle(IntPtr hWnd)
{
IHTMLDocument2 document = null;
int lRes;
if (WinApi.WM_HTML_GETOBJECT != 0)
{
WinApi.SendMessageTimeout(hWnd, WinApi.WM_HTML_GETOBJECT, 0, 0, WinApi.SMTO_ABORTIFHUNG, 1000, out lRes);
if (!(lRes == 0))
{
Guid iid = IID_IHTMLDocument;
WinApi.ObjectFromLresult(lRes, ref iid, 0, ref document);
}
}
return document;
}
public event EventHandler<ActionClickEvent> JuickClicked;
public void InvokeJuick(string action, bool autoSend)
{
if (JuickClicked == null)
return;
JuickClicked(this, new ActionClickEvent(action, autoSend));
}
~IEHandler()
{
}
#region Implementation of IDisposable
public void Dispose()
{
doBrake = true;
if (cookie != -1)
{
connPoint.Unadvise(cookie);
}
cookie = -1;
handler = null;
}
#endregion
}
internal class Handler : HTMLDocumentEvents2
{
private IEHandler parent;
public Handler(IEHandler parent)
{
this.parent = parent;
}
public bool onclick(IHTMLEventObj pEvtObj)
{
IHTMLElement el = pEvtObj.SrcElement;
if (!el.tagName.Equals("DIV", StringComparison.InvariantCultureIgnoreCase))
return false;
string action = el.getAttribute("action", 0).ToString();
if (String.IsNullOrEmpty(action))
return false;
string autoSendStr = el.getAttribute("autosend", 0).ToString();
bool autoSend = autoSendStr.Equals("1") ||
autoSendStr.Equals("true", StringComparison.CurrentCultureIgnoreCase);
pEvtObj.ReturnValue = false;
pEvtObj.CancelBubble = true;
parent.InvokeJuick(action, autoSend);
return false;
}
}
}

View File

@ -0,0 +1,84 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.Interop
{
[StructLayout(LayoutKind.Sequential)]
public struct COLORREF
{
public uint ColorDWORD;
public COLORREF(System.Drawing.Color color)
{
ColorDWORD = (uint)color.R + (((uint)color.G) << 8) + (((uint)color.B) << 16);
}
public System.Drawing.Color GetColor()
{
return System.Drawing.Color.FromArgb((int)(0x000000FFU & ColorDWORD),
(int)(0x0000FF00U & ColorDWORD) >> 8, (int)(0x00FF0000U & ColorDWORD) >> 16);
}
public void SetColor(System.Drawing.Color color)
{
ColorDWORD = (uint)color.R + (((uint)color.G) << 8) + (((uint)color.B) << 16);
}
}
[StructLayout(LayoutKind.Sequential)]
public struct RECT
{
public int Left;
public int Top;
public int Right;
public int Bottom;
public RECT(int left, int top, int right, int bottom)
{
Left = left;
Top = top;
Right = right;
Bottom = bottom;
}
public static RECT Empty
{
get { return new RECT(0,0,0,0); }
}
public bool IsEmpty
{
get { return (Left == Right) && (Top == Bottom) && (Right == Top) && (Bottom == 0); }
}
public bool Equals(RECT rect)
{
return Top == rect.Top && Bottom == rect.Bottom && Left == rect.Left && Right == rect.Right;
}
}
[StructLayout(LayoutKind.Sequential)]
public struct POINT
{
public int X;
public int Y;
public POINT(int x, int y)
{
this.X = x;
this.Y = y;
}
public static implicit operator System.Drawing.Point(POINT p)
{
return new System.Drawing.Point(p.X, p.Y);
}
public static implicit operator POINT(System.Drawing.Point p)
{
return new POINT(p.X, p.Y);
}
}
}

View File

@ -0,0 +1,71 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.Interop
{
public class Subclassing : IDisposable
{
private const int GWL_WNDPROC = -4;
[DllImport("user32", SetLastError = true)]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex, Win32WndProc newProc);
[DllImport("user32", SetLastError = true)]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex, IntPtr newProc);
[DllImport("user32")]
private static extern int CallWindowProc(IntPtr lpPrevWndFunc, IntPtr hWnd, int Msg, int wParam, int lParam);
[DllImport("kernel32.dll")]
public static extern void SetLastError(uint dwErrCode);
private IntPtr wHandle;
private Win32WndProc wProc;
private IntPtr oldWndProc = IntPtr.Zero;
public Subclassing(IntPtr wHandle)
{
this.wHandle = wHandle;
}
public int StartSubclassing(Win32WndProc newWindowProc)
{
wProc = newWindowProc;
SetLastError(0);
if (oldWndProc != IntPtr.Zero)
SetWindowLong(wHandle, GWL_WNDPROC, wProc);
else
oldWndProc = SetWindowLong(wHandle, GWL_WNDPROC, wProc);
return Marshal.GetLastWin32Error();
}
public int CallParent(IntPtr hWnd, int Msg, int wParam, int lParam)
{
if (Msg == 0x02 || Msg == 0x10)
{
StopSubclass();
}
return CallWindowProc(oldWndProc, hWnd, Msg, wParam, lParam);
}
public void StopSubclass()
{
if (wHandle != IntPtr.Zero && oldWndProc != IntPtr.Zero)
{
SetWindowLong(wHandle, GWL_WNDPROC, oldWndProc);
wHandle = IntPtr.Zero;
wProc = null;
}
}
#region Implementation of IDisposable
public void Dispose()
{
StopSubclass();
}
#endregion
}
public delegate int Win32WndProc(IntPtr hWnd, int Msg, int wParam, int lParam);
}

View File

@ -0,0 +1,356 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
using Speak.Interfaces;
using Speak.RichEdit;
namespace Speak.Interop
{
internal class WinApi
{
public static int SMTO_ABORTIFHUNG = 0x2;
public static int WM_HTML_GETOBJECT = RegisterWindowMessage("WM_HTML_GETOBJECT");
public const int WM_USER = 0x0400;
public static int GWL_STYLE = -16;
public const int NM_CLICK = -2;
public const int WM_HSCROLL = -16;
public static IntPtr HWND_DESKTOP = IntPtr.Zero;
public const Int32 PSM_CHANGED = WM_USER + 104;
public const Int32 PSN_APPLY = ((0 - 200) - 2);
public const Int32 MK_CONTROL = 0x8;
public const int WM_MOUSEMOVE = 0x200;
public const int WM_LBUTTONDOWN = 0x201;
public const int WM_LBUTTONUP = 0x202;
public const int WM_RBUTTONDOWN = 0x204;
public const int WM_RBUTTONUP = 0x205;
public const int WM_MBUTTONDOWN = 0x207;
public const int WM_MBUTTONUP = 0x208;
public const int WM_LBUTTONDBLCLK = 0x203;
public const int WM_MBUTTONDBLCLK = 0x209;
public const int WM_RBUTTONDBLCLK = 0x206;
public const int WM_KEYUP = 0x101;
public const int WM_KEYDOWN = 0x100;
public const int WM_SYSKEYDOWN = 0x104;
public const int UM_CHECKSTATECHANGE = WM_USER + 100;
public const int WM_VSCROLL = 0x115;
public const int WM_UPDATE = 0x401;
public const int WM_RESIZE = 0x0085;
public const int WM_PAINT = 0x0F;
public const int WM_SETTEXT = 0xC;
public const int WM_NOTIFY = 0x4E;
public const int WM_GETTEXT = 13;
public const int WM_GETTEXTLENGTH = 14;
public const int WM_INITDIALOG = 0x0110;
public const int WM_COMMAND = 0x0111;
public const int WM_SETFOCUS = 0x0007;
public const int WM_DESTROY = 0x2;
public const int BM_GETCHECK = 0x00F0;
public const int BM_SETCHECK = 0x00F1;
public const int BST_UNCHECKED = 0;
public const int BST_CHECKED = 1;
public const int BST_INDETERMINATE = 2;
public const int BST_PUSHED = 4;
public const int BST_FOCUS = 8;
public const int CB_ADDSTRING = 0x0143;
public const int CB_SETCURSEL = 0x014E;
public const int CB_GETCURSEL = 0x0147;
public const int CB_GETLBTEXT = 0x0148;
public const int CB_SELECTSTRING = 0x014D;
public const int CB_GETLBTEXTLEN = 0x0149;
public const int CB_RESETCONTENT = 0x014B;
public const int CBN_SELCHANGE = 1;
public const int LVM_FIRST = 0x1000;
public const int LVM_INSERTITEM = LVM_FIRST + 7;
public const int LVIF_TEXT = 0x0001;
public const int LVIF_IMAGE = 0x0002;
public const int LVIF_PARAM = 0x0004;
public const int LVIF_INDENT = 0x0010;
public const int ILC_MASK = 0x0001;
public const int ILC_COLOR32 = 0x0020;
public const int BN_CLICKED = 0;
public const int EN_CHANGE = 0x300;
public const int STM_SETICON = 368;
public const uint ILD_NORMAL = 0;
public const int COLOR_WINDOW = 5; //http://msdn.microsoft.com/en-us/library/windows/desktop/ms724371(v=vs.85).aspx
public const int COLOR_WINDOWTEXT = 8;
public const int TBM_SETRANGE = WM_USER + 6;
public const int TBM_SETPOS = WM_USER + 5;
public const int TBM_GETPOS = WM_USER;
[DllImport("user32.dll")]
public static extern int GetSysColor(int XAmount);
[DllImport("user32.dll")]
public static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, Int32 Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, Int32 Msg, Int32 wParam, Int32 lParam);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, Int32 Msg, Int64 wParam, Int64 lParam);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, Int32 Msg, Int32 wParam, IntPtr lParam);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, Int32 Msg, Int32 wParam, ref POINTL lParam);
[DllImport("user32.dll", EntryPoint = "SendMessageA", /*CharSet = CharSet.Auto, */SetLastError = true)]
public static extern int SendMessageA(IntPtr hwnd, int msg, int wParam, IntPtr lParam);
[return: MarshalAs(UnmanagedType.Bool)]
[DllImport("user32.dll", SetLastError = true)]
public static extern bool PostMessage(IntPtr hWnd, UInt32 Msg, Int32 wParam, Int32 lParam);
[return: MarshalAs(UnmanagedType.Bool)]
[DllImport("user32.dll", SetLastError = true)]
public static extern bool PostMessage(IntPtr hWnd, UInt32 Msg, Int32 wParam, IntPtr lParam);
[DllImport("user32.dll")]
public static extern bool ScrollWindow(IntPtr hWnd, int XAmount, int YAmount, IntPtr lpRect, IntPtr wpRect);
[DllImport("user32.dll")]
public static extern bool DestroyIcon(int hIcon);
[DllImport("comctl32.dll")]
public static extern bool ImageList_Destroy(int himl);
[DllImport("user32.dll", SetLastError = true, CharSet = CharSet.Auto)]
public static extern int GetClassName(IntPtr hWnd, StringBuilder lpClassName, int nMaxCount);
[DllImport("user32.dll", EntryPoint = "SendMessageTimeoutA")]
public static extern int SendMessageTimeout(IntPtr hwnd, int msg, int wParam, int lParam, int fuFlags, int uTimeout, out int lpdwResult);
[DllImport("user32.dll", SetLastError = true)]
public static extern int GetWindowLong(IntPtr hWnd, int nIndex);
[DllImport("OLEACC.dll")]
public static extern int ObjectFromLresult(int lResult, ref Guid riid, int wParam, ref IHTMLDocument2 ppvObject);
[DllImport("user32.dll", EntryPoint = "RegisterWindowMessageA")]
public static extern int RegisterWindowMessage(string lpString);
[DllImport("user32.dll")]
public static extern bool ClientToScreen(IntPtr hwnd, ref POINT lpPoint);
[DllImport("user32.dll")]
public static extern bool ScreenToClient(IntPtr hwnd, ref POINT lpPoint);
[DllImport("user32.dll")]
public static extern IntPtr GetDlgItem(IntPtr hDlg, int nIDDlgItem);
[DllImport("user32.dll")]
public static extern Int32 SendDlgItemMessage(IntPtr hDlg, int nIDDlgItem, uint Msg, Int32 wParam, Int32 lParam);
[DllImport("user32.dll")]
public static extern Int32 SendDlgItemMessage(IntPtr hDlg, int nIDDlgItem, uint Msg, Int32 wParam, IntPtr lParam);
[DllImport("user32.dll")]
public static extern bool EnableWindow(IntPtr hWnd, bool bEnable);
[DllImport("user32.dll")]
public static extern bool ShowWindow(IntPtr hWnd, Int32 nCmdShow);
[DllImport("comctl32.dll", SetLastError = true)]
public static extern IntPtr ImageList_Create(int cx, int cy, uint flags, int cInitial, int cGrow);
[DllImport("comctl32.dll", SetLastError = true)]
public static extern Int32 ImageList_ReplaceIcon(IntPtr imageList, Int32 iconIndex, IntPtr hIcon);
[DllImport("comctl32.dll", SetLastError = true)]
public static extern Int32 ImageList_GetIcon(IntPtr imageList, Int32 iconIndex, uint flags);
[DllImport("user32.dll")]
public static extern uint GetMessagePos();
[DllImport("user32.dll")]
public static extern Int32 GetFocus();
[DllImport("user32.dll")]
public static extern Int32 SetFocus(IntPtr hWnd);
[DllImport("user32.dll")]
public static extern IntPtr GetParent(IntPtr hWnd);
[DllImport("user32.dll", SetLastError = true)]
public static extern int MapWindowPoints(IntPtr hwndFrom, IntPtr hwndTo, ref POINT lpPoints, [MarshalAs(UnmanagedType.U4)] int cPoints);
[DllImport("kernel32", CharSet = CharSet.Ansi, ExactSpelling = true, SetLastError = true)]
public static extern IntPtr GetProcAddress(IntPtr hModule, string procName);
[DllImport("user32")]
[return: MarshalAs(UnmanagedType.Bool)]
public static extern bool EnumChildWindows(IntPtr window, EnumWindowProc callback, IntPtr i);
public delegate bool EnumWindowProc(IntPtr hWnd, IntPtr parameter);
public static IntPtr MakeLParam(int wLow, int wHigh)
{
return (IntPtr)(((short)wHigh << 16) | (wLow & 0xffff));
}
public static List<IntPtr> GetChildWindows(IntPtr parent)
{
List<IntPtr> result = new List<IntPtr>();
GCHandle listHandle = GCHandle.Alloc(result);
try
{
EnumWindowProc childProc = EnumWindow;
EnumChildWindows(parent, childProc, GCHandle.ToIntPtr(listHandle));
}
finally
{
if (listHandle.IsAllocated)
listHandle.Free();
}
return result;
}
public static string GetWindowName(IntPtr window)
{
StringBuilder className = new StringBuilder(100);
GetClassName(window, className, className.Capacity);
return className.ToString();
}
private static bool EnumWindow(IntPtr handle, IntPtr pointer)
{
GCHandle gch = GCHandle.FromIntPtr(pointer);
List<IntPtr> list = gch.Target as List<IntPtr>;
if (list == null)
{
throw new InvalidCastException("GCHandle Target could not be cast as List<IntPtr>");
}
list.Add(handle);
// You can modify this to check to see if you want to cancel the operation, then return a null here
return true;
}
public static IntPtr GetLogWindow(IntPtr parent, string className)
{
List<IntPtr> childs = GetChildWindows(parent);
for (int i = 0, iCount = childs.Count; i < iCount; i++)
{
#if DEBUG
System.Diagnostics.Debug.WriteLine("[" + childs[i].ToString("X") + "] " + GetWindowName(childs[i]));
#endif
if (GetWindowName(childs[i]).StartsWith(className))
return childs[i];
}
return IntPtr.Zero;
}
// sciver 2.8.1.1+ fix
public static IntPtr GetLogWindowByStyles(IntPtr parent, string className)
{
List<IntPtr> childs = GetChildWindows(parent);
for (int i = 0, iCount = childs.Count; i < iCount; i++)
{
if (GetWindowName(childs[i]).StartsWith(className))
{
Int32 exStyles = GetWindowLong(childs[i], GWL_STYLE);
if (exStyles != 0 && ((exStyles & REConstants.ES_READONLY) != 0) && ((exStyles & REConstants.ES_AUTOVSCROLL) != 0))
return childs[i];
}
}
return IntPtr.Zero;
}
}
[StructLayout(LayoutKind.Sequential)]
public struct NMHDR
{
public IntPtr handleFrom;
public Int32 idFrom;
public Int32 code;
}
public struct WindowShowStyle
{
/// <summary>Hides the window and activates another window.</summary>
public const Int32 SW_HIDE = 0;
/// <summary>Activates and displays a window. If the window is minimized
/// or maximized, the system restores it to its original size and
/// position. An application should specify this flag when displaying
/// the window for the first time.</summary>
public const Int32 SW_SHOWNORMAL = 1;
/// <summary>Activates the window and displays it as a minimized window.</summary>
public const Int32 SW_SHOWMINIMIZED = 2;
/// <summary>Activates the window and displays it as a maximized window.</summary>
public const Int32 SW_SHOWMAXIMIZED = 3;
/// <summary>Maximizes the specified window.</summary>
public const Int32 SW_MAXIMIZE = 3;
/// <summary>Displays a window in its most recent size and position.
/// This value is similar to "ShowNormal", except the window is not
/// actived.</summary>
public const Int32 SW_SHOWNOACTIVATE = 4;
/// <summary>Activates the window and displays it in its current size
/// and position.</summary>
public const Int32 SW_SHOW = 5;
/// <summary>Minimizes the specified window and activates the next
/// top-level window in the Z order.</summary>
public const Int32 SW_MINIMIZE = 6;
/// <summary>Displays the window as a minimized window. This value is
/// similar to "ShowMinimized", except the window is not activated.</summary>
public const Int32 SW_SHOWMINNOACTIVE = 7;
/// <summary>Displays the window in its current size and position. This
/// value is similar to "Show", except the window is not activated.</summary>
public const Int32 SW_SHOWNA = 8;
/// <summary>Activates and displays the window. If the window is
/// minimized or maximized, the system restores it to its original size
/// and position. An application should specify this flag when restoring
/// a minimized window.</summary>
public const Int32 SW_RESTORE = 9;
/// <summary>Sets the show state based on the SW_ value specified in the
/// STARTUPINFO structure passed to the CreateProcess function by the
/// program that started the application.</summary>
/// <remarks>See SW_SHOWDEFAULT</remarks>
public const Int32 ShowDefault = 10;
/// <summary>Windows 2000/XP: Minimizes a window, even if the thread
/// that owns the window is hung. This flag should only be used when
/// minimizing windows from a different thread.</summary>
public const Int32 SW_FORCEMINIMIZE = 11;
}
[ComImport]
[Guid("6d5140c1-7436-11ce-8034-00aa006009fa")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
interface IServiceProvider
{
void QueryService(ref Guid guidService, ref Guid riid, [MarshalAs(UnmanagedType.Interface)] out object ppvObject);
}
}

230
Speak/Speak/MainClass.cs Normal file
View File

@ -0,0 +1,230 @@
using System;
using System.Collections.Generic;
using System.Text;
using Virtuoso.Miranda.Plugins;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Hyphen.Mini;
using Virtuoso.Hyphen.Mini.Custom;
using Virtuoso.Miranda.Plugins.ThirdParty.Updater;
using System.Windows.Forms;
using Speak;
using Speak.Opt;
using Speak.Storage;
using Speak.TTS;
using Speak.Structs;
[assembly: ExposingPlugin(typeof(MainClass))]
namespace Speak
{
/// <summary>
/// MainClass of Speak
/// </summary>
public class MainClass : StandalonePlugin
{
private Options option;
private MainClass()
{
this.option = new Options();
this.option.Changed += new Options.ChangedEventHandler(option_hasUpdated);
}
/// <summary>
/// Run after the Plugin Initialisation
/// </summary>
protected override void AfterPluginInitialization()
{
option_hasUpdated(Options.EventChanged.Active);
option_hasUpdated(Options.EventChanged.Announce);
option_hasUpdated(Options.EventChanged.Engine);
RegisterUpdate();
EventManager.CreateEventHook(API.ME_OPT_INITIALISE, this.option.Opts, this);
EventManager.CreateEventHook(API.ME_DB_EVENT_ADDED, Message, this);
EventManager.CreateEventHook(API.ME_DB_CONTACT_SETTINGCHANGED, StatusChange, this);
SpeakWelcome();
}
protected override void BeforePluginDisable()
{
EventManager.RemoveEventHook(API.ME_OPT_INITIALISE, this);
EventManager.RemoveEventHook(API.ME_DB_EVENT_ADDED, this);
EventManager.RemoveEventHook(API.ME_DB_CONTACT_SETTINGCHANGED, this);
TextToSpeak.getInstance().Stop();
}
private int Message(UIntPtr wParam, IntPtr lParam)
{
DatabaseEventInfo d = DatabaseEventInfo.FromHandle(lParam);
if (d.Type == DatabaseEventType.Message && !((d.Flags & DatabaseEventProperties.Sent) == DatabaseEventProperties.Sent))
{
ContactInfo c = ContactInfo.FromHandle(d.GetContactHandle());
Settings s = Settings.getInstance();
if (s.canMessageRead(d.Data, c.UniqueID.ToString()))
{
TextToSpeak tts = TextToSpeak.getInstance();
string text = String.Format(s.getSpeakString(), c.DisplayName, d.Data);
string sig = text + d.Timestamp;
//MessageBox.Show(sig);
tts.speak(text, sig);
}
}
return 0;
}
private int StatusChange(UIntPtr wParam, IntPtr lParam)
{
ContactInfo c = ContactInfo.FromHandle(wParam);
if (c.UniqueID == null) //Unknown User (maybe myself)
{
return 0;
}
Settings s = Settings.getInstance();
if (s.hasChangedStatus(c.UniqueID.ToString(), c.Status.ToString()))
{
if (s.canStatusRead(c.UniqueID.ToString()))
{
TextToSpeak tts = TextToSpeak.getInstance();
string text = String.Format(s.getStatusString(c.Status), c.DisplayName, c.Status.ToString());
tts.speak(text,"");
}
}
return 0;
}
private void option_hasUpdated(Options.EventChanged e)
{
if (e == Options.EventChanged.Engine)
{
TextToSpeak tts = TextToSpeak.getInstance();
tts.setVoice(Options.readDBString("engine", "speak_config"));
tts.setVolume(int.Parse(Options.readDBLong("volume", "speak_config").ToString()));
tts.setRate(int.Parse(Options.readDBLong("rate", "speak_config").ToString()));
tts.setPitch(int.Parse(Options.readDBLong("pitch", "speak_config").ToString()));
}
if (e == Options.EventChanged.Active)
{
Settings s = Settings.getInstance();
s.ReadContactList();
}
if (e == Options.EventChanged.Announce)
{
Settings s = Settings.getInstance();
s.SetGlobalSettings();
}
}
private void SpeakWelcome()
{
TextToSpeak tts = TextToSpeak.getInstance();
tts.speak(Options.readDBString("welcome_msg", "speak_config"), "welcome" + DateTime.Now);
}
private void RegisterUpdate()
{
try
{
Update update = new Update(this, new Uri(this.HomePage.ToString() + "files/miranda/speak_last.zip"), new Uri(this.HomePage.ToString() + "files/miranda/speak_updater_version.txt"), " ");
UpdaterPlugin.RegisterForUpdate(update);
}
catch (NotSupportedException) { }
}
#region Constants
/// <summary>
/// Get Version
/// </summary>
private static Version VERSION = new Version(0, 8, 0, 0);
/// <summary>
/// Get Author
/// </summary>
public override string Author
{
get { return "BlubbFish"; }
}
/// <summary>
/// Get Description
/// </summary>
public override string Description
{
get { return ".NET Speak Provider"; }
}
/// <summary>
/// Get HasOptions
/// </summary>
public override bool HasOptions
{
get { return false; }
}
/// <summary>
/// Get Hompage
/// </summary>
public override Uri HomePage
{
get { return new Uri("http://dev.blubbfish.net"); }
}
/// <summary>
/// Get Name
/// </summary>
public override string Name
{
get { return "Speak"; }
}
/// <summary>
/// Get Version
/// </summary>
public override Version Version
{
get { return VERSION; }
}
/// <summary>
/// Get AutorEmail
/// </summary>
public override string AuthorEmail
{
get { return "dev@blubbfish.net"; }
}
/// <summary>
/// Get Copyright String
/// </summary>
public override string Copyright
{
get { return "2013 © BlubbFish"; }
}
/// <summary>
/// Get GUID PrluginInterfaces
/// </summary>
public override Guid[] PluginInterfaces
{
get { return new Guid[] { uuid }; }
}
/// <summary>
/// Get ReplaceDefaultModule
/// </summary>
public override int ReplacesDefaultModule
{
get { return 0; }
}
/// <summary>
/// Get GUID
/// </summary>
public override Guid UUID
{
get { return uuid; }
}
private static readonly Guid uuid = new Guid("65BC8980-1028-40A4-A52F-440C48035E02");
#endregion
}
}

967
Speak/Speak/Opt/Options.cs Normal file
View File

@ -0,0 +1,967 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Resources;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using System.Collections.ObjectModel;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
//using xJuick.Core;
//using xJuick.Fork;
using Speak.Interop;
using Speak.Structs;
//using xJuick.UI;
using Speak.Utils;
using Speak.TTS;
//using ISite = xJuick.Sites.ISite;
namespace Speak.Opt
{
internal class Options
{
#region Menu Constants
private const Int32 IDD_SPEAK_OPTIONS_DIALOG = 666;
private const Int32 IDD_ANNOUNCE_OPTIONS_DIALOG = 667;
private const Int32 IDD_ENGINE_OPTIONS_DIALOG = 668;
private const Int32 IDC_SPEAK_LIST = 1079;
private const Int32 IDC_SPEAK_VISIBLEICON = 1204;
private const Int32 IDC_SPEAK_INVISIBLEICON = 1205;
private const Int32 IDI_ANNOUNCE_OFFLINE = 1002;
private const Int32 IDI_ANNOUNCE_ONLINE = 1025;
private const Int32 IDI_ANNOUNCE_AWAY = 1024;
private const Int32 IDI_ANNOUNCE_DND = 1019;
private const Int32 IDI_ANNOUNCE_NA = 1026;
private const Int32 IDI_ANNOUNCE_OCCUPIED = 1027;
private const Int32 IDI_ANNOUNCE_FREEFORCHAT = 1028;
private const Int32 IDI_ANNOUNCE_INVISIBLE = 1029;
private const Int32 IDI_ANNOUNCE_CONNECT = 1030;
private const Int32 IDI_ANNOUNCE_DISCONNECT = 1031;
private const Int32 IDI_ANNOUNCE_SHUTDOWN = 1032;
private const Int32 IDI_ANNOUNCE_ACTIVE = 1033;
private const Int32 IDI_ANNOUNCE_ONOPEN = 1034;
private const Int32 IDI_ANNOUNCE_ONFOCUS = 1035;
private const Int32 IDI_ANNOUNCE_LENGTH = 1011;
private const Int32 IDI_ENGINE_VOICES = 1001;
private const Int32 IDI_ENGINE_VOLUME = 1000;
private const Int32 IDI_ENGINE_RATE = 1002;
private const Int32 IDI_ENGINE_PITCH = 1003;
private const Int32 IDI_ENGINE_WELCOME = 1011;
private const Int32 IDI_ENGINE_TEST = 1006;
#endregion
private bool initset = true;
private Delegate dlgProcSpeak;
private Delegate dlgProcAnnounce;
private Delegate dlgProcEngine;
private int hItemUnkSpeak;
private static Win32ImageList imagelistSpeak;
/// <summary>
/// Enum of the Events
/// </summary>
public enum EventChanged
{
/// <summary>
/// When A Usercontact has Changed
/// </summary>
Active,
/// <summary>
/// When the Global Settings Changed
/// </summary>
Announce,
/// <summary>
/// When the Engine Settings Changed
/// </summary>
Engine,
/// <summary>
/// No Events has Raised
/// </summary>
None
}
/// <summary>
/// Delegate an Event of Changed
/// </summary>
/// <param name="e">Eventtype</param>
public delegate void ChangedEventHandler(EventChanged e);
/// <summary>
/// Raises When Settings was Changed
/// </summary>
public event ChangedEventHandler Changed;
/// <summary>
/// Internal Raising for Event
/// </summary>
/// <param name="e"></param>
protected virtual void OnChanged(EventChanged e)
{
if (Changed != null)
Changed(e);
}
/// <summary>
/// The Option Class that Handles the Optionsdialog
/// </summary>
public Options()
{
initImageLists();
}
private void initImageLists()
{
imagelistSpeak = createImageList(new List<string>() { StandartIcons.SKINICON_OTHER_SMALLDOT, StandartIcons.SKINICON_EVENT_MESSAGE, StandartIcons.ID_STATUS_ONLINE });
}
private Win32ImageList createImageList(List<string> list)
{
list.Sort();
Win32ImageList imageList = new Win32ImageList();
for (int i = 0, iconCount = list.Count; i < iconCount; i++)
{
imageList.AddIcon(list[i], IconTable.GetDefaultIcon(list[i]));
}
return imageList;
}
/// <summary>
/// Here you Can Connect your Options
/// </summary>
/// <param name="wparam">Miranda Handle</param>
/// <param name="lparam"></param>
/// <returns>0</returns>
public int Opts(UIntPtr wparam, IntPtr lparam)
{
initset = !initset;
if (initset)
return 0;
#region Active Status Page
dlgProcSpeak = new Win32WndProc(WndProcSpeak);
OptionsDialogPage odpspeak = new OptionsDialogPage();
odpspeak.szTitle = Marshal.StringToHGlobalAnsi("Active Modes");
odpspeak.cbSize = Marshal.SizeOf(odpspeak);
odpspeak.position = 0;
odpspeak.pszTemplate = new IntPtr((UInt32)((short)IDD_SPEAK_OPTIONS_DIALOG));
odpspeak.pfnDlgProc = Marshal.GetFunctionPointerForDelegate(dlgProcSpeak);
odpspeak.szGroup = Marshal.StringToHGlobalAnsi("Speak");
odpspeak.groupPosition = 100;
odpspeak.hGroupIcon = IntPtr.Zero;
odpspeak.flags = MainConstants.ODPF_BOLDGROUPS;
odpspeak.hInstance = Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0]);
IntPtr cmdPtrSpeak = Marshal.AllocHGlobal(Marshal.SizeOf(odpspeak));
Marshal.StructureToPtr(odpspeak, cmdPtrSpeak, false);
MirandaContext.Current.CallService(API.MS_OPT_ADDPAGE, wparam, cmdPtrSpeak);
#endregion
#region Announce Page
dlgProcAnnounce = new Win32WndProc(WndProcAnnounce);
OptionsDialogPage odpannounce = new OptionsDialogPage();
odpannounce.szTitle = Marshal.StringToHGlobalAnsi("Announce");
odpannounce.cbSize = Marshal.SizeOf(odpannounce);
odpannounce.position = 0;
odpannounce.pszTemplate = new IntPtr((UInt32)((short)IDD_ANNOUNCE_OPTIONS_DIALOG));
odpannounce.pfnDlgProc = Marshal.GetFunctionPointerForDelegate(dlgProcAnnounce);
odpannounce.szGroup = Marshal.StringToHGlobalAnsi("Speak");
odpannounce.groupPosition = 101;
odpannounce.hGroupIcon = IntPtr.Zero;
odpannounce.flags = MainConstants.ODPF_BOLDGROUPS;
odpannounce.hInstance = Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0]);
IntPtr cmdPtrAnnounce = Marshal.AllocHGlobal(Marshal.SizeOf(odpannounce));
Marshal.StructureToPtr(odpannounce, cmdPtrAnnounce, false);
MirandaContext.Current.CallService(API.MS_OPT_ADDPAGE, wparam, cmdPtrAnnounce);
#endregion
#region Engine/Voice Page
dlgProcEngine = new Win32WndProc(WndProcEngine);
OptionsDialogPage odpengine = new OptionsDialogPage();
odpengine.szTitle = Marshal.StringToHGlobalAnsi("Engine/Voice");
odpengine.cbSize = Marshal.SizeOf(odpengine);
odpengine.position = 0;
odpengine.pszTemplate = new IntPtr((UInt32)((short)IDD_ENGINE_OPTIONS_DIALOG));
odpengine.pfnDlgProc = Marshal.GetFunctionPointerForDelegate(dlgProcEngine);
odpengine.szGroup = Marshal.StringToHGlobalAnsi("Speak");
odpengine.groupPosition = 102;
odpengine.hGroupIcon = IntPtr.Zero;
odpengine.flags = MainConstants.ODPF_BOLDGROUPS;
odpengine.hInstance = Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0]);
IntPtr cmdPtrEngine = Marshal.AllocHGlobal(Marshal.SizeOf(odpengine));
Marshal.StructureToPtr(odpengine, cmdPtrEngine, false);
MirandaContext.Current.CallService(API.MS_OPT_ADDPAGE, wparam, cmdPtrEngine);
#endregion
return 0;
}
private int WndProcEngine(IntPtr hWnd, int Msg, int wParam, int lParam)
{
switch (Msg)
{
case WinApi.WM_INITDIALOG:
InitEngine(hWnd);
return 0;
case WinApi.WM_COMMAND:
return ProcessCommandEngine(hWnd, Util.LoWord(wParam), Util.HiWord(wParam), lParam);
case WinApi.WM_NOTIFY:
return NotifyEngine(hWnd, wParam, lParam);
}
return 0;
}
private int NotifyEngine(IntPtr hWnd, int wParam, int lParam)
{
NMHDR lParams;
lParams = (NMHDR)Marshal.PtrToStructure((IntPtr)lParam, typeof(NMHDR));
switch (lParams.idFrom)
{
case IDI_ENGINE_VOLUME:
case IDI_ENGINE_RATE:
case IDI_ENGINE_PITCH:
if (lParams.code == WinApi.WM_HSCROLL)
{
WinApi.SendMessage(WinApi.GetParent(hWnd), WinApi.PSM_CHANGED, 0, 0);
return 0;
}
break;
case 0:
switch (lParams.code)
{
case WinApi.PSN_APPLY:
{
writeDBstring("engine", "speak_config", GetComboText(hWnd, IDI_ENGINE_VOICES));
writeDBlong("volume", "speak_config", (uint)GetSlider(hWnd, IDI_ENGINE_VOLUME));
writeDBlong("rate", "speak_config", (uint)GetSlider(hWnd, IDI_ENGINE_RATE));
writeDBlong("pitch", "speak_config", (uint)GetSlider(hWnd, IDI_ENGINE_PITCH));
writeDBstring("welcome_msg", "speak_config", GetText(hWnd, IDI_ENGINE_WELCOME));
OnChanged(EventChanged.Engine);
return 1;
}
}
break;
}
return 0;
}
private int ProcessCommandEngine(IntPtr hwndDlg, Int16 item, Int16 command, Int32 lParam)
{
switch (item)
{
case IDI_ENGINE_TEST:
{
if (command == WinApi.BN_CLICKED)
{
TextToSpeak s = TextToSpeak.getInstance();
s.setVoice(GetComboText(hwndDlg, IDI_ENGINE_VOICES));
s.setVolume(GetSlider(hwndDlg, IDI_ENGINE_VOLUME));
s.setRate(GetSlider(hwndDlg, IDI_ENGINE_RATE));
s.setPitch(GetSlider(hwndDlg, IDI_ENGINE_PITCH));
s.speak(GetText(hwndDlg, IDI_ENGINE_WELCOME), "test" + GetText(hwndDlg, IDI_ENGINE_WELCOME) + DateTime.Now);
}
}
break;
case IDI_ENGINE_VOICES:
{
if (command == WinApi.CBN_SELCHANGE)
{
WinApi.SendMessage(WinApi.GetParent(hwndDlg), WinApi.PSM_CHANGED, 0, 0);
return 0;
}
}
break;
case IDI_ENGINE_WELCOME:
if (command == WinApi.EN_CHANGE)
{
WinApi.SendMessage(WinApi.GetParent(hwndDlg), WinApi.PSM_CHANGED, 0, 0);
}
return 0;
}
return 0;
}
private int GetSlider(IntPtr hwndDlg, int ID)
{
return (int)WinApi.SendDlgItemMessage(hwndDlg, ID, WinApi.TBM_GETPOS, 0, 0);
}
private string GetComboText(IntPtr hWnd, Int32 ID)
{
int nIndex = WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_GETCURSEL, 0, 0);
if (nIndex == -1)
return "";
int nStrLen = WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_GETLBTEXTLEN, nIndex, 0);
IntPtr strPtr = Marshal.AllocHGlobal(nStrLen);
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_GETLBTEXT, nIndex, strPtr);
return Util.GetNormalRussian(strPtr, (uint)nStrLen); ;
}
private void InitEngine(IntPtr hWnd)
{
ClearComboBox(hWnd, IDI_ENGINE_VOICES);
SetVoices(hWnd, IDI_ENGINE_VOICES, TextToSpeak.getVoices(), readDBString("engine", "speak_config"));
SetRateSlider(hWnd, IDI_ENGINE_VOLUME, readDBLong("volume", "speak_config"));
SetRateSlider(hWnd, IDI_ENGINE_RATE, readDBLong("rate", "speak_config"));
SetRateSlider(hWnd, IDI_ENGINE_PITCH, readDBLong("pitch", "speak_config"));
SetText(hWnd, IDI_ENGINE_WELCOME, readDBString("welcome_msg", "speak_config"));
}
private void SetRateSlider(IntPtr hWnd, int ID, long pos)
{
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.TBM_SETRANGE, 1, WinApi.MakeLParam(1,100));
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.TBM_SETPOS, 1, int.Parse(pos.ToString()));
}
private void SetVoices(IntPtr hWnd, int ID, List<string> list, string standart)
{
int i = 0;
int def = -1;
foreach (string item in list)
{
if (item == standart)
def = i;
AddComboText(hWnd, ID, item);
i++;
}
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_SETCURSEL, def, 0);
}
private void AddComboText(IntPtr hWnd, Int32 ID, string text)
{
int length;
IntPtr str = Util.GetStringPtr(text, out length);
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_ADDSTRING, 0, str);
if (str != IntPtr.Zero)
Marshal.FreeHGlobal(str);
}
private void ClearComboBox(IntPtr hWnd, Int32 ID)
{
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.CB_RESETCONTENT, 0, 0);
}
private int WndProcAnnounce(IntPtr hWnd, int Msg, int wParam, int lParam)
{
switch (Msg)
{
case WinApi.WM_INITDIALOG:
InitAnnounce(hWnd);
return 0;
case WinApi.WM_COMMAND:
return ProcessCommandAnnounce(hWnd, Util.LoWord(wParam), Util.HiWord(wParam), lParam);
case WinApi.WM_NOTIFY:
return NotifyAnnounce(hWnd, wParam, lParam);
}
return 0;
}
private int NotifyAnnounce(IntPtr hwndDlg, int wParam, int lParam)
{
NMHDR lParams;
lParams = (NMHDR)Marshal.PtrToStructure((IntPtr)lParam, typeof(NMHDR));
switch (lParams.idFrom)
{
case 0:
switch (lParams.code)
{
case WinApi.PSN_APPLY:
{
writeDBBool("status_" + (int)StatusModes.Offline, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_OFFLINE));
writeDBBool("status_" + (int)StatusModes.Online, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_ONLINE));
writeDBBool("status_" + (int)StatusModes.Away, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_AWAY));
writeDBBool("status_" + (int)StatusModes.DND, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_DND));
writeDBBool("status_" + (int)StatusModes.NA, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_NA));
writeDBBool("status_" + (int)StatusModes.Occupied, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_OCCUPIED));
writeDBBool("status_" + (int)StatusModes.FreeForChat, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_FREEFORCHAT));
writeDBBool("status_" + (int)StatusModes.Invisible, "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_INVISIBLE));
writeDBBool("active_connect", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_CONNECT));
writeDBBool("active_disconnect", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_DISCONNECT));
writeDBBool("active_shutdown", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_SHUTDOWN));
writeDBBool("active", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_ACTIVE));
writeDBBool("ignore_onopen", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_ONOPEN));
writeDBBool("ignore_onfocus", "speak_config", IsBtnChecked(hwndDlg, IDI_ANNOUNCE_ONFOCUS));
writeDBlong("max_msg_size", "speak_config", UInt32.Parse(GetText(hwndDlg, IDI_ANNOUNCE_LENGTH)));
OnChanged(EventChanged.Announce);
return 1;
}
}
break;
}
return 0;
}
private string GetText(IntPtr hwndDlg, int ID)
{
int nStrLen = WinApi.SendDlgItemMessage(hwndDlg, ID, WinApi.WM_GETTEXTLENGTH, 0, 0);
IntPtr strPtr = Marshal.AllocHGlobal(nStrLen + 1);
WinApi.SendDlgItemMessage(hwndDlg, ID, WinApi.WM_GETTEXT, nStrLen + 1, strPtr);
return Marshal.PtrToStringAnsi(strPtr, nStrLen);
}
private bool IsBtnChecked(IntPtr hwndDlg, Int32 ID)
{
return WinApi.SendDlgItemMessage(hwndDlg, ID, WinApi.BM_GETCHECK, 0, 0) == WinApi.BST_CHECKED;
}
private int ProcessCommandAnnounce(IntPtr hwndDlg, Int16 item, Int16 command, Int32 lParam)
{
switch (item)
{
case IDI_ANNOUNCE_OFFLINE:
case IDI_ANNOUNCE_ONLINE:
case IDI_ANNOUNCE_AWAY:
case IDI_ANNOUNCE_DND:
case IDI_ANNOUNCE_NA:
case IDI_ANNOUNCE_OCCUPIED:
case IDI_ANNOUNCE_FREEFORCHAT:
case IDI_ANNOUNCE_INVISIBLE:
case IDI_ANNOUNCE_CONNECT:
case IDI_ANNOUNCE_DISCONNECT:
case IDI_ANNOUNCE_SHUTDOWN:
case IDI_ANNOUNCE_ACTIVE:
case IDI_ANNOUNCE_ONOPEN:
case IDI_ANNOUNCE_ONFOCUS:
WinApi.SendMessage(WinApi.GetParent(hwndDlg), WinApi.PSM_CHANGED, 0, 0);
return 0;
case IDI_ANNOUNCE_LENGTH:
if (command == WinApi.EN_CHANGE)
{
WinApi.SendMessage(WinApi.GetParent(hwndDlg), WinApi.PSM_CHANGED, 0, 0);
}
return 0;
}
return 0;
}
private void InitAnnounce(IntPtr hWnd)
{
SetCheckState(hWnd, IDI_ANNOUNCE_OFFLINE, readDBBool("status_" + (int)StatusModes.Offline, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_ONLINE, readDBBool("status_" + (int)StatusModes.Online, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_AWAY, readDBBool("status_" + (int)StatusModes.Away, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_DND, readDBBool("status_" + (int)StatusModes.DND, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_NA, readDBBool("status_" + (int)StatusModes.NA, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_OCCUPIED, readDBBool("status_" + (int)StatusModes.Occupied, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_FREEFORCHAT, readDBBool("status_" + (int)StatusModes.FreeForChat, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_INVISIBLE, readDBBool("status_" + (int)StatusModes.Invisible, "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_CONNECT, readDBBool("active_connect", "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_DISCONNECT, readDBBool("active_disconnect", "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_SHUTDOWN, readDBBool("active_shutdown", "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_ACTIVE, readDBBool("active", "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_ONOPEN, readDBBool("ignore_onopen", "speak_config"));
SetCheckState(hWnd, IDI_ANNOUNCE_ONFOCUS, readDBBool("ignore_onfocus", "speak_config"));
SetText(hWnd, IDI_ANNOUNCE_LENGTH, readDBLong("max_msg_size","speak_config").ToString());
}
private void SetText(IntPtr hWnd, Int32 ID, string text)
{
int length;
IntPtr str = Util.GetStringPtr(text, out length);
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.WM_SETTEXT, 0, Marshal.StringToHGlobalAnsi(text));
if (str != IntPtr.Zero)
Marshal.FreeHGlobal(str);
}
private void SetCheckState(IntPtr hWnd, Int32 ID, bool isChecked)
{
WinApi.SendDlgItemMessage(hWnd, ID, WinApi.BM_SETCHECK, isChecked ? WinApi.BST_CHECKED : WinApi.BST_UNCHECKED, 0);
}
private int WndProcSpeak(IntPtr hWnd, int Msg, int wParam, int lParam)
{
switch (Msg)
{
case WinApi.WM_INITDIALOG:
initImageLists();
InitSpeakList(hWnd);
return 0;
case WinApi.WM_SETFOCUS:
WinApi.SetFocus(WinApi.GetDlgItem(hWnd, IDC_SPEAK_LIST));
break;
case WinApi.WM_NOTIFY:
return NotifySpeak(hWnd, wParam, lParam);
case WinApi.WM_DESTROY:
DestroySpeak(hWnd);
break;
}
return 0;
}
private int NotifySpeak(IntPtr hwndDlg, int wParam, int lParam)
{
NMHDR lParams;
lParams = (NMHDR)Marshal.PtrToStructure((IntPtr)lParam, typeof(NMHDR));
switch (lParams.idFrom)
{
case IDC_SPEAK_LIST:
switch (lParams.code)
{
case ContactListConstants.CLN_NEWCONTACT:
case ContactListConstants.CLN_LISTREBUILT:
WinApi.SendMessage(WinApi.GetDlgItem(hwndDlg, IDC_SPEAK_LIST), ContactListConstants.CLM_AUTOREBUILD, 0, 0);
SetAllContactIcons(WinApi.GetDlgItem(hwndDlg, IDC_SPEAK_LIST), imagelistSpeak);
SetListGroupIcons(WinApi.GetDlgItem(hwndDlg, IDC_SPEAK_LIST), WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_ROOT, 0), 0, imagelistSpeak, null);
break;
case ContactListConstants.CLN_OPTIONSCHANGED:
SetListGroupIcons(WinApi.GetDlgItem(hwndDlg, IDC_SPEAK_LIST), WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_ROOT, 0), 0, imagelistSpeak, null);
break;
case WinApi.NM_CLICK:
{
int hItem;
NMCLISTCONTROL nm;
nm = (NMCLISTCONTROL)Marshal.PtrToStructure((IntPtr)lParam, typeof(NMCLISTCONTROL));
int iImage;
int itemType;
// Make sure we have an extra column
if (nm.iColumn == -1)
break;
// Find clicked item
hItem = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_HITTEST, 0, WinApi.MakeLParam(nm.pt.X, nm.pt.Y));
// Nothing was clicked
if (hItem == 0)
break;
// Get image in clicked column (2=none, 1=online, 0=message)
iImage = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(nm.iColumn, 0));
if (iImage == imagelistSpeak[StandartIcons.SKINICON_OTHER_SMALLDOT])
{
iImage = (nm.iColumn == 0) ? imagelistSpeak[StandartIcons.ID_STATUS_ONLINE] : imagelistSpeak[StandartIcons.SKINICON_EVENT_MESSAGE];
}
else
{
if (iImage == imagelistSpeak[StandartIcons.ID_STATUS_ONLINE] || iImage == imagelistSpeak[StandartIcons.SKINICON_EVENT_MESSAGE])
{
iImage = imagelistSpeak[StandartIcons.SKINICON_OTHER_SMALLDOT];
}
}
itemType = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETITEMTYPE, hItem, 0);
if (itemType == ContactListConstants.CLCIT_CONTACT)
{ // A contact
WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(nm.iColumn, iImage));
}
else if (itemType == ContactListConstants.CLCIT_INFO)
{
WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(nm.iColumn, iImage));
}
// Update the all/none icons
SetListGroupIcons(WinApi.GetDlgItem(hwndDlg, IDC_SPEAK_LIST), WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_ROOT, 0), 0, imagelistSpeak, null);
// Activate Apply button
WinApi.SendMessage(WinApi.GetParent(hwndDlg), WinApi.PSM_CHANGED, 0, 0);
}
break;
}
break;
case 0:
switch (lParams.code)
{
case WinApi.PSN_APPLY:
{
int hContact = MirandaContext.Current.CallService(API.MS_DB_CONTACT_FINDFIRST, IntPtr.Zero, IntPtr.Zero);
do
{
int hItem = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_FINDCONTACT, hContact, 0);
if (hItem != 0)
{
for (int i = 0; i < 2; i++)
{
int iImage = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(i, 0));
if (i == 0)
{
if (iImage == imagelistSpeak[StandartIcons.ID_STATUS_ONLINE])
{
writeDBBool("status", "speak_config", false, (IntPtr)hContact);
}
else
{
writeDBBool("status", "speak_config", true, (IntPtr)hContact);
}
}
if (i == 1)
{
if (iImage == imagelistSpeak[StandartIcons.SKINICON_EVENT_MESSAGE])
{
writeDBBool("message", "speak_config", false, (IntPtr)hContact);
}
else
{
writeDBBool("message", "speak_config", true, (IntPtr)hContact);
}
}
}
}
} while ((hContact = MirandaContext.Current.CallService(API.MS_DB_CONTACT_FINDNEXT, (IntPtr)hContact, IntPtr.Zero)) != 0);
for (int i = 0; i < 2; i++)
{
int iImageu = WinApi.SendDlgItemMessage(hwndDlg, IDC_SPEAK_LIST, ContactListConstants.CLM_GETEXTRAIMAGE, hItemUnkSpeak, WinApi.MakeLParam(i, 0));
if (i == 0)
{
if (iImageu == imagelistSpeak[StandartIcons.ID_STATUS_ONLINE])
{
writeDBBool("status_u", "speak_config", false);
}
else
{
writeDBBool("status_u", "speak_config", true);
}
}
if (i == 1)
{
if (iImageu == imagelistSpeak[StandartIcons.SKINICON_EVENT_MESSAGE])
{
writeDBBool("message_u", "speak_config", false);
}
else
{
writeDBBool("message_u", "speak_config", true);
}
}
}
OnChanged(EventChanged.Active);
return 1;
}
}
break;
}
return 0;
}
private void DestroySpeak(IntPtr hWnd)
{
WinApi.DestroyIcon(imagelistSpeak.GetIcon(StandartIcons.SKINICON_EVENT_MESSAGE));
WinApi.DestroyIcon(imagelistSpeak.GetIcon(StandartIcons.ID_STATUS_ONLINE));
{
int hIml = WinApi.SendDlgItemMessage(hWnd, IDC_SPEAK_LIST, ContactListConstants.CLM_GETEXTRAIMAGELIST, 0, 0);
WinApi.ImageList_Destroy(hIml);
}
}
private void InitSpeakList(IntPtr handle)
{
setIcons(handle, IDC_SPEAK_LIST, imagelistSpeak);
setIcons(imagelistSpeak, StandartIcons.SKINICON_EVENT_MESSAGE, IDC_SPEAK_VISIBLEICON, handle);
setIcons(imagelistSpeak, StandartIcons.ID_STATUS_ONLINE, IDC_SPEAK_INVISIBLEICON, handle);
ResetListOptions(WinApi.GetDlgItem(handle, IDC_SPEAK_LIST));
WinApi.SendDlgItemMessage(handle, IDC_SPEAK_LIST, ContactListConstants.CLM_SETEXTRACOLUMNS, 2, 0);
hItemUnkSpeak = addStringCList(IDC_SPEAK_LIST, "** Unknown contacts **", handle);
SetUnknownIcons(WinApi.GetDlgItem(handle, IDC_SPEAK_LIST), hItemUnkSpeak, imagelistSpeak);
SetAllContactIcons(WinApi.GetDlgItem(handle, IDC_SPEAK_LIST), imagelistSpeak);
SetListGroupIcons(WinApi.GetDlgItem(handle, IDC_SPEAK_LIST), WinApi.SendDlgItemMessage(handle, IDC_SPEAK_LIST, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_ROOT, 0), 0, imagelistSpeak, null);
}
private void SetUnknownIcons(IntPtr hwndList, int hItem, Win32ImageList imageList)
{
if (WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(0, 0)) == 0xFF)
{
int icon = imageList[StandartIcons.SKINICON_OTHER_SMALLDOT];
if (!readDBBool("status_u", "speak_config", true))
{
icon = imageList[StandartIcons.ID_STATUS_ONLINE];
}
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(0, icon));
}
if (WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(1, 0)) == 0xFF)
{
int icon = imageList[StandartIcons.SKINICON_OTHER_SMALLDOT];
if (!readDBBool("message_u", "speak_config", true))
{
icon = imageList[StandartIcons.SKINICON_EVENT_MESSAGE];
}
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(1, icon));
}
}
private void SetListGroupIcons(IntPtr hwndList, int hFirstItem, int hParentItem, Win32ImageList imageList, int[] groupChildCount)
{
int[] childCount = { 0, 0 };
int[] iconOn = { 1, 1 };
int[] iconshow = { imageList[StandartIcons.ID_STATUS_ONLINE], imageList[StandartIcons.SKINICON_EVENT_MESSAGE] };
int typeOfFirst = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETITEMTYPE, hFirstItem, 0);
int hItem;
//check groups
if (typeOfFirst == ContactListConstants.CLCIT_GROUP)
{
hItem = hFirstItem;
}
else
{
hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_NEXTGROUP, hFirstItem);
}
while (hItem != 0)
{
int hChildItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_CHILD, hItem);
if (hChildItem != 0)
{
SetListGroupIcons(hwndList, hChildItem, hItem, imageList, childCount);
}
for (int i = 0; i < iconOn.Length; i++)
{
if (iconOn[i] != 0 && WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, i) != imageList[StandartIcons.SKINICON_OTHER_SMALLDOT])
{
iconOn[i] = 0;
}
}
hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_NEXTGROUP, hItem);
}
//check contacts
if (typeOfFirst == ContactListConstants.CLCIT_CONTACT)
{
hItem = hFirstItem;
}
else
{
hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_NEXTCONTACT, hFirstItem);
}
while (hItem != 0)
{
for (int i = 0; i < iconOn.Length; i++)
{
int iImage = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, i);
if (iconOn[i] != 0 && iImage != imageList[StandartIcons.SKINICON_OTHER_SMALLDOT])
{
iconOn[i] = 0;
}
if (iImage != 0xFF)
{
childCount[i]++;
}
}
hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETNEXTITEM, ContactListConstants.CLGN_NEXTCONTACT, hItem);
}
//set icons
for (int i = 0; i < iconOn.Length; i++)
{
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETEXTRAIMAGE, hParentItem, WinApi.MakeLParam(i, childCount[i] != 0 ? (iconOn[i] == 0 ? iconshow[i] : imageList[StandartIcons.SKINICON_OTHER_SMALLDOT]) : 0xFF));
if (groupChildCount != null)
{
groupChildCount[i] += childCount[i];
}
}
}
private void SetAllContactIcons(IntPtr hwndList, Win32ImageList imageList)
{
WinApi.SendMessage(hwndList, ContactListConstants.CLM_AUTOREBUILD, 0, 0);
int hContact = MirandaContext.Current.CallService(API.MS_DB_CONTACT_FINDFIRST, IntPtr.Zero, IntPtr.Zero);
do
{
int hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_FINDCONTACT, hContact, 0);
if (hItem == 0)
{
hItem = WinApi.SendMessage(hwndList, ContactListConstants.CLM_AUTOREBUILD, 0, 0);
}
else
{
if (hItem != 0)
{
int szProto = MirandaContext.Current.CallService(API.MS_PROTO_GETCONTACTBASEPROTO, (IntPtr)hItem, IntPtr.Zero);
if (szProto != 0)
{
if (WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(0, 0)) == 0xFF)
{
int icon = imageList[StandartIcons.SKINICON_OTHER_SMALLDOT];
if (!readDBBool("status", "speak_config", (IntPtr)hContact, true))
{
icon = imageList[StandartIcons.ID_STATUS_ONLINE];
}
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(0, icon));
}
if (WinApi.SendMessage(hwndList, ContactListConstants.CLM_GETEXTRAIMAGE, hItem, WinApi.MakeLParam(1, 0)) == 0xFF)
{
int icon = imageList[StandartIcons.SKINICON_OTHER_SMALLDOT];
if (!readDBBool("message", "speak_config", (IntPtr)hContact, true))
{
icon = imageList[StandartIcons.SKINICON_EVENT_MESSAGE];
}
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETEXTRAIMAGE, hItem, WinApi.MakeLParam(1, icon));
}
}
}
}
} while ((hContact = MirandaContext.Current.CallService(API.MS_DB_CONTACT_FINDNEXT, (IntPtr)hContact, IntPtr.Zero)) > 0);
}
private void ResetListOptions(IntPtr hwndList)
{
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETBKBITMAP, 0, IntPtr.Zero);
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETBKCOLOR, WinApi.GetSysColor(WinApi.COLOR_WINDOW), 0);
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETGREYOUTFLAGS, 0, 0);
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETLEFTMARGIN, 2, 0);
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETINDENT, 10, 0);
for (int i = 0; i <= ContactListConstants.FONTID_MAX; i++)
{
WinApi.SendMessage(hwndList, ContactListConstants.CLM_SETTEXTCOLOR, i, WinApi.GetSysColor(WinApi.COLOR_WINDOWTEXT));
}
WinApi.SetWindowLong(hwndList, WinApi.GWL_STYLE, WinApi.GetWindowLong(hwndList, WinApi.GWL_STYLE) | ContactListConstants.CLS_SHOWHIDDEN);
}
private void setIcons(IntPtr handle, int IDC_LIST, Win32ImageList imageList)
{
WinApi.SendDlgItemMessage(handle, IDC_LIST, ContactListConstants.CLM_SETEXTRAIMAGELIST, 0, imageList.Handle);
}
private void setIcons(Win32ImageList imageList, string iconKey, int ID, IntPtr handle)
{
WinApi.SendDlgItemMessage(handle, ID, WinApi.STM_SETICON, imageList.GetIcon(iconKey), 0);
}
private int addStringCList(Int32 ID, string text, IntPtr handle)
{
int length;
IntPtr str = Util.GetStringPtr(text, out length);
CLCINFOITEM cii = new CLCINFOITEM();
cii.cbSize = Marshal.SizeOf(cii);
cii.flags = ContactListConstants.CLCIIF_GROUPFONT;
cii.pszText = Marshal.StringToHGlobalUni(text);
IntPtr cmdPtr = Marshal.AllocHGlobal(Marshal.SizeOf(cii));
Marshal.StructureToPtr(cii, cmdPtr, false);
int ret = WinApi.SendDlgItemMessage(handle, ID, ContactListConstants.CLM_ADDINFOITEM, 0, cmdPtr);
if (str != IntPtr.Zero)
Marshal.FreeHGlobal(str);
return ret;
}
/// <summary>
/// Read a boolean value from Miranda Databse
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
public static bool readDBBool(string name, string owner)
{
return readDBBool(name, owner, false);
}
/// <summary>
/// Read a boolean value from Mirana Database and if it not Present use standart
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="standart">Default Value</param>
public static bool readDBBool(string name, string owner, bool standart)
{
return readDBBool(name, owner, IntPtr.Zero, standart);
}
/// <summary>
/// Read a value from Miranda Databse from specefic user and use a default value if not present
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="contact">Default value</param>
/// <param name="standart">Userhandle</param>
/// <returns></returns>
public static bool readDBBool(string name, string owner, IntPtr contact, bool standart)
{
object value = ContactInfo.FromHandle(contact).ReadSetting(name, owner, DatabaseSettingType.Byte);
if (value != null)
{
if ((byte)value == 1)
{
return true;
}
else
{
return false;
}
}
return standart;
}
/// <summary>
/// Read a value from Miranda Database
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <returns>Return 0 if not present</returns>
public static long readDBLong(string name, string owner)
{
object value = ContactInfo.ReadSetting(IntPtr.Zero, name, owner, DatabaseSettingType.UInt32);
if (value != null)
{
return (UInt32)value;
}
return 0;
}
/// <summary>
/// Read a value from Miranda Databse
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <returns>Returns an empty String if not presend</returns>
public static string readDBString(string name, string owner)
{
object value = ContactInfo.ReadSetting(IntPtr.Zero, name, owner, DatabaseSettingType.AsciiString);
if (value != null)
{
return (string)value;
}
return "";
}
/// <summary>
/// Write a boolean value into Miranda Databse
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="value">Value</param>
public static bool writeDBBool(string name, string owner, bool value)
{
writeDBBool(name, owner, value, IntPtr.Zero);
return readDBBool(name, owner) == value;
}
/// <summary>
/// Write a boolean value into Miranda Database for specific user
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="value">Value</param>
/// <param name="contact">User handle</param>
public static bool writeDBBool(string name, string owner, bool value, IntPtr contact)
{
byte v = (value) ? (byte)1 : (byte)0;
ContactInfo.FromHandle(contact).WriteSetting(name, owner, v, DatabaseSettingType.Byte);
return readDBBool(name, owner, contact, false) == value;
}
/// <summary>
/// Write a long value into Miranda Databse
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="value">long value</param>
public static bool writeDBlong(string name, string owner, uint value)
{
ContactInfo.FromHandle(IntPtr.Zero).WriteSetting(name, owner, (UInt32)value, DatabaseSettingType.UInt32);
return readDBLong(name, owner) == value;
}
/// <summary>
/// Write a string value into Miranda Databse
/// </summary>
/// <param name="name">Name</param>
/// <param name="owner">Module</param>
/// <param name="value">string value</param>
public static bool writeDBstring(string name, string owner, string value)
{
ContactInfo.FromHandle(IntPtr.Zero).WriteSetting(name, owner, (string)value, DatabaseSettingType.AsciiString);
return readDBString(name, owner) == value;
}
}
}

View File

@ -0,0 +1,64 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using Speak.Interop;
namespace Speak.Opt
{
internal class Win32ImageList
{
private IntPtr handle;
private Dictionary<string, int> icons;
private int defaultIndex;
private string defaultName;
public Win32ImageList() : this (16, 16, 0) { }
public Win32ImageList(int width, int height, int count)
{
handle = WinApi.ImageList_Create(width, height, WinApi.ILC_MASK | WinApi.ILC_COLOR32, count, 0);
icons = new Dictionary<string, int>();
defaultIndex = -1;
defaultName = "xJuick_Default";
}
public int AddIcon(string iconKey, IntPtr hIcon)
{
int result = -1;
if (icons.ContainsKey(iconKey))
return icons[iconKey];
result = WinApi.ImageList_ReplaceIcon(handle, -1, hIcon);
if (result != -1)
{
icons.Add(iconKey, result);
if (defaultName.Equals(iconKey))
defaultIndex = result;
}
return result;
}
public IntPtr Handle
{
get { return handle; }
}
public int this[string iconKey]
{
get { return icons.ContainsKey(iconKey) ? icons[iconKey] : defaultIndex; }
}
public int Length
{
get { return icons.Count; }
}
public int GetIcon(string iconKey)
{
int icon = this.icons[iconKey];
return WinApi.ImageList_GetIcon(handle, icon, WinApi.ILD_NORMAL);
}
}
}

BIN
Speak/Speak/Opt/dialog.res Normal file

Binary file not shown.

View File

@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
// Allgemeine Informationen über eine Assembly werden über die folgenden
// Attribute gesteuert. Ändern Sie diese Attributwerte, um die Informationen zu ändern,
// die mit einer Assembly verknüpft sind.
[assembly: AssemblyTitle("Speak")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("Speak")]
[assembly: AssemblyCopyright("Copyright © 2013")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
// Durch Festlegen von ComVisible auf "false" werden die Typen in dieser Assembly unsichtbar
// für COM-Komponenten. Wenn Sie auf einen Typ in dieser Assembly von
// COM zugreifen müssen, legen Sie das ComVisible-Attribut für diesen Typ auf "true" fest.
[assembly: ComVisible(false)]
// Die folgende GUID bestimmt die ID der Typbibliothek, wenn dieses Projekt für COM verfügbar gemacht wird
[assembly: Guid("8661d35b-6865-4e4e-a32b-feb32a681897")]
// Versionsinformationen für eine Assembly bestehen aus den folgenden vier Werten:
//
// Hauptversion
// Nebenversion
// Buildnummer
// Revision
//
// Sie können alle Werte angeben oder die standardmäßigen Build- und Revisionsnummern
// übernehmen, indem Sie "*" eingeben:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

View File

@ -0,0 +1,93 @@
//------------------------------------------------------------------------------
// <auto-generated>
// Dieser Code wurde von einem Tool generiert.
// Laufzeitversion:4.0.30319.18033
//
// Änderungen an dieser Datei können falsches Verhalten verursachen und gehen verloren, wenn
// der Code erneut generiert wird.
// </auto-generated>
//------------------------------------------------------------------------------
namespace Speak.Properties {
using System;
/// <summary>
/// Eine stark typisierte Ressourcenklasse zum Suchen von lokalisierten Zeichenfolgen usw.
/// </summary>
// Diese Klasse wurde von der StronglyTypedResourceBuilder automatisch generiert
// -Klasse über ein Tool wie ResGen oder Visual Studio automatisch generiert.
// Um einen Member hinzuzufügen oder zu entfernen, bearbeiten Sie die .ResX-Datei und führen dann ResGen
// mit der /str-Option erneut aus, oder Sie erstellen Ihr VS-Projekt neu.
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
internal class Resources {
private static global::System.Resources.ResourceManager resourceMan;
private static global::System.Globalization.CultureInfo resourceCulture;
[global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
internal Resources() {
}
/// <summary>
/// Gibt die zwischengespeicherte ResourceManager-Instanz zurück, die von dieser Klasse verwendet wird.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Resources.ResourceManager ResourceManager {
get {
if (object.ReferenceEquals(resourceMan, null)) {
global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("Speak.Properties.Resources", typeof(Resources).Assembly);
resourceMan = temp;
}
return resourceMan;
}
}
/// <summary>
/// Überschreibt die CurrentUICulture-Eigenschaft des aktuellen Threads für alle
/// Ressourcenzuordnungen, die diese stark typisierte Ressourcenklasse verwenden.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Globalization.CultureInfo Culture {
get {
return resourceCulture;
}
set {
resourceCulture = value;
}
}
/// <summary>
/// Sucht eine lokalisierte Ressource vom Typ System.Drawing.Icon ähnlich wie (Symbol).
/// </summary>
internal static System.Drawing.Icon icon_message {
get {
object obj = ResourceManager.GetObject("icon_message", resourceCulture);
return ((System.Drawing.Icon)(obj));
}
}
/// <summary>
/// Sucht eine lokalisierte Ressource vom Typ System.Drawing.Icon ähnlich wie (Symbol).
/// </summary>
internal static System.Drawing.Icon icon_small_dot {
get {
object obj = ResourceManager.GetObject("icon_small_dot", resourceCulture);
return ((System.Drawing.Icon)(obj));
}
}
/// <summary>
/// Sucht eine lokalisierte Ressource vom Typ System.Drawing.Icon ähnlich wie (Symbol).
/// </summary>
internal static System.Drawing.Icon status_online {
get {
object obj = ResourceManager.GetObject("status_online", resourceCulture);
return ((System.Drawing.Icon)(obj));
}
}
}
}

View File

@ -0,0 +1,130 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<assembly alias="System.Windows.Forms" name="System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
<data name="icon_message" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\icon_message.ico;System.Drawing.Icon, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="icon_small_dot" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\icon_small_dot.ico;System.Drawing.Icon, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="status_online" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\status_online.ico;System.Drawing.Icon, System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
</root>

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

View File

@ -0,0 +1,349 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Security.Permissions;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using Speak.Core;
using Speak.Interop;
using Speak.Structs;
using Speak.UI;
namespace Speak.RichEdit
{
[Guid("49b0db79-a3d5-494f-be22-544286053dd9")]
internal class ActionOleObject : Control, IActionOleObject, IActionOleGUID
{
protected Color normalBackColor;
protected Color hoverBackColor;
protected Color hoverForeColor;
protected Color borderColor;
protected bool pressed;
protected bool onControl;
protected bool isTailObjectSet;
protected string text;
protected int iconWidth;
protected int iconHeight;
protected Size textSize;
protected TextFormatFlags textFormat;
protected HoverPart currentHover;
protected ActionWordType actionType;
protected ActionObjectType objectType;
protected enum HoverPart { None, MainWord, Icon }
public static readonly Guid Guid = new Guid("49b0db79-a3d5-494f-be22-544286053dd9");
public ActionOleObject()
{
//SetStyle(ControlStyles.SupportsTransparentBackColor, true);
this.SetStyle(ControlStyles.DoubleBuffer, true);
this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
this.SetStyle(ControlStyles.UserPaint, true);
currentHover = HoverPart.None;
iconWidth = Properties.Resources.icon_small_dot.Width;
iconHeight = Properties.Resources.icon_small_dot.Height;
Width = 18;
Height = 18;
normalBackColor = Color.Green;
hoverBackColor = Color.White;
hoverForeColor = Color.Black;
borderColor = Color.Black;
BackColor = normalBackColor;
text = String.Empty;
Text = "";
textFormat = new TextFormatFlags();
textFormat |= TextFormatFlags.Default ;
onControl = false;
actionType = ActionWordType.None;
objectType = ActionObjectType.Default;
}
private void DoResize()
{
textSize = TextRenderer.MeasureText(Text, Font, Size, TextFormatFlags.Default);
Size = new Size(textSize.Width + iconWidth, iconHeight > textSize.Height ? iconHeight : textSize.Height);
}
protected override void OnPaint(PaintEventArgs e)
{
Graphics g = e.Graphics;
TextRenderer.DrawText(
g, Text, Font,
onControl ? new Point(1, (Height - textSize.Height) / 2) : new Point(1, Height - textSize.Height),
onControl ? hoverForeColor : ForeColor, TextFormatFlags.Default);
/*using (Bitmap bm = Properties.Resources.power)
{
g.DrawImage(bm, Width - iconWidth, (Height - iconHeight) / 2 + 1);
} */
}
protected override void OnPaintBackground(PaintEventArgs pevent)
{
Graphics g = pevent.Graphics;
Rectangle clip = pevent.ClipRectangle;
Rectangle activePart;
switch (currentHover)
{
case HoverPart.None:
base.OnPaintBackground(new PaintEventArgs(g, clip));
return;
case HoverPart.MainWord:
activePart = new Rectangle(0, 0, textSize.Width, Height - 1);
break;
case HoverPart.Icon:
activePart = new Rectangle(textSize.Width, 0, iconWidth - 1, Height - 1);
break;
default:
throw new ArgumentOutOfRangeException();
}
using (SolidBrush b = new SolidBrush(BackColor))
{
g.FillRectangle(b, activePart);
}
using (Pen p = new Pen(borderColor, 1.0f))
{
g.DrawRectangle(p, activePart);
}
Rectangle border = new Rectangle(clip.Location, new Size(clip.Width - 1, clip.Height - 1));
using (Pen p = new Pen(borderColor, 1.0f))
{
g.DrawRectangle(p, border);
}
}
private void SetHoverPart(int x, int y)
{
if (x > Left + (Width - iconWidth))
{
currentHover = HoverPart.Icon;
}
else
{
currentHover = HoverPart.MainWord;
}
}
new private void Click(IntPtr richEditHwnd, Int32 topOffset)
{
switch (currentHover)
{
case HoverPart.None:
break;
case HoverPart.MainWord:
InvokeAction(text, Point.Empty);
break;
case HoverPart.Icon:
POINT pt = new POINT(Left, Top);
WinApi.ClientToScreen(richEditHwnd, ref pt);
InvokeAction(text, new Point(pt.X - Left + Width - iconWidth - (topOffset == Int32.MinValue ? 3 : -1), (topOffset != Int32.MinValue ? topOffset : 0) + pt.Y - Top - 7));
break;
}
}
public event EventHandler<ActionObjectClickEvent> ActionClicked;
private void InvokeAction(string action, Point menuLocation)
{
EventHandler<ActionObjectClickEvent> handler = ActionClicked;
if (handler != null) handler(this, new ActionObjectClickEvent(action, actionType, menuLocation));
}
public Guid GUID
{
get { return Guid; }
}
#region Implementation of IActionOleObject
public bool IsTailObjectSet
{
get { return isTailObjectSet; }
set { isTailObjectSet = value; }
}
public ActionObjectType ObjectType
{
get { return objectType; }
set { objectType = value; }
}
public ActionWordType ActionType
{
get { return actionType; }
set { actionType = value; }
}
new public int Bottom
{
set { Top = value - Height; }
get { return base.Bottom; }
}
public void SetLMBDownState()
{
pressed = true;
}
public void SetLMBUpState(IntPtr hwnd, Int32 topOffset)
{
if (pressed)
{
pressed = false;
Click(hwnd, topOffset);
}
}
public void MouseMoving(int x, int y)
{
bool isHover = HitTest(x, y);
if (isHover)
{
HoverPart oldHP = currentHover;
SetHoverPart(x, y);
if (!onControl)
{
BackColor = hoverBackColor;
onControl = true;
Invalidate();
}
else if (oldHP != currentHover)
{
Invalidate();
}
Cursor.Current = Cursors.Hand;
}
else
{
if (onControl)
{
currentHover = HoverPart.None;
BackColor = normalBackColor;
onControl = false;
pressed = false;
Invalidate();
return;
}
}
}
new protected virtual void Invalidate()
{
base.Invalidate();
}
public bool HitTest(int x, int y)
{
return x >= Left && x < (Left+Width) && y >= Top && y < base.Bottom;
}
public Color BgColor
{
get { return normalBackColor; }
set
{
if (value != normalBackColor)
{
BackColor = normalBackColor = value;
}
}
}
new public string Text
{
get { return text; }
set
{
base.Text = value;
if (!text.Equals(value))
{
text = value;
DoResize();
}
}
}
#endregion
}
internal enum ActionObjectType
{
Default,
Nick,
FirstNick
}
internal class ActionObjectClickEvent : EventArgs
{
private string actionText;
private Point menuLocation;
private ActionWordType actionType;
public ActionObjectClickEvent(string actionText, ActionWordType actionType, Point menuLocation)
{
this.actionText = actionText;
this.menuLocation = menuLocation;
this.actionType = actionType;
}
public string ActionText
{
get { return actionText; }
set { actionText = value; }
}
public Point MenuLocation
{
get { return menuLocation; }
set { menuLocation = value; }
}
public ActionWordType ActionType
{
get { return actionType; }
set { actionType = value; }
}
}
[Guid("3289a6c9-b670-4840-b297-733372ab26b5")]
internal interface IActionOleObject
{
string Text { get; set; }
int Width { get; }
int Height { get; }
int Left { get; set; }
int Bottom { set; }
ActionObjectType ObjectType { get; set; }
bool IsTailObjectSet { get; set; }
bool HitTest(int x, int y);
void MouseMoving(int x, int y);
Color BgColor { get; set; }
void SetLMBDownState();
void SetLMBUpState(IntPtr richEditHwnd, Int32 topOffset);
ActionWordType ActionType { get; set; }
}
internal interface IActionOleGUID
{
Guid GUID { get; }
}
}

View File

@ -0,0 +1,75 @@
using System;
using System.Drawing;
using System.IO;
using System.Runtime.InteropServices;
using System.Windows.Forms;
using Speak.Core;
namespace Speak.RichEdit
{
[Guid("a2c9c6c9-aa99-46bd-9f67-c3a8b38c5da2")]
internal class AvatarObject : Control, IActionOleGUID, IDisposable
{
protected Image image;
public static readonly Guid Guid = new Guid("a2c9c6c9-aa99-46bd-9f67-c3a8b38c5da2");
public AvatarObject(AvatarProcessor ap, string nick, Color bgColor)
{
SetStyle(ControlStyles.DoubleBuffer, true);
SetStyle(ControlStyles.AllPaintingInWmPaint, true);
SetStyle(ControlStyles.UserPaint, true);
SetStyle(ControlStyles.SupportsTransparentBackColor, true);
BackColor = bgColor;
string imagePath = ap.GetUserAvatar(nick, AvatarCallback);
if (!String.IsNullOrEmpty(imagePath))
{
try
{
image = Image.FromFile(imagePath);
}
catch (Exception)
{
File.Delete(imagePath);
}
}
Width = Height = 32;
}
public virtual void AvatarCallback(string userName, string avatarPath)
{
image = Image.FromFile(avatarPath);
Invalidate();
}
protected override void OnPaint(PaintEventArgs e)
{
if (image != null)
{
e.Graphics.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
e.Graphics.DrawImage(image, 0, 0, Width, Height);
}
else
{
base.OnPaint(e);
}
}
new protected virtual void Invalidate()
{
base.Invalidate();
}
public Guid GUID
{
get { return Guid; }
}
new public void Dispose()
{
image = null;
base.Dispose();
}
}
}

View File

@ -0,0 +1,927 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.RichEdit
{
[Flags(), ComVisible(false)]
public enum STGM : int
{
STGM_DIRECT = 0x0,
STGM_TRANSACTED = 0x10000,
STGM_SIMPLE = 0x8000000,
STGM_READ = 0x0,
STGM_WRITE = 0x1,
STGM_READWRITE = 0x2,
STGM_SHARE_DENY_NONE = 0x40,
STGM_SHARE_DENY_READ = 0x30,
STGM_SHARE_DENY_WRITE = 0x20,
STGM_SHARE_EXCLUSIVE = 0x10,
STGM_PRIORITY = 0x40000,
STGM_DELETEONRELEASE = 0x4000000,
STGM_NOSCRATCH = 0x100000,
STGM_CREATE = 0x1000,
STGM_CONVERT = 0x20000,
STGM_FAILIFTHERE = 0x0,
STGM_NOSNAPSHOT = 0x200000,
}
// DVASPECT
[Flags(), ComVisible(false)]
public enum DVASPECT : int
{
DVASPECT_CONTENT = 1,
DVASPECT_THUMBNAIL = 2,
DVASPECT_ICON = 4,
DVASPECT_DOCPRINT = 8,
DVASPECT_OPAQUE = 16,
DVASPECT_TRANSPARENT = 32,
}
// CLIPFORMAT
[ComVisible(false)]
public enum CLIPFORMAT : int
{
CF_TEXT = 1,
CF_BITMAP = 2,
CF_METAFILEPICT = 3,
CF_SYLK = 4,
CF_DIF = 5,
CF_TIFF = 6,
CF_OEMTEXT = 7,
CF_DIB = 8,
CF_PALETTE = 9,
CF_PENDATA = 10,
CF_RIFF = 11,
CF_WAVE = 12,
CF_UNICODETEXT = 13,
CF_ENHMETAFILE = 14,
CF_HDROP = 15,
CF_LOCALE = 16,
CF_MAX = 17,
CF_OWNERDISPLAY = 0x80,
CF_DSPTEXT = 0x81,
CF_DSPBITMAP = 0x82,
CF_DSPMETAFILEPICT = 0x83,
CF_DSPENHMETAFILE = 0x8E,
}
// Object flags
[Flags(), ComVisible(false)]
public enum REOOBJECTFLAGS : uint
{
REO_NULL = 0x00000000, // No flags
REO_READWRITEMASK = 0x0000003F, // Mask out RO bits
REO_DONTNEEDPALETTE = 0x00000020, // Object doesn't need palette
REO_BLANK = 0x00000010, // Object is blank
REO_DYNAMICSIZE = 0x00000008, // Object defines size always
REO_INVERTEDSELECT = 0x00000004, // Object drawn all inverted if sel
REO_BELOWBASELINE = 0x00000002, // Object sits below the baseline
REO_RESIZABLE = 0x00000001, // Object may be resized
REO_LINK = 0x80000000, // Object is a link (RO)
REO_STATIC = 0x40000000, // Object is static (RO)
REO_SELECTED = 0x08000000, // Object selected (RO)
REO_OPEN = 0x04000000, // Object open in its server (RO)
REO_INPLACEACTIVE = 0x02000000, // Object in place active (RO)
REO_HILITED = 0x01000000, // Object is to be hilited (RO)
REO_LINKAVAILABLE = 0x00800000, // Link believed available (RO)
REO_GETMETAFILE = 0x00400000 // Object requires metafile (RO)
}
// OLERENDER
[ComVisible(false)]
public enum OLERENDER : int
{
OLERENDER_NONE = 0,
OLERENDER_DRAW = 1,
OLERENDER_FORMAT = 2,
OLERENDER_ASIS = 3,
}
// TYMED
[Flags(), ComVisible(false)]
public enum TYMED : int
{
TYMED_NULL = 0,
TYMED_HGLOBAL = 1,
TYMED_FILE = 2,
TYMED_ISTREAM = 4,
TYMED_ISTORAGE = 8,
TYMED_GDI = 16,
TYMED_MFPICT = 32,
TYMED_ENHMF = 64,
}
[StructLayout(LayoutKind.Sequential), ComVisible(false)]
public struct FORMATETC
{
public CLIPFORMAT cfFormat;
public IntPtr ptd;
public DVASPECT dwAspect;
public int lindex;
public TYMED tymed;
}
[StructLayout(LayoutKind.Sequential), ComVisible(false)]
public struct STGMEDIUM
{
//[MarshalAs(UnmanagedType.I4)]
public int tymed;
public IntPtr unionmember;
public IntPtr pUnkForRelease;
}
[ComVisible(true),
ComImport(),
Guid("00000103-0000-0000-C000-000000000046"),
InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IEnumFORMATETC
{
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Next(
[In, MarshalAs(UnmanagedType.U4)]
int celt,
[Out]
FORMATETC rgelt,
[In, Out, MarshalAs(UnmanagedType.LPArray)]
int[] pceltFetched);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Skip(
[In, MarshalAs(UnmanagedType.U4)]
int celt);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Reset();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Clone(
[Out, MarshalAs(UnmanagedType.LPArray)]
IEnumFORMATETC[] ppenum);
}
[ComVisible(true), StructLayout(LayoutKind.Sequential)]
public class COMRECT
{
public int left;
public int top;
public int right;
public int bottom;
public COMRECT()
{
}
public COMRECT(int left, int top, int right, int bottom)
{
this.left = left;
this.top = top;
this.right = right;
this.bottom = bottom;
}
public static COMRECT FromXYWH(int x, int y, int width, int height)
{
return new COMRECT(x, y, x + width, y + height);
}
}
public enum GETOBJECTOPTIONS
{
REO_GETOBJ_NO_INTERFACES = 0x00000000,
REO_GETOBJ_POLEOBJ = 0x00000001,
REO_GETOBJ_PSTG = 0x00000002,
REO_GETOBJ_POLESITE = 0x00000004,
REO_GETOBJ_ALL_INTERFACES = 0x00000007,
}
public enum GETCLIPBOARDDATAFLAGS
{
RECO_PASTE = 0,
RECO_DROP = 1,
RECO_COPY = 2,
RECO_CUT = 3,
RECO_DRAG = 4
}
[StructLayout(LayoutKind.Sequential)]
public struct CHARRANGE
{
public int cpMin;
public int cpMax;
}
[StructLayout(LayoutKind.Sequential)]
public class REOBJECT
{
public int cbStruct = Marshal.SizeOf(typeof(REOBJECT)); // Size of structure
public int cp; // Character position of object
public Guid clsid; // Class ID of object
public IntPtr poleobj; // OLE object interface
public IStorage pstg; // Associated storage interface
public IOleClientSite polesite; // Associated client site interface
public Size sizel; // Size of object (may be 0,0)
public uint dvAspect; // Display aspect to use
public uint dwFlags; // Object status flags
public uint dwUser; // Dword for user's use
}
[ComVisible(true), Guid("0000010F-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IAdviseSink
{
//C#r: UNDONE (Field in interface) public static readonly Guid iid;
void OnDataChange(
[In]
FORMATETC pFormatetc,
[In]
STGMEDIUM pStgmed);
void OnViewChange(
[In, MarshalAs(UnmanagedType.U4)]
int dwAspect,
[In, MarshalAs(UnmanagedType.I4)]
int lindex);
void OnRename(
[In, MarshalAs(UnmanagedType.Interface)]
object pmk);
void OnSave();
void OnClose();
}
[ComVisible(false), StructLayout(LayoutKind.Sequential)]
public sealed class STATDATA
{
[MarshalAs(UnmanagedType.U4)]
public int advf;
[MarshalAs(UnmanagedType.U4)]
public int dwConnection;
}
[ComVisible(false), StructLayout(LayoutKind.Sequential)]
public sealed class tagOLEVERB
{
[MarshalAs(UnmanagedType.I4)]
public int lVerb;
[MarshalAs(UnmanagedType.LPWStr)]
public String lpszVerbName;
[MarshalAs(UnmanagedType.U4)]
public int fuFlags;
[MarshalAs(UnmanagedType.U4)]
public int grfAttribs;
}
[ComVisible(true), ComImport(), Guid("00000104-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IEnumOLEVERB
{
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Next(
[MarshalAs(UnmanagedType.U4)]
int celt,
[Out]
tagOLEVERB rgelt,
[Out, MarshalAs(UnmanagedType.LPArray)]
int[] pceltFetched);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Skip(
[In, MarshalAs(UnmanagedType.U4)]
int celt);
void Reset();
void Clone(
out IEnumOLEVERB ppenum);
}
[ComVisible(true), Guid("00000105-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IEnumSTATDATA
{
//C#r: UNDONE (Field in interface) public static readonly Guid iid;
void Next(
[In, MarshalAs(UnmanagedType.U4)]
int celt,
[Out]
STATDATA rgelt,
[Out, MarshalAs(UnmanagedType.LPArray)]
int[] pceltFetched);
void Skip(
[In, MarshalAs(UnmanagedType.U4)]
int celt);
void Reset();
void Clone(
[Out, MarshalAs(UnmanagedType.LPArray)]
IEnumSTATDATA[] ppenum);
}
[ComVisible(true), Guid("0000011B-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IOleContainer
{
void ParseDisplayName(
[In, MarshalAs(UnmanagedType.Interface)] object pbc,
[In, MarshalAs(UnmanagedType.BStr)] string pszDisplayName,
[Out, MarshalAs(UnmanagedType.LPArray)] int[] pchEaten,
[Out, MarshalAs(UnmanagedType.LPArray)] object[] ppmkOut);
void EnumObjects(
[In, MarshalAs(UnmanagedType.U4)] int grfFlags,
[Out, MarshalAs(UnmanagedType.LPArray)] object[] ppenum);
void LockContainer(
[In, MarshalAs(UnmanagedType.I4)] int fLock);
}
[ComVisible(true),
ComImport(),
Guid("0000010E-0000-0000-C000-000000000046"),
InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IDataObject
{
[PreserveSig()]
uint GetData(
ref FORMATETC a,
ref STGMEDIUM b);
[PreserveSig()]
uint GetDataHere(
ref FORMATETC pFormatetc,
out STGMEDIUM pMedium);
[PreserveSig()]
uint QueryGetData(
ref FORMATETC pFormatetc);
[PreserveSig()]
uint GetCanonicalFormatEtc(
ref FORMATETC pformatectIn,
out FORMATETC pformatetcOut);
[PreserveSig()]
uint SetData(
ref FORMATETC pFormatectIn,
ref STGMEDIUM pmedium,
[In, MarshalAs(UnmanagedType.Bool)]
bool fRelease);
[PreserveSig()]
uint EnumFormatEtc(
uint dwDirection, IEnumFORMATETC penum);
[PreserveSig()]
uint DAdvise(
ref FORMATETC pFormatetc,
int advf,
[In, MarshalAs(UnmanagedType.Interface)]
IAdviseSink pAdvSink,
out uint pdwConnection);
[PreserveSig()]
uint DUnadvise(
uint dwConnection);
[PreserveSig()]
uint EnumDAdvise(
[Out, MarshalAs(UnmanagedType.Interface)]
out IEnumSTATDATA ppenumAdvise);
}
[ComVisible(true), Guid("00000118-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IOleClientSite
{
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SaveObject();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetMoniker(
[In, MarshalAs(UnmanagedType.U4)] int dwAssign,
[In, MarshalAs(UnmanagedType.U4)] int dwWhichMoniker,
[Out, MarshalAs(UnmanagedType.Interface)] out object ppmk);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetContainer([MarshalAs(UnmanagedType.Interface)] out IOleContainer container);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int ShowObject();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int OnShowWindow(
[In, MarshalAs(UnmanagedType.I4)] int fShow);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int RequestNewObjectLayout();
}
[ComVisible(false), StructLayout(LayoutKind.Sequential)]
public sealed class tagLOGPALETTE
{
[MarshalAs(UnmanagedType.U2)/*leftover(offset=0, palVersion)*/]
public short palVersion;
[MarshalAs(UnmanagedType.U2)/*leftover(offset=2, palNumEntries)*/]
public short palNumEntries;
// UNMAPPABLE: palPalEntry: Cannot be used as a structure field.
// /** @com.structmap(UNMAPPABLE palPalEntry) */
// public UNMAPPABLE palPalEntry;
}
[ComVisible(true), ComImport(), Guid("00000112-0000-0000-C000-000000000046"), InterfaceTypeAttribute(ComInterfaceType.InterfaceIsIUnknown)]
public interface IOleObject
{
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetClientSite(
[In, MarshalAs(UnmanagedType.Interface)]
IOleClientSite pClientSite);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetClientSite(out IOleClientSite site);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetHostNames(
[In, MarshalAs(UnmanagedType.LPWStr)]
string szContainerApp,
[In, MarshalAs(UnmanagedType.LPWStr)]
string szContainerObj);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Close(
[In, MarshalAs(UnmanagedType.I4)]
int dwSaveOption);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetMoniker(
[In, MarshalAs(UnmanagedType.U4)]
int dwWhichMoniker,
[In, MarshalAs(UnmanagedType.Interface)]
object pmk);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetMoniker(
[In, MarshalAs(UnmanagedType.U4)]
int dwAssign,
[In, MarshalAs(UnmanagedType.U4)]
int dwWhichMoniker,
out object moniker);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int InitFromData(
[In, MarshalAs(UnmanagedType.Interface)]
IDataObject pDataObject,
[In, MarshalAs(UnmanagedType.I4)]
int fCreation,
[In, MarshalAs(UnmanagedType.U4)]
int dwReserved);
int GetClipboardData(
[In, MarshalAs(UnmanagedType.U4)]
int dwReserved,
out IDataObject data);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int DoVerb(
[In, MarshalAs(UnmanagedType.I4)]
int iVerb,
[In]
IntPtr lpmsg,
[In, MarshalAs(UnmanagedType.Interface)]
IOleClientSite pActiveSite,
[In, MarshalAs(UnmanagedType.I4)]
int lindex,
[In]
IntPtr hwndParent,
[In]
COMRECT lprcPosRect);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int EnumVerbs(out IEnumOLEVERB e);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Update();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int IsUpToDate();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetUserClassID(
[In, Out]
ref Guid pClsid);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetUserType(
[In, MarshalAs(UnmanagedType.U4)]
int dwFormOfType,
[Out, MarshalAs(UnmanagedType.LPWStr)]
out string userType);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetExtent(
[In, MarshalAs(UnmanagedType.U4)]
int dwDrawAspect,
[In]
Size pSizel);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetExtent(
[In, MarshalAs(UnmanagedType.U4)]
int dwDrawAspect,
[Out]
Size pSizel);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Advise([In, MarshalAs(UnmanagedType.Interface)] IAdviseSink pAdvSink, out int cookie);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int Unadvise([In, MarshalAs(UnmanagedType.U4)] int dwConnection);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int EnumAdvise(out IEnumSTATDATA e);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetMiscStatus([In, MarshalAs(UnmanagedType.U4)] int dwAspect, out int misc);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetColorScheme([In] tagLOGPALETTE pLogpal);
}
[ComImport]
[Guid("0000000d-0000-0000-C000-000000000046")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IEnumSTATSTG
{
// The user needs to allocate an STATSTG array whose size is celt.
[PreserveSig]
uint
Next(
uint celt,
[MarshalAs(UnmanagedType.LPArray), Out]
System.Runtime.InteropServices.ComTypes.STATSTG[] rgelt,
out uint pceltFetched
);
void Skip(uint celt);
void Reset();
[return: MarshalAs(UnmanagedType.Interface)]
IEnumSTATSTG Clone();
}
[ComImport]
[Guid("0000000b-0000-0000-C000-000000000046")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IStorage
{
int CreateStream(
/* [string][in] */ string pwcsName,
/* [in] */ uint grfMode,
/* [in] */ uint reserved1,
/* [in] */ uint reserved2,
/* [out] */ out IStream ppstm);
int OpenStream(
/* [string][in] */ string pwcsName,
/* [unique][in] */ IntPtr reserved1,
/* [in] */ uint grfMode,
/* [in] */ uint reserved2,
/* [out] */ out IStream ppstm);
int CreateStorage(
/* [string][in] */ string pwcsName,
/* [in] */ uint grfMode,
/* [in] */ uint reserved1,
/* [in] */ uint reserved2,
/* [out] */ out IStorage ppstg);
int OpenStorage(
/* [string][unique][in] */ string pwcsName,
/* [unique][in] */ IStorage pstgPriority,
/* [in] */ uint grfMode,
/* [unique][in] */ IntPtr snbExclude,
/* [in] */ uint reserved,
/* [out] */ out IStorage ppstg);
int CopyTo(
/* [in] */ uint ciidExclude,
/* [size_is][unique][in] */ Guid rgiidExclude,
/* [unique][in] */ IntPtr snbExclude,
/* [unique][in] */ IStorage pstgDest);
int MoveElementTo(
/* [string][in] */ string pwcsName,
/* [unique][in] */ IStorage pstgDest,
/* [string][in] */ string pwcsNewName,
/* [in] */ uint grfFlags);
int Commit(
/* [in] */ uint grfCommitFlags);
int Revert();
int EnumElements(
/* [in] */ uint reserved1,
/* [size_is][unique][in] */ IntPtr reserved2,
/* [in] */ uint reserved3,
/* [out] */ out IEnumSTATSTG ppenum);
int DestroyElement(
/* [string][in] */ string pwcsName);
int RenameElement(
/* [string][in] */ string pwcsOldName,
/* [string][in] */ string pwcsNewName);
int SetElementTimes(
/* [string][unique][in] */ string pwcsName,
/* [unique][in] */ System.Runtime.InteropServices.ComTypes.FILETIME pctime,
/* [unique][in] */ System.Runtime.InteropServices.ComTypes.FILETIME patime,
/* [unique][in] */ System.Runtime.InteropServices.ComTypes.FILETIME pmtime);
int SetClass(
/* [in] */ Guid clsid);
int SetStateBits(
/* [in] */ uint grfStateBits,
/* [in] */ uint grfMask);
int Stat(
/* [out] */ out System.Runtime.InteropServices.ComTypes.STATSTG pstatstg,
/* [in] */ uint grfStatFlag);
}
[ComImport]
[Guid("0000000a-0000-0000-C000-000000000046")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface ILockBytes
{
int ReadAt(
/* [in] */ ulong ulOffset,
/* [unique][out] */ IntPtr pv,
/* [in] */ uint cb,
/* [out] */ out IntPtr pcbRead);
int WriteAt(
/* [in] */ ulong ulOffset,
/* [size_is][in] */ IntPtr pv,
/* [in] */ uint cb,
/* [out] */ out IntPtr pcbWritten);
int Flush();
int SetSize(
/* [in] */ ulong cb);
int LockRegion(
/* [in] */ ulong libOffset,
/* [in] */ ulong cb,
/* [in] */ uint dwLockType);
int UnlockRegion(
/* [in] */ ulong libOffset,
/* [in] */ ulong cb,
/* [in] */ uint dwLockType);
int Stat(
/* [out] */ out System.Runtime.InteropServices.ComTypes.STATSTG pstatstg,
/* [in] */ uint grfStatFlag);
}
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown), Guid("0c733a30-2a1c-11ce-ade5-00aa0044773d")]
public interface ISequentialStream
{
int Read(
/* [length_is][size_is][out] */ IntPtr pv,
/* [in] */ uint cb,
/* [out] */ out uint pcbRead);
int Write(
/* [size_is][in] */ IntPtr pv,
/* [in] */ uint cb,
/* [out] */ out uint pcbWritten);
};
[ComImport]
[Guid("0000000c-0000-0000-C000-000000000046")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IStream : ISequentialStream
{
int Seek(
/* [in] */ ulong dlibMove,
/* [in] */ uint dwOrigin,
/* [out] */ out ulong plibNewPosition);
int SetSize(
/* [in] */ ulong libNewSize);
int CopyTo(
/* [unique][in] */ [In] IStream pstm,
/* [in] */ ulong cb,
/* [out] */ out ulong pcbRead,
/* [out] */ out ulong pcbWritten);
int Commit(
/* [in] */ uint grfCommitFlags);
int Revert();
int LockRegion(
/* [in] */ ulong libOffset,
/* [in] */ ulong cb,
/* [in] */ uint dwLockType);
int UnlockRegion(
/* [in] */ ulong libOffset,
/* [in] */ ulong cb,
/* [in] */ uint dwLockType);
int Stat(
/* [out] */ out System.Runtime.InteropServices.ComTypes.STATSTG pstatstg,
/* [in] */ uint grfStatFlag);
int Clone(
/* [out] */ out IStream ppstm);
};
/// <summary>
/// Definition for interface IPersist.
/// </summary>
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown), Guid("0000010c-0000-0000-C000-000000000046")]
public interface IPersist
{
/// <summary>
/// getClassID
/// </summary>
/// <param name="pClassID"></param>
void GetClassID( /* [out] */ out Guid pClassID);
}
/// <summary>
/// Definition for interface IPersistStream.
/// </summary>
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown), Guid("00000109-0000-0000-C000-000000000046")]
public interface IPersistStream : IPersist
{
/// <summary>
/// GetClassID
/// </summary>
/// <param name="pClassID"></param>
new void GetClassID(out Guid pClassID);
/// <summary>
/// isDirty
/// </summary>
/// <returns></returns>
[PreserveSig]
int IsDirty();
/// <summary>
/// Load
/// </summary>
/// <param name="pStm"></param>
void Load([In] System.Runtime.InteropServices.ComTypes.IStream pStm);
/// <summary>
/// Save
/// </summary>
/// <param name="pStm"></param>
/// <param name="fClearDirty"></param>
void Save([In] System.Runtime.InteropServices.ComTypes.IStream pStm, [In, MarshalAs(UnmanagedType.Bool)] bool fClearDirty);
/// <summary>
/// GetSizeMax
/// </summary>
/// <param name="pcbSize"></param>
void GetSizeMax(out long pcbSize);
}
[ComImport(), Guid("00020D00-0000-0000-c000-000000000046"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IRichEditOle
{
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetClientSite(out IOleClientSite site);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetObjectCount();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetLinkCount();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetObject(int iob, [In, Out] REOBJECT lpreobject, [MarshalAs(UnmanagedType.U4)]GETOBJECTOPTIONS flags);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int InsertObject(REOBJECT lpreobject);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int ConvertObject(int iob, Guid rclsidNew, string lpstrUserTypeNew);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int ActivateAs(Guid rclsid, Guid rclsidAs);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetHostNames(string lpstrContainerApp, string lpstrContainerObj);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetLinkAvailable(int iob, bool fAvailable);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SetDvaspect(int iob, uint dvaspect);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int HandsOffStorage(int iob);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int SaveCompleted(int iob, IStorage lpstg);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int InPlaceDeactivate();
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int ContextSensitiveHelp(bool fEnterMode);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int GetClipboardData([In, Out] ref CHARRANGE lpchrg, [MarshalAs(UnmanagedType.U4)] GETCLIPBOARDDATAFLAGS reco, out IDataObject lplpdataobj);
[return: MarshalAs(UnmanagedType.I4)]
[PreserveSig]
int ImportDataObject(IDataObject lpdataobj, int cf, IntPtr hMetaPict);
}
}

View File

@ -0,0 +1,52 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Name")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C0-A1DF-11CE-8098-00AA0047BE5D")]
[TypeLibType(TypeLibTypeFlags.FDispatchable | TypeLibTypeFlags.FDual | TypeLibTypeFlags.FNonExtensible)]
internal interface ITextDocument
{
string Name { get; }
ITextSelection Selection { get; }
int StoryCount { get; }
ITextStoryRanges StoryRanges { get; }
//void GetStoryRanges(ref IntPtr ppStories);
int Saved { get; set; }
float DefaultTabStop { get; set; }
void New();
void Open([In, MarshalAs(UnmanagedType.Struct)] ref object pVar, [In] int Flags, [In] int CodePage);
void Save([In, MarshalAs(UnmanagedType.Struct)] ref object pVar, [In] int Flags, [In] int CodePage);
int Freeze();
int Unfreeze();
void BeginEditCollection();
void EndEditCollection();
int Undo([In] int Count);
int Redo([In] int Count);
ITextRange Range([In] int cp1, [In] int cp2);
ITextRange RangeFromPoint([In] int x, [In] int y);
}
}

View File

@ -0,0 +1,76 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Duplicate")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C3-A1DF-11CE-8098-00AA0047BE5D")]
[TypeLibType(TypeLibTypeFlags.FDispatchable | TypeLibTypeFlags.FDual | TypeLibTypeFlags.FNonExtensible)]
public interface ITextFont
{
ITextFont Duplicate { [return: MarshalAs(UnmanagedType.Interface)] get; set; }
int CanChange();
int IsEqual([In, MarshalAs(UnmanagedType.Interface)] ITextFont pFont);
void Reset([In] int Value);
int Style { get; set; }
int AllCaps { get; set; }
int Animation { get; set; }
int BackColor { get; set; }
int Bold { get; set; }
int Emboss { get; set; }
int ForeColor { get; set; }
int Hidden { get; set; }
int Engrave { get; set; }
int Italic { get; set; }
float Kerning { get; set; }
int LanguageID { get; set; }
string Name { get; set; }
int Outline { get; set; }
float Position { get; set; }
int Protected { get; set; }
int Shadow { get; set; }
float Size { get; set; }
int SmallCaps { get; set; }
float Spacing { get; set; }
int StrikeThrough { get; set; }
int Subscript { get; set; }
int Superscript { get; set; }
int Underline { get; set; }
int Weight { get; set; }
}
}

View File

@ -0,0 +1,80 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Duplicate")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C4-A1DF-11CE-8098-00AA0047BE5D")]
[TypeLibType(TypeLibTypeFlags.FDispatchable | TypeLibTypeFlags.FDual | TypeLibTypeFlags.FNonExtensible)]
public interface ITextPara
{
ITextPara Duplicate { get; set; }
int CanChange();
int IsEqual([In, MarshalAs(UnmanagedType.Interface)] ITextPara pPara);
void Reset([In] int Value);
int Style { get; set; }
int Alignment { get; set; }
int Hyphenation { get; set; }
float FirstLineIndent { get; }
int KeepTogether { get; set; }
int KeepWithNext { get; set; }
float LeftIndent { get; }
float LineSpacing { get; }
int LineSpacingRule { get; }
int ListAlignment { get; set; }
int ListLevelIndex { get; set; }
int ListStart { get; set; }
float ListTab { get; set; }
int ListType { get; set; }
int NoLineNumber { get; set; }
int PageBreakBefore { get; set; }
float RightIndent { get; set; }
void SetIndents([In] float StartIndent, [In] float LeftIndent, [In] float RightIndent);
void SetLineSpacing([In] int LineSpacingRule, [In] float LineSpacing);
float SpaceAfter { get; set; }
float SpaceBefore { get; set; }
int WidowControl { get; set; }
int TabCount { get; }
void AddTab([In] float tbPos, [In] int tbAlign, [In] int tbLeader);
void ClearAllTabs();
void DeleteTab([In] float tbPos);
void GetTab([In] int iTab, out float ptbPos, out int ptbAlign, out int ptbLeader);
}
}

View File

@ -0,0 +1,108 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Text")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C2-A1DF-11CE-8098-00AA0047BE5D")]
[TypeLibType(TypeLibTypeFlags.FDispatchable | TypeLibTypeFlags.FDual | TypeLibTypeFlags.FNonExtensible)]
public interface ITextRange
{
string Text { get; set; }
int Char { get; set; }
ITextRange GetDuplicate();
ITextRange FormattedText { get; set; }
int Start { get; set; }
int End { get; set; }
ITextFont Font { get; set; }
ITextPara Para { get; set; }
int StoryLength { get; }
int StoryType { get; }
void Collapse([In] int bStart);
int Expand([In] int Unit);
int GetIndex([In] int Unit);
void SetIndex([In] int Unit, [In] int Index, [In] int Extend);
void SetRange([In] int cpActive, [In] int cpOther);
int InRange([In, MarshalAs(UnmanagedType.Interface)] ITextRange pRange);
int InStory([In, MarshalAs(UnmanagedType.Interface)] ITextRange pRange);
int IsEqual([In, MarshalAs(UnmanagedType.Interface)] ITextRange pRange);
void Select();
int StartOf([In] int Unit, [In] int Extend);
int EndOf([In] int Unit, [In] int Extend);
int Move([In] int Unit, [In] int Count);
int MoveStart([In] int Unit, [In] int Count);
int MoveEnd([In] int Unit, [In] int Count);
int MoveWhile([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int MoveStartWhile([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int MoveEndWhile([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int MoveUntil([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int MoveStartUntil([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int MoveEndUntil([In, MarshalAs(UnmanagedType.Struct)] ref object Cset, [In] int Count);
int FindText([In, MarshalAs(UnmanagedType.BStr)] string bstr, [In] int cch, [In] int Flags);
int FindTextStart([In, MarshalAs(UnmanagedType.BStr)] string bstr, [In] int cch, [In] int Flags);
int FindTextEnd([In, MarshalAs(UnmanagedType.BStr)] string bstr, [In] int cch, [In] int Flags);
int Delete([In] int Unit, [In] int Count);
void Cut([MarshalAs(UnmanagedType.Struct)] out object pVar);
void Copy([MarshalAs(UnmanagedType.Struct)] out object pVar);
void Paste([In, MarshalAs(UnmanagedType.Struct)] ref object pVar, [In] int Format);
int CanPaste([In, MarshalAs(UnmanagedType.Struct)] ref object pVar, [In] int Format);
int CanEdit();
void ChangeCase([In] int Type);
void GetPoint([In] int Type, out int px, out int py);
void SetPoint([In] int x, [In] int y, [In] int Type, [In] int Extend);
void ScrollIntoView([In] int Value);
[return: MarshalAs(UnmanagedType.IUnknown)]
object GetEmbeddedObject();
}
}

View File

@ -0,0 +1,35 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Text")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C1-A1DF-11CE-8098-00AA0047BE5D")]
[TypeLibType(TypeLibTypeFlags.FDispatchable | TypeLibTypeFlags.FDual | TypeLibTypeFlags.FNonExtensible)]
public interface ITextSelection : ITextRange
{
int Flags { get; set; }
int Type { get; }
int MoveLeft([In] int Unit, [In] int Count, [In] int Extend);
int MoveRight([In] int Unit, [In] int Count, [In] int Extend);
int MoveUp([In] int Unit, [In] int Count, [In] int Extend);
int MoveDown([In] int Unit, [In] int Count, [In] int Extend);
int HomeKey([In] int Unit, [In] int Extend);
int EndKey([In] int Unit, [In] int Extend);
void TypeText([In, MarshalAs(UnmanagedType.BStr)] string bstr);
}
}

View File

@ -0,0 +1,22 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security;
using System.Text;
namespace Speak.RichEdit
{
[ComImport]
[DefaultMember("Item")]
[SuppressUnmanagedCodeSecurity]
[Guid("8CC497C5-A1DF-11CE-8098-00AA0047BE5D")]
public interface ITextStoryRanges : IEnumerable
{
[return: MarshalAs(UnmanagedType.Interface)]
ITextRange Item([In] int Index);
int Count { get; }
}
}

View File

@ -0,0 +1,100 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
using System.Text;
namespace Speak.RichEdit
{
internal static class REConstants
{
public static Int32 ErrTransparentConst = -9999997;
public const int WM_USER = 0x0400;
public const int EM_STREAMIN = WM_USER + 73;
public const int EM_STREAMOUT = WM_USER + 74;
public static int SF_RTF = 0x02;
public static int SF_TEXT = 0x01;
public static int SF_UNICODE = 0x010;
public const int ES_READONLY = 0x800;
public const int ES_AUTOVSCROLL = 0x40;
public static int SCF_SELECTION = 0x0001;
public static int SCF_WORD = 0x0002;
public static int SCF_ALL = 0x0004;
public static UInt32 CFM_LINK = 0x00000020;
public static UInt32 CFE_LINK = 0x0020;
public static int EM_GETLINE = 0xC4;
public static int EM_LINELENGTH = 0xC1;
public static int EM_POSFROMCHAR = 0xD6;
public static int EM_GETTEXTRANGE = 0x44;
public const int EM_GETCHARFORMAT = WM_USER + 58;
public static int EM_SETCHARFORMAT = WM_USER + 68;
public static int EM_HIDESELECTION = 0x43F;
public const int EM_CHARFROMPOS = 0x0D7;
public static int EM_LINEINDEX = 0x0BB;
public static int EM_EXLINEFROMCHAR = WM_USER + 54;
public static int EM_GETOLEINTERFACE = WM_USER + 60;
public static int EM_SETREADONLY = 0x00CF;
public static int TomStart = 0x20;
public static int TomEnd = 0;
public static int TA_TOP = 0;
public static int TA_BOTTOM = 8;
public static int TA_LEFT = 0;
public static int TA_RIGHT = 2;
}
public delegate UInt32 EditStreamCallback(IntPtr dwCookie, IntPtr pbBuff, Int32 cb, out IntPtr pcb);
[StructLayout(LayoutKind.Sequential)]
internal struct EditStream
{
public IntPtr dwCookie;
public UInt32 dwError;
public EditStreamCallback pfnCallback;
}
[StructLayout(LayoutKind.Sequential)]
public struct CHARFORMAT2_STRUCT
{
public UInt32 cbSize;
public UInt32 dwMask;
public UInt32 dwEffects;
public Int32 yHeight;
public Int32 yOffset;
public Int32 crTextColor;
public byte bCharSet;
public byte bPitchAndFamily;
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 32)]
public char[] szFaceName;
public UInt16 wWeight;
public UInt16 sSpacing;
public int crBackColor; // Color.ToArgb() -> Int32
public int lcid;
public int dwReserved;
public Int16 sStyle;
public Int16 wKerning;
public byte bUnderlineType;
public byte bAnimation;
public byte bRevAuthor;
public byte bReserved1;
}
public struct POINTL
{
public POINTL(int x, int y)
{
this.x = x;
this.y = y;
}
public int x;
public int y;
}
}

View File

@ -0,0 +1,656 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.IO;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Core;
using Speak.Interop;
using Speak.Sites;
using Speak.Structs;
using Speak.UI;
using Speak.Utils;
namespace Speak.RichEdit
{
[System.Runtime.InteropServices.GuidAttribute("1EC46826-B20F-4B93-830F-7ABC39F371CC")]
internal class RichEditHandler : IMessageProcessor
{
private IntPtr wHandle;
private IRichEditOle richEditOle;
private ITextDocument richEdit = null;
private IntPtr richEditPtr = IntPtr.Zero;
private IntPtr pRichEdit;
private IntPtr tmpPtr;
private ISite site;
private AvatarProcessor ap;
private SimpleWordAction srmmNickAction;
private SimpleWordAction srmmNumberAction;
private Subclassing subclass;
private ContextMenu context;
private List<ActionOleObject> btns = new List<ActionOleObject>();
private bool needRecalc;
private static Guid IID_ITextDocument = typeof(ITextDocument).GUID;
private static Guid IID_IOleObject = typeof(IOleObject).GUID;
public RichEditHandler(ISite site, IntPtr wHandle)
{
pRichEdit = IntPtr.Zero;
tmpPtr = IntPtr.Zero;
this.site = site;
this.wHandle = wHandle;
string errMessage = String.Empty;
tmpPtr = Marshal.AllocCoTaskMem(Marshal.SizeOf(typeof(IntPtr)));
Marshal.WriteIntPtr(tmpPtr, IntPtr.Zero);
try
{
richEditOle = RichEditHelpers.SendMessage(this.wHandle, REConstants.EM_GETOLEINTERFACE, 0);
subclass = new Subclassing(this.wHandle);
int subResult = subclass.StartSubclassing(WndProc);
if (subResult != 0)
throw new Exception(
"Epic fail of RichView subclassing." + Environment.NewLine +
"ErrorCode: " + subResult.ToString() + Environment.NewLine +
"Message: " + new System.ComponentModel.Win32Exception(subResult).Message);
if (WinApi.SendMessage(this.wHandle, REConstants.EM_GETOLEINTERFACE, IntPtr.Zero, tmpPtr) != 0)
{
pRichEdit = Marshal.ReadIntPtr(tmpPtr);
if (pRichEdit != IntPtr.Zero)
{
try
{
Marshal.QueryInterface(pRichEdit, ref IID_ITextDocument, out richEditPtr);
richEdit = (ITextDocument)Marshal.GetTypedObjectForIUnknown(richEditPtr, typeof(ITextDocument));
if (richEdit == null)
errMessage = "Failed to get the object wrapper for the interface.";
}
catch (Exception ex) { errMessage = ex.Message; }
}
else
{
errMessage = "Failed to get the pRichEdit pointer.";
}
}
}
catch (Exception ex) { errMessage = ex.Message; }
if (richEdit == null)
{
MessageBox.Show(
"Cant connect to SRMM's RichEdit window." + Environment.NewLine +
"Links highlighting will be disabled" + Environment.NewLine + Environment.NewLine +
errMessage,
"[xJuick] SRMM init error",
MessageBoxButtons.OK,
MessageBoxIcon.Error);
return;
}
srmmNickAction = Settings.Instance.SRMMNickAction;
srmmNumberAction = Settings.Instance.SRMMNumberAction;
ap = new AvatarProcessor(site);
MakeContextMenu();
Routine();
}
private void MakeContextMenu()
{
context = new ContextMenu();
foreach (LinkButton lb in Settings.Instance.SRMMLinkButtons)
{
if (!lb.Enabled)
continue;
ActionMenuItem mi = new ActionMenuItem(lb);
//mi.Image = IconTable.GetActionIcon(lb.IconName);
mi.Click += ActionMenuClick;
context.MenuItems.Add(mi);
}
ActionMenuItem contextAvatar = new ActionMenuItem(new LinkButton(String.Empty, String.Empty, false, LinkDisplayType.Image));
//contextAvatar.Image = Image.FromFile(ap.GetUserAvatar("xa0c", null));
context.MenuItems.Add(contextAvatar);
}
public int WndProc(IntPtr hWnd, int Msg, int wParam, int lParam)
{
bool lmb = false;
switch (Msg)
{
case WinApi.WM_LBUTTONDBLCLK:
case WinApi.WM_LBUTTONDOWN:
case WinApi.WM_LBUTTONUP:
int x = Util.LoWord(lParam);
int y = Util.HiWord(lParam);
foreach (ActionOleObject btn in btns)
{
if (btn.HitTest(x, y))
{
if (Msg == WinApi.WM_LBUTTONDOWN)
{
btn.SetLMBDownState();
}
else if (Msg == WinApi.WM_LBUTTONUP)
{
btn.SetLMBUpState(hWnd, Int32.MinValue);
}
lmb = true;
break;
}
}
break;
}
int result = 0;
if (!lmb)
result = subclass.CallParent(hWnd, Msg, wParam, lParam);
switch (Msg)
{
case WinApi.WM_MOUSEMOVE:
if (needRecalc)
{
SetActionObjectPosition();
needRecalc = false;
}
int x = Util.LoWord(lParam);
int y = Util.HiWord(lParam);
for (int i = 0, iCount = btns.Count; i < iCount; i++)
btns[i].MouseMoving(x, y);
if (((wParam & WinApi.MK_CONTROL) == WinApi.MK_CONTROL) && Settings.Instance.ShowPreview)
{
string url = GetCurrentURL(x, y);
if (!String.IsNullOrEmpty(url) /*&& ImagePreview.IsImage(url)*/)
{
POINT pt = new POINT(x,y);
WinApi.ClientToScreen(wHandle, ref pt);
ImagePreview.Show(pt.X, pt.Y+10, url);
}
else
{
ImagePreview.Hide();
}
}
else
{
ImagePreview.Hide();
}
break;
case REConstants.EM_STREAMIN:
Routine();
break;
case WinApi.WM_SETTEXT:
string text = Marshal.PtrToStringAnsi(new IntPtr(lParam));
if (String.IsNullOrEmpty(text))
btns.Clear();
break;
case WinApi.WM_PAINT:
needRecalc = true;
break;
case MainConstants.WM_REMAKERICH:
Routine();
needRecalc = true;
break;
}
return result;
}
public void SettingsChanged()
{
MakeContextMenu();
Avatars();
}
public void Update()
{
// well... do nothing :)
}
public void ShowThreads()
{
// not implemented :)
}
public void Avatars()
{
bool readOnly = (WinApi.GetWindowLong(wHandle, WinApi.GWL_STYLE) & REConstants.ES_READONLY) != 0;
if (readOnly)
WinApi.SendMessage(wHandle, REConstants.EM_SETREADONLY, 0, 0);
if (!Settings.Instance.ShowAvatars)
DeleteAvatars();
else
ShowAvatars();
if (readOnly)
WinApi.SendMessage(wHandle, REConstants.EM_SETREADONLY, 1, 0);
}
private void SetActionObjectPosition()
{
ITextRange range = richEdit.Range(0, Int32.MaxValue);
for (int i = 0, iCount = richEditOle.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (richEditOle.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
if (reoObject.clsid == ActionOleObject.Guid)
{
int x;
int y;
range.SetRange(reoObject.cp, reoObject.cp);
range.GetPoint(REConstants.TomStart | REConstants.TA_LEFT | REConstants.TA_BOTTOM, out x, out y);
IntPtr iaolep;
Marshal.QueryInterface(reoObject.poleobj, ref IID_IOleObject, out iaolep);
IActionOleObject iao = (IActionOleObject)Marshal.GetTypedObjectForIUnknown(iaolep, typeof(IActionOleObject));
POINT stc = new POINT(x, y);
WinApi.ScreenToClient(wHandle, ref stc);
iao.Left = stc.X;
iao.Bottom = stc.Y;
}
}
}
}
private void Routine()
{
bool readOnly = (WinApi.GetWindowLong(wHandle, WinApi.GWL_STYLE) & REConstants.ES_READONLY) != 0;
if (readOnly)
WinApi.SendMessage(wHandle, REConstants.EM_SETREADONLY, 0, 0);
richEdit.Freeze();
string text = richEdit.Range(0, Int32.MaxValue).Text;
// posts/comments
Match m = site.NumRegex.Match(text);
while (m.Success)
{
string victimWord = m.Groups["full"].Value;
ActionWordType actionWord = !String.IsNullOrEmpty(m.Groups["cmnt"].Value)
? ActionWordType.Comments
: ActionWordType.Post;
int selStart = text.IndexOf(victimWord);
bool correctID = true;
if (victimWord.Length < 3)
correctID = false;
// fucking urls
if (correctID && victimWord.Length < 5)
{
richEdit.Selection.Start = selStart;
richEdit.Selection.End = selStart+1;
CHARFORMAT2_STRUCT cf = new CHARFORMAT2_STRUCT();
cf.cbSize = (UInt32) Marshal.SizeOf(cf);
cf.szFaceName = new char[32];
IntPtr wpar = new IntPtr(REConstants.SCF_SELECTION);
IntPtr lpar = Marshal.AllocCoTaskMem(Marshal.SizeOf(cf));
Marshal.StructureToPtr(cf, lpar, false);
new IntPtr(WinApi.SendMessage(wHandle, REConstants.EM_GETCHARFORMAT, wpar, lpar));
cf = (CHARFORMAT2_STRUCT) Marshal.PtrToStructure(lpar, typeof (CHARFORMAT2_STRUCT));
if (
((cf.dwMask & REConstants.CFM_LINK) == REConstants.CFM_LINK) &&
((cf.dwEffects & REConstants.CFE_LINK) == REConstants.CFE_LINK)
)
{
correctID = false;
}
Marshal.FreeCoTaskMem(lpar);
}
if (correctID)
{
AddActionObject(selStart, victimWord, actionWord);
text = richEdit.Range(0, Int32.MaxValue).Text;
}
m = m.NextMatch();
}
// JIDs
m = Regexps.JidRegEx.Match(text);
while (m.Success)
{
string victimWord = m.Groups["name"].Value;
AddActionObject(text.IndexOf(victimWord), victimWord, ActionWordType.Nick);
text = richEdit.Range(0, Int32.MaxValue).Text;
m = m.NextMatch();
}
// @nicks
m = site.NameRegex.Match(text);
while (m.Success)
{
string victimWord = m.Groups["name"].Value;
ActionObjectType objectType = !String.IsNullOrEmpty(m.Groups["isFirst"].Value) ? ActionObjectType.FirstNick : ActionObjectType.Nick;
AddActionObject(text.IndexOf(victimWord), victimWord, ActionWordType.Nick, objectType);
text = richEdit.Range(0, Int32.MaxValue).Text;
m = m.NextMatch();
}
richEdit.Unfreeze();
// avatars
if (Settings.Instance.ShowAvatars)
ShowAvatars();
if (readOnly)
WinApi.SendMessage(wHandle, REConstants.EM_SETREADONLY, 1, 0);
}
private void DeleteAvatars()
{
richEdit.Freeze();
for (int i = 0, iCount = richEditOle.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (richEditOle.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
if (reoObject.clsid == AvatarObject.Guid)
{
richEdit.Range(reoObject.cp, reoObject.cp + 2).Text = "";
}
}
}
for (int i = 0, iCount = btns.Count; i < iCount; i++)
{
if(btns[i].ObjectType == ActionObjectType.FirstNick)
btns[i].IsTailObjectSet = false;
}
richEdit.Unfreeze();
// well... Надо бы инвалидейт вместо скролла сделать, нр-но
//WinApi.SendMessage(wHandle, WinApi.WM_VSCROLL, 7, 0);
WinApi.SendMessage(wHandle, MainConstants.WM_REMAKERICH, 0, 0);
}
private void ShowAvatars()
{
richEdit.Freeze();
List<KeyValuePair<string, int>> avatars = new List<KeyValuePair<string, int>>();
//Int32 lastLine = -1;
for (int i = 0, iCount = richEditOle.GetObjectCount(); i < iCount; i++)
{
REOBJECT reoObject = new REOBJECT();
if (richEditOle.GetObject(i, reoObject, GETOBJECTOPTIONS.REO_GETOBJ_POLEOBJ) == 0)
{
if (reoObject.clsid == ActionOleObject.Guid)
{
IntPtr iaolep;
Marshal.QueryInterface(reoObject.poleobj, ref IID_IOleObject, out iaolep);
IActionOleObject iao = (IActionOleObject)Marshal.GetTypedObjectForIUnknown(iaolep, typeof(IActionOleObject));
if (!iao.IsTailObjectSet && iao.ObjectType == ActionObjectType.FirstNick)
{
int lineIndex = WinApi.SendMessage(wHandle, REConstants.EM_EXLINEFROMCHAR, 0, reoObject.cp);
// select for yourself
//int charOffset = reoObject.cp - WinApi.SendMessage(wHandle, REConstants.EM_LINEINDEX, lineIndex, 0);
//avatars.Add(new KeyValuePair<string, int>(iao.Text.Substring(1), reoObject.cp + avatars.Count - (lastLine != lineIndex ? charOffset : 0)));
avatars.Add(new KeyValuePair<string, int>(iao.Text.Substring(1), reoObject.cp + avatars.Count));
//lastLine = lineIndex;
iao.IsTailObjectSet = true;
}
}
}
}
int offset = 0;
foreach (KeyValuePair<string, int> ava in avatars)
{
int index = offset + ava.Value;
richEdit.Selection.Start = index;
richEdit.Selection.End = index;
Color backColor = richEdit.Selection.Font.BackColor != REConstants.ErrTransparentConst ? ColorTranslator.FromWin32(richEdit.Selection.Font.BackColor) : LogWindow.SRMMBackColor;
RichEditHelpers.InsertControl(richEditOle, new AvatarObject(ap, ava.Key, backColor));
richEdit.Range(index + 1, index + 1).Text = " ";
offset += 1;
}
ap.Process();
richEdit.Unfreeze();
}
private void ActionMenuClick(object sender, EventArgs e)
{
ActionMenuItem mi = (ActionMenuItem) sender;
InvokeJuick(new ActionClickEvent(mi.Action, mi.AutoSend));
}
private void actionObject_JuickClicked(object sender, ActionObjectClickEvent e)
{
ActionWordType actionWord = e.ActionType;
if (e.MenuLocation != Point.Empty)
{
if (actionWord == ActionWordType.None)
return;
for (int i = 0, iCount = context.MenuItems.Count; i < iCount; i++)
{
ActionMenuItem btn = (ActionMenuItem)context.MenuItems[i];
btn.MainWord = e.ActionText;
if (btn.DisplayType != LinkDisplayType.Always)
{
if (
(btn.DisplayType == LinkDisplayType.Comments && actionWord != ActionWordType.Comments) ||
(btn.DisplayType == LinkDisplayType.Posts && actionWord != ActionWordType.Post) ||
(btn.DisplayType == LinkDisplayType.Nicks && actionWord != ActionWordType.Nick)
)
{
btn.Visible = false;
continue;
}
}
if (btn.DisplayType == LinkDisplayType.Image)
{
if (Settings.Instance.ShowContextAvatars)
{
string avatarPath = ap.GetUserAvatar(btn.MainWord.Substring(1), null);
if (String.IsNullOrEmpty(avatarPath))
{
ap.Process();
btn.Visible = false;
continue;
}
else
{
btn.Image = Image.FromFile(avatarPath);
}
}
else
{
btn.Visible = false;
continue;
}
}
Match m = site.NumRegex.Match(btn.MainWord);
if (m.Success)
{
if (!String.IsNullOrEmpty(m.Groups["cmnt"].Value))
{
btn.AdditionalWord = m.Groups["full"].Value;
btn.MainWord = m.Groups["post"].Value;
}
}
btn.Visible = true;
continue;
}
context.Show(sender as Control, e.MenuLocation);
}
else
{
if (actionWord == ActionWordType.Nick)
InvokeJuick(new ActionClickEvent(srmmNickAction.Action.Replace("%NICK%", e.ActionText), srmmNickAction.Autosend));
else if (actionWord == ActionWordType.Post || actionWord == ActionWordType.Comments)
InvokeJuick(new ActionClickEvent(srmmNumberAction.Action.Replace("%NUMBER%", e.ActionText), srmmNumberAction.Autosend));
}
}
private void AddActionObject(int selStart, string fullWord, ActionWordType actionType)
{
AddActionObject(selStart, fullWord, actionType, ActionObjectType.Default);
}
private void AddActionObject(int selStart, string fullWord, ActionWordType actionType, ActionObjectType objectType)
{
richEdit.Selection.Start = selStart;
richEdit.Selection.End = selStart + fullWord.Length;
ActionOleObject aoo = new ActionOleObject();
aoo.ObjectType = objectType;
aoo.ActionType = actionType;
aoo.ActionClicked += actionObject_JuickClicked;
ITextFont font = richEdit.Selection.Font;
aoo.BgColor = font.BackColor != REConstants.ErrTransparentConst ? ColorTranslator.FromWin32(font.BackColor) : LogWindow.SRMMBackColor;
aoo.Font = new Font(font.Name, font.Size);
aoo.ForeColor = ColorTranslator.FromWin32(font.ForeColor);
aoo.Text = fullWord;
btns.Add(aoo);
RichEditHelpers.InsertControl(richEditOle, aoo);
}
private string GetCurrentURL(int x, int y)
{
POINTL pointl = new POINTL(x, y);
Subclassing.SetLastError(0);
int charIndex = WinApi.SendMessage(wHandle, REConstants.EM_CHARFROMPOS, 0, ref pointl);
int err = Marshal.GetLastWin32Error();
if (err != 0 && err != 6)
return String.Empty;
if (charIndex <= 0)
return null;
int lineIndex = WinApi.SendMessage(wHandle, REConstants.EM_EXLINEFROMCHAR, 0, charIndex);
int charOffset = charIndex - WinApi.SendMessage(wHandle, REConstants.EM_LINEINDEX, lineIndex, 0);
int len = WinApi.SendMessage(wHandle, REConstants.EM_LINELENGTH, charIndex, 0);
string line = richEdit.Range(charIndex - charOffset, (charIndex - charOffset) + len).Text;
if (String.IsNullOrEmpty(line))
return null;
if (charOffset == len)
return null;
string result = String.Empty;
int i = charOffset - 1;
int j = charOffset - 1;
try
{
while (i >= 0 && line[i] != ' ')
{
i--;
}
i = i + 1;
if (j == -1)
return null;
while (j < len && line[j] != ' ')
{
j++;
}
if (j < i)
return null;
result = line.Substring(i, j - i).Trim();
if (result.IndexOf("http://") != -1)
{
return result;
}
}
catch { return String.Empty; }
return String.Empty;
}
public event EventHandler<ActionClickEvent> JuickClicked;
public void InvokeJuick(ActionClickEvent e)
{
EventHandler<ActionClickEvent> handler = JuickClicked;
if (handler != null) handler(this, e);
}
#region Implementation of IDisposable
public void Dispose()
{
if (pRichEdit != IntPtr.Zero)
{
Marshal.Release(pRichEdit);
pRichEdit = IntPtr.Zero;
}
if (tmpPtr != IntPtr.Zero)
{
Marshal.FreeCoTaskMem(tmpPtr);
tmpPtr = IntPtr.Zero;
}
if (richEditPtr != IntPtr.Zero)
{
Marshal.Release(richEditPtr);
richEditPtr = IntPtr.Zero;
}
if (richEditOle != null)
{
richEditOle = null;
}
if (subclass != null)
{
subclass.StopSubclass();
subclass.Dispose();
}
richEdit = null;
}
#endregion
}
}

View File

@ -0,0 +1,138 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Text;
using Speak.Interop;
using Speak.Structs;
namespace Speak.RichEdit
{
internal static class RichEditHelpers
{
private static Guid IID_ITextDocument = typeof(ITextDocument).GUID;
private static Type TFVCNDATAType = typeof(TFVCNDATA_NMHDR);
private static Int32 TFVCNDATASize = Marshal.SizeOf(TFVCNDATAType);
[DllImport("ole32.dll", PreserveSig = false)]
public static extern int CreateILockBytesOnHGlobal(IntPtr hGlobal, bool fDeleteOnRelease, [Out] out ILockBytes ppLkbyt);
[DllImport("ole32.dll")]
public static extern int StgCreateDocfileOnILockBytes(ILockBytes plkbyt, uint grfMode, uint reserved, out IStorage ppstgOpen);
//public static int WM_USER = 0x0400;
//public static int EM_GETOLEINTERFACE = WM_USER + 60;
[DllImport("User32.dll", CharSet = CharSet.Auto, PreserveSig = false)]
public static extern IRichEditOle SendMessage(IntPtr hWnd, int message, int wParam);
public static void InsertControl(IRichEditOle richEditOle, IActionOleGUID control)
{
if (control == null || richEditOle == null)
return;
ILockBytes pLockBytes;
CreateILockBytesOnHGlobal(IntPtr.Zero, true, out pLockBytes);
IOleClientSite pOleClientSite;
richEditOle.GetClientSite(out pOleClientSite);
REOBJECT reoObject = new REOBJECT();
reoObject.cp = -1;//REO_CP_SELECTION;
reoObject.clsid = control.GUID;
reoObject.poleobj = Marshal.GetIUnknownForObject(control);
reoObject.polesite = pOleClientSite;
reoObject.dvAspect = (uint)(DVASPECT.DVASPECT_CONTENT);
reoObject.dwFlags = (uint)(REOOBJECTFLAGS.REO_BELOWBASELINE | REOOBJECTFLAGS.REO_BLANK);
richEditOle.InsertObject(reoObject);
Marshal.ReleaseComObject(pLockBytes);
Marshal.ReleaseComObject(pOleClientSite);
}
public static ITextDocument GetIText(IntPtr handle)
{
IntPtr pRichEdit = IntPtr.Zero;
IntPtr tmpPtr = IntPtr.Zero;
IntPtr richEditPtr = IntPtr.Zero;
tmpPtr = Marshal.AllocCoTaskMem(Marshal.SizeOf(typeof(IntPtr)));
Marshal.WriteIntPtr(tmpPtr, IntPtr.Zero);
ITextDocument richEdit = null;
if (WinApi.SendMessage(handle, REConstants.EM_GETOLEINTERFACE, IntPtr.Zero, tmpPtr) != 0)
{
if ((pRichEdit = Marshal.ReadIntPtr(tmpPtr)) != IntPtr.Zero)
{
Marshal.QueryInterface(pRichEdit, ref IID_ITextDocument, out richEditPtr);
richEdit = (ITextDocument)Marshal.GetTypedObjectForIUnknown(richEditPtr, typeof(ITextDocument));
if (richEdit == null)
throw new Exception("Failed to get the object wrapper for the interface.");
}
else
{
throw new Exception("Failed to get the pRichEdit pointer.");
}
}
return richEdit;
}
public static RichEditInfo GetRichEditInfo(IntPtr owner, IntPtr mainHandle)
{
TFVCNDATA_NMHDR mh = new TFVCNDATA_NMHDR();
mh.cbSize = TFVCNDATASize;
mh.handleFrom = owner;
mh.code = HppConstaints.NM_FIREVIEWCHANGE;
mh.bEvent = HppConstaints.FVCN_GETINFO;
mh.bAction = HppConstaints.FVCA_NONE;
mh.rcRect = new RECT(0, 0, 0, 0);
IntPtr cmd = Marshal.AllocHGlobal(TFVCNDATASize);
Marshal.StructureToPtr(mh, cmd, false);
WinApi.SendMessage(mainHandle, WinApi.WM_NOTIFY, owner, cmd);
mh = (TFVCNDATA_NMHDR)Marshal.PtrToStructure(cmd, TFVCNDATAType);
if (mh.bAction == HppConstaints.FVCA_INFO)
return new RichEditInfo(mh.rcRect, mh.clrBackground.GetColor());
return RichEditInfo.Empty;
}
}
internal class RichEditInfo
{
private RECT rect;
private Color bgColor;
public RichEditInfo(RECT rect, Color bgColor)
{
this.rect = rect;
this.bgColor = bgColor;
}
public static RichEditInfo Empty
{
get { return new RichEditInfo(RECT.Empty, Color.Empty);}
}
public bool IsEmpty
{
get { return rect.IsEmpty && bgColor.IsEmpty; }
}
public RECT Rect
{
get { return rect; }
}
public Color BgColor
{
get { return bgColor; }
}
}
}

View File

@ -0,0 +1,83 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.Xml.Serialization;
namespace Speak.Sites
{
[Serializable]
public class BNWSite : ISite
{
private string name;
private string mainContact;
private string[] additionalContacts;
private static Regex numRegEx = new Regex(
"(?<full>(?<post>\\#[A-Z\\d]+)(?<cmnt>/[A-Z\\d]+)?)",
RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
private static Regex nameRegEx = new Regex(
"(?<name>\\B@\\w+[-_\\.\\w]*\\w+)(?<isFirst>\\:{1})?",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public BNWSite()
{
name = "BNW";
mainContact = "bnw.blasux.ru";
additionalContacts = new string[0];
}
public override ISite CreateDefaultInstance()
{
return new BNWSite();
}
#region -=[ Avatars ]=-
public override string GetAvatarPath(string userName)
{
return String.Empty;
}
#endregion
[XmlIgnore]
public override Regex NumRegex
{
get { return numRegEx; }
}
[XmlIgnore]
public override Regex NameRegex
{
get { return nameRegEx; }
}
public override string Name
{
get { return name; }
set { name = value; }
}
public override string MainContact
{
get { return mainContact; }
set { mainContact = value; }
}
public override string[] AdditionalContacts
{
get { return additionalContacts; }
set { additionalContacts = value; }
}
}
}

View File

@ -0,0 +1,43 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.Xml.Serialization;
namespace Speak.Sites
{
[Serializable]
public abstract class ISite
{
public abstract ISite CreateDefaultInstance();
public abstract string GetAvatarPath(string userName);
[XmlIgnore]
public abstract Regex NumRegex
{
get;
}
[XmlIgnore]
public abstract Regex NameRegex
{
get;
}
public abstract string Name
{
get; set;
}
public abstract string MainContact
{
get; set;
}
public abstract string[] AdditionalContacts
{
get; set;
}
}
}

View File

@ -0,0 +1,116 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.Xml;
using System.Xml.Serialization;
using Speak.Core;
namespace Speak.Sites
{
[Serializable]
public class JuickSite : ISite
{
private string name;
private string mainContact;
private string[] additionalContacts;
private static Regex numRegEx = new Regex(
"(?<full>(?<post>\\#\\d+)(?<cmnt>/\\d+)?)",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
private static Regex nameRegEx = new Regex(
"(?<name>\\B@\\w+[-_\\.\\w]*\\w+)(?<isFirst>\\:{1})?",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public JuickSite()
{
name = "Juick";
mainContact = "juick@juick.com";
additionalContacts = new string[] {"jubo@nologin.ru"};
}
public override ISite CreateDefaultInstance()
{
return new JuickSite();
}
#region -=[ Avatars ]=-
private static string ava32 = "http://i.juick.com/as/{0}.png";
//private static string ava96 = "http://i.juick.com/a/{0}.png";
private static string rss = "http://rss.juick.com/{0}/blog";
public override string GetAvatarPath(string userName)
{
string userUrl = String.Format(rss, userName);
string avatarUrl = String.Empty;
string rssContent = HTTP.StaticSendGet(userUrl);
XmlDocument doc = new XmlDocument();
try
{
doc.LoadXml(rssContent);
}
catch { }
XmlNodeList nodes = doc.GetElementsByTagName("image");
if (nodes == null || nodes.Count == 0)
return avatarUrl;
XmlNodeList childNodes = nodes[0].ChildNodes;
for (int i = 0, iCount = childNodes.Count; i < iCount; i++)
{
if (childNodes[i].Name.Equals("url", StringComparison.InvariantCultureIgnoreCase))
{
Match m = Regexps.UID.Match(childNodes[i].InnerXml);
if (m.Success)
avatarUrl = String.Format(ava32, m.Groups["uid"].Value);
break;
}
}
return avatarUrl;
}
#endregion
[XmlIgnore]
public override Regex NumRegex
{
get { return numRegEx; }
}
[XmlIgnore]
public override Regex NameRegex
{
get { return nameRegEx; }
}
public override string Name
{
get { return name; }
set { name = value; }
}
public override string MainContact
{
get { return mainContact; }
set { mainContact = value; }
}
public override string[] AdditionalContacts
{
get { return additionalContacts; }
set { additionalContacts = value; }
}
}
}

View File

@ -0,0 +1,102 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Text.RegularExpressions;
using System.Xml.Serialization;
using Speak.Core;
namespace Speak.Sites
{
[Serializable]
public class PstoSite : ISite
{
private string name;
private string mainContact;
private string[] additionalContacts;
private static Regex numRegEx = new Regex(
"(?<full>(?<post>\\#[A-Za-z\\d]+)(?<cmnt>/[\\d]+)?)",
RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
private static Regex nameRegEx = new Regex(
"(?<name>\\B@\\w+[-_\\.\\w]*\\w+)(?<isFirst>\\:{1}|\\ \\-\\>)?",
RegexOptions.IgnoreCase
| RegexOptions.Multiline
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
private static Regex AvaIDRegEx = new Regex(
"src=\\\"/(?:.+?)/80/(?<avaID>\\d+)\\.png\\\"",
RegexOptions.IgnoreCase
| RegexOptions.Singleline
| RegexOptions.CultureInvariant
| RegexOptions.IgnorePatternWhitespace
| RegexOptions.Compiled
);
public PstoSite()
{
name = "Psto";
mainContact = "psto@psto.net";
additionalContacts = new string[0];
}
public override ISite CreateDefaultInstance()
{
return new PstoSite();
}
#region -=[ Avatars ]=-
private string userPageUrl = "http://{0}.psto.net";
private string avaUrl = "http://psto.net/img/a/40/{0}.png";
public override string GetAvatarPath(string userName)
{
string userUrl = String.Format(userPageUrl, userName);
string avatarUrl = String.Empty;
string userPageContent = HTTP.StaticSendGet(userUrl);
Match m = AvaIDRegEx.Match(userPageContent);
if (m.Success)
avatarUrl = String.Format(avaUrl, m.Groups["avaID"].Value);
return avatarUrl;
}
#endregion
[XmlIgnore]
public override Regex NumRegex
{
get { return numRegEx; }
}
[XmlIgnore]
public override Regex NameRegex
{
get { return nameRegEx; }
}
public override string Name
{
get { return name; }
set { name = value; }
}
public override string MainContact
{
get { return mainContact; }
set { mainContact = value; }
}
public override string[] AdditionalContacts
{
get { return additionalContacts; }
set { additionalContacts = value; }
}
}
}

View File

@ -0,0 +1,66 @@
using System;
using System.Collections.Generic;
using System.Text;
using Speak.Core;
namespace Speak.Sites
{
class SitesManager
{
public static Dictionary<string, ISite> Sites;
public static Dictionary<IntPtr, ISite> SitesInfo;
static SitesManager()
{
Sites = new Dictionary<string, ISite>();
SitesInfo = new Dictionary<IntPtr, ISite>();
ISite juick = new JuickSite();
Sites.Add(juick.Name, juick);
ISite bnw = new BNWSite();
Sites.Add(bnw.Name, bnw);
ISite psto = new PstoSite();
Sites.Add(psto.Name, psto);
}
public static ISite CreateDefaultSiteInstance()
{
ISite site = new PstoSite();
site.AdditionalContacts = new string[0];
return site;
}
public static ISite GetContactSite(IntPtr hContact)
{
if (SitesInfo.ContainsKey(hContact))
return SitesInfo[hContact];
return null;
}
public static ISite GetContactSite(string UID, bool searchInAdditional)
{
for (int i = 0, iCount = Settings.Instance.Sites.Length; i < iCount; i++)
{
if (UID.Equals(Settings.Instance.Sites[i].MainContact, StringComparison.InvariantCultureIgnoreCase))
{
return Settings.Instance.Sites[i];
}
if (!searchInAdditional)
continue;
for (int j = 0, jCount = Settings.Instance.Sites[i].AdditionalContacts.Length; j < jCount; j++)
{
if (UID.Equals(Settings.Instance.Sites[i].AdditionalContacts[j], StringComparison.InvariantCultureIgnoreCase))
{
return Settings.Instance.Sites[i];
}
}
}
return null;
}
}
}

169
Speak/Speak/Speak.csproj Normal file
View File

@ -0,0 +1,169 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{EC92954F-19E9-43D6-8871-09C651108FA9}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>Speak</RootNamespace>
<AssemblyName>Speak.master</AssemblyName>
<TargetFrameworkVersion>v3.5</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<TargetFrameworkProfile />
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>..\..\..\..\..\Desktop\Miranda\Plugins\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
<PlatformTarget>x86</PlatformTarget>
<DocumentationFile>..\..\..\..\..\Desktop\Miranda\Plugins\Speak.master.XML</DocumentationFile>
<NoWarn>1591</NoWarn>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>..\..\..\..\..\Desktop\Miranda\Plugins\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
<PlatformTarget>x86</PlatformTarget>
<DocumentationFile>..\..\..\..\..\Desktop\Miranda\Plugins\Speak.master.XML</DocumentationFile>
<NoWarn>1591</NoWarn>
</PropertyGroup>
<PropertyGroup>
<Win32Resource>C:\Users\netz\Documents\Visual Studio 2012\Projects\Speak\Speak\Opt\dialog.res</Win32Resource>
</PropertyGroup>
<ItemGroup>
<Reference Include="Hyphen">
<HintPath>..\..\..\..\..\Desktop\Miranda\Plugins\Hyphen.dll</HintPath>
<Private>False</Private>
</Reference>
<Reference Include="System" />
<Reference Include="System.Drawing" />
<Reference Include="System.Speech" />
<Reference Include="System.Web" />
<Reference Include="System.Windows.Forms" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="Core\ActionClickEvent.cs" />
<Compile Include="Core\ActionProcessor.cs" />
<Compile Include="Core\AvatarProcessor.cs" />
<Compile Include="Core\Buttons.cs" />
<Compile Include="Core\HTTP.cs" />
<Compile Include="Core\ImagePreview.cs" />
<Compile Include="Core\IMessageProcessor.cs" />
<Compile Include="Core\LinkButton.cs" />
<Compile Include="Core\LogWindow.cs" />
<Compile Include="Core\MirandaDB.cs" />
<Compile Include="Core\Regexps.cs" />
<Compile Include="Core\Settings.cs" />
<Compile Include="Fork\ContactContainer.cs" />
<Compile Include="Fork\ContactManager.cs" />
<Compile Include="HPP\HistoryppHandler.cs" />
<Compile Include="HPP\HppActionOleObject.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="HPP\HppAvatarObject.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="Interfaces\HTMLDispIDs.cs" />
<Compile Include="Interfaces\HTMLDocumentEvents2.cs" />
<Compile Include="Interfaces\IHTMLDocument2.cs" />
<Compile Include="Interfaces\IHTMLElement.cs" />
<Compile Include="Interfaces\IHTMLEventObj.cs" />
<Compile Include="Interfaces\IHTMLStyle.cs" />
<Compile Include="Interop\IEHandler.cs" />
<Compile Include="Interop\Structs.cs" />
<Compile Include="Interop\Subclassing.cs" />
<Compile Include="Interop\WinApi.cs" />
<Compile Include="MainClass.cs" />
<Compile Include="Opt\Options.cs" />
<Compile Include="Opt\Win32ImageList.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Properties\Resources.Designer.cs">
<AutoGen>True</AutoGen>
<DesignTime>True</DesignTime>
<DependentUpon>Resources.resx</DependentUpon>
</Compile>
<Compile Include="RichEdit\ActionOleObject.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="RichEdit\AvatarObject.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="RichEdit\IRichEditOle.cs" />
<Compile Include="RichEdit\ITextDocument.cs" />
<Compile Include="RichEdit\ITextFont.cs" />
<Compile Include="RichEdit\ITextPara.cs" />
<Compile Include="RichEdit\ITextRange.cs" />
<Compile Include="RichEdit\ITextSelection.cs" />
<Compile Include="RichEdit\ITextStoryRanges.cs" />
<Compile Include="RichEdit\REConstants.cs" />
<Compile Include="RichEdit\RichEditHandler.cs" />
<Compile Include="RichEdit\RichEditHelpers.cs" />
<Compile Include="Sites\BNWSite.cs" />
<Compile Include="Sites\ISite.cs" />
<Compile Include="Sites\JuickSite.cs" />
<Compile Include="Sites\PstoSite.cs" />
<Compile Include="Sites\SitesManager.cs" />
<Compile Include="Storage\Settings.cs" />
<Compile Include="Structs\API.cs" />
<Compile Include="Structs\IconLib.cs" />
<Compile Include="Structs\Miranda.cs" />
<Compile Include="Structs\TabSRMM.cs" />
<Compile Include="TTS\TextToSpeak.cs" />
<Compile Include="UI\ActionMenuItem.cs">
<SubType>Component</SubType>
</Compile>
<Compile Include="UI\PreviewForm.cs">
<SubType>Form</SubType>
</Compile>
<Compile Include="UI\PreviewForm.designer.cs">
<DependentUpon>PreviewForm.cs</DependentUpon>
</Compile>
<Compile Include="Utils\IconTable.cs" />
<Compile Include="Utils\Invokable.cs" />
<Compile Include="Utils\Util.cs" />
</ItemGroup>
<ItemGroup>
<Content Include="Resources\icon_message.ico" />
<Content Include="Resources\icon_small_dot.ico" />
<Content Include="Resources\status_online.ico" />
<Content Include="Speak.dll">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</Content>
</ItemGroup>
<ItemGroup>
<None Include="Opt\dialog.res" />
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="Properties\Resources.resx">
<Generator>ResXFileCodeGenerator</Generator>
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
</EmbeddedResource>
<EmbeddedResource Include="UI\PreviewForm.resx">
<DependentUpon>PreviewForm.cs</DependentUpon>
</EmbeddedResource>
</ItemGroup>
<ItemGroup />
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<PropertyGroup>
<PostBuildEvent>if not exist IL mkdir IL
"C:\Program Files (x86)\Microsoft SDKs\Windows\v7.0A\Bin\x64\ildasm.exe" /linenum "$(TargetFileName)" /out="IL\$(ProjectName).il"</PostBuildEvent>
</PropertyGroup>
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets.
<Target Name="BeforeBuild">
</Target>
<Target Name="AfterBuild">
</Target>
-->
</Project>

BIN
Speak/Speak/Speak.dll Normal file

Binary file not shown.

View File

@ -0,0 +1,157 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections.ObjectModel;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Speak.Opt;
namespace Speak.Storage
{
class Settings
{
private class Contact
{
public string Status;
public bool message_read;
public bool status_read;
public Contact(string status, bool rmessage, bool rstatus)
{
this.Status = status;
this.message_read = rmessage;
this.status_read = rstatus;
}
}
private static Settings instance;
private Dictionary<string, Contact> contactlist;
private long maxTextLength = 0;
private bool globalActive = true;
private bool unknownmessageread = true;
private bool unknownstatusread = true;
/// <summary>
/// Get a Setting Class
/// </summary>
/// <returns>Settings Object</returns>
public static Settings getInstance()
{
if (instance == null)
instance = new Settings();
return instance;
}
private Settings()
{
this.contactlist = new Dictionary<string, Contact>();
}
public void ReadContactList()
{
this.contactlist = new Dictionary<string, Contact>();
ReadOnlyCollection<ContactInfo> list = MirandaContext.Current.MirandaDatabase.GetContacts();
foreach (ContactInfo item in list)
{
if (item.UniqueID != null)
{
//System.Windows.Forms.MessageBox.Show("leer");
Contact c = new Contact(item.Status.ToString(),
Options.readDBBool("message", "speak_config", item.MirandaHandle, true),
Options.readDBBool("status", "speak_config", item.MirandaHandle, true));
this.contactlist.Add(item.UniqueID.ToString(), c);
}
}
}
public void SetGlobalSettings()
{
this.maxTextLength = Options.readDBLong("max_msg_size", "speak_config");
this.globalActive = Options.readDBBool("active", "speak_config", true);
this.unknownmessageread = Options.readDBBool("message_u", "speak_config", true);
this.unknownstatusread = Options.readDBBool("status_u", "speak_config", true);
}
public bool canMessageRead(string text, string uid)
{
if (!this.globalActive)
{
return false;
}
if (text.Length > this.maxTextLength)
{
return false;
}
Contact c;
try
{
c = this.contactlist[uid];
}
catch (System.Collections.Generic.KeyNotFoundException)
{
return this.unknownmessageread;
}
return c.message_read;
}
public string getSpeakString()
{
return "{0} meint: {1}";
}
public bool hasChangedStatus(string uid, string status)
{
Contact c;
try
{
c = this.contactlist[uid];
}
catch (System.Collections.Generic.KeyNotFoundException)
{
if (uid != "" && status != "")
{
ReadContactList();
return true;
}
return false;
}
if (c.Status != status)
{
this.contactlist[uid] = new Contact(status, c.message_read, c.status_read);
return true;
}
return false;
}
public bool canStatusRead(string uid)
{
Contact c = this.contactlist[uid];
if (c != null)
{
return c.status_read;
}
return this.unknownstatusread;
}
public string getStatusString(StatusMode? status)
{
switch (status)
{
case StatusMode.Offline:
return "{0} ist Off";
case StatusMode.Online:
return "{0} ist da";
case StatusMode.Away:
return "{0} ist nur mal kurz weg";
case StatusMode.Invisible:
return "{0} hat sich versteckt";
case StatusMode.NA:
return "{0} ist nicht mehr da";
case StatusMode.DND:
return "{0} will in ruhe gelassen werden, schnautze";
case StatusMode.Occupied:
return "{0} ist beschäftigt";
case StatusMode.FreeForChat:
return "{0} will chatten";
}
return "{0} ist {1}";
}
}
}

View File

@ -0,0 +1,98 @@
using System;
namespace Speak.Structs
{
internal static class API
{
public static string MS_SYSTEM_GETVERSION = "Miranda/System/GetVersion";
public static string MS_DB_EVENT_ADD = "DB/Event/Add";
public static string MS_DB_EVENT_GET = "DB/Event/Get";
public static string MS_DB_EVENT_DELETE = "DB/Event/Delete";
public static string MS_DB_EVENT_GETBLOBSIZE = "DB/Event/GetBlobSize";
public static string MS_DB_TIME_TIMESTAMPTOLOCAL = "DB/Time/TimestampToLocal";
public static string MS_PROTO_ADDTOCONTACT = "Proto/AddToContact";
public static string MS_PROTO_ISPROTOONCONTACT = "Proto/IsProtoOnContact";
public static string MS_PROTO_REGISTERMODULE = "Proto/RegisterModule";
public static string MS_PROTO_CHAINSEND = "Proto/ChainSend";
public static string MS_PROTO_CHAINRECV = "Proto/ChainRecv";
public static string MS_PROTO_CALLCONTACTSERVICE = "Proto/CallContactService";
public static string MS_PROTO_GETCONTACTBASEPROTO = "Proto/GetContactBaseProto";
public static string PS_SETSTATUS = "/SetStatus";
public static string PS_GETSTATUS = "/GetStatus";
public static string PSR_MESSAGE = "/RecvMessage";
public static string PSR_MESSAGEW = "/RecvMessageW";
public static string PSS_MESSAGE = "/SendMsg";
public static string PSS_MESSAGEW = "/SendMsgW"; // instant send msg
public static string MS_MSG_SENDMESSAGE = "SRMsg/SendCommand"; // type msg
public static string ME_MSG_WINDOWEVENT = "MessageAPI/WindowEvent";
public static string MS_SKIN2_ADDICON = "Skin2/Icons/AddIcon";
public static string MS_SKIN2_GETICON = "Skin2/Icons/GetIcon";
public static string MS_SKIN2_GETICONBYHANDLE = "Skin2/Icons/GetIconByHandle";
public static string ME_SKIN2_ICONSCHANGED = "Skin2/IconsChanged";
public static string MS_BB_ADDBUTTON = "TabSRMM/ButtonsBar/AddButton";
public static string MS_BB_REMOVEBUTTON = "TabSRMM/ButtonsBar/RemoveButton";
public static string MS_BB_GETBUTTONSTATE = "TabSRMM/ButtonsBar/GetButtonState";
public static string MS_BB_SETBUTTONSTATE = "TabSRMM/ButtonsBar/SetButtonState";
public static string ME_MSG_TOOLBARLOADED = "TabSRMM/ButtonsBar/ModuleLoaded";
public static string ME_MSG_BUTTONPRESSED = "TabSRMM/ButtonsBar/ButtonPressed";
public static string ME_IEVIEW_OPTIONSCHANGED = "IEVIEW/OptionsChanged";
public static string ME_DB_CONTACT_SETTINGCHANGED = "DB/Contact/SettingChanged";
public static string ME_DB_EVENT_ADDED = "DB/Event/Added";
public static string MS_UTILS_OPENURL = "Utils/OpenURL";
public static string ME_OPT_INITIALISE = "Opt/Initialise";
public static string MS_OPT_ADDPAGE = "Opt/AddPage";
public static string MS_GC_NEWSESSION = "GChat/NewChat";
public static string MS_MSG_GETWINDOWCLASS = "MessageAPI/WindowClass";
public static string MS_PROTO_ENUMPROTOS = "Proto/EnumProtos";
public static string MS_PROTO_ENUMPROTOCOLS = "Proto/EnumProtocols";
public static string MS_PROTO_ENUMACCOUNTS = "Proto/EnumAccounts";
public static string MS_IEVIEW_WINDOW = "IEVIEW/NewWindow";
public static string ME_HPP_RICHEDIT_ITEMPROCESS = "History++/RichEdit/ItemProcessEvent";
public static string MS_HPP_EG_WINDOW = "History++/ExtGrid/NewWindow";
public static string MS_HPP_GETVERSION = "History++/GetVersion";
public static string MS_DB_GETPROFILEPATH = "DB/GetProfilePath";
public static string MS_DB_GETPROFILENAME = "DB/GetProfileName";
public static Int32 CALLSERVICE_NOTFOUND = unchecked((int) 0x80000000);
public static string MS_DB_CONTACT_FINDFIRST = "DB/Contact/FindFirst";
public static string MS_DB_CONTACT_FINDNEXT = "DB/Contact/FindNext";
}
public enum StatusModes
{
Offline = 40071,
Online = 40072,
Away = 40073,
DND = 40074,
NA = 40075,
Occupied = 40076,
FreeForChat = 40077,
Invisible = 40078,
OnThePhone = 40079,
OutToLunch = 40080,
Idle = 40081
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.Runtime.InteropServices;
namespace Speak.Structs
{
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
struct IconName
{
public Int32 cbSize;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szSection;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szDescription;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszName;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pczDefaultFile;
public Int32 iDefaultIndex;
public IntPtr hDefaultIcon;
public Int32 cx;
public Int32 cy;
public Int32 flags;
public void Init()
{
pszName = pczDefaultFile = String.Empty;
cx = cy = 16;
}
}
}

View File

@ -0,0 +1,462 @@
using System;
using System.Runtime.InteropServices;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Interop;
using Speak.Utils;
namespace Speak.Structs
{
public static class MainConstants
{
public const UInt32 MSG_WINDOW_EVT_OPENING = 1; // window is about to be opened
public const UInt32 MSG_WINDOW_EVT_OPEN = 2; // window has been opened
public const UInt32 MSG_WINDOW_EVT_CLOSING = 3; // window is about to be closed
public const UInt32 MSG_WINDOW_EVT_CLOSE = 4; // window has been closed
public const UInt32 MSG_WINDOW_EVT_CUSTOM = 5; // custom event for message plugins to use
// (custom uFlags may be used)
public const Int32 MSG_WINDOW_UFLAG_MSG_FROM = 0x00000001;
public const Int32 MSG_WINDOW_UFLAG_MSG_TO = 0x00000002;
public const Int32 MSG_WINDOW_UFLAG_MSG_BOTH = 0x00000004;
public const Int32 DBEF_UTF = 16;
public const Int32 MI_IDC_LOG = 1001; // rich edit
public const Int32 MI_IDC_MESSAGE = 1002; // edit control
public const Int32 MI_IDC_QUOTE = 1034; // button control
public const Int32 MI_IDC_NAME = 1009; // text control
public const Int32 MI_IDC_ADD = 1070; // add button
public const Int32 WM_REMAKERICH = WinApi.WM_USER + 0x3457;
public const uint ODPF_BOLDGROUPS = 4;
}
public static class ContactListConstants
{
public const int CLM_FIRST = 0x1000; //this is the same as LVM_FIRST
public const int CLN_FIRST = -100;
public const int CLM_ADDINFOITEM = CLM_FIRST + 53; //lParam=&cii, returns hItem
public const int CLM_SETEXTRAIMAGELIST = CLM_FIRST + 32; //lParam=HIMAGELIST, wParam=WideImageList
public const int CLM_SETBKBITMAP = CLM_FIRST + 27; //wParam=mode, lParam=hBitmap (don't delete it), NULL for none
public const int CLM_SETBKCOLOR = CLM_FIRST + 28; //wParam=a COLORREF, default is GetSysColor(COLOR_3DFACE)
public const int CLM_SETGREYOUTFLAGS = CLM_FIRST + 39; //wParam=new flags
public const int CLM_SETLEFTMARGIN = CLM_FIRST + 47; //wParam=pixels
public const int CLM_SETINDENT = CLM_FIRST + 34; //wParam=new indent, default is 3 pixels
public const int FONTID_MAX = 18;
public const int CLM_SETTEXTCOLOR = CLM_FIRST + 52; //wParam=FONTID_, lParam=COLORREF
public const int CLS_SHOWHIDDEN = 0x0002;
public const int CLM_SETEXTRACOLUMNS = CLM_FIRST + 30; //wParam=number of extra columns (zero to MAXEXTRACOLUMNS from clc.h, currently 16)
public const int CLCIIF_GROUPFONT = 0x80;
public const int CLM_FINDCONTACT = CLM_FIRST + 8; //wParam=hContact, returns an hItem
public const int CLM_GETEXTRAIMAGE = CLM_FIRST + 16; ////wParam=hItem, lParam=MAKELPARAM(iColumn (0 based),0), returns iImage or 0xFFa
public const int CLM_SETEXTRAIMAGE = CLM_FIRST + 31; //wParam=hItem, lParam=MAKELPARAM(iColumn (0 based),iImage). iImage=0xFF is a blank
public const int CLM_AUTOREBUILD = CLM_FIRST+2;
public const int CLM_GETNEXTITEM = CLM_FIRST + 50; //wParam=flag, lParam=hItem, returns an hItem
public const int CLGN_ROOT = 0;
public const int CLM_GETITEMTYPE = CLM_FIRST + 49; //wParam=hItem, returns a CLCIT_
public const int CLCIT_GROUP = 0;
public const int CLGN_NEXTGROUP = 7;
public const int CLGN_CHILD = 1;
public const int CLCIT_CONTACT = 1;
public const int CLGN_NEXTCONTACT = 5;
public const int CLM_GETEXTRAIMAGELIST = CLM_FIRST + 17; //returns HIMAGELIST
public const int CLN_OPTIONSCHANGED = CLN_FIRST - 6; //nothing valid. If you set some extended options they have been overwritten and should be re-set
public const int CLN_NEWCONTACT = CLN_FIRST - 8; //hItem,flags valid. sent when a new contact is added without a full list rebuild
public const int CLN_LISTREBUILT = CLN_FIRST - 9; //hItem,flags valid. sent when contact is moved without a full list rebuild
public const int CLM_HITTEST = CLM_FIRST + 25; //lParam=MAKELPARAM(x,y) (relative to control), wParam=(PDWORD)&hitTest (see encoding of HitTest() in clc.h, can be NULL) returns hItem or NULL
public const int CLCIT_INFO = 3;
}
public static class StandartIcons
{
public const string SKINICON_OTHER_SMALLDOT = "Small Dot";
public const string SKINICON_EVENT_MESSAGE = "Message";
public const string ID_STATUS_ONLINE = "Online";
}
public static class HppConstaints
{
public static Version MinumumVersion = new Version(1, 5, 1, 4);
public const UInt32 IRDHW_CONTACTHISTORY = 0x1;
public const UInt32 IRDHW_GLOBALHISTORY = 0x2;
public const UInt32 IRDHW_GLOBALSEARCH = 0x3;
public const UInt32 IRDHW_EXTERNALGRID = 0x4;
public const UInt32 IRDF_SELECTED = 0x1;
public const UInt32 IRDF_INLINE = 0x2;
public const UInt32 IRDF_EVENT = 0x4;
public const Int32 NM_FIREVIEWCHANGE = 1;
public const Int32 FVCN_PREFIRE = 1;
public const Int32 FVCN_POSTFIRE = 2;
public const Int32 FVCA_NONE = 0;
public const Int32 FVCA_INFO = 255;
public const Int32 FVCN_GETINFO = 255;
public const Int32 FVCA_DRAW = 1;
public const Int32 FVCA_CUSTOMDRAW = 2;
}
[StructLayout(LayoutKind.Sequential)]
struct MessageWindowEventData
{
public Int32 cbSize;
public IntPtr hContact;
public IntPtr hWnd; // top level window for the contact
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szModule; // used to get plugin type (which means you could use local if needed)
public UInt32 uType; // see event types below
public UInt32 uFlags; // used to indicate message direction for all event types except custom
public IntPtr pointer; // used to store pointer to custom data
public IntPtr hWndInput; // input area window for the contact (or NULL if there is none)
public IntPtr hLog; // log area window for the contact (or NULL if there is none)
}
[StructLayout(LayoutKind.Sequential, Pack = 1)]
internal struct ItemRenderDetails
{
public UInt32 cbSize;
public IntPtr hContact;
public IntPtr hDBEvent;
public UInt32 dwEventTime;
public UInt16 wEventType;
public byte isEventSent;
public UInt32 dwFlags; // ???
public byte bHistoryWindow;
public IntPtr pProto;
public IntPtr pModule;
public IntPtr pText;
public IntPtr pExtended;
public string Proto
{
get { return pProto == IntPtr.Zero ? String.Empty : Marshal.PtrToStringAnsi(pProto); }
}
public string Module
{
get { return pModule == IntPtr.Zero ? String.Empty : Marshal.PtrToStringAnsi(pModule); }
}
public string Text
{
get { return pText == IntPtr.Zero ? String.Empty : Marshal.PtrToStringUni(pText); }
}
public string Extended
{
get { return pExtended == IntPtr.Zero ? String.Empty : Marshal.PtrToStringAnsi(pExtended); }
}
public bool IsEventSent
{
get { return Convert.ToBoolean(isEventSent); }
}
}
[StructLayout(LayoutKind.Sequential)]
internal struct NMCLISTCONTROL
{
public NMHDR hdr;
public int hItem;
public int action;
public int iColumn;
public int flags;
public POINT pt;
}
[StructLayout(LayoutKind.Sequential)]
internal struct TFVCNDATA_NMHDR
{
public IntPtr handleFrom;
public UInt32 idFrom;
public UInt32 code;
public Int32 cbSize;
public byte bEvent;
public byte bAction;
public IntPtr hDC;
public RECT rcRect;
public COLORREF clrBackground;
public bool fTransparent;
public IntPtr lparam;
}
[StructLayout(LayoutKind.Sequential)]
internal struct DBTimeToString
{
public IntPtr Format;
public IntPtr Output;
public int MaxBytes;
public DBTimeToString(string format)
{
UnmanagedStringHandle str = new UnmanagedStringHandle(format, StringEncoding.Ansi);
this.Format = str.IntPtr;
this.Output = IntPtr.Zero;
this.MaxBytes = 0;
}
public void Free()
{
if (this.Format != IntPtr.Zero)
{
Marshal.FreeHGlobal(this.Format);
}
}
}
[StructLayout(LayoutKind.Sequential)]
struct ProtoRecieveEvent
{
public UInt32 flags;
public UInt32 timestamp;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 2048)]
public string szMessage;
public Int32 lParam;
}
[StructLayout(LayoutKind.Sequential)]
struct PGDest
{
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszModule; //Name of the protocol (same as you registered with)
public IntPtr szID; //Unique identifier of the session, or NULL to broadcast to all sessions as specified above
public Int32 iType; //Use GC_EVENT_* as defined above. Only one event per service call.
public string ID
{
set { szID = Marshal.StringToHGlobalAnsi(value); }
}
public void Free()
{
if (szID != IntPtr.Zero)
{
Marshal.FreeHGlobal(szID);
szID = IntPtr.Zero;
}
}
}
[StructLayout(LayoutKind.Sequential)]
struct GCEvent
{
public Int32 cbSize;
public IntPtr pDest; // pointer to a GCDEST structure which specifies the session to receive the event
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szText; // usage depends on type of event, max 2048 characters
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szNick; // usage depends on type of event
public IntPtr szUID; // usage depends on type of event, Do NOT use spaces for unique user identifiers.
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szStatus; // usage depends on type of event
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szUserInfo; // Additional user information that is displayed after the nickname.
// IRC use it to display a hostmask for JOIN, PART (and more) events.
public bool bIsMe; // Is this event from the Miranda user?
public UInt32 dwFlags; // event flags: GCEF_ADDTOLOG, GC_UNICODE
// FALSE any other time than when initializing the window (before sending SESSION_INITDONE)
public UInt32 dwItemData; // User specified data.
public UInt32 time; // Timestamp of the event
public GCEvent(bool z)
{
cbSize = 0;
pDest = new IntPtr();
szText = null;
szNick = null;
szUID = new IntPtr();
szStatus = null;
szUserInfo = null;
bIsMe = false;
dwFlags = 0u;
dwItemData = 0u;
time = 0u;
}
public string UID
{
set { szUID = Marshal.StringToHGlobalAnsi(value); }
}
public void Free()
{
if (szUID != IntPtr.Zero)
{
Marshal.FreeHGlobal(szUID);
szUID = IntPtr.Zero;
}
}
}
[StructLayout(LayoutKind.Sequential)]
struct GCRegister
{
public Int32 cbSize; //Set to sizeof(GCREGISTER);
public UInt32 dwFlags; //Use GC_* flags above to indicate features supported
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszModule; //This MUST be the protocol name as registered with Miranda IM
public IntPtr pszModuleDispName; //This is the protocol's real name as it will be displayed to the user
public Int32 iMaxText; //Max message length the protocol supports. Will limit the typing area input. 0 = no limit
public Int32 nColors; //Number of colors in the colorchooser menu for the color buttons. Max = 100
public IntPtr pColors; // ^TCOLORREF; //pointer to the first item in a static COLORREF array containing the colors
//that should be showed in the colorchooser menu.
//ie: COLORREF crCols[nColors];
// pColors = &crCols[0];
public string ModuleDispName
{
set { pszModuleDispName = Marshal.StringToHGlobalAnsi(value); }
}
public void Free()
{
if (pszModuleDispName != IntPtr.Zero)
{
Marshal.FreeHGlobal(pszModuleDispName);
pszModuleDispName = IntPtr.Zero;
}
}
}
[StructLayout(LayoutKind.Sequential)]
struct GSession
{
public Int32 cbSize; //Set to sizeof(GCSESSION);
public Int32 iType; //Use one of the GCW_* flags above to set the type of session
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszModule; //The name of the protocol owning the session (the same as pszModule when you register)
public IntPtr szName; //The name of the session as it will be displayed to the user
//[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public IntPtr szID; //The unique identifier for the session.
public IntPtr szStatusbarText; //Optional text to set in the statusbar of the chat room window, or NULL.
public UInt32 dwFlags;
public UInt32 dwItemData; //Set user defined data for this session. Retrieve it by using the GC_EVENT_GETITEMDATA event
public string StatusbarText
{
set { szStatusbarText = Marshal.StringToHGlobalAnsi(value); }
}
public string Name
{
set { szName = Marshal.StringToHGlobalAnsi(value); }
}
public string ID
{
set { szID = Marshal.StringToHGlobalAnsi(value); }
}
public void Free()
{
if (szStatusbarText != IntPtr.Zero)
{
Marshal.FreeHGlobal(szStatusbarText);
szStatusbarText = IntPtr.Zero;
}
if (szName != IntPtr.Zero)
{
Marshal.FreeHGlobal(szName);
szName = IntPtr.Zero;
}
if (szID != IntPtr.Zero)
{
Marshal.FreeHGlobal(szID);
szID = IntPtr.Zero;
}
}
}
[StructLayout(LayoutKind.Sequential)]
public struct CSSData
{
public IntPtr hContact;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string szProtoService;
public IntPtr wParam;
public IntPtr lParam;
}
/*typedef struct {
int cbSize;
const TCHAR *pszText;
HANDLE hParentGroup;
DWORD flags;
HICON hIcon; //todo
} CLCINFOITEM;*/
[StructLayout(LayoutKind.Sequential)]
public struct CLCINFOITEM
{
public Int32 cbSize;
public IntPtr pszText;
public IntPtr hParentGroup;
public UInt32 flags;
public IntPtr hIcon;
}
[StructLayout(LayoutKind.Sequential)]
public struct OptionsDialogPage
{
public Int32 cbSize;
public Int32 position;
//[MarshalAsAttribute(UnmanagedType.LPTStr, SizeConst = 64)]
//public string szTitle;
public IntPtr szTitle;
public IntPtr pfnDlgProc;
public IntPtr pszTemplate;
public IntPtr hInstance; // Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly().GetModules()[0])
public IntPtr hIcon;
//[MarshalAsAttribute(UnmanagedType.LPTStr, SizeConst = 64)]
public IntPtr szGroup;
public Int32 groupPosition;
public IntPtr hGroupIcon;
public UInt32 flags;
public Int32 nIDBottomSimpleControl;
public Int32 nIDRightSimpleControl;
public Int32 expertOnlyControls;
public Int32 nExpertOnlyControls;
public Int32 szTab;
//public IntPtr dwInitParam;
}
[StructLayout(LayoutKind.Sequential, Pack = 4)]
public struct PLUGININFOEX
{
public int Size;
[MarshalAs(UnmanagedType.LPStr)]
public string ShortName;
public uint Version;
[MarshalAs(UnmanagedType.LPStr)]
public string Description;
[MarshalAs(UnmanagedType.LPStr)]
public string Author;
[MarshalAs(UnmanagedType.LPStr)]
public string AuthorEmail;
[MarshalAs(UnmanagedType.LPStr)]
public string Copyright;
[MarshalAs(UnmanagedType.LPStr)]
public string HomePage;
public byte Flags;
public int ReplacesDefaultModule;
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = 32+16+16+8)]
public byte[] MUUID; // Ex
}
}

View File

@ -0,0 +1,63 @@
using System;
using System.Runtime.InteropServices;
using Speak.Interop;
namespace Speak.Structs
{
public static class TabSRMMConstants
{
public const UInt32 BBBF_DISABLED = 0x0001;
public const UInt32 BBBF_HIDDEN = 0x0002;
public const UInt32 BBBF_ISPUSHBUTTON = 0x0004;
public const UInt32 BBBF_ISARROWBUTTON = 0x0008;
public const UInt32 BBBF_ISCHATBUTTON = 0x0010;
public const UInt32 BBBF_ISIMBUTTON = 0x0020;
public const UInt32 BBBF_ISLSIDEBUTTON = 0x0040;
public const UInt32 BBBF_ISRSIDEBUTTON = 0x0080;
public const UInt32 BBBF_CANBEHIDDEN = 0x0100;
public const UInt32 BBBF_ISDUMMYBUTTON = 0x0200;
public const UInt32 BBBF_ANSITOOLTIP = 0x0400;
public const UInt32 BBBF_CREATEBYID = 0x0800; //only for tabsrmm internal use
public const UInt32 BBSF_DOSNT_EXISTS = 0; // added by xa0c
public const UInt32 BBSF_HIDDEN = 1;
public const UInt32 BBSF_DISABLED = 2;
public const UInt32 BBSF_PUSHED = 4;
public const UInt32 BBSF_RELEASED = 8;
}
[StructLayout(LayoutKind.Sequential)]
struct CustomButtonClickData
{
public Int32 cbSize;
public POINT point;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszName;
public UInt32 dwButtonID;
public IntPtr hwindForm;
public IntPtr hContact;
public UInt32 flags;
}
[StructLayout(LayoutKind.Sequential)]
struct BBButton
{
public Int32 cbSize;
public UInt32 dwButtonID;
[MarshalAsAttribute(UnmanagedType.LPStr, SizeConst = 64)]
public string pszModuleName;
[MarshalAsAttribute(UnmanagedType.LPTStr, SizeConst = 64)]
public string szTooltip;
public UInt32 dwDefPos;
public Int32 iButtonWidth;
public UInt32 bbbFlags;
public IntPtr hIcon;
}
}

View File

@ -0,0 +1,157 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Speech.Synthesis;
using System.Collections.ObjectModel;
using System.Threading;
namespace Speak.TTS
{
/// <summary>
/// Speak Text
/// </summary>
class TextToSpeak
{
private SpeechSynthesizer syn;
private Queue<string> quene;
private static TextToSpeak instance;
private List<string> last;
private Boolean runner;
private Thread workerThread;
/// <summary>
/// Returns the Instance of TextToSpeak Class
/// </summary>
/// <returns>TextToSpeak</returns>
public static TextToSpeak getInstance()
{
if (instance == null)
instance = new TextToSpeak();
return instance;
}
private TextToSpeak()
{
this.syn = new SpeechSynthesizer();
this.quene = new Queue<string>();
this.last = new List<string>();
this.runner = true;
this.workerThread = new Thread(this.Speaker);
workerThread.Start();
while (!workerThread.IsAlive) ;
}
private void Speaker()
{
while (runner)
{
string text = "";
try
{
text = quene.Dequeue();
}
catch (InvalidOperationException) { }
if (text != "")
{
syn.Speak(text);
}
else
{
Thread.Sleep(300);
}
}
}
/// <summary>
/// Adds a Text to the to Speak Quene
/// </summary>
/// <param name="text">Text that will be spoken</param>
/// <param name="signature">Signature of Message, to catch to offten spoken text</param>
public void speak(string text, string signature)
{
if (!last.Contains(signature))
{
last.Add(signature);
quene.Enqueue(text);
}
if (last.Count > 10)
{
last.RemoveAt(0);
}
}
/// <summary>
/// Returns a list of Installed Voices
/// </summary>
/// <returns></returns>
public static List<String> getVoices()
{
List<string> ret = new List<string>();
ReadOnlyCollection<InstalledVoice> voices = new SpeechSynthesizer().GetInstalledVoices();
foreach (InstalledVoice item in voices)
{
ret.Add(item.VoiceInfo.Name);
}
return ret;
}
/// <summary>
/// Sets a voice to the current Speak Engine
/// </summary>
/// <param name="voice">Name of the Voice</param>
/// <returns></returns>
public bool setVoice(string voice)
{
if (voice == "")
return false;
this.syn.SelectVoice(voice);
return this.syn.Voice.Name == voice;
}
/// <summary>
/// Set a new Volume to the Current Speak Engine
/// </summary>
/// <param name="volume"></param>
/// <returns>from 0 to 100</returns>
public bool setVolume(int volume)
{
if (volume > 100 || volume < 0)
return false;
this.syn.Volume = volume;
return this.syn.Volume == volume;
}
/// <summary>
/// Set a new Rate to the Current Speak engine
/// </summary>
/// <param name="rate"></param>
/// <returns>from 0 to 100</returns>
public bool setRate(int rate)
{
if (rate > 100 || rate < 0)
return false;
rate = rate / 5;
rate = rate - 10;
this.syn.Rate = rate;
return this.syn.Rate == rate;
}
/// <summary>
/// Setting a new Pitch to the current Speak Engine
/// NOT IMPLEMENTED
/// </summary>
/// <param name="pitch"></param>
/// <returns></returns>
public bool setPitch(int pitch)
{
return true;
}
public void Stop()
{
this.workerThread.Abort();
this.runner = false;
}
}
}

View File

@ -0,0 +1,132 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using Speak.Core;
namespace Speak.UI
{
public class ActionMenuItem : MenuItem
{
private Image itemImage;
private string displayName;
private string action;
private bool autoSend;
private LinkDisplayType displayType;
private string mainWord;
private string additionalWord;
public ActionMenuItem(LinkButton link)
{
OwnerDraw = true;
Text = displayName = link.DisplayName;
action = link.Action;
autoSend = link.AutoSend;
mainWord = String.Empty;
additionalWord = String.Empty;
displayType = link.DisplayType;
}
public Image Image
{
get { return itemImage; }
set { itemImage = value; }
}
public LinkDisplayType DisplayType
{
get { return displayType; }
set { displayType = value; }
}
public string Action
{
get { return action.Replace("%NUMBER%", mainWord).Replace("%NICK%", mainWord).Replace("%COMMENT%", additionalWord); }
set { action = value; }
}
public bool AutoSend
{
get { return autoSend; }
set { autoSend = value; }
}
public string AdditionalWord
{
get { return additionalWord; }
set { additionalWord = value; }
}
public string MainWord
{
get { return mainWord; }
set
{
mainWord = value;
Text = displayName.Replace("%NUMBER%", mainWord).Replace("%NICK%", mainWord).Replace("%COMMENT%", additionalWord);
}
}
protected override void OnMeasureItem(MeasureItemEventArgs e)
{
Font menuFont = SystemInformation.MenuFont;
StringFormat strfmt = new StringFormat();
SizeF sizef = e.Graphics.MeasureString(Text, menuFont, 1000, strfmt);
e.ItemWidth = (int)Math.Ceiling(sizef.Width) + itemImage.Width;
e.ItemHeight = itemImage.Height > sizef.Height ? itemImage.Height : (int)Math.Ceiling(sizef.Height);
base.OnMeasureItem(e);
}
protected override void OnDrawItem(DrawItemEventArgs e)
{
Font menuFont = SystemInformation.MenuFont;
SolidBrush menuBrush = null;
if (Enabled == false)
{
menuBrush = new SolidBrush(SystemColors.GrayText);
}
else
{
menuBrush = (e.State & DrawItemState.Selected) != 0 ? new SolidBrush(SystemColors.HighlightText) : new SolidBrush(SystemColors.MenuText);
}
StringFormat strfmt = new StringFormat();
strfmt.LineAlignment = StringAlignment.Center;
Rectangle rectImage = e.Bounds;
rectImage.Width = itemImage.Width;
rectImage.Height = itemImage.Height;
if (displayType != LinkDisplayType.Image)
{
rectImage.Y = e.Bounds.Top + (e.Bounds.Height - itemImage.Height) / 2;
}
else
{
rectImage.X = e.Bounds.Left + (e.Bounds.Width - itemImage.Width) / 2;
rectImage.Y = e.Bounds.Top + (e.Bounds.Height - itemImage.Height) / 2;
}
Rectangle rectText = e.Bounds;
rectText.X += rectImage.Width;
e.Graphics.FillRectangle(
(e.State & DrawItemState.Selected) != 0 ? SystemBrushes.Highlight : SystemBrushes.Menu,
e.Bounds);
e.Graphics.DrawImage(itemImage, rectImage);
e.Graphics.DrawString(
Text, menuFont, menuBrush,
e.Bounds.Left + itemImage.Width,
e.Bounds.Top + ((e.Bounds.Height) / 2),
strfmt);
menuBrush.Dispose();
}
}
}

View File

@ -0,0 +1,205 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.IO;
using System.Net;
using System.Text;
using System.Threading;
using System.Windows.Forms;
using Speak.Core;
using Speak.Interop;
namespace Speak.UI
{
public partial class PreviewForm : Form
{
private HTTP http;
private Thread downloadThread;
private Image image;
private string url;
private int retryCount;
private int sleep = 1500;
private bool abort;
public PreviewForm()
{
InitializeComponent();
url = String.Empty;
http = new HTTP();
}
protected override CreateParams CreateParams
{
get
{
const int CS_DROPSHADOW = 0x20000;
CreateParams param = base.CreateParams;
param.ClassStyle += CS_DROPSHADOW;
return param;
}
}
private void GetImage()
{
Stream imageStream = http.GetImage(url, false);
if (imageStream is MemoryStream && imageStream.Length == 0)
{
SetError("Error while downloading");
return;
}
try
{
/*
byte[] bt = new byte[255];
int read = 0;
FileStream fs = File.OpenWrite("C:\\img.jpg");
while ((read = imageStream.Read(bt, 0, 255)) != 0)
{
fs.Write(bt, 0, read);
}
fs.Close();
return;
*/
image = Image.FromStream(imageStream);
if (image.Height == 1)
{
if (abort)
{
SetError("Aborted");
abort = false;
return;
}
SetError("Uncached, retrying [" + ++retryCount + "]...");
Thread.Sleep(sleep);
GetImage();
}
SetError("done");
CrossInvalidate();
}
catch
{
SetError("Cant create image");
}
}
private delegate void CrossInvalidateDelegate();
private void CrossInvalidate()
{
if (this.InvokeRequired)
{
CrossInvalidateDelegate d = CrossInvalidate;
this.Invoke(d, new object[0]);
}
else
{
Draw(Graphics.FromHwnd(Handle));
}
}
private delegate void SetErrorDelegate(string errorText);
private void SetError(string errorText)
{
if (lblInfo.InvokeRequired)
{
SetErrorDelegate d = SetError;
lblInfo.Invoke(d, new object[] { errorText });
}
else
{
lblInfo.Text = errorText;
}
}
private void Clear()
{
lblInfo.Text = "Loading...";
lblInfo.Visible = true;
Width = 150;
Height = 80;
retryCount = 0;
abort = false;
url = String.Empty;
}
new public void Show()
{
Clear();
base.Show();
}
new public void Hide()
{
if (downloadThread != null)
{
//abort = true;
//downloadThread.Abort();
}
base.Hide();
}
private void Draw(Graphics g)
{
Width = image.Width;
Height = image.Height;
g.SmoothingMode = SmoothingMode.AntiAlias;
g.InterpolationMode = InterpolationMode.HighQualityBicubic;
g.CompositingQuality = CompositingQuality.HighQuality;
lblInfo.Visible = false;
g.DrawImage(image, 0, 0, Width, Height);
}
protected override void OnPaint(PaintEventArgs e)
{
if (image == null || image.Height == 1)
{
base.OnPaint(e);
}
else
{
Draw(e.Graphics);
}
}
protected override void OnPaintBackground(PaintEventArgs e)
{
if (image == null || image.Height == 1)
{
base.OnPaintBackground(e);
}
else
{
Draw(e.Graphics);
}
}
public string Url
{
set
{
if (!url.Equals(value))
{
Clear();
url = value;
if(downloadThread != null)
{
abort = true;
//downloadThread.Abort();
}
downloadThread = new Thread(GetImage);
downloadThread.IsBackground = false;
downloadThread.Start();
}
}
}
}
}

66
Speak/Speak/UI/PreviewForm.designer.cs generated Normal file
View File

@ -0,0 +1,66 @@
namespace Speak.UI
{
partial class PreviewForm
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
this.lblInfo = new System.Windows.Forms.Label();
this.SuspendLayout();
//
// lblInfo
//
this.lblInfo.Dock = System.Windows.Forms.DockStyle.Fill;
this.lblInfo.Location = new System.Drawing.Point(0, 0);
this.lblInfo.Name = "lblInfo";
this.lblInfo.Size = new System.Drawing.Size(150, 80);
this.lblInfo.TabIndex = 0;
this.lblInfo.Text = "Loading...";
this.lblInfo.TextAlign = System.Drawing.ContentAlignment.MiddleCenter;
//
// PreviewForm
//
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(255)))), ((int)(((byte)(224)))), ((int)(((byte)(192)))));
this.ClientSize = new System.Drawing.Size(150, 80);
this.Controls.Add(this.lblInfo);
this.DoubleBuffered = true;
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;
this.Name = "PreviewForm";
this.ShowIcon = false;
this.ShowInTaskbar = false;
this.StartPosition = System.Windows.Forms.FormStartPosition.Manual;
this.TopMost = true;
this.ResumeLayout(false);
}
#endregion
private System.Windows.Forms.Label lblInfo;
}
}

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@ -0,0 +1,30 @@
using System;
using System.Drawing;
using Speak.Core;
using Speak.Properties;
using Speak.Structs;
namespace Speak.Utils
{
internal static class IconTable
{
public static IntPtr GetDefaultIcon(string btnName)
{
switch (btnName)
{
case StandartIcons.SKINICON_OTHER_SMALLDOT:
return Resources.icon_small_dot.Handle;
case StandartIcons.SKINICON_EVENT_MESSAGE:
return Resources.icon_message.Handle;
case StandartIcons.ID_STATUS_ONLINE:
return Resources.status_online.Handle;
}
return Resources.icon_small_dot.Handle;
}
/*public static Image GetActionIcon(string btnName)
{
return Resources.icon_small_dot;
}*/
}
}

View File

@ -0,0 +1,134 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
namespace Speak.Utils
{
// It's fucking awesome.
// So am I. :)
internal class Invokable
{
private const int GWL_WNDPROC = -4;
private const int WM_USER = 0x0400;
private const int WF_THREADCALLBACKMESSAGE = WM_USER + 123;
[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern int SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll")]
static extern IntPtr CreateWindowEx(int dwExStyle, string lpClassName, string lpWindowName, uint dwStyle, int x, int y, int nWidth, int nHeight, IntPtr hWndParent, IntPtr hMenu, IntPtr hInstance, IntPtr lpParam);
[DllImport("user32.dll")]
static extern uint GetWindowThreadProcessId(IntPtr hWnd, IntPtr ProcessId);
[DllImport("kernel32.dll")]
static extern uint GetCurrentThreadId();
[DllImport("user32")]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex, IntPtr newProc);
[DllImport("user32")]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex, Win32WndProc newProc);
[DllImport("user32")]
private static extern int CallWindowProc(IntPtr lpPrevWndFunc, IntPtr hWnd, int Msg, int wParam, int lParam);
private delegate int Win32WndProc(IntPtr hWnd, int Msg, int wParam, int lParam);
[DllImport("user32.dll", CharSet = CharSet.Unicode, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool DestroyWindow(IntPtr hwnd);
private Queue<CallBackDelegate> callbackDelegates;
private Win32WndProc wProc;
private IntPtr oldWndProc = IntPtr.Zero;
private IntPtr handle;
public Invokable(IntPtr parent)
{
callbackDelegates = new Queue<CallBackDelegate>();
handle = CreateWindowEx(0, "#32769", "WF_InvokableNativeWindow", 0, -1, -1, 0, 0, parent, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);
StartSubclass();
}
private void StartSubclass()
{
wProc = new Win32WndProc(WndProc);
if (oldWndProc != IntPtr.Zero)
SetWindowLong(handle, GWL_WNDPROC, wProc);
else
oldWndProc = SetWindowLong(handle, GWL_WNDPROC, wProc);
}
public void StopSubclass()
{
if (handle != IntPtr.Zero)
{
SetWindowLong(handle, GWL_WNDPROC, oldWndProc);
DestroyWindow(handle);
handle = IntPtr.Zero;
}
}
public Invokable() : this(IntPtr.Zero) { }
public object Invoke(Delegate method, object[] args)
{
callbackDelegates.Enqueue(new CallBackDelegate(method, args));
SendMessage(handle, WF_THREADCALLBACKMESSAGE, IntPtr.Zero, IntPtr.Zero);
return null;
}
public bool InvokeRequired
{
get { return GetWindowThreadProcessId(handle, IntPtr.Zero) != GetCurrentThreadId(); }
}
private void InnerInvoke()
{
lock (callbackDelegates)
{
while (callbackDelegates.Count != 0)
{
CallBackDelegate d = callbackDelegates.Dequeue();
d.Delegate.DynamicInvoke(d.Args);
}
}
}
protected int WndProc(IntPtr hWnd, int Msg, int wParam, int lParam)
{
switch (Msg)
{
case WF_THREADCALLBACKMESSAGE:
InnerInvoke();
return 0;
}
return CallWindowProc(oldWndProc, hWnd, Msg, wParam, lParam);
}
~Invokable()
{
StopSubclass();
}
}
internal class CallBackDelegate
{
private Delegate _delegate;
private object[] _args;
public CallBackDelegate(Delegate _delegate, object[] args)
{
this._delegate = _delegate;
this._args = args;
}
public Delegate Delegate
{
get { return _delegate; }
}
public object[] Args
{
get { return _args; }
}
}
}

188
Speak/Speak/Utils/Util.cs Normal file
View File

@ -0,0 +1,188 @@
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;
using System.Text;
using Virtuoso.Miranda.Plugins.Collections;
using Virtuoso.Miranda.Plugins.Infrastructure;
using Virtuoso.Miranda.Plugins.Native;
using Speak.Core;
using Speak.Fork;
using Speak.Interop;
using Speak.Structs;
using Encoder=System.Text.Encoder;
namespace Speak.Utils
{
internal static class Util
{
public static DateTime unixEpoc = new DateTime(1970, 1, 1, 0, 0, 0, 0);
public static string GetNormalRussian(IntPtr strPtr)
{
return Util.GetNormalRussian(strPtr, 2048);
}
public static string GetNormalRussian(IntPtr strPtr, uint size)
{
byte[] buff = new byte[size];
byte letter = 0;
int counter = 0;
while ((letter = Marshal.ReadByte(strPtr, counter)) != 0)
{
buff[counter] = letter;
counter++;
if (counter == size)
break;
}
return Encoding.UTF8.GetString(buff, 0, counter);
}
public static IntPtr GetStringPtr(string str, out int length)
{
byte[] array = Encoding.UTF8.GetBytes(str);
IntPtr strPtr = Marshal.AllocHGlobal(array.Length+1);
Marshal.Copy(array, 0, strPtr, array.Length);
Marshal.WriteByte(strPtr, array.Length, 0);
length = array.Length + 1;
return strPtr;
}
public static void OpenURL(string url)
{
UnmanagedStringHandle str = new UnmanagedStringHandle(url, StringEncoding.Ansi);
MirandaContext.Current.CallService(API.MS_UTILS_OPENURL, new IntPtr(1), str);
str.Free();
}
public static DateTime GetDateTime(uint timestamp)
{
int ts = MirandaContext.Current.CallService(API.MS_DB_TIME_TIMESTAMPTOLOCAL, new UIntPtr(timestamp), IntPtr.Zero);
return unixEpoc.AddSeconds(ts);
}
public static List<string> EnumProtocols()
{
List<string> result = new List<string>();
IntPtr countPtr = Marshal.AllocHGlobal(4);
IntPtr arrayPtr = Marshal.AllocHGlobal(4);
MirandaContext.Current.CallService(API.MS_PROTO_ENUMPROTOCOLS, countPtr, arrayPtr);
byte[] intArr = new byte[4];
Marshal.Copy(countPtr, intArr, 0, 4);
int pCount = BitConverter.ToInt32(intArr, 0);
intArr = new byte[4];
Marshal.Copy(arrayPtr, intArr, 0, 4);
Int32 itemPtr = BitConverter.ToInt32(intArr, 0);
for (int i = 0; i < pCount; i++)
{
intArr = new byte[4];
Marshal.Copy(new IntPtr(itemPtr+i*4), intArr, 0, 4);
IntPtr pdPtr = new IntPtr(BitConverter.ToInt32(intArr, 0));
PROTOCOLDESCRIPTOR descriptor = (PROTOCOLDESCRIPTOR)(Marshal.PtrToStructure(pdPtr, typeof(PROTOCOLDESCRIPTOR)));
string name = Marshal.PtrToStringAnsi(descriptor.Name);
result.Add(name);
}
Marshal.FreeHGlobal(countPtr);
Marshal.FreeHGlobal(arrayPtr);
return result;
}
public static StatusMode GetProtocolStatus(string pName)
{
return (StatusMode)MirandaContext.Current.CallService(String.Format("{0}{1}", pName, API.PS_GETSTATUS), IntPtr.Zero, IntPtr.Zero);
}
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
private delegate IntPtr MirandaPluginInfo(UInt32 mirandaVersion);
public static string CurrentMessageEngine()
{
// SRMM
// tabSRMM
// Scriver
int buffSize = 50;
IntPtr buffPtr = Marshal.AllocHGlobal(buffSize);
MirandaContext.Current.CallService(API.MS_MSG_GETWINDOWCLASS, buffPtr, new IntPtr(buffSize));
byte[] buff = new byte[buffSize];
byte letter = 0;
int counter = 0;
while ((letter = Marshal.ReadByte(buffPtr, counter)) != 0)
{
buff[counter] = letter;
counter++;
if (counter == buffSize)
break;
}
Marshal.FreeHGlobal(buffPtr);
string engine = Encoding.ASCII.GetString(buff, 0, counter);
// Scriver 2.8.1.1+ fix
if (engine.Equals(LogWindow.ScriverEngine))
{
Version vScriver = GetModuleVersion("scriver.dll");
if (vScriver != null && vScriver > new Version(2, 8, 1, 1))
{
return LogWindow.ScriverEnginePlus;
}
}
// SRMM 0.9.0.0+ fix
else if (engine.Equals(LogWindow.SRMMEngine))
{
Version vSRMM = GetModuleVersion("srmm.dll");
if (vSRMM != null && vSRMM > new Version(0, 9, 0, 0))
{
return LogWindow.SRMMEnginePlus;
}
}
return engine;
}
private static Version GetModuleVersion(string moduleName)
{
foreach (System.Diagnostics.ProcessModule module in System.Diagnostics.Process.GetCurrentProcess().Modules)
{
if (module.ModuleName.Equals(moduleName, StringComparison.InvariantCultureIgnoreCase))
{
UInt32 mirandaVersion = (UInt32)MirandaContext.Current.CallService(API.MS_SYSTEM_GETVERSION, IntPtr.Zero, IntPtr.Zero);
IntPtr pAddressOfFunctionToCall = WinApi.GetProcAddress(module.BaseAddress, "MirandaPluginInfoEx");
if (pAddressOfFunctionToCall == IntPtr.Zero)
break;
MirandaPluginInfo pPluginInfo = (MirandaPluginInfo)Marshal.GetDelegateForFunctionPointer(pAddressOfFunctionToCall, typeof(MirandaPluginInfo));
IntPtr pluginInfo = pPluginInfo(mirandaVersion);
PLUGININFOEX pInfo = (PLUGININFOEX)Marshal.PtrToStructure(pluginInfo, typeof(PLUGININFOEX));
byte[] vBytes = BitConverter.GetBytes(pInfo.Version);
return new Version(vBytes[3], vBytes[2], vBytes[1], vBytes[0]);
}
}
return null;
}
public static Int32 MakeLParam(int LoWord, int HiWord)
{
return (HiWord << 16) | (LoWord & 0xffff);
}
public static int MakeLong(short lowPart, short highPart)
{
return (int)(((ushort)lowPart) | (uint)(highPart << 16));
}
public static short HiWord(int dword)
{
return (short)(dword >> 16);
}
public static short LoWord(int dword)
{
return (short)dword;
}
}
}

View File

@ -0,0 +1,53 @@
Miranda IM is proudly brought to you by:
Gennady Feldman
Tim Hunter
Kubilay Kocak
Boris Krasnovskiy
Josef Kucera
Aaron Landwehr
Lyon Lim
Tjado Maecke
Piotr Piastucki
Robert Rainwater
Alex Sanda
Adam Strzelecki
Victor Pavlychko
Bartosz Białek
Retired Members:
Martin Öberg
Denis Stanishevskiy
Richard Hughes
Emostar
Esnow
Figbug
Tristan_VdV
Crypt0gl
Lowspirit
Glutnix
Santithorn Bunchua
Sam K
Jörgen Persson
George Hazan
Artem Shpynov
Maxim Mluhov
Ricardo Domenecci
Our plugin developers, too multitudinous to name individually, but whos works are nontheless crucial to our success.
Special mention to Scott Ellis, a welcome part of arguably almost every Miranda IM installation :)
Our translators, who have done great things to expand our reach, and who are infuriated that
I won't let them change this text.
Our media developers, who bring us the icons, sounds and skins you love so much.
Special mention to Angeli-Ka, a0x, Faith Healer, Quadrone, and Valkyre for their work on the application icons.
Our bug reporters and moderators, who strive thanklessly to bring quality into Miranda.
Special mention to Piotr Lukaszewski aka nowotny, not always smiling, but always doing his part.
Our forum residents, who discover new and exciting ways to break Miranda daily and who are the gestalt
slash 'mob' that shapes how Miranda IM works and evolves.
Our users, who...er...use it, and without who...well...we love that you love Miranda.

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

BIN
Speak/Speak/res/Off.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

BIN
Speak/Speak/res/On.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

BIN
Speak/Speak/res/_blank.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 318 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 150 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 150 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 326 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 326 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

Some files were not shown because too many files have changed in this diff Show More