简体   繁体   English

如何从c#ASP.net中的GridView行制作单按钮照片上传

[英]How to make a Single Button Photo Upload from a GridView row in c# ASP.net

I'm trying to accomplish a photo upload from within a row in GridView. 我正在尝试从GridView中的一行内完成照片上传。 I want details taken from my row when creating the file name. 创建文件名时,我希望从行中获取详细信息。 I have a working version of this, however it will not work across multiple browsers. 我有一个有效的版本,但是无法在多个浏览器上运行。

This currently works in, 目前适用于

Microsoft Internet Explorer Mozilla Fire Fox Microsoft Internet Explorer Mozilla Fire Fox

Where I've identified it as not working, 在我发现它不起作用的地方,

Chrome

Here's what I've written so far, 到目前为止,这是我写的

On my ASP Page 在我的ASP页面上

I've used the File Upload, however I've hidden its button and field. 我使用了文件上传,但是隐藏了它的按钮和字段。

        <asp:FileUpload id="imageupload" runat="server" Style="display: none"/>
    <asp:Button ID="btnUpload" Text="Upload" runat="server" OnClick="Upload" Style="display: none" />

My Gridview - In my Lbl template field i have a button which launches my PromptUploader method in the code behind. 我的Gridview-在我的Lbl模板字段中,我有一个按钮,可在后面的代码中启动PromptUploader方法。 This begins the process and carries out the row selection so after postback the next methods continue. 这将开始该过程并执行行选择,因此在回发之后,继续使用下一个方法。

<asp:GridView ID="LocationView" runat="server" AutoGenerateColumns="False" 
CssClass="table table-hover table-striped basepadding" GridLines="None">
      <Columns>
            <asp:TemplateField HeaderText="Product">
                <ItemTemplate>
                    <asp:Label ID="lblproduct" runat="server" Text='<%# Bind("product") %>'></asp:Label><br />
                    <asp:Label ID="lblorderh" runat="server" Text="SO:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lblorderno" runat="server" Text='<%# Bind("Order_No") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Qty">
                <ItemTemplate>
                    <asp:Label ID="lblcqty" runat="server" Text='<%# Bind("Qtycomplete") %>'></asp:Label><br />
                    <asp:Label ID="lbllineh" runat="server" Text="LNE:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lblline" runat="server" Text='<%# Bind("Line_no") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Time">
                <ItemTemplate>
                    <asp:Label ID="lbllogtime" runat="server" Text='<%# Bind("opslogtime") %>'></asp:Label><br />
                    <asp:Label ID="lbluserh" runat="server" Text="USR:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lbluser" runat="server" Text='<%# Bind("opsusername") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="LBl">
                <ItemTemplate>
                    <asp:Label ID="lbllabelno" runat="server" Text='<%# Bind("Labelno") %>'></asp:Label><br />
                    </br>                       
                    <asp:Button ID="btnimagescan" runat="server" text="Image" commandname="Select" CssClass="btn edit btn-primary" OnClick="PromptUploader"/>
                </ItemTemplate>
            </asp:TemplateField>
        </Columns>
    </asp:GridView>

For the button to work I've had to include some Javascript - (i've very little experience with it) 为了使按钮正常工作,我必须包含一些Javascript-(我对此的经验很少)

        <script type="text/javascript">
        function UploadFile(fileUpload) {
            if (fileUpload.value != '') {
                document.getElementById("<%=btnUpload.ClientID %>").click();
            }
        }
    </script>
    <script type="text/javascript">
        function importClick() {
            document.getElementById("<%=imageupload.ClientID%>").click();
        }
    </script>

In the Code behind i've added the line to trigger onchange with the fileupload box. 在后面的代码中,我添加了一行以使用fileupload框触发onchange。 This means when i select my image/file the fileuploader will trigger the next piece of javascript UploadFile(fileUpload) 这意味着当我选择我的图像/文件时,fileuploader将触发下一段javascript UploadFile(fileUpload)

protected void Page_Load(object sender, EventArgs e)
    {            
        imageupload.Attributes["onchange"] = "UploadFile(this)";
    }

The PromtUploader method. PromtUploader方法。 This adds a bool to a session so that on my postback i can (if true) register a startup script which launches my importclick() method. 这会在会话中添加一个布尔值,以便在回发时(如果为true)我可以注册一个启动脚本,该脚本启动我的importclick()方法。 I change the gridview selected index here also for row identification in next method. 我在这里也更改了gridview选择的索引,以便在下一个方法中进行行标识。

        public void PromptUploader(object sender, EventArgs e)
    {
        Button btn = (Button)sender;
        GridViewRow gvr = (GridViewRow)btn.NamingContainer;

        LocationView.SelectedIndex = gvr.RowIndex;
        _activateimport = true;
        Session["importsetting"] = _activateimport;

    }

