扫描二维码关注官方公众号
返回列表
+ 发新帖
查看: 144|回复: 0

[转载发布] 完美输入法最后修正版~

[复制链接]
累计送礼:
0 个
累计收礼:
0 个
  • TA的每日心情
    开心
    昨天 18:01
  • 签到天数: 114 天

    连续签到: 4 天

    [LV.6]常住居民II

    2338

    主题

    403

    回帖

    1万

    积分

    管理员

    Rank: 9Rank: 9Rank: 9

    VIP
    6
    卡币
    10622
    OK点
    16
    推广点
    0
    同能卷
    0
    积分
    13391

    灌水之王

    发表于 2024-4-19 16:09:59 | 显示全部楼层 |阅读模式
    脚本:完美输入法最后修正版~

    说明:略,参考脚本中注释部分。

    点击下载范例工程
    1. =begin  脚本:【完美输入法修正】    功能:输入法。    说明: 直接用Type_Field创建输入域即可进行输入,在此可根据Type_Field域对象          的活动标记active来自定义刷新等,在Type_Field中需要自己处理特殊按键                的处理方法。具体不明白之处请参考范例工程。  作者:灼眼的夏娜    补充: 至于以前那个版本也许很多人都注意到那个烦人的问题了吧,按Enter和Tab那          些会出现不爽的声音,这个版本解决了那个问题,并简化添加了Type_Field类                来方便创建输入域。=end#==============================================================================# ■ RInput#------------------------------------------------------------------------------#  全键盘处理的模块。#==============================================================================module RInput    #--------------------------------------------------------------------------  # ● 常量定义  #--------------------------------------------------------------------------  ENTER             = 0x0D  SPACE             = 0x20  UP                = 0x26  DOWN              = 0x28  LEFT              = 0x25  RIGHT             = 0x27    LCTRL             = 0xA2  LALT              = 0xA4   #--------------------------------------------------------------------------  # ● 临时Hash  #--------------------------------------------------------------------------  @R_Key_Hash = {}  @R_Key_Repeat = {}    #--------------------------------------------------------------------------  # ● 唯一API  #--------------------------------------------------------------------------  GetKeyState = Win32API.new("user32","GetAsyncKeyState",['I'],'I')  #--------------------------------------------------------------------------  # ● 单键处理  #--------------------------------------------------------------------------  def self.trigger?(rkey)    result = GetKeyState.call(rkey)    if @R_Key_Hash[rkey] == 1 and result != 0      return false    end    if result != 0      @R_Key_Hash[rkey] = 1      return true    else      @R_Key_Hash[rkey] = 0      return false    end  endend#==============================================================================# ■ EasyConv#------------------------------------------------------------------------------#  转码模块。#==============================================================================module EasyConv  #--------------------------------------------------------------------------  # ● 常量定义  #--------------------------------------------------------------------------  CP_ACP = 0  CP_UTF8 = 65001  #--------------------------------------------------------------------------  # ● 模块函数  #--------------------------------------------------------------------------  module_function    #--------------------------------------------------------------------------  # ● 转码  #--------------------------------------------------------------------------  def s2u(text)    m2w = Win32API.new('kernel32', 'MultiByteToWideChar', 'ilpipi', 'i')    w2m = Win32API.new('kernel32', 'WideCharToMultiByte', 'ilpipipp', 'i')    len = m2w.call(CP_ACP, 0, text, -1, nil, 0)    buf = "\0" * (len*2)    m2w.call(CP_ACP, 0, text, -1, buf, buf.size/2)    len = w2m.call(CP_UTF8, 0, buf, -1, nil, 0, nil, nil)    ret = "\0" * len    w2m.call(CP_UTF8, 0, buf, -1, ret, ret.size, nil, nil)    ret[-1] = ""        return ret  end  #--------------------------------------------------------------------------  # ● 转码  #--------------------------------------------------------------------------  def u2s(text)       m2w = Win32API.new('kernel32', 'MultiByteToWideChar', 'ilpipi', 'i')    w2m = Win32API.new('kernel32', 'WideCharToMultiByte', 'ilpipipp', 'i')    len = m2w.call(CP_UTF8, 0, text, -1, nil, 0)    buf = "\0" * (len*2)    m2w.call(CP_UTF8, 0, text, -1, buf, buf.size/2)    len = w2m.call(CP_ACP, 0, buf, -1, nil, 0, nil, nil)    ret = "\0" * len    w2m.call(CP_ACP, 0, buf, -1, ret, ret.size, nil, nil)       return ret  endend#==============================================================================# ■ TypeAPI#------------------------------------------------------------------------------#  输入法相关API模块。#==============================================================================module TypeAPI    #--------------------------------------------------------------------------  # ● API定义  #--------------------------------------------------------------------------  GPPS         = Win32API.new("kernel32","GetPrivateProfileString",'pppplp','l')  FindWindow   = Win32API.new("user32", "FindWindow", 'pp', 'i')  CreateWindow = Win32API.new("NetGame","CreatWnd",'l','l')  SetHK        = Win32API.new("NetGame","SetHK",'v','v')  GetText      = Win32API.new("NetGame","GetWndText",'l','p')  SetFocus     = Win32API.new("user32","SetFocus",'l','l')  IfBack       = Win32API.new("NetGame","If_Back",'v','i')  StartType    = Win32API.new("NetGame","StartType",'v','v')  EndType      = Win32API.new("NetGame","EndType",'v','v')  GetKeyInfos  = Win32API.new("NetGame","GetKeyInfo",'v','i')    #--------------------------------------------------------------------------  # ● 模块函数  #--------------------------------------------------------------------------  module_function    #--------------------------------------------------------------------------  # ● 获取参数  #--------------------------------------------------------------------------  def getParam    val = "\0" * 256    GPPS.call("Game","Title","",val,256,"./Game.ini")    val.delete!("\0")    return val  end    #--------------------------------------------------------------------------  # ● 获取窗口  #--------------------------------------------------------------------------  def findWindow    return FindWindow.call("RGSS Player",self.getParam)  end    #--------------------------------------------------------------------------  # ● 创建窗口  #--------------------------------------------------------------------------  def createWindow(hwnd)    return CreateWindow.call(hwnd)  end    #--------------------------------------------------------------------------  # ● 设置HK  #--------------------------------------------------------------------------  def setHK    SetHK.call  end    #--------------------------------------------------------------------------  # ● 获取文字  #--------------------------------------------------------------------------  def getText    return EasyConv.s2u(GetText.call(@subhwnd))  end    #--------------------------------------------------------------------------  # ● 设置焦点  #--------------------------------------------------------------------------  def setFocus    SetFocus.call(@subhwnd)  end    #--------------------------------------------------------------------------  # ● 转换焦点  #--------------------------------------------------------------------------  def lostFocus    SetFocus.call(@hwnd)  end    #--------------------------------------------------------------------------  # ● 退格判定  #--------------------------------------------------------------------------  def ifBack    return IfBack.call  end    #--------------------------------------------------------------------------  # ● 开始输入  #--------------------------------------------------------------------------  def startType    StartType.call  end    #--------------------------------------------------------------------------  # ● 结束输入  #--------------------------------------------------------------------------  def endType    EndType.call  end    #--------------------------------------------------------------------------  # ● 输入中特殊按键处理  #--------------------------------------------------------------------------  def getKeyInfos    return GetKeyInfos.call  end    #--------------------------------------------------------------------------  # ● 获取句柄  #--------------------------------------------------------------------------  @hwnd    = self.findWindow    @subhwnd = self.createWindow(@hwnd)  #--------------------------------------------------------------------------  # ● 设置HK应用  #--------------------------------------------------------------------------  self.setHK  end#==============================================================================# ■ Type_Field#------------------------------------------------------------------------------#  处理输入域的类。#==============================================================================class Type_Field    #--------------------------------------------------------------------------  # ● 定义实例变量  #--------------------------------------------------------------------------  attr(:active)    #--------------------------------------------------------------------------  # ● 初始化  #--------------------------------------------------------------------------  def initialize(v,default_text = "",default_careth = nil,default_fonts = 16,\    default_fontc = Color.new(0,0,0))    # active    @active = true    # 视口    rect = v.rect    @v = Viewport.new(rect.x,rect.y,rect.width,rect.height)    @w = rect.width    @h = rect.height    # 属性    @caret_h = default_careth.nil? ? @h : [@h,default_careth].min    @caret_y = rect.y + (@h - @caret_h) / 2    @font_size = [default_fonts,@h].min    # 描绘contents    @cts = Sprite.new(@v)    @cts.bitmap = Bitmap.new(@w - 3,@h)    @cts.bitmap.font.size = @font_size    @cts.bitmap.font.color = default_fontc    # 辅助属性    @bk_count = 0    @text = default_text.scan(/./)    @max_width = @w - 3    @caret_pos = @text.size    @save_pos = @caret_pos    # 光标Caret    @v1 = Viewport.new(rect.x,@caret_y,@w + 3,@caret_h)    @caret_sp = Sprite.new(@v1)    @caret_bitmap = Bitmap.new(3,@caret_h)    @caret_bitmap.fill_rect(0,0,1,@caret_h,Color.new(0,0,0,180))    @caret_bitmap.fill_rect(1,0,1,@caret_h,Color.new(0,0,0))    @caret_bitmap.fill_rect(2,0,1,@caret_h,Color.new(120,120,120))    @caret_sp.bitmap = @caret_bitmap    @caret_sp.x = self.get_width(@text[0,@caret_pos].to_s)    @caret_sp.y = 0    @caret_sp.visible = false    @caret_flash_count = 0    # 刷新    refresh    # 设置焦点    TypeAPI.setFocus    # 开始输入    TypeAPI.startType  end    #--------------------------------------------------------------------------  # ● 设置活动标记  #--------------------------------------------------------------------------  def active=(value)    if value != true and value != false      return    end    @active = value    @caret_sp.visible = @active  end    #--------------------------------------------------------------------------  # ● 释放  #--------------------------------------------------------------------------  def dispose    @caret_bitmap.dispose    @caret_sp.bitmap.dispose    @caret_sp.dispose    @cts.bitmap.dispose    @cts.dispose    @v.dispose    @v1.dispose  end  #--------------------------------------------------------------------------  # ● 刷新  #--------------------------------------------------------------------------  def refresh    @cts.bitmap.clear    @cts.bitmap.draw_text(0,0,@w,@h,@text.to_s)  end  #--------------------------------------------------------------------------  # ● 获取文字  #--------------------------------------------------------------------------  def get_text    return @text.to_s  end  #--------------------------------------------------------------------------  # ● 取得字符宽度  #--------------------------------------------------------------------------  def get_width(str)    return @cts.bitmap.text_size(str).width  end    #--------------------------------------------------------------------------  # ● 更新  #--------------------------------------------------------------------------  def update    # 非激活状态则返回    unless @active      return    end    # 获取按键信息    key_info = TypeAPI.getKeyInfos    case key_info    when 0x09 # Tab      # 按下 Tab 键的情况自己定义怎么处理      return    when 0x0d # Enter      # 按下 Enter 键的情况自己定义怎么处理      return    when 0x1B # Esc      # 按下 Esc 键的情况自己定义怎么处理      return    end    self.update_text    self.update_lrb    self.update_back    self.update_caret  end  #--------------------------------------------------------------------------  # ● 更新文字  #--------------------------------------------------------------------------  def update_text    # 文字刷新    TypeAPI.setFocus    text = TypeAPI.getText    if text != ""      for char in text.scan(/./)        if self.get_width(@text.to_s + char)  0      @caret_pos -= 1      return    end    if RInput.trigger?(RInput::RIGHT) and @caret_pos < @text.size      @caret_pos += 1      return    end  end    #--------------------------------------------------------------------------  # ● 更新退格  #--------------------------------------------------------------------------  def update_back    # 前退格处理    @bk_count += TypeAPI.ifBack    if @bk_count > 0      @bk_count -= 1      if @caret_pos > 0        @text.delete_at(@caret_pos - 1);@caret_pos -= 1;refresh      end    end  end    #--------------------------------------------------------------------------  # ● 更新光标闪烁  #--------------------------------------------------------------------------  def update_caret    # 闪烁计时    @caret_flash_count += 1    if @caret_flash_count == 20      @caret_sp.visible = !@caret_sp.visible      @caret_flash_count = 0    end    # Caret位置刷新    if @save_pos != @caret_pos      @save_pos = @caret_pos      @caret_sp.x = self.get_width(@text[0,@save_pos].to_s)    end  end  end    复制代码
    复制代码
                 本帖来自P1论坛作者尤莉斯,因Project1站服务器在国外有时候访问缓慢不方便作者交流学习,经联系P1站长fux2同意署名转载一起分享游戏制作经验,共同为国内独立游戏作者共同创造良好交流环境,原文地址:https://rpg.blue/forum.php?mod=viewthread&tid=47019  若有侵权,发帖作者可联系底部站长QQ在线咨询功能删除,谢谢。
    天天去同能,天天有童年!
    回复 送礼论坛版权

    使用道具 举报

    文明发言,和谐互动
    文明发言,和谐互动
    高级模式
    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    关闭

    幸运抽奖

    社区每日抽奖来袭,快来试试你是欧皇还是非酋~

    立即查看

    聊天机器人
    Loading...

    QQ|Archiver|手机版|小黑屋|同能RPG制作大师 ( 沪ICP备12027754号-3 )

    GMT+8, 2025-3-15 00:10 , Processed in 0.132407 second(s), 53 queries .

    Powered by Discuz! X3.4

    Copyright © 2001-2020, Tencent Cloud.

    快速回复 返回顶部 返回列表