如何在不刷新页面的情况下持续更新PHP变量?

4
我正在制作一个网站,可以通过Morris图表显示MySQL数据库中的数据。基本上,我有一个数据库,每分钟都会得到新的测量值,并且我正在尝试在无需重新加载整个页面的情况下实时显示这些更改。我为了这个问题缩短了我的代码,但基本上我有以下内容:
PHP代码:
<?php
   while($measurement = mysqli_fetch_array($result)){
       $data += $measurement['data'];
   }
?>

而且脚本:

function data() {
        var ret = [];
        ret.push({
          y: 'Today',
          a: <?php echo $data; ?>
        });
      return ret;
    }

var graph = Morris.Bar({
        element: 'graph',
        data: data(),
        xkey: 'y',
        ykeys: ['a'],
        labels: ['random label']
    });

function update() {
      graph.setData(data());
    }

setInterval(update, 60000);

该图表随后显示在ID为“graph”的div中。问题在于更新函数不会使用新数据更新图表,因为$data没有更新。我听说可以通过某种方式创建一个PHP函数并使用Ajax持续运行它,然后让它更新我的$data变量,但我不知道如何做。
为了更新图表,我必须重新加载整个页面,使用一个meta标签每60秒刷新页面可以正常工作,但这似乎是一个糟糕的解决方案。
我还尝试将代码放在一个单独的PHP文件中,并使用以下代码运行:
var auto_updater = setInterval(
    (function () {
        $("#graph").load("data.php");
    }), 60000);

这也可以正常工作,但问题是它重新绘制了整个图表,导致我的网站滚动条疯狂跳动。我想要的是更新Morris.Bar中的数据变量,而不是整个图表。任何帮助都将不胜感激。
3个回答

6

编辑:因为你只需要一个值,所以你的json只有那个值。 尽管从技术上讲,这不是有效的json(顶层应该有一个对象),但在jquery中它可以正常工作。

PHP:(data.php)

<?php
  $data = // obtain current value of data from somewhere
  echo $data; // should be an integer
?>

JS:

$(document).ready( function () {
  var data = []; // data is empty
  var graph = Morris.Bar({
    element: 'graph',
    data: data
    labels: ['random label']
  });

  function update () {
    $.getJSON( "data.php", function (newv) {
      data.push( { x: newv, y: "Today" } ); // store new value
      graph.setData( data );                // update the graph
    });
  }

  update();
  setInterval( update, 1000 );
});

这就是全部内容了!


“让PHP在后台运行”是不可能的,您的尝试是正确的。但是,您应该加载纯数据(例如作为JSON文档),而不是加载新的HTML,然后通过JS将该数据推入现有数据集中。 使用JS从服务器获取更新的数据可以使用AJAX来完成。

例如,您可以使用$.getJSON

编辑: 完整的JS代码如下:

var initial_data = <?php echo $data; ?> // or leave this out and replace with another $.getJSON for clean code!
$(document).ready( function () {
  var graph = Morris.Bar( ... );

  setInterval( function () {
    $.getJSON( "data.php", function (data) {
      graph.setData( data );
    });
  }, 1000 );
});

PHP返回的响应应该类似于以下内容:

[
  { "x": 10, "y": 20 },
  { "x": 3, "y": 12 },
  { "x": 8, "y": 19 }
]

所以 PHP 可能看起来像这样:

[
  <?php
    // first one seperately because it can't have a leading comma - JSON is strict
    $measurement = mysqli_fetch_array($result)
    echo '{ "x": ' . $result["data"]["x"] . ', "y": ' . $result["data"]["x"] . ' }';
    while($measurement = mysqli_fetch_array($result)) {
     // no idea what data looks like, I'm assuming it has x and y properties
     echo ', { "x": ' . $result["data"]["x"] . ', "y": ' . $result["data"]["x"] . ' }';
    }
  ?>
]

谢谢您的回答,但我不确定在data.php中应该包含什么,因为我不懂JSON或如何使PHP返回这样的内容。我知道如何制作整个东西,但不知道如何只返回那些数据。我是否只需像我的帖子中的data()函数一样创建一个函数并在data.php中调用它? - dansan
只需在您的服务器上添加一个名为 data.php 的文件,该文件获取数据并按照我在第二个代码块中展示的格式进行 echo(不要返回任何 HTML,只返回 JSON 部分)。 - s-ol
我只需要将整个内容作为字符串输出吗?如何在不将它们转换为字符串的情况下输出括号? - dansan
我上传了data.php的全部内容,除了数据库连接和查询。 - s-ol
我刚意识到你只需要一个更新的值,那就是 y 值,而 x 则随时间步进。我会很快草拟出一个解决方案。 - s-ol

0
尝试将所有PHP代码放在一个单独的脚本中,并让它返回一个PHP数组中的表格(使用json_encode()函数)。
这样,您就可以使用JavaScript重新绘制表格,如下所示:
var getTableData = function(){
  $.getJSON("data.php").done(function(data){

    // code to generate html from JSON data

    $("#graph").html(tableHTML) // puts the html table into the document

    setTimeout(getTableData, 2000); // interval
  });
};
setTimeout(getTableData, 0);

我不确定你的数据格式是怎样的,所以你需要自己创建 HTML!


这可能会导致同样的延迟 - 你仍然需要重建整个DOM。 - s-ol

0

你需要使用某种ajax调用来更新服务器上的值。 此外,在更新值后,您需要将其保存在某个地方,例如数据库或缓存中,因为当PHP运行结束时,该进程会终止,并且您在PHP运行时创建的所有数据都将丢失。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接