Я пытаюсь использовать API датчика с реакцией, и я не вижу, чтобы он работал.
Это дает мне сообщение об ошибке, говорящее, что AmbientLightSensor (in my case this sensor) не определен
Если я запускаю скрипт снаружи, реагируйте ( more exactly with an extension from VSCode "live server" ), он работает нормально ( just a html with some JS code in it ).
Это круто и все такое, но в этом случае, по крайней мере, я хочу запустить этот скрипт внутри реакции, и он просто не позволяет мне.
So far I've tried:
Вот мой код, код js, который я пытаюсь запустить, находится внутри компонента Did mount
class App extends Component {
constructor(props) {
super(props);
}
componentDidMount() {
const details = document.getElementById("details");
// Feature detection
if (window.AmbientLightSensor) {
try {
const sensor = new AmbientLightSensor();
// Detect changes in the light
sensor.onreading = () => {
details.innerHTML = sensor.illuminance;
// Read the light levels in lux
// < 50 is dark room
if (sensor.illuminance < 50) {
document.body.className = "darkLight";
} else {
document.body.className = "brightLight";
}
};
// Has an error occured?
sensor.onerror = event =>
(document.getElementById("details").innerHTML =
event.error.message);
sensor.start();
} catch (err) {
details.innerHTML = err.message;
}
} else {
details.innerHTML =
"It looks like your browser doesnt support this feature";
}
}
render() {
return (
<div className = "app">
<h1>Ambient Light Sensor</h1>
<p>Current Light Levels</p>
<div id = "details"></div>
</div>
);
}
}
А также вот рабочий html
<head>
<meta charset = "UTF-8" />
<title>Ambient Light Sensor</title>
</head>
<body class = "brightLight">
<h1>Ambient Light Sensor</h1>
<p>Current Light Levels</p>
<div id = "details"></div>
</body>
<script>
const details = document.getElementById("details");
// Feature detection
if (window.AmbientLightSensor) {
try {
const sensor = new AmbientLightSensor();
// Detect changes in the light
sensor.onreading = () => {
details.innerHTML = sensor.illuminance;
// Read the light levels in lux
// < 50 is dark room
if (sensor.illuminance < 50) {
document.body.className = "darkLight";
} else {
document.body.className = "brightLight";
}
};
// Has an error occured?
sensor.onerror = event =>
(document.getElementById("details").innerHTML =
event.error.message);
sensor.start();
} catch (err) {
details.innerHTML = err.message;
}
} else {
details.innerHTML =
"It looks like your browser doesnt support this feature";
}
</script>
</html>```
PS* for this to work you need to run this on a https server



![Безумие обратных вызовов в javascript [JS]](https://i.imgur.com/WsjO6zJb.png)


Реакт работает не так...
Я бы посоветовал посмотреть dangerouslySetInnerHTML ссылку здесь: https://reactjs.org/docs/dom-elements.html#dangeroussetinnerhtml
И createRef ссылка здесь: https://reactjs.org/docs/refs-and-the-dom.html#creating-refs
Вот простой пример использования обоих, чтобы дать вам лучшее представление:
import React from 'react';
class App extends React.Component {
constructor(props) {
super(props);
this.detailsRef = React.createRef();
}
createMarkup() {
return { __html: 'whatever you want...' };
}
componentDidMount() {
console.info(this.detailsRef.current.innerHTML);
}
render() {
return (
<div className = "app">
<h1>Ambient Light Sensor</h1>
<p>Current Light Levels</p>
<div
ref = {this.detailsRef}
dangerouslySetInnerHTML = {this.createMarkup()}
/>
</div>
);
}
}
export default App;
Поэкспериментируйте с ним и прочитайте ссылки из официальной документации, чтобы адаптировать его к вашему конкретному варианту использования...
Никогда раньше не использовал AmbientLightSensorAPI, но попробуйте что-то вроде этого:
class App extends Component {
constructor(props) {
super(props);
this.state = {
details: ''
};
}
componentDidMount() {
if (window.AmbientLightSensor) {
try {
const sensor = new AmbientLightSensor();
sensor.onreading = () => {
this.setState({ details: sensor.illuminance });
if (sensor.illuminance < 50) {
document.body.className = 'darkLight';
} else {
document.body.className = 'brightLight';
}
};
sensor.onerror = event =>
this.setState({ details: event.error.message });
sensor.start();
} catch (err) {
this.setState({ details: err.message });
}
} else {
this.setState({
details:
'It looks like your browser doesnt support this feature'
});
}
}
render() {
return (
<div className = "app">
<h1>Ambient Light Sensor</h1>
<p>Current Light Levels</p>
<div id = "details">{this.state.details}</div>
</div>
);
}
}
@SakoBu да, вы правы, возможно, это не совсем хорошая идея ... но, поскольку у него нет доступа к ней самой по себе, и поскольку я действительно не знаю, чего он пытается достичь (у него могут быть другие компоненты и т. д.), Я не знаю, как заменить этот аспект
AmbientLightSensor не определен no-undef
Спасибо, что уделили время ^^
@IonutEugen Я как бы ожидал этой ошибки ... Я предположил, что это было локально для меня ...
Хорошо, я понял :D
Единственный рабочий способ, который я нашел, чтобы отправить файл JavaScript и запустить его is by declaring it in the index.html file inside the public folder (если вы сделали приложение с созданием приложения для реагирования)
Normally react servers you this file and it adds it's components over it.
Причина, по которой запуск скрипта внутри класса реагирования не работает (насколько мне удалось понять), заключается в том, что на самом деле там работает не реакция JavaScript, а язык, основанный на JavaScript ES6.
Хотя это означает, что большинство функций, к которым вы, возможно, привыкли, работают в нем, есть и исключения, в основном для новых функций (таких как API датчика, он довольно новый).
Это может не быть проблемой в будущем, но на данный момент я думаю, что это один из способов сделать это.
Edit * And @SakoBu's answer turned out to be the safe way of doing this
( #Change my mind meme :3 )
Не уверен, что добавление ha className в тело, подобное этому, является хорошей идеей...