1 /* libs/graphics/animator/SkDisplayEvent.cpp 2 ** 3 ** Copyright 2006, The Android Open Source Project 4 ** 5 ** Licensed under the Apache License, Version 2.0 (the "License"); 6 ** you may not use this file except in compliance with the License. 7 ** You may obtain a copy of the License at 8 ** 9 ** http://www.apache.org/licenses/LICENSE-2.0 10 ** 11 ** Unless required by applicable law or agreed to in writing, software 12 ** distributed under the License is distributed on an "AS IS" BASIS, 13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 ** See the License for the specific language governing permissions and 15 ** limitations under the License. 16 */ 17 18 #include "SkDisplayEvent.h" 19 #include "SkAnimateMaker.h" 20 #include "SkDisplayApply.h" 21 #include "SkDisplayInput.h" 22 #include "SkDisplayList.h" 23 #ifdef SK_DEBUG 24 #include "SkDump.h" 25 #endif 26 #include "SkEvent.h" 27 #include "SkDisplayInput.h" 28 #include "SkKey.h" 29 #include "SkMetaData.h" 30 #include "SkScript.h" 31 #include "SkUtils.h" 32 33 enum SkDisplayEvent_Properties { 34 SK_PROPERTY(key), 35 SK_PROPERTY(keys) 36 }; 37 38 #if SK_USE_CONDENSED_INFO == 0 39 40 const SkMemberInfo SkDisplayEvent::fInfo[] = { 41 SK_MEMBER(code, EventCode), 42 SK_MEMBER(disable, Boolean), 43 SK_MEMBER_PROPERTY(key, String), // a single key (also last key pressed) 44 SK_MEMBER_PROPERTY(keys, String), // a single key or dash-delimited range of keys 45 SK_MEMBER(kind, EventKind), 46 SK_MEMBER(target, String), 47 SK_MEMBER(x, Float), 48 SK_MEMBER(y, Float) 49 }; 50 51 #endif 52 53 DEFINE_GET_MEMBER(SkDisplayEvent); 54 55 SkDisplayEvent::SkDisplayEvent() : code((SkKey) -1), disable(false), 56 kind(kUser), x(0), y(0), fLastCode((SkKey) -1), fMax((SkKey) -1), fTarget(NULL) { 57 } 58 59 SkDisplayEvent::~SkDisplayEvent() { 60 deleteMembers(); 61 } 62 63 bool SkDisplayEvent::add(SkAnimateMaker& , SkDisplayable* child) { 64 *fChildren.append() = child; 65 return true; 66 } 67 68 bool SkDisplayEvent::contains(SkDisplayable* match) { 69 for (int index = 0; index < fChildren.count(); index++) { 70 if (fChildren[index] == match || fChildren[index]->contains(match)) 71 return true; 72 } 73 return false; 74 } 75 76 SkDisplayable* SkDisplayEvent::contains(const SkString& match) { 77 for (int index = 0; index < fChildren.count(); index++) { 78 SkDisplayable* child = fChildren[index]; 79 if (child->contains(match)) 80 return child; 81 } 82 return NULL; 83 } 84 85 void SkDisplayEvent::deleteMembers() { 86 for (int index = 0; index < fChildren.count(); index++) { 87 SkDisplayable* evt = fChildren[index]; 88 delete evt; 89 } 90 } 91 92 #ifdef SK_DUMP_ENABLED 93 void SkDisplayEvent::dumpEvent(SkAnimateMaker* maker) { 94 dumpBase(maker); 95 SkString str; 96 SkDump::GetEnumString(SkType_EventKind, kind, &str); 97 SkDebugf("kind=\"%s\" ", str.c_str()); 98 if (kind == SkDisplayEvent::kKeyPress || kind == SkDisplayEvent::kKeyPressUp) { 99 if (code >= 0) 100 SkDump::GetEnumString(SkType_EventCode, code, &str); 101 else 102 str.set("none"); 103 SkDebugf("code=\"%s\" ", str.c_str()); 104 } 105 if (kind == SkDisplayEvent::kKeyChar) { 106 if (fMax != (SkKey) -1 && fMax != code) 107 SkDebugf("keys=\"%c - %c\" ", code, fMax); 108 else 109 SkDebugf("key=\"%c\" ", code); 110 } 111 if (fTarget != NULL) { 112 SkDebugf("target=\"%s\" ", fTarget->id); 113 } 114 if (kind >= SkDisplayEvent::kMouseDown && kind <= SkDisplayEvent::kMouseUp) { 115 #ifdef SK_CAN_USE_FLOAT 116 SkDebugf("x=\"%g\" y=\"%g\" ", SkScalarToFloat(x), SkScalarToFloat(y)); 117 #else 118 SkDebugf("x=\"%x\" y=\"%x\" ", x, y); 119 #endif 120 } 121 if (disable) 122 SkDebugf("disable=\"true\" "); 123 SkDebugf("/>\n"); 124 } 125 #endif 126 127 bool SkDisplayEvent::enableEvent(SkAnimateMaker& maker) 128 { 129 maker.fActiveEvent = this; 130 if (fChildren.count() == 0) 131 return false; 132 if (disable) 133 return false; 134 #ifdef SK_DUMP_ENABLED 135 if (maker.fDumpEvents) { 136 SkDebugf("enable: "); 137 dumpEvent(&maker); 138 } 139 #endif 140 SkDisplayList& displayList = maker.fDisplayList; 141 for (int index = 0; index < fChildren.count(); index++) { 142 SkDisplayable* displayable = fChildren[index]; 143 if (displayable->isGroup()) { 144 SkTDDrawableArray* parentList = displayList.getDrawList(); 145 *parentList->append() = (SkDrawable*) displayable; // make it findable before children are enabled 146 } 147 if (displayable->enable(maker)) 148 continue; 149 if (maker.hasError()) 150 return true; 151 if (displayable->isDrawable() == false) 152 return true; // error 153 SkDrawable* drawable = (SkDrawable*) displayable; 154 SkTDDrawableArray* parentList = displayList.getDrawList(); 155 *parentList->append() = drawable; 156 } 157 return false; 158 } 159 160 bool SkDisplayEvent::getProperty(int index, SkScriptValue* value) const { 161 switch (index) { 162 case SK_PROPERTY(key): 163 case SK_PROPERTY(keys): { 164 value->fType = SkType_String; 165 char scratch[8]; 166 SkKey convert = index == SK_PROPERTY(keys) ? code : fLastCode; 167 size_t size = convert > 0 ? SkUTF8_FromUnichar(convert, scratch) : 0; 168 fKeyString.set(scratch, size); 169 value->fOperand.fString = &fKeyString; 170 if (index != SK_PROPERTY(keys) || fMax == (SkKey) -1 || fMax == code) 171 break; 172 value->fOperand.fString->append("-"); 173 size = SkUTF8_FromUnichar(fMax, scratch); 174 value->fOperand.fString->append(scratch, size); 175 } break; 176 default: 177 SkASSERT(0); 178 return false; 179 } 180 return true; 181 } 182 183 void SkDisplayEvent::onEndElement(SkAnimateMaker& maker) 184 { 185 if (kind == kUser) 186 return; 187 maker.fEvents.addEvent(this); 188 if (kind == kOnEnd) { 189 bool found = maker.find(target.c_str(), &fTarget); 190 SkASSERT(found); 191 SkASSERT(fTarget && fTarget->isAnimate()); 192 SkAnimateBase* animate = (SkAnimateBase*) fTarget; 193 animate->setHasEndEvent(); 194 } 195 } 196 197 void SkDisplayEvent::populateInput(SkAnimateMaker& maker, const SkEvent& fEvent) { 198 const SkMetaData& meta = fEvent.getMetaData(); 199 SkMetaData::Iter iter(meta); 200 SkMetaData::Type type; 201 int number; 202 const char* name; 203 while ((name = iter.next(&type, &number)) != NULL) { 204 if (name[0] == '\0') 205 continue; 206 SkDisplayable* displayable; 207 SkInput* input; 208 for (int index = 0; index < fChildren.count(); index++) { 209 displayable = fChildren[index]; 210 if (displayable->getType() != SkType_Input) 211 continue; 212 input = (SkInput*) displayable; 213 if (input->name.equals(name)) 214 goto found; 215 } 216 if (!maker.find(name, &displayable) || displayable->getType() != SkType_Input) 217 continue; 218 input = (SkInput*) displayable; 219 found: 220 switch (type) { 221 case SkMetaData::kS32_Type: 222 meta.findS32(name, &input->fInt); 223 break; 224 case SkMetaData::kScalar_Type: 225 meta.findScalar(name, &input->fFloat); 226 break; 227 case SkMetaData::kPtr_Type: 228 SkASSERT(0); 229 break; // !!! not handled for now 230 case SkMetaData::kString_Type: 231 input->string.set(meta.findString(name)); 232 break; 233 default: 234 SkASSERT(0); 235 } 236 } 237 // re-evaluate all animators that may have built their values from input strings 238 for (SkDisplayable** childPtr = fChildren.begin(); childPtr < fChildren.end(); childPtr++) { 239 SkDisplayable* displayable = *childPtr; 240 if (displayable->isApply() == false) 241 continue; 242 SkApply* apply = (SkApply*) displayable; 243 apply->refresh(maker); 244 } 245 } 246 247 bool SkDisplayEvent::setProperty(int index, SkScriptValue& value) { 248 SkASSERT(index == SK_PROPERTY(key) || index == SK_PROPERTY(keys)); 249 SkASSERT(value.fType == SkType_String); 250 SkString* string = value.fOperand.fString; 251 const char* chars = string->c_str(); 252 int count = SkUTF8_CountUnichars(chars); 253 SkASSERT(count >= 1); 254 code = (SkKey) SkUTF8_NextUnichar(&chars); 255 fMax = code; 256 SkASSERT(count == 1 || index == SK_PROPERTY(keys)); 257 if (--count > 0) { 258 SkASSERT(*chars == '-'); 259 chars++; 260 fMax = (SkKey) SkUTF8_NextUnichar(&chars); 261 SkASSERT(fMax >= code); 262 } 263 return true; 264 } 265 266 #ifdef ANDROID 267 268 #include "SkMetaData.h" 269 #include "SkParse.h" 270 #include "SkTextBox.h" 271 #include "SkXMLWriter.h" 272 273 void SkMetaData::setPtr(char const*, void* ) {} 274 void SkMetaData::setS32(char const*, int ) {} 275 bool SkEventSink::doEvent(SkEvent const& ) { return false; } 276 bool SkXMLParser::parse(SkStream& ) { return false; } 277 SkXMLParserError::SkXMLParserError( ) {} 278 void SkEvent::setType(char const*, unsigned long ) {} 279 bool SkEvent::PostTime(SkEvent*, unsigned int, unsigned int ) { return false; } 280 SkEvent::SkEvent(char const* ) {} 281 SkEvent::SkEvent(SkEvent const& ) {} 282 SkEvent::SkEvent( ) {} 283 SkEvent::~SkEvent( ) {} 284 bool SkEventSink::onQuery(SkEvent* ) { return false; } 285 SkEventSink::SkEventSink( ) {} 286 SkEventSink::~SkEventSink( ) {} 287 bool SkXMLParser::parse(char const*, unsigned long ) { return false; } 288 bool SkXMLParser::parse(SkDOM const&, SkDOMNode const* ) { return false; } 289 bool SkEvent::Post(SkEvent*, unsigned int, unsigned int ) { return false; } 290 void SkParse::UnitTest( ) {} 291 const char* SkMetaData::findString(char const*) const {return 0;} 292 bool SkMetaData::findPtr(char const*, void**) const {return false;} 293 bool SkMetaData::findS32(char const*, int*) const {return false;} 294 bool SkEvent::isType(char const*, unsigned long) const { return false; } 295 void SkMetaData::setString(char const*, char const* ) {} 296 const char* SkParse::FindNamedColor(char const*, unsigned long, unsigned int* ) {return false; } 297 const char* SkMetaData::Iter::next(SkMetaData::Type*, int* ) { return false; } 298 SkMetaData::Iter::Iter(SkMetaData const& ) {} 299 bool SkMetaData::findScalar(char const*, int*) const {return false;} 300 void SkMetaData::reset( ) {} 301 void SkEvent::setType(SkString const& ) {} 302 bool SkMetaData::findBool(char const*, bool*) const {return false;} 303 void SkEvent::getType(SkString*) const {} 304 bool SkXMLParser::endElement(char const* ) { return false; } 305 bool SkXMLParser::addAttribute(char const*, char const* ) { return false;} 306 bool SkXMLParser::startElement(char const* ) { return false;} 307 bool SkXMLParser::text(char const*, int ) { return false;} 308 bool SkXMLParser::onText(char const*, int ) { return false;} 309 SkXMLParser::SkXMLParser(SkXMLParserError* ) {} 310 SkXMLParser::~SkXMLParser( ) {} 311 SkXMLParserError::~SkXMLParserError( ) {} 312 void SkXMLParserError::getErrorString(SkString*) const {} 313 void SkTextBox::setSpacing(int, int ) {} 314 void SkTextBox::setSpacingAlign(SkTextBox::SpacingAlign ) {} 315 void SkTextBox::draw(SkCanvas*, char const*, unsigned long, SkPaint const& ) {} 316 void SkTextBox::setBox(SkRect const& ) {} 317 void SkTextBox::setMode(SkTextBox::Mode ) {} 318 SkTextBox::SkTextBox( ) {} 319 void SkMetaData::setScalar(char const*, int ) {} 320 const char* SkParse::FindScalar(char const*, int* ) {return 0; } 321 const char* SkParse::FindScalars(char const*, int*, int ) {return 0; } 322 const char* SkParse::FindHex(char const*, unsigned int* ) {return 0; } 323 const char* SkParse::FindS32(char const*, int* ) {return 0; } 324 void SkXMLWriter::addAttribute(char const*, char const* ) {} 325 void SkXMLWriter::startElement(char const* ) {} 326 void SkXMLWriter::doEnd(SkXMLWriter::Elem* ) {} 327 SkXMLWriter::Elem* SkXMLWriter::getEnd( ) { return 0; } 328 bool SkXMLWriter::doStart(char const*, unsigned long ) { return false; } 329 SkXMLWriter::SkXMLWriter(bool ) {} 330 SkXMLWriter::~SkXMLWriter( ) {} 331 SkMetaData::SkMetaData() {} 332 SkMetaData::~SkMetaData() {} 333 bool SkEventSink::onEvent(SkEvent const&) {return false;} 334 bool SkXMLParser::onEndElement(char const*) {return false;} 335 bool SkXMLParser::onAddAttribute(char const*, char const*) {return false;} 336 bool SkXMLParser::onStartElement(char const*) {return false;} 337 void SkXMLWriter::writeHeader() {} 338 339 #endif 340