Я просто тестирую машинописный текст в VisualStudio 2012, и у меня проблема с его системой типов. На моем html-сайте есть тег холста с идентификатором «mycanvas». Я пытаюсь нарисовать прямоугольник на этом холсте. Вот код
var canvas = document.getElementById("mycanvas");
var ctx: CanvasRenderingContext2D = canvas.getContext("2d");
ctx.fillStyle = "#00FF00";
ctx.fillRect(0, 0, 100, 100);
К сожалению, VisualStudio жалуется, что
свойство getContext не существует для значения типа HTMLElement
Вторая строка помечается как ошибка. Я думал, это будет просто предупреждение, но код не компилируется. VisualStudio говорит, что
были ошибки сборки. Хотите продолжить и запустить последнюю успешную сборку?
Мне эта ошибка совсем не понравилась. Почему нет вызова динамических методов? В конце концов, метод getContext определенно существует в моем элементе холста. Однако я думал, что эту проблему будет легко решить. Я только что добавил аннотацию типа для холста:
var canvas : HTMLCanvasElement = document.getElementById("mycanvas");
var ctx: CanvasRenderingContext2D = canvas.getContext("2d");
ctx.fillStyle = "#00FF00";
ctx.fillRect(0, 0, 100, 100);
Но система типов все еще не устраивала. Вот новое сообщение об ошибке, на этот раз в первой строке:
Невозможно преобразовать HTMLElement в HTMLCanvasElement: для типа HTMLElement отсутствует свойство toDataURL из типа HTMLCanvasElement
Что ж, я очень люблю статическую типизацию, но это делает язык непригодным для использования. Что система типов хочет от меня?
ОБНОВИТЬ:
В Typescript действительно нет поддержки динамического вызова, и мою проблему можно решить с помощью преобразования типов. Мой вопрос в основном дублирует этот TypeScript: кастинг HTMLElement
CanvasRenderingContext2D
вместоany
type."2d"
и.getContext("2d")
вернет его с типомCanvasRenderingContext2D
. Вам не нужно приводить его явно.источник
В то время как другие ответы продвигают утверждения типа (вот что они есть - TypeScript не имеет приведений типов, которые фактически изменяют тип; они просто способ подавления ошибок проверки типов), интеллектуально честный способ подойти к вашей проблеме - это прислушаться к Сообщения об ошибках.
В вашем случае есть 3 вещи, которые могут пойти не так:
document.getElementById("mycanvas")
может вернутьсяnull
, потому что ни один узел с этим идентификатором не найден (он мог быть переименован, еще не введен в документ, кто-то мог попытаться запустить вашу функцию в среде без доступа к DOM)document.getElementById("mycanvas")
может вернуть ссылку на элемент DOM, но этот элемент DOM не являетсяHTMLCanvasElement
document.getElementById("mycanvas")
действительно вернул действительныйHTMLElement
, это действительноHTMLCanvasElement
, ноCanvasRenderingContext2D
не поддерживается браузером.Вместо того, чтобы приказать компилятору заткнуться (и, возможно, оказаться в ситуации, когда выдается бесполезное сообщение об ошибке, например
Cannot read property 'getContext' of null
), я рекомендую взять под контроль границы вашего приложения.Убедитесь, что элемент содержит HTMLCanvasElement
Убедитесь, что контекст рендеринга поддерживается браузером.
Использование:
Смотрите TypeScript Playground .
источник
Похоже, это исправлено в версии TypeScript .9: http://blogs.msdn.com/b/typescript/archive/2013/03/25/working-on-typescript-0-9-generics-overload- on-constants-and-compiler-performance.aspx См. раздел «Перегрузка констант», где явно показан тег холста.
источник
У меня была такая же проблема, но с SVGSVGElement вместо HTMLCanvasElement. Приведение к SVGSVGElement дало ошибку времени компиляции:
Невозможно преобразовать «HTMLElement» в «SVGSVGElement»: для
типа «HTMLElement» отсутствует свойство «width» из типа «SVGSVGElement».
В типе «SVGSVGElement» отсутствует свойство «onmouseleave» из типа «HTMLElement».
Если исправить это путем первого преобразования в 'любой':
или так (имеет тот же эффект)
Теперь mySvg строго типизирован как SVGSVGElement.
источник
Это старая тема ... возможно, мертвая для 2012 года, но захватывающая и новая для VS Code и машинописного текста.
Мне пришлось сделать следующее, чтобы заставить это работать в VS Code со следующими ссылками на пакеты.
Версия машинописного текста:
источник
Вы , возможно , придется добавить
DOM
кcompilerOptions.lib
в вашейtsconfig.json
.источник