On the PreRender Event i've added, -- This is basically a check on a bool that is set and stored in a session prior this point. 在我添加的PreRender事件上,-这基本上是对在此之前设置并存储在会话中的布尔值的检查。 If it exists it will check if its true before adding the next motion to the script manager. 如果存在,它将在将下一个动作添加到脚本管理器之前检查其是否为true。 This runs the upload() java script method. 这将运行upload()Java脚本方法。

        private bool _activateimport;

    protected void Page_PreRender(object sender, EventArgs e)
    {
        if (Session["importsetting"] != null)
        {
            _activateimport = (bool)Session["importsetting"];
            if (_activateimport)
            {
                ScriptManager.RegisterStartupScript(this, GetType(), "text", "importClick();", true);
                Session.Remove("importsetting");
            }
        }
    }

Upload Method. 上传方法。 This takes the information from the gridview and uses another method which carries over the fileupload and finishes the process. 这将从gridview中获取信息,并使用另一种方法来继承文件上传并完成该过程。 There's a resizer in this method which is configured on object creation. 此方法中有一个大小调整器,该大小调整器是在对象创建时配置的。

        public void Upload(object sender, EventArgs e)
    {
        UploadResize fileUpld = new UploadResize(1024, 768, System.Drawing.Color.Black);

        GridViewRow gvr = LocationView.SelectedRow;

        PackLabel labelClicked = new PackLabel();

        labelClicked.order_no = ((Label)gvr.FindControl("lblorderno")).Text.Trim();
        labelClicked.order_line_no = ((Label)gvr.FindControl("lblline")).Text.Trim();
        labelClicked.label_no = Convert.ToInt32(((Label)gvr.FindControl("lbllabelno")).Text.Trim());
        labelClicked.product = ((Label)gvr.FindControl("lblproduct")).Text.Trim();
        labelClicked.pack_qty = Convert.ToInt32(((Label)gvr.FindControl("lblcqty")).Text.Trim());

        fileUpld.Upload(imageupload, txtlocation.Text.Trim(), labelClicked);

        if (!fileUpld.IsUploaded)
        {
            lblstatus.Text = fileUpld.UploadError;
        }

    }

My real question is. 我的真正问题是。 Why won't this work in Chrome? 为什么在Chrome中无法使用? Is there better/more optimised way to carry out this procedure. 有没有更好/更好的方法来执行此过程。

I managed to solve my own issue here. 我设法在这里解决自己的问题。 I found that the order in which Internet Explorer and Chrome post can be slightly different. 我发现Internet Explorer和Chrome发布的顺序可能略有不同。 Chrome appeared to be posting on a button click immediately before my Javascript was completing its course. 在我的Javascript完成课程学习之前,Chrome似乎发布了一个按钮单击。 This was resolved by returning false. 这通过返回false来解决。

I've also changed my method a fair bit to reduce the necessary postbacks. 我还对我的方法进行了相当多的更改,以减少必要的回发。

My Gridview 我的Gridview

        <asp:GridView ID="LocationView" runat="server" AutoGenerateColumns="False" CssClass="table table-hover table-striped basepadding" GridLines="None" OnRowDataBound="LocationView_RowDataBound">
        <Columns>
            <asp:TemplateField HeaderText="Product">
                <ItemTemplate>
                    <asp:Label ID="lblproduct" runat="server" Text='<%# Bind("product") %>'></asp:Label><br />
                    <asp:Label ID="lblorderh" runat="server" Text="SO:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lblorderno" runat="server" Text='<%# Bind("Order_No") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Qty">
                <ItemTemplate>
                    <asp:Label ID="lblcqty" runat="server" Text='<%# Bind("Qtycomplete") %>'></asp:Label><br />
                    <asp:Label ID="lbllineh" runat="server" Text="LNE:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lblline" runat="server" Text='<%# Bind("Line_no") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="Time">
                <ItemTemplate>
                    <asp:Label ID="lbllogtime" runat="server" Text='<%# Bind("opslogtime") %>'></asp:Label><br />
                    <asp:Label ID="lbluserh" runat="server" Text="USR:" Font-Italic="True" ForeColor="#000066" Font-Size="12px"></asp:Label><br />
                    <asp:Label ID="lbluser" runat="server" Text='<%# Bind("opsusername") %>' Font-Italic="True" ForeColor="Maroon" Font-Size="12px"></asp:Label>
                </ItemTemplate>
            </asp:TemplateField>
            <asp:TemplateField HeaderText="LBl">
                <ItemTemplate>
                    <asp:Label ID="lbllabelno" runat="server" Text='<%# Bind("Labelno") %>'></asp:Label><br />
                    </br>
                    <asp:FileUpload id="imageupload" runat="server" Style="display: none"/>                      
                    <asp:ImageButton id="btnimagescan" runat="server" Text="Image" class="btn edit btn-primary" ImageUrl="~/Images/whitecamera25px.png"  />
                </ItemTemplate>
            </asp:TemplateField>
        </Columns>
    </asp:GridView>

I've configured the OnDataBond event so it can check for uploaded files to display if an image has been received or not. 我已经配置了OnDataBond事件,因此它可以检查上传的文件以显示是否已接收到图像。 Here i also add the attribute on the individual FileUpload for the onchange event to trigger my java script. 在这里,我还在onChange事件的单个FileUpload上添加了属性,以触发我的Java脚本。

