quick-cocos2d-x的输入框

quick-cocos2d-x的输入框,第1张

概述游戏引擎一般提供两种输入框:editbox和textfielttf。editbox比较简单,在ios上效果也还行,但是在android上就比较丑了,每次输入都会悬浮一个小框框。对于游戏来说eidtbox可以满足基本需求,毕竟输入还是少数情况。textfielttf是一种特殊的label,显示效果比较好,但是计算起来比较麻烦,要自己绘制光标,要自己绘制文字,自己计算增加和删除。 这里还是说一下自己实

游戏引擎一般提供两种输入框:editBox和textfIElttf。editBox比较简单,在ios上效果也还行,但是在androID上就比较丑了,每次输入都会悬浮一个小框框。对于游戏来说eIDtBox可以满足基本需求,毕竟输入还是少数情况。textfIElttf是一种特殊的label,显示效果比较好,但是计算起来比较麻烦,要自己绘制光标,要自己绘制文字,自己计算增加和删除。

这里还是说一下自己实现的一种简陋的支持增加删除的方式吧。其实比较简单,原理就是记录每个字及每个字的位置,然后增加删除的时候既要对字处理也要对位置处理。(这里只针对单行进行说明,多行的还要自己维护高度等信息)。

先来说一下绘制函数,这里用的是自己维护的显示内容contentString

