mirror of https://github.com/axmolengine/axmol.git
Merge remote branch 'origin/master'
This commit is contained in:
commit
2cceeb5c39
|
@ -69,7 +69,7 @@ bool AppDelegate::applicationDidFinishLaunching()
|
|||
// enable High Resource Mode(2x, such as iphone4) and maintains low resource on other devices.
|
||||
// pDirector->enableRetinaDisplay(true);
|
||||
|
||||
// sets landscape mode
|
||||
// sets opengl landscape mode
|
||||
pDirector->setDeviceOrientation(kCCDeviceOrientationLandscapeLeft);
|
||||
|
||||
// turn on display FPS
|
||||
|
|
|
@ -2,17 +2,146 @@ package org.cocos2dx.lib;
|
|||
|
||||
import android.content.Context;
|
||||
import android.opengl.GLSurfaceView;
|
||||
import android.os.Bundle;
|
||||
import android.util.AttributeSet;
|
||||
import android.util.Log;
|
||||
import android.view.KeyEvent;
|
||||
import android.view.MotionEvent;
|
||||
import android.view.ViewGroup.LayoutParams;
|
||||
import android.view.inputmethod.CompletionInfo;
|
||||
import android.view.inputmethod.EditorInfo;
|
||||
import android.view.inputmethod.ExtractedText;
|
||||
import android.view.inputmethod.ExtractedTextRequest;
|
||||
import android.view.inputmethod.InputConnection;
|
||||
import android.view.inputmethod.InputMethodManager;
|
||||
|
||||
class Cocos2dxInputConnection implements InputConnection {
|
||||
|
||||
@Override
|
||||
public boolean beginBatchEdit() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean clearMetaKeyStates(int states) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean commitCompletion(CompletionInfo text) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean commitText(CharSequence text, int newCursorPosition) {
|
||||
if (null != mView) {
|
||||
final String insertText = text.toString();
|
||||
mView.insertText(insertText);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean deleteSurroundingText(int leftLength, int rightLength) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean endBatchEdit() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean finishComposingText() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getCursorCapsMode(int reqModes) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ExtractedText getExtractedText(ExtractedTextRequest request,
|
||||
int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CharSequence getTextAfterCursor(int n, int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CharSequence getTextBeforeCursor(int n, int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performContextMenuAction(int id) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performEditorAction(int editorAction) {
|
||||
if (null != mView) {
|
||||
final String insertText = "\n";
|
||||
mView.insertText(insertText);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performPrivateCommand(String action, Bundle data) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean reportFullscreenMode(boolean enabled) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean sendKeyEvent(KeyEvent event) {
|
||||
if (null != mView) {
|
||||
switch (event.getKeyCode()) {
|
||||
|
||||
case KeyEvent.KEYCODE_DEL:
|
||||
mView.deleteBackward();
|
||||
break;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean setComposingText(CharSequence text, int newCursorPosition) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean setSelection(int start, int end) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public void setGLSurfaceView(Cocos2dxGLSurfaceView view) {
|
||||
mView = view;
|
||||
}
|
||||
|
||||
private Cocos2dxGLSurfaceView mView;
|
||||
}
|
||||
|
||||
public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
||||
private static final String TAG = Cocos2dxGLSurfaceView.class
|
||||
.getCanonicalName();
|
||||
|
||||
static private Cocos2dxGLSurfaceView mainView;
|
||||
|
||||
private static final String TAG = Cocos2dxGLSurfaceView.class.getCanonicalName();
|
||||
private Cocos2dxRenderer mRenderer;
|
||||
private final boolean debug = false;
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for initialize
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
public Cocos2dxGLSurfaceView(Context context) {
|
||||
super(context);
|
||||
initView();
|
||||
|
@ -27,6 +156,7 @@ public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
|||
mRenderer = new Cocos2dxRenderer();
|
||||
setFocusableInTouchMode(true);
|
||||
setRenderer(mRenderer);
|
||||
mainView = this;
|
||||
}
|
||||
|
||||
public void onPause(){
|
||||
|
@ -51,6 +181,83 @@ public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
|||
});
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for text input
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public static void openIMEKeyboard() {
|
||||
if (null == mainView) {
|
||||
return;
|
||||
}
|
||||
InputMethodManager imm = (InputMethodManager)mainView.getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
|
||||
if (imm == null) {
|
||||
return;
|
||||
}
|
||||
imm.showSoftInput(mainView, 0);
|
||||
}
|
||||
|
||||
public static void closeIMEKeyboard() {
|
||||
if (null == mainView) {
|
||||
return;
|
||||
}
|
||||
InputMethodManager imm = (InputMethodManager)mainView.getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
|
||||
if (imm == null) {
|
||||
return;
|
||||
}
|
||||
imm.hideSoftInputFromWindow(mainView.getWindowToken(), 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onCheckIsTextEditor() {
|
||||
if (null == mainView)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private Cocos2dxInputConnection ic;
|
||||
@Override
|
||||
public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
|
||||
if (onCheckIsTextEditor()) {
|
||||
|
||||
outAttrs.inputType = EditorInfo.TYPE_CLASS_TEXT;
|
||||
outAttrs.imeOptions = EditorInfo.IME_NULL;
|
||||
outAttrs.initialSelStart = -1;
|
||||
outAttrs.initialSelEnd = -1;
|
||||
outAttrs.initialCapsMode = 0;
|
||||
|
||||
if (null == ic)
|
||||
{
|
||||
ic = new Cocos2dxInputConnection();
|
||||
ic.setGLSurfaceView(this);
|
||||
}
|
||||
return ic;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public void insertText(final String text) {
|
||||
queueEvent(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
mRenderer.handleInsertText(text);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void deleteBackward() {
|
||||
queueEvent(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
mRenderer.handleDeleteBackward();
|
||||
}
|
||||
});
|
||||
}
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for touch event
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public boolean onTouchEvent(final MotionEvent event) {
|
||||
// these data are used in ACTION_MOVE and ACTION_CANCEL
|
||||
final int pointerNumber = event.getPointerCount();
|
||||
|
|
|
@ -75,7 +75,6 @@ public class Cocos2dxRenderer implements GLSurfaceView.Renderer {
|
|||
public static void setAnimationInterval(double interval){
|
||||
animationInterval = (long)(interval * NANOSECONDSPERSECOND);
|
||||
}
|
||||
|
||||
private static native void nativeTouchesBegin(int id, float x, float y);
|
||||
private static native void nativeTouchesEnd(int id, float x, float y);
|
||||
private static native void nativeTouchesMove(int[] id, float[] x, float[] y);
|
||||
|
@ -85,4 +84,19 @@ public class Cocos2dxRenderer implements GLSurfaceView.Renderer {
|
|||
private static native void nativeInit(int w, int h);
|
||||
private static native void nativeOnPause();
|
||||
private static native void nativeOnResume();
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
// handle input method edit message
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public void handleInsertText(final String text) {
|
||||
nativeInsertText(text);
|
||||
}
|
||||
|
||||
public void handleDeleteBackward() {
|
||||
nativeDeleteBackward();
|
||||
}
|
||||
|
||||
private static native void nativeInsertText(String text);
|
||||
private static native void nativeDeleteBackward();
|
||||
}
|
||||
|
|
|
@ -1 +1 @@
|
|||
4b1a0a89eeffc4ac07d3adecd95b38b431f8cd5c
|
||||
3300607858936d3cd32e8d541a02eb4464613808
|
|
@ -83,6 +83,8 @@ support/image_support/TGAlib.cpp \
|
|||
support/zip_support/ZipUtils.cpp \
|
||||
support/zip_support/ioapi.cpp \
|
||||
support/zip_support/unzip.cpp \
|
||||
text_input_node/CCIMEDispatcher.cpp \
|
||||
text_input_node/CCTextFieldTTF.cpp \
|
||||
textures/CCTexture2D.cpp \
|
||||
textures/CCTextureAtlas.cpp \
|
||||
textures/CCTextureCache.cpp \
|
||||
|
|
|
@ -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_IME_DELEGATE_H__
|
||||
#define __CC_IME_DELEGATE_H__
|
||||
|
||||
#include "CCGeometry.h"
|
||||
|
||||
NS_CC_BEGIN;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
CCRect begin; // the soft keyboard rectangle when animatin begin
|
||||
CCRect end; // the soft keyboard rectangle when animatin end
|
||||
float duration; // the soft keyboard animation duration
|
||||
} CCIMEKeyboardNotificationInfo;
|
||||
|
||||
/**
|
||||
@brief Input method editor delegate.
|
||||
*/
|
||||
class CC_DLL CCIMEDelegate
|
||||
{
|
||||
public:
|
||||
virtual ~CCIMEDelegate();
|
||||
|
||||
virtual bool attachWithIME();
|
||||
virtual bool detachWithIME();
|
||||
|
||||
protected:
|
||||
friend class CCIMEDispatcher;
|
||||
|
||||
/**
|
||||
@brief Decide the delegate instance is ready for receive ime message or not.
|
||||
|
||||
Called by CCIMEDispatcher.
|
||||
*/
|
||||
virtual bool canAttachWithIME() { return false; }
|
||||
/**
|
||||
@brief When the delegate detach with IME, this method call by CCIMEDispatcher.
|
||||
*/
|
||||
virtual void didAttachWithIME() {}
|
||||
|
||||
/**
|
||||
@brief Decide the delegate instance can stop receive ime message or not.
|
||||
*/
|
||||
virtual bool canDetachWithIME() { return false; }
|
||||
|
||||
/**
|
||||
@brief When the delegate detach with IME, this method call by CCIMEDispatcher.
|
||||
*/
|
||||
virtual void didDetachWithIME() {}
|
||||
|
||||
/**
|
||||
@brief Called by CCIMEDispatcher when some text input from IME.
|
||||
*/
|
||||
virtual void insertText(const char * text, int len) {}
|
||||
|
||||
/**
|
||||
@brief Called by CCIMEDispatcher when user clicked the backward key.
|
||||
*/
|
||||
virtual void deleteBackward() {}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// keyboard show/hide notification
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
virtual void keyboardWillShow(CCIMEKeyboardNotificationInfo& info) {}
|
||||
virtual void keyboardDidShow(CCIMEKeyboardNotificationInfo& info) {}
|
||||
virtual void keyboardWillHide(CCIMEKeyboardNotificationInfo& info) {}
|
||||
virtual void keyboardDidHide(CCIMEKeyboardNotificationInfo& info) {}
|
||||
|
||||
protected:
|
||||
CCIMEDelegate();
|
||||
};
|
||||
|
||||
NS_CC_END;
|
||||
|
||||
#endif // __CC_IME_DELEGATE_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_IME_DISPATCHER_H__
|
||||
#define __CC_IME_DISPATCHER_H__
|
||||
|
||||
#include "CCIMEDelegate.h"
|
||||
|
||||
NS_CC_BEGIN;
|
||||
|
||||
/**
|
||||
@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();
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// dispatch keyboard notification
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
void dispatchKeyboardWillShow(CCIMEKeyboardNotificationInfo& info);
|
||||
void dispatchKeyboardDidShow(CCIMEKeyboardNotificationInfo& info);
|
||||
void dispatchKeyboardWillHide(CCIMEKeyboardNotificationInfo& info);
|
||||
void dispatchKeyboardDidHide(CCIMEKeyboardNotificationInfo& info);
|
||||
|
||||
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);
|
||||
bool detachDelegateWithIME(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__
|
|
@ -0,0 +1,102 @@
|
|||
/****************************************************************************
|
||||
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 Open keyboard and receive input text.
|
||||
*/
|
||||
virtual bool attachWithIME();
|
||||
|
||||
/**
|
||||
@brief End text input and close keyboard.
|
||||
*/
|
||||
virtual bool detachWithIME();
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// 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 canDetachWithIME();
|
||||
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__
|
|
@ -57,8 +57,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) {}
|
||||
|
|
|
@ -83,6 +83,7 @@ THE SOFTWARE.
|
|||
#include "CCTouchDispatcher.h"
|
||||
#include "CCDrawingPrimitives.h"
|
||||
#include "CCScheduler.h"
|
||||
#include "CCTextFieldTTF.h"
|
||||
|
||||
//
|
||||
// cocoa includes
|
||||
|
|
|
@ -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;
|
||||
}
|
||||
|
||||
|
|
|
@ -28,6 +28,7 @@ THE SOFTWARE.
|
|||
#include "CCDirector.h"
|
||||
#include "ccMacros.h"
|
||||
#include "CCTouchDispatcher.h"
|
||||
#include "Cocos2dJni.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
|
@ -168,5 +169,11 @@ CCRect CCEGLView::getViewPort()
|
|||
}
|
||||
}
|
||||
|
||||
void CCEGLView::setIMEKeyboardState(bool bOpen)
|
||||
{
|
||||
|
||||
setKeyboardStateJNI((int)bOpen);
|
||||
}
|
||||
|
||||
} // end of namespace cocos2d
|
||||
|
||||
|
|
|
@ -60,6 +60,7 @@ public:
|
|||
void setViewPortInPoints(float x, float y, float w, float h);
|
||||
CCRect getViewPort();
|
||||
float getScreenScaleFactor();
|
||||
void setIMEKeyboardState(bool bOpen);
|
||||
|
||||
// static function
|
||||
/**
|
||||
|
|
|
@ -31,6 +31,8 @@ THE SOFTWARE.
|
|||
#include "CCGeometry.h"
|
||||
#include "CCAccelerometer.h"
|
||||
#include "CCApplication.h"
|
||||
#include "CCIMEDispatcher.h"
|
||||
#include "platform/android/CCAccelerometer_android.h"
|
||||
#include <android/log.h>
|
||||
|
||||
#if 0
|
||||
|
@ -44,21 +46,70 @@ using namespace cocos2d;
|
|||
|
||||
extern "C"
|
||||
{
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// java vm helper function
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
JavaVM *gJavaVM = NULL;
|
||||
|
||||
jint JNI_OnLoad(JavaVM *vm, void *reserved)
|
||||
{
|
||||
gJavaVM = vm;
|
||||
return JNI_VERSION_1_4;
|
||||
}
|
||||
|
||||
struct TMethodJNI
|
||||
{
|
||||
JNIEnv * env;
|
||||
jclass classID;
|
||||
jmethodID methodID;
|
||||
};
|
||||
static bool getMethodID(struct TMethodJNI& t, const char *className, const char *methodName, const char *paramCode)
|
||||
{
|
||||
bool ret = 0;
|
||||
do
|
||||
{
|
||||
if (gJavaVM->GetEnv((void**)&t.env, JNI_VERSION_1_4) != JNI_OK)
|
||||
{
|
||||
LOGD("Failed to get the environment using GetEnv()");
|
||||
break;
|
||||
}
|
||||
|
||||
if (gJavaVM->AttachCurrentThread(&t.env, 0) < 0)
|
||||
{
|
||||
LOGD("Failed to get the environment using AttachCurrentThread()");
|
||||
break;
|
||||
}
|
||||
|
||||
t.classID = t.env->FindClass(className);
|
||||
if (! t.classID)
|
||||
{
|
||||
LOGD("Failed to find class of %s", className);
|
||||
break;
|
||||
}
|
||||
|
||||
t.methodID = t.env->GetStaticMethodID(t.classID, methodName, paramCode);
|
||||
if (! t.methodID)
|
||||
{
|
||||
LOGD("Failed to find method id of %s", methodName);
|
||||
break;
|
||||
}
|
||||
ret = true;
|
||||
} while (0);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// native renderer
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#define MAX_TOUCHES 5
|
||||
static CCTouch *s_pTouches[MAX_TOUCHES] = { NULL };
|
||||
|
||||
// handle accelerometer changes
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxAccelerometer_onSensorChanged(JNIEnv* env, jobject thiz, jfloat x, jfloat y, jfloat z, jlong timeStamp)
|
||||
void Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeRender(JNIEnv* env)
|
||||
{
|
||||
// We need to invert to make it compatible with iOS.
|
||||
CCRect rcRect = CCEGLView::sharedOpenGLView().getViewPort();
|
||||
float fScreenScaleFactor = CCEGLView::sharedOpenGLView().getScreenScaleFactor();
|
||||
cocos2d::CCAccelerometer::sharedAccelerometer()->update((x - rcRect.origin.x) / fScreenScaleFactor,
|
||||
(y - rcRect.origin.y) / fScreenScaleFactor,
|
||||
z,
|
||||
timeStamp);
|
||||
cocos2d::CCDirector::sharedDirector()->mainLoop();
|
||||
}
|
||||
|
||||
// handle touch event
|
||||
|
@ -211,6 +262,21 @@ extern "C"
|
|||
return JNI_FALSE;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// handle accelerometer changes
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxAccelerometer_onSensorChanged(JNIEnv* env, jobject thiz, jfloat x, jfloat y, jfloat z, jlong timeStamp)
|
||||
{
|
||||
// We need to invert to make it compatible with iOS.
|
||||
CCRect rcRect = CCEGLView::sharedOpenGLView().getViewPort();
|
||||
float fScreenScaleFactor = CCEGLView::sharedOpenGLView().getScreenScaleFactor();
|
||||
cocos2d::CCAccelerometer::sharedAccelerometer()->update((x - rcRect.origin.x) / fScreenScaleFactor,
|
||||
(y - rcRect.origin.y) / fScreenScaleFactor,
|
||||
z,
|
||||
timeStamp);
|
||||
}
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxActivity_nativeSetPaths(JNIEnv* env, jobject thiz, jstring apkPath)
|
||||
{
|
||||
const char* str;
|
||||
|
@ -222,72 +288,29 @@ extern "C"
|
|||
}
|
||||
}
|
||||
|
||||
// record the java vm
|
||||
|
||||
JavaVM *gJavaVM = NULL;
|
||||
jclass classOfCocos2dxActivity = 0;
|
||||
JNIEnv *env = 0;
|
||||
|
||||
jint JNI_OnLoad(JavaVM *vm, void *reserved)
|
||||
{
|
||||
gJavaVM = vm;
|
||||
return JNI_VERSION_1_4;
|
||||
}
|
||||
|
||||
static jmethodID getMethodID(const char *methodName, const char *paramCode)
|
||||
{
|
||||
jmethodID ret = 0;
|
||||
|
||||
// get jni environment and java class for Cocos2dxActivity
|
||||
if (gJavaVM->GetEnv((void**)&env, JNI_VERSION_1_4) != JNI_OK)
|
||||
{
|
||||
LOGD("Failed to get the environment using GetEnv()");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (gJavaVM->AttachCurrentThread(&env, 0) < 0)
|
||||
{
|
||||
LOGD("Failed to get the environment using AttachCurrentThread()");
|
||||
return 0;
|
||||
}
|
||||
|
||||
classOfCocos2dxActivity = env->FindClass("org/cocos2dx/lib/Cocos2dxActivity");
|
||||
if (! classOfCocos2dxActivity)
|
||||
{
|
||||
LOGD("Failed to find class of org/cocos2dx/lib/Cocos2dxActivity");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (env != 0 && classOfCocos2dxActivity != 0)
|
||||
{
|
||||
ret = env->GetStaticMethodID(classOfCocos2dxActivity, methodName, paramCode);
|
||||
}
|
||||
|
||||
if (! ret)
|
||||
{
|
||||
LOGD("get method id of %s error", methodName);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void enableAccelerometerJNI()
|
||||
{
|
||||
jmethodID methodID = getMethodID("enableAccelerometer", "()V");
|
||||
|
||||
if (methodID)
|
||||
TMethodJNI t;
|
||||
if (getMethodID(t
|
||||
, "org/cocos2dx/lib/Cocos2dxActivity"
|
||||
, "enableAccelerometer"
|
||||
, "()V"))
|
||||
{
|
||||
env->CallStaticVoidMethod(classOfCocos2dxActivity, methodID);
|
||||
t.env->CallStaticVoidMethod(t.classID, t.methodID);
|
||||
}
|
||||
}
|
||||
|
||||
void disableAccelerometerJNI()
|
||||
{
|
||||
jmethodID methodID = getMethodID("disableAccelerometer", "()V");
|
||||
TMethodJNI t;
|
||||
|
||||
if (methodID)
|
||||
if (getMethodID(t
|
||||
, "org/cocos2dx/lib/Cocos2dxActivity"
|
||||
, "disableAccelerometer"
|
||||
, "()V"))
|
||||
{
|
||||
env->CallStaticVoidMethod(classOfCocos2dxActivity, methodID);
|
||||
t.env->CallStaticVoidMethod(t.classID, t.methodID);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -298,30 +321,58 @@ extern "C"
|
|||
return;
|
||||
}
|
||||
|
||||
jmethodID methodID = getMethodID("showMessageBox", "(Ljava/lang/String;Ljava/lang/String;)V");
|
||||
|
||||
if (methodID)
|
||||
TMethodJNI t;
|
||||
if (getMethodID(t
|
||||
, "org/cocos2dx/lib/Cocos2dxActivity"
|
||||
, "showMessageBox"
|
||||
, "(Ljava/lang/String;Ljava/lang/String;)V"))
|
||||
{
|
||||
jstring StringArg1;
|
||||
|
||||
if (! pszTitle)
|
||||
{
|
||||
StringArg1 = env->NewStringUTF("");
|
||||
StringArg1 = t.env->NewStringUTF("");
|
||||
}
|
||||
else
|
||||
{
|
||||
StringArg1 = env->NewStringUTF(pszTitle);
|
||||
StringArg1 = t.env->NewStringUTF(pszTitle);
|
||||
}
|
||||
|
||||
jstring StringArg2 = env->NewStringUTF(pszMsg);
|
||||
env->CallStaticVoidMethod(classOfCocos2dxActivity, methodID, StringArg1, StringArg2);
|
||||
jstring StringArg2 = t.env->NewStringUTF(pszMsg);
|
||||
t.env->CallStaticVoidMethod(t.classID, t.methodID, StringArg1, StringArg2);
|
||||
}
|
||||
}
|
||||
|
||||
// native renderer
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// handle IME message
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeRender(JNIEnv* env)
|
||||
void setKeyboardStateJNI(int bOpen)
|
||||
{
|
||||
cocos2d::CCDirector::sharedDirector()->mainLoop();
|
||||
TMethodJNI t;
|
||||
jint open = bOpen;
|
||||
if (getMethodID(t
|
||||
, "org/cocos2dx/lib/Cocos2dxGLSurfaceView"
|
||||
, (bOpen) ? "openIMEKeyboard" : "closeIMEKeyboard"
|
||||
, "()V"))
|
||||
{
|
||||
t.env->CallStaticVoidMethod(t.classID, t.methodID);
|
||||
}
|
||||
}
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeInsertText(JNIEnv* env, jobject thiz, jstring text)
|
||||
{
|
||||
jboolean isCopy = 0;
|
||||
const char* pszText = env->GetStringUTFChars(text, &isCopy);
|
||||
if (isCopy)
|
||||
{
|
||||
cocos2d::CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(pszText, strlen(pszText));
|
||||
env->ReleaseStringUTFChars(text, pszText);
|
||||
}
|
||||
}
|
||||
|
||||
void Java_org_cocos2dx_lib_Cocos2dxRenderer_nativeDeleteBackward(JNIEnv* env, jobject thiz)
|
||||
{
|
||||
cocos2d::CCIMEDispatcher::sharedDispatcher()->dispatchDeleteBackward();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,6 +33,7 @@ extern "C"
|
|||
void enableAccelerometerJNI();
|
||||
void disableAccelerometerJNI();
|
||||
void showMessageBoxJNI(const char * pszMsg, const char * pszTitle);
|
||||
void setKeyboardStateJNI(int bOpen);
|
||||
}
|
||||
|
||||
#endif // __ANDROID_COCOS2D_JNI_H__
|
||||
|
|
|
@ -55,6 +55,8 @@ public:
|
|||
void touchesEnded(CCSet *set);
|
||||
void touchesCancelled(CCSet *set);
|
||||
|
||||
void setIMEKeyboardState(bool bOpen);
|
||||
|
||||
static CCEGLView& sharedOpenGLView();
|
||||
|
||||
private:
|
||||
|
|
|
@ -114,6 +114,18 @@ void CCEGLView::setViewPortInPoints(float x, float y, float w, float h)
|
|||
glViewport((GLint)x, (GLint)y, (GLint)w, (GLint)h);
|
||||
}
|
||||
|
||||
void CCEGLView::setIMEKeyboardState(bool bOpen)
|
||||
{
|
||||
if (bOpen)
|
||||
{
|
||||
[[EAGLView sharedEGLView] becomeFirstResponder];
|
||||
}
|
||||
else
|
||||
{
|
||||
[[EAGLView sharedEGLView] resignFirstResponder];
|
||||
}
|
||||
}
|
||||
|
||||
CCEGLView& CCEGLView::sharedOpenGLView()
|
||||
{
|
||||
static CCEGLView instance;
|
||||
|
|
|
@ -77,7 +77,7 @@ Copyright (C) 2008 Apple Inc. All Rights Reserved.
|
|||
* The view content is basically an EAGL surface you render your OpenGL scene into.
|
||||
* Note that setting the view non-opaque will only work if the EAGL surface has an alpha channel.
|
||||
*/
|
||||
@interface EAGLView : UIView
|
||||
@interface EAGLView : UIView <UIKeyInput, UITextInput>
|
||||
{
|
||||
id <ESRenderer> renderer_;
|
||||
EAGLContext *context_; // weak ref
|
||||
|
@ -95,8 +95,17 @@ Copyright (C) 2008 Apple Inc. All Rights Reserved.
|
|||
@private
|
||||
CFMutableDictionaryRef touchesIntergerDict;
|
||||
unsigned int indexBitsUsed;
|
||||
NSString * markedText_;
|
||||
}
|
||||
|
||||
@property(nonatomic, readonly) UITextPosition *beginningOfDocument;
|
||||
@property(nonatomic, readonly) UITextPosition *endOfDocument;
|
||||
@property(nonatomic, assign) id<UITextInputDelegate> inputDelegate;
|
||||
@property(nonatomic, readonly) UITextRange *markedTextRange;
|
||||
@property (nonatomic, copy) NSDictionary *markedTextStyle;
|
||||
@property(readwrite, copy) UITextRange *selectedTextRange;
|
||||
@property(nonatomic, readonly) id<UITextInputTokenizer> tokenizer;
|
||||
|
||||
/** creates an initializes an EAGLView with a frame and 0-bit depth buffer, and a RGB565 color buffer */
|
||||
+ (id) viewWithFrame:(CGRect)frame;
|
||||
/** creates an initializes an EAGLView with a frame, a color buffer format, and 0-bit depth buffer */
|
||||
|
@ -142,4 +151,5 @@ Copyright (C) 2008 Apple Inc. All Rights Reserved.
|
|||
-(int) getHeight;
|
||||
-(int) getUnUsedIndex;
|
||||
-(void) removeUsedIndexBit:(int) index;
|
||||
|
||||
@end
|
||||
|
|
|
@ -68,6 +68,7 @@ Copyright (C) 2008 Apple Inc. All Rights Reserved.
|
|||
#import "CCDirector.h"
|
||||
#import "CCSet.h"
|
||||
#import "CCTouch.h"
|
||||
#import "CCIMEDispatcher.h"
|
||||
#import "OpenGL_Internal.h"
|
||||
|
||||
//CLASS IMPLEMENTATIONS:
|
||||
|
@ -176,6 +177,25 @@ static cocos2d::CCTouch *s_pTouches[MAX_TOUCHES];
|
|||
return self;
|
||||
}
|
||||
|
||||
- (void)didMoveToWindow;
|
||||
{
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
||||
selector:@selector(onUIKeyboardNotification:)
|
||||
name:UIKeyboardWillShowNotification object:nil];
|
||||
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
||||
selector:@selector(onUIKeyboardNotification:)
|
||||
name:UIKeyboardDidShowNotification object:nil];
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
||||
selector:@selector(onUIKeyboardNotification:)
|
||||
name:UIKeyboardWillHideNotification object:nil];
|
||||
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self
|
||||
selector:@selector(onUIKeyboardNotification:)
|
||||
name:UIKeyboardDidHideNotification object:nil];
|
||||
|
||||
}
|
||||
|
||||
-(int) getWidth
|
||||
{
|
||||
CGSize bound = [self bounds].size;
|
||||
|
@ -491,4 +511,306 @@ static cocos2d::CCTouch *s_pTouches[MAX_TOUCHES];
|
|||
cocos2d::CCDirector::sharedDirector()->getOpenGLView()->touchesCancelled(&set);
|
||||
}
|
||||
|
||||
#pragma mark -
|
||||
#pragma mark UIView - Responder
|
||||
|
||||
- (BOOL)canBecomeFirstResponder
|
||||
{
|
||||
markedText_ = nil;
|
||||
return YES;
|
||||
}
|
||||
|
||||
#pragma mark -
|
||||
#pragma mark UIKeyInput protocol
|
||||
|
||||
- (BOOL)hasText
|
||||
{
|
||||
return NO;
|
||||
}
|
||||
|
||||
- (void)insertText:(NSString *)text
|
||||
{
|
||||
const char * pszText = [text cStringUsingEncoding:NSUTF8StringEncoding];
|
||||
cocos2d::CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(pszText, strlen(pszText));
|
||||
}
|
||||
|
||||
- (void)deleteBackward
|
||||
{
|
||||
cocos2d::CCIMEDispatcher::sharedDispatcher()->dispatchDeleteBackward();
|
||||
}
|
||||
|
||||
#pragma mark -
|
||||
#pragma mark UITextInputTrait protocol
|
||||
|
||||
-(UITextAutocapitalizationType) autocapitalizationType
|
||||
{
|
||||
return UITextAutocapitalizationTypeNone;
|
||||
}
|
||||
|
||||
#pragma mark -
|
||||
#pragma mark UITextInput protocol
|
||||
|
||||
#pragma mark UITextInput - properties
|
||||
|
||||
@synthesize beginningOfDocument;
|
||||
@synthesize endOfDocument;
|
||||
@synthesize inputDelegate;
|
||||
@synthesize markedTextRange;
|
||||
@synthesize markedTextStyle;
|
||||
// @synthesize selectedTextRange; // must implement
|
||||
@synthesize tokenizer;
|
||||
|
||||
/* Text may have a selection, either zero-length (a caret) or ranged. Editing operations are
|
||||
* always performed on the text from this selection. nil corresponds to no selection. */
|
||||
- (void)setSelectedTextRange:(UITextRange *)aSelectedTextRange;
|
||||
{
|
||||
CCLOG("UITextRange:setSelectedTextRange");
|
||||
}
|
||||
- (UITextRange *)selectedTextRange;
|
||||
{
|
||||
return [[[UITextRange alloc] init] autorelease];
|
||||
}
|
||||
|
||||
#pragma mark UITextInput - Replacing and Returning Text
|
||||
|
||||
- (NSString *)textInRange:(UITextRange *)range;
|
||||
{
|
||||
CCLOG("textInRange");
|
||||
return nil;
|
||||
}
|
||||
- (void)replaceRange:(UITextRange *)range withText:(NSString *)theText;
|
||||
{
|
||||
CCLOG("replaceRange");
|
||||
}
|
||||
|
||||
#pragma mark UITextInput - Working with Marked and Selected Text
|
||||
|
||||
|
||||
|
||||
/* If text can be selected, it can be marked. Marked text represents provisionally
|
||||
* inserted text that has yet to be confirmed by the user. It requires unique visual
|
||||
* treatment in its display. If there is any marked text, the selection, whether a
|
||||
* caret or an extended range, always resides witihin.
|
||||
*
|
||||
* Setting marked text either replaces the existing marked text or, if none is present,
|
||||
* inserts it from the current selection. */
|
||||
|
||||
- (void)setMarkedTextRange:(UITextRange *)markedTextRange;
|
||||
{
|
||||
CCLOG("setMarkedTextRange");
|
||||
}
|
||||
|
||||
- (UITextRange *)markedTextRange;
|
||||
{
|
||||
CCLOG("markedTextRange");
|
||||
return nil; // Nil if no marked text.
|
||||
}
|
||||
- (void)setMarkedTextStyle:(NSDictionary *)markedTextStyle;
|
||||
{
|
||||
CCLOG("setMarkedTextStyle");
|
||||
|
||||
}
|
||||
- (NSDictionary *)markedTextStyle;
|
||||
{
|
||||
CCLOG("markedTextStyle");
|
||||
return nil;
|
||||
}
|
||||
- (void)setMarkedText:(NSString *)markedText selectedRange:(NSRange)selectedRange;
|
||||
{
|
||||
CCLOG("setMarkedText");
|
||||
markedText_ = markedText;
|
||||
}
|
||||
- (void)unmarkText;
|
||||
{
|
||||
CCLOG("unmarkText");
|
||||
if (nil == markedText_)
|
||||
{
|
||||
return;
|
||||
}
|
||||
const char * pszText = [markedText_ cStringUsingEncoding:NSUTF8StringEncoding];
|
||||
cocos2d::CCIMEDispatcher::sharedDispatcher()->dispatchInsertText(pszText, strlen(pszText));
|
||||
markedText_ = nil;
|
||||
}
|
||||
|
||||
#pragma mark Methods for creating ranges and positions.
|
||||
|
||||
- (UITextRange *)textRangeFromPosition:(UITextPosition *)fromPosition toPosition:(UITextPosition *)toPosition;
|
||||
{
|
||||
CCLOG("textRangeFromPosition");
|
||||
return nil;
|
||||
}
|
||||
- (UITextPosition *)positionFromPosition:(UITextPosition *)position offset:(NSInteger)offset;
|
||||
{
|
||||
CCLOG("positionFromPosition");
|
||||
return nil;
|
||||
}
|
||||
- (UITextPosition *)positionFromPosition:(UITextPosition *)position inDirection:(UITextLayoutDirection)direction offset:(NSInteger)offset;
|
||||
{
|
||||
CCLOG("positionFromPosition");
|
||||
return nil;
|
||||
}
|
||||
|
||||
/* Simple evaluation of positions */
|
||||
- (NSComparisonResult)comparePosition:(UITextPosition *)position toPosition:(UITextPosition *)other;
|
||||
{
|
||||
CCLOG("comparePosition");
|
||||
return 0;
|
||||
}
|
||||
- (NSInteger)offsetFromPosition:(UITextPosition *)from toPosition:(UITextPosition *)toPosition;
|
||||
{
|
||||
CCLOG("offsetFromPosition");
|
||||
return 0;
|
||||
}
|
||||
|
||||
- (UITextPosition *)positionWithinRange:(UITextRange *)range farthestInDirection:(UITextLayoutDirection)direction;
|
||||
{
|
||||
CCLOG("positionWithinRange");
|
||||
return nil;
|
||||
}
|
||||
- (UITextRange *)characterRangeByExtendingPosition:(UITextPosition *)position inDirection:(UITextLayoutDirection)direction;
|
||||
{
|
||||
CCLOG("characterRangeByExtendingPosition");
|
||||
return nil;
|
||||
}
|
||||
|
||||
#pragma mark Writing direction
|
||||
|
||||
- (UITextWritingDirection)baseWritingDirectionForPosition:(UITextPosition *)position inDirection:(UITextStorageDirection)direction;
|
||||
{
|
||||
CCLOG("baseWritingDirectionForPosition");
|
||||
return UITextWritingDirectionNatural;
|
||||
}
|
||||
- (void)setBaseWritingDirection:(UITextWritingDirection)writingDirection forRange:(UITextRange *)range;
|
||||
{
|
||||
CCLOG("setBaseWritingDirection");
|
||||
}
|
||||
|
||||
#pragma mark Geometry
|
||||
|
||||
/* Geometry used to provide, for example, a correction rect. */
|
||||
- (CGRect)firstRectForRange:(UITextRange *)range;
|
||||
{
|
||||
CCLOG("firstRectForRange");
|
||||
return CGRectNull;
|
||||
}
|
||||
- (CGRect)caretRectForPosition:(UITextPosition *)position;
|
||||
{
|
||||
CCLOG("caretRectForPosition");
|
||||
return CGRectMake(0, 0, 0, 0);
|
||||
}
|
||||
|
||||
#pragma mark Hit testing
|
||||
|
||||
/* JS - Find the closest position to a given point */
|
||||
- (UITextPosition *)closestPositionToPoint:(CGPoint)point;
|
||||
{
|
||||
CCLOG(@"closestPositionToPoint");
|
||||
return nil;
|
||||
}
|
||||
- (UITextPosition *)closestPositionToPoint:(CGPoint)point withinRange:(UITextRange *)range;
|
||||
{
|
||||
CCLOG("closestPositionToPoint");
|
||||
return nil;
|
||||
}
|
||||
- (UITextRange *)characterRangeAtPoint:(CGPoint)point;
|
||||
{
|
||||
CCLOG("characterRangeAtPoint");
|
||||
return nil;
|
||||
}
|
||||
|
||||
#pragma mark -
|
||||
#pragma mark UIKeyboard notification
|
||||
|
||||
- (void)onUIKeyboardNotification:(NSNotification *)notif;
|
||||
{
|
||||
NSString * type = notif.name;
|
||||
|
||||
NSDictionary* info = [notif userInfo];
|
||||
CGRect begin = [self convertRect:
|
||||
[[info objectForKey:UIKeyboardFrameBeginUserInfoKey] CGRectValue]
|
||||
fromView:self];
|
||||
CGRect end = [self convertRect:
|
||||
[[info objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue]
|
||||
fromView:self];
|
||||
double aniDuration = [[info objectForKey:UIKeyboardAnimationDurationUserInfoKey] doubleValue];
|
||||
|
||||
CGSize viewSize = self.frame.size;
|
||||
CGFloat tmp;
|
||||
|
||||
switch ([[UIApplication sharedApplication] statusBarOrientation])
|
||||
{
|
||||
case UIInterfaceOrientationPortrait:
|
||||
begin.origin.y = viewSize.height - begin.origin.y - begin.size.height;
|
||||
end.origin.y = viewSize.height - end.origin.y - end.size.height;
|
||||
break;
|
||||
|
||||
case UIInterfaceOrientationPortraitUpsideDown:
|
||||
begin.origin.x = viewSize.width - (begin.origin.x + begin.size.width);
|
||||
end.origin.x = viewSize.width - (end.origin.x + end.size.width);
|
||||
break;
|
||||
|
||||
case UIInterfaceOrientationLandscapeLeft:
|
||||
tmp = begin.size.width;
|
||||
begin.size.width = begin.size.height;
|
||||
begin.size.height = tmp;
|
||||
tmp = end.size.width;
|
||||
end.size.width = end.size.height;
|
||||
end.size.height = tmp;
|
||||
|
||||
tmp = begin.origin.x;
|
||||
begin.origin.x = begin.origin.y;
|
||||
begin.origin.y = viewSize.width - tmp - begin.size.height;
|
||||
tmp = end.origin.x;
|
||||
end.origin.x = end.origin.y;
|
||||
end.origin.y = viewSize.width - tmp - end.size.height;
|
||||
break;
|
||||
|
||||
case UIInterfaceOrientationLandscapeRight:
|
||||
tmp = begin.size.width;
|
||||
begin.size.width = begin.size.height;
|
||||
begin.size.height = tmp;
|
||||
tmp = end.size.width;
|
||||
end.size.width = end.size.height;
|
||||
end.size.height = tmp;
|
||||
|
||||
tmp = begin.origin.x;
|
||||
begin.origin.x = begin.origin.y;
|
||||
begin.origin.y = tmp;
|
||||
tmp = end.origin.x;
|
||||
end.origin.x = end.origin.y;
|
||||
end.origin.y = tmp;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
cocos2d::CCIMEKeyboardNotificationInfo notiInfo;
|
||||
notiInfo.begin = cocos2d::CCRect(begin.origin.x,
|
||||
begin.origin.y,
|
||||
begin.size.width,
|
||||
begin.size.height);
|
||||
notiInfo.end = cocos2d::CCRect(end.origin.x,
|
||||
end.origin.y,
|
||||
end.size.width,
|
||||
end.size.height);
|
||||
notiInfo.duration = (float)aniDuration;
|
||||
cocos2d::CCIMEDispatcher* dispatcher = cocos2d::CCIMEDispatcher::sharedDispatcher();
|
||||
if (UIKeyboardWillShowNotification == type)
|
||||
{
|
||||
dispatcher->dispatchKeyboardWillShow(notiInfo);
|
||||
}
|
||||
else if (UIKeyboardDidShowNotification == type)
|
||||
{
|
||||
dispatcher->dispatchKeyboardDidShow(notiInfo);
|
||||
}
|
||||
else if (UIKeyboardWillHideNotification == type)
|
||||
{
|
||||
dispatcher->dispatchKeyboardWillHide(notiInfo);
|
||||
}
|
||||
else if (UIKeyboardDidHideNotification == type)
|
||||
{
|
||||
dispatcher->dispatchKeyboardDidHide(notiInfo);
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
|
|
|
@ -32,6 +32,7 @@ THE SOFTWARE.
|
|||
#include "CCDirector.h"
|
||||
#include "CCTouch.h"
|
||||
#include "CCTouchDispatcher.h"
|
||||
#include "CCIMEDispatcher.h"
|
||||
|
||||
NS_CC_BEGIN;
|
||||
|
||||
|
@ -310,6 +311,42 @@ 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_RETURN == wParam)
|
||||
{
|
||||
CCIMEDispatcher::sharedDispatcher()->dispatchInsertText("\n", 1);
|
||||
}
|
||||
else if (VK_TAB == wParam)
|
||||
{
|
||||
// tab input
|
||||
}
|
||||
else if (VK_ESCAPE == wParam)
|
||||
{
|
||||
// ESC input
|
||||
}
|
||||
}
|
||||
else if (wParam < 128)
|
||||
{
|
||||
// ascii char
|
||||
CCIMEDispatcher::sharedDispatcher()->dispatchInsertText((const char *)&wParam, 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
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 +444,10 @@ void CCEGLView::setViewPortInPoints(float x, float y, float w, float h)
|
|||
}
|
||||
}
|
||||
|
||||
void CCEGLView::setIMEKeyboardState(bool /*bOpen*/)
|
||||
{
|
||||
}
|
||||
|
||||
HWND CCEGLView::getHWnd()
|
||||
{
|
||||
return m_hWnd;
|
||||
|
|
|
@ -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);
|
||||
|
|
|
@ -419,6 +419,14 @@
|
|||
RelativePath="..\include\CCGL.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\include\CCIMEDelegate.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\include\CCIMEDispatcher.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\include\CCKeypadDelegate.h"
|
||||
>
|
||||
|
@ -555,6 +563,10 @@
|
|||
RelativePath="..\include\CCString.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\include\CCTextFieldTTF.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\include\CCTexture2D.h"
|
||||
>
|
||||
|
@ -1048,6 +1060,18 @@
|
|||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="text_input_node"
|
||||
>
|
||||
<File
|
||||
RelativePath="..\text_input_node\CCIMEDispatcher.cpp"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\text_input_node\CCTextFieldTTF.cpp"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<File
|
||||
RelativePath="..\CCCamera.cpp"
|
||||
>
|
||||
|
|
|
@ -0,0 +1,320 @@
|
|||
/****************************************************************************
|
||||
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 <list>
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
bool CCIMEDelegate::detachWithIME()
|
||||
{
|
||||
return CCIMEDispatcher::sharedDispatcher()->detachDelegateWithIME(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 = 0;
|
||||
}
|
||||
|
||||
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;
|
||||
CCIMEDelegate* 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)
|
||||
{
|
||||
// if old delegate canDetachWithIME return false
|
||||
// or pDelegate canAttachWithIME return false,
|
||||
// do nothing.
|
||||
CC_BREAK_IF(! m_pImpl->m_DelegateWithIme->canDetachWithIME()
|
||||
|| ! pDelegate->canAttachWithIME());
|
||||
|
||||
// detach first
|
||||
CCIMEDelegate * pOldDelegate = m_pImpl->m_DelegateWithIme;
|
||||
m_pImpl->m_DelegateWithIme = 0;
|
||||
pOldDelegate->didDetachWithIME();
|
||||
}
|
||||
m_pImpl->m_DelegateWithIme = *iter;
|
||||
pDelegate->didAttachWithIME();
|
||||
bRet = true;
|
||||
} while (0);
|
||||
return bRet;
|
||||
}
|
||||
|
||||
bool CCIMEDispatcher::detachDelegateWithIME(CCIMEDelegate * pDelegate)
|
||||
{
|
||||
bool bRet = false;
|
||||
do
|
||||
{
|
||||
CC_BREAK_IF(! m_pImpl || ! pDelegate);
|
||||
|
||||
// if pDelegate is not the current delegate attached with ime, return
|
||||
CC_BREAK_IF(m_pImpl->m_DelegateWithIme != pDelegate);
|
||||
|
||||
CC_BREAK_IF(! pDelegate->canDetachWithIME());
|
||||
|
||||
m_pImpl->m_DelegateWithIme = 0;
|
||||
pDelegate->didDetachWithIME();
|
||||
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)
|
||||
|
||||
if (*iter == m_pImpl->m_DelegateWithIme)
|
||||
{
|
||||
m_pImpl->m_DelegateWithIme = 0;
|
||||
}
|
||||
m_pImpl->m_DelegateList.erase(iter);
|
||||
} while (0);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// dispatch text message
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
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_DelegateWithIme->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_DelegateWithIme->deleteBackward();
|
||||
} while (0);
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// dispatch keyboard message
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void CCIMEDispatcher::dispatchKeyboardWillShow(CCIMEKeyboardNotificationInfo& info)
|
||||
{
|
||||
if (m_pImpl)
|
||||
{
|
||||
CCIMEDelegate * pDelegate = 0;
|
||||
DelegateIter last = m_pImpl->m_DelegateList.end();
|
||||
for (DelegateIter first = m_pImpl->m_DelegateList.begin(); first != last; ++first)
|
||||
{
|
||||
pDelegate = *(first);
|
||||
if (pDelegate)
|
||||
{
|
||||
pDelegate->keyboardWillShow(info);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CCIMEDispatcher::dispatchKeyboardDidShow(CCIMEKeyboardNotificationInfo& info)
|
||||
{
|
||||
if (m_pImpl)
|
||||
{
|
||||
CCIMEDelegate * pDelegate = 0;
|
||||
DelegateIter last = m_pImpl->m_DelegateList.end();
|
||||
for (DelegateIter first = m_pImpl->m_DelegateList.begin(); first != last; ++first)
|
||||
{
|
||||
pDelegate = *(first);
|
||||
if (pDelegate)
|
||||
{
|
||||
pDelegate->keyboardDidShow(info);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CCIMEDispatcher::dispatchKeyboardWillHide(CCIMEKeyboardNotificationInfo& info)
|
||||
{
|
||||
if (m_pImpl)
|
||||
{
|
||||
CCIMEDelegate * pDelegate = 0;
|
||||
DelegateIter last = m_pImpl->m_DelegateList.end();
|
||||
for (DelegateIter first = m_pImpl->m_DelegateList.begin(); first != last; ++first)
|
||||
{
|
||||
pDelegate = *(first);
|
||||
if (pDelegate)
|
||||
{
|
||||
pDelegate->keyboardWillHide(info);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CCIMEDispatcher::dispatchKeyboardDidHide(CCIMEKeyboardNotificationInfo& info)
|
||||
{
|
||||
if (m_pImpl)
|
||||
{
|
||||
CCIMEDelegate * pDelegate = 0;
|
||||
DelegateIter last = m_pImpl->m_DelegateList.end();
|
||||
for (DelegateIter first = m_pImpl->m_DelegateList.begin(); first != last; ++first)
|
||||
{
|
||||
pDelegate = *(first);
|
||||
if (pDelegate)
|
||||
{
|
||||
pDelegate->keyboardDidHide(info);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// protected member function
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// static member function
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
CCIMEDispatcher* CCIMEDispatcher::sharedDispatcher()
|
||||
{
|
||||
static CCIMEDispatcher s_instance;
|
||||
return &s_instance;
|
||||
}
|
||||
|
||||
NS_CC_END;
|
|
@ -0,0 +1,277 @@
|
|||
/****************************************************************************
|
||||
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 <vector>
|
||||
|
||||
#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::detachWithIME()
|
||||
{
|
||||
bool bRet = CCIMEDelegate::detachWithIME();
|
||||
if (bRet)
|
||||
{
|
||||
// close keyboard
|
||||
CCEGLView * pGlView = CCDirector::sharedDirector()->getOpenGLView();
|
||||
if (pGlView)
|
||||
{
|
||||
pGlView->setIMEKeyboardState(false);
|
||||
}
|
||||
}
|
||||
return bRet;
|
||||
}
|
||||
|
||||
bool CCTextFieldTTF::canAttachWithIME()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CCTextFieldTTF::canDetachWithIME()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
void CCTextFieldTTF::insertText(const char * text, int len)
|
||||
{
|
||||
std::string sInsert(text, len);
|
||||
|
||||
// insert \n means input end
|
||||
int nPos = sInsert.find('\n');
|
||||
if (sInsert.npos != nPos)
|
||||
{
|
||||
len = nPos;
|
||||
sInsert.erase(nPos);
|
||||
}
|
||||
if (len <= 0)
|
||||
{
|
||||
// close keyboard
|
||||
CCEGLView * pGlView = CCDirector::sharedDirector()->getOpenGLView();
|
||||
if (pGlView)
|
||||
{
|
||||
pGlView->setIMEKeyboardState(false);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
m_bLock = true;
|
||||
std::string sText(*m_pInputText);
|
||||
sText.append(sInsert);
|
||||
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;
|
|
@ -253,7 +253,6 @@ bool CCTexture2D::initPremultipliedATextureWithImage(CCImage *image, unsigned in
|
|||
unsigned char* tempData =NULL;
|
||||
unsigned int* inPixel32 = NULL;
|
||||
unsigned short* outPixel16 = NULL;
|
||||
unsigned char* outPixel8 = NULL;
|
||||
bool hasAlpha;
|
||||
CCSize imageSize;
|
||||
CCTexture2DPixelFormat pixelFormat;
|
||||
|
|
|
@ -69,8 +69,8 @@ bool AppDelegate::applicationDidFinishLaunching()
|
|||
// enable High Resource Mode(2x, such as iphone4) and maintains low resource on other devices.
|
||||
// pDirector->enableRetinaDisplay(true);
|
||||
|
||||
// sets landscape mode
|
||||
pDirector->setDeviceOrientation(kCCDeviceOrientationLandscapeLeft);
|
||||
// sets opengl landscape mode
|
||||
// pDirector->setDeviceOrientation(kCCDeviceOrientationLandscapeLeft);
|
||||
|
||||
// turn on display FPS
|
||||
pDirector->setDisplayFPS(true);
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
android:debuggable="true">
|
||||
<activity android:name=".TestsDemo"
|
||||
android:label="@string/app_name"
|
||||
android:screenOrientation="portrait"
|
||||
android:screenOrientation="landscape"
|
||||
android:theme="@android:style/Theme.NoTitleBar.Fullscreen">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
|
|
|
@ -44,6 +44,7 @@ LOCAL_SRC_FILES := main.cpp \
|
|||
../../../tests/KeypadTest/KeypadTest.cpp \
|
||||
../../../tests/LabelTest/LabelTest.cpp \
|
||||
../../../tests/LayerTest/LayerTest.cpp \
|
||||
../../../tests/TextInputTest/TextInputTest.cpp \
|
||||
../../../tests/MenuTest/MenuTest.cpp \
|
||||
../../../tests/MotionStreakTest/MotionStreakTest.cpp \
|
||||
../../../tests/ParallaxTest/ParallaxTest.cpp \
|
||||
|
|
|
@ -2,17 +2,145 @@ package org.cocos2dx.lib;
|
|||
|
||||
import android.content.Context;
|
||||
import android.opengl.GLSurfaceView;
|
||||
import android.os.Bundle;
|
||||
import android.util.AttributeSet;
|
||||
import android.util.Log;
|
||||
import android.view.KeyEvent;
|
||||
import android.view.MotionEvent;
|
||||
import android.view.inputmethod.CompletionInfo;
|
||||
import android.view.inputmethod.EditorInfo;
|
||||
import android.view.inputmethod.ExtractedText;
|
||||
import android.view.inputmethod.ExtractedTextRequest;
|
||||
import android.view.inputmethod.InputConnection;
|
||||
import android.view.inputmethod.InputMethodManager;
|
||||
|
||||
class Cocos2dxInputConnection implements InputConnection {
|
||||
|
||||
@Override
|
||||
public boolean beginBatchEdit() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean clearMetaKeyStates(int states) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean commitCompletion(CompletionInfo text) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean commitText(CharSequence text, int newCursorPosition) {
|
||||
if (null != mView) {
|
||||
final String insertText = text.toString();
|
||||
mView.insertText(insertText);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean deleteSurroundingText(int leftLength, int rightLength) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean endBatchEdit() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean finishComposingText() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getCursorCapsMode(int reqModes) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ExtractedText getExtractedText(ExtractedTextRequest request,
|
||||
int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CharSequence getTextAfterCursor(int n, int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CharSequence getTextBeforeCursor(int n, int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performContextMenuAction(int id) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performEditorAction(int editorAction) {
|
||||
if (null != mView) {
|
||||
final String insertText = "\n";
|
||||
mView.insertText(insertText);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean performPrivateCommand(String action, Bundle data) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean reportFullscreenMode(boolean enabled) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean sendKeyEvent(KeyEvent event) {
|
||||
if (null != mView) {
|
||||
switch (event.getKeyCode()) {
|
||||
|
||||
case KeyEvent.KEYCODE_DEL:
|
||||
mView.deleteBackward();
|
||||
break;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean setComposingText(CharSequence text, int newCursorPosition) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean setSelection(int start, int end) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public void setGLSurfaceView(Cocos2dxGLSurfaceView view) {
|
||||
mView = view;
|
||||
}
|
||||
|
||||
private Cocos2dxGLSurfaceView mView;
|
||||
}
|
||||
|
||||
public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
||||
private static final String TAG = Cocos2dxGLSurfaceView.class
|
||||
.getCanonicalName();
|
||||
|
||||
static private Cocos2dxGLSurfaceView mainView;
|
||||
|
||||
private static final String TAG = Cocos2dxGLSurfaceView.class.getCanonicalName();
|
||||
private Cocos2dxRenderer mRenderer;
|
||||
private final boolean debug = false;
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for initialize
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
public Cocos2dxGLSurfaceView(Context context) {
|
||||
super(context);
|
||||
initView();
|
||||
|
@ -27,6 +155,7 @@ public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
|||
mRenderer = new Cocos2dxRenderer();
|
||||
setFocusableInTouchMode(true);
|
||||
setRenderer(mRenderer);
|
||||
mainView = this;
|
||||
}
|
||||
|
||||
public void onPause(){
|
||||
|
@ -51,6 +180,83 @@ public class Cocos2dxGLSurfaceView extends GLSurfaceView {
|
|||
});
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for text input
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public static void openIMEKeyboard() {
|
||||
if (null == mainView) {
|
||||
return;
|
||||
}
|
||||
InputMethodManager imm = (InputMethodManager)mainView.getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
|
||||
if (imm == null) {
|
||||
return;
|
||||
}
|
||||
imm.showSoftInput(mainView, InputMethodManager.SHOW_IMPLICIT);
|
||||
}
|
||||
|
||||
public static void closeIMEKeyboard() {
|
||||
if (null == mainView) {
|
||||
return;
|
||||
}
|
||||
InputMethodManager imm = (InputMethodManager)mainView.getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
|
||||
if (imm == null) {
|
||||
return;
|
||||
}
|
||||
imm.hideSoftInputFromWindow(mainView.getWindowToken(), 0);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onCheckIsTextEditor() {
|
||||
if (null == mainView)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private Cocos2dxInputConnection ic;
|
||||
@Override
|
||||
public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
|
||||
if (onCheckIsTextEditor()) {
|
||||
|
||||
outAttrs.inputType = EditorInfo.TYPE_CLASS_TEXT;
|
||||
outAttrs.imeOptions = EditorInfo.IME_NULL;
|
||||
outAttrs.initialSelStart = -1;
|
||||
outAttrs.initialSelEnd = -1;
|
||||
outAttrs.initialCapsMode = 0;
|
||||
|
||||
if (null == ic)
|
||||
{
|
||||
ic = new Cocos2dxInputConnection();
|
||||
ic.setGLSurfaceView(this);
|
||||
}
|
||||
return ic;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public void insertText(final String text) {
|
||||
queueEvent(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
mRenderer.handleInsertText(text);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
public void deleteBackward() {
|
||||
queueEvent(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
mRenderer.handleDeleteBackward();
|
||||
}
|
||||
});
|
||||
}
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// for touch event
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public boolean onTouchEvent(final MotionEvent event) {
|
||||
// these data are used in ACTION_MOVE and ACTION_CANCEL
|
||||
final int pointerNumber = event.getPointerCount();
|
||||
|
|
|
@ -75,7 +75,6 @@ public class Cocos2dxRenderer implements GLSurfaceView.Renderer {
|
|||
public static void setAnimationInterval(double interval){
|
||||
animationInterval = (long)(interval * NANOSECONDSPERSECOND);
|
||||
}
|
||||
|
||||
private static native void nativeTouchesBegin(int id, float x, float y);
|
||||
private static native void nativeTouchesEnd(int id, float x, float y);
|
||||
private static native void nativeTouchesMove(int[] id, float[] x, float[] y);
|
||||
|
@ -85,4 +84,19 @@ public class Cocos2dxRenderer implements GLSurfaceView.Renderer {
|
|||
private static native void nativeInit(int w, int h);
|
||||
private static native void nativeOnPause();
|
||||
private static native void nativeOnResume();
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
// handle input method edit message
|
||||
/////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public void handleInsertText(final String text) {
|
||||
nativeInsertText(text);
|
||||
}
|
||||
|
||||
public void handleDeleteBackward() {
|
||||
nativeDeleteBackward();
|
||||
}
|
||||
|
||||
private static native void nativeInsertText(String text);
|
||||
private static native void nativeDeleteBackward();
|
||||
}
|
||||
|
|
|
@ -1 +1 @@
|
|||
248fcaeecce01b0f5a391117dfb33f5332030bdf
|
||||
85a9422443707c5ba69d66e2047740c1a865b91c
|
|
@ -935,6 +935,18 @@
|
|||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="TextInputTest"
|
||||
>
|
||||
<File
|
||||
RelativePath="..\tests\TextInputTest\TextInputTest.cpp"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\tests\TextInputTest\TextInputTest.h"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
</Filter>
|
||||
</Filter>
|
||||
</Files>
|
||||
|
|
|
@ -0,0 +1,262 @@
|
|||
#include "TextInputTest.h"
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// local function
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
enum
|
||||
{
|
||||
kTextFieldTTFTest,
|
||||
kTextInputTestsCount,
|
||||
};
|
||||
|
||||
static int testIdx = -1;
|
||||
|
||||
CCLayer* createTextInputTest(int nIndex)
|
||||
{
|
||||
switch(nIndex)
|
||||
{
|
||||
case kTextFieldTTFTest: return new TextFieldTTFTest();
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CCLayer* restartTextInputTest()
|
||||
{
|
||||
CCLayer* pContainerLayer = new TextInputTest;
|
||||
pContainerLayer->autorelease();
|
||||
|
||||
CCLayer* pTestLayer = createTextInputTest(testIdx);
|
||||
pTestLayer->autorelease();
|
||||
|
||||
pContainerLayer->addChild(pTestLayer);
|
||||
|
||||
return pContainerLayer;
|
||||
}
|
||||
|
||||
CCLayer* nextTextInputTest()
|
||||
{
|
||||
testIdx++;
|
||||
testIdx = testIdx % kTextInputTestsCount;
|
||||
|
||||
return restartTextInputTest();
|
||||
}
|
||||
|
||||
CCLayer* backTextInputTest()
|
||||
{
|
||||
testIdx--;
|
||||
int total = kTextInputTestsCount;
|
||||
if( testIdx < 0 )
|
||||
testIdx += total;
|
||||
|
||||
return restartTextInputTest();
|
||||
}
|
||||
|
||||
CCRect getRect(CCNode * pNode)
|
||||
{
|
||||
CCRect rc;
|
||||
rc.origin = pNode->getPosition();
|
||||
rc.size = pNode->getContentSize();
|
||||
rc.origin.x -= rc.size.width / 2;
|
||||
rc.origin.y -= rc.size.height / 2;
|
||||
return rc;
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// implement TextInputTest
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TextInputTest::restartCallback(CCObject* pSender)
|
||||
{
|
||||
CCScene* s = new TextInputTestScene();
|
||||
s->addChild(restartTextInputTest());
|
||||
|
||||
CCDirector::sharedDirector()->replaceScene(s);
|
||||
s->release();
|
||||
}
|
||||
|
||||
void TextInputTest::nextCallback(CCObject* pSender)
|
||||
{
|
||||
CCScene* s = new TextInputTestScene();
|
||||
s->addChild( nextTextInputTest() );
|
||||
CCDirector::sharedDirector()->replaceScene(s);
|
||||
s->release();
|
||||
}
|
||||
|
||||
void TextInputTest::backCallback(CCObject* pSender)
|
||||
{
|
||||
CCScene* s = new TextInputTestScene();
|
||||
s->addChild( backTextInputTest() );
|
||||
CCDirector::sharedDirector()->replaceScene(s);
|
||||
s->release();
|
||||
}
|
||||
|
||||
void TextInputTest::onEnter()
|
||||
{
|
||||
CCLayer::onEnter();
|
||||
|
||||
CCSize s = CCDirector::sharedDirector()->getWinSize();
|
||||
|
||||
CCLabelTTF* label = CCLabelTTF::labelWithString(title().c_str(), "Arial", 32);
|
||||
addChild(label);
|
||||
label->setPosition(ccp(s.width/2, s.height-50));
|
||||
|
||||
std::string subTitle = subtitle();
|
||||
if(! subTitle.empty())
|
||||
{
|
||||
CCLabelTTF* l = CCLabelTTF::labelWithString(subTitle.c_str(), "Thonburi", 16);
|
||||
addChild(l, 1);
|
||||
l->setPosition(ccp(s.width/2, s.height-80));
|
||||
}
|
||||
|
||||
CCMenuItemImage *item1 = CCMenuItemImage::itemFromNormalImage("Images/b1.png", "Images/b2.png", this, menu_selector(TextInputTest::backCallback));
|
||||
CCMenuItemImage *item2 = CCMenuItemImage::itemFromNormalImage("Images/r1.png","Images/r2.png", this, menu_selector(TextInputTest::restartCallback) );
|
||||
CCMenuItemImage *item3 = CCMenuItemImage::itemFromNormalImage("Images/f1.png", "Images/f2.png", this, menu_selector(TextInputTest::nextCallback) );
|
||||
|
||||
CCMenu *menu = CCMenu::menuWithItems(item1, item2, item3, NULL);
|
||||
menu->setPosition(CCPointZero);
|
||||
item1->setPosition(ccp( s.width/2 - 100,30));
|
||||
item2->setPosition(ccp( s.width/2, 30));
|
||||
item3->setPosition(ccp( s.width/2 + 100,30));
|
||||
|
||||
addChild(menu, 1);
|
||||
}
|
||||
|
||||
std::string TextInputTest::title()
|
||||
{
|
||||
return "text input test";
|
||||
}
|
||||
|
||||
std::string TextInputTest::subtitle()
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// implement KeyboardNotificationLayer
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
KeyboardNotificationLayer::KeyboardNotificationLayer()
|
||||
: m_pTrackNode(0)
|
||||
{
|
||||
setIsTouchEnabled(true);
|
||||
}
|
||||
|
||||
void KeyboardNotificationLayer::registerWithTouchDispatcher()
|
||||
{
|
||||
CCTouchDispatcher::sharedDispatcher()->addTargetedDelegate(this, 0, false);
|
||||
}
|
||||
|
||||
void KeyboardNotificationLayer::keyboardWillShow(CCIMEKeyboardNotificationInfo& info)
|
||||
{
|
||||
if (! m_pTrackNode)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
CCRect rectTracked = getRect(m_pTrackNode);
|
||||
if (! CCRect::CCRectIntersectsRect(rectTracked, info.end))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
float adjustVert = CCRect::CCRectGetMaxY(info.end) - CCRect::CCRectGetMinY(rectTracked);
|
||||
|
||||
CCArray * children = getChildren();
|
||||
CCNode * node = 0;
|
||||
int count = children->count();
|
||||
CCPoint pos;
|
||||
for (int i = 0; i < count; ++i)
|
||||
{
|
||||
node = (CCNode*)children->objectAtIndex(i);
|
||||
pos = node->getPosition();
|
||||
pos.y += adjustVert;
|
||||
node->setPosition(pos);
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// implement TextFieldTTFTest
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
TextFieldTTFTest::TextFieldTTFTest()
|
||||
: m_nSelected(-1)
|
||||
{
|
||||
CCSize s = CCDirector::sharedDirector()->getWinSize();
|
||||
|
||||
m_pTextField[0] = CCTextFieldTTF::textFieldWithPlaceHolder("<click here>",
|
||||
CCSizeMake(240, 28),
|
||||
CCTextAlignmentCenter,
|
||||
"Thonburi",
|
||||
24);
|
||||
addChild(m_pTextField[0]);
|
||||
m_pTextField[0]->setPosition(ccp(s.width/2, s.height/2 + 16));
|
||||
|
||||
m_pTextField[1] = CCTextFieldTTF::textFieldWithPlaceHolder("<click here>",
|
||||
"Thonburi",
|
||||
24);
|
||||
addChild(m_pTextField[1]);
|
||||
m_pTextField[1]->setPosition(ccp(s.width/2, s.height/2 - 16));
|
||||
}
|
||||
|
||||
std::string TextFieldTTFTest::subtitle()
|
||||
{
|
||||
return "CCTextFieldTTF test";
|
||||
}
|
||||
|
||||
bool TextFieldTTFTest::ccTouchBegan(CCTouch *pTouch, CCEvent *pEvent)
|
||||
{
|
||||
m_beginPos = pTouch->locationInView(pTouch->view());
|
||||
m_beginPos = CCDirector::sharedDirector()->convertToGL(m_beginPos);
|
||||
return true;
|
||||
}
|
||||
|
||||
void TextFieldTTFTest::ccTouchEnded(CCTouch *pTouch, CCEvent *pEvent)
|
||||
{
|
||||
CCPoint endPos = pTouch->locationInView(pTouch->view());
|
||||
endPos = CCDirector::sharedDirector()->convertToGL(endPos);
|
||||
|
||||
float delta = 5.0f;
|
||||
if (::abs(endPos.x - m_beginPos.x) > delta
|
||||
|| ::abs(endPos.y - m_beginPos.y) > delta)
|
||||
{
|
||||
// not click
|
||||
m_beginPos.x = m_beginPos.y = -1;
|
||||
return;
|
||||
}
|
||||
|
||||
int index = 0;
|
||||
for (; index < sizeof(m_pTextField) / sizeof(CCTextFieldTTF *); ++index)
|
||||
{
|
||||
if (CCRect::CCRectContainsPoint(getRect(m_pTextField[index]), convertTouchToNodeSpaceAR(pTouch)))
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (index < sizeof(m_pTextField) / sizeof(CCTextFieldTTF *))
|
||||
{
|
||||
m_nSelected = index;
|
||||
m_pTrackNode = m_pTextField[index];
|
||||
m_pTextField[index]->attachWithIME();
|
||||
}
|
||||
else if (m_nSelected >= 0)
|
||||
{
|
||||
m_pTextField[m_nSelected]->detachWithIME();
|
||||
m_nSelected = -1;
|
||||
m_pTrackNode = 0;
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// implement TextInputTestScene
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TextInputTestScene::runThisTest()
|
||||
{
|
||||
CCLayer* pLayer = nextTextInputTest();
|
||||
addChild(pLayer);
|
||||
|
||||
CCDirector::sharedDirector()->replaceScene(this);
|
||||
}
|
|
@ -0,0 +1,51 @@
|
|||
#ifndef __TEXT_INPUT_TEST_H__
|
||||
#define __TEXT_INPUT_TEST_H__
|
||||
|
||||
#include "../testBasic.h"
|
||||
|
||||
class TextInputTest : public CCLayer, public CCIMEDelegate
|
||||
{
|
||||
public:
|
||||
void restartCallback(CCObject* pSender);
|
||||
void nextCallback(CCObject* pSender);
|
||||
void backCallback(CCObject* pSender);
|
||||
|
||||
virtual std::string title();
|
||||
virtual std::string subtitle();
|
||||
|
||||
virtual void onEnter();
|
||||
};
|
||||
|
||||
class KeyboardNotificationLayer : public CCLayer, public CCIMEDelegate
|
||||
{
|
||||
public:
|
||||
KeyboardNotificationLayer();
|
||||
|
||||
virtual void registerWithTouchDispatcher();
|
||||
virtual void keyboardWillShow(CCIMEKeyboardNotificationInfo& info);
|
||||
|
||||
protected:
|
||||
CCNode * m_pTrackNode;
|
||||
};
|
||||
|
||||
class TextFieldTTFTest : public KeyboardNotificationLayer
|
||||
{
|
||||
CCPoint m_beginPos;
|
||||
CCTextFieldTTF * m_pTextField[2];
|
||||
int m_nSelected;
|
||||
public:
|
||||
TextFieldTTFTest();
|
||||
|
||||
virtual std::string subtitle();
|
||||
|
||||
virtual bool ccTouchBegan(CCTouch *pTouch, CCEvent *pEvent);
|
||||
virtual void ccTouchEnded(CCTouch *pTouch, CCEvent *pEvent);
|
||||
};
|
||||
|
||||
class TextInputTestScene : public TestScene
|
||||
{
|
||||
public:
|
||||
virtual void runThisTest();
|
||||
};
|
||||
|
||||
#endif // __TEXT_INPUT_TEST_H__
|
|
@ -34,7 +34,7 @@ static TestScene* CreateTestScene(int nIdx)
|
|||
case TEST_COCOSNODE:
|
||||
pScene = new CocosNodeTestScene(); break;
|
||||
case TEST_TOUCHES:
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationPortrait);
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationLandscapeLeft);
|
||||
pScene = new PongScene(); break;
|
||||
case TEST_MENU:
|
||||
pScene = new MenuTestScene(); break;
|
||||
|
@ -52,18 +52,20 @@ static TestScene* CreateTestScene(int nIdx)
|
|||
pScene = new IntervalTestScene(); break;
|
||||
case TEST_CHIPMUNK:
|
||||
#if (CC_TARGET_PLATFORM != CC_PLATFORM_AIRPLAY)
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationPortrait);
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationLandscapeLeft);
|
||||
pScene = new ChipmunkTestScene(); break;
|
||||
#else
|
||||
#ifdef AIRPLAYUSECHIPMUNK
|
||||
#if (AIRPLAYUSECHIPMUNK == 1)
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationPortrait);
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationLandscapeLeft);
|
||||
pScene = new ChipmunkTestScene(); break;
|
||||
#endif
|
||||
#endif
|
||||
#endif
|
||||
case TEST_ATLAS:
|
||||
case TEST_LABEL:
|
||||
pScene = new AtlasTestScene(); break;
|
||||
case TEST_TEXT_INPUT:
|
||||
pScene = new TextInputTestScene(); break;
|
||||
case TEST_SPRITE:
|
||||
pScene = new SpriteTestScene(); break;
|
||||
case TEST_SCHEDULER:
|
||||
|
@ -102,7 +104,7 @@ static TestScene* CreateTestScene(int nIdx)
|
|||
TestController::TestController()
|
||||
: m_tBeginPos(CCPointZero)
|
||||
{
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationLandscapeLeft);
|
||||
CCDirector::sharedDirector()->setDeviceOrientation(CCDeviceOrientationPortrait);
|
||||
|
||||
// add close menu
|
||||
CCMenuItemImage *pCloseItem = CCMenuItemImage::itemFromNormalImage(s_pPathClose, s_pPathClose, this, menu_selector(TestController::closeCallback) );
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "TileMapTest/TileMapTest.h"
|
||||
#include "IntervalTest/IntervalTest.h"
|
||||
#include "LabelTest/LabelTest.h"
|
||||
#include "TextInputTest/TextInputTest.h"
|
||||
#include "SpriteTest/SpriteTest.h"
|
||||
#include "SchedulerTest/SchedulerTest.h"
|
||||
#include "RenderTextureTest/RenderTextureTest.h"
|
||||
|
@ -67,7 +68,8 @@ enum
|
|||
TEST_TILE_MAP,
|
||||
TEST_INTERVAL,
|
||||
TEST_CHIPMUNK,
|
||||
TEST_ATLAS,
|
||||
TEST_LABEL,
|
||||
TEST_TEXT_INPUT,
|
||||
TEST_SPRITE,
|
||||
TEST_SCHEDULER,
|
||||
TEST_RENDERTEXTURE,
|
||||
|
@ -107,6 +109,7 @@ const std::string g_aTestNames[TESTS_COUNT] = {
|
|||
"IntervalTest",
|
||||
"ChipmunkTest",
|
||||
"LabelTest",
|
||||
"TextInputTest",
|
||||
"SpriteTest",
|
||||
"SchdulerTest",
|
||||
"RenderTextureTest",
|
||||
|
|
Loading…
Reference in New Issue