diff --git a/cocos2dx/include/CCIMEDelegate.h b/cocos2dx/include/CCIMEDelegate.h new file mode 100644 index 0000000000..fe40c4f887 --- /dev/null +++ b/cocos2dx/include/CCIMEDelegate.h @@ -0,0 +1,78 @@ +/**************************************************************************** +Copyright (c) 2010 cocos2d-x.org + +http://www.cocos2d-x.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +****************************************************************************/ + +#ifndef __CC_IME_DELEGATE_H__ +#define __CC_IME_DELEGATE_H__ + +#include "CCCommon.h" + +NS_CC_BEGIN; + +/** +@brief Input method editor protocol. +*/ +class CC_DLL CCIMEDelegate +{ +public: + virtual ~CCIMEDelegate(); + + bool attachWithIME(); + +protected: + friend class CCIMEDispatcher; + + /** + @brief Decide the delegate instance is ready for receive ime message or not. + + Called by CCIMEDispatcher. + */ + virtual bool canAttachWithIME() = 0; + + /** + @brief Decide the delegate instance can stop receive ime message or not. + */ + virtual bool canDetatchWithIME() = 0; + + /** + @brief Input end and release keyboard. + */ + virtual void detatchWithIME() = 0; + + /** + @brief Called by CCIMEDispatcher when some text input from IME. + */ + virtual void insertText(const char * text, int len) = 0; + + /** + @brief Called by CCIMEDispatcher when user clicked the backward key. + */ + virtual void deleteBackward() = 0; + +protected: + CCIMEDelegate(); +}; + +NS_CC_END; + +#endif // __CC_IME_DELEGATE_H__ diff --git a/cocos2dx/include/CCIMEDispatcher.h b/cocos2dx/include/CCIMEDispatcher.h new file mode 100644 index 0000000000..5e71d0239a --- /dev/null +++ b/cocos2dx/include/CCIMEDispatcher.h @@ -0,0 +1,91 @@ +/**************************************************************************** +Copyright (c) 2010 cocos2d-x.org + +http://www.cocos2d-x.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +****************************************************************************/ + +#ifndef __CC_IME_DISPATCHER_H__ +#define __CC_IME_DISPATCHER_H__ + +#include "CCCommon.h" + +NS_CC_BEGIN; + +class CCIMEDelegate; + +/** +@brief Input Method Edit Message Dispatcher. +*/ +class CC_DLL CCIMEDispatcher +{ +public: + ~CCIMEDispatcher(); + + /** + @brief Returns the shared CCIMEDispatcher object for the system. + */ + static CCIMEDispatcher* sharedDispatcher(); + +// /** +// @brief Release all CCIMEDelegates from shared dispatcher. +// */ +// static void purgeSharedDispatcher(); + + /** + @brief dispatch the input text from ime + */ + void dispatchInsertText(const char * pText, int nLen); + + /** + @brief dispatch the delete backward operation + */ + void dispatchDeleteBackward(); + +protected: + friend class CCIMEDelegate; + + /** + @brief add delegate to concern ime msg + */ + void addDelegate(CCIMEDelegate * pDelegate); + + /** + @brief attach the pDeleate with ime. + @return If the old delegate can detattach with ime and the new delegate + can attach with ime, return true, otherwise return false. + */ + bool attachDelegateWithIME(CCIMEDelegate * pDelegate); + + /** + @brief remove the delegate from the delegates who concern ime msg + */ + void removeDelegate(CCIMEDelegate * pDelegate); + +private: + CCIMEDispatcher(); + + class Impl; + Impl * m_pImpl; +}; + +NS_CC_END; + +#endif // __CC_IME_DISPATCHER_H__ diff --git a/cocos2dx/include/CCTextFieldTTF.h b/cocos2dx/include/CCTextFieldTTF.h new file mode 100644 index 0000000000..d7a6e34ba2 --- /dev/null +++ b/cocos2dx/include/CCTextFieldTTF.h @@ -0,0 +1,98 @@ +/**************************************************************************** +Copyright (c) 2010 cocos2d-x.org + +http://www.cocos2d-x.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +****************************************************************************/ + +#ifndef __CC_TEXT_FIELD_H__ +#define __CC_TEXT_FIELD_H__ + +#include "CCLabelTTF.h" +#include "CCIMEDelegate.h" +#include "CCTouchDelegateProtocol.h" + +NS_CC_BEGIN; + +/** +@brief A simple text input field with system TTF font. +*/ + +class CC_DLL CCTextFieldTTF : public CCLabelTTF, public CCIMEDelegate//, public CCTargetedTouchDelegate +{ +public: + CCTextFieldTTF(); + virtual ~CCTextFieldTTF(); + + //char * description(); + + /** creates a CCTextFieldTTF from a fontname, alignment, dimension and font size */ + static CCTextFieldTTF * textFieldWithPlaceHolder(const char *placeholder, CCSize dimensions, CCTextAlignment alignment, const char *fontName, float fontSize); + /** creates a CCLabelTTF from a fontname and font size */ + static CCTextFieldTTF * textFieldWithPlaceHolder(const char *placeholder, const char *fontName, float fontSize); + /** initializes the CCTextFieldTTF with a font name, alignment, dimension and font size */ + bool initWithPlaceHolder(const char *placeholder, CCSize dimensions, CCTextAlignment alignment, const char *fontName, float fontSize); + /** initializes the CCTextFieldTTF with a font name and font size */ + bool initWithPlaceHolder(const char *placeholder, const char *fontName, float fontSize); + + /** + @brief Get keyboard ready and waiting for input. + */ + bool attachWithIME(); + + ////////////////////////////////////////////////////////////////////////// + // properties + ////////////////////////////////////////////////////////////////////////// + + // input text property +public: + virtual void setString(const char *text); + virtual const char* getString(void); +protected: + std::string * m_pInputText; + + // place holder text property + // place holder text displayed when there is no text in the text field. +public: + virtual void setPlaceHolder(const char * text); + virtual const char * getPlaceHolder(void); +protected: + std::string * m_pPlaceHolder; + bool m_bLock; // when insertText or deleteBackward called, m_bLock is true +protected: + + ////////////////////////////////////////////////////////////////////////// + // CCIMEDelegate interface + ////////////////////////////////////////////////////////////////////////// + + virtual bool canAttachWithIME(); + virtual bool canDetatchWithIME(); + virtual void detatchWithIME(); + virtual void insertText(const char * text, int len); + virtual void deleteBackward(); + +private: + class LengthStack; + LengthStack * m_pLens; +}; + +NS_CC_END; + +#endif // __CC_TEXT_FIELD_H__ \ No newline at end of file diff --git a/cocos2dx/include/CCTouchDelegateProtocol.h b/cocos2dx/include/CCTouchDelegateProtocol.h index d2cd187d0c..119a7413fe 100644 --- a/cocos2dx/include/CCTouchDelegateProtocol.h +++ b/cocos2dx/include/CCTouchDelegateProtocol.h @@ -53,8 +53,8 @@ public: virtual void keep(void) {} virtual bool ccTouchBegan(CCTouch *pTouch, CCEvent *pEvent) { return false;}; - // optional + virtual void ccTouchMoved(CCTouch *pTouch, CCEvent *pEvent) {} virtual void ccTouchEnded(CCTouch *pTouch, CCEvent *pEvent) {} virtual void ccTouchCancelled(CCTouch *pTouch, CCEvent *pEvent) {} diff --git a/cocos2dx/label_nodes/CCLabelTTF.cpp b/cocos2dx/label_nodes/CCLabelTTF.cpp index ca25edf7b1..6b9abef6a3 100644 --- a/cocos2dx/label_nodes/CCLabelTTF.cpp +++ b/cocos2dx/label_nodes/CCLabelTTF.cpp @@ -50,7 +50,7 @@ namespace cocos2d{ pRet->autorelease(); return pRet; } - CC_SAFE_DELETE(pRet) + CC_SAFE_DELETE(pRet); return NULL; } CCLabelTTF * CCLabelTTF::labelWithString(const char *label, const char *fontName, float fontSize) @@ -61,7 +61,7 @@ namespace cocos2d{ pRet->autorelease(); return pRet; } - CC_SAFE_DELETE(pRet) + CC_SAFE_DELETE(pRet); return NULL; } diff --git a/cocos2dx/platform/win32/CCEGLView_win32.cpp b/cocos2dx/platform/win32/CCEGLView_win32.cpp index 0a9cea49de..22c340388f 100644 --- a/cocos2dx/platform/win32/CCEGLView_win32.cpp +++ b/cocos2dx/platform/win32/CCEGLView_win32.cpp @@ -32,6 +32,7 @@ THE SOFTWARE. #include "CCDirector.h" #include "CCTouch.h" #include "CCTouchDispatcher.h" +#include "CCIMEDispatcher.h" NS_CC_BEGIN; @@ -310,6 +311,32 @@ LRESULT CCEGLView::WindowProc(UINT message, WPARAM wParam, LPARAM lParam) } break; + case WM_CHAR: + { + if (wParam < 0x20) + { + if (VK_BACK == wParam) + { + CCIMEDispatcher::sharedDispatcher()->dispatchDeleteBackward(); + } + else if (VK_TAB == wParam) + { + // tab input + } + else if (VK_ESCAPE == wParam) + { + // ESC input + } + + break; + } + char szUtf8[8] = {0}; + int nLen = WideCharToMultiByte(CP_ACP, 0, (LPCWSTR)&wParam, 1, szUtf8, sizeof(szUtf8), NULL, NULL); + + CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(szUtf8, nLen); + } + break; + case WM_PAINT: BeginPaint(m_hWnd, &ps); EndPaint(m_hWnd, &ps); @@ -407,6 +434,10 @@ void CCEGLView::setViewPortInPoints(float x, float y, float w, float h) } } +void CCEGLView::setIMEKeyboardState(bool /*bOpen*/) +{ +} + HWND CCEGLView::getHWnd() { return m_hWnd; diff --git a/cocos2dx/platform/win32/CCEGLView_win32.h b/cocos2dx/platform/win32/CCEGLView_win32.h index b50fcf2504..37914b1b93 100644 --- a/cocos2dx/platform/win32/CCEGLView_win32.h +++ b/cocos2dx/platform/win32/CCEGLView_win32.h @@ -59,6 +59,8 @@ public: int setDeviceOrientation(int eOritation); void setViewPortInPoints(float x, float y, float w, float h); + void setIMEKeyboardState(bool bOpen); + // win32 platform function HWND getHWnd(); void resize(int width, int height); diff --git a/cocos2dx/proj.win32/cocos2d-win32.vcproj b/cocos2dx/proj.win32/cocos2d-win32.vcproj index 611fd6c093..9d1d8e2047 100644 --- a/cocos2dx/proj.win32/cocos2d-win32.vcproj +++ b/cocos2dx/proj.win32/cocos2d-win32.vcproj @@ -415,6 +415,14 @@ RelativePath="..\include\CCGL.h" > + + + + @@ -551,6 +559,10 @@ RelativePath="..\include\CCString.h" > + + @@ -1040,6 +1052,18 @@ > + + + + + + diff --git a/cocos2dx/text_input_node/CCIMEDispatcher.cpp b/cocos2dx/text_input_node/CCIMEDispatcher.cpp new file mode 100644 index 0000000000..4032cd6910 --- /dev/null +++ b/cocos2dx/text_input_node/CCIMEDispatcher.cpp @@ -0,0 +1,222 @@ +/**************************************************************************** +Copyright (c) 2010 cocos2d-x.org + +http://www.cocos2d-x.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +****************************************************************************/ + +#include "CCIMEDispatcher.h" + +#include + +#include "CCIMEDelegate.h" + +NS_CC_BEGIN; + +////////////////////////////////////////////////////////////////////////// +// add/remove delegate in CCIMEDelegate Cons/Destructor +////////////////////////////////////////////////////////////////////////// + +CCIMEDelegate::CCIMEDelegate() +{ + CCIMEDispatcher::sharedDispatcher()->addDelegate(this); +} + +CCIMEDelegate::~CCIMEDelegate() +{ + CCIMEDispatcher::sharedDispatcher()->removeDelegate(this); +} + +bool CCIMEDelegate::attachWithIME() +{ + return CCIMEDispatcher::sharedDispatcher()->attachDelegateWithIME(this); +} + +////////////////////////////////////////////////////////////////////////// + +typedef std::list< CCIMEDelegate * > DelegateList; +typedef std::list< CCIMEDelegate * >::iterator DelegateIter; + +////////////////////////////////////////////////////////////////////////// +// Delegate List manage class +////////////////////////////////////////////////////////////////////////// + +class CCIMEDispatcher::Impl +{ +public: + Impl() + { + } + + ~Impl() + { + + } + + void init() + { + m_DelegateWithIme = m_DelegateList.end(); + } + + DelegateIter findDelegate(CCIMEDelegate* pDelegate) + { + DelegateIter end = m_DelegateList.end(); + for (DelegateIter iter = m_DelegateList.begin(); iter != end; ++iter) + { + if (pDelegate == *iter) + { + return iter; + } + } + return end; + } + + DelegateList m_DelegateList; + DelegateIter m_DelegateWithIme; +}; + +////////////////////////////////////////////////////////////////////////// +// Cons/Destructor +////////////////////////////////////////////////////////////////////////// + +CCIMEDispatcher::CCIMEDispatcher() +: m_pImpl(new CCIMEDispatcher::Impl) +{ + m_pImpl->init(); +} + +CCIMEDispatcher::~CCIMEDispatcher() +{ + CC_SAFE_DELETE(m_pImpl); +} + +////////////////////////////////////////////////////////////////////////// +// Add/Attach/Remove CCIMEDelegate +////////////////////////////////////////////////////////////////////////// + +void CCIMEDispatcher::addDelegate(CCIMEDelegate* pDelegate) +{ + if (! pDelegate || ! m_pImpl) + { + return; + } + if (m_pImpl->m_DelegateList.end() != m_pImpl->findDelegate(pDelegate)) + { + // pDelegate already in list + return; + } + m_pImpl->m_DelegateList.push_front(pDelegate); +} + +bool CCIMEDispatcher::attachDelegateWithIME(CCIMEDelegate * pDelegate) +{ + bool bRet = false; + do + { + CC_BREAK_IF(! m_pImpl || ! pDelegate); + + DelegateIter end = m_pImpl->m_DelegateList.end(); + DelegateIter iter = m_pImpl->findDelegate(pDelegate); + + // if pDelegate is not in delegate list, return + CC_BREAK_IF(end == iter); + + if (m_pImpl->m_DelegateWithIme != end) + { + // if old delegate canDetatchWithIME return false + // or pDelegate canAttachWithIME return false, + // do nothing. + CC_BREAK_IF(! (*(m_pImpl->m_DelegateWithIme))->canDetatchWithIME() + || ! pDelegate->canAttachWithIME()); + + // detach first + CCIMEDelegate * pOldDelegate = *(m_pImpl->m_DelegateWithIme); + m_pImpl->m_DelegateWithIme = end; + pOldDelegate->detatchWithIME(); + } + m_pImpl->m_DelegateWithIme = iter; + bRet = true; + } while (0); + return bRet; +} + +void CCIMEDispatcher::removeDelegate(CCIMEDelegate* pDelegate) +{ + do + { + CC_BREAK_IF(! pDelegate || ! m_pImpl); + + DelegateIter iter = m_pImpl->findDelegate(pDelegate); + DelegateIter end = m_pImpl->m_DelegateList.end(); + CC_BREAK_IF(end == iter); + + if (m_pImpl->m_DelegateWithIme != end + &&*iter == *(m_pImpl->m_DelegateWithIme)) + { + m_pImpl->m_DelegateWithIme == end; + } + m_pImpl->m_DelegateList.erase(iter); + } while (0); +} + +void CCIMEDispatcher::dispatchInsertText(const char * pText, int nLen) +{ + do + { + CC_BREAK_IF(! m_pImpl || ! pText || nLen <= 0); + + // there is no delegate attach with ime + CC_BREAK_IF(m_pImpl->m_DelegateWithIme == m_pImpl->m_DelegateList.end()); + + CCIMEDelegate * pDelegate = *(m_pImpl->m_DelegateWithIme); + pDelegate->insertText(pText, nLen); + } while (0); +} + +void CCIMEDispatcher::dispatchDeleteBackward() +{ + do + { + CC_BREAK_IF(! m_pImpl); + + // there is no delegate attach with ime + CC_BREAK_IF(m_pImpl->m_DelegateWithIme == m_pImpl->m_DelegateList.end()); + + CCIMEDelegate * pDelegate = *(m_pImpl->m_DelegateWithIme); + pDelegate->deleteBackward(); + } while (0); +} + +////////////////////////////////////////////////////////////////////////// +// protected member function +////////////////////////////////////////////////////////////////////////// + + +////////////////////////////////////////////////////////////////////////// +// static member function +////////////////////////////////////////////////////////////////////////// + +CCIMEDispatcher* CCIMEDispatcher::sharedDispatcher() +{ + static CCIMEDispatcher s_instance; + return &s_instance; +} + +NS_CC_END; diff --git a/cocos2dx/text_input_node/CCTextFieldTTF.cpp b/cocos2dx/text_input_node/CCTextFieldTTF.cpp new file mode 100644 index 0000000000..65a935b839 --- /dev/null +++ b/cocos2dx/text_input_node/CCTextFieldTTF.cpp @@ -0,0 +1,251 @@ +/**************************************************************************** +Copyright (c) 2010 cocos2d-x.org + +http://www.cocos2d-x.org + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +****************************************************************************/ + +#include "CCTextFieldTTF.h" + +#include + +#include "CCDirector.h" +#include "CCEGLView.h" + +NS_CC_BEGIN; + +/** +@brief Use std::vector store every input text length. +*/ +class CCTextFieldTTF::LengthStack : public std::vector< unsigned short > +{ +}; + +////////////////////////////////////////////////////////////////////////// +// constructor and destructor +////////////////////////////////////////////////////////////////////////// + +CCTextFieldTTF::CCTextFieldTTF() +: m_pInputText(new std::string) +, m_pPlaceHolder(new std::string) // prevent CCLabelTTF initWithString assertion +, m_pLens(new LengthStack) +, m_bLock(false) +{ +} + +CCTextFieldTTF::~CCTextFieldTTF() +{ + CC_SAFE_DELETE(m_pInputText); + CC_SAFE_DELETE(m_pPlaceHolder); +} + +////////////////////////////////////////////////////////////////////////// +// static constructor +////////////////////////////////////////////////////////////////////////// + +CCTextFieldTTF * CCTextFieldTTF::textFieldWithPlaceHolder(const char *placeholder, CCSize dimensions, CCTextAlignment alignment, const char *fontName, float fontSize) +{ + CCTextFieldTTF *pRet = new CCTextFieldTTF(); + if(pRet && pRet->initWithPlaceHolder("", dimensions, alignment, fontName, fontSize)) + { + pRet->autorelease(); + if (placeholder) + { + pRet->setPlaceHolder(placeholder); + } + return pRet; + } + CC_SAFE_DELETE(pRet); + return NULL; +} + +CCTextFieldTTF * CCTextFieldTTF::textFieldWithPlaceHolder(const char *placeholder, const char *fontName, float fontSize) +{ + CCTextFieldTTF *pRet = new CCTextFieldTTF(); + if(pRet && pRet->initWithString("", fontName, fontSize)) + { + pRet->autorelease(); + if (placeholder) + { + pRet->setPlaceHolder(placeholder); + } + return pRet; + } + CC_SAFE_DELETE(pRet); + return NULL; +} + +////////////////////////////////////////////////////////////////////////// +// initialize +////////////////////////////////////////////////////////////////////////// + +bool CCTextFieldTTF::initWithPlaceHolder(const char *placeholder, CCSize dimensions, CCTextAlignment alignment, const char *fontName, float fontSize) +{ + if (placeholder) + { + CC_SAFE_DELETE(m_pPlaceHolder); + m_pPlaceHolder = new std::string(placeholder); + } + return CCLabelTTF::initWithString(m_pPlaceHolder->c_str(), dimensions, alignment, fontName, fontSize); +} +bool CCTextFieldTTF::initWithPlaceHolder(const char *placeholder, const char *fontName, float fontSize) +{ + if (placeholder) + { + CC_SAFE_DELETE(m_pPlaceHolder); + m_pPlaceHolder = new std::string(placeholder); + } + return CCLabelTTF::initWithString(m_pPlaceHolder->c_str(), fontName, fontSize); +} + +////////////////////////////////////////////////////////////////////////// +// CCIMEDelegate +////////////////////////////////////////////////////////////////////////// + +bool CCTextFieldTTF::attachWithIME() +{ + bool bRet = CCIMEDelegate::attachWithIME(); + if (bRet) + { + // open keyboard + CCEGLView * pGlView = CCDirector::sharedDirector()->getOpenGLView(); + if (pGlView) + { + pGlView->setIMEKeyboardState(true); + } + } + return bRet; +} + +bool CCTextFieldTTF::canAttachWithIME() +{ + return true; +} + +bool CCTextFieldTTF::canDetatchWithIME() +{ + return true; +} + +void CCTextFieldTTF::detatchWithIME() +{ + CCEGLView * pGlView = CCDirector::sharedDirector()->getOpenGLView(); + if (pGlView) + { + pGlView->setIMEKeyboardState(false); + } +} + +void CCTextFieldTTF::insertText(const char * text, int len) +{ + m_bLock = true; + std::string sText(*m_pInputText); + sText.append(text, len); + m_pLens->push_back((unsigned short)len); + setString(sText.c_str()); + m_bLock = false; +} + +void CCTextFieldTTF::deleteBackward() +{ + int nStrLen = m_pInputText->length(); + if (! nStrLen) + { + // there is no string + return; + } + + m_bLock = true; + + // get the delete byte number + int nStackSize = m_pLens->size(); + unsigned short uDeleteLen = 1; // default, erase 1 byte + if (nStackSize) + { + // get the last input text size + uDeleteLen = m_pLens->at(nStackSize - 1); + m_pLens->pop_back(); + } + + // if delete all text, show space holder string + if (nStrLen <= uDeleteLen) + { + CC_SAFE_DELETE(m_pInputText); + m_pInputText = new std::string; + CCLabelTTF::setString(m_pPlaceHolder->c_str()); + return; + } + + // set new input text + std::string sText(m_pInputText->c_str(), nStrLen - uDeleteLen); + setString(sText.c_str()); + m_bLock = false; +} + +////////////////////////////////////////////////////////////////////////// +// properties +////////////////////////////////////////////////////////////////////////// + +// input text property +void CCTextFieldTTF::setString(const char *text) +{ + CC_SAFE_DELETE(m_pInputText); + if (false == m_bLock) + { + // user use this function to set string value, clear lenStack + m_pLens->clear(); + } + if (text) + { + m_pInputText = new std::string(text); + } + else + { + m_pInputText = new std::string; + } + + // if there is no input text, display placeholder instead if (! m_pInputText->length()) { CCLabelTTF::setString(m_pPlaceHolder->c_str()); } else + { + CCLabelTTF::setString(m_pInputText->c_str()); + } +} + +const char* CCTextFieldTTF::getString(void) +{ + return m_pInputText->c_str(); +} + +// place holder text property +void CCTextFieldTTF::setPlaceHolder(const char * text) +{ + CC_SAFE_DELETE(m_pPlaceHolder); + m_pPlaceHolder = (text) ? new std::string(text) : new std::string; + if (! m_pInputText->length()) + { + CCLabelTTF::setString(m_pPlaceHolder->c_str()); + } +} + +const char * CCTextFieldTTF::getPlaceHolder(void) +{ + return m_pPlaceHolder->c_str(); +} + +NS_CC_END;