The imagebutton i've added the method importClick to the onclientclick. 我已经在imagebutton中添加了importClick方法到onclientclick上。 This sends through the clientid for the fileupload so it can be found by the javascript for clicking. 这通过文件上传的clientid发送,因此可以由javascript单击找到。 originally my onclientclick event for the btnimgscan button was causing a post back on chrome and not IE. 最初,我的btnimgscan按钮的onclientclick事件导致在chrome而不是IE上发回邮件。 I resolved by adding return false; 我通过添加return false来解决; to the onclientclick script for the imagebutton. 到imagebutton的onclientclick脚本。

    protected void LocationView_RowDataBound(object sender, GridViewRowEventArgs e)
    {
        if (e.Row.RowType == DataControlRowType.DataRow)
        {
            string order_no = ((Label)e.Row.FindControl("lblorderno")).Text.Trim();
            string order_line_no = ((Label)e.Row.FindControl("lblline")).Text.Trim();
            string label_no = ((Label)e.Row.FindControl("lbllabelno")).Text.Trim();

            string imagefile = DefaultFileName + LocationDat.Location + @"\" + order_no.Trim().Replace("/", "-") +
            @"\" + order_line_no.Trim() + @"\" + label_no + ".jpg";


            FileUpload rowimageupload = (e.Row.FindControl("imageupload") as FileUpload);
            ImageButton btnimagescan = (e.Row.FindControl("btnimagescan") as ImageButton);
            Button btnstart = (e.Row.FindControl("btnstart") as Button);              
            btnimagescan.OnClientClick = "importClick('" + rowimageupload.ClientID.Trim() + "');return false;";
            rowimageupload.Attributes["onchange"] = "UploadFile();";

            try
            {
                if (File.Exists(imagefile))
                {
                    btnimagescan.ImageUrl = "~/Images/completewhite25px.png";
                }
            }
            catch (Exception Ex)
            {
                lblstatus.Text = Ex.Message;
            }

        }
    }

I've added one button on the main page. 我在主页上添加了一个按钮。 Hidden also like the FileUpload on the gridview. 隐藏也喜欢gridview上的FileUpload。

        <asp:Button ID="btnpost" OnClick="FindUpload" runat="server" Text="" Style="display: none"/>

This button triggers a method FindUpload which iterates through my gridview checking if any of the objects have a file. 该按钮触发一个方法FindUpload,该方法通过我的gridview进行迭代,检查是否有任何对象具有文件。 when found this in turn triggers the upload method. 找到后依次触发上传方法。

    public void FindUpload(object sender, EventArgs e)
    {
        if (Session["package"] != null)
        {
            foreach (GridViewRow row in LocationView.Rows)
            {
                FileUpload file = ((FileUpload)row.FindControl("imageupload"));

                if (file != null)
                {
                    if (file.HasFile)
                    {
                        Upload(file, row);
                    }
                }
            }
        }
    }

Below the Upload method has been updated to receive the objects and carry out the usual actions including conditional formatting for the button when a successful upload completes. 下方的Upload方法已更新,可以接收对象并在成功完成上传后执行常规操作,包括对按钮进行条件格式化。

    public void Upload(FileUpload file, GridViewRow gvr)
    {
        FileUpload fileupload = file;
        UploadResize fileUpld = new UploadResize(1024, 768, System.Drawing.Color.Black);

        PackLabel labelClicked = new PackLabel();

        labelClicked.order_no = ((Label)gvr.FindControl("lblorderno")).Text.Trim();
        labelClicked.order_line_no = ((Label)gvr.FindControl("lblline")).Text.Trim();
        labelClicked.label_no = Convert.ToInt32(((Label)gvr.FindControl("lbllabelno")).Text.Trim());
        labelClicked.product = ((Label)gvr.FindControl("lblproduct")).Text.Trim();
        labelClicked.pack_qty = Convert.ToInt32(((Label)gvr.FindControl("lblcqty")).Text.Trim());

        var btnImageScan = (ImageButton)gvr.FindControl("btnimagescan");

        fileUpld.Upload(fileupload,txtlocation.Text.Trim(),labelClicked);
        if (!fileUpld.IsUploaded)
        {
            lblstatus.Text = fileUpld.UploadError;
        }
        else
        {
            btnImageScan.ImageUrl = "~/Images/completewhite25px.png";
        }
    }

I changed the Javascript slightly. 我稍微更改了Javascript。 The upload method no longer checks a file exists but now activates the check on the grid for possible file upload. 上载方法不再检查文件是否存在,而是现在激活网格上的检查以进行可能的文件上载。 This is the one and only post back. 这是一次也是唯一的回发。

<script type="text/javascript">
    function importClick(ClientId)
    {
        if (ClientId != '')
        {
            document.getElementById(ClientId).click();
        }               
    }
</script>
<script type="text/javascript">
    function UploadFile()
    {
        document.getElementById("<%=btnpost.ClientID%>").click();
    }
</script>

Below are a couple of screen shots of the solution, 以下是该解决方案的几个屏幕截图,

单击之前的网格视图点击后的操作

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM