alroyso 7 ماه پیش
والد
کامیت
738458b8cd

+ 2 - 0
app/Http/Controllers/Controller.php

@@ -126,6 +126,8 @@ class Controller extends BaseController
         return $data ?? null;
     }
 
+
+
     // 流量使用图表
     public function dataFlowChart($id, $is_node = false): array
     {

+ 12 - 0
app/Http/Controllers/UserController.php

@@ -118,14 +118,26 @@ class UserController extends Controller
         // 获取当前用户可用节点
         $nodeList = $user->nodes()->with(['labels', 'level_table'])->get();
         $onlineNode = NodeHeartbeat::recently()->distinct()->pluck('node_id')->toArray();
+        $node_txt = "";
+
+        $servers = [];
         foreach ($nodeList as $node) {
             // 节点在线状态
             $node->offline = ! in_array($node->id, $onlineNode, true);
+            //$this->getUserNodeInfo($node, $request->input('type') !== 'text');
+
+            $servers[] = $node->config($user);
+
         }
 
+        foreach ($servers as $node) {
+            $node_txt .= $this->getUserNodeInfo($node,true);
+        }
+        //var_dump($servers); die();
         return view('user.nodeList', [
             'nodesGeo' => $nodeList->pluck('name', 'geo')->toArray(),
             'nodeList' => $nodeList,
+            'node_txt' => $node_txt,
         ]);
     }
 

تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 146 - 0
public/assets/custom/jquery-qrcode/qrcode.js


تفاوت فایلی نمایش داده نمی شود زیرا این فایل بسیار بزرگ است
+ 0 - 0
public/assets/custom/jquery-qrcode/qrcode.min.js


+ 208 - 52
resources/views/user/nodeList.blade.php

@@ -6,58 +6,152 @@
     <link href="/assets/global/vendor/jvectormap/jquery-jvectormap.min.css" type="text/css" rel="stylesheet">
 @endsection
 @section('content')
-    <!-- BEGIN CONTENT BODY -->
+
     <div class="page-content container-fluid">
         <div class="row">