bool CCTextFIEldTTFExtend::onDraw(CCTextFIEldTTF *pSender){    cclog("the contentstring in fIEldttf extend is %s",contentString.c_str());    //检测是否有删改    pSender->setString(contentString.c_str());    if (once == 1) {        once = 0;        if (recordPos.size() > 0 && pSender->getContentSize().wIDth - recordPos[recordPos.size()-1].point.x < 0) {            //有记录的数据,切 *** 作之后显示的文字内容比记录的要短,说明进行的是删除 *** 作            if (posInList > 1) {                float distance = recordPos[posInList-2].point.x - recordPos[posInList-1].point.x;                m_pCursorSprite->setpositionX(m_pCursorSprite->getpositionX() + distance/2);                pSender->setString(contentString.c_str());                updateDelete(pSender);            }else if (posInList== 1){                float distance = 0 - recordPos[posInList-1].point.x;                m_pCursorSprite->setpositionX(m_pCursorSprite->getpositionX() + distance/2);                pSender->setString(contentString.c_str());                updateDelete(pSender);            }            return false;        }        if (recordPos.size() > 0 && pSender->getContentSize().wIDth-recordPos[recordPos.size()-1].point.x > 1 ) {            //有记录的数据,切 *** 作之后显示的文字内容比记录的要长,说明进行的是增加 *** 作            float distance = pSender->getContentSize().wIDth - recordPos[recordPos.size()-1].point.x;            m_pCursorSprite->setpositionX(m_pCursorSprite->getpositionX() + distance/2);            pSender->setString(contentString.c_str());            updateAdd(pSender);            return false;        }else{            if(recordPos.size() == 0 && pSender->getContentSize().wIDth > 0){                //显现没有记录说明没有文字,现在有记录说明是增加 *** 作                m_pCursorSprite->setpositionX(m_pCursorSprite->getpositionX() + pSender->getContentSize().wIDth/2);                updateAdd(pSender);            }        }    }    return false;}

删除内容 *** 作:
//删除内容voID CCTextFIEldTTFExtend::deleteString(){    if (strcmp(contentString.c_str(),"") && posInList < 1) {        return;    }    //计算删除了几个汉字或字符    int nDeleteLen = 1;    while(0x80 == (0xC0 & contentString.at(posInString - nDeleteLen)))    {        ++nDeleteLen;    }    string tempNext = contentString.substr(posInString);    string tempPrev = contentString.substr(0,posInString-nDeleteLen);    contentString = tempPrev + tempNext;    posInString -= nDeleteLen;    once = 1;    }

增加内容 *** 作:
//增加内容voID CCTextFIEldTTFExtend::addString(const char *text){    string tempPrev = contentString.substr(0,posInString);    string tempNext = contentString.substr(posInString);        string tempString = tempPrev + text + tempNext;    int addLength = (strlen(tempString.c_str())-strlen(contentString.c_str()));    posInString += addLength;    contentString = tempString;    judgeChines = addLength;    cclog("the contentString is %s",contentString.c_str());    once = 1;}

删除位置 *** 作:
voID CCTextFIEldTTFExtend::updateDelete(CCTextFIEldTTF * pSender){    //销毁足迹    float distance = 0;    if (posInList != 0) {        distance = recordPos[posInList].point.x - recordPos[posInList-1].point.x;    }        vector<RecordTTF> temp = recordPos;    recordPos.clear();    for (int i = 0; i < posInList-1; ++ i) {        recordPos.push_back(temp[i]);    }    for (int i = posInList; i < temp.size(); ++ i) {        temp[i].point.x -= distance;        recordPos.push_back(temp[i]);    }        posInList --;}

添加足迹的 *** 作:
voID CCTextFIEldTTFExtend::updateAdd(CCTextFIEldTTF * pSender){    //原先字段的前部    vector<RecordTTF> temp = recordPos;    recordPos.clear();    for (int i = 0; i < posInList; ++ i) {        recordPos.push_back(temp[i]);    }        //现增加的部分    float distance = 0;    if (posInList > 0) {        RecordTTF local;        distance = pSender->getContentSize().wIDth - temp[temp.size()-1].point.x;        local.point = CCPoint(temp[posInList-1].point.x += distance,0);        cclog("现在的 %f",local.point.x);        local.flag = judgeChines;        recordPos.push_back(local);    }else{        if(temp.size() < 1){            RecordTTF local;            local.point = CCPoint(pSender->getContentSize().wIDth,0);            local.flag = judgeChines;            recordPos.push_back(local);        }else{            RecordTTF local;            cclog("the contentSize is %f",pSender->getContentSize().wIDth);            distance = pSender->getContentSize().wIDth - temp[temp.size()-1].point.x;            local.point = CCPoint(temp[posInList-1].point.x += distance,0);            cclog("现在的 %f",local.point.x);            local.flag = judgeChines;            recordPos.push_back(local);        }    }        //原先文字的后部    for (int i = posInList; i < temp.size(); ++ i) {        temp[i].point.x += distance;        recordPos.push_back(temp[i]);    }    posInList ++;}


还有一种可能,如果要换行的话,我这里采用的是用系统控件的方式。但是ios上输入完内容之后,只有回车才能关闭键盘,点击空白处,或者自己的按钮都接收不到触摸事件,这时改一下lib/cocos2d-x/cocos2dx/platform/ios/EAGLVIEw.mm,
-(voID) handletouchesAfterKeyboardShow{    NSArray *subvIEws = self.subvIEws;        for(UIVIEw* vIEw in subvIEws)    {        if([vIEw isKindOfClass:NSClassFromString(@"CustomUITextFIEld")])        {            if ([vIEw isFirstResponder])            {                [vIEw resignFirstResponder];                return;            }        }        if([vIEw isKindOfClass:NSClassFromString(@"UITextVIEw")])        {            if ([vIEw isFirstResponder])            {                [vIEw resignFirstResponder];                return;            }        }    }}

原因代码也说的比较清楚了,原先quick只对自己的控件进行了处理,现在你增加一下把系统控件也处理以下。

此外,在做androID微信授权登陆的时候出现从cocos2dActivity跳转出去再跳转回来之后所有的cocos2d输入框不显示键盘,跟踪发现启动键盘确实走到

Cocos2dxGLSurfaceVIEw.sHandler = new Handler() {			@OverrIDe			public voID handleMessage(final Message msg) {				switch (msg.what) {					case HANDLER_OPEN_IME_KEYBOARD:						Log.i("","接收到启动键盘通知");						if (null != Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText && Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText.requestFocus()) {							Log.i("","接收到启动键盘通知 开始启动键盘");							Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText.removeTextChangedListener(Cocos2dxGLSurfaceVIEw.sCocos2dxTextinputWraper);							Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText.setText("");							final String text = (String) msg.obj;							Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText.append(text);							Cocos2dxGLSurfaceVIEw.sCocos2dxTextinputWraper.setoriginText(text);							Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText.addTextChangedListener(Cocos2dxGLSurfaceVIEw.sCocos2dxTextinputWraper);							final inputMethodManager imm = (inputMethodManager) Cocos2dxGLSurfaceVIEw.mCocos2dxGLSurfaceVIEw.getContext().getSystemService(Context.input_METHOD_SERVICE);							imm.showSoftinput(Cocos2dxGLSurfaceVIEw.this.mCocos2dxEditText,0);							Log.d("GLSurfaceVIEw","showSoftinput");						}						break;


原因是我将微信授权的回调activity也设成了cocos2dActivity。具体是什么造成的没有去深究,将其改为activity,并注意下到底是UIThread还是OpenGLThread,这样的问题就没有了。大部分这种 *** 作都是线程混乱造成的,出现这种类似的情况,多看一下是否是线程的原因。

总结

以上是内存溢出为你收集整理的quick-cocos2d-x的输入框全部内容,希望文章能够帮你解决quick-cocos2d-x的输入框所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/web/1027510.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-23
下一篇 2022-05-23

发表评论

登录后才能评论

评论列表(0条)

保存