textEncoder_ext.cxx 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117
  1. /**
  2. * PANDA 3D SOFTWARE
  3. * Copyright (c) Carnegie Mellon University. All rights reserved.
  4. *
  5. * All use of this software is subject to the terms of the revised BSD
  6. * license. You should have received a copy of this license along
  7. * with this source code in a file named "LICENSE."
  8. *
  9. * @file textEncoder_ext.cxx
  10. * @author rdb
  11. * @date 2018-09-29
  12. */
  13. #include "textEncoder_ext.h"
  14. #ifdef HAVE_PYTHON
  15. /**
  16. * Sets the text as a Unicode string. In Python 2, if a regular str is given,
  17. * it is assumed to be in the TextEncoder's specified encoding.
  18. */
  19. void Extension<TextEncoder>::
  20. set_text(PyObject *text) {
  21. if (PyUnicode_Check(text)) {
  22. Py_ssize_t len;
  23. const char *str = PyUnicode_AsUTF8AndSize(text, &len);
  24. _this->set_text(std::string(str, len), TextEncoder::E_utf8);
  25. } else {
  26. Dtool_Raise_TypeError("expected string");
  27. }
  28. }
  29. /**
  30. * Sets the text as an encoded byte string of the given encoding.
  31. */
  32. void Extension<TextEncoder>::
  33. set_text(PyObject *text, TextEncoder::Encoding encoding) {
  34. char *str;
  35. Py_ssize_t len;
  36. if (PyBytes_AsStringAndSize(text, &str, &len) >= 0) {
  37. _this->set_text(std::string(str, len), encoding);
  38. }
  39. }
  40. /**
  41. * Returns the text as a string. In Python 2, the returned string is in the
  42. * TextEncoder's specified encoding. In Python 3, it is returned as unicode.
  43. */
  44. PyObject *Extension<TextEncoder>::
  45. get_text() const {
  46. std::wstring text = _this->get_wtext();
  47. return PyUnicode_FromWideChar(text.data(), (Py_ssize_t)text.size());
  48. }
  49. /**
  50. * Returns the text as a bytes object in the given encoding.
  51. */
  52. PyObject *Extension<TextEncoder>::
  53. get_text(TextEncoder::Encoding encoding) const {
  54. std::string text = _this->get_text(encoding);
  55. return PyBytes_FromStringAndSize((char *)text.data(), (Py_ssize_t)text.size());
  56. }
  57. /**
  58. * Appends the text as a string (or Unicode object in Python 2).
  59. */
  60. void Extension<TextEncoder>::
  61. append_text(PyObject *text) {
  62. if (PyUnicode_Check(text)) {
  63. Py_ssize_t len;
  64. const char *str = PyUnicode_AsUTF8AndSize(text, &len);
  65. std::string text_str(str, len);
  66. if (_this->get_encoding() == TextEncoder::E_utf8) {
  67. _this->append_text(text_str);
  68. } else {
  69. _this->append_wtext(TextEncoder::decode_text(text_str, TextEncoder::E_utf8));
  70. }
  71. } else {
  72. Dtool_Raise_TypeError("expected string");
  73. }
  74. }
  75. /**
  76. * Encodes the given wide character as byte string in the given encoding.
  77. */
  78. PyObject *Extension<TextEncoder>::
  79. encode_wchar(char32_t ch, TextEncoder::Encoding encoding) {
  80. std::string value = TextEncoder::encode_wchar(ch, encoding);
  81. return PyBytes_FromStringAndSize((char *)value.data(), (Py_ssize_t)value.size());
  82. }
  83. /**
  84. * Encodes a wide-text string into a single-char string, according to the
  85. * given encoding.
  86. */
  87. PyObject *Extension<TextEncoder>::
  88. encode_wtext(const wstring &wtext, TextEncoder::Encoding encoding) {
  89. std::string value = TextEncoder::encode_wtext(wtext, encoding);
  90. return PyBytes_FromStringAndSize((char *)value.data(), (Py_ssize_t)value.size());
  91. }
  92. /**
  93. * Returns the given wstring decoded to a single-byte string, via the given
  94. * encoding system.
  95. */
  96. PyObject *Extension<TextEncoder>::
  97. decode_text(PyObject *text, TextEncoder::Encoding encoding) {
  98. char *str;
  99. Py_ssize_t len;
  100. if (PyBytes_AsStringAndSize(text, &str, &len) >= 0) {
  101. return Dtool_WrapValue(TextEncoder::decode_text(std::string(str, len), encoding));
  102. } else {
  103. return nullptr;
  104. }
  105. }
  106. #endif // HAVE_PYTHON