-            <div class="col-md-9">
-                <div class="card card-inverse card-shadow bg-white map">
-                    <div class="card-block h-450">
-                        <div class="h-p100" id="world-map"></div>
+
+    <!--        <div class="col-md-3">-->
+    <!--            <div class="row map">-->
+    <!--                <div class="col-md-12">-->
+    <!--                    <div class="card card-block p-20  bg-indigo-500">-->
+    <!--                        <div class="counter counter-lg counter-inverse">-->
+    <!--                            <div class="counter-label text-uppercase font-size-16">{{trans('user.account.level')}}</div>-->
+    <!--                            <div class="counter-number-group">-->
+    <!--                                <span class="counter-icon"><i class="icon wb-user-circle" aria-hidden="true"></i></span>-->
+    <!--                                <span class="counter-number ml-10">{{Auth::getUser()->level}}</span>-->
+    <!--                            </div>-->
+    <!--                            <div class="counter-label text-uppercase font-size-16">{{Auth::getUser()->level_name}}</div>-->
+    <!--                        </div>-->
+    <!--                    </div>-->
+    <!--                </div>-->
+                    <!--@if(Auth::getUser()->group_id)-->
+                    <!--    <div class="col-md-12">-->
+                    <!--        <div class="card card-block p-20 bg-indigo-500">-->
+                    <!--            <div class="counter counter-lg counter-inverse">-->
+                    <!--                <div class="counter-label text-uppercase font-size-16">{{trans('user.account.group')}}</div>-->
+                    <!--                <div class="counter-number-group">-->
+                    <!--                    <span class="counter-icon"><i class="icon wb-globe" aria-hidden="true"></i></span>-->
+                    <!--                    <span class="counter-number ml-10">{{Auth::getUser()->group->name}}</span>-->
+                    <!--                </div>-->
+                    <!--            </div>-->
+                    <!--        </div>-->
+                    <!--    </div>-->
+                    <!--@endif-->
+            <!--        <div class="col-md-12">-->
+            <!--            <div class="card card-block p-20 bg-indigo-500">-->
+            <!--                <div class="counter counter-lg counter-inverse">-->
+            <!--                    <div class="counter-label text-uppercase font-size-16">{{trans('user.account.speed_limit')}}</div>-->
+            <!--                    <div class="counter-number-group">-->
+            <!--                        <span class="counter-icon"><i class="icon wb-signal" aria-hidden="true"></i></span>-->
+            <!--                        <span class="counter-number ml-10">{{Auth::getUser()->speed_limit ?? trans('common.unlimited')}}</span>-->
+            <!--                    </div>-->
+            <!--                    <div class="counter-label font-size-16">Mbps</div>-->
+            <!--                </div>-->
+            <!--            </div>-->
+            <!--        </div>-->
+            <!--    </div>-->
+            <!--</div>-->
+             <h3>请复制节点链接后, 然后粘贴到软件即可。请使用我们推荐的软件!!</h3>
+
+
+
+{{--            <div class="col-xxl-3 col-xl-4 col-sm-6">--}}
+{{--                <div class="card card-inverse card-shadow bg-white node">--}}
+{{--                    <div class="card-block p-30 row">--}}
+{{--                        <div class="col-4">--}}
+{{--                            <svg class="w-p100 text-center" aria-hidden="true">--}}
+
+{{--                            </svg>--}}
+{{--                        </div>--}}
+{{--                        <div class="col-8 text-break text-right">--}}
+{{--                            <p class="font-size-20 blue-600">--}}
+{{--                                {{$node_txt}}--}}
+{{--                            </p>--}}
+{{--                            <blockquote>--}}
+{{--                            </blockquote>--}}
+
+{{--                        </div>--}}
+{{--                    </div>--}}
+{{--                </div>--}}
+{{--            </div>--}}
+
+
+            <div class="col-xxl-3 col-xl-4 col-sm-6">
+                <div class="card card-inverse card-shadow bg-white node">
+                    <div class="card-block p-30 row">
+                        <div class="col-4">
+                            <svg class="w-p100 text-center" aria-hidden="true">
+                                <!-- SVG内容 -->
+                            </svg>
+                        </div>
+                        <div class="col-8 text-break text-right">
+                            <p class="font-size-20 blue-600">
+                                {{-- {{$node_txt}} --}}
+                            </p>
+                            <blockquote>
+                            </blockquote>
+                            <!-- 按钮触发模态框 -->
+                            <button type="button" class="btn btn-primary" data-toggle="modal" data-target="#exampleModal">
+                                复制所有节点
+                            </button>
+                        </div>
                     </div>
                 </div>
             </div>
-            <div class="col-md-3">
-                <div class="row map">
-                    <div class="col-md-12">
-                        <div class="card card-block p-20  bg-indigo-500">
-                            <div class="counter counter-lg counter-inverse">
-                                <div class="counter-label text-uppercase font-size-16">{{trans('user.account.level')}}</div>
-                                <div class="counter-number-group">
-                                    <span class="counter-icon"><i class="icon wb-user-circle" aria-hidden="true"></i></span>
-                                    <span class="counter-number ml-10">{{Auth::getUser()->level}}</span>
-                                </div>
-                                <div class="counter-label text-uppercase font-size-16">{{Auth::getUser()->level_name}}</div>
-                            </div>
+
+            <!-- 模态框结构 -->
+            <div class="modal fade" id="exampleModal" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
+                <div class="modal-dialog" role="document">
+                    <div class="modal-content">
+                        <div class="modal-header">
+                            <h5 class="modal-title" id="exampleModalLabel">详细内容</h5>
+                            <button type="button" class="close" data-dismiss="modal" aria-label="Close">
+                                <span aria-hidden="true">&times;</span>
+                            </button>
+                        </div>
+                        <div class="modal-body">
+                            <!-- 这里放你想展示的内容 -->
+                            <p>
+                                <textarea id="modalContent" class="form-control" rows="12" readonly="readonly">{{$node_txt}}</textarea>
+                            </p>
+
+
+                        </div>
+                        <div class="modal-footer">
+                            <!-- 生成二维码按钮 -->
+{{--                            <button type="button" class="btn btn-primary" onclick="generateQRCode()">生成二维码</button>--}}
+                            <!-- 复制按钮 -->
+                            <button type="button" class="btn btn-primary" onclick="copyToClipboard()">一键复制</button>
+                            <button type="button" class="btn btn-secondary" data-dismiss="modal">关闭</button>
                         </div>
                     </div>
-                    @if(Auth::getUser()->group_id)
-                        <div class="col-md-12">
-                            <div class="card card-block p-20 bg-indigo-500">
-                                <div class="counter counter-lg counter-inverse">
-                                    <div class="counter-label text-uppercase font-size-16">{{trans('user.account.group')}}</div>
-                                    <div class="counter-number-group">
-                                        <span class="counter-icon"><i class="icon wb-globe" aria-hidden="true"></i></span>
-                                        <span class="counter-number ml-10">{{Auth::getUser()->group->name}}</span>
-                                    </div>
-                                </div>
-                            </div>
+                </div>
+            </div>
+
+            <!-- 模态框结构 - 显示二维码 -->
+            <div class="modal fade" id="qrModal" tabindex="-1" role="dialog" aria-labelledby="qrModalLabel" aria-hidden="true">
+                <div class="modal-dialog" role="document">
+                    <div class="modal-content">
+                        <div class="modal-header">
+                            <h5 class="modal-title" id="qrModalLabel">二维码</h5>
+                            <button type="button" class="close" data-dismiss="modal" aria-label="Close">
+                                <span aria-hidden="true">&times;</span>
+                            </button>
                         </div>
-                    @endif
-                    <div class="col-md-12">
-                        <div class="card card-block p-20 bg-indigo-500">
-                            <div class="counter counter-lg counter-inverse">
-                                <div class="counter-label text-uppercase font-size-16">{{trans('user.account.speed_limit')}}</div>
-                                <div class="counter-number-group">
-                                    <span class="counter-icon"><i class="icon wb-signal" aria-hidden="true"></i></span>
-                                    <span class="counter-number ml-10">{{Auth::getUser()->speed_limit ?? trans('common.unlimited')}}</span>
-                                </div>
-                                <div class="counter-label font-size-16">Mbps</div>
-                            </div>
+                        <div class="modal-body text-center">
+                            <!-- 显示二维码的地方 -->
+                            <div id="qrcode"></div>
+                            <img id="qrcodeImage" src="" alt="QR Code as Base64" />
+                        </div>
+                        <div class="modal-footer">
+                            <button type="button" class="btn btn-secondary" data-dismiss="modal">关闭</button>
                         </div>
                     </div>
                 </div>
             </div>
-            @foreach($nodeList as $node)
+
+        @foreach($nodeList as $node)
+
                 <div class="col-xxl-3 col-xl-4 col-sm-6">
                     <div class="card card-inverse card-shadow bg-white node">
                         <div class="card-block p-30 row">
@@ -68,11 +162,11 @@
                             </div>
                             <div class="col-8 text-break text-right">
                                 <p class="font-size-20 blue-600">
-                                    <span class="badge badge-pill up m-0 badge-default">{{$node->level_table->name}}</span>
-                                    @if($node->offline)
-                                        <i class="red-600 icon wb-warning" data-content="{{trans('user.node.unstable')}}"
-                                           data-trigger="hover" data-toggle="popover" data-placement="top"></i>
-                                    @endif
+                                    <!--<span class="badge badge-pill up m-0 badge-default">{{$node->level_table->name}}</span>-->
+                                    <!--@if($node->offline)-->
+                                    <!--    <i class="red-600 icon wb-warning" data-content="{{trans('user.node.unstable')}}"-->
+                                    <!--       data-trigger="hover" data-toggle="popover" data-placement="top"></i>-->
+                                    <!--@endif-->
                                     @if($node->traffic_rate != 1)
                                         <i class="green-600 icon wb-info-circle" data-content="{{trans('user.node.rate', ['ratio' => $node->traffic_rate])}}"
                                            data-trigger="hover" data-toggle="popover" data-placement="top"></i>
@@ -90,12 +184,12 @@
                                     <button class="btn btn-sm btn-outline-info" onclick="getInfo('{{$node->id}}','code')">
                                         <i id="code{{$node->id}}" class="icon fa-code"></i>
                                     </button>
-                                    <button class="btn btn-sm btn-outline-info" onclick="getInfo('{{$node->id}}','qrcode')">
-                                        <i id="qrcode{{$node->id}}" class="icon fa-qrcode"></i>
-                                    </button>
-                                    <button class="btn btn-sm btn-outline-info" onclick="getInfo('{{$node->id}}','text')">
-                                        <i id="text{{$node->id}}" class="icon fa-list"></i>
-                                    </button>
+                                    <!--<button class="btn btn-sm btn-outline-info" onclick="getInfo('{{$node->id}}','qrcode')">-->
+                                    <!--    <i id="qrcode{{$node->id}}" class="icon fa-qrcode"></i>-->
+                                    <!--</button>-->
+                                    <!--<button class="btn btn-sm btn-outline-info" onclick="getInfo('{{$node->id}}','text')">-->
+                                    <!--    <i id="text{{$node->id}}" class="icon fa-list"></i>-->
+                                    <!--</button>-->
                                 </p>
                             </div>
                         </div>
@@ -108,12 +202,74 @@
 @section('javascript')
     <script src="/assets/global/vendor/matchheight/jquery.matchHeight-min.js" type="text/javascript"></script>
     <script src="/assets/global/js/Plugin/matchheight.js" type="text/javascript"></script>
-    <script src="/assets/custom/jquery-qrcode/jquery.qrcode.min.js" type="text/javascript"></script>
+    <script src="/assets/custom/jquery-qrcode/qrcode.js" type="text/javascript"></script>
     <script src="/assets/global/js/Plugin/webui-popover.js" type="text/javascript"></script>
     <script src="/assets/global/vendor/jvectormap/jquery-jvectormap.min.js"></script>
     <script src="/assets/custom/maps/jquery-jvectormap-world-mill-cn.js"></script>
 
     <script type="text/javascript">
+        function copyToClipboard() {
+            var textarea = document.getElementById("modalContent");
+            textarea.select();
+            textarea.setSelectionRange(0, 99999); // 对于移动设备的选择范围
+            document.execCommand("copy");
+            alert("内容已复制到剪贴板!");
+        }
+
+        function generateQRCode() {
+            var content = document.getElementById("modalContent").value;
+
+            // 检查内容是否为空
+            if (!content || content.trim() === "") {
+                alert("内容不能为空!");
+                return;
+            }
+
+            // 对内容进行Base64编码
+            var encodedContent = btoa(content);
+
+            //console.error(encodedContent);
+
+            // 清除之前生成的二维码
+            document.getElementById("qrcode").innerHTML = "";
+
+            // 创建一个隐藏的 canvas 用于生成 Base64 URL
+            var canvas = document.createElement('canvas');
+            canvas.width = 256;
+            canvas.height = 256;
+
+            try {
+                // 生成二维码到隐藏的 canvas 中
+                var qrCode = new QRCode(canvas, {
+                    text: encodedContent,  // 使用Base64编码后的内容
+                    width: 256, // 二维码的宽度
+                    height: 256, // 二维码的高度
+                    correctLevel: QRCode.CorrectLevel.H // 使用最高的纠错级别
+                });
+
+                // 等待二维码生成后,将其转换为 Base64 URL
+                setTimeout(function() {
+                    var base64URL = canvas.toDataURL("image/png");
+
+                    // 在页面上显示Base64二维码图片
+                    var imgElement = document.getElementById("qrcodeImage");
+                    imgElement.src = base64URL;
+
+                    // 输出到控制台或进一步处理
+                    console.log(base64URL);
+                }, 500); // 等待二维码生成(延迟时间可以根据实际情况调整)
+
+            } catch (error) {
+                console.error("二维码生成失败:", error);
+                alert("二维码生成失败,请检查内容格式。");
+            }
+
+            // 关闭当前模态框
+            $('#exampleModal').modal('hide');
+
+            // 打开二维码模态框
+            $('#qrModal').modal('show');
+        }
       $(function() {
         $('#world-map').vectorMap({
           map: 'world_mill',

برخی فایل ها در این مقایسه diff نمایش داده نمی شوند زیرا تعداد فایل ها بسیار زیاد است