asp.net 4.0 webforms - how to keep ContentPlaceHolder1_ out of client id's in a simple way?

百般思念 提交于 2020-03-20 18:35:17

问题


I'm attempting to introduce master pages to an existing webforms site that's avoided using them because of client id mangling in the past (and me not wanting to deal with the mangling and doing <% foo.ClientID %> everywhere :)

GOAL: use 'static' id values (whatever is in the server control's id attribute) except for data-bound / repeating controls which would break for those cases and therefore need suffixes or whatever to differentiate (basically, Predictable)

Now that the site migrated to ASP.NET 4.0, I first attempted to use ClientIDMode of Static (in the web.config) but that broke too many places doing repeating controls (checkboxes inside gridviews, for instance) since they all resulted with the same id.

So, I then tried Predictable (again, just in the web.config) so that the repeating controls wouldn't have conflicting id's, and it works well except that the master page content placeholder (which is indeed a naming container) is still reflecting in the resulting client id's (for instance, ContentPlaceHolder1_someCheckbox).

Certainly I could leave the web.config setting as static and then go through all the databound/repeating controls switch them to Predictable, but I'm hoping there's some easier/simpler way to get that effect without having to scatter ClientIDMode attributes in those N number of places (or extend all those databound controls with my own usercontrol that just sets clientidmode, or whatever).

I even thought of leaving web.config set to static and doing a master or basepage handler (preinit? not sure if that would work or not) that would go walk Controls with OfType<INamingContainer>() (might be a better choice on the type, but that seems like a good starting choice looking at repeater and gridview) and then set those to Predictable so I'd get static for all my 'normal' things outside of repeating controls but not have to deal with static inside things like gridview/repeater/etc.

I don't see any way to mark the content placeholder such that it 'opts out' of being included in child id's - setting the ID of the placeholder to empty/blank doesn't work as it's a required attribute :)

At that point I figured there was a better/simpler way that I was missing and decided to ask on SO :)

Edit: I thought about changing all my 'fetch by id' jquery calls from $('#foo') to fetch_by_id('foo') and then having that function return the 'right one' by checking $('#foo').length and then $('#ContentPlaceHolder1_foo').length (and maybe other patterns) or even just have it return $('#foo, #ContentPlaceHolder1_foo') (again, potentially other patterns) but changing all the places I fetch elements by id seemed pretty ugly too, and I'd like to avoid that abstraction layer if possible to do so easily :)

Edit2: WRT using jQuery selector of id$='foo':

my worry doing such a thing (although it may be more imagined than real) is when one of the id's in a page ends with another. For instance, if a page has elements with id's of 'foo' and 'barfoo' then id$='foo' will accidentally include the 'barfoo' as well. Certainly there are plenty of methods for preventing that (like suffixing with the element type, so fooCheckbox and barfooButton or whatever) but I didn't want to have to scan the existing source and/or enforce a new rule for naming.

Since not all of the controls are server controls, I can't $='_foo' either since a normal div id="foo" won't be found (and I'd rather avoid runat="server" just to mangle the name :)

another thing I considered was making a unique css class name per element and selecting on that instead (since class obviously doesn't get mangled) but it's very hacky to do so and certainly muddies things up when doing the 'real' CSS work :)


回答1:


I honestly don't know if there is an easy way of doing it, but considering you are using jQuery what I have done in the past is, I used the attribute ends with the selector method.

Since .Net appends your "static" id to the end of it's generated id, you can get that with the jquery selector $("input[id$='yourstaticid']").

I know this is not THE solution that you are looking for but it would make your 'fetch_by_id' simpler.

Hope it helps or gives you an idea at least.




回答2:


ClientIDMode = UI.ClientIDMode.Static

You have to set this in the "constructor".



来源:https://stackoverflow.com/questions/2828719/asp-net-4-0-webforms-how-to-keep-contentplaceholder1-out-of-client-ids-in-a

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!